aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--README2
-rw-r--r--RELNOTES4
-rw-r--r--etc/firejail.config4
-rw-r--r--etc/inc/disable-programs.inc10
-rw-r--r--etc/profile-a-l/alpine.profile104
-rw-r--r--etc/profile-a-l/alpinef.profile14
-rw-r--r--etc/profile-a-l/cargo.profile1
-rw-r--r--etc/profile-a-l/chromium-common.profile3
-rw-r--r--etc/profile-a-l/firefox.profile3
-rw-r--r--etc/profile-a-l/librewolf.profile3
-rw-r--r--etc/profile-m-z/minecraft-launcher.profile1
-rw-r--r--src/firecfg/firecfg.config2
-rw-r--r--src/firejail/appimage.c6
-rw-r--r--src/firejail/checkcfg.c5
-rw-r--r--src/firejail/dbus.c4
-rw-r--r--src/firejail/dhcp.c3
-rw-r--r--src/firejail/firejail.h6
-rw-r--r--src/firejail/fs.c33
-rw-r--r--src/firejail/fs_home.c99
-rw-r--r--src/firejail/fs_whitelist.c8
-rw-r--r--src/firejail/main.c25
-rw-r--r--src/firejail/profile.c14
-rw-r--r--src/firejail/sandbox.c2
-rw-r--r--src/firejail/seccomp.c5
-rw-r--r--src/firejail/util.c48
-rw-r--r--src/firejail/x11.c6
-rw-r--r--src/jailcheck/jailcheck.h2
-rw-r--r--src/jailcheck/main.c23
-rw-r--r--src/jailcheck/network.c56
-rw-r--r--src/man/firejail-profile.txt2
-rw-r--r--src/man/firejail.txt60
-rw-r--r--src/man/jailcheck.txt12
-rwxr-xr-xtest/environment/rlimit-bad-profile.exp2
-rwxr-xr-xtest/environment/rlimit-bad.exp2
-rwxr-xr-xtest/fs/fscheck-tmpfs.exp2
35 files changed, 468 insertions, 108 deletions
diff --git a/README b/README
index b8c0aef44..8284ce825 100644
--- a/README
+++ b/README
@@ -571,6 +571,8 @@ kortewegdevries (https://github.com/kortewegdevries)
571 - whitelisting evolution, kmail 571 - whitelisting evolution, kmail
572Kristóf Marussy (https://github.com/kris7t) 572Kristóf Marussy (https://github.com/kris7t)
573 - dns support 573 - dns support
574kuesji koesnu (https://github.com/kuesji)
575 - unit suffixes for rlimit-fsize and rlimit-as
574Kunal Mehta (https://github.com/legoktm) 576Kunal Mehta (https://github.com/legoktm)
575 - converted all links to https in manpages 577 - converted all links to https in manpages
576laniakea64 (https://github.com/laniakea64) 578laniakea64 (https://github.com/laniakea64)
diff --git a/RELNOTES b/RELNOTES
index c989b00ff..0a07e7bda 100644
--- a/RELNOTES
+++ b/RELNOTES
@@ -1,6 +1,10 @@
1firejail (0.9.65) baseline; urgency=low 1firejail (0.9.65) baseline; urgency=low
2 * deprecated --audit options, relpaced by jailcheck utility 2 * deprecated --audit options, relpaced by jailcheck utility
3 * deprecated follow-symlink-as-user from firejail.config 3 * deprecated follow-symlink-as-user from firejail.config
4 * new firejail.config settings: private-bin, private-etc
5 * new firejail.config settings: private-opt, private-srv
6 * new firejail.config settings: whitelist-disable-topdir
7 * new firejail.config settings: seccomp-filter-add
4 * rename --noautopulse to keep-config-pulse 8 * rename --noautopulse to keep-config-pulse
5 * filtering environment variables 9 * filtering environment variables
6 * zsh completion 10 * zsh completion
diff --git a/etc/firejail.config b/etc/firejail.config
index f5b3d5efa..43db49422 100644
--- a/etc/firejail.config
+++ b/etc/firejail.config
@@ -113,6 +113,10 @@
113# Enable or disable seccomp support, default enabled. 113# Enable or disable seccomp support, default enabled.
114# seccomp yes 114# seccomp yes
115 115
116# Add rules to the default seccomp filter. Same syntax as for --seccomp=
117# None by default; this is an example.
118# seccomp-filter-add !chroot,kcmp,mincore
119
116# Seccomp error action, kill, log or errno (EPERM, ENOSYS etc) 120# Seccomp error action, kill, log or errno (EPERM, ENOSYS etc)
117# seccomp-error-action EPERM 121# seccomp-error-action EPERM
118 122
diff --git a/etc/inc/disable-programs.inc b/etc/inc/disable-programs.inc
index 6fb62e017..0e575e5eb 100644
--- a/etc/inc/disable-programs.inc
+++ b/etc/inc/disable-programs.inc
@@ -39,6 +39,8 @@ blacklist ${HOME}/.WebStorm*
39blacklist ${HOME}/.Wolfram Research 39blacklist ${HOME}/.Wolfram Research
40blacklist ${HOME}/.ZAP 40blacklist ${HOME}/.ZAP
41blacklist ${HOME}/.abook 41blacklist ${HOME}/.abook
42blacklist ${HOME}/.addressbook
43blacklist ${HOME}/.alpine-smime
42blacklist ${HOME}/.aMule 44blacklist ${HOME}/.aMule
43blacklist ${HOME}/.android 45blacklist ${HOME}/.android
44blacklist ${HOME}/.anydesk 46blacklist ${HOME}/.anydesk
@@ -831,6 +833,14 @@ blacklist ${HOME}/.paradoxinteractive
831blacklist ${HOME}/.parallelrealities/blobwars 833blacklist ${HOME}/.parallelrealities/blobwars
832blacklist ${HOME}/.pcsxr 834blacklist ${HOME}/.pcsxr
833blacklist ${HOME}/.penguin-command 835blacklist ${HOME}/.penguin-command
836blacklist ${HOME}/.pine-crash
837blacklist ${HOME}/.pine-debug1
838blacklist ${HOME}/.pine-debug2
839blacklist ${HOME}/.pine-debug3
840blacklist ${HOME}/.pine-debug4
841blacklist ${HOME}/.pine-interrupted-mail
842blacklist ${HOME}/.pinerc
843blacklist ${HOME}/.pinercex
834blacklist ${HOME}/.pingus 844blacklist ${HOME}/.pingus
835blacklist ${HOME}/.pioneer 845blacklist ${HOME}/.pioneer
836blacklist ${HOME}/.purple 846blacklist ${HOME}/.purple
diff --git a/etc/profile-a-l/alpine.profile b/etc/profile-a-l/alpine.profile
new file mode 100644
index 000000000..0b5cf0df0
--- /dev/null
+++ b/etc/profile-a-l/alpine.profile
@@ -0,0 +1,104 @@
1# Firejail profile for alpine
2# Description: Text-based email and newsgroups reader
3# This file is overwritten after every install/update
4quiet
5# Persistent local customizations
6include alpine.local
7# Persistent global definitions
8include globals.local
9
10# Workaround for bug https://github.com/netblue30/firejail/issues/2747
11# firejail --private-bin=sh --include='${CFG}/allow-bin-sh.inc' --profile=alpine sh -c '(alpine)'
12
13noblacklist /var/mail
14noblacklist /var/spool/mail
15noblacklist ${DOCUMENTS}
16noblacklist ${HOME}/.addressbook
17noblacklist ${HOME}/.alpine-smime
18noblacklist ${HOME}/.mailcap
19noblacklist ${HOME}/.mh_profile
20noblacklist ${HOME}/.mime.types
21noblacklist ${HOME}/.newsrc
22noblacklist ${HOME}/.pine-crash
23noblacklist ${HOME}/.pine-debug1
24noblacklist ${HOME}/.pine-debug2
25noblacklist ${HOME}/.pine-debug3
26noblacklist ${HOME}/.pine-debug4
27noblacklist ${HOME}/.pine-interrupted-mail
28noblacklist ${HOME}/.pinerc
29noblacklist ${HOME}/.pinercex
30noblacklist ${HOME}/.signature
31noblacklist ${HOME}/mail
32
33blacklist /tmp/.X11-unix
34blacklist ${RUNUSER}/wayland-*
35
36include disable-common.inc
37include disable-devel.inc
38include disable-exec.inc
39include disable-interpreters.inc
40include disable-passwdmgr.inc
41include disable-programs.inc
42include disable-shell.inc
43include disable-xdg.inc
44
45#whitelist ${DOCUMENTS}
46#whitelist ${DOWNLOADS}
47#whitelist ${HOME}/.addressbook
48#whitelist ${HOME}/.alpine-smime
49#whitelist ${HOME}/.mailcap
50#whitelist ${HOME}/.mh_profile
51#whitelist ${HOME}/.mime.types
52#whitelist ${HOME}/.newsrc
53#whitelist ${HOME}/.pine-crash
54#whitelist ${HOME}/.pine-interrupted-mail
55#whitelist ${HOME}/.pinerc
56#whitelist ${HOME}/.pinercex
57#whitelist ${HOME}/.pine-debug1
58#whitelist ${HOME}/.pine-debug2
59#whitelist ${HOME}/.pine-debug3
60#whitelist ${HOME}/.pine-debug4
61#whitelist ${HOME}/.signature
62#whitelist ${HOME}/mail
63whitelist /var/mail
64whitelist /var/spool/mail
65#include whitelist-common.inc
66include whitelist-runuser-common.inc
67include whitelist-usr-share-common.inc
68include whitelist-var-common.inc
69
70apparmor
71caps.drop all
72ipc-namespace
73machine-id
74netfilter
75no3d
76nodvd
77nogroups
78noinput
79nonewprivs
80noroot
81nosound
82notv
83nou2f
84novideo
85protocol unix,inet,inet6
86seccomp
87seccomp.block-secondary
88shell none
89tracelog
90
91disable-mnt
92private-bin alpine
93private-cache
94private-dev
95private-etc alternatives,c-client.cf,ca-certificates,crypto-policies,host.conf,hostname,hosts,krb5.keytab,ld.so.cache,ld.so.conf,ld.so.conf.d,ld.so.preload,locale,locale.alias,locale.conf,localtime,mailcap,mime.types,nsswitch.conf,passwd,pine.conf,pinerc.fixed,pki,protocols,resolv.conf,rpc,services,ssl,terminfo,xdg
96private-tmp
97writable-run-user
98writable-var
99
100dbus-user none
101dbus-system none
102
103memory-deny-write-execute
104read-only ${HOME}/.signature
diff --git a/etc/profile-a-l/alpinef.profile b/etc/profile-a-l/alpinef.profile
new file mode 100644
index 000000000..97b97fe5f
--- /dev/null
+++ b/etc/profile-a-l/alpinef.profile
@@ -0,0 +1,14 @@
1# Firejail profile for alpinef
2# Description: Text-based email and newsgroups reader using function keys
3# This file is overwritten after every install/update
4quiet
5# Persistent local customizations
6include alpinef.local
7# Persistent global definitions
8# added by included profile
9#include globals.local
10
11private-bin alpinef
12
13# Redirect
14include alpine.profile
diff --git a/etc/profile-a-l/cargo.profile b/etc/profile-a-l/cargo.profile
index 043fd6718..7cf04c550 100644
--- a/etc/profile-a-l/cargo.profile
+++ b/etc/profile-a-l/cargo.profile
@@ -34,6 +34,7 @@ include disable-xdg.inc
34#whitelist ${HOME}/.cargo 34#whitelist ${HOME}/.cargo
35#whitelist ${HOME}/.rustup 35#whitelist ${HOME}/.rustup
36#include whitelist-common.inc 36#include whitelist-common.inc
37whitelist /usr/share/pkgconfig
37include whitelist-runuser-common.inc 38include whitelist-runuser-common.inc
38include whitelist-usr-share-common.inc 39include whitelist-usr-share-common.inc
39include whitelist-var-common.inc 40include whitelist-var-common.inc
diff --git a/etc/profile-a-l/chromium-common.profile b/etc/profile-a-l/chromium-common.profile
index f7493aa82..b0e0254d4 100644
--- a/etc/profile-a-l/chromium-common.profile
+++ b/etc/profile-a-l/chromium-common.profile
@@ -37,8 +37,9 @@ include whitelist-var-common.inc
37# Add the next line to your chromium-common.local if your kernel allows unprivileged userns clone. 37# Add the next line to your chromium-common.local if your kernel allows unprivileged userns clone.
38#include chromium-common-hardened.inc.profile 38#include chromium-common-hardened.inc.profile
39 39
40# Add the next line to your chromium-common.local to allow screen sharing under wayland. 40# Add the next two lines to your chromium-common.local to allow screen sharing under wayland.
41#whitelist ${RUNUSER}/pipewire-0 41#whitelist ${RUNUSER}/pipewire-0
42#whitelist /usr/share/pipewire/client.conf
42 43
43apparmor 44apparmor
44caps.keep sys_admin,sys_chroot 45caps.keep sys_admin,sys_chroot
diff --git a/etc/profile-a-l/firefox.profile b/etc/profile-a-l/firefox.profile
index 7874c882f..3ad67734d 100644
--- a/etc/profile-a-l/firefox.profile
+++ b/etc/profile-a-l/firefox.profile
@@ -56,8 +56,9 @@ dbus-user.own org.mpris.MediaPlayer2.firefox.*
56#dbus-user.own org.mpris.MediaPlayer2.plasma-browser-integration 56#dbus-user.own org.mpris.MediaPlayer2.plasma-browser-integration
57#dbus-user.talk org.kde.JobViewServer 57#dbus-user.talk org.kde.JobViewServer
58#dbus-user.talk org.kde.kuiserver 58#dbus-user.talk org.kde.kuiserver
59# Add the next two lines to your firefox.local to allow screen sharing under wayland. 59# Add the next three lines to your firefox.local to allow screen sharing under wayland.
60#whitelist ${RUNUSER}/pipewire-0 60#whitelist ${RUNUSER}/pipewire-0
61#whitelist /usr/share/pipewire/client.conf
61#dbus-user.talk org.freedesktop.portal.* 62#dbus-user.talk org.freedesktop.portal.*
62# Add the next line to your firefox.local if screen sharing sharing still does not work 63# Add the next line to your firefox.local if screen sharing sharing still does not work
63# with the above lines (might depend on the portal implementation). 64# with the above lines (might depend on the portal implementation).
diff --git a/etc/profile-a-l/librewolf.profile b/etc/profile-a-l/librewolf.profile
index 8e3e58f19..da047357a 100644
--- a/etc/profile-a-l/librewolf.profile
+++ b/etc/profile-a-l/librewolf.profile
@@ -44,8 +44,9 @@ dbus-user filter
44#dbus-user.own org.mpris.MediaPlayer2.plasma-browser-integration 44#dbus-user.own org.mpris.MediaPlayer2.plasma-browser-integration
45#dbus-user.talk org.kde.JobViewServer 45#dbus-user.talk org.kde.JobViewServer
46#dbus-user.talk org.kde.kuiserver 46#dbus-user.talk org.kde.kuiserver
47# Add the next lines to your librewolf.local to allow screensharing under Wayland. 47# Add the next three lines to your librewolf.local to allow screensharing under Wayland.
48#whitelist ${RUNUSER}/pipewire-0 48#whitelist ${RUNUSER}/pipewire-0
49#whitelist /usr/share/pipewire/client.conf
49#dbus-user.talk org.freedesktop.portal.* 50#dbus-user.talk org.freedesktop.portal.*
50# Also add the next line to your librewolf.local if screensharing does not work with 51# Also add the next line to your librewolf.local if screensharing does not work with
51# the above lines (depends on the portal implementation). 52# the above lines (depends on the portal implementation).
diff --git a/etc/profile-m-z/minecraft-launcher.profile b/etc/profile-m-z/minecraft-launcher.profile
index 2536d0b38..1028e374a 100644
--- a/etc/profile-m-z/minecraft-launcher.profile
+++ b/etc/profile-m-z/minecraft-launcher.profile
@@ -31,7 +31,6 @@ include whitelist-runuser-common.inc
31include whitelist-usr-share-common.inc 31include whitelist-usr-share-common.inc
32include whitelist-var-common.inc 32include whitelist-var-common.inc
33 33
34apparmor
35caps.drop all 34caps.drop all
36netfilter 35netfilter
37nodvd 36nodvd
diff --git a/src/firecfg/firecfg.config b/src/firecfg/firecfg.config
index f23488e20..e58fe39ec 100644
--- a/src/firecfg/firecfg.config
+++ b/src/firecfg/firecfg.config
@@ -38,6 +38,8 @@ abrowser
38akonadi_control 38akonadi_control
39akregator 39akregator
40alacarte 40alacarte
41alpine
42alpinef
41amarok 43amarok
42amule 44amule
43amuled 45amuled
diff --git a/src/firejail/appimage.c b/src/firejail/appimage.c
index e019de36f..056640eec 100644
--- a/src/firejail/appimage.c
+++ b/src/firejail/appimage.c
@@ -61,9 +61,13 @@ int appimage_find_profile(const char *archive) {
61 char *ptr = strchr(buf, '\n'); 61 char *ptr = strchr(buf, '\n');
62 if (ptr) 62 if (ptr)
63 *ptr = '\0'; 63 *ptr = '\0';
64 if (strcasestr(archive, buf)) 64 if (strcasestr(archive, buf)) {
65 fclose(fp);
65 return profile_find_firejail(buf, 1); 66 return profile_find_firejail(buf, 1);
67 }
66 } 68 }
69
70 fclose(fp);
67 return 0; 71 return 0;
68 72
69} 73}
diff --git a/src/firejail/checkcfg.c b/src/firejail/checkcfg.c
index f3ab0a6d8..1e9f4b641 100644
--- a/src/firejail/checkcfg.c
+++ b/src/firejail/checkcfg.c
@@ -35,6 +35,7 @@ char *xvfb_extra_params = "";
35char *netfilter_default = NULL; 35char *netfilter_default = NULL;
36unsigned long join_timeout = 5000000; // microseconds 36unsigned long join_timeout = 5000000; // microseconds
37char *config_seccomp_error_action_str = "EPERM"; 37char *config_seccomp_error_action_str = "EPERM";
38char *config_seccomp_filter_add = NULL;
38char **whitelist_reject_topdirs = NULL; 39char **whitelist_reject_topdirs = NULL;
39 40
40int checkcfg(int val) { 41int checkcfg(int val) {
@@ -225,6 +226,10 @@ int checkcfg(int val) {
225 else if (strncmp(ptr, "join-timeout ", 13) == 0) 226 else if (strncmp(ptr, "join-timeout ", 13) == 0)
226 join_timeout = strtoul(ptr + 13, NULL, 10) * 1000000; // seconds to microseconds 227 join_timeout = strtoul(ptr + 13, NULL, 10) * 1000000; // seconds to microseconds
227 228
229 // add rules to default seccomp filter
230 else if (strncmp(ptr, "seccomp-filter-add ", 19) == 0)
231 config_seccomp_filter_add = seccomp_check_list(ptr + 19);
232
228 // seccomp error action 233 // seccomp error action
229 else if (strncmp(ptr, "seccomp-error-action ", 21) == 0) { 234 else if (strncmp(ptr, "seccomp-error-action ", 21) == 0) {
230 if (strcmp(ptr + 21, "kill") == 0) 235 if (strcmp(ptr + 21, "kill") == 0)
diff --git a/src/firejail/dbus.c b/src/firejail/dbus.c
index bfa28fcba..9a4cb2e6b 100644
--- a/src/firejail/dbus.c
+++ b/src/firejail/dbus.c
@@ -470,7 +470,7 @@ void dbus_apply_policy(void) {
470 create_empty_dir_as_root(RUN_DBUS_DIR, 0755); 470 create_empty_dir_as_root(RUN_DBUS_DIR, 0755);
471 471
472 if (arg_dbus_user != DBUS_POLICY_ALLOW) { 472 if (arg_dbus_user != DBUS_POLICY_ALLOW) {
473 create_empty_file_as_root(RUN_DBUS_USER_SOCKET, 0700); 473 create_empty_file_as_root(RUN_DBUS_USER_SOCKET, 0600);
474 474
475 if (arg_dbus_user == DBUS_POLICY_FILTER) { 475 if (arg_dbus_user == DBUS_POLICY_FILTER) {
476 assert(dbus_user_proxy_socket != NULL); 476 assert(dbus_user_proxy_socket != NULL);
@@ -509,7 +509,7 @@ void dbus_apply_policy(void) {
509 } 509 }
510 510
511 if (arg_dbus_system != DBUS_POLICY_ALLOW) { 511 if (arg_dbus_system != DBUS_POLICY_ALLOW) {
512 create_empty_file_as_root(RUN_DBUS_SYSTEM_SOCKET, 0700); 512 create_empty_file_as_root(RUN_DBUS_SYSTEM_SOCKET, 0600);
513 513
514 if (arg_dbus_system == DBUS_POLICY_FILTER) { 514 if (arg_dbus_system == DBUS_POLICY_FILTER) {
515 assert(dbus_system_proxy_socket != NULL); 515 assert(dbus_system_proxy_socket != NULL);
diff --git a/src/firejail/dhcp.c b/src/firejail/dhcp.c
index 47dd39ac0..ec482e2ea 100644
--- a/src/firejail/dhcp.c
+++ b/src/firejail/dhcp.c
@@ -160,9 +160,6 @@ void dhcp_start(void) {
160 exit(1); 160 exit(1);
161 } 161 }
162 162
163 sbox_run(SBOX_ROOT| SBOX_SECCOMP, 4, PATH_FCOPY, "--follow-link", dhclient_path, RUN_MNT_DIR);
164 dhclient_path = RUN_MNT_DIR "/dhclient";
165
166 EUID_ROOT(); 163 EUID_ROOT();
167 if (mkdir(RUN_DHCLIENT_DIR, 0700)) 164 if (mkdir(RUN_DHCLIENT_DIR, 0700))
168 errExit("mkdir"); 165 errExit("mkdir");
diff --git a/src/firejail/firejail.h b/src/firejail/firejail.h
index 622be4d97..9971d30b6 100644
--- a/src/firejail/firejail.h
+++ b/src/firejail/firejail.h
@@ -5,7 +5,7 @@
5 * 5 *
6 * This program is free software; you can redistribute it and/or modify 6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by 7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; eithe r version 2 of the License, or 8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version. 9 * (at your option) any later version.
10 * 10 *
11 * This program is distributed in the hope that it will be useful, 11 * This program is distributed in the hope that it will be useful,
@@ -498,6 +498,7 @@ int macro_id(const char *name);
498void errLogExit(char* fmt, ...) __attribute__((noreturn)); 498void errLogExit(char* fmt, ...) __attribute__((noreturn));
499void fwarning(char* fmt, ...); 499void fwarning(char* fmt, ...);
500void fmessage(char* fmt, ...); 500void fmessage(char* fmt, ...);
501long long unsigned parse_arg_size(char *str);
501void drop_privs(int nogroups); 502void drop_privs(int nogroups);
502int mkpath_as_root(const char* path); 503int mkpath_as_root(const char* path);
503void extract_command_name(int index, char **argv); 504void extract_command_name(int index, char **argv);
@@ -507,7 +508,7 @@ void logargs(int argc, char **argv) ;
507void logerr(const char *msg); 508void logerr(const char *msg);
508void set_nice(int inc); 509void set_nice(int inc);
509int copy_file(const char *srcname, const char *destname, uid_t uid, gid_t gid, mode_t mode); 510int copy_file(const char *srcname, const char *destname, uid_t uid, gid_t gid, mode_t mode);
510void copy_file_as_user(const char *srcname, const char *destname, uid_t uid, gid_t gid, mode_t mode); 511void copy_file_as_user(const char *srcname, const char *destname, mode_t mode);
511void copy_file_from_user_to_root(const char *srcname, const char *destname, uid_t uid, gid_t gid, mode_t mode); 512void copy_file_from_user_to_root(const char *srcname, const char *destname, uid_t uid, gid_t gid, mode_t mode);
512void touch_file_as_user(const char *fname, mode_t mode); 513void touch_file_as_user(const char *fname, mode_t mode);
513int is_dir(const char *fname); 514int is_dir(const char *fname);
@@ -809,6 +810,7 @@ extern char *xvfb_extra_params;
809extern char *netfilter_default; 810extern char *netfilter_default;
810extern unsigned long join_timeout; 811extern unsigned long join_timeout;
811extern char *config_seccomp_error_action_str; 812extern char *config_seccomp_error_action_str;
813extern char *config_seccomp_filter_add;
812extern char **whitelist_reject_topdirs; 814extern char **whitelist_reject_topdirs;
813 815
814int checkcfg(int val); 816int checkcfg(int val);
diff --git a/src/firejail/fs.c b/src/firejail/fs.c
index 803b081c9..806fa9249 100644
--- a/src/firejail/fs.c
+++ b/src/firejail/fs.c
@@ -171,21 +171,28 @@ static void disable_file(OPERATION op, const char *filename) {
171 fs_remount_rec(fname, op); 171 fs_remount_rec(fname, op);
172 } 172 }
173 else if (op == MOUNT_TMPFS) { 173 else if (op == MOUNT_TMPFS) {
174 if (S_ISDIR(s.st_mode)) { 174 if (!S_ISDIR(s.st_mode)) {
175 if (getuid()) { 175 fwarning("%s is not a directory; cannot mount a tmpfs on top of it.\n", fname);
176 if (strncmp(cfg.homedir, fname, strlen(cfg.homedir)) != 0 || 176 free(fname);
177 fname[strlen(cfg.homedir)] != '/') { 177 return;
178 fprintf(stderr, "Error: tmpfs outside $HOME is only available for root\n"); 178 }
179 exit(1); 179
180 } 180 uid_t uid = getuid();
181 if (uid != 0) {
182 // only user owned directories in user home
183 if (s.st_uid != uid ||
184 strncmp(cfg.homedir, fname, strlen(cfg.homedir)) != 0 ||
185 fname[strlen(cfg.homedir)] != '/') {
186 fwarning("you are not allowed to mount a tmpfs on %s\n", fname);
187 free(fname);
188 return;
181 } 189 }
182 // fs_tmpfs returns with EUID 0
183 fs_tmpfs(fname, getuid());
184 selinux_relabel_path(fname, fname);
185 EUID_USER();
186 } 190 }
187 else 191
188 fwarning("%s is not a directory; cannot mount a tmpfs on top of it.\n", fname); 192 fs_tmpfs(fname, uid);
193 EUID_USER(); // fs_tmpfs returns with EUID 0
194
195 selinux_relabel_path(fname, fname);
189 } 196 }
190 else 197 else
191 assert(0); 198 assert(0);
diff --git a/src/firejail/fs_home.c b/src/firejail/fs_home.c
index eab952eb8..0ed476063 100644
--- a/src/firejail/fs_home.c
+++ b/src/firejail/fs_home.c
@@ -34,12 +34,13 @@
34#define O_PATH 010000000 34#define O_PATH 010000000
35#endif 35#endif
36 36
37static void skel(const char *homedir, uid_t u, gid_t g) { 37static void skel(const char *homedir) {
38 char *fname; 38 EUID_ASSERT();
39 39
40 // zsh 40 // zsh
41 if (!arg_shell_none && (strcmp(cfg.shell,"/usr/bin/zsh") == 0 || strcmp(cfg.shell,"/bin/zsh") == 0)) { 41 if (!arg_shell_none && (strcmp(cfg.shell,"/usr/bin/zsh") == 0 || strcmp(cfg.shell,"/bin/zsh") == 0)) {
42 // copy skel files 42 // copy skel files
43 char *fname;
43 if (asprintf(&fname, "%s/.zshrc", homedir) == -1) 44 if (asprintf(&fname, "%s/.zshrc", homedir) == -1)
44 errExit("asprintf"); 45 errExit("asprintf");
45 // don't copy it if we already have the file 46 // don't copy it if we already have the file
@@ -50,7 +51,7 @@ static void skel(const char *homedir, uid_t u, gid_t g) {
50 exit(1); 51 exit(1);
51 } 52 }
52 if (access("/etc/skel/.zshrc", R_OK) == 0) { 53 if (access("/etc/skel/.zshrc", R_OK) == 0) {
53 copy_file_as_user("/etc/skel/.zshrc", fname, u, g, 0644); // regular user 54 copy_file_as_user("/etc/skel/.zshrc", fname, 0644); // regular user
54 fs_logger("clone /etc/skel/.zshrc"); 55 fs_logger("clone /etc/skel/.zshrc");
55 fs_logger2("clone", fname); 56 fs_logger2("clone", fname);
56 } 57 }
@@ -64,6 +65,7 @@ static void skel(const char *homedir, uid_t u, gid_t g) {
64 // csh 65 // csh
65 else if (!arg_shell_none && strcmp(cfg.shell,"/bin/csh") == 0) { 66 else if (!arg_shell_none && strcmp(cfg.shell,"/bin/csh") == 0) {
66 // copy skel files 67 // copy skel files
68 char *fname;
67 if (asprintf(&fname, "%s/.cshrc", homedir) == -1) 69 if (asprintf(&fname, "%s/.cshrc", homedir) == -1)
68 errExit("asprintf"); 70 errExit("asprintf");
69 // don't copy it if we already have the file 71 // don't copy it if we already have the file
@@ -74,7 +76,7 @@ static void skel(const char *homedir, uid_t u, gid_t g) {
74 exit(1); 76 exit(1);
75 } 77 }
76 if (access("/etc/skel/.cshrc", R_OK) == 0) { 78 if (access("/etc/skel/.cshrc", R_OK) == 0) {
77 copy_file_as_user("/etc/skel/.cshrc", fname, u, g, 0644); // regular user 79 copy_file_as_user("/etc/skel/.cshrc", fname, 0644); // regular user
78 fs_logger("clone /etc/skel/.cshrc"); 80 fs_logger("clone /etc/skel/.cshrc");
79 fs_logger2("clone", fname); 81 fs_logger2("clone", fname);
80 } 82 }
@@ -88,6 +90,7 @@ static void skel(const char *homedir, uid_t u, gid_t g) {
88 // bash etc. 90 // bash etc.
89 else { 91 else {
90 // copy skel files 92 // copy skel files
93 char *fname;
91 if (asprintf(&fname, "%s/.bashrc", homedir) == -1) 94 if (asprintf(&fname, "%s/.bashrc", homedir) == -1)
92 errExit("asprintf"); 95 errExit("asprintf");
93 // don't copy it if we already have the file 96 // don't copy it if we already have the file
@@ -98,7 +101,7 @@ static void skel(const char *homedir, uid_t u, gid_t g) {
98 exit(1); 101 exit(1);
99 } 102 }
100 if (access("/etc/skel/.bashrc", R_OK) == 0) { 103 if (access("/etc/skel/.bashrc", R_OK) == 0) {
101 copy_file_as_user("/etc/skel/.bashrc", fname, u, g, 0644); // regular user 104 copy_file_as_user("/etc/skel/.bashrc", fname, 0644); // regular user
102 fs_logger("clone /etc/skel/.bashrc"); 105 fs_logger("clone /etc/skel/.bashrc");
103 fs_logger2("clone", fname); 106 fs_logger2("clone", fname);
104 } 107 }
@@ -108,6 +111,7 @@ static void skel(const char *homedir, uid_t u, gid_t g) {
108} 111}
109 112
110static int store_xauthority(void) { 113static int store_xauthority(void) {
114 EUID_ASSERT();
111 if (arg_x11_block) 115 if (arg_x11_block)
112 return 0; 116 return 0;
113 117
@@ -118,7 +122,7 @@ static int store_xauthority(void) {
118 errExit("asprintf"); 122 errExit("asprintf");
119 123
120 struct stat s; 124 struct stat s;
121 if (lstat_as_user(src, &s) == 0) { 125 if (lstat(src, &s) == 0) {
122 if (S_ISLNK(s.st_mode)) { 126 if (S_ISLNK(s.st_mode)) {
123 fwarning("invalid .Xauthority file\n"); 127 fwarning("invalid .Xauthority file\n");
124 free(src); 128 free(src);
@@ -126,6 +130,7 @@ static int store_xauthority(void) {
126 } 130 }
127 131
128 // create an empty file as root, and change ownership to user 132 // create an empty file as root, and change ownership to user
133 EUID_ROOT();
129 FILE *fp = fopen(dest, "we"); 134 FILE *fp = fopen(dest, "we");
130 if (fp) { 135 if (fp) {
131 fprintf(fp, "\n"); 136 fprintf(fp, "\n");
@@ -134,10 +139,11 @@ static int store_xauthority(void) {
134 } 139 }
135 else 140 else
136 errExit("fopen"); 141 errExit("fopen");
142 EUID_USER();
137 143
138 copy_file_as_user(src, dest, getuid(), getgid(), 0600); // regular user 144 copy_file_as_user(src, dest, 0600); // regular user
139 fs_logger2("clone", dest);
140 selinux_relabel_path(dest, src); 145 selinux_relabel_path(dest, src);
146 fs_logger2("clone", dest);
141 free(src); 147 free(src);
142 return 1; // file copied 148 return 1; // file copied
143 } 149 }
@@ -147,6 +153,7 @@ static int store_xauthority(void) {
147} 153}
148 154
149static int store_asoundrc(void) { 155static int store_asoundrc(void) {
156 EUID_ASSERT();
150 if (arg_nosound) 157 if (arg_nosound)
151 return 0; 158 return 0;
152 159
@@ -157,11 +164,11 @@ static int store_asoundrc(void) {
157 errExit("asprintf"); 164 errExit("asprintf");
158 165
159 struct stat s; 166 struct stat s;
160 if (lstat_as_user(src, &s) == 0) { 167 if (lstat(src, &s) == 0) {
161 if (S_ISLNK(s.st_mode)) { 168 if (S_ISLNK(s.st_mode)) {
162 // make sure the real path of the file is inside the home directory 169 // make sure the real path of the file is inside the home directory
163 /* coverity[toctou] */ 170 /* coverity[toctou] */
164 char *rp = realpath_as_user(src); 171 char *rp = realpath(src, NULL);
165 if (!rp) { 172 if (!rp) {
166 fprintf(stderr, "Error: Cannot access %s\n", src); 173 fprintf(stderr, "Error: Cannot access %s\n", src);
167 exit(1); 174 exit(1);
@@ -174,6 +181,7 @@ static int store_asoundrc(void) {
174 } 181 }
175 182
176 // create an empty file as root, and change ownership to user 183 // create an empty file as root, and change ownership to user
184 EUID_ROOT();
177 FILE *fp = fopen(dest, "we"); 185 FILE *fp = fopen(dest, "we");
178 if (fp) { 186 if (fp) {
179 fprintf(fp, "\n"); 187 fprintf(fp, "\n");
@@ -182,10 +190,11 @@ static int store_asoundrc(void) {
182 } 190 }
183 else 191 else
184 errExit("fopen"); 192 errExit("fopen");
193 EUID_USER();
185 194
186 copy_file_as_user(src, dest, getuid(), getgid(), 0644); // regular user 195 copy_file_as_user(src, dest, 0644); // regular user
187 selinux_relabel_path(dest, src);
188 fs_logger2("clone", dest); 196 fs_logger2("clone", dest);
197 selinux_relabel_path(dest, src);
189 free(src); 198 free(src);
190 return 1; // file copied 199 return 1; // file copied
191 } 200 }
@@ -195,6 +204,7 @@ static int store_asoundrc(void) {
195} 204}
196 205
197static void copy_xauthority(void) { 206static void copy_xauthority(void) {
207 EUID_ASSERT();
198 // copy XAUTHORITY_FILE in the new home directory 208 // copy XAUTHORITY_FILE in the new home directory
199 char *src = RUN_XAUTHORITY_FILE ; 209 char *src = RUN_XAUTHORITY_FILE ;
200 char *dest; 210 char *dest;
@@ -207,16 +217,18 @@ static void copy_xauthority(void) {
207 exit(1); 217 exit(1);
208 } 218 }
209 219
210 copy_file_as_user(src, dest, getuid(), getgid(), S_IRUSR | S_IWUSR); // regular user 220 copy_file_as_user(src, dest, S_IRUSR | S_IWUSR); // regular user
211 selinux_relabel_path(dest, src);
212 fs_logger2("clone", dest); 221 fs_logger2("clone", dest);
222 selinux_relabel_path(dest, dest);
213 free(dest); 223 free(dest);
214 224
215 // delete the temporary file 225 EUID_ROOT();
216 unlink(src); 226 unlink(src); // delete the temporary file
227 EUID_USER();
217} 228}
218 229
219static void copy_asoundrc(void) { 230static void copy_asoundrc(void) {
231 EUID_ASSERT();
220 // copy ASOUNDRC_FILE in the new home directory 232 // copy ASOUNDRC_FILE in the new home directory
221 char *src = RUN_ASOUNDRC_FILE ; 233 char *src = RUN_ASOUNDRC_FILE ;
222 char *dest; 234 char *dest;
@@ -229,13 +241,14 @@ static void copy_asoundrc(void) {
229 exit(1); 241 exit(1);
230 } 242 }
231 243
232 copy_file_as_user(src, dest, getuid(), getgid(), S_IRUSR | S_IWUSR); // regular user 244 copy_file_as_user(src, dest, S_IRUSR | S_IWUSR); // regular user
233 selinux_relabel_path(dest, src);
234 fs_logger2("clone", dest); 245 fs_logger2("clone", dest);
246 selinux_relabel_path(dest, dest);
235 free(dest); 247 free(dest);
236 248
237 // delete the temporary file 249 EUID_ROOT();
238 unlink(src); 250 unlink(src); // delete the temporary file
251 EUID_USER();
239} 252}
240 253
241// private mode (--private=homedir): 254// private mode (--private=homedir):
@@ -248,18 +261,18 @@ void fs_private_homedir(void) {
248 char *private_homedir = cfg.home_private; 261 char *private_homedir = cfg.home_private;
249 assert(homedir); 262 assert(homedir);
250 assert(private_homedir); 263 assert(private_homedir);
264 EUID_ASSERT();
265
266 uid_t u = getuid();
267 // gid_t g = getgid();
251 268
252 int xflag = store_xauthority(); 269 int xflag = store_xauthority();
253 int aflag = store_asoundrc(); 270 int aflag = store_asoundrc();
254 271
255 uid_t u = getuid();
256 gid_t g = getgid();
257
258 // mount bind private_homedir on top of homedir 272 // mount bind private_homedir on top of homedir
259 if (arg_debug) 273 if (arg_debug)
260 printf("Mount-bind %s on top of %s\n", private_homedir, homedir); 274 printf("Mount-bind %s on top of %s\n", private_homedir, homedir);
261 // get file descriptors for homedir and private_homedir, fails if there is any symlink 275 // get file descriptors for homedir and private_homedir, fails if there is any symlink
262 EUID_USER();
263 int src = safer_openat(-1, private_homedir, O_PATH|O_DIRECTORY|O_NOFOLLOW|O_CLOEXEC); 276 int src = safer_openat(-1, private_homedir, O_PATH|O_DIRECTORY|O_NOFOLLOW|O_CLOEXEC);
264 if (src == -1) 277 if (src == -1)
265 errExit("opening private directory"); 278 errExit("opening private directory");
@@ -287,6 +300,7 @@ void fs_private_homedir(void) {
287 EUID_ROOT(); 300 EUID_ROOT();
288 if (bind_mount_by_fd(src, dst)) 301 if (bind_mount_by_fd(src, dst))
289 errExit("mount bind"); 302 errExit("mount bind");
303 EUID_USER();
290 304
291 // check /proc/self/mountinfo to confirm the mount is ok 305 // check /proc/self/mountinfo to confirm the mount is ok
292 MountData *mptr = get_last_mount(); 306 MountData *mptr = get_last_mount();
@@ -305,6 +319,7 @@ void fs_private_homedir(void) {
305// if (chmod(homedir, s.st_mode) == -1) 319// if (chmod(homedir, s.st_mode) == -1)
306// errExit("mount-bind chmod"); 320// errExit("mount-bind chmod");
307 321
322 EUID_ROOT();
308 if (u != 0) { 323 if (u != 0) {
309 // mask /root 324 // mask /root
310 if (arg_debug) 325 if (arg_debug)
@@ -323,8 +338,9 @@ void fs_private_homedir(void) {
323 selinux_relabel_path("/home", "/home"); 338 selinux_relabel_path("/home", "/home");
324 fs_logger("tmpfs /home"); 339 fs_logger("tmpfs /home");
325 } 340 }
341 EUID_USER();
326 342
327 skel(homedir, u, g); 343 skel(homedir);
328 if (xflag) 344 if (xflag)
329 copy_xauthority(); 345 copy_xauthority();
330 if (aflag) 346 if (aflag)
@@ -339,12 +355,15 @@ void fs_private_homedir(void) {
339void fs_private(void) { 355void fs_private(void) {
340 char *homedir = cfg.homedir; 356 char *homedir = cfg.homedir;
341 assert(homedir); 357 assert(homedir);
358 EUID_ASSERT();
359
342 uid_t u = getuid(); 360 uid_t u = getuid();
343 gid_t g = getgid(); 361 gid_t g = getgid();
344 362
345 int xflag = store_xauthority(); 363 int xflag = store_xauthority();
346 int aflag = store_asoundrc(); 364 int aflag = store_asoundrc();
347 365
366 EUID_ROOT();
348 // mask /root 367 // mask /root
349 if (arg_debug) 368 if (arg_debug)
350 printf("Mounting a new /root directory\n"); 369 printf("Mounting a new /root directory\n");
@@ -387,8 +406,9 @@ void fs_private(void) {
387 406
388 selinux_relabel_path(homedir, homedir); 407 selinux_relabel_path(homedir, homedir);
389 } 408 }
409 EUID_USER();
390 410
391 skel(homedir, u, g); 411 skel(homedir);
392 if (xflag) 412 if (xflag)
393 copy_xauthority(); 413 copy_xauthority();
394 if (aflag) 414 if (aflag)
@@ -530,26 +550,29 @@ static void duplicate(char *name) {
530// set skel files, 550// set skel files,
531// restore .Xauthority 551// restore .Xauthority
532void fs_private_home_list(void) { 552void fs_private_home_list(void) {
533 timetrace_start();
534
535 char *homedir = cfg.homedir; 553 char *homedir = cfg.homedir;
536 char *private_list = cfg.home_private_keep; 554 char *private_list = cfg.home_private_keep;
537 assert(homedir); 555 assert(homedir);
538 assert(private_list); 556 assert(private_list);
557 EUID_ASSERT();
539 558
540 int xflag = store_xauthority(); 559 timetrace_start();
541 int aflag = store_asoundrc();
542 560
543 uid_t uid = getuid(); 561 uid_t uid = getuid();
544 gid_t gid = getgid(); 562 gid_t gid = getgid();
545 563
564 int xflag = store_xauthority();
565 int aflag = store_asoundrc();
566
546 // create /run/firejail/mnt/home directory 567 // create /run/firejail/mnt/home directory
568 EUID_ROOT();
547 mkdir_attr(RUN_HOME_DIR, 0755, uid, gid); 569 mkdir_attr(RUN_HOME_DIR, 0755, uid, gid);
548 selinux_relabel_path(RUN_HOME_DIR, homedir); 570 selinux_relabel_path(RUN_HOME_DIR, homedir);
571
549 fs_logger_print(); // save the current log 572 fs_logger_print(); // save the current log
573 EUID_USER();
550 574
551 // copy the list of files in the new home directory 575 // copy the list of files in the new home directory
552 EUID_USER();
553 if (arg_debug) 576 if (arg_debug)
554 printf("Copying files in the new home:\n"); 577 printf("Copying files in the new home:\n");
555 char *dlist = strdup(cfg.home_private_keep); 578 char *dlist = strdup(cfg.home_private_keep);
@@ -587,6 +610,7 @@ void fs_private_home_list(void) {
587 EUID_ROOT(); 610 EUID_ROOT();
588 if (bind_mount_path_to_fd(RUN_HOME_DIR, fd)) 611 if (bind_mount_path_to_fd(RUN_HOME_DIR, fd))
589 errExit("mount bind"); 612 errExit("mount bind");
613 EUID_USER();
590 close(fd); 614 close(fd);
591 615
592 // check /proc/self/mountinfo to confirm the mount is ok 616 // check /proc/self/mountinfo to confirm the mount is ok
@@ -595,11 +619,7 @@ void fs_private_home_list(void) {
595 errLogExit("invalid private-home mount"); 619 errLogExit("invalid private-home mount");
596 fs_logger2("tmpfs", homedir); 620 fs_logger2("tmpfs", homedir);
597 621
598 // mask RUN_HOME_DIR, it is writable and not noexec 622 EUID_ROOT();
599 if (mount("tmpfs", RUN_HOME_DIR, "tmpfs", MS_NOSUID | MS_NODEV | MS_STRICTATIME, "mode=755,gid=0") < 0)
600 errExit("mounting tmpfs");
601 fs_logger2("tmpfs", RUN_HOME_DIR);
602
603 if (uid != 0) { 623 if (uid != 0) {
604 // mask /root 624 // mask /root
605 if (arg_debug) 625 if (arg_debug)
@@ -619,7 +639,12 @@ void fs_private_home_list(void) {
619 fs_logger("tmpfs /home"); 639 fs_logger("tmpfs /home");
620 } 640 }
621 641
622 skel(homedir, uid, gid); 642 // mask RUN_HOME_DIR, it is writable and not noexec
643 if (mount("tmpfs", RUN_HOME_DIR, "tmpfs", MS_NOSUID | MS_NODEV | MS_STRICTATIME, "mode=755,gid=0") < 0)
644 errExit("mounting tmpfs");
645 EUID_USER();
646
647 skel(homedir);
623 if (xflag) 648 if (xflag)
624 copy_xauthority(); 649 copy_xauthority();
625 if (aflag) 650 if (aflag)
diff --git a/src/firejail/fs_whitelist.c b/src/firejail/fs_whitelist.c
index 370035a4d..943f275de 100644
--- a/src/firejail/fs_whitelist.c
+++ b/src/firejail/fs_whitelist.c
@@ -374,9 +374,11 @@ static void tmpfs_topdirs(const TopDir *topdirs) {
374 } 374 }
375 375
376 // user home directory 376 // user home directory
377 if (tmpfs_home) 377 if (tmpfs_home) {
378 // checks owner if outside /home 378 EUID_USER();
379 fs_private(); 379 fs_private(); // checks owner if outside /home
380 EUID_ROOT();
381 }
380 382
381 // /run/user/$UID directory 383 // /run/user/$UID directory
382 if (tmpfs_runuser) { 384 if (tmpfs_runuser) {
diff --git a/src/firejail/main.c b/src/firejail/main.c
index 86c6575e2..7b32f6f07 100644
--- a/src/firejail/main.c
+++ b/src/firejail/main.c
@@ -967,7 +967,7 @@ void filter_add_blacklist_override(int fd, int syscall, int arg, void *ptrarg, b
967static int check_postexec(const char *list) { 967static int check_postexec(const char *list) {
968 char *prelist, *postlist; 968 char *prelist, *postlist;
969 969
970 if (list) { 970 if (list && list[0]) {
971 syscalls_in_list(list, "@default-keep", -1, &prelist, &postlist, true); 971 syscalls_in_list(list, "@default-keep", -1, &prelist, &postlist, true);
972 if (postlist) 972 if (postlist)
973 return 1; 973 return 1;
@@ -1496,8 +1496,11 @@ int main(int argc, char **argv, char **envp) {
1496 arg_rlimit_nproc = 1; 1496 arg_rlimit_nproc = 1;
1497 } 1497 }
1498 else if (strncmp(argv[i], "--rlimit-fsize=", 15) == 0) { 1498 else if (strncmp(argv[i], "--rlimit-fsize=", 15) == 0) {
1499 check_unsigned(argv[i] + 15, "Error: invalid rlimit"); 1499 cfg.rlimit_fsize = parse_arg_size(argv[i] + 15);
1500 sscanf(argv[i] + 15, "%llu", &cfg.rlimit_fsize); 1500 if (cfg.rlimit_fsize == 0) {
1501 perror("Error: invalid rlimit-fsize. Only use positive numbers and k, m or g suffix.");
1502 exit(1);
1503 }
1501 arg_rlimit_fsize = 1; 1504 arg_rlimit_fsize = 1;
1502 } 1505 }
1503 else if (strncmp(argv[i], "--rlimit-sigpending=", 20) == 0) { 1506 else if (strncmp(argv[i], "--rlimit-sigpending=", 20) == 0) {
@@ -1506,8 +1509,11 @@ int main(int argc, char **argv, char **envp) {
1506 arg_rlimit_sigpending = 1; 1509 arg_rlimit_sigpending = 1;
1507 } 1510 }
1508 else if (strncmp(argv[i], "--rlimit-as=", 12) == 0) { 1511 else if (strncmp(argv[i], "--rlimit-as=", 12) == 0) {
1509 check_unsigned(argv[i] + 12, "Error: invalid rlimit"); 1512 cfg.rlimit_as = parse_arg_size(argv[i] + 12);
1510 sscanf(argv[i] + 12, "%llu", &cfg.rlimit_as); 1513 if (cfg.rlimit_as == 0) {
1514 perror("Error: invalid rlimit-as. Only use positive numbers and k, m or g suffix.");
1515 exit(1);
1516 }
1511 arg_rlimit_as = 1; 1517 arg_rlimit_as = 1;
1512 } 1518 }
1513 else if (strncmp(argv[i], "--ipc-namespace", 15) == 0) 1519 else if (strncmp(argv[i], "--ipc-namespace", 15) == 0)
@@ -2889,6 +2895,15 @@ int main(int argc, char **argv, char **envp) {
2889 // check network configuration options - it will exit if anything went wrong 2895 // check network configuration options - it will exit if anything went wrong
2890 net_check_cfg(); 2896 net_check_cfg();
2891 2897
2898 // customization of default seccomp filter
2899 if (config_seccomp_filter_add) {
2900 if (arg_seccomp && !cfg.seccomp_list_keep && !cfg.seccomp_list_drop)
2901 profile_list_augment(&cfg.seccomp_list, config_seccomp_filter_add);
2902
2903 if (arg_seccomp32 && !cfg.seccomp_list_keep32 && !cfg.seccomp_list_drop32)
2904 profile_list_augment(&cfg.seccomp_list32, config_seccomp_filter_add);
2905 }
2906
2892 if (arg_seccomp) 2907 if (arg_seccomp)
2893 arg_seccomp_postexec = check_postexec(cfg.seccomp_list) || check_postexec(cfg.seccomp_list_drop); 2908 arg_seccomp_postexec = check_postexec(cfg.seccomp_list) || check_postexec(cfg.seccomp_list_drop);
2894 2909
diff --git a/src/firejail/profile.c b/src/firejail/profile.c
index 8675a1712..7b21eb387 100644
--- a/src/firejail/profile.c
+++ b/src/firejail/profile.c
@@ -1510,8 +1510,11 @@ int profile_check_line(char *ptr, int lineno, const char *fname) {
1510 arg_rlimit_nproc = 1; 1510 arg_rlimit_nproc = 1;
1511 } 1511 }
1512 else if (strncmp(ptr, "rlimit-fsize ", 13) == 0) { 1512 else if (strncmp(ptr, "rlimit-fsize ", 13) == 0) {
1513 check_unsigned(ptr + 13, "Error: invalid rlimit in profile file: "); 1513 cfg.rlimit_fsize = parse_arg_size(ptr + 13);
1514 sscanf(ptr + 13, "%llu", &cfg.rlimit_fsize); 1514 if (cfg.rlimit_fsize == 0) {
1515 perror("Error: invalid rlimit-fsize in profile file. Only use positive numbers and k, m or g suffix.");
1516 exit(1);
1517 }
1515 arg_rlimit_fsize = 1; 1518 arg_rlimit_fsize = 1;
1516 } 1519 }
1517 else if (strncmp(ptr, "rlimit-sigpending ", 18) == 0) { 1520 else if (strncmp(ptr, "rlimit-sigpending ", 18) == 0) {
@@ -1520,8 +1523,11 @@ int profile_check_line(char *ptr, int lineno, const char *fname) {
1520 arg_rlimit_sigpending = 1; 1523 arg_rlimit_sigpending = 1;
1521 } 1524 }
1522 else if (strncmp(ptr, "rlimit-as ", 10) == 0) { 1525 else if (strncmp(ptr, "rlimit-as ", 10) == 0) {
1523 check_unsigned(ptr + 10, "Error: invalid rlimit in profile file: "); 1526 cfg.rlimit_as = parse_arg_size(ptr + 10);
1524 sscanf(ptr + 10, "%llu", &cfg.rlimit_as); 1527 if (cfg.rlimit_as == 0) {
1528 perror("Error: invalid rlimit-as in profile file. Only use positive numbers and k, m or g suffix.");
1529 exit(1);
1530 }
1525 arg_rlimit_as = 1; 1531 arg_rlimit_as = 1;
1526 } 1532 }
1527 else { 1533 else {
diff --git a/src/firejail/sandbox.c b/src/firejail/sandbox.c
index 7bf372a14..99abce57f 100644
--- a/src/firejail/sandbox.c
+++ b/src/firejail/sandbox.c
@@ -840,6 +840,7 @@ int sandbox(void* sandbox_arg) {
840 // private mode 840 // private mode
841 //**************************** 841 //****************************
842 if (arg_private) { 842 if (arg_private) {
843 EUID_USER();
843 if (cfg.home_private) { // --private= 844 if (cfg.home_private) { // --private=
844 if (cfg.chrootdir) 845 if (cfg.chrootdir)
845 fwarning("private=directory feature is disabled in chroot\n"); 846 fwarning("private=directory feature is disabled in chroot\n");
@@ -858,6 +859,7 @@ int sandbox(void* sandbox_arg) {
858 } 859 }
859 else // --private 860 else // --private
860 fs_private(); 861 fs_private();
862 EUID_ROOT();
861 } 863 }
862 864
863 if (arg_private_dev) 865 if (arg_private_dev)
diff --git a/src/firejail/seccomp.c b/src/firejail/seccomp.c
index 9670fe816..3d9bf9082 100644
--- a/src/firejail/seccomp.c
+++ b/src/firejail/seccomp.c
@@ -208,7 +208,8 @@ int seccomp_filter_drop(bool native) {
208 // - seccomp 208 // - seccomp
209 if (cfg.seccomp_list_drop == NULL) { 209 if (cfg.seccomp_list_drop == NULL) {
210 // default seccomp if error action is not changed 210 // default seccomp if error action is not changed
211 if (cfg.seccomp_list == NULL && arg_seccomp_error_action == DEFAULT_SECCOMP_ERROR_ACTION) { 211 if ((cfg.seccomp_list == NULL || cfg.seccomp_list[0] == '\0')
212 && arg_seccomp_error_action == DEFAULT_SECCOMP_ERROR_ACTION) {
212 if (arg_seccomp_block_secondary) 213 if (arg_seccomp_block_secondary)
213 seccomp_filter_block_secondary(); 214 seccomp_filter_block_secondary();
214 else { 215 else {
@@ -261,7 +262,7 @@ int seccomp_filter_drop(bool native) {
261 } 262 }
262 263
263 // build the seccomp filter as a regular user 264 // build the seccomp filter as a regular user
264 if (list) 265 if (list && list[0])
265 if (arg_allow_debuggers) 266 if (arg_allow_debuggers)
266 rv = sbox_run(SBOX_USER | SBOX_CAPS_NONE | SBOX_SECCOMP, 7, 267 rv = sbox_run(SBOX_USER | SBOX_CAPS_NONE | SBOX_SECCOMP, 7,
267 PATH_FSECCOMP, command, "drop", filter, postexec_filter, list, "allow-debuggers"); 268 PATH_FSECCOMP, command, "drop", filter, postexec_filter, list, "allow-debuggers");
diff --git a/src/firejail/util.c b/src/firejail/util.c
index 71dd84e8f..55998e6c3 100644
--- a/src/firejail/util.c
+++ b/src/firejail/util.c
@@ -31,6 +31,9 @@
31#include <sys/wait.h> 31#include <sys/wait.h>
32#include <limits.h> 32#include <limits.h>
33 33
34#include <string.h>
35#include <ctype.h>
36
34#include <fcntl.h> 37#include <fcntl.h>
35#ifndef O_PATH 38#ifndef O_PATH
36#define O_PATH 010000000 39#define O_PATH 010000000
@@ -50,6 +53,44 @@
50#define EMPTY_STRING ("") 53#define EMPTY_STRING ("")
51 54
52 55
56long long unsigned parse_arg_size(char *str) {
57 long long unsigned result = 0;
58 int len = strlen(str);
59 sscanf(str, "%llu", &result);
60
61 char suffix = *(str + len - 1);
62 if (!isdigit(suffix) && (suffix == 'k' || suffix == 'm' || suffix == 'g')) {
63 len -= 1;
64 }
65
66 /* checks for is value valid positive number */
67 for (int i = 0; i < len; i++) {
68 if (!isdigit(*(str+i))) {
69 return 0;
70 }
71 }
72
73 if (isdigit(suffix))
74 return result;
75
76 switch (suffix) {
77 case 'k':
78 result *= 1024;
79 break;
80 case 'm':
81 result *= 1024 * 1024;
82 break;
83 case 'g':
84 result *= 1024 * 1024 * 1024;
85 break;
86 default:
87 result = 0;
88 break;
89 }
90
91 return result;
92}
93
53// send the error to /var/log/auth.log and exit after a small delay 94// send the error to /var/log/auth.log and exit after a small delay
54void errLogExit(char* fmt, ...) { 95void errLogExit(char* fmt, ...) {
55 va_list args; 96 va_list args;
@@ -329,7 +370,7 @@ int copy_file(const char *srcname, const char *destname, uid_t uid, gid_t gid, m
329} 370}
330 371
331// return -1 if error, 0 if no error 372// return -1 if error, 0 if no error
332void copy_file_as_user(const char *srcname, const char *destname, uid_t uid, gid_t gid, mode_t mode) { 373void copy_file_as_user(const char *srcname, const char *destname, mode_t mode) {
333 pid_t child = fork(); 374 pid_t child = fork();
334 if (child < 0) 375 if (child < 0)
335 errExit("fork"); 376 errExit("fork");
@@ -337,8 +378,8 @@ void copy_file_as_user(const char *srcname, const char *destname, uid_t uid, gid
337 // drop privileges 378 // drop privileges
338 drop_privs(0); 379 drop_privs(0);
339 380
340 // copy, set permissions and ownership 381 // copy, set permissions
341 int rv = copy_file(srcname, destname, uid, gid, mode); // already a regular user 382 int rv = copy_file(srcname, destname, -1, -1, mode); // already a regular user
342 if (rv) 383 if (rv)
343 fwarning("cannot copy %s\n", srcname); 384 fwarning("cannot copy %s\n", srcname);
344#ifdef HAVE_GCOV 385#ifdef HAVE_GCOV
@@ -1190,6 +1231,7 @@ unsigned extract_timeout(const char *str) {
1190} 1231}
1191 1232
1192void disable_file_or_dir(const char *fname) { 1233void disable_file_or_dir(const char *fname) {
1234 assert(geteuid() == 0);
1193 assert(fname); 1235 assert(fname);
1194 1236
1195 EUID_USER(); 1237 EUID_USER();
diff --git a/src/firejail/x11.c b/src/firejail/x11.c
index 0619ff380..896aa2fd3 100644
--- a/src/firejail/x11.c
+++ b/src/firejail/x11.c
@@ -1290,9 +1290,11 @@ void x11_xorg(void) {
1290 if (envar) { 1290 if (envar) {
1291 char *rp = realpath(envar, NULL); 1291 char *rp = realpath(envar, NULL);
1292 if (rp) { 1292 if (rp) {
1293 if (strcmp(rp, dest) != 0) 1293 if (strcmp(rp, dest) != 0) {
1294 // disable_file_or_dir returns with EUID 0 1294 EUID_ROOT();
1295 disable_file_or_dir(rp); 1295 disable_file_or_dir(rp);
1296 EUID_USER();
1297 }
1296 free(rp); 1298 free(rp);
1297 } 1299 }
1298 } 1300 }
diff --git a/src/jailcheck/jailcheck.h b/src/jailcheck/jailcheck.h
index 32be1c978..be3104da3 100644
--- a/src/jailcheck/jailcheck.h
+++ b/src/jailcheck/jailcheck.h
@@ -53,6 +53,8 @@ void apparmor_test(pid_t pid);
53// seccomp.c 53// seccomp.c
54void seccomp_test(pid_t pid); 54void seccomp_test(pid_t pid);
55 55
56// network.c
57void network_test(void);
56// utils.c 58// utils.c
57char *get_sudo_user(void); 59char *get_sudo_user(void);
58char *get_homedir(const char *user, uid_t *uid, gid_t *gid); 60char *get_homedir(const char *user, uid_t *uid, gid_t *gid);
diff --git a/src/jailcheck/main.c b/src/jailcheck/main.c
index 4d642bf96..812ac5808 100644
--- a/src/jailcheck/main.c
+++ b/src/jailcheck/main.c
@@ -157,6 +157,7 @@ int main(int argc, char **argv) {
157 seccomp_test(pid); 157 seccomp_test(pid);
158 fflush(0); 158 fflush(0);
159 159
160 // filesystem tests
160 pid_t child = fork(); 161 pid_t child = fork();
161 if (child == -1) 162 if (child == -1)
162 errExit("fork"); 163 errExit("fork");
@@ -185,6 +186,28 @@ int main(int argc, char **argv) {
185 } 186 }
186 int status; 187 int status;
187 wait(&status); 188 wait(&status);
189
190 // network test
191 child = fork();
192 if (child == -1)
193 errExit("fork");
194 if (child == 0) {
195 int rv = join_namespace(pid, "net");
196 if (rv == 0)
197 network_test();
198 else {
199 printf(" Error: I cannot join the process network stack\n");
200 exit(1);
201 }
202
203 // drop privileges in order not to trigger cleanup()
204 if (setgid(user_gid) != 0)
205 errExit("setgid");
206 if (setuid(user_uid) != 0)
207 errExit("setuid");
208 return 0;
209 }
210 wait(&status);
188 } 211 }
189 } 212 }
190 213
diff --git a/src/jailcheck/network.c b/src/jailcheck/network.c
new file mode 100644
index 000000000..636344e77
--- /dev/null
+++ b/src/jailcheck/network.c
@@ -0,0 +1,56 @@
1/*
2 * Copyright (C) 2014-2021 Firejail Authors
3 *
4 * This file is part of firejail project
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License along
17 * with this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19*/
20#include "jailcheck.h"
21#include <netdb.h>
22#include <arpa/inet.h>
23#include <ifaddrs.h>
24#include <net/if.h>
25#include <linux/connector.h>
26#include <linux/netlink.h>
27#include <linux/if_link.h>
28#include <linux/sockios.h>
29#include <sys/ioctl.h>
30
31
32void network_test(void) {
33 // I am root running in a network namespace
34 struct ifaddrs *ifaddr, *ifa;
35 int found = 0;
36
37 // walk through the linked list
38 if (getifaddrs(&ifaddr) == -1)
39 errExit("getifaddrs");
40 for (ifa = ifaddr; ifa != NULL; ifa = ifa->ifa_next) {
41 if (strcmp(ifa->ifa_name, "lo") == 0)
42 continue;
43 found = 1;
44 break;
45 }
46
47 freeifaddrs(ifaddr);
48
49 if (found)
50 printf(" Networking: enabled\n");
51 else
52 printf(" Networking: disabled\n");
53}
54
55
56
diff --git a/src/man/firejail-profile.txt b/src/man/firejail-profile.txt
index 6f3bef7f2..db58e0910 100644
--- a/src/man/firejail-profile.txt
+++ b/src/man/firejail-profile.txt
@@ -420,7 +420,7 @@ Make directory or file read-only.
420Make directory or file read-write. 420Make directory or file read-write.
421.TP 421.TP
422\fBtmpfs directory 422\fBtmpfs directory
423Mount an empty tmpfs filesystem on top of directory. This option is available only when running the sandbox as root. 423Mount an empty tmpfs filesystem on top of directory. Directories outside user home or not owned by the user are not allowed. Sandboxes running as root are exempt from these restrictions.
424.TP 424.TP
425\fBtracelog 425\fBtracelog
426Blacklist violations logged to syslog. 426Blacklist violations logged to syslog.
diff --git a/src/man/firejail.txt b/src/man/firejail.txt
index 3212a88e4..0462705c0 100644
--- a/src/man/firejail.txt
+++ b/src/man/firejail.txt
@@ -2129,6 +2129,7 @@ $ firejail --read-only=~/test --read-write=~/test/a
2129.TP 2129.TP
2130\fB\-\-rlimit-as=number 2130\fB\-\-rlimit-as=number
2131Set the maximum size of the process's virtual memory (address space) in bytes. 2131Set the maximum size of the process's virtual memory (address space) in bytes.
2132Use k(ilobyte), m(egabyte) or g(igabyte) for size suffix (base 1024).
2132 2133
2133.TP 2134.TP
2134\fB\-\-rlimit-cpu=number 2135\fB\-\-rlimit-cpu=number
@@ -2142,6 +2143,7 @@ track of CPU seconds for each process independently.
2142.TP 2143.TP
2143\fB\-\-rlimit-fsize=number 2144\fB\-\-rlimit-fsize=number
2144Set the maximum file size that can be created by a process. 2145Set the maximum file size that can be created by a process.
2146Use k(ilobyte), m(egabyte) or g(igabyte) for size suffix (base 1024).
2145.TP 2147.TP
2146\fB\-\-rlimit-nofile=number 2148\fB\-\-rlimit-nofile=number
2147Set the maximum number of files that can be opened by a process. 2149Set the maximum number of files that can be opened by a process.
@@ -2176,7 +2178,7 @@ $ firejail \-\-net=eth0 \-\-scan
2176.TP 2178.TP
2177\fB\-\-seccomp 2179\fB\-\-seccomp
2178Enable seccomp filter and blacklist the syscalls in the default list, 2180Enable seccomp filter and blacklist the syscalls in the default list,
2179which is @default-nodebuggers unless allow-debuggers is specified, 2181which is @default-nodebuggers unless \-\-allow-debuggers is specified,
2180then it is @default. 2182then it is @default.
2181 2183
2182.br 2184.br
@@ -2187,18 +2189,13 @@ system call groups are defined: @aio, @basic-io, @chown, @clock,
2187@network-io, @obsolete, @privileged, @process, @raw-io, @reboot, 2189@network-io, @obsolete, @privileged, @process, @raw-io, @reboot,
2188@resources, @setuid, @swap, @sync, @system-service and @timer. 2190@resources, @setuid, @swap, @sync, @system-service and @timer.
2189More information about groups can be found in /usr/share/doc/firejail/syscalls.txt 2191More information about groups can be found in /usr/share/doc/firejail/syscalls.txt
2190 2192.br
2191In addition, a system call can be specified by its number instead of
2192name with prefix $, so for example $165 would be equal to mount on i386.
2193Exceptions can be allowed with prefix !.
2194 2193
2195.br 2194.br
2196System architecture is strictly imposed only if flag 2195System architecture is strictly imposed only if flag
2197\-\-seccomp.block-secondary is used. The filter is applied at run time 2196\-\-seccomp.block-secondary is used. The filter is applied at run time
2198only if the correct architecture was detected. For the case of I386 2197only if the correct architecture was detected. For the case of I386
2199and AMD64 both 32-bit and 64-bit filters are installed. On a 64 bit 2198and AMD64 both 32-bit and 64-bit filters are installed.
2200architecture, an additional filter for 32 bit system calls can be
2201installed with \-\-seccomp.32.
2202.br 2199.br
2203 2200
2204.br 2201.br
@@ -2209,11 +2206,18 @@ Firejail will print seccomp violations to the audit log if the kernel was compil
2209Example: 2206Example:
2210.br 2207.br
2211$ firejail \-\-seccomp 2208$ firejail \-\-seccomp
2209.br
2210
2211.br
2212The default list can be customized, see \-\-seccomp= for a description. It can be customized
2213also globally in /etc/firejail/firejail.config file.
2214
2212.TP 2215.TP
2213\fB\-\-seccomp=syscall,@group,!syscall2 2216\fB\-\-seccomp=syscall,@group,!syscall2
2214Enable seccomp filter, whitelist "syscall2", but blacklist the default 2217Enable seccomp filter, blacklist the default list and the syscalls or syscall groups
2215list and the syscalls or syscall groups specified by the 2218specified by the command, but don't blacklist "syscall2". On a 64 bit
2216command. 2219architecture, an additional filter for 32 bit system calls can be
2220installed with \-\-seccomp.32.
2217.br 2221.br
2218 2222
2219.br 2223.br
@@ -2223,6 +2227,13 @@ $ firejail \-\-seccomp=utime,utimensat,utimes firefox
2223.br 2227.br
2224$ firejail \-\-seccomp=@clock,mkdir,unlinkat transmission-gtk 2228$ firejail \-\-seccomp=@clock,mkdir,unlinkat transmission-gtk
2225.br 2229.br
2230$ firejail '\-\-seccomp=@ipc,!pipe,!pipe2' audacious
2231.br
2232
2233.br
2234Syscalls can be specified by their number if prefix $ is added,
2235so for example $165 would be equal to mount on i386.
2236.br
2226 2237
2227.br 2238.br
2228Instead of dropping the syscall by returning EPERM, another error 2239Instead of dropping the syscall by returning EPERM, another error
@@ -2235,6 +2246,7 @@ by using \fBsyscall:kill\fR syntax, or the attempt may be logged with
2235 2246
2236.br 2247.br
2237Example: 2248Example:
2249.br
2238$ firejail \-\-seccomp=unlinkat:ENOENT,utimensat,utimes 2250$ firejail \-\-seccomp=unlinkat:ENOENT,utimensat,utimes
2239.br 2251.br
2240Parent pid 10662, child pid 10663 2252Parent pid 10662, child pid 10663
@@ -2243,9 +2255,13 @@ Child process initialized
2243.br 2255.br
2244$ touch testfile 2256$ touch testfile
2245.br 2257.br
2258$ ls testfile
2259.br
2260testfile
2261.br
2246$ rm testfile 2262$ rm testfile
2247.br 2263.br
2248rm: cannot remove `testfile': Operation not permitted 2264rm: cannot remove `testfile': No such file or directory
2249.br 2265.br
2250 2266
2251.br 2267.br
@@ -2258,7 +2274,7 @@ filters.
2258.br 2274.br
2259Example: 2275Example:
2260.br 2276.br
2261$ firejail \-\-noprofile \-\-shell=none \-\-seccomp=execve bash 2277$ firejail \-\-noprofile \-\-shell=none \-\-seccomp=execve sh
2262.br 2278.br
2263Parent pid 32751, child pid 32752 2279Parent pid 32751, child pid 32752
2264.br 2280.br
@@ -2270,8 +2286,7 @@ Child process initialized in 46.44 ms
2270.br 2286.br
2271$ ls 2287$ ls
2272.br 2288.br
2273Bad system call 2289Operation not permitted
2274.br
2275 2290
2276.TP 2291.TP
2277\fB\-\-seccomp.block-secondary 2292\fB\-\-seccomp.block-secondary
@@ -2315,15 +2330,15 @@ Child process initialized
2315.br 2330.br
2316$ touch testfile 2331$ touch testfile
2317.br 2332.br
2333$ ls testfile
2334.br
2335testfile
2336.br
2318$ rm testfile 2337$ rm testfile
2319.br 2338.br
2320rm: cannot remove `testfile': Operation not permitted 2339rm: cannot remove `testfile': No such file or directory
2321.br 2340.br
2322 2341
2323
2324
2325
2326
2327.TP 2342.TP
2328\fB\-\-seccomp.keep=syscall,@group,!syscall2 2343\fB\-\-seccomp.keep=syscall,@group,!syscall2
2329Enable seccomp filter, blacklist all syscall not listed and "syscall2". 2344Enable seccomp filter, blacklist all syscall not listed and "syscall2".
@@ -2566,14 +2581,13 @@ Kill the sandbox automatically after the time has elapsed. The time is specified
2566$ firejail \-\-timeout=01:30:00 firefox 2581$ firejail \-\-timeout=01:30:00 firefox
2567.TP 2582.TP
2568\fB\-\-tmpfs=dirname 2583\fB\-\-tmpfs=dirname
2569Mount a writable tmpfs filesystem on directory dirname. This option is available only when running the sandbox as root. 2584Mount a writable tmpfs filesystem on directory dirname. Directories outside user home or not owned by the user are not allowed. Sandboxes running as root are exempt from these restrictions. File globbing is supported, see \fBFILE GLOBBING\fR section for more details.
2570File globbing is supported, see \fBFILE GLOBBING\fR section for more details.
2571.br 2585.br
2572 2586
2573.br 2587.br
2574Example: 2588Example:
2575.br 2589.br
2576# firejail \-\-tmpfs=/var 2590$ firejail \-\-tmpfs=~/.local/share
2577.TP 2591.TP
2578\fB\-\-top 2592\fB\-\-top
2579Monitor the most CPU-intensive sandboxes, see \fBMONITORING\fR section for more details. 2593Monitor the most CPU-intensive sandboxes, see \fBMONITORING\fR section for more details.
diff --git a/src/man/jailcheck.txt b/src/man/jailcheck.txt
index c80e305cc..483f47fb9 100644
--- a/src/man/jailcheck.txt
+++ b/src/man/jailcheck.txt
@@ -23,6 +23,8 @@ them from inside the sandbox.
23.TP 23.TP
24\fB5. Seccomp test 24\fB5. Seccomp test
25.TP 25.TP
26\fB6. Networking test
27.TP
26The program is started as root using sudo. 28The program is started as root using sudo.
27 29
28.SH OPTIONS 30.SH OPTIONS
@@ -56,6 +58,8 @@ $ sudo jailcheck
56.br 58.br
57 Warning: I can run programs in /home/netblue 59 Warning: I can run programs in /home/netblue
58.br 60.br
61 Networking: disabled
62.br
59 63
60.br 64.br
612055:netblue::firejail /usr/bin/ssh -X netblue@x.y.z.net 652055:netblue::firejail /usr/bin/ssh -X netblue@x.y.z.net
@@ -64,12 +68,16 @@ $ sudo jailcheck
64.br 68.br
65 Warning: I can read ~/.ssh 69 Warning: I can read ~/.ssh
66.br 70.br
71 Networking: enabled
72.br
67 73
68.br 74.br
692186:netblue:libreoffice:firejail --appimage /opt/LibreOffice-fresh.appimage 752186:netblue:libreoffice:firejail --appimage /opt/LibreOffice-fresh.appimage
70.br 76.br
71 Virtual dirs: /tmp, /var/tmp, /dev, 77 Virtual dirs: /tmp, /var/tmp, /dev,
72.br 78.br
79 Networking: enabled
80.br
73 81
74.br 82.br
7526090:netblue::/usr/bin/firejail /opt/firefox/firefox 8326090:netblue::/usr/bin/firejail /opt/firefox/firefox
@@ -78,6 +86,8 @@ $ sudo jailcheck
78.br 86.br
79 /run/user/1000, 87 /run/user/1000,
80.br 88.br
89 Networking: enabled
90.br
81 91
82.br 92.br
8326160:netblue:tor:firejail --private=~/tor-browser_en-US ./start-tor 9326160:netblue:tor:firejail --private=~/tor-browser_en-US ./start-tor
@@ -90,6 +100,8 @@ $ sudo jailcheck
90.br 100.br
91 Warning: I can run programs in /home/netblue 101 Warning: I can run programs in /home/netblue
92.br 102.br
103 Networking: enabled
104.br
93 105
94 106
95.SH LICENSE 107.SH LICENSE
diff --git a/test/environment/rlimit-bad-profile.exp b/test/environment/rlimit-bad-profile.exp
index b838f83f4..b1572afb6 100755
--- a/test/environment/rlimit-bad-profile.exp
+++ b/test/environment/rlimit-bad-profile.exp
@@ -11,7 +11,7 @@ match_max 100000
11send -- "firejail --profile=rlimit-bad1.profile\r" 11send -- "firejail --profile=rlimit-bad1.profile\r"
12expect { 12expect {
13 timeout {puts "TESTING ERROR 4\n";exit} 13 timeout {puts "TESTING ERROR 4\n";exit}
14 "invalid rlimit" 14 "invalid rlimit-fsize in profile file. Only use positive numbers and k, m or g suffix."
15} 15}
16after 100 16after 100
17 17
diff --git a/test/environment/rlimit-bad.exp b/test/environment/rlimit-bad.exp
index 3a82ded9b..c05e14b97 100755
--- a/test/environment/rlimit-bad.exp
+++ b/test/environment/rlimit-bad.exp
@@ -10,7 +10,7 @@ match_max 100000
10send -- "firejail --rlimit-fsize=-1024\r" 10send -- "firejail --rlimit-fsize=-1024\r"
11expect { 11expect {
12 timeout {puts "TESTING ERROR 0\n";exit} 12 timeout {puts "TESTING ERROR 0\n";exit}
13 "invalid rlimit" 13 "invalid rlimit-fsize. Only use positive numbers and k, m or g suffix."
14} 14}
15after 100 15after 100
16 16
diff --git a/test/fs/fscheck-tmpfs.exp b/test/fs/fscheck-tmpfs.exp
index 8dd08aa72..78b6efb76 100755
--- a/test/fs/fscheck-tmpfs.exp
+++ b/test/fs/fscheck-tmpfs.exp
@@ -41,7 +41,7 @@ after 500
41send -- "firejail --noprofile --tmpfs=/tmp/fjtest-dir\r" 41send -- "firejail --noprofile --tmpfs=/tmp/fjtest-dir\r"
42expect { 42expect {
43 timeout {puts "TESTING ERROR 5\n";exit} 43 timeout {puts "TESTING ERROR 5\n";exit}
44 "Error" 44 "Warning: you are not allowed to mount a tmpfs"
45} 45}
46after 500 46after 500
47 47