--- execute_cmd.c +++ execute_cmd.c 2010-06-24 09:18:46.858925084 +0200 @@ -1525,7 +1525,7 @@ static struct cpelement *cpl_search __P( static struct cpelement *cpl_searchbyname __P((char *)); static void cpl_prune __P((void)); -Coproc sh_coproc = { 0, NO_PID, -1, -1, 0, 0 }; +Coproc sh_coproc = { 0, NO_PID, -1, -1, 0, 0, 0, 0 }; cplist_t coproc_list = {0, 0, 0}; @@ -2047,13 +2047,19 @@ execute_coproc (command, pipe_in, pipe_o } #endif +static void restore_stdin(int lstdin) +{ + dup2(lstdin, 0); + close(lstdin); +} + static int execute_pipeline (command, asynchronous, pipe_in, pipe_out, fds_to_close) COMMAND *command; int asynchronous, pipe_in, pipe_out; struct fd_bitmap *fds_to_close; { - int prev, fildes[2], new_bitmap_size, dummyfd, ignore_return, exec_result; + int lstdin, prev, fildes[2], new_bitmap_size, dummyfd, ignore_return, exec_result; COMMAND *cmd; struct fd_bitmap *fd_bitmap; @@ -2148,11 +2154,37 @@ execute_pipeline (command, asynchronous, /* Now execute the rightmost command in the pipeline. */ if (ignore_return && cmd) cmd->flags |= CMD_IGNORE_RETURN; + + begin_unwind_frame ("pipe-file-descriptors"); + lstdin = -1; + if (!asynchronous && pipe_out == NO_PIPE && prev > 0) + { + lstdin = move_to_high_fd(0, 0, 255); + if (lstdin > 0) + { + dup2(prev, 0); + close(prev); + prev = NO_PIPE; + stop_pipeline (0, (COMMAND *)NULL); + add_unwind_protect (restore_stdin, lstdin); + } + } + if (prev >= 0) + add_unwind_protect (close, prev); + exec_result = execute_command_internal (cmd, asynchronous, prev, pipe_out, fds_to_close); + if (lstdin > 0) + { + dup2(lstdin, 0); + close(lstdin); + } + if (prev >= 0) close (prev); + discard_unwind_frame ("pipe-file-descriptors"); + #if defined (JOB_CONTROL) UNBLOCK_CHILD (oset); #endif