Documentation / technical / api-run-command.txton commit Merge branch 'lt/maint-diff-reduce-lstat' into maint (5e04a1e)
   1run-command API
   2===============
   3
   4The run-command API offers a versatile tool to run sub-processes with
   5redirected input and output as well as with a modified environment
   6and an alternate current directory.
   7
   8A similar API offers the capability to run a function asynchronously,
   9which is primarily used to capture the output that the function
  10produces in the caller in order to process it.
  11
  12
  13Functions
  14---------
  15
  16`start_command`::
  17
  18        Start a sub-process. Takes a pointer to a `struct child_process`
  19        that specifies the details and returns pipe FDs (if requested).
  20        See below for details.
  21
  22`finish_command`::
  23
  24        Wait for the completion of a sub-process that was started with
  25        start_command().
  26
  27`run_command`::
  28
  29        A convenience function that encapsulates a sequence of
  30        start_command() followed by finish_command(). Takes a pointer
  31        to a `struct child_process` that specifies the details.
  32
  33`run_command_v_opt`, `run_command_v_opt_cd_env`::
  34
  35        Convenience functions that encapsulate a sequence of
  36        start_command() followed by finish_command(). The argument argv
  37        specifies the program and its arguments. The argument opt is zero
  38        or more of the flags `RUN_COMMAND_NO_STDIN`, `RUN_GIT_CMD`, or
  39        `RUN_COMMAND_STDOUT_TO_STDERR` that correspond to the members
  40        .no_stdin, .git_cmd, .stdout_to_stderr of `struct child_process`.
  41        The argument dir corresponds the member .dir. The argument env
  42        corresponds to the member .env.
  43
  44`start_async`::
  45
  46        Run a function asynchronously. Takes a pointer to a `struct
  47        async` that specifies the details and returns a pipe FD
  48        from which the caller reads. See below for details.
  49
  50`finish_async`::
  51
  52        Wait for the completion of an asynchronous function that was
  53        started with start_async().
  54
  55`run_hook`::
  56
  57        Run a hook.
  58        The first argument is a pathname to an index file, or NULL
  59        if the hook uses the default index file or no index is needed.
  60        The second argument is the name of the hook.
  61        The further arguments correspond to the hook arguments.
  62        The last argument has to be NULL to terminate the arguments list.
  63        If the hook does not exist or is not executable, the return
  64        value will be zero.
  65        If it is executable, the hook will be executed and the exit
  66        status of the hook is returned.
  67        On execution, .stdout_to_stderr and .no_stdin will be set.
  68        (See below.)
  69
  70
  71Data structures
  72---------------
  73
  74* `struct child_process`
  75
  76This describes the arguments, redirections, and environment of a
  77command to run in a sub-process.
  78
  79The caller:
  80
  811. allocates and clears (memset(&chld, 0, sizeof(chld));) a
  82   struct child_process variable;
  832. initializes the members;
  843. calls start_command();
  854. processes the data;
  865. closes file descriptors (if necessary; see below);
  876. calls finish_command().
  88
  89The .argv member is set up as an array of string pointers (NULL
  90terminated), of which .argv[0] is the program name to run (usually
  91without a path). If the command to run is a git command, set argv[0] to
  92the command name without the 'git-' prefix and set .git_cmd = 1.
  93
  94The members .in, .out, .err are used to redirect stdin, stdout,
  95stderr as follows:
  96
  97. Specify 0 to request no special redirection. No new file descriptor
  98  is allocated. The child process simply inherits the channel from the
  99  parent.
 100
 101. Specify -1 to have a pipe allocated; start_command() replaces -1
 102  by the pipe FD in the following way:
 103
 104        .in: Returns the writable pipe end into which the caller writes;
 105                the readable end of the pipe becomes the child's stdin.
 106
 107        .out, .err: Returns the readable pipe end from which the caller
 108                reads; the writable end of the pipe end becomes child's
 109                stdout/stderr.
 110
 111  The caller of start_command() must close the so returned FDs
 112  after it has completed reading from/writing to it!
 113
 114. Specify a file descriptor > 0 to be used by the child:
 115
 116        .in: The FD must be readable; it becomes child's stdin.
 117        .out: The FD must be writable; it becomes child's stdout.
 118        .err > 0 is not supported.
 119
 120  The specified FD is closed by start_command(), even if it fails to
 121  run the sub-process!
 122
 123. Special forms of redirection are available by setting these members
 124  to 1:
 125
 126        .no_stdin, .no_stdout, .no_stderr: The respective channel is
 127                redirected to /dev/null.
 128
 129        .stdout_to_stderr: stdout of the child is redirected to its
 130                stderr. This happens after stderr is itself redirected.
 131                So stdout will follow stderr to wherever it is
 132                redirected.
 133
 134To modify the environment of the sub-process, specify an array of
 135string pointers (NULL terminated) in .env:
 136
 137. If the string is of the form "VAR=value", i.e. it contains '='
 138  the variable is added to the child process's environment.
 139
 140. If the string does not contain '=', it names an environment
 141  variable that will be removed from the child process's environment.
 142
 143To specify a new initial working directory for the sub-process,
 144specify it in the .dir member.
 145
 146
 147* `struct async`
 148
 149This describes a function to run asynchronously, whose purpose is
 150to produce output that the caller reads.
 151
 152The caller:
 153
 1541. allocates and clears (memset(&asy, 0, sizeof(asy));) a
 155   struct async variable;
 1562. initializes .proc and .data;
 1573. calls start_async();
 1584. processes the data by reading from the fd in .out;
 1595. closes .out;
 1606. calls finish_async().
 161
 162The function pointer in .proc has the following signature:
 163
 164        int proc(int fd, void *data);
 165
 166. fd specifies a writable file descriptor to which the function must
 167  write the data that it produces. The function *must* close this
 168  descriptor before it returns.
 169
 170. data is the value that the caller has specified in the .data member
 171  of struct async.
 172
 173. The return value of the function is 0 on success and non-zero
 174  on failure. If the function indicates failure, finish_async() will
 175  report failure as well.
 176
 177
 178There are serious restrictions on what the asynchronous function can do
 179because this facility is implemented by a pipe to a forked process on
 180UNIX, but by a thread in the same address space on Windows:
 181
 182. It cannot change the program's state (global variables, environment,
 183  etc.) in a way that the caller notices; in other words, .out is the
 184  only communication channel to the caller.
 185
 186. It must not change the program's state that the caller of the
 187  facility also uses.