New command -named_pipe_loop
This commit is contained in:
@ -87,11 +87,14 @@ int Xorriso_dialog_input(struct XorrisO *xorriso, char line[], int linesize,
|
||||
get_single:;
|
||||
#ifdef Xorriso_with_readlinE
|
||||
|
||||
if(xorriso->use_stdin || xorriso->dev_fd_1>=0) {
|
||||
if(xorriso->use_stdin || xorriso->dev_fd_1>=0 ||
|
||||
xorriso->tolerate_stdin_eof) {
|
||||
if(flag&2)
|
||||
{ret= 1; goto ex;}
|
||||
if(Sfile_fgets_n(linept,linesize - base_length - 1, stdin,
|
||||
(xorriso->dialog == 2)) == NULL) {
|
||||
if(xorriso->tolerate_stdin_eof)
|
||||
{ret= -2; goto ex;}
|
||||
/* need a very dramatic end */
|
||||
kill(getpid(),SIGHUP);
|
||||
{ret= -1; goto ex;}
|
||||
@ -126,6 +129,8 @@ process_single:;
|
||||
{ret= 1; goto ex;}
|
||||
if(Sfile_fgets_n(linept, linesize - base_length - 1, stdin,
|
||||
(xorriso->dialog == 2)) == NULL) {
|
||||
if(xorriso->tolerate_stdin_eof)
|
||||
{ret= -2; goto ex;}
|
||||
/* need a very dramatic end */
|
||||
kill(getpid(),SIGHUP);
|
||||
{ret= -1; goto ex;}
|
||||
@ -3949,3 +3954,168 @@ ex:;
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
|
||||
int Xorriso_open_named_pipe(struct XorrisO *xorriso, char fd_names[3][20],
|
||||
int mem_fds[], char *pipe_paths[], int pipe_fds[],
|
||||
int i, int flag)
|
||||
{
|
||||
if(mem_fds[i] == -1)
|
||||
return(2);
|
||||
pipe_fds[i]= open(pipe_paths[i], i == 0 ? O_RDONLY : O_WRONLY);
|
||||
if(pipe_fds[i] == -1) {
|
||||
sprintf(xorriso->info_text,
|
||||
"-named_pipe_loop: Failed to open %s pipe ", fd_names[i]);
|
||||
Text_shellsafe(pipe_paths[i], xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, "FAILURE",0);
|
||||
return(0);
|
||||
}
|
||||
close(i);
|
||||
dup2(pipe_fds[i], i);
|
||||
return(1);
|
||||
}
|
||||
|
||||
|
||||
/* Usage example via bash:
|
||||
|
||||
xorriso_cmd() {
|
||||
echo "$@" >/u/test/xorriso_stdin
|
||||
cat </u/test/xorriso_stdout
|
||||
}
|
||||
# Transport safety of filenames by wrapping in quotes and escaping quotes
|
||||
xorriso_esc() {
|
||||
echo -n "'"
|
||||
echo -n "$1" | sed -e "s/'/'"'"'"'"'"'"'/g"
|
||||
echo -n "'"
|
||||
}
|
||||
disk_path=...arbitrary.characters...
|
||||
iso_path=...arbitrary.characters...
|
||||
xorriso_cmd map $(xorriso_esc "$disk_path") $(xorriso_esc "$iso_path")
|
||||
*/
|
||||
int Xorriso_named_pipe_loop(struct XorrisO *xorriso,
|
||||
char *pipe_paths[3], int flag)
|
||||
{
|
||||
char *line= NULL;
|
||||
int i, ret, mem_fds[3], pipe_fds[3], first_line, hret;
|
||||
struct stat stbuf;
|
||||
static char fd_names[3][20] = {
|
||||
"standard input", "standard output", "standard error" };
|
||||
|
||||
if(xorriso->tolerate_stdin_eof) {
|
||||
sprintf(xorriso->info_text,
|
||||
"Already in -named_pipe_loop. Ignoring further -named_pipe_loop command.");
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, "SORRY", 0);
|
||||
return(0); /* intentionally not goto ex */
|
||||
}
|
||||
|
||||
Xorriso_alloc_meM(line, char, SfileadrL);
|
||||
for(i= 0; i < 3; i++ )
|
||||
mem_fds[i]= pipe_fds[i]= -1;
|
||||
|
||||
/* Memorize stdin, stdout, and stderr. Close originals. */
|
||||
for(i= 0; i < 3; i++ ) {
|
||||
if(pipe_paths[i][0] == 0 || strcmp(pipe_paths[i], "-") == 0)
|
||||
continue;
|
||||
if(stat(pipe_paths[i], &stbuf) == -1) {
|
||||
sprintf(xorriso->info_text,
|
||||
"-named_pipe_loop: Cannot determine properties of file ");
|
||||
Text_shellsafe(pipe_paths[i], xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
if(!S_ISFIFO(stbuf.st_mode)) {
|
||||
sprintf(xorriso->info_text,
|
||||
"-named_pipe_loop: File is not a named pipe: ");
|
||||
Text_shellsafe(pipe_paths[i], xorriso->info_text, 1);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, 0, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
mem_fds[i]= dup(i);
|
||||
if(mem_fds[i] == -1) {
|
||||
sprintf(xorriso->info_text,
|
||||
"-named_pipe_loop: Cannot duplicate original %s", fd_names[i]);
|
||||
Xorriso_msgs_submit(xorriso, 0, xorriso->info_text, errno, "FAILURE", 0);
|
||||
ret= 0; goto ex;
|
||||
}
|
||||
}
|
||||
|
||||
while(1) {
|
||||
/* Open input pipe */
|
||||
ret= Xorriso_open_named_pipe(xorriso, fd_names, mem_fds, pipe_paths,
|
||||
pipe_fds, 0, 0);
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
|
||||
/* As long as the input connection exists */
|
||||
xorriso->tolerate_stdin_eof= 1;
|
||||
first_line= 1;
|
||||
while(1) {
|
||||
|
||||
/* Fetch input line */
|
||||
ret= Xorriso_dialog_input(xorriso, line, SfileadrL, 1);
|
||||
|
||||
/* Open output pipes late to allow the sender to open them after
|
||||
the first (and usually only) input line was transmitted:
|
||||
echo ... >stdin_pipe
|
||||
res=$(cat <stdout_pipe)
|
||||
This will work independently of the stdin_pipe buffer size.
|
||||
*/
|
||||
if(first_line) {
|
||||
first_line= 0;
|
||||
for(i= 1; i < 3; i++) {
|
||||
hret= Xorriso_open_named_pipe(xorriso, fd_names, mem_fds, pipe_paths,
|
||||
pipe_fds, i, 0);
|
||||
if(hret <= 0 && ret > 0)
|
||||
{ret= hret; goto ex;}
|
||||
}
|
||||
}
|
||||
|
||||
/* Now evaluate outcome of Xorriso_dialog_input() */
|
||||
if(ret == -2) /* EOF at stdin */
|
||||
break;
|
||||
if(ret <= 0) /* Other error */
|
||||
goto ex;
|
||||
|
||||
/* Regular end of command */
|
||||
if(strcmp(line, "end_named_pipe_loop") == 0)
|
||||
{ret= 1; goto ex;}
|
||||
|
||||
/* Perform xorriso command */
|
||||
ret= Xorriso_execute_option(xorriso, line, (1 << 16));
|
||||
if(ret <= 0)
|
||||
goto ex;
|
||||
if(ret == 3) /* e.g. -end command */
|
||||
goto ex;
|
||||
Xorriso_mark(xorriso,0);
|
||||
}
|
||||
|
||||
/* Restore stdin, stdout and stderr */
|
||||
for(i= 0; i < 3; i++) {
|
||||
if(mem_fds[i] != -1) {
|
||||
if(pipe_fds[i] != -1)
|
||||
close(pipe_fds[i]);
|
||||
pipe_fds[i]= -1;
|
||||
close(i);
|
||||
dup2(mem_fds[i], i);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ret= 1;
|
||||
ex:;
|
||||
xorriso->tolerate_stdin_eof= 0;
|
||||
/* Close any open pipes. Restore stdin, stdout and stderr. */
|
||||
for(i= 0; i < 3; i++) {
|
||||
if(pipe_fds[i] != -1)
|
||||
close(pipe_fds[i]);
|
||||
if(mem_fds[i] != -1) {
|
||||
close(i);
|
||||
dup2(mem_fds[i], i);
|
||||
close(mem_fds[i]);
|
||||
}
|
||||
}
|
||||
Xorriso_free_meM(line);
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
|
Reference in New Issue
Block a user