diff options
Diffstat (limited to 'src/firejail/sandbox.c')
-rw-r--r-- | src/firejail/sandbox.c | 68 |
1 files changed, 62 insertions, 6 deletions
diff --git a/src/firejail/sandbox.c b/src/firejail/sandbox.c index 47c6b7a06..55733d5d7 100644 --- a/src/firejail/sandbox.c +++ b/src/firejail/sandbox.c | |||
@@ -295,10 +295,64 @@ static void print_time(void) { | |||
295 | printf("Child process initialized\n"); | 295 | printf("Child process initialized\n"); |
296 | } | 296 | } |
297 | 297 | ||
298 | void start_application(void) { | ||
299 | //if (setsid() == -1) | ||
300 | //errExit("setsid"); | ||
301 | 298 | ||
299 | // check execute permissions for the program | ||
300 | // this is done typically by the shell | ||
301 | // we are here because of --shell=none | ||
302 | // we duplicate execvp functionality (man execvp): | ||
303 | // [...] if the specified | ||
304 | // filename does not contain a slash (/) character. The file is sought | ||
305 | // in the colon-separated list of directory pathnames specified in the | ||
306 | // PATH environment variable. | ||
307 | static int ok_to_run(const char *program) { | ||
308 | if (strstr(program, "/")) { | ||
309 | if (access(program, X_OK) == 0) // it will also dereference symlinks | ||
310 | return 1; | ||
311 | } | ||
312 | else { // search $PATH | ||
313 | char *path1 = getenv("PATH"); | ||
314 | if (path1) { | ||
315 | if (arg_debug) | ||
316 | printf("Searching $PATH for %s\n", program); | ||
317 | char *path2 = strdup(path1); | ||
318 | if (!path2) | ||
319 | errExit("strdup"); | ||
320 | |||
321 | // use path2 to count the entries | ||
322 | char *ptr = strtok(path2, ":"); | ||
323 | while (ptr) { | ||
324 | char *fname; | ||
325 | |||
326 | if (asprintf(&fname, "%s/%s", ptr, program) == -1) | ||
327 | errExit("asprintf"); | ||
328 | if (arg_debug) | ||
329 | printf("trying #%s#\n", fname); | ||
330 | |||
331 | struct stat s; | ||
332 | int rv = stat(fname, &s); | ||
333 | if (rv == 0) { | ||
334 | if (access(fname, X_OK) == 0) { | ||
335 | free(path2); | ||
336 | free(fname); | ||
337 | return 1; | ||
338 | } | ||
339 | else | ||
340 | fprintf(stderr, "Error: execute permission denied for %s\n", fname); | ||
341 | |||
342 | free(fname); | ||
343 | break; | ||
344 | } | ||
345 | |||
346 | free(fname); | ||
347 | ptr = strtok(NULL, ":"); | ||
348 | } | ||
349 | free(path2); | ||
350 | } | ||
351 | } | ||
352 | return 0; | ||
353 | } | ||
354 | |||
355 | void start_application(void) { | ||
302 | // set environment | 356 | // set environment |
303 | env_defaults(); | 357 | env_defaults(); |
304 | env_apply(); | 358 | env_apply(); |
@@ -338,10 +392,14 @@ void start_application(void) { | |||
338 | if (!arg_command && !arg_quiet) | 392 | if (!arg_command && !arg_quiet) |
339 | print_time(); | 393 | print_time(); |
340 | 394 | ||
395 | int rv = ok_to_run(cfg.original_argv[cfg.original_program_index]); | ||
341 | #ifdef HAVE_GCOV | 396 | #ifdef HAVE_GCOV |
342 | __gcov_dump(); | 397 | __gcov_dump(); |
343 | #endif | 398 | #endif |
344 | execvp(cfg.original_argv[cfg.original_program_index], &cfg.original_argv[cfg.original_program_index]); | 399 | if (rv) |
400 | execvp(cfg.original_argv[cfg.original_program_index], &cfg.original_argv[cfg.original_program_index]); | ||
401 | else | ||
402 | fprintf(stderr, "Error: no suitable %s executable found\n", cfg.original_argv[cfg.original_program_index]); | ||
345 | exit(1); | 403 | exit(1); |
346 | } | 404 | } |
347 | //**************************************** | 405 | //**************************************** |
@@ -555,7 +613,6 @@ int sandbox(void* sandbox_arg) { | |||
555 | printf("Network namespace enabled\n"); | 613 | printf("Network namespace enabled\n"); |
556 | } | 614 | } |
557 | 615 | ||
558 | |||
559 | // print network configuration | 616 | // print network configuration |
560 | if (!arg_quiet) { | 617 | if (!arg_quiet) { |
561 | if (any_bridge_configured() || any_interface_configured() || cfg.defaultgw || cfg.dns1) { | 618 | if (any_bridge_configured() || any_interface_configured() || cfg.defaultgw || cfg.dns1) { |
@@ -767,7 +824,6 @@ int sandbox(void* sandbox_arg) { | |||
767 | } | 824 | } |
768 | } | 825 | } |
769 | 826 | ||
770 | |||
771 | //**************************** | 827 | //**************************** |
772 | // hosts and hostname | 828 | // hosts and hostname |
773 | //**************************** | 829 | //**************************** |