If the ns_cgroup does not exist, we use the clone_children feature.
Everytime a cgroup is created, we set this compatibility flag and we create
the cgroup manually and add the child task to the cgroup.

Signed-off-by: Daniel Lezcano <daniel.lezc...@free.fr>
---
 src/lxc/cgroup.c |   75 +++++++++++++++++++++++++++++++++++++++++++++++++++++-
 1 files changed, 74 insertions(+), 1 deletions(-)

diff --git a/src/lxc/cgroup.c b/src/lxc/cgroup.c
index b711c64..1c603fc 100644
--- a/src/lxc/cgroup.c
+++ b/src/lxc/cgroup.c
@@ -101,10 +101,56 @@ int lxc_rename_nsgroup(const char *mnt, const char *name, 
pid_t pid)
        return 0;
 }
 
+static int cgroup_enable_clone_children(const char *path)
+{
+       FILE *f;
+       int ret = 0;
+
+       f = fopen(path, "w");
+       if (!f) {
+               SYSERROR("failed to open '%s'", path);
+               return -1;
+       }
+
+       if (fprintf(f, "1") < 1) {
+               ERROR("failed to write flag to '%s'", path);
+               ret = -1;
+       }
+
+       fclose(f);
+
+       return ret;
+}
+
+static int cgroup_attach(const char *path, pid_t pid)
+{
+       FILE *f;
+       char tasks[MAXPATHLEN];
+       int ret = 0;
+
+       snprintf(tasks, MAXPATHLEN, "%s/tasks", path);
+
+       f = fopen(tasks, "w");
+       if (!f) {
+               SYSERROR("failed to open '%s'", tasks);
+               return -1;
+       }
+
+       if (fprintf(f, "%d", pid) <= 0) {
+               SYSERROR("failed to write pid '%d' to '%s'", pid, tasks);
+               ret = -1;
+       }
+
+       fclose(f);
+
+       return ret;
+}
+
 int lxc_cgroup_create(const char *name, pid_t pid)
 {
        char cgmnt[MAXPATHLEN];
        char cgname[MAXPATHLEN];
+       char clonechild[MAXPATHLEN];
 
        if (get_cgroup_mount(MTAB, cgmnt)) {
                ERROR("cgroup is not mounted");
@@ -122,7 +168,34 @@ int lxc_cgroup_create(const char *name, pid_t pid)
                return -1;
        }
 
-       return lxc_rename_nsgroup(cgmnt, cgname, pid);
+       snprintf(clonechild, MAXPATHLEN, "%s/cgroup.clone_children", cgmnt);
+
+       /* we check if the kernel has ns_cgroup or clone_children */
+       if (access(clonechild, F_OK)) {
+               WARN("using deprecated ns_cgroup");
+               return lxc_rename_nsgroup(cgmnt, cgname, pid);
+       }
+
+       /* we enable the clone_children flag of the cgroup */
+       if (cgroup_enable_clone_children(clonechild)) {
+               SYSERROR("failed to enable 'clone_children flag");
+               return -1;
+       }
+
+       /* Let's create the cgroup */
+       if (mkdir(cgname, 0700)) {
+               SYSERROR("failed to create '%s' directory", cgname);
+               return -1;
+       }
+
+       /* Let's add the pid to the 'tasks' file */
+       if (cgroup_attach(cgname, pid)) {
+               SYSERROR("failed to attach pid '%d' to '%s'", pid, cgname);
+               rmdir(cgname);
+               return -1;
+       }
+
+       return 0;
 }
 
 int lxc_cgroup_destroy(const char *name)
-- 
1.7.0.4


------------------------------------------------------------------------------
Lotusphere 2011
Register now for Lotusphere 2011 and learn how
to connect the dots, take your collaborative environment
to the next level, and enter the era of Social Business.
http://p.sf.net/sfu/lotusphere-d2d
_______________________________________________
Lxc-devel mailing list
Lxc-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/lxc-devel

Reply via email to