cgroupv2: fix CPUQuota parsing

CPUQuota can return "max PERIOD", in this case, we detect "max"
and return `-1, nil`, which for the current usecase of detecting
cpu-num from quota should be sufficient.

Signed-off-by: Daniel Dao <dqminh89@gmail.com>
This commit is contained in:
Daniel Dao
2021-11-26 10:14:08 +00:00
parent 881a271ff7
commit caf6f8d152
3 changed files with 56 additions and 2 deletions
+12 -1
View File
@@ -234,11 +234,21 @@ func (c *cgroupV2) CPUQuota() (float64, error) {
if err != nil {
return -1, err
}
data := strings.SplitN(cpuMax, " ", 2)
return parseCPUQuota(cpuMax)
}
func parseCPUQuota(cpuMax string) (float64, error) {
data := strings.SplitN(strings.TrimSpace(cpuMax), " ", 2)
if len(data) != 2 {
return -1, fmt.Errorf("invalid cpu.max data %q", cpuMax)
}
// no cpu limit if quota is max
if data[0] == "max" {
return -1, nil
}
quota, err := strconv.ParseInt(data[0], 10, 64)
if err != nil {
return -1, err
@@ -253,6 +263,7 @@ func (c *cgroupV2) CPUQuota() (float64, error) {
return -1, err
}
return float64(quota) / float64(period), nil
}
// CPUUsage returns the total CPU usage of the cgroup.
+43
View File
@@ -197,3 +197,46 @@ func TestConvertMemorySwapToCgroupV2Value(t *testing.T) {
}
}
}
func TestParseCPUQuota(t *testing.T) {
cases := []struct {
quota string
expected float64
expErr bool
}{
{
quota: "max 100000\n",
expected: -1,
},
{
quota: "10000 100000",
expected: 0.1,
},
{
quota: "20000 100000\n",
expected: 0.2,
},
{
quota: "-1",
expected: -1,
expErr: true,
},
}
for _, c := range cases {
res, err := parseCPUQuota(c.quota)
if c.expErr {
if err == nil {
t.Errorf("quota: %q, expected error, got %.2f, nil", c.quota, res)
}
continue
}
if err != nil {
t.Errorf("quota: %q, expected success, got error %s", c.quota, err)
}
if res != c.expected {
t.Errorf("quota: %q, expected %.2f, got error %.2f", c.quota, c.expected, res)
}
}
}
+1 -1
View File
@@ -777,7 +777,7 @@ func (s *Sandbox) createSandboxProcess(conf *config.Config, args *Args, startSyn
quota, err := s.CgroupJSON.Cgroup.CPUQuota()
if err != nil {
return fmt.Errorf("getting cpu qouta from cgroups: %v", err)
return fmt.Errorf("getting cpu quota from cgroups: %v", err)
}
if n := int(math.Ceil(quota)); n > 0 {
if n < minCPUs {