diff --git a/vendor/src/github.com/opencontainers/runc/libcontainer/cgroups/systemd/apply_systemd.go b/vendor/src/github.com/opencontainers/runc/libcontainer/cgroups/systemd/apply_systemd.go index 93300cda385fb..0e3034bdb09d5 100644 --- a/vendor/src/github.com/opencontainers/runc/libcontainer/cgroups/systemd/apply_systemd.go +++ b/vendor/src/github.com/opencontainers/runc/libcontainer/cgroups/systemd/apply_systemd.go @@ -218,49 +218,7 @@ func (m *Manager) Apply(pid int) error { return err } - if err := joinDevices(c, pid); err != nil { - return err - } - - // TODO: CpuQuota and CpuPeriod not available in systemd - // we need to manually join the cpu.cfs_quota_us and cpu.cfs_period_us - if err := joinCpu(c, pid); err != nil { - return err - } - - // TODO: MemoryReservation and MemorySwap not available in systemd - if err := joinMemory(c, pid); err != nil { - return err - } - - // we need to manually join the freezer, net_cls, net_prio and cpuset cgroup in systemd - // because it does not currently support it via the dbus api. - if err := joinFreezer(c, pid); err != nil { - return err - } - - if err := joinNetPrio(c, pid); err != nil { - return err - } - if err := joinNetCls(c, pid); err != nil { - return err - } - - if err := joinCpuset(c, pid); err != nil { - return err - } - - if err := joinHugetlb(c, pid); err != nil { - return err - } - - if err := joinPerfEvent(c, pid); err != nil { - return err - } - // FIXME: Systemd does have `BlockIODeviceWeight` property, but we got problem - // using that (at least on systemd 208, see https://github.com/opencontainers/runc/libcontainer/pull/354), - // so use fs work around for now. - if err := joinBlkio(c, pid); err != nil { + if err := joinCgroups(c, pid); err != nil { return err } @@ -329,71 +287,6 @@ func join(c *configs.Cgroup, subsystem string, pid int) (string, error) { return path, nil } -func joinCpu(c *configs.Cgroup, pid int) error { - path, err := getSubsystemPath(c, "cpu") - if err != nil && !cgroups.IsNotFound(err) { - return err - } - if c.Resources.CpuQuota != 0 { - if err = writeFile(path, "cpu.cfs_quota_us", strconv.FormatInt(c.Resources.CpuQuota, 10)); err != nil { - return err - } - } - if c.Resources.CpuPeriod != 0 { - if err = writeFile(path, "cpu.cfs_period_us", strconv.FormatInt(c.Resources.CpuPeriod, 10)); err != nil { - return err - } - } - if c.Resources.CpuRtPeriod != 0 { - if err = writeFile(path, "cpu.rt_period_us", strconv.FormatInt(c.Resources.CpuRtPeriod, 10)); err != nil { - return err - } - } - if c.Resources.CpuRtRuntime != 0 { - if err = writeFile(path, "cpu.rt_runtime_us", strconv.FormatInt(c.Resources.CpuRtRuntime, 10)); err != nil { - return err - } - } - - return nil -} - -func joinFreezer(c *configs.Cgroup, pid int) error { - path, err := join(c, "freezer", pid) - if err != nil && !cgroups.IsNotFound(err) { - return err - } - freezer, err := subsystems.Get("freezer") - if err != nil { - return err - } - return freezer.Set(path, c) -} - -func joinNetPrio(c *configs.Cgroup, pid int) error { - path, err := join(c, "net_prio", pid) - if err != nil && !cgroups.IsNotFound(err) { - return err - } - netPrio, err := subsystems.Get("net_prio") - if err != nil { - return err - } - return netPrio.Set(path, c) -} - -func joinNetCls(c *configs.Cgroup, pid int) error { - path, err := join(c, "net_cls", pid) - if err != nil && !cgroups.IsNotFound(err) { - return err - } - netcls, err := subsystems.Get("net_cls") - if err != nil { - return err - } - return netcls.Set(path, c) -} - func getSubsystemPath(c *configs.Cgroup, subsystem string) (string, error) { mountpoint, err := cgroups.FindCgroupMountpoint(subsystem) if err != nil { @@ -475,31 +368,6 @@ func getUnitName(c *configs.Cgroup) string { return fmt.Sprintf("%s-%s.scope", c.ScopePrefix, c.Name) } -// Atm we can't use the systemd device support because of two missing things: -// * Support for wildcards to allow mknod on any device -// * Support for wildcards to allow /dev/pts support -// -// The second is available in more recent systemd as "char-pts", but not in e.g. v208 which is -// in wide use. When both these are available we will be able to switch, but need to keep the old -// implementation for backwards compat. -// -// Note: we can't use systemd to set up the initial limits, and then change the cgroup -// because systemd will re-write the device settings if it needs to re-apply the cgroup context. -// This happens at least for v208 when any sibling unit is started. -func joinDevices(c *configs.Cgroup, pid int) error { - path, err := join(c, "devices", pid) - // Even if it's `not found` error, we'll return err because devices cgroup - // is hard requirement for container security. - if err != nil { - return err - } - devices, err := subsystems.Get("devices") - if err != nil { - return err - } - return devices.Set(path, c) -} - func setKernelMemory(c *configs.Cgroup) error { path, err := getSubsystemPath(c, "memory") if err != nil && !cgroups.IsNotFound(err) { @@ -520,125 +388,48 @@ func setKernelMemory(c *configs.Cgroup) error { return nil } -func joinMemory(c *configs.Cgroup, pid int) error { - path, err := getSubsystemPath(c, "memory") - if err != nil && !cgroups.IsNotFound(err) { - return err - } - - // -1 disables memoryswap - if c.Resources.MemorySwap > 0 { - err = writeFile(path, "memory.memsw.limit_in_bytes", strconv.FormatInt(c.Resources.MemorySwap, 10)) - if err != nil { - return err - } - } - if c.Resources.MemoryReservation > 0 { - err = writeFile(path, "memory.soft_limit_in_bytes", strconv.FormatInt(c.Resources.MemoryReservation, 10)) - if err != nil { - return err - } - } - if c.Resources.OomKillDisable { - if err := writeFile(path, "memory.oom_control", "1"); err != nil { - return err - } - } - - if c.Resources.MemorySwappiness >= 0 && c.Resources.MemorySwappiness <= 100 { - err = writeFile(path, "memory.swappiness", strconv.FormatInt(c.Resources.MemorySwappiness, 10)) - if err != nil { - return err - } - } else if c.Resources.MemorySwappiness == -1 { - return nil - } else { - return fmt.Errorf("invalid value:%d. valid memory swappiness range is 0-100", c.Resources.MemorySwappiness) - } - - return nil -} - -// systemd does not atm set up the cpuset controller, so we must manually -// join it. Additionally that is a very finicky controller where each -// level must have a full setup as the default for a new directory is "no cpus" -func joinCpuset(c *configs.Cgroup, pid int) error { - path, err := getSubsystemPath(c, "cpuset") - if err != nil && !cgroups.IsNotFound(err) { - return err - } - - s := &fs.CpusetGroup{} - - return s.ApplyDir(path, c, pid) -} +func joinCgroups(c *configs.Cgroup, pid int) error { + for _, sys := range subsystems { + name := sys.Name() + switch name { + case "name=systemd": + // let systemd handle this + break + case "cpuset": + path, err := getSubsystemPath(c, name) + if err != nil && !cgroups.IsNotFound(err) { + return err + } + s := &fs.CpusetGroup{} + if err := s.ApplyDir(path, c, pid); err != nil { + return err + } + break + default: + _, err := join(c, name, pid) + if err != nil { + // Even if it's `not found` error, we'll return err + // because devices cgroup is hard requirement for + // container security. + if name == "devices" { + return err + } + // For other subsystems, omit the `not found` error + // because they are optional. + if !cgroups.IsNotFound(err) { + return err + } + } + path, err := getSubsystemPath(c, name) + if err != nil && !cgroups.IsNotFound(err) { + return err + } -// `BlockIODeviceWeight` property of systemd does not work properly, and systemd -// expects device path instead of major minor numbers, which is also confusing -// for users. So we use fs work around for now. -func joinBlkio(c *configs.Cgroup, pid int) error { - path, err := getSubsystemPath(c, "blkio") - if err != nil { - return err - } - // systemd doesn't directly support this in the dbus properties - if c.Resources.BlkioLeafWeight != 0 { - if err := writeFile(path, "blkio.leaf_weight", strconv.FormatUint(uint64(c.Resources.BlkioLeafWeight), 10)); err != nil { - return err - } - } - for _, wd := range c.Resources.BlkioWeightDevice { - if err := writeFile(path, "blkio.weight_device", wd.WeightString()); err != nil { - return err - } - if err := writeFile(path, "blkio.leaf_weight_device", wd.LeafWeightString()); err != nil { - return err - } - } - for _, td := range c.Resources.BlkioThrottleReadBpsDevice { - if err := writeFile(path, "blkio.throttle.read_bps_device", td.String()); err != nil { - return err - } - } - for _, td := range c.Resources.BlkioThrottleWriteBpsDevice { - if err := writeFile(path, "blkio.throttle.write_bps_device", td.String()); err != nil { - return err - } - } - for _, td := range c.Resources.BlkioThrottleReadIOPSDevice { - if err := writeFile(path, "blkio.throttle.read_iops_device", td.String()); err != nil { - return err - } - } - for _, td := range c.Resources.BlkioThrottleWriteIOPSDevice { - if err := writeFile(path, "blkio.throttle.write_iops_device", td.String()); err != nil { - return err + if err := sys.Set(path, c); err != nil { + return err + } } } return nil } - -func joinHugetlb(c *configs.Cgroup, pid int) error { - path, err := join(c, "hugetlb", pid) - if err != nil && !cgroups.IsNotFound(err) { - return err - } - hugetlb, err := subsystems.Get("hugetlb") - if err != nil { - return err - } - return hugetlb.Set(path, c) -} - -func joinPerfEvent(c *configs.Cgroup, pid int) error { - path, err := join(c, "perf_event", pid) - if err != nil && !cgroups.IsNotFound(err) { - return err - } - perfEvent, err := subsystems.Get("perf_event") - if err != nil { - return err - } - return perfEvent.Set(path, c) -}