diff options
author | dcashman <dcashman@google.com> | 2015-06-15 21:57:42 +0000 |
---|---|---|
committer | Android Git Automerger <android-git-automerger@android.com> | 2015-06-15 21:57:42 +0000 |
commit | cca1ff102be826f247eb787dabf0844f9359049a (patch) | |
tree | 722df8151f8b9d258b7e0f18ed4782e10eaf5faf | |
parent | 8d99ef1f308d2a18bce9484f86fe7f685ccf1571 (diff) | |
parent | 06d45512e2df93f65a51877a51549e522b4f2cf5 (diff) | |
download | libselinux-cca1ff102be826f247eb787dabf0844f9359049a.tar.gz |
am 06d45512: restorecon: only operate on canonical paths.
* commit '06d45512e2df93f65a51877a51549e522b4f2cf5':
restorecon: only operate on canonical paths.
-rw-r--r-- | src/android.c | 42 |
1 files changed, 33 insertions, 9 deletions
diff --git a/src/android.c b/src/android.c index f2b2370..1b4496d 100644 --- a/src/android.c +++ b/src/android.c @@ -28,6 +28,7 @@ #include "selinux_internal.h" #include "label_internal.h" #include <fnmatch.h> +#include <limits.h> /* * XXX Where should this configuration file be located? @@ -1212,7 +1213,7 @@ err: #define SYS_PATH "/sys" #define SYS_PREFIX SYS_PATH "/" -static int selinux_android_restorecon_common(const char* pathname, +static int selinux_android_restorecon_common(const char* pathname_orig, const char *seinfo, uid_t uid, unsigned int flags) @@ -1222,12 +1223,13 @@ static int selinux_android_restorecon_common(const char* pathname, bool recurse = (flags & SELINUX_ANDROID_RESTORECON_RECURSE) ? true : false; bool force = (flags & SELINUX_ANDROID_RESTORECON_FORCE) ? true : false; bool datadata = (flags & SELINUX_ANDROID_RESTORECON_DATADATA) ? true : false; - bool issys = (!strcmp(pathname, SYS_PATH) || !strncmp(pathname, SYS_PREFIX, sizeof(SYS_PREFIX)-1)) ? true : false; + bool issys; bool setrestoreconlast = true; struct stat sb; FTS *fts; FTSENT *ftsent; - char *const paths[2] = { __UNCONST(pathname), NULL }; + char *pathname; + char * paths[2] = { NULL , NULL }; int ftsflags = FTS_NOCHDIR | FTS_XDEV | FTS_PHYSICAL; int error, sverrno; char xattr_value[FC_DIGEST_SIZE]; @@ -1241,11 +1243,28 @@ static int selinux_android_restorecon_common(const char* pathname, if (!fc_sehandle) return 0; + // convert passed-in pathname to canonical pathname + pathname = realpath(pathname_orig, NULL); + if (!pathname) { + sverrno = errno; + selinux_log(SELINUX_ERROR, "SELinux: Could not get canonical path %s restorecon: %s.\n", + pathname_orig, strerror(errno)); + errno = sverrno; + error = -1; + goto cleanup; + } + paths[0] = pathname; + issys = (!strcmp(pathname, SYS_PATH) + || !strncmp(pathname, SYS_PREFIX, sizeof(SYS_PREFIX)-1)) ? true : false; + if (!recurse) { - if (lstat(pathname, &sb) < 0) - return -1; + if (lstat(pathname, &sb) < 0) { + error = -1; + goto cleanup; + } - return restorecon_sb(pathname, &sb, nochange, verbose, seinfo, uid); + error = restorecon_sb(pathname, &sb, nochange, verbose, seinfo, uid); + goto cleanup; } /* @@ -1269,13 +1288,16 @@ static int selinux_android_restorecon_common(const char* pathname, selinux_log(SELINUX_INFO, "SELinux: Skipping restorecon_recursive(%s)\n", pathname); - return 0; + error = 0; + goto cleanup; } } fts = fts_open(paths, ftsflags, NULL); - if (!fts) - return -1; + if (!fts) { + error = -1; + goto cleanup; + } error = 0; while ((ftsent = fts_read(fts)) != NULL) { @@ -1332,6 +1354,8 @@ out: sverrno = errno; (void) fts_close(fts); errno = sverrno; +cleanup: + free(pathname); return error; } |