diff options
-rw-r--r-- | src/apk_database.h | 1 | ||||
-rw-r--r-- | src/database.c | 15 |
2 files changed, 14 insertions, 2 deletions
diff --git a/src/apk_database.h b/src/apk_database.h index 3488031..917ee35 100644 --- a/src/apk_database.h +++ b/src/apk_database.h @@ -159,6 +159,7 @@ struct apk_database { int permanent : 1; int autoupdate : 1; int open_complete : 1; + int no_chroot : 1; int compat_newfeatures : 1; int compat_notinstallable : 1; diff --git a/src/database.c b/src/database.c index 4b53732..e930f10 100644 --- a/src/database.c +++ b/src/database.c @@ -1552,6 +1552,7 @@ int apk_db_open(struct apk_database *db, struct apk_db_options *dbopts) db->cache_max_age = dbopts->cache_max_age ?: 4*60*60; /* 4 hours default */ db->root = strdup(dbopts->root ?: "/"); + if (!strcmp(db->root, "/")) db->no_chroot = 1; /* skip chroot if root is default */ db->root_fd = openat(AT_FDCWD, db->root, O_RDONLY | O_CLOEXEC); if (db->root_fd < 0 && (dbopts->open_flags & APK_OPENF_CREATE)) { mkdirat(AT_FDCWD, db->root, 0755); @@ -1957,8 +1958,18 @@ int apk_db_run_script(struct apk_database *db, char *fn, char **argv) } if (pid == 0) { umask(0022); - if (fchdir(db->root_fd) == 0 && chroot(".") == 0) - execve(fn, argv, environment); + + if (fchdir(db->root_fd) != 0) { + apk_error("%s: fchdir: %s", basename(fn), strerror(errno)); + exit(127); + } + + if (!db->no_chroot && chroot(".") != 0) { + apk_error("%s: chroot: %s", basename(fn), strerror(errno)); + exit(127); + } + + execve(fn, argv, environment); exit(127); /* should not get here */ } waitpid(pid, &status, 0); |