From f7d1401a6998bf2036608e049e858ce174651087 Mon Sep 17 00:00:00 2001 From: Mrunal Patel Date: Fri, 25 Sep 2015 13:47:31 -0400 Subject: [PATCH] Add validation for sysctl /proc/sys isn't completely namespaced and only some properties are allowed per linux namespace. Signed-off-by: Mrunal Patel --- libcontainer/configs/validate/config.go | 45 +++++++++++++++++++++++++ 1 file changed, 45 insertions(+) diff --git a/libcontainer/configs/validate/config.go b/libcontainer/configs/validate/config.go index 848a67c3..e155ca12 100644 --- a/libcontainer/configs/validate/config.go +++ b/libcontainer/configs/validate/config.go @@ -4,6 +4,7 @@ import ( "fmt" "os" "path/filepath" + "strings" "github.com/opencontainers/runc/libcontainer/configs" ) @@ -35,6 +36,9 @@ func (v *ConfigValidator) Validate(config *configs.Config) error { if err := v.usernamespace(config); err != nil { return err } + if err := v.sysctl(config); err != nil { + return err + } return nil } @@ -91,3 +95,44 @@ func (v *ConfigValidator) usernamespace(config *configs.Config) error { } return nil } + +// sysctl validates that the specified sysctl keys are valid or not. +// /proc/sys isn't completely namespaced and depending on which namespaces +// are specified, a subset of sysctls are permitted. +func (v *ConfigValidator) sysctl(config *configs.Config) error { + validSysctlPrefixes := []string{} + validSysctlMap := make(map[string]bool) + if config.Namespaces.Contains(configs.NEWNET) { + validSysctlPrefixes = append(validSysctlPrefixes, "net.") + } + if config.Namespaces.Contains(configs.NEWIPC) { + validSysctlPrefixes = append(validSysctlPrefixes, "fs.mqueue.") + validSysctlMap = map[string]bool{ + "kernel.msgmax": true, + "kernel.msgmnb": true, + "kernel.msgmni": true, + "kernel.sem": true, + "kernel.shmall": true, + "kernel.shmmax": true, + "kernel.shmmni": true, + "kernel.shm_rmid_forced": true, + } + } + for s := range config.Sysctl { + if validSysctlMap[s] { + continue + } + valid := false + for _, vp := range validSysctlPrefixes { + if strings.HasPrefix(s, vp) { + valid = true + break + } + } + if !valid { + return fmt.Errorf("sysctl %q is not permitted in the config", s) + } + } + + return nil +}