From b96c4046a8db538f0a341ff01126c814a8da3783 Mon Sep 17 00:00:00 2001 From: Tobi Knaup Date: Thu, 23 Apr 2015 17:07:52 -0700 Subject: [PATCH] Add --cgroup_root flag to Kubelet to set the parent cgroup for all pods. Implements #6991. --- cmd/kubelet/app/server.go | 9 ++++++++- pkg/kubelet/container/runtime.go | 2 ++ pkg/kubelet/dockertools/manager.go | 3 +++ pkg/kubelet/kubelet.go | 12 +++++++++--- 4 files changed, 22 insertions(+), 4 deletions(-) diff --git a/cmd/kubelet/app/server.go b/cmd/kubelet/app/server.go index baac8510fe..7d034c65fc 100644 --- a/cmd/kubelet/app/server.go +++ b/cmd/kubelet/app/server.go @@ -99,6 +99,7 @@ type KubeletServer struct { CertDirectory string NodeStatusUpdateFrequency time.Duration ResourceContainer string + CgroupRoot string // Flags intended for testing @@ -151,6 +152,7 @@ func NewKubeletServer() *KubeletServer { CertDirectory: "/var/run/kubernetes", NodeStatusUpdateFrequency: 10 * time.Second, ResourceContainer: "/kubelet", + CgroupRoot: "", } } @@ -202,6 +204,7 @@ func (s *KubeletServer) AddFlags(fs *pflag.FlagSet) { fs.StringVar(&s.CloudProvider, "cloud-provider", s.CloudProvider, "The provider for cloud services. Empty string for no provider.") fs.StringVar(&s.CloudConfigFile, "cloud-config", s.CloudConfigFile, "The path to the cloud provider configuration file. Empty string for no configuration file.") fs.StringVar(&s.ResourceContainer, "resource-container", s.ResourceContainer, "Absolute name of the resource-only container to create and run the Kubelet in (Default: /kubelet).") + fs.StringVar(&s.CgroupRoot, "cgroup_root", s.CgroupRoot, "Optional root cgroup to use for pods. This is handled by the container runtime on a best effort basis. Default: '', which means use the container runtime default.") // Flags intended for testing, not recommended used in production environments. fs.BoolVar(&s.ReallyCrashForTesting, "really-crash-for-testing", s.ReallyCrashForTesting, "If true, when panics occur crash. Intended for testing.") @@ -301,6 +304,7 @@ func (s *KubeletServer) Run(_ []string) error { Cloud: cloud, NodeStatusUpdateFrequency: s.NodeStatusUpdateFrequency, ResourceContainer: s.ResourceContainer, + CgroupRoot: s.CgroupRoot, } RunKubelet(&kcfg, nil) @@ -409,6 +413,7 @@ func SimpleKubelet(client *client.Client, NodeStatusUpdateFrequency: 10 * time.Second, ResourceContainer: "/kubelet", OSInterface: osInterface, + CgroupRoot: "", } return &kcfg } @@ -536,6 +541,7 @@ type KubeletConfig struct { NodeStatusUpdateFrequency time.Duration ResourceContainer string OSInterface kubecontainer.OSInterface + CgroupRoot string } func createAndInitKubelet(kc *KubeletConfig) (k KubeletBootstrap, pc *config.PodConfig, err error) { @@ -580,7 +586,8 @@ func createAndInitKubelet(kc *KubeletConfig) (k KubeletBootstrap, pc *config.Pod kc.Cloud, kc.NodeStatusUpdateFrequency, kc.ResourceContainer, - kc.OSInterface) + kc.OSInterface, + kc.CgroupRoot) if err != nil { return nil, nil, err diff --git a/pkg/kubelet/container/runtime.go b/pkg/kubelet/container/runtime.go index c322569deb..710475f8e7 100644 --- a/pkg/kubelet/container/runtime.go +++ b/pkg/kubelet/container/runtime.go @@ -201,6 +201,8 @@ type RunContainerOptions struct { // into docker's container runtime. NetMode string IpcMode string + // The parent cgroup to pass to Docker + CgroupParent string } type Pods []*Pod diff --git a/pkg/kubelet/dockertools/manager.go b/pkg/kubelet/dockertools/manager.go index 780300b350..e056a53391 100644 --- a/pkg/kubelet/dockertools/manager.go +++ b/pkg/kubelet/dockertools/manager.go @@ -556,6 +556,9 @@ func (dm *DockerManager) runContainer(pod *api.Pod, container *api.Container, op if len(opts.DNSSearch) > 0 { hc.DNSSearch = opts.DNSSearch } + if len(opts.CgroupParent) > 0 { + hc.CgroupParent = opts.CgroupParent + } if err = dm.client.StartContainer(dockerContainer.ID, hc); err != nil { if ref != nil { diff --git a/pkg/kubelet/kubelet.go b/pkg/kubelet/kubelet.go index a0d2ca0753..a615577fb5 100644 --- a/pkg/kubelet/kubelet.go +++ b/pkg/kubelet/kubelet.go @@ -123,7 +123,8 @@ func NewMainKubelet( cloud cloudprovider.Interface, nodeStatusUpdateFrequency time.Duration, resourceContainer string, - osInterface kubecontainer.OSInterface) (*Kubelet, error) { + osInterface kubecontainer.OSInterface, + cgroupRoot string) (*Kubelet, error) { if rootDirectory == "" { return nil, fmt.Errorf("invalid root directory %q", rootDirectory) } @@ -236,6 +237,7 @@ func NewMainKubelet( os: osInterface, oomWatcher: oomWatcher, runtimeHooks: newKubeletRuntimeHooks(recorder), + cgroupRoot: cgroupRoot, } if plug, err := network.InitNetworkPlugin(networkPlugins, networkPluginName, &networkHost{klet}); err != nil { @@ -411,6 +413,9 @@ type Kubelet struct { // TODO(vmarmol): Remove this when we only have to inject the hooks into the runtimes. // Hooks injected into the container runtime. runtimeHooks kubecontainer.RuntimeHooks + + // If non-empty, pass this to the container runtime as the root cgroup. + cgroupRoot string } // getRootDir returns the full path to the directory under which kubelet can @@ -659,8 +664,9 @@ func makeBinds(container *api.Container, podVolumes volumeMap) (binds []string) func (kl *Kubelet) GenerateRunContainerOptions(pod *api.Pod, container *api.Container, netMode, ipcMode string) (*kubecontainer.RunContainerOptions, error) { var err error opts := &kubecontainer.RunContainerOptions{ - NetMode: netMode, - IpcMode: ipcMode, + NetMode: netMode, + IpcMode: ipcMode, + CgroupParent: kl.cgroupRoot, } vol, ok := kl.volumeManager.GetVolumes(pod.UID)