aboutsummaryrefslogtreecommitdiffstats
path: root/src/firejail
diff options
context:
space:
mode:
authorLibravatar netblue30 <netblue30@yahoo.com>2019-01-08 10:52:25 -0500
committerLibravatar netblue30 <netblue30@yahoo.com>2019-01-08 10:52:25 -0500
commit6a3a7eb06fc08e17097f8ffe14cd24485902c9a6 (patch)
treed5eacd8ce45dc47d6cbf8fdf0b1af28bcb7399d0 /src/firejail
parentmerges (diff)
downloadfirejail-6a3a7eb06fc08e17097f8ffe14cd24485902c9a6.tar.gz
firejail-6a3a7eb06fc08e17097f8ffe14cd24485902c9a6.tar.zst
firejail-6a3a7eb06fc08e17097f8ffe14cd24485902c9a6.zip
fix join/seccomp #2296
Diffstat (limited to 'src/firejail')
-rw-r--r--src/firejail/firejail.h3
-rw-r--r--src/firejail/join.c24
-rw-r--r--src/firejail/seccomp.c77
3 files changed, 75 insertions, 29 deletions
diff --git a/src/firejail/firejail.h b/src/firejail/firejail.h
index 245ea5bde..a3d3dfcd4 100644
--- a/src/firejail/firejail.h
+++ b/src/firejail/firejail.h
@@ -57,7 +57,7 @@
57#define RUN_LIB_FILE "/run/firejail/mnt/libfiles" 57#define RUN_LIB_FILE "/run/firejail/mnt/libfiles"
58#define RUN_DNS_ETC "/run/firejail/mnt/dns-etc" 58#define RUN_DNS_ETC "/run/firejail/mnt/dns-etc"
59 59
60 60#define RUN_SECCOMP_LIST "/run/firejail/mnt/seccomp.list" // list of seccomp files installed
61#define RUN_SECCOMP_PROTOCOL "/run/firejail/mnt/seccomp.protocol" // protocol filter 61#define RUN_SECCOMP_PROTOCOL "/run/firejail/mnt/seccomp.protocol" // protocol filter
62#define RUN_SECCOMP_CFG "/run/firejail/mnt/seccomp" // configured filter 62#define RUN_SECCOMP_CFG "/run/firejail/mnt/seccomp" // configured filter
63#define RUN_SECCOMP_32 "/run/firejail/mnt/seccomp.32" // 32bit arch filter installed on 64bit architectures 63#define RUN_SECCOMP_32 "/run/firejail/mnt/seccomp.32" // 32bit arch filter installed on 64bit architectures
@@ -607,6 +607,7 @@ int seccomp_filter_keep(void);
607void seccomp_print_filter(pid_t pid); 607void seccomp_print_filter(pid_t pid);
608 608
609// caps.c 609// caps.c
610void seccomp_load_file_list(void);
610int caps_default_filter(void); 611int caps_default_filter(void);
611void caps_print(void); 612void caps_print(void);
612void caps_drop_all(void); 613void caps_drop_all(void);
diff --git a/src/firejail/join.c b/src/firejail/join.c
index 3ee069305..9cc4cd75d 100644
--- a/src/firejail/join.c
+++ b/src/firejail/join.c
@@ -160,7 +160,7 @@ static void extract_cgroup(pid_t pid) {
160 free(fname); 160 free(fname);
161} 161}
162 162
163static void extract_caps_seccomp(pid_t pid) { 163static void extract_caps(pid_t pid) {
164 // open stat file 164 // open stat file
165 char *file; 165 char *file;
166 if (asprintf(&file, "/proc/%u/status", pid) == -1) { 166 if (asprintf(&file, "/proc/%u/status", pid) == -1) {
@@ -173,16 +173,7 @@ static void extract_caps_seccomp(pid_t pid) {
173 173
174 char buf[BUFLEN]; 174 char buf[BUFLEN];
175 while (fgets(buf, BUFLEN - 1, fp)) { 175 while (fgets(buf, BUFLEN - 1, fp)) {
176 if (strncmp(buf, "Seccomp:", 8) == 0) { 176 if (strncmp(buf, "CapBnd:", 7) == 0) {
177 char *ptr = buf + 8;
178 int val;
179 if (sscanf(ptr, "%d", &val) != 1)
180 goto errexit;
181 if (val == 2)
182 apply_seccomp = 1;
183 break;
184 }
185 else if (strncmp(buf, "CapBnd:", 7) == 0) {
186 char *ptr = buf + 7; 177 char *ptr = buf + 7;
187 unsigned long long val; 178 unsigned long long val;
188 if (sscanf(ptr, "%llx", &val) != 1) 179 if (sscanf(ptr, "%llx", &val) != 1)
@@ -323,7 +314,7 @@ void join(pid_t pid, int argc, char **argv, int index) {
323 // in user mode set caps seccomp, cpu, cgroup, etc 314 // in user mode set caps seccomp, cpu, cgroup, etc
324 if (getuid() != 0) { 315 if (getuid() != 0) {
325 extract_nonewprivs(pid); // redundant on Linux >= 4.10; duplicated in function extract_caps_seccomp 316 extract_nonewprivs(pid); // redundant on Linux >= 4.10; duplicated in function extract_caps_seccomp
326 extract_caps_seccomp(pid); 317 extract_caps(pid);
327 extract_cpu(pid); 318 extract_cpu(pid);
328 extract_cgroup(pid); 319 extract_cgroup(pid);
329 extract_nogroups(pid); 320 extract_nogroups(pid);
@@ -397,15 +388,8 @@ void join(pid_t pid, int argc, char **argv, int index) {
397 if (apply_caps == 1) // not available for uid 0 388 if (apply_caps == 1) // not available for uid 0
398 caps_set(caps); 389 caps_set(caps);
399#ifdef HAVE_SECCOMP 390#ifdef HAVE_SECCOMP
400 // read cfg.protocol from file
401 if (getuid() != 0) 391 if (getuid() != 0)
402 protocol_filter_load(RUN_PROTOCOL_CFG); 392 seccomp_load_file_list();
403 if (cfg.protocol) // not available for uid 0
404 seccomp_load(RUN_SECCOMP_PROTOCOL); // install filter
405
406 // set seccomp filter
407 if (apply_seccomp == 1) // not available for uid 0
408 seccomp_load(RUN_SECCOMP_CFG);
409#endif 393#endif
410 394
411 // mount user namespace or drop privileges 395 // mount user namespace or drop privileges
diff --git a/src/firejail/seccomp.c b/src/firejail/seccomp.c
index 974e36ba7..1cdd96025 100644
--- a/src/firejail/seccomp.c
+++ b/src/firejail/seccomp.c
@@ -83,6 +83,41 @@ int seccomp_install_filters(void) {
83 return r; 83 return r;
84} 84}
85 85
86static void seccomp_save_file_list(const char *fname) {
87 assert(fname);
88
89 FILE *fp = fopen(RUN_SECCOMP_LIST, "a+");
90 if (!fp)
91 errExit("fopen");
92
93 fprintf(fp, "%s\n", fname);
94 fclose(fp);
95 int rv = chown(RUN_SECCOMP_LIST, getuid(), getgid());
96 (void) rv;
97}
98
99#define MAXBUF 4096
100static int load_file_list_flag = 0;
101void seccomp_load_file_list(void) {
102 FILE *fp = fopen(RUN_SECCOMP_LIST, "r");
103 if (!fp)
104 return; // no seccomp configuration whatsoever
105
106 load_file_list_flag = 1;
107 char buf[MAXBUF];
108 while (fgets(buf, MAXBUF, fp)) {
109 // clean '\n'
110 char *ptr = strchr(buf, '\n');
111 if (ptr)
112 *ptr = '\0';
113 seccomp_load(buf);
114 }
115
116 fclose(fp);
117 load_file_list_flag = 0;
118}
119
120
86int seccomp_load(const char *fname) { 121int seccomp_load(const char *fname) {
87 assert(fname); 122 assert(fname);
88 123
@@ -125,6 +160,10 @@ int seccomp_load(const char *fname) {
125 PATH_FSEC_PRINT, fname); 160 PATH_FSEC_PRINT, fname);
126 } 161 }
127 162
163 // save the file name in seccomp list
164 if (!load_file_list_flag)
165 seccomp_save_file_list(fname);
166
128 return 0; 167 return 0;
129errexit: 168errexit:
130 fprintf(stderr, "Error: cannot read %s\n", fname); 169 fprintf(stderr, "Error: cannot read %s\n", fname);
@@ -308,23 +347,45 @@ void seccomp_print_filter(pid_t pid) {
308 } 347 }
309 } 348 }
310 349
311 // find the seccomp filter 350 // find the seccomp list file
312 EUID_ROOT(); 351 EUID_ROOT();
313 char *fname; 352 char *fname;
314 if (asprintf(&fname, "/proc/%d/root%s", pid, RUN_SECCOMP_CFG) == -1) 353 if (asprintf(&fname, "/proc/%d/root%s", pid, RUN_SECCOMP_LIST) == -1)
315 errExit("asprintf"); 354 errExit("asprintf");
316 355
317 struct stat s; 356 struct stat s;
318 if (stat(fname, &s) == -1) { 357 if (stat(fname, &s) == -1)
319 printf("Cannot access seccomp filter.\n"); 358 goto errexit;
320 exit(1);
321 }
322 359
323 // read and print the filter - run this as root, the user doesn't have access 360 FILE *fp = fopen(fname, "r");
324 sbox_run(SBOX_ROOT | SBOX_SECCOMP, 2, PATH_FSEC_PRINT, fname); 361 if (!fp)
362 goto errexit;
325 free(fname); 363 free(fname);
326 364
365 char buf[MAXBUF];
366 while (fgets(buf, MAXBUF, fp)) {
367 // clean '\n'
368 char *ptr = strchr(buf, '\n');
369 if (ptr)
370 *ptr = '\0';
371
372 if (asprintf(&fname, "/proc/%d/root%s", pid, buf) == -1)
373 errExit("asprintf");
374 printf("FILE: %s\n", fname); fflush(0);
375
376 // read and print the filter - run this as root, the user doesn't have access
377 sbox_run(SBOX_ROOT | SBOX_SECCOMP, 2, PATH_FSEC_PRINT, fname);
378 fflush(0);
379
380 printf("\n"); fflush(0);
381 free(fname);
382 }
383 fclose(fp);
327 exit(0); 384 exit(0);
385
386errexit:
387 printf("Cannot access seccomp filter.\n");
388 exit(1);
328} 389}
329 390
330#endif // HAVE_SECCOMP 391#endif // HAVE_SECCOMP