#include <sys/types.h>
#include <sys/wait.h>
-#include <pakfire/logging.h>
#include <pakfire/jail.h>
+#include <pakfire/logging.h>
+#include <pakfire/mount.h>
#include <pakfire/pakfire.h>
#include <pakfire/util.h>
if (r)
return r;
+ // Perform further initialization
+
+ // Fetch UID/GID
+ uid_t uid = getuid();
+ gid_t gid = getgid();
+
+ // Fetch EUID/EGID
+ uid_t euid = geteuid();
+ gid_t egid = getegid();
+
+ DEBUG(jail->pakfire, " UID: %d (effective %d)\n", uid, euid);
+ DEBUG(jail->pakfire, " GID: %d (effective %d)\n", gid, egid);
+
+ // Check if we are (effectively running as root)
+ if (uid != 0 || gid != 0) {
+ ERROR(jail->pakfire, "Child process is not running as root\n");
+ return 126;
+ }
+
+ const char* root = pakfire_get_path(jail->pakfire);
+ const char* arch = pakfire_get_arch(jail->pakfire);
+
+ // Change root (unless root is /)
+ if (!pakfire_on_root(jail->pakfire)) {
+ // Mount everything
+ r = pakfire_mount_all(jail->pakfire);
+ if (r)
+ return r;
+
+ // Log all mountpoints
+ pakfire_mount_list(jail->pakfire);
+
+ // Call chroot()
+ r = chroot(root);
+ if (r) {
+ ERROR(jail->pakfire, "chroot() to %s failed: %m\n", root);
+ return 1;
+ }
+
+ // Change directory to /
+ r = chdir("/");
+ if (r) {
+ ERROR(jail->pakfire, "chdir() after chroot() failed: %m\n");
+ return 1;
+ }
+ }
+
return 0;
}
// Run a command in the jail
int pakfire_jail_exec(struct pakfire_jail* jail, const char* argv[]) {
+ int exit = -1;
+ int status = 0;
int r;
DEBUG(jail->pakfire, "Executing jail...\n");
if (r)
goto ERROR;
- // Set some useful error code
- int exit;
- int status = 0;
-
DEBUG(jail->pakfire, "Waiting for PID %d to finish its work\n", pid);
if (!status)
exit = -1;
}
- return exit;
-
ERROR:
- return -1;
+ // Umount everything
+ if (!pakfire_on_root(jail->pakfire))
+ pakfire_umount_all(jail->pakfire);
+
+ return exit;
}