diff options
-rw-r--r-- | src/firejail/cgroup.c | 11 | ||||
-rw-r--r-- | src/firejail/cpu.c | 10 | ||||
-rw-r--r-- | src/firejail/firejail.h | 19 | ||||
-rw-r--r-- | src/firejail/fs_etc.c | 4 | ||||
-rw-r--r-- | src/firejail/fs_home.c | 14 | ||||
-rw-r--r-- | src/firejail/fs_hostname.c | 47 | ||||
-rw-r--r-- | src/firejail/fs_trace.c | 12 | ||||
-rw-r--r-- | src/firejail/fs_var.c | 38 | ||||
-rw-r--r-- | src/firejail/join.c | 10 | ||||
-rw-r--r-- | src/firejail/main.c | 2 | ||||
-rw-r--r-- | src/firejail/pulseaudio.c | 17 | ||||
-rw-r--r-- | src/firejail/sandbox.c | 19 | ||||
-rw-r--r-- | src/firejail/seccomp.c | 24 |
13 files changed, 77 insertions, 150 deletions
diff --git a/src/firejail/cgroup.c b/src/firejail/cgroup.c index 9e6a2e549..aab7be0fd 100644 --- a/src/firejail/cgroup.c +++ b/src/firejail/cgroup.c | |||
@@ -26,30 +26,23 @@ void save_cgroup(void) { | |||
26 | if (cfg.cgroup == NULL) | 26 | if (cfg.cgroup == NULL) |
27 | return; | 27 | return; |
28 | 28 | ||
29 | char *fname; | 29 | FILE *fp = fopen(CGROUP_CFG, "w"); |
30 | if (asprintf(&fname, "%s/cgroup", MNT_DIR) == -1) | ||
31 | errExit(fname); | ||
32 | |||
33 | FILE *fp = fopen(fname, "w"); | ||
34 | if (fp) { | 30 | if (fp) { |
35 | fprintf(fp, "%s", cfg.cgroup); | 31 | fprintf(fp, "%s", cfg.cgroup); |
36 | fflush(0); | 32 | fflush(0); |
37 | if (fclose(fp)) | 33 | if (fclose(fp)) |
38 | goto errout; | 34 | goto errout; |
39 | if (chown(fname, 0, 0) < 0) | 35 | if (chown(CGROUP_CFG, 0, 0) < 0) |
40 | errExit("chown"); | 36 | errExit("chown"); |
41 | } | 37 | } |
42 | else | 38 | else |
43 | goto errout; | 39 | goto errout; |
44 | 40 | ||
45 | free(fname); | ||
46 | return; | 41 | return; |
47 | 42 | ||
48 | errout: | 43 | errout: |
49 | fprintf(stderr, "Error: cannot save cgroup\n"); | 44 | fprintf(stderr, "Error: cannot save cgroup\n"); |
50 | free(fname); | ||
51 | exit(1); | 45 | exit(1); |
52 | |||
53 | } | 46 | } |
54 | 47 | ||
55 | void load_cgroup(const char *fname) { | 48 | void load_cgroup(const char *fname) { |
diff --git a/src/firejail/cpu.c b/src/firejail/cpu.c index 9462568f2..6dcbbd07b 100644 --- a/src/firejail/cpu.c +++ b/src/firejail/cpu.c | |||
@@ -71,23 +71,17 @@ void save_cpu(void) { | |||
71 | if (cfg.cpus == 0) | 71 | if (cfg.cpus == 0) |
72 | return; | 72 | return; |
73 | 73 | ||
74 | char *fname; | 74 | FILE *fp = fopen(CPU_CFG, "w"); |
75 | if (asprintf(&fname, "%s/cpu", MNT_DIR) == -1) | ||
76 | errExit("asprintf"); | ||
77 | FILE *fp = fopen(fname, "w"); | ||
78 | if (fp) { | 75 | if (fp) { |
79 | fprintf(fp, "%x\n", cfg.cpus); | 76 | fprintf(fp, "%x\n", cfg.cpus); |
80 | fclose(fp); | 77 | fclose(fp); |
81 | if (chown(fname, 0, 0) < 0) | 78 | if (chown(CPU_CFG, 0, 0) < 0) |
82 | errExit("chown"); | 79 | errExit("chown"); |
83 | } | 80 | } |
84 | else { | 81 | else { |
85 | fprintf(stderr, "Error: cannot save cpu affinity mask\n"); | 82 | fprintf(stderr, "Error: cannot save cpu affinity mask\n"); |
86 | free(fname); | ||
87 | exit(1); | 83 | exit(1); |
88 | } | 84 | } |
89 | |||
90 | free(fname); | ||
91 | } | 85 | } |
92 | 86 | ||
93 | void load_cpu(const char *fname) { | 87 | void load_cpu(const char *fname) { |
diff --git a/src/firejail/firejail.h b/src/firejail/firejail.h index e79cc4a2c..1068485ff 100644 --- a/src/firejail/firejail.h +++ b/src/firejail/firejail.h | |||
@@ -21,20 +21,33 @@ | |||
21 | #define FIREJAIL_H | 21 | #define FIREJAIL_H |
22 | #include "../include/common.h" | 22 | #include "../include/common.h" |
23 | 23 | ||
24 | #define USELOCK | 24 | // filesystem |
25 | #define FIREJAIL_DIR "/tmp/firejail" | 25 | #define FIREJAIL_DIR "/tmp/firejail" |
26 | #define NETWORK_LOCK_FILE "/tmp/firejail/firejail.lock" | ||
26 | #define RO_DIR "/tmp/firejail/firejail.ro.dir" | 27 | #define RO_DIR "/tmp/firejail/firejail.ro.dir" |
27 | #define RO_FILE "/tmp/firejail/firejail.ro.file" | 28 | #define RO_FILE "/tmp/firejail/firejail.ro.file" |
28 | #define MNT_DIR "/tmp/firejail/mnt" | 29 | #define MNT_DIR "/tmp/firejail/mnt" // a tmpfs is mounted on this directory before any of the files below are created |
30 | #define SECCOMP_CFG "/tmp/firejail/mnt/seccomp" | ||
31 | #define CGROUP_CFG "/tmp/firejail/mnt/cgroup" | ||
32 | #define CPU_CFG "/tmp/firejail/mnt/cpu" | ||
33 | #define GROUPS_CFG "/tmp/firejail/mnt/groups" | ||
29 | #define CP_COMMAND "/tmp/firejail/mnt/cp" | 34 | #define CP_COMMAND "/tmp/firejail/mnt/cp" |
30 | #define HOME_DIR "/tmp/firejail/mnt/home" | 35 | #define HOME_DIR "/tmp/firejail/mnt/home" |
31 | #define ETC_DIR "/tmp/firejail/mnt/etc" | 36 | #define ETC_DIR "/tmp/firejail/mnt/etc" |
32 | #define BIN_DIR "/tmp/firejail/mnt/bin" | 37 | #define BIN_DIR "/tmp/firejail/mnt/bin" |
33 | #define DRI_DIR "/tmp/firejail/mnt/dri" | 38 | #define DRI_DIR "/tmp/firejail/mnt/dri" |
39 | #define PULSE_DIR "/tmp/firejail/mnt/pulse" | ||
34 | #define WHITELIST_HOME_DIR "/tmp/firejail/mnt/whome" | 40 | #define WHITELIST_HOME_DIR "/tmp/firejail/mnt/whome" |
41 | #define XAUTHORITY_FILE "/tmp/firejail/mnt/.Xauthority" | ||
42 | #define HOSTNAME_FILE "/tmp/firejail/mnt/hostname" | ||
43 | #define RESOLVCONF_FILE "/tmp/firejail/mnt/resolv.conf" | ||
44 | #define LDPRELOAD_FILE "/tmp/firejail/mnt/ld.so.preload" | ||
45 | #define UTMP_FILE "/tmp/firejail/mnt/utmp" | ||
46 | |||
47 | // profiles | ||
35 | #define DEFAULT_USER_PROFILE "generic" | 48 | #define DEFAULT_USER_PROFILE "generic" |
36 | #define DEFAULT_ROOT_PROFILE "server" | 49 | #define DEFAULT_ROOT_PROFILE "server" |
37 | #define MAX_INCLUDE_LEVEL 6 | 50 | #define MAX_INCLUDE_LEVEL 6 // include levels in profile files |
38 | 51 | ||
39 | // main.c | 52 | // main.c |
40 | typedef struct bridge_t { | 53 | typedef struct bridge_t { |
diff --git a/src/firejail/fs_etc.c b/src/firejail/fs_etc.c index 617d45d06..f9088f1ba 100644 --- a/src/firejail/fs_etc.c +++ b/src/firejail/fs_etc.c | |||
@@ -75,7 +75,7 @@ void fs_check_etc_list(void) { | |||
75 | static void duplicate(char *fname) { | 75 | static void duplicate(char *fname) { |
76 | char *cmd; | 76 | char *cmd; |
77 | 77 | ||
78 | // copy the file | 78 | // copy the file - this code assumes ETC_DIR is actually MNT_DIR/etc |
79 | if (asprintf(&cmd, "%s -a --parents /etc/%s %s", CP_COMMAND, fname, MNT_DIR) == -1) | 79 | if (asprintf(&cmd, "%s -a --parents /etc/%s %s", CP_COMMAND, fname, MNT_DIR) == -1) |
80 | errExit("asprintf"); | 80 | errExit("asprintf"); |
81 | if (arg_debug) | 81 | if (arg_debug) |
@@ -113,7 +113,7 @@ void fs_private_etc_list(void) { | |||
113 | errExit("fork"); | 113 | errExit("fork"); |
114 | if (child == 0) { | 114 | if (child == 0) { |
115 | if (arg_debug) | 115 | if (arg_debug) |
116 | printf("Copying files in the new home:\n"); | 116 | printf("Copying files in the new etc directory:\n"); |
117 | 117 | ||
118 | // elevate privileges - files in the new /etc directory belong to root | 118 | // elevate privileges - files in the new /etc directory belong to root |
119 | if (setreuid(0, 0) < 0) | 119 | if (setreuid(0, 0) < 0) |
diff --git a/src/firejail/fs_home.c b/src/firejail/fs_home.c index 2cbb59e69..63c03a8db 100644 --- a/src/firejail/fs_home.c +++ b/src/firejail/fs_home.c | |||
@@ -109,15 +109,13 @@ static void skel(const char *homedir, uid_t u, gid_t g) { | |||
109 | } | 109 | } |
110 | 110 | ||
111 | static int store_xauthority(void) { | 111 | static int store_xauthority(void) { |
112 | // put a copy of .Xauthority in MNT_DIR | 112 | // put a copy of .Xauthority in XAUTHORITY_FILE |
113 | fs_build_mnt_dir(); | 113 | fs_build_mnt_dir(); |
114 | 114 | ||
115 | char *src; | 115 | char *src; |
116 | char *dest; | 116 | char *dest = XAUTHORITY_FILE; |
117 | if (asprintf(&src, "%s/.Xauthority", cfg.homedir) == -1) | 117 | if (asprintf(&src, "%s/.Xauthority", cfg.homedir) == -1) |
118 | errExit("asprintf"); | 118 | errExit("asprintf"); |
119 | if (asprintf(&dest, "%s/.Xauthority", MNT_DIR) == -1) | ||
120 | errExit("asprintf"); | ||
121 | 119 | ||
122 | struct stat s; | 120 | struct stat s; |
123 | if (stat(src, &s) == 0) { | 121 | if (stat(src, &s) == 0) { |
@@ -133,15 +131,11 @@ static int store_xauthority(void) { | |||
133 | } | 131 | } |
134 | 132 | ||
135 | static void copy_xauthority(void) { | 133 | static void copy_xauthority(void) { |
136 | // put a copy of .Xauthority in MNT_DIR | 134 | // copy XAUTHORITY_FILE in the new home directory |
137 | fs_build_mnt_dir(); | 135 | char *src = XAUTHORITY_FILE ; |
138 | |||
139 | char *src; | ||
140 | char *dest; | 136 | char *dest; |
141 | if (asprintf(&dest, "%s/.Xauthority", cfg.homedir) == -1) | 137 | if (asprintf(&dest, "%s/.Xauthority", cfg.homedir) == -1) |
142 | errExit("asprintf"); | 138 | errExit("asprintf"); |
143 | if (asprintf(&src, "%s/.Xauthority", MNT_DIR) == -1) | ||
144 | errExit("asprintf"); | ||
145 | int rv = copy_file(src, dest); | 139 | int rv = copy_file(src, dest); |
146 | if (rv) | 140 | if (rv) |
147 | fprintf(stderr, "Warning: cannot transfer .Xauthority in private home directory\n"); | 141 | fprintf(stderr, "Warning: cannot transfer .Xauthority in private home directory\n"); |
diff --git a/src/firejail/fs_hostname.c b/src/firejail/fs_hostname.c index 2d9ad6fa7..94251df57 100644 --- a/src/firejail/fs_hostname.c +++ b/src/firejail/fs_hostname.c | |||
@@ -33,49 +33,40 @@ void fs_hostname(const char *hostname) { | |||
33 | if (stat("/etc/hostname", &s) == 0) { | 33 | if (stat("/etc/hostname", &s) == 0) { |
34 | if (arg_debug) | 34 | if (arg_debug) |
35 | printf("Creating a new /etc/hostname file\n"); | 35 | printf("Creating a new /etc/hostname file\n"); |
36 | char *fhost; | 36 | |
37 | if (asprintf(&fhost, "%s/hostname", MNT_DIR) == -1) | 37 | FILE *fp = fopen(HOSTNAME_FILE, "w"); |
38 | errExit("asprintf"); | ||
39 | FILE *fp = fopen(fhost, "w"); | ||
40 | if (!fp) { | 38 | if (!fp) { |
41 | fprintf(stderr, "Error: cannot create %s\n", fhost); | 39 | fprintf(stderr, "Error: cannot create %s\n", HOSTNAME_FILE); |
42 | free(fhost); | ||
43 | exit(1); | 40 | exit(1); |
44 | } | 41 | } |
45 | fprintf(fp, "%s\n", hostname); | 42 | fprintf(fp, "%s\n", hostname); |
46 | fclose(fp); | 43 | fclose(fp); |
47 | 44 | ||
48 | // mode and owner | 45 | // mode and owner |
49 | if (chown(fhost, 0, 0) < 0) | 46 | if (chown(HOSTNAME_FILE, 0, 0) < 0) |
50 | errExit("chown"); | 47 | errExit("chown"); |
51 | if (chmod(fhost, S_IRUSR | S_IWRITE | S_IRGRP | S_IROTH ) < 0) | 48 | if (chmod(HOSTNAME_FILE, S_IRUSR | S_IWRITE | S_IRGRP | S_IROTH ) < 0) |
52 | errExit("chmod"); | 49 | errExit("chmod"); |
53 | 50 | ||
54 | // bind-mount the file on top of /etc/hostname | 51 | // bind-mount the file on top of /etc/hostname |
55 | if (mount(fhost, "/etc/hostname", NULL, MS_BIND|MS_REC, NULL) < 0) | 52 | if (mount(HOSTNAME_FILE, "/etc/hostname", NULL, MS_BIND|MS_REC, NULL) < 0) |
56 | errExit("mount bind /etc/hostname"); | 53 | errExit("mount bind /etc/hostname"); |
57 | free(fhost); | ||
58 | } | 54 | } |
59 | 55 | ||
60 | // create a new /etc/hosts | 56 | // create a new /etc/hosts |
61 | if (stat("/etc/hosts", &s) == 0) { | 57 | if (stat("/etc/hosts", &s) == 0) { |
62 | if (arg_debug) | 58 | if (arg_debug) |
63 | printf("Creating a new /etc/hosts file\n"); | 59 | printf("Creating a new /etc/hosts file\n"); |
64 | char *fhost; | ||
65 | if (asprintf(&fhost, "%s/hosts", MNT_DIR) == -1) | ||
66 | errExit("asprintf"); | ||
67 | // copy /etc/host into our new file, and modify it on the fly | 60 | // copy /etc/host into our new file, and modify it on the fly |
68 | /* coverity[toctou] */ | 61 | /* coverity[toctou] */ |
69 | FILE *fp1 = fopen("/etc/hosts", "r"); | 62 | FILE *fp1 = fopen("/etc/hosts", "r"); |
70 | if (!fp1) { | 63 | if (!fp1) { |
71 | fprintf(stderr, "Error: cannot open /etc/hosts\n"); | 64 | fprintf(stderr, "Error: cannot open /etc/hosts\n"); |
72 | free(fhost); | ||
73 | exit(1); | 65 | exit(1); |
74 | } | 66 | } |
75 | FILE *fp2 = fopen(fhost, "w"); | 67 | FILE *fp2 = fopen(HOSTNAME_FILE, "w"); |
76 | if (!fp2) { | 68 | if (!fp2) { |
77 | fprintf(stderr, "Error: cannot create %s\n", fhost); | 69 | fprintf(stderr, "Error: cannot create %s\n", HOSTNAME_FILE); |
78 | free(fhost); | ||
79 | exit(1); | 70 | exit(1); |
80 | } | 71 | } |
81 | 72 | ||
@@ -96,15 +87,14 @@ void fs_hostname(const char *hostname) { | |||
96 | fclose(fp2); | 87 | fclose(fp2); |
97 | 88 | ||
98 | // mode and owner | 89 | // mode and owner |
99 | if (chown(fhost, 0, 0) < 0) | 90 | if (chown(HOSTNAME_FILE, 0, 0) < 0) |
100 | errExit("chown"); | 91 | errExit("chown"); |
101 | if (chmod(fhost, S_IRUSR | S_IWRITE | S_IRGRP | S_IROTH ) < 0) | 92 | if (chmod(HOSTNAME_FILE, S_IRUSR | S_IWRITE | S_IRGRP | S_IROTH ) < 0) |
102 | errExit("chmod"); | 93 | errExit("chmod"); |
103 | 94 | ||
104 | // bind-mount the file on top of /etc/hostname | 95 | // bind-mount the file on top of /etc/hostname |
105 | if (mount(fhost, "/etc/hosts", NULL, MS_BIND|MS_REC, NULL) < 0) | 96 | if (mount(HOSTNAME_FILE, "/etc/hosts", NULL, MS_BIND|MS_REC, NULL) < 0) |
106 | errExit("mount bind /etc/hosts"); | 97 | errExit("mount bind /etc/hosts"); |
107 | free(fhost); | ||
108 | } | 98 | } |
109 | } | 99 | } |
110 | 100 | ||
@@ -119,13 +109,9 @@ void fs_resolvconf(void) { | |||
119 | if (stat("/etc/resolv.conf", &s) == 0) { | 109 | if (stat("/etc/resolv.conf", &s) == 0) { |
120 | if (arg_debug) | 110 | if (arg_debug) |
121 | printf("Creating a new /etc/resolv.conf file\n"); | 111 | printf("Creating a new /etc/resolv.conf file\n"); |
122 | char *fname; | 112 | FILE *fp = fopen(RESOLVCONF_FILE, "w"); |
123 | if (asprintf(&fname, "%s/resolv.conf", MNT_DIR) == -1) | ||
124 | errExit("asprintf"); | ||
125 | FILE *fp = fopen(fname, "w"); | ||
126 | if (!fp) { | 113 | if (!fp) { |
127 | fprintf(stderr, "Error: cannot create %s\n", fname); | 114 | fprintf(stderr, "Error: cannot create %s\n", RESOLVCONF_FILE); |
128 | free(fname); | ||
129 | exit(1); | 115 | exit(1); |
130 | } | 116 | } |
131 | 117 | ||
@@ -138,15 +124,14 @@ void fs_resolvconf(void) { | |||
138 | fclose(fp); | 124 | fclose(fp); |
139 | 125 | ||
140 | // mode and owner | 126 | // mode and owner |
141 | if (chown(fname, 0, 0) < 0) | 127 | if (chown(RESOLVCONF_FILE, 0, 0) < 0) |
142 | errExit("chown"); | 128 | errExit("chown"); |
143 | if (chmod(fname, S_IRUSR | S_IWRITE | S_IRGRP | S_IROTH ) < 0) | 129 | if (chmod(RESOLVCONF_FILE, S_IRUSR | S_IWRITE | S_IRGRP | S_IROTH ) < 0) |
144 | errExit("chmod"); | 130 | errExit("chmod"); |
145 | 131 | ||
146 | // bind-mount the file on top of /etc/hostname | 132 | // bind-mount the file on top of /etc/hostname |
147 | if (mount(fname, "/etc/resolv.conf", NULL, MS_BIND|MS_REC, NULL) < 0) | 133 | if (mount(RESOLVCONF_FILE, "/etc/resolv.conf", NULL, MS_BIND|MS_REC, NULL) < 0) |
148 | errExit("mount bind /etc/resolv.conf"); | 134 | errExit("mount bind /etc/resolv.conf"); |
149 | free(fname); | ||
150 | } | 135 | } |
151 | else { | 136 | else { |
152 | fprintf(stderr, "Error: cannot set DNS servers, /etc/resolv.conf file is missing\n"); | 137 | fprintf(stderr, "Error: cannot set DNS servers, /etc/resolv.conf file is missing\n"); |
diff --git a/src/firejail/fs_trace.c b/src/firejail/fs_trace.c index 6058bf3c4..2b0f52a98 100644 --- a/src/firejail/fs_trace.c +++ b/src/firejail/fs_trace.c | |||
@@ -52,23 +52,21 @@ void fs_trace(void) { | |||
52 | // create the new ld.so.preload file and mount-bind it | 52 | // create the new ld.so.preload file and mount-bind it |
53 | if (arg_debug) | 53 | if (arg_debug) |
54 | printf("Create the new ld.so.preload file\n"); | 54 | printf("Create the new ld.so.preload file\n"); |
55 | char *preload; | 55 | |
56 | if (asprintf(&preload, "%s/ld.so.preload", MNT_DIR) == -1) | 56 | FILE *fp = fopen(LDPRELOAD_FILE, "w"); |
57 | errExit("asprintf"); | ||
58 | FILE *fp = fopen(preload, "w"); | ||
59 | if (!fp) | 57 | if (!fp) |
60 | errExit("fopen"); | 58 | errExit("fopen"); |
61 | fprintf(fp, "%s/firejail/libtrace.so\n", LIBDIR); | 59 | fprintf(fp, "%s/firejail/libtrace.so\n", LIBDIR); |
62 | fclose(fp); | 60 | fclose(fp); |
63 | if (chown(preload, 0, 0) < 0) | 61 | if (chown(LDPRELOAD_FILE, 0, 0) < 0) |
64 | errExit("chown"); | 62 | errExit("chown"); |
65 | if (chmod(preload, S_IRUSR | S_IWRITE | S_IRGRP | S_IROTH ) < 0) | 63 | if (chmod(LDPRELOAD_FILE, S_IRUSR | S_IWRITE | S_IRGRP | S_IROTH ) < 0) |
66 | errExit("chmod"); | 64 | errExit("chmod"); |
67 | 65 | ||
68 | // mount the new preload file | 66 | // mount the new preload file |
69 | if (arg_debug) | 67 | if (arg_debug) |
70 | printf("Mount the new ld.so.preload file\n"); | 68 | printf("Mount the new ld.so.preload file\n"); |
71 | if (mount(preload, "/etc/ld.so.preload", NULL, MS_BIND|MS_REC, NULL) < 0) | 69 | if (mount(LDPRELOAD_FILE, "/etc/ld.so.preload", NULL, MS_BIND|MS_REC, NULL) < 0) |
72 | errExit("mount bind ls.so.preload"); | 70 | errExit("mount bind ls.so.preload"); |
73 | } | 71 | } |
74 | 72 | ||
diff --git a/src/firejail/fs_var.c b/src/firejail/fs_var.c index 93625633a..7e822f614 100644 --- a/src/firejail/fs_var.c +++ b/src/firejail/fs_var.c | |||
@@ -317,10 +317,8 @@ void fs_var_utmp(void) { | |||
317 | // create a new utmp file | 317 | // create a new utmp file |
318 | if (arg_debug) | 318 | if (arg_debug) |
319 | printf("Create the new utmp file\n"); | 319 | printf("Create the new utmp file\n"); |
320 | char *utmp; | 320 | |
321 | if (asprintf(&utmp, "%s/utmp", MNT_DIR) == -1) | 321 | FILE *fp = fopen(UTMP_FILE, "w"); |
322 | errExit("asprintf"); | ||
323 | FILE *fp = fopen(utmp, "w"); | ||
324 | if (!fp) | 322 | if (!fp) |
325 | errExit("fopen"); | 323 | errExit("fopen"); |
326 | 324 | ||
@@ -339,42 +337,16 @@ void fs_var_utmp(void) { | |||
339 | // save new utmp file | 337 | // save new utmp file |
340 | fwrite(&u_boot, sizeof(u_boot), 1, fp); | 338 | fwrite(&u_boot, sizeof(u_boot), 1, fp); |
341 | fclose(fp); | 339 | fclose(fp); |
342 | if (chown(utmp, 0, utmp_group) < 0) | 340 | if (chown(UTMP_FILE, 0, utmp_group) < 0) |
343 | errExit("chown"); | 341 | errExit("chown"); |
344 | if (chmod(utmp, S_IRUSR | S_IWRITE | S_IRGRP | S_IWGRP | S_IROTH ) < 0) | 342 | if (chmod(UTMP_FILE, S_IRUSR | S_IWRITE | S_IRGRP | S_IWGRP | S_IROTH ) < 0) |
345 | errExit("chmod"); | 343 | errExit("chmod"); |
346 | 344 | ||
347 | // mount the new utmp file | 345 | // mount the new utmp file |
348 | if (arg_debug) | 346 | if (arg_debug) |
349 | printf("Mount the new utmp file\n"); | 347 | printf("Mount the new utmp file\n"); |
350 | if (mount(utmp, "/var/run/utmp", NULL, MS_BIND|MS_REC, NULL) < 0) | 348 | if (mount(UTMP_FILE, "/var/run/utmp", NULL, MS_BIND|MS_REC, NULL) < 0) |
351 | errExit("mount bind utmp"); | 349 | errExit("mount bind utmp"); |
352 | } | 350 | } |
353 | 351 | ||
354 | 352 | ||
355 | #if 0 | ||
356 | Testing servers: | ||
357 | |||
358 | brctl addbr br0 | ||
359 | ifconfig br0 10.10.20.1/24 | ||
360 | |||
361 | apt-get install snmpd | ||
362 | insserv -r snmpd | ||
363 | sudo firejail --net=br0 --ip=10.10.20.10 "/etc/init.d/rsyslog start; /etc/init.d/ssh start; /etc/init.d/snmpd start; sleep inf" | ||
364 | |||
365 | apt-get install apache2 | ||
366 | insserv -r apache2 | ||
367 | sudo firejail --net=br0 --ip=10.10.20.10 "/etc/init.d/rsyslog start; /etc/init.d/ssh start; /etc/init.d/apache2 start; sleep inf" | ||
368 | |||
369 | apt-get install nginx | ||
370 | insserv -r nginx | ||
371 | sudo firejail --net=br0 --ip=10.10.20.10 "/etc/init.d/rsyslog start; /etc/init.d/ssh start; /etc/init.d/nginx start; sleep inf" | ||
372 | |||
373 | apt-get install lighttpd | ||
374 | insserv -r lighttpd | ||
375 | sudo firejail --net=br0 --ip=10.10.20.10 "/etc/init.d/rsyslog start; /etc/init.d/ssh start; /etc/init.d/lighttpd start; sleep inf" | ||
376 | |||
377 | apt-get install isc-dhcp-server | ||
378 | insserv -r isc-dhcp-server | ||
379 | sudo firejail --net=br0 --ip=10.10.20.10 "/etc/init.d/rsyslog start; /etc/init.d/ssh start; /etc/init.d/isc-dhcp-server start; sleep inf" | ||
380 | #endif | ||
diff --git a/src/firejail/join.c b/src/firejail/join.c index 35e302bf0..91dad420a 100644 --- a/src/firejail/join.c +++ b/src/firejail/join.c | |||
@@ -69,7 +69,7 @@ static void extract_command(int argc, char **argv, int index) { | |||
69 | 69 | ||
70 | static void extract_nogroups(pid_t pid) { | 70 | static void extract_nogroups(pid_t pid) { |
71 | char *fname; | 71 | char *fname; |
72 | if (asprintf(&fname, "/proc/%d/root%s/groups", pid, MNT_DIR) == -1) | 72 | if (asprintf(&fname, "/proc/%d/root%s", pid, GROUPS_CFG) == -1) |
73 | errExit("asprintf"); | 73 | errExit("asprintf"); |
74 | 74 | ||
75 | struct stat s; | 75 | struct stat s; |
@@ -82,28 +82,28 @@ static void extract_nogroups(pid_t pid) { | |||
82 | 82 | ||
83 | static void extract_cpu(pid_t pid) { | 83 | static void extract_cpu(pid_t pid) { |
84 | char *fname; | 84 | char *fname; |
85 | if (asprintf(&fname, "/proc/%d/root%s/cpu", pid, MNT_DIR) == -1) | 85 | if (asprintf(&fname, "/proc/%d/root%s", pid, CPU_CFG) == -1) |
86 | errExit("asprintf"); | 86 | errExit("asprintf"); |
87 | 87 | ||
88 | struct stat s; | 88 | struct stat s; |
89 | if (stat(fname, &s) == -1) | 89 | if (stat(fname, &s) == -1) |
90 | return; | 90 | return; |
91 | 91 | ||
92 | // there is a cpu file in MNT_DIR; load the information from the file | 92 | // there is a CPU_CFG file, load it! |
93 | load_cpu(fname); | 93 | load_cpu(fname); |
94 | free(fname); | 94 | free(fname); |
95 | } | 95 | } |
96 | 96 | ||
97 | static void extract_cgroup(pid_t pid) { | 97 | static void extract_cgroup(pid_t pid) { |
98 | char *fname; | 98 | char *fname; |
99 | if (asprintf(&fname, "/proc/%d/root%s/cgroup", pid, MNT_DIR) == -1) | 99 | if (asprintf(&fname, "/proc/%d/root%s", pid, CGROUP_CFG) == -1) |
100 | errExit("asprintf"); | 100 | errExit("asprintf"); |
101 | 101 | ||
102 | struct stat s; | 102 | struct stat s; |
103 | if (stat(fname, &s) == -1) | 103 | if (stat(fname, &s) == -1) |
104 | return; | 104 | return; |
105 | 105 | ||
106 | // there is a cgroup file in MNT_DIR; load the information from the file | 106 | // there is a cgroup file CGROUP_CFG, load it! |
107 | load_cgroup(fname); | 107 | load_cgroup(fname); |
108 | free(fname); | 108 | free(fname); |
109 | } | 109 | } |
diff --git a/src/firejail/main.c b/src/firejail/main.c index 1c1c3a08f..4fa2e5b3b 100644 --- a/src/firejail/main.c +++ b/src/firejail/main.c | |||
@@ -1255,7 +1255,7 @@ int main(int argc, char **argv) { | |||
1255 | 1255 | ||
1256 | // check and assign an IP address - for macvlan it will be done again in the sandbox! | 1256 | // check and assign an IP address - for macvlan it will be done again in the sandbox! |
1257 | if (any_bridge_configured()) { | 1257 | if (any_bridge_configured()) { |
1258 | lockfd = open("/tmp/firejail/firejail.lock", O_WRONLY | O_CREAT, S_IRUSR | S_IWUSR); | 1258 | lockfd = open(NETWORK_LOCK_FILE, O_WRONLY | O_CREAT, S_IRUSR | S_IWUSR); |
1259 | if (lockfd != -1) { | 1259 | if (lockfd != -1) { |
1260 | int rv = fchown(lockfd, 0, 0); | 1260 | int rv = fchown(lockfd, 0, 0); |
1261 | (void) rv; | 1261 | (void) rv; |
diff --git a/src/firejail/pulseaudio.c b/src/firejail/pulseaudio.c index 0cd5bace2..22c2a0d3d 100644 --- a/src/firejail/pulseaudio.c +++ b/src/firejail/pulseaudio.c | |||
@@ -86,26 +86,24 @@ void pulseaudio_disable(void) { | |||
86 | void pulseaudio_init(void) { | 86 | void pulseaudio_init(void) { |
87 | struct stat s; | 87 | struct stat s; |
88 | 88 | ||
89 | printf("here %d\n", __LINE__); | ||
89 | // do we have pulseaudio in the system? | 90 | // do we have pulseaudio in the system? |
90 | if (stat("/etc/pulse/client.conf", &s) == -1) | 91 | if (stat("/etc/pulse/client.conf", &s) == -1) |
91 | return; | 92 | return; |
92 | 93 | printf("here %d\n", __LINE__); | |
93 | 94 | ||
94 | // create the new user pulseaudio directory | 95 | // create the new user pulseaudio directory |
95 | fs_build_mnt_dir(); | 96 | fs_build_mnt_dir(); |
96 | char *pulsedir; | 97 | int rv = mkdir(PULSE_DIR, S_IRWXU | S_IRWXG | S_IRWXO); |
97 | if (asprintf(&pulsedir, "%s/pulse", MNT_DIR) == -1) | ||
98 | errExit("asprintf"); | ||
99 | int rv = mkdir(pulsedir, S_IRWXU | S_IRWXG | S_IRWXO); | ||
100 | (void) rv; // in --chroot mode the directory canalready be there | 98 | (void) rv; // in --chroot mode the directory canalready be there |
101 | if (chown(pulsedir, getuid(), getgid()) < 0) | 99 | if (chown(PULSE_DIR, getuid(), getgid()) < 0) |
102 | errExit("chown"); | 100 | errExit("chown"); |
103 | if (chmod(pulsedir, 0700) < 0) | 101 | if (chmod(PULSE_DIR, 0700) < 0) |
104 | errExit("chmod"); | 102 | errExit("chmod"); |
105 | 103 | ||
106 | // create the new client.conf file | 104 | // create the new client.conf file |
107 | char *pulsecfg = NULL; | 105 | char *pulsecfg = NULL; |
108 | if (asprintf(&pulsecfg, "%s/client.conf", pulsedir) == -1) | 106 | if (asprintf(&pulsecfg, "%s/client.conf", PULSE_DIR) == -1) |
109 | errExit("asprintf"); | 107 | errExit("asprintf"); |
110 | if (copy_file("/etc/pulse/client.conf", pulsecfg)) | 108 | if (copy_file("/etc/pulse/client.conf", pulsecfg)) |
111 | errExit("copy_file"); | 109 | errExit("copy_file"); |
@@ -119,12 +117,9 @@ void pulseaudio_init(void) { | |||
119 | if (chown(pulsecfg, getuid(), getgid()) == -1) | 117 | if (chown(pulsecfg, getuid(), getgid()) == -1) |
120 | errExit("chown"); | 118 | errExit("chown"); |
121 | 119 | ||
122 | |||
123 | // set environment | 120 | // set environment |
124 | if (setenv("PULSE_CLIENTCONFIG", pulsecfg, 1) < 0) | 121 | if (setenv("PULSE_CLIENTCONFIG", pulsecfg, 1) < 0) |
125 | errExit("setenv"); | 122 | errExit("setenv"); |
126 | 123 | ||
127 | |||
128 | free(pulsecfg); | 124 | free(pulsecfg); |
129 | free(pulsedir); | ||
130 | } | 125 | } |
diff --git a/src/firejail/sandbox.c b/src/firejail/sandbox.c index b23c5d742..d9ce717e0 100644 --- a/src/firejail/sandbox.c +++ b/src/firejail/sandbox.c | |||
@@ -46,23 +46,18 @@ void save_nogroups(void) { | |||
46 | if (arg_nogroups == 0) | 46 | if (arg_nogroups == 0) |
47 | return; | 47 | return; |
48 | 48 | ||
49 | char *fname; | 49 | FILE *fp = fopen(GROUPS_CFG, "w"); |
50 | if (asprintf(&fname, "%s/groups", MNT_DIR) == -1) | ||
51 | errExit("asprintf"); | ||
52 | FILE *fp = fopen(fname, "w"); | ||
53 | if (fp) { | 50 | if (fp) { |
54 | fprintf(fp, "\n"); | 51 | fprintf(fp, "\n"); |
55 | fclose(fp); | 52 | fclose(fp); |
56 | if (chown(fname, 0, 0) < 0) | 53 | if (chown(GROUPS_CFG, 0, 0) < 0) |
57 | errExit("chown"); | 54 | errExit("chown"); |
58 | } | 55 | } |
59 | else { | 56 | else { |
60 | fprintf(stderr, "Error: cannot save nogroups state\n"); | 57 | fprintf(stderr, "Error: cannot save nogroups state\n"); |
61 | free(fname); | ||
62 | exit(1); | 58 | exit(1); |
63 | } | 59 | } |
64 | 60 | ||
65 | free(fname); | ||
66 | } | 61 | } |
67 | 62 | ||
68 | static void sandbox_if_up(Bridge *br) { | 63 | static void sandbox_if_up(Bridge *br) { |
@@ -436,21 +431,21 @@ int sandbox(void* sandbox_arg) { | |||
436 | // if a keep list is available, disregard the drop list | 431 | // if a keep list is available, disregard the drop list |
437 | if (arg_seccomp == 1) { | 432 | if (arg_seccomp == 1) { |
438 | if (cfg.seccomp_list_keep) | 433 | if (cfg.seccomp_list_keep) |
439 | seccomp_filter_keep(); // this will also save the fmyilter to MNT_DIR/seccomp file | 434 | seccomp_filter_keep(); |
440 | else if (cfg.seccomp_list_errno) | 435 | else if (cfg.seccomp_list_errno) |
441 | seccomp_filter_errno(); // this will also save the filter to MNT_DIR/seccomp file | 436 | seccomp_filter_errno(); |
442 | else | 437 | else |
443 | seccomp_filter_drop(); // this will also save the filter to MNT_DIR/seccomp file | 438 | seccomp_filter_drop(); |
444 | } | 439 | } |
445 | #endif | 440 | #endif |
446 | 441 | ||
447 | // set cpu affinity | 442 | // set cpu affinity |
448 | if (cfg.cpus) { | 443 | if (cfg.cpus) { |
449 | save_cpu(); // save cpu affinity mask to MNT_DIR/cpu file | 444 | save_cpu(); // save cpu affinity mask to CPU_CFG file |
450 | set_cpu_affinity(); | 445 | set_cpu_affinity(); |
451 | } | 446 | } |
452 | 447 | ||
453 | // save cgroup in MNT_DIR/cgroup file | 448 | // save cgroup in CGROUP_CFG file |
454 | if (cfg.cgroup) | 449 | if (cfg.cgroup) |
455 | save_cgroup(); | 450 | save_cgroup(); |
456 | 451 | ||
diff --git a/src/firejail/seccomp.c b/src/firejail/seccomp.c index 353b212f6..f8053d698 100644 --- a/src/firejail/seccomp.c +++ b/src/firejail/seccomp.c | |||
@@ -266,10 +266,7 @@ static void write_seccomp_file(void) { | |||
266 | fs_build_mnt_dir(); | 266 | fs_build_mnt_dir(); |
267 | assert(sfilter); | 267 | assert(sfilter); |
268 | 268 | ||
269 | char *fname; | 269 | int fd = open(SECCOMP_CFG, O_CREAT | O_WRONLY, S_IRUSR | S_IWUSR); |
270 | if (asprintf(&fname, "%s/seccomp", MNT_DIR) == -1) | ||
271 | errExit("asprintf"); | ||
272 | int fd = open(fname, O_CREAT | O_WRONLY, S_IRUSR | S_IWUSR); | ||
273 | if (fd == -1) | 270 | if (fd == -1) |
274 | errExit("open"); | 271 | errExit("open"); |
275 | 272 | ||
@@ -282,23 +279,14 @@ static void write_seccomp_file(void) { | |||
282 | exit(1); | 279 | exit(1); |
283 | } | 280 | } |
284 | close(fd); | 281 | close(fd); |
285 | if (chown(fname, 0, 0) < 0) | 282 | if (chown(SECCOMP_CFG, 0, 0) < 0) |
286 | errExit("chown"); | 283 | errExit("chown"); |
287 | free(fname); | ||
288 | } | 284 | } |
289 | 285 | ||
290 | // read seccomp filter from /tmp/firejail/mnt/seccomp | 286 | // read seccomp filter from /tmp/firejail/mnt/seccomp |
291 | static void read_seccomp_file(char *file_name) { | 287 | static void read_seccomp_file(const char *fname) { |
292 | assert(sfilter == NULL && sfilter_index == 0); | 288 | assert(sfilter == NULL && sfilter_index == 0); |
293 | 289 | ||
294 | char *fname; | ||
295 | if (file_name) | ||
296 | fname = file_name; | ||
297 | else { | ||
298 | if (asprintf(&fname, "%s/seccomp", MNT_DIR) == -1) | ||
299 | errExit("asprintf"); | ||
300 | } | ||
301 | |||
302 | // check file | 290 | // check file |
303 | struct stat s; | 291 | struct stat s; |
304 | if (stat(fname, &s) == -1) { | 292 | if (stat(fname, &s) == -1) { |
@@ -331,7 +319,6 @@ static void read_seccomp_file(char *file_name) { | |||
331 | printf("Read seccomp filter, size %u bytes\n", (unsigned) (sfilter_index * sizeof(struct sock_filter))); | 319 | printf("Read seccomp filter, size %u bytes\n", (unsigned) (sfilter_index * sizeof(struct sock_filter))); |
332 | 320 | ||
333 | close(fd); | 321 | close(fd); |
334 | free(fname); | ||
335 | 322 | ||
336 | if (arg_debug) | 323 | if (arg_debug) |
337 | filter_debug(); | 324 | filter_debug(); |
@@ -706,7 +693,7 @@ int seccomp_filter_errno(void) { | |||
706 | 693 | ||
707 | void seccomp_set(void) { | 694 | void seccomp_set(void) { |
708 | // read seccomp filter from /tmp/firejail/mnt/seccomp | 695 | // read seccomp filter from /tmp/firejail/mnt/seccomp |
709 | read_seccomp_file(NULL); | 696 | read_seccomp_file(SECCOMP_CFG); |
710 | 697 | ||
711 | // apply filter | 698 | // apply filter |
712 | struct sock_fprog prog = { | 699 | struct sock_fprog prog = { |
@@ -767,7 +754,7 @@ void seccomp_print_filter(pid_t pid) { | |||
767 | 754 | ||
768 | // find the seccomp filter | 755 | // find the seccomp filter |
769 | char *fname; | 756 | char *fname; |
770 | if (asprintf(&fname, "/proc/%d/root/tmp/firejail/mnt/seccomp", pid) == -1) | 757 | if (asprintf(&fname, "/proc/%d/root%s", pid, SECCOMP_CFG) == -1) |
771 | errExit("asprintf"); | 758 | errExit("asprintf"); |
772 | 759 | ||
773 | struct stat s; | 760 | struct stat s; |
@@ -780,6 +767,7 @@ void seccomp_print_filter(pid_t pid) { | |||
780 | read_seccomp_file(fname); | 767 | read_seccomp_file(fname); |
781 | drop_privs(1); | 768 | drop_privs(1); |
782 | filter_debug(); | 769 | filter_debug(); |
770 | free(fname); | ||
783 | 771 | ||
784 | exit(0); | 772 | exit(0); |
785 | } | 773 | } |