From 1ff604c2980f587b5e5f817ac2d9285b28e49de7 Mon Sep 17 00:00:00 2001 From: Arun Raghavan Date: Tue, 3 Jul 2012 08:49:26 +0530 Subject: [PATCH] core-util: Fix permissions handling while creating directories MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit This makes updating of permissions on existing directories optional with pa_make_secure_dir() and pa_make_secure_parent_dir(). This makes sure that the recursive directory creation doesn't end up modifying existing directories, and also fixes a problem where creating an auth cookie (specifically ~/.esd_auth) would end up modifying permissions on ~. Thanks to Frédéric Danis for reporting this. --- src/daemon/main.c | 4 ++-- src/modules/module-protocol-stub.c | 2 +- src/pulsecore/authkey.c | 2 +- src/pulsecore/core-util.c | 23 ++++++++++++++--------- src/pulsecore/core-util.h | 4 ++-- 5 files changed, 20 insertions(+), 15 deletions(-) diff --git a/src/daemon/main.c b/src/daemon/main.c index a67bf063..f7b102d4 100644 --- a/src/daemon/main.c +++ b/src/daemon/main.c @@ -202,12 +202,12 @@ static int change_user(void) { if (!pa_streq(pw->pw_dir, PA_SYSTEM_RUNTIME_PATH)) pa_log_warn(_("Home directory of user '%s' is not '%s', ignoring."), PA_SYSTEM_USER, PA_SYSTEM_RUNTIME_PATH); - if (pa_make_secure_dir(PA_SYSTEM_RUNTIME_PATH, 0755, pw->pw_uid, gr->gr_gid) < 0) { + if (pa_make_secure_dir(PA_SYSTEM_RUNTIME_PATH, 0755, pw->pw_uid, gr->gr_gid, TRUE) < 0) { pa_log(_("Failed to create '%s': %s"), PA_SYSTEM_RUNTIME_PATH, pa_cstrerror(errno)); return -1; } - if (pa_make_secure_dir(PA_SYSTEM_STATE_PATH, 0700, pw->pw_uid, gr->gr_gid) < 0) { + if (pa_make_secure_dir(PA_SYSTEM_STATE_PATH, 0700, pw->pw_uid, gr->gr_gid, TRUE) < 0) { pa_log(_("Failed to create '%s': %s"), PA_SYSTEM_STATE_PATH, pa_cstrerror(errno)); return -1; } diff --git a/src/modules/module-protocol-stub.c b/src/modules/module-protocol-stub.c index dbc19174..1b7f6ed1 100644 --- a/src/modules/module-protocol-stub.c +++ b/src/modules/module-protocol-stub.c @@ -337,7 +337,7 @@ int pa__init(pa_module*m) { /* This socket doesn't reside in our own runtime dir but in * /tmp/.esd/, hence we have to create the dir first */ - if (pa_make_secure_parent_dir(u->socket_path, pa_in_system_mode() ? 0755U : 0700U, (uid_t)-1, (gid_t)-1) < 0) { + if (pa_make_secure_parent_dir(u->socket_path, pa_in_system_mode() ? 0755U : 0700U, (uid_t)-1, (gid_t)-1, FALSE) < 0) { pa_log("Failed to create socket directory '%s': %s\n", u->socket_path, pa_cstrerror(errno)); goto fail; } diff --git a/src/pulsecore/authkey.c b/src/pulsecore/authkey.c index 73e4f5e6..fdf49de5 100644 --- a/src/pulsecore/authkey.c +++ b/src/pulsecore/authkey.c @@ -83,7 +83,7 @@ static int load(const char *fn, pa_bool_t create, void *data, size_t length) { pa_assert(length > 0); if (create) - pa_make_secure_parent_dir(fn, pa_in_system_mode() ? 0755U : 0700U, -1, -1); + pa_make_secure_parent_dir(fn, pa_in_system_mode() ? 0755U : 0700U, -1, -1, FALSE); if ((fd = pa_open_cloexec(fn, (create ? O_RDWR|O_CREAT : O_RDONLY)|O_BINARY, S_IRUSR|S_IWUSR)) < 0) { diff --git a/src/pulsecore/core-util.c b/src/pulsecore/core-util.c index 1275c6e7..e435cc40 100644 --- a/src/pulsecore/core-util.c +++ b/src/pulsecore/core-util.c @@ -216,8 +216,10 @@ void pa_make_fd_cloexec(int fd) { } -/** Creates a directory securely */ -int pa_make_secure_dir(const char* dir, mode_t m, uid_t uid, gid_t gid) { +/** Creates a directory securely. Will create parent directories recursively if + * required. This will not update permissions on parent directories if they + * already exist, however. */ +int pa_make_secure_dir(const char* dir, mode_t m, uid_t uid, gid_t gid, pa_bool_t update_perms) { struct stat st; int r, saved_errno; pa_bool_t retry = TRUE; @@ -239,7 +241,7 @@ again: if (r < 0 && errno == ENOENT && retry) { /* If a parent directory in the path doesn't exist, try to create that * first, then try again. */ - pa_make_secure_parent_dir(dir, m, uid, gid); + pa_make_secure_parent_dir(dir, m, uid, gid, FALSE); retry = FALSE; goto again; } @@ -274,6 +276,9 @@ again: goto fail; } + if (!update_perms) + return 0; + #ifdef HAVE_FCHOWN if (uid == (uid_t) -1) uid = getuid(); @@ -335,14 +340,14 @@ char *pa_parent_dir(const char *fn) { } /* Creates a the parent directory of the specified path securely */ -int pa_make_secure_parent_dir(const char *fn, mode_t m, uid_t uid, gid_t gid) { +int pa_make_secure_parent_dir(const char *fn, mode_t m, uid_t uid, gid_t gid, pa_bool_t update_perms) { int ret = -1; char *dir; if (!(dir = pa_parent_dir(fn))) goto finish; - if (pa_make_secure_dir(dir, m, uid, gid) < 0) + if (pa_make_secure_dir(dir, m, uid, gid, update_perms) < 0) goto finish; ret = 0; @@ -1502,7 +1507,7 @@ char *pa_get_state_dir(void) { /* If PULSE_STATE_PATH and PULSE_RUNTIME_PATH point to the same * dir then this will break. */ - if (pa_make_secure_dir(d, 0700U, (uid_t) -1, (gid_t) -1) < 0) { + if (pa_make_secure_dir(d, 0700U, (uid_t) -1, (gid_t) -1, TRUE) < 0) { pa_log_error("Failed to create secure directory: %s", pa_cstrerror(errno)); pa_xfree(d); return NULL; @@ -1644,7 +1649,7 @@ char *pa_get_runtime_dir(void) { d = getenv("PULSE_RUNTIME_PATH"); if (d) { - if (pa_make_secure_dir(d, m, (uid_t) -1, (gid_t) -1) < 0) { + if (pa_make_secure_dir(d, m, (uid_t) -1, (gid_t) -1, TRUE) < 0) { pa_log_error("Failed to create secure directory: %s", pa_cstrerror(errno)); goto fail; } @@ -1657,7 +1662,7 @@ char *pa_get_runtime_dir(void) { if (d) { k = pa_sprintf_malloc("%s" PA_PATH_SEP "pulse", d); - if (pa_make_secure_dir(k, m, (uid_t) -1, (gid_t) -1) < 0) { + if (pa_make_secure_dir(k, m, (uid_t) -1, (gid_t) -1, TRUE) < 0) { free(k); pa_log_error("Failed to create secure directory: %s", pa_cstrerror(errno)); goto fail; @@ -1671,7 +1676,7 @@ char *pa_get_runtime_dir(void) { if (!d) goto fail; - if (pa_make_secure_dir(d, m, (uid_t) -1, (gid_t) -1) < 0) { + if (pa_make_secure_dir(d, m, (uid_t) -1, (gid_t) -1, TRUE) < 0) { pa_log_error("Failed to create secure directory: %s", pa_cstrerror(errno)); pa_xfree(d); goto fail; diff --git a/src/pulsecore/core-util.h b/src/pulsecore/core-util.h index a3c22470..b181266b 100644 --- a/src/pulsecore/core-util.h +++ b/src/pulsecore/core-util.h @@ -58,8 +58,8 @@ struct timeval; void pa_make_fd_nonblock(int fd); void pa_make_fd_cloexec(int fd); -int pa_make_secure_dir(const char* dir, mode_t m, uid_t uid, gid_t gid); -int pa_make_secure_parent_dir(const char *fn, mode_t, uid_t uid, gid_t gid); +int pa_make_secure_dir(const char* dir, mode_t m, uid_t uid, gid_t gid, pa_bool_t update_perms); +int pa_make_secure_parent_dir(const char *fn, mode_t, uid_t uid, gid_t gid, pa_bool_t update_perms); ssize_t pa_read(int fd, void *buf, size_t count, int *type); ssize_t pa_write(int fd, const void *buf, size_t count, int *type); -- 2.39.2