From e7b209d90f7855614415d020940396ae3c719cdc Mon Sep 17 00:00:00 2001 From: Kevin Maris Date: Mon, 13 Jul 2026 16:08:50 -0600 Subject: [PATCH] update: fix --cpus writing cpuset instead of quota/period The `--cpus` flag was incorrectly assigning opts.CpusetCpus to the CPU Cpus (cpuset) field. Persist the converted quota and period instead, matching how --cpu-quota and --cpu-period are applied. test: run update --cpus subtest against Docker The test-wide require.Not(nerdtest.Docker) prevented the --cpus subtest from running. Moved the docker skipping down to the subtests that need it so the --cpus subtest will run. The cpus subtest also is changed to verify against the container cgroup files but now requires cgroup v2. Closes #5066 Signed-off-by: Kevin Maris --- cmd/nerdctl/container/container_update.go | 7 +++---- .../container/container_update_linux_test.go | 14 +++++++++++++- 2 files changed, 16 insertions(+), 5 deletions(-) diff --git a/cmd/nerdctl/container/container_update.go b/cmd/nerdctl/container/container_update.go index 51240b87d24..507e051c3fa 100644 --- a/cmd/nerdctl/container/container_update.go +++ b/cmd/nerdctl/container/container_update.go @@ -295,10 +295,9 @@ func updateContainer(ctx context.Context, client *containerd.Client, id string, spec.Linux.Resources.CPU.Period = &opts.CPUPeriod } } - if cmd.Flags().Changed("cpus") { - if spec.Linux.Resources.CPU.Cpus != opts.CpusetCpus { - spec.Linux.Resources.CPU.Cpus = opts.CpusetCpus - } + if cmd.Flags().Changed("cpus") && opts.CPUQuota != -1 && opts.CPUPeriod != 0 { + spec.Linux.Resources.CPU.Quota = &opts.CPUQuota + spec.Linux.Resources.CPU.Period = &opts.CPUPeriod } if cmd.Flags().Changed("cpuset-mems") { if spec.Linux.Resources.CPU.Mems != opts.CpusetMems { diff --git a/cmd/nerdctl/container/container_update_linux_test.go b/cmd/nerdctl/container/container_update_linux_test.go index f51b277bbaf..93be65076ef 100644 --- a/cmd/nerdctl/container/container_update_linux_test.go +++ b/cmd/nerdctl/container/container_update_linux_test.go @@ -30,7 +30,6 @@ import ( func TestUpdateContainer(t *testing.T) { testCase := nerdtest.Setup() - testCase.Require = require.Not(nerdtest.Docker) testCase.Setup = func(data test.Data, helpers test.Helpers) { containerName := testutil.Identifier(t) @@ -48,6 +47,7 @@ func TestUpdateContainer(t *testing.T) { { Description: "should fail on unsupported restart policy value", NoParallel: true, + Require: require.Not(nerdtest.Docker), Command: func(data test.Data, helpers test.Helpers) test.TestableCommand { containerName := data.Labels().Get("containerName") return helpers.Command("update", "--memory", "999999999", "--restart", "123", containerName) @@ -57,12 +57,24 @@ func TestUpdateContainer(t *testing.T) { { Description: "should not update memory in inspect", NoParallel: true, + Require: require.Not(nerdtest.Docker), Command: func(data test.Data, helpers test.Helpers) test.TestableCommand { containerName := data.Labels().Get("containerName") return helpers.Command("inspect", "--mode=native", containerName) }, Expected: test.Expects(expect.ExitCodeSuccess, nil, expect.DoesNotContain(`"limit": 999999999,`)), }, + { + Description: "should persist the quota and period converted from --cpus", + NoParallel: true, + Require: nerdtest.CGroupV2, + Command: func(data test.Data, helpers test.Helpers) test.TestableCommand { + containerName := data.Labels().Get("containerName") + helpers.Ensure("update", "--cpus", "0.5", containerName) + return helpers.Command("exec", containerName, "cat", "/sys/fs/cgroup/cpu.max") + }, + Expected: test.Expects(expect.ExitCodeSuccess, nil, expect.Contains("50000 100000")), + }, } testCase.Run(t)