From 35784a3e6af802577a1145ea1302fb0476ae71e4 Mon Sep 17 00:00:00 2001 From: lifubang Date: Fri, 18 Feb 2022 08:18:27 +0800 Subject: [PATCH] ensure the path is a sub-cgroup path Signed-off-by: lifubang (cherry picked from commit 01f00e1fd5635e1399e35b1dcfbe600dedad1ee6) Signed-off-by: Kir Kolyshkin --- libcontainer/container_linux.go | 12 ++++++++++-- tests/integration/exec.bats | 10 ++++++++++ 2 files changed, 20 insertions(+), 2 deletions(-) diff --git a/libcontainer/container_linux.go b/libcontainer/container_linux.go index f6877b7429f..9df830d8cdb 100644 --- a/libcontainer/container_linux.go +++ b/libcontainer/container_linux.go @@ -636,7 +636,11 @@ func (c *linuxContainer) newSetnsProcess(p *Process, cmd *exec.Cmd, messageSockP // cgroup v1: using the same path for all controllers. // cgroup v2: the only possible way. for k := range proc.cgroupPaths { - proc.cgroupPaths[k] = path.Join(proc.cgroupPaths[k], add) + subPath := path.Join(proc.cgroupPaths[k], add) + if !strings.HasPrefix(subPath, proc.cgroupPaths[k]) { + return nil, fmt.Errorf("%s is not a sub cgroup path", add) + } + proc.cgroupPaths[k] = subPath } // cgroup v2: do not try to join init process's cgroup // as a fallback (see (*setnsProcess).start). @@ -645,7 +649,11 @@ func (c *linuxContainer) newSetnsProcess(p *Process, cmd *exec.Cmd, messageSockP // Per-controller paths. for ctrl, add := range p.SubCgroupPaths { if val, ok := proc.cgroupPaths[ctrl]; ok { - proc.cgroupPaths[ctrl] = path.Join(val, add) + subPath := path.Join(val, add) + if !strings.HasPrefix(subPath, val) { + return nil, fmt.Errorf("%s is not a sub cgroup path", add) + } + proc.cgroupPaths[ctrl] = subPath } else { return nil, fmt.Errorf("unknown controller %s in SubCgroupPaths", ctrl) } diff --git a/tests/integration/exec.bats b/tests/integration/exec.bats index 24444d1ec1c..140cd181011 100644 --- a/tests/integration/exec.bats +++ b/tests/integration/exec.bats @@ -197,6 +197,11 @@ function check_exec_debug() { __runc run -d --console-socket "$CONSOLE_SOCKET" test_busybox testcontainer test_busybox running + # Check we can't join parent cgroup. + runc exec --cgroup ".." test_busybox cat /proc/self/cgroup + [ "$status" -ne 0 ] + [[ "$output" == *" .. is not a sub cgroup path"* ]] + # Check we can't join non-existing subcgroup. runc exec --cgroup nonexistent test_busybox cat /proc/self/cgroup [ "$status" -ne 0 ] @@ -243,6 +248,11 @@ function check_exec_debug() { __runc run -d --console-socket "$CONSOLE_SOCKET" test_busybox testcontainer test_busybox running + # Check we can't join parent cgroup. + runc exec --cgroup ".." test_busybox cat /proc/self/cgroup + [ "$status" -ne 0 ] + [[ "$output" == *" .. is not a sub cgroup path"* ]] + # Check we can't join non-existing subcgroup. runc exec --cgroup nonexistent test_busybox cat /proc/self/cgroup [ "$status" -ne 0 ]