diff options
-rw-r--r-- | src/firejail/firejail.h | 1 | ||||
-rw-r--r-- | src/firejail/fs_bin.c | 21 | ||||
-rw-r--r-- | src/firejail/fs_lib.c | 31 |
3 files changed, 48 insertions, 5 deletions
diff --git a/src/firejail/firejail.h b/src/firejail/firejail.h index 8e47a72d5..86f730aa0 100644 --- a/src/firejail/firejail.h +++ b/src/firejail/firejail.h | |||
@@ -50,6 +50,7 @@ | |||
50 | #define RUN_PULSE_DIR "/run/firejail/mnt/pulse" | 50 | #define RUN_PULSE_DIR "/run/firejail/mnt/pulse" |
51 | #define RUN_LIB_DIR "/run/firejail/mnt/lib" | 51 | #define RUN_LIB_DIR "/run/firejail/mnt/lib" |
52 | #define RUN_LIB_FILE "/run/firejail/mnt/libfiles" | 52 | #define RUN_LIB_FILE "/run/firejail/mnt/libfiles" |
53 | #define RUN_LIB_BIN "/run/firejail/mnt/binfiles" | ||
53 | 54 | ||
54 | #define RUN_SECCOMP_PROTOCOL "/run/firejail/mnt/seccomp.protocol" // protocol filter | 55 | #define RUN_SECCOMP_PROTOCOL "/run/firejail/mnt/seccomp.protocol" // protocol filter |
55 | #define RUN_SECCOMP_CFG "/run/firejail/mnt/seccomp" // configured filter | 56 | #define RUN_SECCOMP_CFG "/run/firejail/mnt/seccomp" // configured filter |
diff --git a/src/firejail/fs_bin.c b/src/firejail/fs_bin.c index 5170f2edc..7b259bf03 100644 --- a/src/firejail/fs_bin.c +++ b/src/firejail/fs_bin.c | |||
@@ -94,7 +94,7 @@ static char *check_dir_or_file(const char *name) { | |||
94 | return paths[i]; | 94 | return paths[i]; |
95 | } | 95 | } |
96 | 96 | ||
97 | static void duplicate(char *fname) { | 97 | static void duplicate(char *fname, FILE *fplist) { |
98 | if (*fname == '~' || *fname == '/' || strstr(fname, "..")) { | 98 | if (*fname == '~' || *fname == '/' || strstr(fname, "..")) { |
99 | fprintf(stderr, "Error: \"%s\" is an invalid filename\n", fname); | 99 | fprintf(stderr, "Error: \"%s\" is an invalid filename\n", fname); |
100 | exit(1); | 100 | exit(1); |
@@ -110,6 +110,9 @@ static void duplicate(char *fname) { | |||
110 | if (asprintf(&full_path, "%s/%s", path, fname) == -1) | 110 | if (asprintf(&full_path, "%s/%s", path, fname) == -1) |
111 | errExit("asprintf"); | 111 | errExit("asprintf"); |
112 | 112 | ||
113 | if (fplist) | ||
114 | fprintf(fplist, "%s\n", full_path); | ||
115 | |||
113 | // copy the file | 116 | // copy the file |
114 | if (checkcfg(CFG_FOLLOW_SYMLINK_PRIVATE_BIN)) | 117 | if (checkcfg(CFG_FOLLOW_SYMLINK_PRIVATE_BIN)) |
115 | sbox_run(SBOX_ROOT| SBOX_SECCOMP, 4, PATH_FCOPY, "--follow-link", full_path, RUN_BIN_DIR); | 118 | sbox_run(SBOX_ROOT| SBOX_SECCOMP, 4, PATH_FCOPY, "--follow-link", full_path, RUN_BIN_DIR); |
@@ -135,12 +138,22 @@ void fs_private_bin_list(void) { | |||
135 | if (!dlist) | 138 | if (!dlist) |
136 | errExit("strdup"); | 139 | errExit("strdup"); |
137 | 140 | ||
141 | // save a list of private-bin files in order to bring in private-libs later | ||
142 | FILE *fplist = NULL; | ||
143 | if (arg_private_lib) { | ||
144 | fplist = fopen(RUN_LIB_BIN, "w"); | ||
145 | if (!fplist) | ||
146 | errExit("fopen"); | ||
147 | } | ||
148 | |||
138 | char *ptr = strtok(dlist, ","); | 149 | char *ptr = strtok(dlist, ","); |
139 | duplicate(ptr); | 150 | duplicate(ptr, fplist); |
140 | while ((ptr = strtok(NULL, ",")) != NULL) | 151 | while ((ptr = strtok(NULL, ",")) != NULL) |
141 | duplicate(ptr); | 152 | duplicate(ptr, fplist); |
142 | free(dlist); | 153 | free(dlist); |
143 | fs_logger_print(); | 154 | fs_logger_print(); |
155 | if (fplist) | ||
156 | fclose(fplist); | ||
144 | 157 | ||
145 | // mount-bind | 158 | // mount-bind |
146 | int i = 0; | 159 | int i = 0; |
diff --git a/src/firejail/fs_lib.c b/src/firejail/fs_lib.c index 890f8daf9..f39349fe6 100644 --- a/src/firejail/fs_lib.c +++ b/src/firejail/fs_lib.c | |||
@@ -23,6 +23,8 @@ | |||
23 | #include <sys/types.h> | 23 | #include <sys/types.h> |
24 | #include <unistd.h> | 24 | #include <unistd.h> |
25 | 25 | ||
26 | #define MAXBUF 4096 | ||
27 | |||
26 | static const char * const lib_paths[] = { | 28 | static const char * const lib_paths[] = { |
27 | "/lib", | 29 | "/lib", |
28 | "/lib/x86_64-linux-gnu", | 30 | "/lib/x86_64-linux-gnu", |
@@ -68,7 +70,6 @@ static void copy_libs(const char *lib, const char *private_run_dir, const char * | |||
68 | if (!fp) | 70 | if (!fp) |
69 | errExit("fopen"); | 71 | errExit("fopen"); |
70 | 72 | ||
71 | #define MAXBUF 4096 | ||
72 | char buf[MAXBUF]; | 73 | char buf[MAXBUF]; |
73 | while (fgets(buf, MAXBUF, fp)) { | 74 | while (fgets(buf, MAXBUF, fp)) { |
74 | // remove \n | 75 | // remove \n |
@@ -98,6 +99,7 @@ static void copy_directory(const char *full_path, const char *dir_name, const ch | |||
98 | if (mount(full_path, dest, NULL, MS_BIND|MS_REC, NULL) < 0 || | 99 | if (mount(full_path, dest, NULL, MS_BIND|MS_REC, NULL) < 0 || |
99 | mount(NULL, dest, NULL, MS_BIND|MS_REMOUNT|MS_NOSUID|MS_NODEV|MS_REC, NULL) < 0) | 100 | mount(NULL, dest, NULL, MS_BIND|MS_REMOUNT|MS_NOSUID|MS_NODEV|MS_REC, NULL) < 0) |
100 | errExit("mount bind"); | 101 | errExit("mount bind"); |
102 | fs_logger2("clone", full_path); | ||
101 | fs_logger2("mount", full_path); | 103 | fs_logger2("mount", full_path); |
102 | free(dest); | 104 | free(dest); |
103 | } | 105 | } |
@@ -200,6 +202,22 @@ void fs_private_lib(void) { | |||
200 | fs_logger_print(); | 202 | fs_logger_print(); |
201 | } | 203 | } |
202 | 204 | ||
205 | // for private-bin files | ||
206 | if (arg_private_bin) { | ||
207 | FILE *fp = fopen(RUN_LIB_BIN, "r"); | ||
208 | if (fp) { | ||
209 | char buf[MAXBUF]; | ||
210 | while (fgets(buf, MAXBUF, fp)) { | ||
211 | // remove \n | ||
212 | char *ptr = strchr(buf, '\n'); | ||
213 | if (ptr) | ||
214 | *ptr = '\0'; | ||
215 | copy_libs(buf, RUN_LIB_DIR, RUN_LIB_FILE); | ||
216 | } | ||
217 | } | ||
218 | fclose(fp); | ||
219 | } | ||
220 | |||
203 | // for our trace and tracelog libs | 221 | // for our trace and tracelog libs |
204 | if (arg_trace) | 222 | if (arg_trace) |
205 | duplicate(LIBDIR "/firejail/libtrace.so", RUN_LIB_DIR); | 223 | duplicate(LIBDIR "/firejail/libtrace.so", RUN_LIB_DIR); |
@@ -212,15 +230,26 @@ void fs_private_lib(void) { | |||
212 | if (mount(RUN_LIB_DIR, "/lib", NULL, MS_BIND|MS_REC, NULL) < 0 || | 230 | if (mount(RUN_LIB_DIR, "/lib", NULL, MS_BIND|MS_REC, NULL) < 0 || |
213 | mount(NULL, "/lib", NULL, MS_BIND|MS_REMOUNT|MS_NOSUID|MS_NODEV|MS_REC, NULL) < 0) | 231 | mount(NULL, "/lib", NULL, MS_BIND|MS_REMOUNT|MS_NOSUID|MS_NODEV|MS_REC, NULL) < 0) |
214 | errExit("mount bind"); | 232 | errExit("mount bind"); |
233 | fs_logger2("tmpfs", "/lib"); | ||
215 | fs_logger("mount /lib"); | 234 | fs_logger("mount /lib"); |
216 | 235 | ||
217 | if (mount(RUN_LIB_DIR, "/lib64", NULL, MS_BIND|MS_REC, NULL) < 0 || | 236 | if (mount(RUN_LIB_DIR, "/lib64", NULL, MS_BIND|MS_REC, NULL) < 0 || |
218 | mount(NULL, "/lib64", NULL, MS_BIND|MS_REMOUNT|MS_NOSUID|MS_NODEV|MS_REC, NULL) < 0) | 237 | mount(NULL, "/lib64", NULL, MS_BIND|MS_REMOUNT|MS_NOSUID|MS_NODEV|MS_REC, NULL) < 0) |
219 | errExit("mount bind"); | 238 | errExit("mount bind"); |
239 | fs_logger2("tmpfs", "/lib64"); | ||
220 | fs_logger("mount /lib64"); | 240 | fs_logger("mount /lib64"); |
221 | 241 | ||
222 | if (mount(RUN_LIB_DIR, "/usr/lib", NULL, MS_BIND|MS_REC, NULL) < 0 || | 242 | if (mount(RUN_LIB_DIR, "/usr/lib", NULL, MS_BIND|MS_REC, NULL) < 0 || |
223 | mount(NULL, "/usr/lib", NULL, MS_BIND|MS_REMOUNT|MS_NOSUID|MS_NODEV|MS_REC, NULL) < 0) | 243 | mount(NULL, "/usr/lib", NULL, MS_BIND|MS_REMOUNT|MS_NOSUID|MS_NODEV|MS_REC, NULL) < 0) |
224 | errExit("mount bind"); | 244 | errExit("mount bind"); |
245 | fs_logger2("tmpfs", "/usr/lib"); | ||
225 | fs_logger("mount /usr/lib"); | 246 | fs_logger("mount /usr/lib"); |
247 | |||
248 | // for amd64 only - we'll deal with i386 later | ||
249 | if (mount(RUN_RO_DIR, "/lib32", "none", MS_BIND, "mode=400,gid=0") < 0) | ||
250 | errExit("disable file"); | ||
251 | fs_logger("blacklist-nolog /lib32"); | ||
252 | if (mount(RUN_RO_DIR, "/libx32", "none", MS_BIND, "mode=400,gid=0") < 0) | ||
253 | errExit("disable file"); | ||
254 | fs_logger("blacklist-nolog /libx32"); | ||
226 | } | 255 | } |