diff options
-rw-r--r-- | configure.ac | 6 | ||||
-rw-r--r-- | src/Makefile.am | 2 | ||||
-rw-r--r-- | src/api.c | 20 | ||||
-rw-r--r-- | src/system.c | 71 | ||||
-rw-r--r-- | src/system.h | 30 |
5 files changed, 103 insertions, 26 deletions
diff --git a/configure.ac b/configure.ac index be2ffd5..8cdf4e5 100644 --- a/configure.ac +++ b/configure.ac @@ -76,6 +76,12 @@ AC_SUBST([VERSION_MINOR]) AC_SUBST([VERSION_MICRO]) dnl #### +dnl function checks +dnl #### +dnl # NOTE: keep this disabled until we can test on a released 3.17 kernel +dnl AC_CHECK_FUNCS(seccomp) + +dnl #### dnl cython checks dnl #### AC_CHECK_PROG(have_cython, cython, "yes", "no") diff --git a/src/Makefile.am b/src/Makefile.am index 271a562..2d1db37 100644 --- a/src/Makefile.am +++ b/src/Makefile.am @@ -32,7 +32,7 @@ SOURCES_ARCH = \ arch-mips64n32.h arch-mips64n32.c arch-mips64n32-syscalls.c SOURCES_GEN = \ - api.c system.h \ + api.c system.h system.c \ db.h db.c \ hash.h hash.c \ gen_pfc.h gen_pfc.c gen_bpf.h gen_bpf.c @@ -27,7 +27,6 @@ #include <stdlib.h> #include <string.h> #include <stdbool.h> -#include <sys/prctl.h> #include <seccomp.h> @@ -225,30 +224,13 @@ API int seccomp_arch_remove(scmp_filter_ctx ctx, uint32_t arch_token) /* NOTE - function header comment in include/seccomp.h */ API int seccomp_load(const scmp_filter_ctx ctx) { - int rc; struct db_filter_col *col; - struct bpf_program *program; if (_ctx_valid(ctx)) return -EINVAL; col = (struct db_filter_col *)ctx; - program = gen_bpf_generate((struct db_filter_col *)ctx); - if (program == NULL) - return -ENOMEM; - /* attempt to set NO_NEW_PRIVS */ - if (col->attr.nnp_enable) { - rc = prctl(PR_SET_NO_NEW_PRIVS, 1, 0, 0, 0); - if (rc < 0) - return -errno; - } - /* load the filter into the kernel */ - rc = prctl(PR_SET_SECCOMP, SECCOMP_MODE_FILTER, program); - gen_bpf_release(program); - if (rc < 0) - return -errno; - - return 0; + return sys_filter_load(col); } /* NOTE - function header comment in include/seccomp.h */ diff --git a/src/system.c b/src/system.c new file mode 100644 index 0000000..fcbaec9 --- /dev/null +++ b/src/system.c @@ -0,0 +1,71 @@ +/** + * Seccomp System Interfaces + * + * Copyright (c) 2014 Red Hat <pmoore@redhat.com> + * Author: Paul Moore <pmoore@redhat.com> + */ + +/* + * This library is free software; you can redistribute it and/or modify it + * under the terms of version 2.1 of the GNU Lesser General Public License as + * published by the Free Software Foundation. + * + * This library is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License + * for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this library; if not, see <http://www.gnu.org/licenses>. + */ + +#include <stdlib.h> +#include <errno.h> +#include <sys/prctl.h> + +#include <seccomp.h> + +#include "db.h" +#include "gen_bpf.h" +#include "system.h" + +/** + * Loads the filter into the kernel + * @param col the filter collection + * + * This function loads the given seccomp filter context into the kernel. If + * the filter was loaded correctly, the kernel will be enforcing the filter + * when this function returns. Returns zero on success, negative values on + * error. + * + */ +int sys_filter_load(const struct db_filter_col *col) +{ + int rc; + struct bpf_program *program = NULL; + + program = gen_bpf_generate(col); + if (program == NULL) + return -ENOMEM; + + /* attempt to set NO_NEW_PRIVS */ + if (col->attr.nnp_enable) { + rc = prctl(PR_SET_NO_NEW_PRIVS, 1, 0, 0, 0); + if (rc < 0) + goto filter_load_out; + } + + /* load the filter into the kernel */ +#ifdef HAVE_SECCOMP + rc = seccomp(SECCOMP_SET_MODE_FILTER, flags, program); +#else + rc = prctl(PR_SET_SECCOMP, SECCOMP_MODE_FILTER, program); +#endif /* HAVE_SECCOMP */ + +filter_load_out: + /* cleanup and return */ + gen_bpf_release(program); + if (rc < 0) + return -errno; + return 0; +} diff --git a/src/system.h b/src/system.h index 11303cf..21e3224 100644 --- a/src/system.h +++ b/src/system.h @@ -1,5 +1,5 @@ /** - * Seccomp System Information + * Seccomp System Interfaces * * Copyright (c) 2012 Red Hat <pmoore@redhat.com> * Author: Paul Moore <pmoore@redhat.com> @@ -27,6 +27,8 @@ #include "configure.h" +struct db_filter_col; + #ifdef HAVE_LINUX_SECCOMP_H /* system header file */ @@ -76,17 +78,33 @@ struct seccomp_data { __u64 args[6]; }; -#endif /* CONF_SYSINC_SECCOMP */ +#endif /* HAVE_LINUX_SECCOMP_H */ /* rename some of the socket filter types to make more sense */ typedef struct sock_filter bpf_instr_raw; +/* no new privs defintions */ #ifndef PR_SET_NO_NEW_PRIVS -#define PR_SET_NO_NEW_PRIVS 38 -#endif /* PR_SET_NO_NEW_PRIVS */ +#define PR_SET_NO_NEW_PRIVS 38 +#endif #ifndef PR_GET_NO_NEW_PRIVS -#define PR_GET_NO_NEW_PRIVS 39 -#endif /* PR_GET_NO_NEW_PRIVS */ +#define PR_GET_NO_NEW_PRIVS 39 +#endif + +/* operations for the seccomp() syscall */ +#ifndef SECCOMP_MODE_STRICT +#define SECCOMP_SET_MODE_STRICT 0 +#endif +#ifndef SECCOMP_SET_MODE_FILTER +#define SECCOMP_SET_MODE_FILTER 1 +#endif + +/* flags for the seccomp() syscall */ +#ifndef SECCOMP_FILTER_FLAG_TSYNC +#define SECCOMP_FILTER_FLAG_TSYNC 1 +#endif + +int sys_filter_load(const struct db_filter_col *col); #endif |