Split run_command into two halves (start/finish)
authorShawn O. Pearce <spearce@spearce.org>
Sat, 10 Mar 2007 08:28:05 +0000 (03:28 -0500)
committerJunio C Hamano <junkio@cox.net>
Mon, 12 Mar 2007 05:49:37 +0000 (22:49 -0700)
If the calling process wants to send data to stdin of a
child process it will need to arrange for a pipe and get
the child process running, feed data to it, then wait
for the child process to finish.  So we split the run
function into two halves, allowing callers to first
start the child then later finish it.

Signed-off-by: Shawn O. Pearce <spearce@spearce.org>
Signed-off-by: Junio C Hamano <junkio@cox.net>
run-command.c
run-command.h

index 1fb7fa5a8d6e0fb89d41a1b05e344bc62463926f..a866a0669426f0f1c94bee92d3b78d191209c28b 100644 (file)
@@ -2,13 +2,12 @@
 #include "run-command.h"
 #include "exec_cmd.h"
 
-int run_command(struct child_process *cmd)
+int start_command(struct child_process *cmd)
 {
-       pid_t pid = fork();
-
-       if (pid < 0)
+       cmd->pid = fork();
+       if (cmd->pid < 0)
                return -ERR_RUN_COMMAND_FORK;
-       if (!pid) {
+       if (!cmd->pid) {
                if (cmd->no_stdin) {
                        int fd = open("/dev/null", O_RDWR);
                        dup2(fd, 0);
@@ -23,9 +22,14 @@ int run_command(struct child_process *cmd)
                }
                die("exec %s failed.", cmd->argv[0]);
        }
+       return 0;
+}
+
+int finish_command(struct child_process *cmd)
+{
        for (;;) {
                int status, code;
-               pid_t waiting = waitpid(pid, &status, 0);
+               pid_t waiting = waitpid(cmd->pid, &status, 0);
 
                if (waiting < 0) {
                        if (errno == EINTR)
@@ -33,7 +37,7 @@ int run_command(struct child_process *cmd)
                        error("waitpid failed (%s)", strerror(errno));
                        return -ERR_RUN_COMMAND_WAITPID;
                }
-               if (waiting != pid)
+               if (waiting != cmd->pid)
                        return -ERR_RUN_COMMAND_WAITPID_WRONG_PID;
                if (WIFSIGNALED(status))
                        return -ERR_RUN_COMMAND_WAITPID_SIGNAL;
@@ -47,6 +51,14 @@ int run_command(struct child_process *cmd)
        }
 }
 
+int run_command(struct child_process *cmd)
+{
+       int code = start_command(cmd);
+       if (code)
+               return code;
+       return finish_command(cmd);
+}
+
 int run_command_v_opt(const char **argv, int opt)
 {
        struct child_process cmd;
index f9db2a7f8cc0462f3a2b5a8edf95348259990010..24cdb4eb190b6bea844e7c674ea4caf32462caa0 100644 (file)
@@ -12,11 +12,14 @@ enum {
 
 struct child_process {
        const char **argv;
+       pid_t pid;
        unsigned no_stdin:1;
        unsigned git_cmd:1; /* if this is to be git sub-command */
        unsigned stdout_to_stderr:1;
 };
 
+int start_command(struct child_process *);
+int finish_command(struct child_process *);
 int run_command(struct child_process *);
 
 #define RUN_COMMAND_NO_STDIN 1