lxccontainer: use thread-safe open() + write()

parent d630991d
...@@ -622,7 +622,7 @@ copy_parent: ...@@ -622,7 +622,7 @@ copy_parent:
*lastslash = oldv; *lastslash = oldv;
free(fpath); free(fpath);
fpath = must_make_path(path, "cpuset.cpus", NULL); fpath = must_make_path(path, "cpuset.cpus", NULL);
ret = lxc_write_to_file(fpath, cpulist, strlen(cpulist), false); ret = lxc_write_to_file(fpath, cpulist, strlen(cpulist), false, 0666);
if (ret < 0) { if (ret < 0) {
SYSERROR("Failed to write cpu list to \"%s\"", fpath); SYSERROR("Failed to write cpu list to \"%s\"", fpath);
goto on_error; goto on_error;
...@@ -673,7 +673,7 @@ static bool copy_parent_file(char *path, char *file) ...@@ -673,7 +673,7 @@ static bool copy_parent_file(char *path, char *file)
*lastslash = oldv; *lastslash = oldv;
fpath = must_make_path(path, file, NULL); fpath = must_make_path(path, file, NULL);
ret = lxc_write_to_file(fpath, value, len, false); ret = lxc_write_to_file(fpath, value, len, false, 0666);
if (ret < 0) if (ret < 0)
SYSERROR("Failed to write \"%s\" to file \"%s\"", value, fpath); SYSERROR("Failed to write \"%s\" to file \"%s\"", value, fpath);
free(fpath); free(fpath);
...@@ -762,7 +762,7 @@ static bool cg_legacy_handle_cpuset_hierarchy(struct hierarchy *h, char *cgname) ...@@ -762,7 +762,7 @@ static bool cg_legacy_handle_cpuset_hierarchy(struct hierarchy *h, char *cgname)
} }
free(cgpath); free(cgpath);
ret = lxc_write_to_file(clonechildrenpath, "1", 1, false); ret = lxc_write_to_file(clonechildrenpath, "1", 1, false, 0666);
if (ret < 0) { if (ret < 0) {
/* Set clone_children so children inherit our settings */ /* Set clone_children so children inherit our settings */
SYSERROR("Failed to write 1 to \"%s\"", clonechildrenpath); SYSERROR("Failed to write 1 to \"%s\"", clonechildrenpath);
...@@ -1712,7 +1712,7 @@ static bool cg_unified_create_cgroup(struct hierarchy *h, char *cgname) ...@@ -1712,7 +1712,7 @@ static bool cg_unified_create_cgroup(struct hierarchy *h, char *cgname)
cgroup = must_append_path(cgroup, parts[i], NULL); cgroup = must_append_path(cgroup, parts[i], NULL);
target = must_make_path(cgroup, "cgroup.subtree_control", NULL); target = must_make_path(cgroup, "cgroup.subtree_control", NULL);
ret = lxc_write_to_file(target, add_controllers, full_len, false); ret = lxc_write_to_file(target, add_controllers, full_len, false, 0666);
free(target); free(target);
if (ret < 0) { if (ret < 0) {
SYSERROR("Could not enable \"%s\" controllers in the " SYSERROR("Could not enable \"%s\" controllers in the "
...@@ -1858,7 +1858,7 @@ static bool cgfsng_enter(void *hdata, pid_t pid) ...@@ -1858,7 +1858,7 @@ static bool cgfsng_enter(void *hdata, pid_t pid)
fullpath = must_make_path(hierarchies[i]->fullcgpath, fullpath = must_make_path(hierarchies[i]->fullcgpath,
"cgroup.procs", NULL); "cgroup.procs", NULL);
ret = lxc_write_to_file(fullpath, pidstr, len, false); ret = lxc_write_to_file(fullpath, pidstr, len, false, 0666);
if (ret != 0) { if (ret != 0) {
SYSERROR("Failed to enter cgroup \"%s\"", fullpath); SYSERROR("Failed to enter cgroup \"%s\"", fullpath);
free(fullpath); free(fullpath);
...@@ -2306,7 +2306,7 @@ static bool cgfsng_escape() ...@@ -2306,7 +2306,7 @@ static bool cgfsng_escape()
fullpath = must_make_path(hierarchies[i]->mountpoint, fullpath = must_make_path(hierarchies[i]->mountpoint,
hierarchies[i]->base_cgroup, hierarchies[i]->base_cgroup,
"cgroup.procs", NULL); "cgroup.procs", NULL);
ret = lxc_write_to_file(fullpath, "0", 2, false); ret = lxc_write_to_file(fullpath, "0", 2, false, 0666);
if (ret != 0) { if (ret != 0) {
SYSERROR("Failed to escape to cgroup \"%s\"", fullpath); SYSERROR("Failed to escape to cgroup \"%s\"", fullpath);
free(fullpath); free(fullpath);
...@@ -2359,7 +2359,7 @@ static bool cgfsng_unfreeze(void *hdata) ...@@ -2359,7 +2359,7 @@ static bool cgfsng_unfreeze(void *hdata)
return false; return false;
fullpath = must_make_path(h->fullcgpath, "freezer.state", NULL); fullpath = must_make_path(h->fullcgpath, "freezer.state", NULL);
ret = lxc_write_to_file(fullpath, THAWED, THAWED_LEN, false); ret = lxc_write_to_file(fullpath, THAWED, THAWED_LEN, false, 0666);
free(fullpath); free(fullpath);
if (ret < 0) if (ret < 0)
return false; return false;
...@@ -2417,7 +2417,7 @@ static int __cg_unified_attach(const struct hierarchy *h, const char *name, ...@@ -2417,7 +2417,7 @@ static int __cg_unified_attach(const struct hierarchy *h, const char *name,
base_path = must_make_path(h->mountpoint, container_cgroup, NULL); base_path = must_make_path(h->mountpoint, container_cgroup, NULL);
full_path = must_make_path(base_path, "cgroup.procs", NULL); full_path = must_make_path(base_path, "cgroup.procs", NULL);
/* cgroup is populated */ /* cgroup is populated */
ret = lxc_write_to_file(full_path, pidstr, pidstr_len, false); ret = lxc_write_to_file(full_path, pidstr, pidstr_len, false, 0666);
if (ret < 0 && errno != EBUSY) if (ret < 0 && errno != EBUSY)
goto on_error; goto on_error;
...@@ -2443,7 +2443,7 @@ static int __cg_unified_attach(const struct hierarchy *h, const char *name, ...@@ -2443,7 +2443,7 @@ static int __cg_unified_attach(const struct hierarchy *h, const char *name,
goto on_error; goto on_error;
strcat(full_path, "/cgroup.procs"); strcat(full_path, "/cgroup.procs");
ret = lxc_write_to_file(full_path, pidstr, len, false); ret = lxc_write_to_file(full_path, pidstr, len, false, 0666);
if (ret == 0) if (ret == 0)
goto on_success; goto on_success;
...@@ -2495,7 +2495,7 @@ static bool cgfsng_attach(const char *name, const char *lxcpath, pid_t pid) ...@@ -2495,7 +2495,7 @@ static bool cgfsng_attach(const char *name, const char *lxcpath, pid_t pid)
fullpath = build_full_cgpath_from_monitorpath(h, path, "cgroup.procs"); fullpath = build_full_cgpath_from_monitorpath(h, path, "cgroup.procs");
free(path); free(path);
ret = lxc_write_to_file(fullpath, pidstr, len, false); ret = lxc_write_to_file(fullpath, pidstr, len, false, 0666);
if (ret < 0) { if (ret < 0) {
SYSERROR("Failed to attach %d to %s", (int)pid, fullpath); SYSERROR("Failed to attach %d to %s", (int)pid, fullpath);
free(fullpath); free(fullpath);
...@@ -2573,7 +2573,7 @@ static int cgfsng_set(const char *filename, const char *value, const char *name, ...@@ -2573,7 +2573,7 @@ static int cgfsng_set(const char *filename, const char *value, const char *name,
char *fullpath; char *fullpath;
fullpath = build_full_cgpath_from_monitorpath(h, path, filename); fullpath = build_full_cgpath_from_monitorpath(h, path, filename);
ret = lxc_write_to_file(fullpath, value, strlen(value), false); ret = lxc_write_to_file(fullpath, value, strlen(value), false, 0666);
free(fullpath); free(fullpath);
} }
free(path); free(path);
...@@ -2698,7 +2698,7 @@ static int cg_legacy_set_data(const char *filename, const char *value, ...@@ -2698,7 +2698,7 @@ static int cg_legacy_set_data(const char *filename, const char *value,
} }
fullpath = must_make_path(h->fullcgpath, filename, NULL); fullpath = must_make_path(h->fullcgpath, filename, NULL);
ret = lxc_write_to_file(fullpath, value, strlen(value), false); ret = lxc_write_to_file(fullpath, value, strlen(value), false, 0666);
free(fullpath); free(fullpath);
return ret; return ret;
} }
...@@ -2767,7 +2767,7 @@ static bool __cg_unified_setup_limits(void *hdata, ...@@ -2767,7 +2767,7 @@ static bool __cg_unified_setup_limits(void *hdata,
struct lxc_cgroup *cg = iterator->elem; struct lxc_cgroup *cg = iterator->elem;
fullpath = must_make_path(h->fullcgpath, cg->subsystem, NULL); fullpath = must_make_path(h->fullcgpath, cg->subsystem, NULL);
ret = lxc_write_to_file(fullpath, cg->value, strlen(cg->value), false); ret = lxc_write_to_file(fullpath, cg->value, strlen(cg->value), false, 0666);
free(fullpath); free(fullpath);
if (ret < 0) { if (ret < 0) {
SYSERROR("Failed to set \"%s\" to \"%s\"", SYSERROR("Failed to set \"%s\" to \"%s\"",
......
...@@ -2560,7 +2560,7 @@ int setup_sysctl_parameters(struct lxc_list *sysctls) ...@@ -2560,7 +2560,7 @@ int setup_sysctl_parameters(struct lxc_list *sysctls)
} }
ret = lxc_write_to_file(filename, elem->value, ret = lxc_write_to_file(filename, elem->value,
strlen(elem->value), false); strlen(elem->value), false, 0666);
if (ret < 0) { if (ret < 0) {
ERROR("Failed to setup sysctl parameters %s to %s", ERROR("Failed to setup sysctl parameters %s to %s",
elem->key, elem->value); elem->key, elem->value);
...@@ -2595,7 +2595,7 @@ int setup_proc_filesystem(struct lxc_list *procs, pid_t pid) ...@@ -2595,7 +2595,7 @@ int setup_proc_filesystem(struct lxc_list *procs, pid_t pid)
} }
ret = lxc_write_to_file(filename, elem->value, ret = lxc_write_to_file(filename, elem->value,
strlen(elem->value), false); strlen(elem->value), false, 0666);
if (ret < 0) { if (ret < 0) {
ERROR("Failed to setup proc filesystem %s to %s", ERROR("Failed to setup proc filesystem %s to %s",
elem->filename, elem->value); elem->filename, elem->value);
......
...@@ -837,7 +837,6 @@ static bool do_lxcapi_start(struct lxc_container *c, int useinit, char * const a ...@@ -837,7 +837,6 @@ static bool do_lxcapi_start(struct lxc_container *c, int useinit, char * const a
struct lxc_handler *handler; struct lxc_handler *handler;
struct lxc_conf *conf; struct lxc_conf *conf;
bool daemonize = false; bool daemonize = false;
FILE *pid_fp = NULL;
char *default_args[] = { char *default_args[] = {
"/sbin/init", "/sbin/init",
NULL, NULL,
...@@ -1001,30 +1000,34 @@ static bool do_lxcapi_start(struct lxc_container *c, int useinit, char * const a ...@@ -1001,30 +1000,34 @@ static bool do_lxcapi_start(struct lxc_container *c, int useinit, char * const a
* write the right PID. * write the right PID.
*/ */
if (c->pidfile) { if (c->pidfile) {
pid_fp = fopen(c->pidfile, "w"); int ret, w;
if (pid_fp == NULL) { char pidstr[LXC_NUMSTRLEN64];
SYSERROR("Failed to create pidfile '%s' for '%s'",
c->pidfile, c->name); w = snprintf(pidstr, LXC_NUMSTRLEN64, "%d", (int)lxc_raw_getpid());
if (w < 0 || (size_t)w >= LXC_NUMSTRLEN64) {
free_init_cmd(init_cmd); free_init_cmd(init_cmd);
lxc_free_handler(handler); lxc_free_handler(handler);
SYSERROR("Failed to write monitor pid to \"%s\"", c->pidfile);
if (daemonize) if (daemonize)
_exit(EXIT_FAILURE); _exit(EXIT_FAILURE);
return false; return false;
} }
if (fprintf(pid_fp, "%d\n", lxc_raw_getpid()) < 0) { ret = lxc_write_to_file(c->pidfile, pidstr, w, false, 0600);
SYSERROR("Failed to write '%s'", c->pidfile); if (ret < 0) {
fclose(pid_fp);
pid_fp = NULL;
free_init_cmd(init_cmd); free_init_cmd(init_cmd);
lxc_free_handler(handler); lxc_free_handler(handler);
SYSERROR("Failed to write '%s'", c->pidfile);
if (daemonize) if (daemonize)
_exit(EXIT_FAILURE); _exit(EXIT_FAILURE);
return false; return false;
} }
fclose(pid_fp);
pid_fp = NULL;
} }
conf->reboot = 0; conf->reboot = 0;
......
...@@ -971,12 +971,13 @@ size_t lxc_array_len(void **array) ...@@ -971,12 +971,13 @@ size_t lxc_array_len(void **array)
return result; return result;
} }
int lxc_write_to_file(const char *filename, const void* buf, size_t count, bool add_newline) int lxc_write_to_file(const char *filename, const void *buf, size_t count,
bool add_newline, mode_t mode)
{ {
int fd, saved_errno; int fd, saved_errno;
ssize_t ret; ssize_t ret;
fd = open(filename, O_WRONLY | O_TRUNC | O_CREAT | O_CLOEXEC, 0666); fd = open(filename, O_WRONLY | O_TRUNC | O_CREAT | O_CLOEXEC, mode);
if (fd < 0) if (fd < 0)
return -1; return -1;
ret = lxc_write_nointr(fd, buf, count); ret = lxc_write_nointr(fd, buf, count);
......
...@@ -392,7 +392,7 @@ extern int sha1sum_file(char *fnam, unsigned char *md_value); ...@@ -392,7 +392,7 @@ extern int sha1sum_file(char *fnam, unsigned char *md_value);
/* read and write whole files */ /* read and write whole files */
extern int lxc_write_to_file(const char *filename, const void *buf, extern int lxc_write_to_file(const char *filename, const void *buf,
size_t count, bool add_newline); size_t count, bool add_newline, mode_t mode);
extern int lxc_read_from_file(const char *filename, void* buf, size_t count); extern int lxc_read_from_file(const char *filename, void* buf, size_t count);
/* convert variadic argument lists to arrays (for execl type argument lists) */ /* convert variadic argument lists to arrays (for execl type argument lists) */
......
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