diff options
Diffstat (limited to 'src/firejail/x11.c')
-rw-r--r-- | src/firejail/x11.c | 40 |
1 files changed, 13 insertions, 27 deletions
diff --git a/src/firejail/x11.c b/src/firejail/x11.c index f4f093138..09956b903 100644 --- a/src/firejail/x11.c +++ b/src/firejail/x11.c | |||
@@ -204,7 +204,6 @@ static int random_display_number(void) { | |||
204 | void x11_start_xvfb(int argc, char **argv) { | 204 | void x11_start_xvfb(int argc, char **argv) { |
205 | EUID_ASSERT(); | 205 | EUID_ASSERT(); |
206 | int i; | 206 | int i; |
207 | struct stat s; | ||
208 | pid_t jail = 0; | 207 | pid_t jail = 0; |
209 | pid_t server = 0; | 208 | pid_t server = 0; |
210 | 209 | ||
@@ -348,7 +347,7 @@ void x11_start_xvfb(int argc, char **argv) { | |||
348 | // wait for x11 server to start | 347 | // wait for x11 server to start |
349 | while (++n < 10) { | 348 | while (++n < 10) { |
350 | sleep(1); | 349 | sleep(1); |
351 | if (stat(fname, &s) == 0) | 350 | if (access(fname, F_OK) == 0) |
352 | break; | 351 | break; |
353 | }; | 352 | }; |
354 | 353 | ||
@@ -427,7 +426,6 @@ static char *extract_setting(int argc, char **argv, const char *argument) { | |||
427 | void x11_start_xephyr(int argc, char **argv) { | 426 | void x11_start_xephyr(int argc, char **argv) { |
428 | EUID_ASSERT(); | 427 | EUID_ASSERT(); |
429 | int i; | 428 | int i; |
430 | struct stat s; | ||
431 | pid_t jail = 0; | 429 | pid_t jail = 0; |
432 | pid_t server = 0; | 430 | pid_t server = 0; |
433 | 431 | ||
@@ -586,7 +584,7 @@ void x11_start_xephyr(int argc, char **argv) { | |||
586 | // wait for x11 server to start | 584 | // wait for x11 server to start |
587 | while (++n < 10) { | 585 | while (++n < 10) { |
588 | sleep(1); | 586 | sleep(1); |
589 | if (stat(fname, &s) == 0) | 587 | if (access(fname, F_OK) == 0) |
590 | break; | 588 | break; |
591 | }; | 589 | }; |
592 | 590 | ||
@@ -701,7 +699,6 @@ static char * get_title_arg_str() { | |||
701 | static void __attribute__((noreturn)) x11_start_xpra_old(int argc, char **argv, int display, char *display_str) { | 699 | static void __attribute__((noreturn)) x11_start_xpra_old(int argc, char **argv, int display, char *display_str) { |
702 | EUID_ASSERT(); | 700 | EUID_ASSERT(); |
703 | int i; | 701 | int i; |
704 | struct stat s; | ||
705 | pid_t client = 0; | 702 | pid_t client = 0; |
706 | pid_t server = 0; | 703 | pid_t server = 0; |
707 | 704 | ||
@@ -818,7 +815,7 @@ static void __attribute__((noreturn)) x11_start_xpra_old(int argc, char **argv, | |||
818 | // wait for x11 server to start | 815 | // wait for x11 server to start |
819 | while (++n < 10) { | 816 | while (++n < 10) { |
820 | sleep(1); | 817 | sleep(1); |
821 | if (stat(fname, &s) == 0) | 818 | if (access(fname, F_OK) == 0) |
822 | break; | 819 | break; |
823 | } | 820 | } |
824 | 821 | ||
@@ -1231,9 +1228,9 @@ void x11_xorg(void) { | |||
1231 | char *dest; | 1228 | char *dest; |
1232 | if (asprintf(&dest, "%s/.Xauthority", cfg.homedir) == -1) | 1229 | if (asprintf(&dest, "%s/.Xauthority", cfg.homedir) == -1) |
1233 | errExit("asprintf"); | 1230 | errExit("asprintf"); |
1234 | if (lstat(dest, &s) == -1) { | 1231 | if (access(dest, F_OK) == -1) { |
1235 | touch_file_as_user(dest, 0600); | 1232 | touch_file_as_user(dest, 0600); |
1236 | if (stat(dest, &s) == -1) { | 1233 | if (access(dest, F_OK) == -1) { |
1237 | fprintf(stderr, "Error: cannot create %s\n", dest); | 1234 | fprintf(stderr, "Error: cannot create %s\n", dest); |
1238 | exit(1); | 1235 | exit(1); |
1239 | } | 1236 | } |
@@ -1276,12 +1273,7 @@ void x11_xorg(void) { | |||
1276 | // mount via the link in /proc/self/fd | 1273 | // mount via the link in /proc/self/fd |
1277 | if (arg_debug) | 1274 | if (arg_debug) |
1278 | printf("Mounting %s on %s\n", tmpfname, dest); | 1275 | printf("Mounting %s on %s\n", tmpfname, dest); |
1279 | char *proc_src, *proc_dst; | 1276 | if (bind_mount_by_fd(src, dst)) { |
1280 | if (asprintf(&proc_src, "/proc/self/fd/%d", src) == -1) | ||
1281 | errExit("asprintf"); | ||
1282 | if (asprintf(&proc_dst, "/proc/self/fd/%d", dst) == -1) | ||
1283 | errExit("asprintf"); | ||
1284 | if (mount(proc_src, proc_dst, NULL, MS_BIND, NULL) == -1) { | ||
1285 | fprintf(stderr, "Error: cannot mount the new .Xauthority file\n"); | 1277 | fprintf(stderr, "Error: cannot mount the new .Xauthority file\n"); |
1286 | exit(1); | 1278 | exit(1); |
1287 | } | 1279 | } |
@@ -1289,8 +1281,6 @@ void x11_xorg(void) { | |||
1289 | MountData *mptr = get_last_mount(); | 1281 | MountData *mptr = get_last_mount(); |
1290 | if (strcmp(mptr->dir, dest) != 0 || strcmp(mptr->fstype, "tmpfs") != 0) | 1282 | if (strcmp(mptr->dir, dest) != 0 || strcmp(mptr->fstype, "tmpfs") != 0) |
1291 | errLogExit("invalid .Xauthority mount"); | 1283 | errLogExit("invalid .Xauthority mount"); |
1292 | free(proc_src); | ||
1293 | free(proc_dst); | ||
1294 | close(src); | 1284 | close(src); |
1295 | close(dst); | 1285 | close(dst); |
1296 | 1286 | ||
@@ -1299,7 +1289,7 @@ void x11_xorg(void) { | |||
1299 | // blacklist user .Xauthority file if it is not masked already | 1289 | // blacklist user .Xauthority file if it is not masked already |
1300 | const char *envar = env_get("XAUTHORITY"); | 1290 | const char *envar = env_get("XAUTHORITY"); |
1301 | if (envar) { | 1291 | if (envar) { |
1302 | char *rp = realpath(envar, NULL); | 1292 | char *rp = realpath_as_user(envar); |
1303 | if (rp) { | 1293 | if (rp) { |
1304 | if (strcmp(rp, dest) != 0) | 1294 | if (strcmp(rp, dest) != 0) |
1305 | disable_file_or_dir(rp); | 1295 | disable_file_or_dir(rp); |
@@ -1336,6 +1326,8 @@ void fs_x11(void) { | |||
1336 | return; | 1326 | return; |
1337 | } | 1327 | } |
1338 | 1328 | ||
1329 | // the mount source is under control of the user, so be careful and | ||
1330 | // mount without following symbolic links, using a file descriptor | ||
1339 | char *x11file; | 1331 | char *x11file; |
1340 | if (asprintf(&x11file, "/tmp/.X11-unix/X%d", display) == -1) | 1332 | if (asprintf(&x11file, "/tmp/.X11-unix/X%d", display) == -1) |
1341 | errExit("asprintf"); | 1333 | errExit("asprintf"); |
@@ -1344,10 +1336,10 @@ void fs_x11(void) { | |||
1344 | free(x11file); | 1336 | free(x11file); |
1345 | return; | 1337 | return; |
1346 | } | 1338 | } |
1347 | struct stat x11stat; | 1339 | struct stat s3; |
1348 | if (fstat(src, &x11stat) < 0) | 1340 | if (fstat(src, &s3) < 0) |
1349 | errExit("fstat"); | 1341 | errExit("fstat"); |
1350 | if (!S_ISSOCK(x11stat.st_mode)) { | 1342 | if (!S_ISSOCK(s3.st_mode)) { |
1351 | close(src); | 1343 | close(src); |
1352 | free(x11file); | 1344 | free(x11file); |
1353 | return; | 1345 | return; |
@@ -1367,14 +1359,8 @@ void fs_x11(void) { | |||
1367 | if (dst < 0) | 1359 | if (dst < 0) |
1368 | errExit("open"); | 1360 | errExit("open"); |
1369 | 1361 | ||
1370 | char *proc_src, *proc_dst; | 1362 | if (bind_mount_by_fd(src, dst)) |
1371 | if (asprintf(&proc_src, "/proc/self/fd/%d", src) == -1 || | ||
1372 | asprintf(&proc_dst, "/proc/self/fd/%d", dst) == -1) | ||
1373 | errExit("asprintf"); | ||
1374 | if (mount(proc_src, proc_dst, NULL, MS_BIND | MS_REC, NULL) < 0) | ||
1375 | errExit("mount bind"); | 1363 | errExit("mount bind"); |
1376 | free(proc_src); | ||
1377 | free(proc_dst); | ||
1378 | close(src); | 1364 | close(src); |
1379 | close(dst); | 1365 | close(dst); |
1380 | fs_logger2("whitelist", x11file); | 1366 | fs_logger2("whitelist", x11file); |