diff options
author | Toni Uhlig <matzeton@googlemail.com> | 2018-05-20 02:26:20 +0200 |
---|---|---|
committer | Toni Uhlig <matzeton@googlemail.com> | 2018-05-20 02:26:20 +0200 |
commit | 9b9825fa6a33a4f9703905100a88190aaf030607 (patch) | |
tree | 1dbb712b543320748e29afb8fd751e67fbfe9ed6 | |
parent | 84d818f280f3a398fc91ca82699bc380d37d99cf (diff) |
POTD skeleton #63.
Signed-off-by: Toni Uhlig <matzeton@googlemail.com>
-rw-r--r-- | src/jail.c | 18 | ||||
-rw-r--r-- | src/main.c | 12 | ||||
-rw-r--r-- | src/pseccomp.c | 115 | ||||
-rw-r--r-- | src/pseccomp.h | 15 | ||||
-rw-r--r-- | src/utils.c | 2 |
5 files changed, 148 insertions, 14 deletions
@@ -10,6 +10,7 @@ #include "jail.h" #include "socket.h" +#include "pseccomp.h" #include "capabilities.h" #include "utils.h" #include "log.h" @@ -241,9 +242,11 @@ static int jail_childfn(prisoner_process *ctx) CLONE_NEWNS|CLONE_NEWNET/*|CLONE_NEWUSER*/; //unsigned int ug_map[3] = { 0, 10000, 65535 }; pid_t self_pid, child_pid; + pseccomp_ctx *psc = NULL; assert(ctx); self_pid = getpid(); + set_procname("[potd] jail-client"); if (set_child_sighandler()) FATAL("Set sighandler for pid %d", self_pid); if (setpgrp()) @@ -257,7 +260,7 @@ static int jail_childfn(prisoner_process *ctx) FATAL("Clearing ENV for pid %d", self_pid); caps_drop_dac_override(0); - caps_drop_all(); + //caps_drop_all(); D2("Unshare prisoner %d", self_pid); if (unshare(unshare_flags)) @@ -300,11 +303,9 @@ static int jail_childfn(prisoner_process *ctx) FATAL("Create directory '%s'", path_proc); D2("Creating device files in '%s%s'", ctx->newroot, path_dev); - if (create_device_files(path_dev)) { - E2("Device file creation failed for rootfs '%s%s'", + if (create_device_files(path_dev)) + FATAL("Device file creation failed for rootfs '%s%s'", ctx->newroot, path_dev); - exit(EXIT_FAILURE); - } D2("Forking a new pty process for " "parent %d", self_pid); @@ -348,6 +349,13 @@ static int jail_childfn(prisoner_process *ctx) " -----------------------------------------------------\n" ); + pseccomp_set_immutable(); + pseccomp_init(&psc); + if (pseccomp_jail_rules(psc)) + FATAL("%s", "SECCOMP: adding jail rules"); + pseccomp_free(&psc); + + sethostname("openwrt", SIZEOF("openwrt")); if (execl(path_shell, path_shell, (char *) NULL)) exit(EXIT_FAILURE); default: @@ -31,6 +31,7 @@ int main(int argc, char *argv[]) event_ctx *jail_event = NULL; int proc_status; pid_t daemon_pid, rdr_pid, jail_pid, child_pid; + pseccomp_ctx *psc = NULL; (void) argc; (void) argv; @@ -39,9 +40,16 @@ int main(int argc, char *argv[]) LOG_SET_FUNCS_VA(LOG_COLORED_FUNCS); N("%s (C) 2018 Toni Uhlig (%s)", PACKAGE_STRING, PACKAGE_BUGREPORT); - pseccomp_init(); - pseccomp_set_immutable(); + if (geteuid() != 0) { + E("%s", "I was made for root!"); + exit(EXIT_FAILURE); + } + caps_default_filter(); + pseccomp_init(&psc); + if (pseccomp_default_rules(psc)) + FATAL("%s", "SECCOMP: adding default rules"); + pseccomp_free(&psc); D("%s", "Forking into background/foreground"); daemon_pid = daemonize(1); diff --git a/src/pseccomp.c b/src/pseccomp.c index 0b6ef15..59414d7 100644 --- a/src/pseccomp.c +++ b/src/pseccomp.c @@ -1,19 +1,92 @@ +#include <assert.h> #include <sys/prctl.h> -#include <seccomp.h> +#include <valgrind/valgrind.h> -#include "seccomp.h" +#include "pseccomp.h" #include "log.h" +#include "utils.h" -static scmp_filter_ctx ctx; +static const int default_allowed_syscalls[] = { + SCMP_SYS(rt_sigreturn), SCMP_SYS(rt_sigprocmask), + SCMP_SYS(rt_sigaction), SCMP_SYS(time), SCMP_SYS(nanosleep), + SCMP_SYS(exit), SCMP_SYS(exit_group), + SCMP_SYS(read), SCMP_SYS(write), SCMP_SYS(fcntl), SCMP_SYS(writev), + SCMP_SYS(close), SCMP_SYS(wait4), + SCMP_SYS(sigprocmask), SCMP_SYS(tgkill), + SCMP_SYS(clone), SCMP_SYS(execve), + SCMP_SYS(socket), SCMP_SYS(bind), SCMP_SYS(setsockopt), + SCMP_SYS(listen), SCMP_SYS(connect), SCMP_SYS(getsockname), + SCMP_SYS(accept), SCMP_SYS(sendto), SCMP_SYS(recvmsg), SCMP_SYS(recvfrom), + SCMP_SYS(epoll_create1), SCMP_SYS(epoll_ctl), SCMP_SYS(epoll_pwait), + SCMP_SYS(poll), + SCMP_SYS(set_robust_list), SCMP_SYS(getrlimit), + SCMP_SYS(seccomp), + SCMP_SYS(prctl), SCMP_SYS(mmap), SCMP_SYS(brk), SCMP_SYS(madvise), + SCMP_SYS(mprotect), SCMP_SYS(munmap), SCMP_SYS(futex), + SCMP_SYS(open), SCMP_SYS(unlink), SCMP_SYS(fstat), SCMP_SYS(access), + SCMP_SYS(lseek), SCMP_SYS(stat), SCMP_SYS(readlink), SCMP_SYS(getcwd), + SCMP_SYS(lstat), SCMP_SYS(sysinfo), + SCMP_SYS(setuid), SCMP_SYS(setgid), + SCMP_SYS(setreuid), SCMP_SYS(setregid), + SCMP_SYS(getuid), SCMP_SYS(geteuid), SCMP_SYS(getgid), SCMP_SYS(getegid), + SCMP_SYS(getgroups), SCMP_SYS(getdents), + SCMP_SYS(getpgrp), SCMP_SYS(setpgid), SCMP_SYS(getpid), SCMP_SYS(kill), + SCMP_SYS(unshare), SCMP_SYS(chroot), SCMP_SYS(chdir), SCMP_SYS(mount), + SCMP_SYS(umount2), + SCMP_SYS(mknod), SCMP_SYS(mkdir), SCMP_SYS(statfs), SCMP_SYS(ioctl), + SCMP_SYS(chown), SCMP_SYS(chmod), SCMP_SYS(setsid), SCMP_SYS(dup2), + SCMP_SYS(sethostname), SCMP_SYS(uname), SCMP_SYS(arch_prctl) +}; +static const int jail_allowed_syscalls[] = { + SCMP_SYS(rt_sigreturn), SCMP_SYS(rt_sigprocmask), + SCMP_SYS(rt_sigaction), SCMP_SYS(time), SCMP_SYS(nanosleep), + SCMP_SYS(exit), SCMP_SYS(exit_group), + SCMP_SYS(read), SCMP_SYS(write), SCMP_SYS(fcntl), SCMP_SYS(writev), + SCMP_SYS(close), SCMP_SYS(wait4), + SCMP_SYS(sigprocmask), SCMP_SYS(tgkill), + SCMP_SYS(clone), SCMP_SYS(execve), + SCMP_SYS(mmap), SCMP_SYS(brk), SCMP_SYS(madvise), + SCMP_SYS(mprotect), SCMP_SYS(munmap), SCMP_SYS(futex), + SCMP_SYS(open), SCMP_SYS(fstat), SCMP_SYS(access), + SCMP_SYS(poll), + SCMP_SYS(lseek), SCMP_SYS(stat), SCMP_SYS(readlink), SCMP_SYS(getcwd), + SCMP_SYS(lstat), SCMP_SYS(sysinfo), + SCMP_SYS(setuid), SCMP_SYS(setgid), + SCMP_SYS(setreuid), SCMP_SYS(setregid), + SCMP_SYS(getuid), SCMP_SYS(geteuid), SCMP_SYS(getgid), SCMP_SYS(getegid), + SCMP_SYS(getgroups), SCMP_SYS(getdents), + SCMP_SYS(getpgrp), SCMP_SYS(setpgid), SCMP_SYS(getpid), SCMP_SYS(kill), + SCMP_SYS(chdir), SCMP_SYS(mount), + SCMP_SYS(umount2), + SCMP_SYS(ioctl), + SCMP_SYS(sethostname), SCMP_SYS(uname), SCMP_SYS(arch_prctl) +}; -int pseccomp_init(void) + +int pseccomp_init(pseccomp_ctx **ctx) { - //ctx = seccomp_init(SCMP_ACT_ERRNO(EINVAL)); + assert(ctx); + + if (!*ctx) + *ctx = (pseccomp_ctx *) malloc(sizeof(**ctx)); + assert(*ctx); + + memset(*ctx, 0, sizeof(**ctx)); + (*ctx)->sfilter = seccomp_init(SCMP_ACT_ERRNO(EINVAL)); return 0; } +void pseccomp_free(pseccomp_ctx **ctx) +{ + assert(ctx && *ctx); + + seccomp_release((*ctx)->sfilter); + free(*ctx); + (*ctx) = NULL; +} + int pseccomp_set_immutable(void) { if (prctl(PR_SET_DUMPABLE, 0) && @@ -24,3 +97,35 @@ int pseccomp_set_immutable(void) return 0; } + +int pseccomp_default_rules(pseccomp_ctx *ctx) +{ + size_t i; + + if (RUNNING_ON_VALGRIND) { + W("%s", "SECCOMP: running on valgrind, disabled"); + return 0; + } + + for (i = 0; i < SIZEOF(default_allowed_syscalls); ++i) + seccomp_rule_add(ctx->sfilter, SCMP_ACT_ALLOW, + default_allowed_syscalls[i], 0); + + return seccomp_load(ctx->sfilter); +} + +int pseccomp_jail_rules(pseccomp_ctx *ctx) +{ + size_t i; + + if (RUNNING_ON_VALGRIND) { + W("%s", "SECCOMP: running on valgrind, disabled"); + return 0; + } + + for (i = 0; i < SIZEOF(jail_allowed_syscalls); ++i) + seccomp_rule_add(ctx->sfilter, SCMP_ACT_ALLOW, + jail_allowed_syscalls[i], 0); + + return seccomp_load(ctx->sfilter); +} diff --git a/src/pseccomp.h b/src/pseccomp.h index 76889b6..d208275 100644 --- a/src/pseccomp.h +++ b/src/pseccomp.h @@ -1,8 +1,21 @@ #ifndef POTD_SECCOMP_H #define POTD_SECCOMP_H 1 -int pseccomp_init(void); +#include <seccomp.h> + +typedef struct pseccomp_ctx { + scmp_filter_ctx sfilter; +} pseccomp_ctx; + + +int pseccomp_init(pseccomp_ctx **ctx); + +void pseccomp_free(pseccomp_ctx **ctx); int pseccomp_set_immutable(void); +int pseccomp_default_rules(pseccomp_ctx *ctx); + +int pseccomp_jail_rules(pseccomp_ctx *ctx); + #endif diff --git a/src/utils.c b/src/utils.c index 4c6224d..ca24f6b 100644 --- a/src/utils.c +++ b/src/utils.c @@ -296,7 +296,7 @@ void mount_root(void) { int s; - s = mount("none", "/", "", MS_SLAVE|MS_NOSUID|MS_REC, NULL); + s = mount("none", "/", "", MS_SLAVE|MS_REC, NULL); if (s) chk_chroot(); } |