ccx-utils

Miscellaneous utilities written in C
git clone https://ccx.te2000.cz/git/ccx-utils
Log | Files | Refs

commit b4cf0b2c84d26aadc22864ed48c6304738d523ea
parent 4c5f4a0c71ee0f1e3fa1db15b96b1eee03a077b9
Author: Jan Pobrislo <ccx@te2000.cz>
Date:   Wed, 12 Nov 2025 23:16:47 +0000

Restructure ns_pivot_into.c

Diffstat:
Msrc/ns_pivot_into.c | 89+++++++++++++++++++++++++++++++++++++++++++++----------------------------------
1 file changed, 51 insertions(+), 38 deletions(-)

diff --git a/src/ns_pivot_into.c b/src/ns_pivot_into.c @@ -7,7 +7,9 @@ #include <sys/capability.h> #include <sys/mount.h> #include <sys/syscall.h> /* for SYS_pivot_root */ -#include <linux/securebits.h> +#include <linux/filter.h> /* for seccomp */ +#include <linux/seccomp.h> /* for seccomp */ +#include <linux/securebits.h> /* for prctl(PR_SET_SECUREBITS, ...) */ #include <skalibs/types.h> #include <skalibs/setgroups.h> @@ -17,9 +19,10 @@ #include <skalibs/djbunix.h> #include <skalibs/exec.h> -#define USAGE "ns_pivot_into [ -U iab_caps ] [ -C chdir ] old-place-for-new-root new-place-for-old-root prog..." +#define USAGE "ns_pivot_into [ -U iab_caps ] [ -S seccomp_bpf_fd ] [ -C chdir ] old-place-for-new-root new-place-for-old-root prog..." #define dieusage() strerr_dieusage(100, USAGE) +/*** data structures ***/ struct drop_privs_s { uid_t uid; gid_t gid; @@ -33,39 +36,15 @@ struct unexport_s { stralloc sa; }; -void drop(struct drop_privs_s const *const privs) { - /* make sure privileges are dropped permanently */ - if (prctl(PR_SET_SECUREBITS, - SECBIT_KEEP_CAPS | /* technically unneeded as NO_SETUID_FIXUP is superset */ - SECBIT_NO_SETUID_FIXUP | - SECBIT_NOROOT | /* disables suid and filecap privilege gain */ - SECBIT_NOROOT_LOCKED) < 0) { - strerr_dief1sys(111, "Failed to set securebits via prctl()"); - } - - /* set these capabilities for the current process */ - if (cap_iab_set_proc(privs->new_iab) != 0) { - strerr_dief1sys(111, "Failed to set capabilities via cap_set_proc()"); - } - - /* ancillary groups */ - if (privs->gidn != (size_t) -1 - && setgroups_and_gid(privs->gid ? privs->gid : getegid(), privs->gidn, - privs->gids) < 0) { - strerr_diefu1sys(111, "set supplementary group list"); - } - - /* primary group */ - if (privs->gid && setgid(privs->gid) < 0) { - strerr_diefu1sys(111, "setgid"); - } - - /* set userid */ - if (privs->uid && setuid(privs->uid) < 0) { - strerr_diefu1sys(111, "setuid"); - } +/*** syscall wrappers ***/ +int syscall_pivot_root(char const *new_root, char const *put_old) { + return syscall(SYS_pivot_root, *new_root, *put_old); +} +int syscall_seccomp_set_filter(unsigned int flags, void *args) { + return syscall(__NR_seccomp, SECCOMP_SET_MODE_FILTER, flags, args); } +/*** utility functions ***/ char const *const getenv_dienotset(char const *const name) { char const *x = getenv(name); if (!x) { @@ -79,10 +58,7 @@ int stralloc_catenv0(stralloc *sa, char const * env_name) { return stralloc_catb(sa, value, strlen(value) + 1); } -int pivot_root(char const *new_root, char const *put_old) { - return syscall(SYS_pivot_root, *new_root, *put_old); -} - +/*** individual steps of dropping into sandbox ***/ void pivot_and_umount( char const *const old_place_for_new_root, char const *const new_place_for_old_root, @@ -114,7 +90,7 @@ void pivot_and_umount( if (chdir(old_place_for_new_root) < 0) { strerr_diefu2sys(111, "chdir to ", old_place_for_new_root) ; } - if (pivot_root(".", new_place_for_old_root) < 0) { + if (syscall_pivot_root(".", new_place_for_old_root) < 0) { strerr_diefu1sys(111, "pivot_root") ; } if (chroot(".") < 0) { @@ -155,6 +131,43 @@ void pivot_and_umount( } } +void drop(struct drop_privs_s const *const privs) { + /* make sure privileges are dropped permanently */ + if (prctl(PR_SET_SECUREBITS, + SECBIT_KEEP_CAPS | /* technically unneeded as NO_SETUID_FIXUP is superset */ + SECBIT_NO_SETUID_FIXUP | + SECBIT_NOROOT | /* disables suid and filecap privilege gain */ + SECBIT_NOROOT_LOCKED) < 0) { + strerr_dief1sys(111, "Failed to set securebits via prctl()"); + } + + /* set these capabilities for the current process */ + if (cap_iab_set_proc(privs->new_iab) != 0) { + strerr_dief1sys(111, "Failed to set capabilities via cap_set_proc()"); + } + + /* ancillary groups */ + if (privs->gidn != (size_t) -1 + && setgroups_and_gid(privs->gid ? privs->gid : getegid(), privs->gidn, + privs->gids) < 0) { + strerr_diefu1sys(111, "set supplementary group list"); + } + + /* primary group */ + if (privs->gid && setgid(privs->gid) < 0) { + strerr_diefu1sys(111, "setgid"); + } + + /* set userid */ + if (privs->uid && setuid(privs->uid) < 0) { + strerr_diefu1sys(111, "setuid"); + } +} + +void load_seccomp_program(int fd) { + strerr_dief(99, "seccomp program loading not yet implemented"); +} + int main (int argc, char const *const *argv) { struct unexport_s unex = { 0, STRALLOC_ZERO }; int drop_privs = 0;