summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorZbigniew Jędrzejewski-Szmek <zbyszek@in.waw.pl>2016-11-03 20:27:45 -0400
committerGitHub <noreply@github.com>2016-11-03 20:27:45 -0400
commitcf88547034d72e0c43e880b89d36643befc54bb9 (patch)
tree4baf2125530aadacc6ac73d5f80b843dad1ce2d1 /src
parentd974f949f10d6945e1abe9bc6525e676bc515928 (diff)
parent1720590bfd7618efa10891f956bf4b265311be04 (diff)
Merge pull request #4548 from keszybz/seccomp-help
systemd-analyze syscall-filter
Diffstat (limited to 'src')
-rw-r--r--src/analyze/analyze.c107
-rw-r--r--src/shared/seccomp-util.c68
-rw-r--r--src/shared/seccomp-util.h4
3 files changed, 122 insertions, 57 deletions
diff --git a/src/analyze/analyze.c b/src/analyze/analyze.c
index cbf9354a7a..f744a84501 100644
--- a/src/analyze/analyze.c
+++ b/src/analyze/analyze.c
@@ -36,6 +36,7 @@
#include "log.h"
#include "pager.h"
#include "parse-util.h"
+#include "seccomp-util.h"
#include "special.h"
#include "strv.h"
#include "strxcpyx.h"
@@ -1275,36 +1276,94 @@ static int set_log_target(sd_bus *bus, char **args) {
return 0;
}
+#ifdef HAVE_SECCOMP
+static void dump_syscall_filter(const SyscallFilterSet *set) {
+ const char *syscall;
+
+ printf("%s\n", set->name);
+ printf(" # %s\n", set->help);
+ NULSTR_FOREACH(syscall, set->value)
+ printf(" %s\n", syscall);
+}
+
+static int dump_syscall_filters(char** names) {
+ bool first = true;
+
+ pager_open(arg_no_pager, false);
+
+ if (strv_isempty(names)) {
+ int i;
+
+ for (i = 0; i < _SYSCALL_FILTER_SET_MAX; i++) {
+ if (!first)
+ puts("");
+ dump_syscall_filter(syscall_filter_sets + i);
+ first = false;
+ }
+ } else {
+ char **name;
+
+ STRV_FOREACH(name, names) {
+ const SyscallFilterSet *set;
+
+ if (!first)
+ puts("");
+
+ set = syscall_filter_set_find(*name);
+ if (!set) {
+ /* make sure the error appears below normal output */
+ fflush(stdout);
+
+ log_error("Filter set \"%s\" not found.", *name);
+ return -ENOENT;
+ }
+
+ dump_syscall_filter(set);
+ first = false;
+ }
+ }
+
+ return 0;
+}
+
+#else
+static int dump_syscall_filters(char** names) {
+ log_error("Not compiled with syscall filters, sorry.");
+ return -EOPNOTSUPP;
+}
+#endif
+
static void help(void) {
pager_open(arg_no_pager, false);
printf("%s [OPTIONS...] {COMMAND} ...\n\n"
"Profile systemd, show unit dependencies, check unit files.\n\n"
- " -h --help Show this help\n"
- " --version Show package version\n"
- " --no-pager Do not pipe output into a pager\n"
- " --system Operate on system systemd instance\n"
- " --user Operate on user systemd instance\n"
- " -H --host=[USER@]HOST Operate on remote host\n"
- " -M --machine=CONTAINER Operate on local container\n"
- " --order Show only order in the graph\n"
- " --require Show only requirement in the graph\n"
- " --from-pattern=GLOB Show only origins in the graph\n"
- " --to-pattern=GLOB Show only destinations in the graph\n"
- " --fuzz=SECONDS Also print also services which finished SECONDS\n"
- " earlier than the latest in the branch\n"
- " --man[=BOOL] Do [not] check for existence of man pages\n\n"
+ " -h --help Show this help\n"
+ " --version Show package version\n"
+ " --no-pager Do not pipe output into a pager\n"
+ " --system Operate on system systemd instance\n"
+ " --user Operate on user systemd instance\n"
+ " -H --host=[USER@]HOST Operate on remote host\n"
+ " -M --machine=CONTAINER Operate on local container\n"
+ " --order Show only order in the graph\n"
+ " --require Show only requirement in the graph\n"
+ " --from-pattern=GLOB Show only origins in the graph\n"
+ " --to-pattern=GLOB Show only destinations in the graph\n"
+ " --fuzz=SECONDS Also print also services which finished SECONDS\n"
+ " earlier than the latest in the branch\n"
+ " --man[=BOOL] Do [not] check for existence of man pages\n\n"
"Commands:\n"
- " time Print time spent in the kernel\n"
- " blame Print list of running units ordered by time to init\n"
- " critical-chain Print a tree of the time critical chain of units\n"
- " plot Output SVG graphic showing service initialization\n"
- " dot Output dependency graph in dot(1) format\n"
- " set-log-level LEVEL Set logging threshold for manager\n"
- " set-log-target TARGET Set logging target for manager\n"
- " dump Output state serialization of service manager\n"
- " verify FILE... Check unit files for correctness\n"
+ " time Print time spent in the kernel\n"
+ " blame Print list of running units ordered by time to init\n"
+ " critical-chain Print a tree of the time critical chain of units\n"
+ " plot Output SVG graphic showing service initialization\n"
+ " dot Output dependency graph in dot(1) format\n"
+ " set-log-level LEVEL Set logging threshold for manager\n"
+ " set-log-target TARGET Set logging target for manager\n"
+ " dump Output state serialization of service manager\n"
+ " syscall-filter [NAME...] Print list of syscalls in seccomp filter\n"
+ " verify FILE... Check unit files for correctness\n"
, program_invocation_short_name);
/* When updating this list, including descriptions, apply
@@ -1471,6 +1530,8 @@ int main(int argc, char *argv[]) {
r = set_log_level(bus, argv+optind+1);
else if (streq(argv[optind], "set-log-target"))
r = set_log_target(bus, argv+optind+1);
+ else if (streq(argv[optind], "syscall-filter"))
+ r = dump_syscall_filters(argv+optind+1);
else
log_error("Unknown operation '%s'.", argv[optind]);
}
diff --git a/src/shared/seccomp-util.c b/src/shared/seccomp-util.c
index c9b24f1065..fc1f6b68f2 100644
--- a/src/shared/seccomp-util.c
+++ b/src/shared/seccomp-util.c
@@ -217,9 +217,27 @@ bool is_seccomp_available(void) {
}
const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
+ [SYSCALL_FILTER_SET_DEFAULT] = {
+ .name = "@default",
+ .help = "System calls that are always permitted",
+ .value =
+ "clock_getres\0"
+ "clock_gettime\0"
+ "clock_nanosleep\0"
+ "execve\0"
+ "exit\0"
+ "exit_group\0"
+ "getrlimit\0" /* make sure processes can query stack size and such */
+ "gettimeofday\0"
+ "nanosleep\0"
+ "pause\0"
+ "rt_sigreturn\0"
+ "sigreturn\0"
+ "time\0"
+ },
[SYSCALL_FILTER_SET_BASIC_IO] = {
- /* Basic IO */
.name = "@basic-io",
+ .help = "Basic IO",
.value =
"close\0"
"dup2\0"
@@ -236,8 +254,8 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"writev\0"
},
[SYSCALL_FILTER_SET_CLOCK] = {
- /* Clock */
.name = "@clock",
+ .help = "Change the system time",
.value =
"adjtimex\0"
"clock_adjtime\0"
@@ -246,8 +264,8 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"stime\0"
},
[SYSCALL_FILTER_SET_CPU_EMULATION] = {
- /* CPU emulation calls */
.name = "@cpu-emulation",
+ .help = "System calls for CPU emulation functionality",
.value =
"modify_ldt\0"
"subpage_prot\0"
@@ -256,8 +274,8 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"vm86old\0"
},
[SYSCALL_FILTER_SET_DEBUG] = {
- /* Debugging/Performance Monitoring/Tracing */
.name = "@debug",
+ .help = "Debugging, performance monitoring and tracing functionality",
.value =
"lookup_dcookie\0"
"perf_event_open\0"
@@ -270,27 +288,9 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
#endif
"sys_debug_setcontext\0"
},
- [SYSCALL_FILTER_SET_DEFAULT] = {
- /* Default list: the most basic of operations */
- .name = "@default",
- .value =
- "clock_getres\0"
- "clock_gettime\0"
- "clock_nanosleep\0"
- "execve\0"
- "exit\0"
- "exit_group\0"
- "getrlimit\0" /* make sure processes can query stack size and such */
- "gettimeofday\0"
- "nanosleep\0"
- "pause\0"
- "rt_sigreturn\0"
- "sigreturn\0"
- "time\0"
- },
[SYSCALL_FILTER_SET_IO_EVENT] = {
- /* Event loop use */
.name = "@io-event",
+ .help = "Event loop system calls",
.value =
"_newselect\0"
"epoll_create1\0"
@@ -308,9 +308,10 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"select\0"
},
[SYSCALL_FILTER_SET_IPC] = {
- /* Message queues, SYSV IPC or other IPC */
.name = "@ipc",
- .value = "ipc\0"
+ .help = "SysV IPC, POSIX Message Queues or other IPC",
+ .value =
+ "ipc\0"
"memfd_create\0"
"mq_getsetattr\0"
"mq_notify\0"
@@ -336,24 +337,24 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"shmget\0"
},
[SYSCALL_FILTER_SET_KEYRING] = {
- /* Keyring */
.name = "@keyring",
+ .help = "Kernel keyring access",
.value =
"add_key\0"
"keyctl\0"
"request_key\0"
},
[SYSCALL_FILTER_SET_MODULE] = {
- /* Kernel module control */
.name = "@module",
+ .help = "Loading and unloading of kernel modules",
.value =
"delete_module\0"
"finit_module\0"
"init_module\0"
},
[SYSCALL_FILTER_SET_MOUNT] = {
- /* Mounting */
.name = "@mount",
+ .help = "Mounting and unmounting of file systems",
.value =
"chroot\0"
"mount\0"
@@ -362,8 +363,8 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"umount\0"
},
[SYSCALL_FILTER_SET_NETWORK_IO] = {
- /* Network or Unix socket IO, should not be needed if not network facing */
.name = "@network-io",
+ .help = "Network or Unix socket IO, should not be needed if not network facing",
.value =
"accept4\0"
"accept\0"
@@ -388,8 +389,9 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"socketpair\0"
},
[SYSCALL_FILTER_SET_OBSOLETE] = {
- /* Unusual, obsolete or unimplemented, some unknown even to libseccomp */
+ /* some unknown even to libseccomp */
.name = "@obsolete",
+ .help = "Unusual, obsolete or unimplemented system calls",
.value =
"_sysctl\0"
"afs_syscall\0"
@@ -417,8 +419,8 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"vserver\0"
},
[SYSCALL_FILTER_SET_PRIVILEGED] = {
- /* Nice grab-bag of all system calls which need superuser capabilities */
.name = "@privileged",
+ .help = "All system calls which need super-user capabilities",
.value =
"@clock\0"
"@module\0"
@@ -459,8 +461,8 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"vhangup\0"
},
[SYSCALL_FILTER_SET_PROCESS] = {
- /* Process control, execution, namespaces */
.name = "@process",
+ .help = "Process control, execution, namespaceing operations",
.value =
"arch_prctl\0"
"clone\0"
@@ -475,8 +477,8 @@ const SyscallFilterSet syscall_filter_sets[_SYSCALL_FILTER_SET_MAX] = {
"vfork\0"
},
[SYSCALL_FILTER_SET_RAW_IO] = {
- /* Raw I/O ports */
.name = "@raw-io",
+ .help = "Raw I/O port access",
.value =
"ioperm\0"
"iopl\0"
diff --git a/src/shared/seccomp-util.h b/src/shared/seccomp-util.h
index 8e209efef2..f0b9f455ab 100644
--- a/src/shared/seccomp-util.h
+++ b/src/shared/seccomp-util.h
@@ -34,15 +34,17 @@ bool is_seccomp_available(void);
typedef struct SyscallFilterSet {
const char *name;
+ const char *help;
const char *value;
} SyscallFilterSet;
enum {
+ /* Please leave DEFAULT first, but sort the rest alphabetically */
+ SYSCALL_FILTER_SET_DEFAULT,
SYSCALL_FILTER_SET_BASIC_IO,
SYSCALL_FILTER_SET_CLOCK,
SYSCALL_FILTER_SET_CPU_EMULATION,
SYSCALL_FILTER_SET_DEBUG,
- SYSCALL_FILTER_SET_DEFAULT,
SYSCALL_FILTER_SET_IO_EVENT,
SYSCALL_FILTER_SET_IPC,
SYSCALL_FILTER_SET_KEYRING,