From 8c04b981005361daaa8a4f58e4ca7448b5459250 Mon Sep 17 00:00:00 2001 From: Kir Kolyshkin Date: Mon, 21 Feb 2022 10:34:27 -0800 Subject: [PATCH] libct/cg/sd/v2: fix ENOENT on cgroup delegation Apparently, not all files listed in /sys/kernel/cgroup/delegate must exist in every cgroup, so we should ignore ENOENT. Dot not ignore ENOENT on the directory itself though. Change cgroupFilesToChown to not return ".", and refactor it to not do any dynamic slice appending in case we're using the default built-in list of files. Fixes: 35d20c4e0 Signed-off-by: Kir Kolyshkin --- libcontainer/cgroups/systemd/v2.go | 36 +++++++++++++++++++----------- 1 file changed, 23 insertions(+), 13 deletions(-) diff --git a/libcontainer/cgroups/systemd/v2.go b/libcontainer/cgroups/systemd/v2.go index c31f0ecfd2..de0cb974d4 100644 --- a/libcontainer/cgroups/systemd/v2.go +++ b/libcontainer/cgroups/systemd/v2.go @@ -2,6 +2,7 @@ package systemd import ( "bufio" + "errors" "fmt" "math" "os" @@ -292,6 +293,12 @@ func (m *unifiedManager) Apply(pid int) error { } if c.OwnerUID != nil { + // The directory itself must be chowned. + err := os.Chown(m.path, *c.OwnerUID, -1) + if err != nil { + return err + } + filesToChown, err := cgroupFilesToChown() if err != nil { return err @@ -299,7 +306,8 @@ func (m *unifiedManager) Apply(pid int) error { for _, v := range filesToChown { err := os.Chown(m.path+"/"+v, *c.OwnerUID, -1) - if err != nil { + // Some files might not be present. + if err != nil && !errors.Is(err, os.ErrNotExist) { return err } } @@ -312,21 +320,23 @@ func (m *unifiedManager) Apply(pid int) error { // uid in /sys/kernel/cgroup/delegate. If the file is not present // (Linux < 4.15), use the initial values mentioned in cgroups(7). func cgroupFilesToChown() ([]string, error) { - filesToChown := []string{"."} // the directory itself must be chowned const cgroupDelegateFile = "/sys/kernel/cgroup/delegate" + f, err := os.Open(cgroupDelegateFile) - if err == nil { - defer f.Close() - scanner := bufio.NewScanner(f) - for scanner.Scan() { - filesToChown = append(filesToChown, scanner.Text()) - } - if err := scanner.Err(); err != nil { - return nil, fmt.Errorf("error reading %s: %w", cgroupDelegateFile, err) - } - } else { - filesToChown = append(filesToChown, "cgroup.procs", "cgroup.subtree_control", "cgroup.threads") + if err != nil { + return []string{"cgroup.procs", "cgroup.subtree_control", "cgroup.threads"}, nil } + defer f.Close() + + filesToChown := []string{} + scanner := bufio.NewScanner(f) + for scanner.Scan() { + filesToChown = append(filesToChown, scanner.Text()) + } + if err := scanner.Err(); err != nil { + return nil, fmt.Errorf("error reading %s: %w", cgroupDelegateFile, err) + } + return filesToChown, nil }