|
|
|
@ -24,6 +24,7 @@
|
|
|
|
|
#include <errno.h> |
|
|
|
|
#include <signal.h> |
|
|
|
|
#include <pthread.h> |
|
|
|
|
#include <fcntl.h> |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/* for -charset */ |
|
|
|
@ -3673,3 +3674,215 @@ ex:;
|
|
|
|
|
return(1); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
/* >>> make configurable by configure.ac # define Xorriso_allow_launch_frontenD 1 */ |
|
|
|
|
/* # define Xorriso_allow_launch_frontend_suiD 1 */ |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
int Xorriso_launch_frontend(struct XorrisO *xorriso, char *cmd, |
|
|
|
|
char *cmd_pipe_adr, char *reply_pipe_adr, int flag) |
|
|
|
|
{ |
|
|
|
|
int command_pipe[2], reply_pipe[2], ret, i, argc= 0, cpid, is_banned= 0; |
|
|
|
|
char **argv= NULL, **exec_argv= NULL, *sfe= NULL, *adrpt; |
|
|
|
|
struct stat stbuf; |
|
|
|
|
|
|
|
|
|
Xorriso_alloc_meM(sfe, char, 5 * SfileadrL); |
|
|
|
|
for(i= 0; i < 2; i++) |
|
|
|
|
command_pipe[i]= reply_pipe[i]= -1; |
|
|
|
|
|
|
|
|
|
#ifndef Xorriso_allow_launch_frontenD |
|
|
|
|
/* To be controlled by: configure --enable-external-filters */ |
|
|
|
|
|
|
|
|
|
sprintf(xorriso->info_text, "-launch_frontend : Banned at compile time."); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"This may be changed at compile time by ./configure option --enable-external-filters"); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "HINT", 0); |
|
|
|
|
is_banned= 1; |
|
|
|
|
|
|
|
|
|
#endif /* ! Xorriso_allow_launch_frontenD */ |
|
|
|
|
|
|
|
|
|
#ifndef Xorriso_allow_launch_frontend_suiD |
|
|
|
|
|
|
|
|
|
/* To be controlled by: configure --enable-external-filters-setuid */ |
|
|
|
|
|
|
|
|
|
if(getuid() != geteuid()) { |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"-set_filter: UID and EUID differ. Will not run external programs."); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FATAL", 0); |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"This may be changed at compile time by ./configure option --enable-external-filters-setuid"); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "HINT", 0); |
|
|
|
|
is_banned= 1; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
#endif /* ! Xorriso_allow_launch_frontend_suiD */ |
|
|
|
|
|
|
|
|
|
if(is_banned) |
|
|
|
|
{ret= 0; goto ex;} |
|
|
|
|
|
|
|
|
|
ret= Xorriso_parse_line(xorriso, cmd, "", "", 0, &argc, &argv, 1 | 64); |
|
|
|
|
if(ret <= 0) |
|
|
|
|
goto ex; |
|
|
|
|
if(argc > 0) { |
|
|
|
|
if(strchr(argv[0], '/') == NULL) { |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"-launch_frontend : Command path does not contain a '/'-character"); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0); |
|
|
|
|
{ret= 0; goto ex;} |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/* Add a NULL pointer for execv() */ |
|
|
|
|
Xorriso_alloc_meM(exec_argv, char *, argc + 1); |
|
|
|
|
if(exec_argv == NULL) { |
|
|
|
|
Xorriso_no_malloc_memory(xorriso, NULL, 0); |
|
|
|
|
ret= -1; goto ex; |
|
|
|
|
} |
|
|
|
|
for(i= 0; i < argc; i++) |
|
|
|
|
exec_argv[i]= argv[i]; |
|
|
|
|
exec_argv[argc]= NULL; |
|
|
|
|
} else if(cmd_pipe_adr[0] == 0 || reply_pipe_adr[0] == 0) |
|
|
|
|
{ret= 0; goto ex;} |
|
|
|
|
|
|
|
|
|
if(cmd_pipe_adr[0] && reply_pipe_adr[0]) { |
|
|
|
|
/* Create named pipes if needed */ |
|
|
|
|
for(i= 0; i < 2; i++) { |
|
|
|
|
if(i == 0) |
|
|
|
|
adrpt= cmd_pipe_adr; |
|
|
|
|
else |
|
|
|
|
adrpt= reply_pipe_adr; |
|
|
|
|
ret= stat(adrpt, &stbuf); |
|
|
|
|
if(ret == -1) { |
|
|
|
|
ret= mknod(adrpt, S_IFIFO | S_IRWXU | S_IRWXG | S_IRWXO | S_IRWXO, |
|
|
|
|
(dev_t) 0); |
|
|
|
|
if(ret == -1) { |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"-launch_frontend: Cannot create named pipe %s", |
|
|
|
|
Text_shellsafe(adrpt, sfe, 0)); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, |
|
|
|
|
"FAILURE", 0); |
|
|
|
|
ret= 0; goto ex; |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
} else { |
|
|
|
|
ret= pipe(command_pipe); |
|
|
|
|
if (ret == -1) { |
|
|
|
|
no_pipe_open: |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"-launch_frontend: Failed to create a nameless pipe object"); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, "FAILURE", 0); |
|
|
|
|
ret= 0; goto ex; |
|
|
|
|
} |
|
|
|
|
ret= pipe(reply_pipe); |
|
|
|
|
if (ret == -1) |
|
|
|
|
goto no_pipe_open; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if(argc > 0) { |
|
|
|
|
cpid = fork(); |
|
|
|
|
if (cpid == -1) { |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"-launch_frontend: Failed to create a child process"); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, "FAILURE", 0); |
|
|
|
|
ret= 0; goto ex; |
|
|
|
|
} |
|
|
|
|
} else |
|
|
|
|
cpid= -1; /* Dummy child id */ |
|
|
|
|
|
|
|
|
|
if (cpid != 0) { |
|
|
|
|
/* Parent becomes the xorriso slave */ |
|
|
|
|
|
|
|
|
|
if(cmd_pipe_adr[0] && reply_pipe_adr[0]) { |
|
|
|
|
command_pipe[0]= open(cmd_pipe_adr, O_RDONLY); |
|
|
|
|
if(command_pipe[0] == -1) { |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"-launch_frontend: Failed to open named command pipe %s", |
|
|
|
|
Text_shellsafe(cmd_pipe_adr, sfe, 0)); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, |
|
|
|
|
"FAILURE", 0); |
|
|
|
|
ret= 0; goto ex; |
|
|
|
|
} |
|
|
|
|
reply_pipe[1]= open(reply_pipe_adr, O_WRONLY | O_APPEND); |
|
|
|
|
if(reply_pipe[1] == -1) { |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"-launch_frontend: Failed to open named reply pipe %s", |
|
|
|
|
Text_shellsafe(reply_pipe_adr, sfe, 0)); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, |
|
|
|
|
"FAILURE", 0); |
|
|
|
|
ret= 0; goto ex; |
|
|
|
|
} |
|
|
|
|
} else { |
|
|
|
|
/* Close unused pipe ends */ |
|
|
|
|
close(command_pipe[1]); |
|
|
|
|
close(reply_pipe[0]); |
|
|
|
|
} |
|
|
|
|
close(0); |
|
|
|
|
close(1); |
|
|
|
|
close(2); |
|
|
|
|
ret= dup2(command_pipe[0], 0); |
|
|
|
|
if(ret == -1) { |
|
|
|
|
no_dup:; |
|
|
|
|
sprintf(xorriso->info_text, |
|
|
|
|
"-launch_frontend: Failed to connect pipe to xorriso standard i/o channels"); |
|
|
|
|
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, "FAILURE", 0); |
|
|
|
|
ret= -1; goto ex; |
|
|
|
|
} |
|
|
|
|
ret= dup2(reply_pipe[1], 1); |
|
|
|
|
if(ret == -1) |
|
|
|
|
goto no_dup; |
|
|
|
|
ret= dup2(reply_pipe[1], 2); |
|
|
|
|
if(ret == -1) |
|
|
|
|
goto no_dup; |
|
|
|
|
ret= 1; goto ex; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
/* Child becomes the frontend program */ |
|
|
|
|
|
|
|
|
|
/* Close unused pipe ends */; |
|
|
|
|
if(cmd_pipe_adr[0] && reply_pipe_adr[0]) { |
|
|
|
|
command_pipe[1]= open(cmd_pipe_adr, O_WRONLY | O_APPEND); |
|
|
|
|
if(command_pipe[1] == -1) { |
|
|
|
|
fprintf(stderr, |
|
|
|
|
"xorriso: -launch_frontend: Failed to open named command pipe '%s'\n", |
|
|
|
|
cmd_pipe_adr); |
|
|
|
|
perror("xorriso: -launch_frontend"); |
|
|
|
|
exit(1);
|
|
|
|
|
} |
|
|
|
|
reply_pipe[0]= open(reply_pipe_adr, O_RDONLY); |
|
|
|
|
if(reply_pipe[0] == -1) { |
|
|
|
|
fprintf(stderr, |
|
|
|
|
"xorriso: -launch_frontend: Failed to open named reply pipe '%s'\n", |
|
|
|
|
reply_pipe_adr); |
|
|
|
|
exit(1);
|
|
|
|
|
} |
|
|
|
|
} else { |
|
|
|
|
close(command_pipe[0]); |
|
|
|
|
close(reply_pipe[1]); |
|
|
|
|
} |
|
|
|
|
close(0); |
|
|
|
|
close(1); |
|
|
|
|
ret= dup2(command_pipe[1], 1); |
|
|
|
|
if(ret == -1) { |
|
|
|
|
perror("xorriso: -launch_frontend: Error on redirecting standard output for frontend"); |
|
|
|
|
exit(1); |
|
|
|
|
} |
|
|
|
|
ret= dup2(reply_pipe[0], 0); |
|
|
|
|
if(ret == -1) { |
|
|
|
|
perror("xorriso: -launch_frontend: Error on redirecting standard input for frontend"); |
|
|
|
|
exit(1); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
execv(exec_argv[0], exec_argv); |
|
|
|
|
fprintf(stderr, "xorriso: -launch_frontend: Failure to start program '%s'\n", |
|
|
|
|
exec_argv[0]); |
|
|
|
|
perror("xorriso: -launch_frontend"); |
|
|
|
|
exit(1); |
|
|
|
|
|
|
|
|
|
ex:; |
|
|
|
|
Xorriso__dispose_words(&argc, &argv); |
|
|
|
|
Xorriso_free_meM(exec_argv); |
|
|
|
|
Xorriso_free_meM(sfe); |
|
|
|
|
return(ret); |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|