Commit de055b79 authored by Tycho Andersen's avatar Tycho Andersen Committed by Pavel Emelyanov

cg: use one path style throughout cg restore code

This commit is in preparation for the (hopefully last :) restore special cpuset
patch.

Previously, we installed the cgroup service fd after calling
prepare_cgroup_dirs, which meant that we had to carry around the temporary
directory name in order to put things in the right place. The
restore_cgroup_prop function uses the cg service fd instead of carrying around
the full path. This means that we can't sue restore_cgroup_prop, without first
sanitizing the path. Instead, we install the service fd before calling
prepare_cgroup_dirs, and all the code just references that instead of carrying
around the temporary path.
Signed-off-by: 's avatarTycho Andersen <tycho.andersen@canonical.com>
Signed-off-by: 's avatarPavel Emelyanov <xemul@parallels.com>
parent 25e1997f
...@@ -1153,10 +1153,12 @@ static int prepare_cgroup_dirs(char *paux, size_t off, CgroupDirEntry **ents, si ...@@ -1153,10 +1153,12 @@ static int prepare_cgroup_dirs(char *paux, size_t off, CgroupDirEntry **ents, si
{ {
size_t i; size_t i;
CgroupDirEntry *e; CgroupDirEntry *e;
int cg = get_service_fd(CGROUP_YARD);
for (i = 0; i < n_ents; i++) { for (i = 0; i < n_ents; i++) {
size_t off2 = off; size_t off2 = off;
e = ents[i]; e = ents[i];
struct stat st;
off2 += sprintf(paux + off, "/%s", e->dir_name); off2 += sprintf(paux + off, "/%s", e->dir_name);
...@@ -1165,12 +1167,13 @@ static int prepare_cgroup_dirs(char *paux, size_t off, CgroupDirEntry **ents, si ...@@ -1165,12 +1167,13 @@ static int prepare_cgroup_dirs(char *paux, size_t off, CgroupDirEntry **ents, si
* it does exist, prevent us from overwriting the properties * it does exist, prevent us from overwriting the properties
* later by removing the CgroupDirEntry's properties. * later by removing the CgroupDirEntry's properties.
*/ */
if (access(paux, F_OK) < 0) { if (fstatat(cg, paux, &st, 0) < 0) {
if (errno != ENOENT) { if (errno != ENOENT) {
pr_perror("Failed accessing file %s", paux); pr_perror("Failed accessing file %s", paux);
return -1; return -1;
} }
if (mkdirp(paux)) {
if (mkdirpat(cg, paux)) {
pr_perror("Can't make cgroup dir %s", paux); pr_perror("Can't make cgroup dir %s", paux);
return -1; return -1;
} }
...@@ -1211,7 +1214,7 @@ static int prepare_cgroup_dirs(char *paux, size_t off, CgroupDirEntry **ents, si ...@@ -1211,7 +1214,7 @@ static int prepare_cgroup_dirs(char *paux, size_t off, CgroupDirEntry **ents, si
static int prepare_cgroup_sfd(CgroupEntry *ce) static int prepare_cgroup_sfd(CgroupEntry *ce)
{ {
int off, i; int off, i, ret;
char paux[PATH_MAX]; char paux[PATH_MAX];
pr_info("Preparing cgroups yard\n"); pr_info("Preparing cgroups yard\n");
...@@ -1238,11 +1241,24 @@ static int prepare_cgroup_sfd(CgroupEntry *ce) ...@@ -1238,11 +1241,24 @@ static int prepare_cgroup_sfd(CgroupEntry *ce)
goto err; goto err;
} }
pr_debug("Opening %s as cg yard\n", cg_yard);
i = open(cg_yard, O_DIRECTORY);
if (i < 0) {
pr_perror("Can't open cgyard");
goto err;
}
ret = install_service_fd(CGROUP_YARD, i);
close(i);
if (ret < 0)
goto err;
paux[off++] = '/'; paux[off++] = '/';
for (i = 0; i < ce->n_controllers; i++) { for (i = 0; i < ce->n_controllers; i++) {
int ctl_off = off; int ctl_off = off, yard_off;
char opt[128]; char opt[128], *yard;
CgControllerEntry *ctrl = ce->controllers[i]; CgControllerEntry *ctrl = ce->controllers[i];
if (ctrl->n_cnames < 1) { if (ctrl->n_cnames < 1) {
...@@ -1265,24 +1281,16 @@ static int prepare_cgroup_sfd(CgroupEntry *ce) ...@@ -1265,24 +1281,16 @@ static int prepare_cgroup_sfd(CgroupEntry *ce)
goto err; goto err;
} }
/* We skip over the .criu.cgyard.XXXXXX/, since those will be
* referred to by the cg yard service fd. */
yard = paux + strlen(cg_yard) + 1;
yard_off = ctl_off - (strlen(cg_yard) + 1);
if (opts.manage_cgroups && if (opts.manage_cgroups &&
prepare_cgroup_dirs(paux, ctl_off, ctrl->dirs, ctrl->n_dirs)) prepare_cgroup_dirs(yard, yard_off, ctrl->dirs, ctrl->n_dirs))
goto err; goto err;
} }
pr_debug("Opening %s as cg yard\n", cg_yard);
i = open(cg_yard, O_DIRECTORY);
if (i < 0) {
pr_perror("Can't open cgyard");
goto err;
}
off = install_service_fd(CGROUP_YARD, i);
close(i);
if (off < 0)
goto err;
return 0; return 0;
err: err:
......
...@@ -212,7 +212,7 @@ static inline bool strstartswith(const char *str, const char *sub) ...@@ -212,7 +212,7 @@ static inline bool strstartswith(const char *str, const char *sub)
/* /*
* mkdir -p * mkdir -p
*/ */
int mkdirp(const char *path); int mkdirpat(int fd, const char *path);
/* /*
* Tests whether a path is a prefix of another path. This is different than * Tests whether a path is a prefix of another path. This is different than
......
...@@ -687,7 +687,7 @@ struct vma_area *alloc_vma_area(void) ...@@ -687,7 +687,7 @@ struct vma_area *alloc_vma_area(void)
return p; return p;
} }
int mkdirp(const char *path) int mkdirpat(int fd, const char *path)
{ {
size_t i; size_t i;
char made_path[PATH_MAX], *pos; char made_path[PATH_MAX], *pos;
...@@ -707,7 +707,7 @@ int mkdirp(const char *path) ...@@ -707,7 +707,7 @@ int mkdirp(const char *path)
pos = strchr(made_path + i, '/'); pos = strchr(made_path + i, '/');
if (pos) if (pos)
*pos = '\0'; *pos = '\0';
if (mkdir(made_path, 0755) < 0 && errno != EEXIST) { if (mkdirat(fd, made_path, 0755) < 0 && errno != EEXIST) {
pr_perror("couldn't mkdirpat directory %s", made_path); pr_perror("couldn't mkdirpat directory %s", made_path);
return -1; return -1;
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment