#define _GNU_SOURCE #include #include #include #include #include #include #include /* Trusted, single-process admission gate. The supervisor charges this PID to * its engine cgroup before releasing stdin. All subsequently created namespace * helpers and threads inherit that charge. No authored code runs here. */ static void fail(const char *message) { fprintf(stderr, "RESTRICTED_SANDBOX: %s\n", message); exit(125); } int main(int argc, char **argv) { struct stat info; if (argc != 2 || argv[1][0] != '/' || strstr(argv[1], "/../") || lstat(argv[1], &info) || !S_ISDIR(info.st_mode) || info.st_uid != getuid() || (info.st_mode & 007)) fail("invalid engine directory"); char gate; if (read(STDIN_FILENO, &gate, 1) != 1 || gate != 1) fail("engine admission was not released"); int input = open("/dev/null", O_RDONLY); if (input < 0 || dup2(input, STDIN_FILENO) < 0) fail("stdin"); close(input); int filter = open(SANDBOX_FILTER, O_RDONLY); if (filter < 0) fail("seccomp filter"); char filter_fd[32]; snprintf(filter_fd, sizeof(filter_fd), "%d", filter); char *args[4096]; size_t count = 0; #define ARG(value) args[count++] = (value) ARG(SANDBOX_BWRAP); ARG("--unshare-all"); ARG("--unshare-user"); ARG("--die-with-parent"); ARG("--disable-userns"); ARG("--assert-userns-disabled"); ARG("--cap-drop"); ARG("ALL"); ARG("--hostname"); ARG("quixos-restricted"); ARG("--clearenv"); ARG("--setenv"); ARG("TZ"); ARG("UTC"); ARG("--setenv"); ARG("LANG"); ARG("C.UTF-8"); FILE *closure = fopen(SANDBOX_CLOSURE, "r"); if (!closure) fail("runtime closure"); char *line = NULL; size_t capacity = 0; while (getline(&line, &capacity, closure) >= 0) { line[strcspn(line, "\n")] = 0; if (strncmp(line, "/nix/store/", 11) || strchr(line, ' ') || count > 4000) fail("runtime closure entry"); char *path = strdup(line); if (!path) fail("runtime closure allocation"); ARG("--ro-bind"); ARG(path); ARG(path); } fclose(closure); free(line); ARG("--proc"); ARG("/proc"); ARG("--dev"); ARG("/dev"); ARG("--tmpfs"); ARG("/tmp"); ARG("--bind"); ARG(argv[1]); ARG(argv[1]); ARG("--chdir"); ARG(argv[1]); ARG("--seccomp"); ARG(filter_fd); ARG("--"); ARG(SANDBOX_EXECUTABLE); ARG("serve"); ARG("--experimental"); ARG("config.capnp"); ARG(NULL); execv(SANDBOX_BWRAP, args); fail("bubblewrap failed"); }