/* Distributed under the OSI-approved BSD 3-Clause License.  See accompanying
   file Copyright.txt or https://cmake.org/licensing#kwsys for details.  */
#include "kwsysPrivate.h"
#include KWSYS_HEADER(Process.h)
#include KWSYS_HEADER(System.h)

/* Work-around CMake dependency scanning limitation.  This must
   duplicate the above list of headers.  */
#if 0
#include "Process.h.in"
#include "System.h.in"
#endif

/*

Implementation for UNIX

On UNIX, a child process is forked to exec the program.  Three output
pipes are read by the parent process using a select call to block
until data are ready.  Two of the pipes are stdout and stderr for the
child.  The third is a special pipe populated by a signal handler to
indicate that a child has terminated.  This is used in conjunction
with the timeout on the select call to implement a timeout for program
even when it closes stdout and stderr and at the same time avoiding
races.

*/

/*

TODO:

We cannot create the pipeline of processes in suspended states.  How
do we cleanup processes already started when one fails to load?  Right
now we are just killing them, which is probably not the right thing to
do.

*/

#if defined(__CYGWIN__)
/* Increase the file descriptor limit for select() before including
   related system headers. (Default: 64) */
#define FD_SETSIZE 16384
#endif

#include <assert.h>    /* assert */
#include <ctype.h>     /* isspace */
#include <dirent.h>    /* DIR, dirent */
#include <errno.h>     /* errno */
#include <fcntl.h>     /* fcntl */
#include <signal.h>    /* sigaction */
#include <stddef.h>    /* ptrdiff_t */
#include <stdio.h>     /* snprintf */
#include <stdlib.h>    /* malloc, free */
#include <string.h>    /* strdup, strerror, memset */
#include <sys/stat.h>  /* open mode */
#include <sys/time.h>  /* struct timeval */
#include <sys/types.h> /* pid_t, fd_set */
#include <sys/wait.h>  /* waitpid */
#include <time.h>      /* gettimeofday */
#include <unistd.h>    /* pipe, close, fork, execvp, select, _exit */

#if defined(__VMS)
#define KWSYSPE_VMS_NONBLOCK , O_NONBLOCK
#else
#define KWSYSPE_VMS_NONBLOCK
#endif

#if defined(KWSYS_C_HAS_PTRDIFF_T) && KWSYS_C_HAS_PTRDIFF_T
typedef ptrdiff_t kwsysProcess_ptrdiff_t;
#else
typedef int kwsysProcess_ptrdiff_t;
#endif

#if defined(KWSYS_C_HAS_SSIZE_T) && KWSYS_C_HAS_SSIZE_T
typedef ssize_t kwsysProcess_ssize_t;
#else
typedef int kwsysProcess_ssize_t;
#endif

#if defined(__BEOS__) && !defined(__ZETA__)
/* BeOS 5 doesn't have usleep(), but it has snooze(), which is identical. */
#include <be/kernel/OS.h>
static inline void kwsysProcess_usleep(unsigned int msec)
{
  snooze(msec);
}
#else
#define kwsysProcess_usleep usleep
#endif

/*
 * BeOS's select() works like WinSock: it's for networking only, and
 * doesn't work with Unix file handles...socket and file handles are
 * different namespaces (the same descriptor means different things in
 * each context!)
 *
 * So on Unix-like systems where select() is flakey, we'll set the
 * pipes' file handles to be non-blocking and just poll them directly
 * without select().
 */
#if !defined(__BEOS__) && !defined(__VMS) && !defined(__MINT__) &&            \
  !defined(KWSYSPE_USE_SELECT)
#define KWSYSPE_USE_SELECT 1
#endif

/* Some platforms do not have siginfo on their signal handlers.  */
#if defined(SA_SIGINFO) && !defined(__BEOS__)
#define KWSYSPE_USE_SIGINFO 1
#endif

/* The number of pipes for the child's output.  The standard stdout
   and stderr pipes are the first two.  One more pipe is used to
   detect when the child process has terminated.  The third pipe is
   not given to the child process, so it cannot close it until it
   terminates.  */
#define KWSYSPE_PIPE_COUNT 3
#define KWSYSPE_PIPE_STDOUT 0
#define KWSYSPE_PIPE_STDERR 1
#define KWSYSPE_PIPE_SIGNAL 2

/* The maximum amount to read from a pipe at a time.  */
#define KWSYSPE_PIPE_BUFFER_SIZE 1024

/* Keep track of times using a signed representation.  Switch to the
   native (possibly unsigned) representation only when calling native
   functions.  */
typedef struct timeval kwsysProcessTimeNative;
typedef struct kwsysProcessTime_s kwsysProcessTime;
struct kwsysProcessTime_s
{
  long tv_sec;
  long tv_usec;
};

typedef struct kwsysProcessCreateInformation_s
{
  int StdIn;
  int StdOut;
  int StdErr;
  int ErrorPipe[2];
} kwsysProcessCreateInformation;

static void kwsysProcessVolatileFree(volatile void* p);
static int kwsysProcessInitialize(kwsysProcess* cp);
static void kwsysProcessCleanup(kwsysProcess* cp, int error);
static void kwsysProcessCleanupDescriptor(int* pfd);
static void kwsysProcessClosePipes(kwsysProcess* cp);
static int kwsysProcessSetNonBlocking(int fd);
static int kwsysProcessCreate(kwsysProcess* cp, int prIndex,
                              kwsysProcessCreateInformation* si);
static void kwsysProcessDestroy(kwsysProcess* cp);
static int kwsysProcessSetupOutputPipeFile(int* p, const char* name);
static int kwsysProcessSetupOutputPipeNative(int* p, int des[2]);
static int kwsysProcessGetTimeoutTime(kwsysProcess* cp, double* userTimeout,
                                      kwsysProcessTime* timeoutTime);
static int kwsysProcessGetTimeoutLeft(kwsysProcessTime* timeoutTime,
                                      double* userTimeout,
                                      kwsysProcessTimeNative* timeoutLength,
                                      int zeroIsExpired);
static kwsysProcessTime kwsysProcessTimeGetCurrent(void);
static double kwsysProcessTimeToDouble(kwsysProcessTime t);
static kwsysProcessTime kwsysProcessTimeFromDouble(double d);
static int kwsysProcessTimeLess(kwsysProcessTime in1, kwsysProcessTime in2);
static kwsysProcessTime kwsysProcessTimeAdd(kwsysProcessTime in1,
                                            kwsysProcessTime in2);
static kwsysProcessTime kwsysProcessTimeSubtract(kwsysProcessTime in1,
                                                 kwsysProcessTime in2);
static void kwsysProcessSetExitExceptionByIndex(kwsysProcess* cp, int sig,
                                                int idx);
static void kwsysProcessChildErrorExit(int errorPipe);
static void kwsysProcessRestoreDefaultSignalHandlers(void);
static pid_t kwsysProcessFork(kwsysProcess* cp,
                              kwsysProcessCreateInformation* si);
static void kwsysProcessKill(pid_t process_id);
#if defined(__VMS)
static int kwsysProcessSetVMSFeature(const char* name, int value);
#endif
static int kwsysProcessesAdd(kwsysProcess* cp);
static void kwsysProcessesRemove(kwsysProcess* cp);
#if KWSYSPE_USE_SIGINFO
static void kwsysProcessesSignalHandler(int signum, siginfo_t* info,
                                        void* ucontext);
#else
static void kwsysProcessesSignalHandler(int signum);
#endif

/* A structure containing results data for each process.  */
typedef struct kwsysProcessResults_s kwsysProcessResults;
struct kwsysProcessResults_s
{
  /* The status of the child process. */
  int State;

  /* The exceptional behavior that terminated the process, if any.  */
  int ExitException;

  /* The process exit code.  */
  int ExitCode;

  /* The process return code, if any.  */
  int ExitValue;

  /* Description for the ExitException.  */
  char ExitExceptionString[KWSYSPE_PIPE_BUFFER_SIZE + 1];
};

/* Structure containing data used to implement the child's execution.  */
struct kwsysProcess_s
{
  /* The command lines to execute.  */
  char*** Commands;
  volatile int NumberOfCommands;

  /* Descriptors for the read ends of the child's output pipes and
     the signal pipe. */
  int PipeReadEnds[KWSYSPE_PIPE_COUNT];

  /* Descriptors for the child's ends of the pipes.
     Used temporarily during process creation.  */
  int PipeChildStd[3];

  /* Write descriptor for child termination signal pipe.  */
  int SignalPipe;

  /* Buffer for pipe data.  */
  char PipeBuffer[KWSYSPE_PIPE_BUFFER_SIZE];

  /* Process IDs returned by the calls to fork.  Everything is volatile
     because the signal handler accesses them.  You must be very careful
     when reaping PIDs or modifying this array to avoid race conditions.  */
  volatile pid_t* volatile ForkPIDs;

  /* Flag for whether the children were terminated by a faild select.  */
  int SelectError;

  /* The timeout length.  */
  double Timeout;

  /* The working directory for the process. */
  char* WorkingDirectory;

  /* Whether to create the child as a detached process.  */
  int OptionDetach;

  /* Whether the child was created as a detached process.  */
  int Detached;

  /* Whether to treat command lines as verbatim.  */
  int Verbatim;

  /* Whether to merge stdout/stderr of the child.  */
  int MergeOutput;

  /* Whether to create the process in a new process group.  */
  volatile sig_atomic_t CreateProcessGroup;

  /* Time at which the child started.  Negative for no timeout.  */
  kwsysProcessTime StartTime;

  /* Time at which the child will timeout.  Negative for no timeout.  */
  kwsysProcessTime TimeoutTime;

  /* Flag for whether the timeout expired.  */
  int TimeoutExpired;

  /* The number of pipes left open during execution.  */
  int PipesLeft;

#if KWSYSPE_USE_SELECT
  /* File descriptor set for call to select.  */
  fd_set PipeSet;
#endif

  /* The number of children still executing.  */
  int CommandsLeft;

  /* The status of the process structure.  Must be atomic because
     the signal handler checks this to avoid a race.  */
  volatile sig_atomic_t State;

  /* Whether the process was killed.  */
  volatile sig_atomic_t Killed;

  /* Buffer for error message in case of failure.  */
  char ErrorMessage[KWSYSPE_PIPE_BUFFER_SIZE + 1];

  /* process results.  */
  kwsysProcessResults* ProcessResults;

  /* The exit codes of each child process in the pipeline.  */
  int* CommandExitCodes;

  /* Name of files to which stdin and stdout pipes are attached.  */
  char* PipeFileSTDIN;
  char* PipeFileSTDOUT;
  char* PipeFileSTDERR;

  /* Whether each pipe is shared with the parent process.  */
  int PipeSharedSTDIN;
  int PipeSharedSTDOUT;
  int PipeSharedSTDERR;

  /* Native pipes provided by the user.  */
  int PipeNativeSTDIN[2];
  int PipeNativeSTDOUT[2];
  int PipeNativeSTDERR[2];

  /* The real working directory of this process.  */
  int RealWorkingDirectoryLength;
  char* RealWorkingDirectory;
};

kwsysProcess* kwsysProcess_New(void)
{
  /* Allocate a process control structure.  */
  kwsysProcess* cp = (kwsysProcess*)malloc(sizeof(kwsysProcess));
  if (!cp) {
    return 0;
  }
  memset(cp, 0, sizeof(kwsysProcess));

  /* Share stdin with the parent process by default.  */
  cp->PipeSharedSTDIN = 1;

  /* No native pipes by default.  */
  cp->PipeNativeSTDIN[0] = -1;
  cp->PipeNativeSTDIN[1] = -1;
  cp->PipeNativeSTDOUT[0] = -1;
  cp->PipeNativeSTDOUT[1] = -1;
  cp->PipeNativeSTDERR[0] = -1;
  cp->PipeNativeSTDERR[1] = -1;

  /* Set initial status.  */
  cp->State = kwsysProcess_State_Starting;

  return cp;
}

void kwsysProcess_Delete(kwsysProcess* cp)
{
  /* Make sure we have an instance.  */
  if (!cp) {
    return;
  }

  /* If the process is executing, wait for it to finish.  */
  if (cp->State == kwsysProcess_State_Executing) {
    if (cp->Detached) {
      kwsysProcess_Disown(cp);
    } else {
      kwsysProcess_WaitForExit(cp, 0);
    }
  }

  /* Free memory.  */
  kwsysProcess_SetCommand(cp, 0);
  kwsysProcess_SetWorkingDirectory(cp, 0);
  kwsysProcess_SetPipeFile(cp, kwsysProcess_Pipe_STDIN, 0);
  kwsysProcess_SetPipeFile(cp, kwsysProcess_Pipe_STDOUT, 0);
  kwsysProcess_SetPipeFile(cp, kwsysProcess_Pipe_STDERR, 0);
  if (cp->CommandExitCodes) {
    free(cp->CommandExitCodes);
  }
  free(cp->ProcessResults);
  free(cp);
}

int kwsysProcess_SetCommand(kwsysProcess* cp, char const* const* command)
{
  int i;
  if (!cp) {
    return 0;
  }
  for (i = 0; i < cp->NumberOfCommands; ++i) {
    char** c = cp->Commands[i];
    while (*c) {
      free(*c++);
    }
    free(cp->Commands[i]);
  }
  cp->NumberOfCommands = 0;
  if (cp->Commands) {
    free(cp->Commands);
    cp->Commands = 0;
  }
  if (command) {
    return kwsysProcess_AddCommand(cp, command);
  }
  return 1;
}

int kwsysProcess_AddCommand(kwsysProcess* cp, char const* const* command)
{
  int newNumberOfCommands;
  char*** newCommands;

  /* Make sure we have a command to add.  */
  if (!cp || !command || !*command) {
    return 0;
  }

  /* Allocate a new array for command pointers.  */
  newNumberOfCommands = cp->NumberOfCommands + 1;
  if (!(newCommands =
          (char***)malloc(sizeof(char**) * (size_t)(newNumberOfCommands)))) {
    /* Out of memory.  */
    return 0;
  }

  /* Copy any existing commands into the new array.  */
  {
    int i;
    for (i = 0; i < cp->NumberOfCommands; ++i) {
      newCommands[i] = cp->Commands[i];
    }
  }

  /* Add the new command.  */
  if (cp->Verbatim) {
    /* In order to run the given command line verbatim we need to
       parse it.  */
    newCommands[cp->NumberOfCommands] =
      kwsysSystem_Parse_CommandForUnix(*command, 0);
    if (!newCommands[cp->NumberOfCommands] ||
        !newCommands[cp->NumberOfCommands][0]) {
      /* Out of memory or no command parsed.  */
      free(newCommands);
      return 0;
    }
  } else {
    /* Copy each argument string individually.  */
    char const* const* c = command;
    kwsysProcess_ptrdiff_t n = 0;
    kwsysProcess_ptrdiff_t i = 0;
    while (*c++)
      ;
    n = c - command - 1;
    newCommands[cp->NumberOfCommands] =
      (char**)malloc((size_t)(n + 1) * sizeof(char*));
    if (!newCommands[cp->NumberOfCommands]) {
      /* Out of memory.  */
      free(newCommands);
      return 0;
    }
    for (i = 0; i < n; ++i) {
      assert(command[i]); /* Quiet Clang scan-build. */
      newCommands[cp->NumberOfCommands][i] = strdup(command[i]);
      if (!newCommands[cp->NumberOfCommands][i]) {
        break;
      }
    }
    if (i < n) {
      /* Out of memory.  */
      for (; i > 0; --i) {
        free(newCommands[cp->NumberOfCommands][i - 1]);
      }
      free(newCommands);
      return 0;
    }
    newCommands[cp->NumberOfCommands][n] = 0;
  }

  /* Successfully allocated new command array.  Free the old array. */
  free(cp->Commands);
  cp->Commands = newCommands;
  cp->NumberOfCommands = newNumberOfCommands;

  return 1;
}

void kwsysProcess_SetTimeout(kwsysProcess* cp, double timeout)
{
  if (!cp) {
    return;
  }
  cp->Timeout = timeout;
  if (cp->Timeout < 0) {
    cp->Timeout = 0;
  }
  // Force recomputation of TimeoutTime.
  cp->TimeoutTime.tv_sec = -1;
}

int kwsysProcess_SetWorkingDirectory(kwsysProcess* cp, const char* dir)
{
  if (!cp) {
    return 0;
  }
  if (cp->WorkingDirectory == dir) {
    return 1;
  }
  if (cp->WorkingDirectory && dir && strcmp(cp->WorkingDirectory, dir) == 0) {
    return 1;
  }
  if (cp->WorkingDirectory) {
    free(cp->WorkingDirectory);
    cp->WorkingDirectory = 0;
  }
  if (dir) {
    cp->WorkingDirectory = (char*)malloc(strlen(dir) + 1);
    if (!cp->WorkingDirectory) {
      return 0;
    }
    strcpy(cp->WorkingDirectory, dir);
  }
  return 1;
}

int kwsysProcess_SetPipeFile(kwsysProcess* cp, int prPipe, const char* file)
{
  char** pfile;
  if (!cp) {
    return 0;
  }
  switch (prPipe) {
    case kwsysProcess_Pipe_STDIN:
      pfile = &cp->PipeFileSTDIN;
      break;
    case kwsysProcess_Pipe_STDOUT:
      pfile = &cp->PipeFileSTDOUT;
      break;
    case kwsysProcess_Pipe_STDERR:
      pfile = &cp->PipeFileSTDERR;
      break;
    default:
      return 0;
  }
  if (*pfile) {
    free(*pfile);
    *pfile = 0;
  }
  if (file) {
    *pfile = (char*)malloc(strlen(file) + 1);
    if (!*pfile) {
      return 0;
    }
    strcpy(*pfile, file);
  }

  /* If we are redirecting the pipe, do not share it or use a native
     pipe.  */
  if (*pfile) {
    kwsysProcess_SetPipeNative(cp, prPipe, 0);
    kwsysProcess_SetPipeShared(cp, prPipe, 0);
  }
  return 1;
}

void kwsysProcess_SetPipeShared(kwsysProcess* cp, int prPipe, int shared)
{
  if (!cp) {
    return;
  }

  switch (prPipe) {
    case kwsysProcess_Pipe_STDIN:
      cp->PipeSharedSTDIN = shared ? 1 : 0;
      break;
    case kwsysProcess_Pipe_STDOUT:
      cp->PipeSharedSTDOUT = shared ? 1 : 0;
      break;
    case kwsysProcess_Pipe_STDERR:
      cp->PipeSharedSTDERR = shared ? 1 : 0;
      break;
    default:
      return;
  }

  /* If we are sharing the pipe, do not redirect it to a file or use a
     native pipe.  */
  if (shared) {
    kwsysProcess_SetPipeFile(cp, prPipe, 0);
    kwsysProcess_SetPipeNative(cp, prPipe, 0);
  }
}

void kwsysProcess_SetPipeNative(kwsysProcess* cp, int prPipe, int p[2])
{
  int* pPipeNative = 0;

  if (!cp) {
    return;
  }

  switch (prPipe) {
    case kwsysProcess_Pipe_STDIN:
      pPipeNative = cp->PipeNativeSTDIN;
      break;
    case kwsysProcess_Pipe_STDOUT:
      pPipeNative = cp->PipeNativeSTDOUT;
      break;
    case kwsysProcess_Pipe_STDERR:
      pPipeNative = cp->PipeNativeSTDERR;
      break;
    default:
      return;
  }

  /* Copy the native pipe descriptors provided.  */
  if (p) {
    pPipeNative[0] = p[0];
    pPipeNative[1] = p[1];
  } else {
    pPipeNative[0] = -1;
    pPipeNative[1] = -1;
  }

  /* If we are using a native pipe, do not share it or redirect it to
     a file.  */
  if (p) {
    kwsysProcess_SetPipeFile(cp, prPipe, 0);
    kwsysProcess_SetPipeShared(cp, prPipe, 0);
  }
}

int kwsysProcess_GetOption(kwsysProcess* cp, int optionId)
{
  if (!cp) {
    return 0;
  }

  switch (optionId) {
    case kwsysProcess_Option_Detach:
      return cp->OptionDetach;
    case kwsysProcess_Option_MergeOutput:
      return cp->MergeOutput;
    case kwsysProcess_Option_Verbatim:
      return cp->Verbatim;
    case kwsysProcess_Option_CreateProcessGroup:
      return cp->CreateProcessGroup;
    default:
      return 0;
  }
}

void kwsysProcess_SetOption(kwsysProcess* cp, int optionId, int value)
{
  if (!cp) {
    return;
  }

  switch (optionId) {
    case kwsysProcess_Option_Detach:
      cp->OptionDetach = value;
      break;
    case kwsysProcess_Option_MergeOutput:
      cp->MergeOutput = value;
      break;
    case kwsysProcess_Option_Verbatim:
      cp->Verbatim = value;
      break;
    case kwsysProcess_Option_CreateProcessGroup:
      cp->CreateProcessGroup = value;
      break;
    default:
      break;
  }
}

int kwsysProcess_GetState(kwsysProcess* cp)
{
  return cp ? cp->State : kwsysProcess_State_Error;
}

int kwsysProcess_GetExitException(kwsysProcess* cp)
{
  return (cp && cp->ProcessResults && (cp->NumberOfCommands > 0))
    ? cp->ProcessResults[cp->NumberOfCommands - 1].ExitException
    : kwsysProcess_Exception_Other;
}

int kwsysProcess_GetExitCode(kwsysProcess* cp)
{
  return (cp && cp->ProcessResults && (cp->NumberOfCommands > 0))
    ? cp->ProcessResults[cp->NumberOfCommands - 1].ExitCode
    : 0;
}

int kwsysProcess_GetExitValue(kwsysProcess* cp)
{
  return (cp && cp->ProcessResults && (cp->NumberOfCommands > 0))
    ? cp->ProcessResults[cp->NumberOfCommands - 1].ExitValue
    : -1;
}

const char* kwsysProcess_GetErrorString(kwsysProcess* cp)
{
  if (!cp) {
    return "Process management structure could not be allocated";
  } else if (cp->State == kwsysProcess_State_Error) {
    return cp->ErrorMessage;
  }
  return "Success";
}

const char* kwsysProcess_GetExceptionString(kwsysProcess* cp)
{
  if (!(cp && cp->ProcessResults && (cp->NumberOfCommands > 0))) {
    return "GetExceptionString called with NULL process management structure";
  } else if (cp->State == kwsysProcess_State_Exception) {
    return cp->ProcessResults[cp->NumberOfCommands - 1].ExitExceptionString;
  }
  return "No exception";
}

/* the index should be in array bound. */
#define KWSYSPE_IDX_CHK(RET)                                                  \
  if (!cp || idx >= cp->NumberOfCommands || idx < 0) {                        \
    return RET;                                                               \
  }

int kwsysProcess_GetStateByIndex(kwsysProcess* cp, int idx)
{
  KWSYSPE_IDX_CHK(kwsysProcess_State_Error)
  return cp->ProcessResults[idx].State;
}

int kwsysProcess_GetExitExceptionByIndex(kwsysProcess* cp, int idx)
{
  KWSYSPE_IDX_CHK(kwsysProcess_Exception_Other)
  return cp->ProcessResults[idx].ExitException;
}

int kwsysProcess_GetExitValueByIndex(kwsysProcess* cp, int idx)
{
  KWSYSPE_IDX_CHK(-1)
  return cp->ProcessResults[idx].ExitValue;
}

int kwsysProcess_GetExitCodeByIndex(kwsysProcess* cp, int idx)
{
  KWSYSPE_IDX_CHK(-1)
  return cp->CommandExitCodes[idx];
}

const char* kwsysProcess_GetExceptionStringByIndex(kwsysProcess* cp, int idx)
{
  KWSYSPE_IDX_CHK("GetExceptionString called with NULL process management "
                  "structure or index out of bound")
  if (cp->ProcessResults[idx].State == kwsysProcess_StateByIndex_Exception) {
    return cp->ProcessResults[idx].ExitExceptionString;
  }
  return "No exception";
}

#undef KWSYSPE_IDX_CHK

void kwsysProcess_Execute(kwsysProcess* cp)
{
  int i;

  /* Do not execute a second copy simultaneously.  */
  if (!cp || cp->State == kwsysProcess_State_Executing) {
    return;
  }

  /* Make sure we have something to run.  */
  if (cp->NumberOfCommands < 1) {
    strcpy(cp->ErrorMessage, "No command");
    cp->State = kwsysProcess_State_Error;
    return;
  }

  /* Initialize the control structure for a new process.  */
  if (!kwsysProcessInitialize(cp)) {
    strcpy(cp->ErrorMessage, "Out of memory");
    cp->State = kwsysProcess_State_Error;
    return;
  }

#if defined(__VMS)
  /* Make sure pipes behave like streams on VMS.  */
  if (!kwsysProcessSetVMSFeature("DECC$STREAM_PIPE", 1)) {
    kwsysProcessCleanup(cp, 1);
    return;
  }
#endif

  /* Save the real working directory of this process and change to
     the working directory for the child processes.  This is needed
     to make pipe file paths evaluate correctly.  */
  if (cp->WorkingDirectory) {
    int r;
    if (!getcwd(cp->RealWorkingDirectory,
                (size_t)(cp->RealWorkingDirectoryLength))) {
      kwsysProcessCleanup(cp, 1);
      return;
    }

    /* Some platforms specify that the chdir call may be
       interrupted.  Repeat the call until it finishes.  */
    while (((r = chdir(cp->WorkingDirectory)) < 0) && (errno == EINTR))
      ;
    if (r < 0) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  }

  /* If not running a detached child, add this object to the global
     set of process objects that wish to be notified when a child
     exits.  */
  if (!cp->OptionDetach) {
    if (!kwsysProcessesAdd(cp)) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  }

  /* Setup the stdin pipe for the first process.  */
  if (cp->PipeFileSTDIN) {
    /* Open a file for the child's stdin to read.  */
    cp->PipeChildStd[0] = open(cp->PipeFileSTDIN, O_RDONLY);
    if (cp->PipeChildStd[0] < 0) {
      kwsysProcessCleanup(cp, 1);
      return;
    }

    /* Set close-on-exec flag on the pipe's end.  */
    if (fcntl(cp->PipeChildStd[0], F_SETFD, FD_CLOEXEC) < 0) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  } else if (cp->PipeSharedSTDIN) {
    cp->PipeChildStd[0] = 0;
  } else if (cp->PipeNativeSTDIN[0] >= 0) {
    cp->PipeChildStd[0] = cp->PipeNativeSTDIN[0];

    /* Set close-on-exec flag on the pipe's ends.  The read end will
       be dup2-ed into the stdin descriptor after the fork but before
       the exec.  */
    if ((fcntl(cp->PipeNativeSTDIN[0], F_SETFD, FD_CLOEXEC) < 0) ||
        (fcntl(cp->PipeNativeSTDIN[1], F_SETFD, FD_CLOEXEC) < 0)) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  } else {
    cp->PipeChildStd[0] = -1;
  }

  /* Create the output pipe for the last process.
     We always create this so the pipe can be passed to select even if
     it will report closed immediately.  */
  {
    /* Create the pipe.  */
    int p[2];
    if (pipe(p KWSYSPE_VMS_NONBLOCK) < 0) {
      kwsysProcessCleanup(cp, 1);
      return;
    }

    /* Store the pipe.  */
    cp->PipeReadEnds[KWSYSPE_PIPE_STDOUT] = p[0];
    cp->PipeChildStd[1] = p[1];

    /* Set close-on-exec flag on the pipe's ends.  */
    if ((fcntl(p[0], F_SETFD, FD_CLOEXEC) < 0) ||
        (fcntl(p[1], F_SETFD, FD_CLOEXEC) < 0)) {
      kwsysProcessCleanup(cp, 1);
      return;
    }

    /* Set to non-blocking in case select lies, or for the polling
       implementation.  */
    if (!kwsysProcessSetNonBlocking(p[0])) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  }

  if (cp->PipeFileSTDOUT) {
    /* Use a file for stdout.  */
    if (!kwsysProcessSetupOutputPipeFile(&cp->PipeChildStd[1],
                                         cp->PipeFileSTDOUT)) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  } else if (cp->PipeSharedSTDOUT) {
    /* Use the parent stdout.  */
    kwsysProcessCleanupDescriptor(&cp->PipeChildStd[1]);
    cp->PipeChildStd[1] = 1;
  } else if (cp->PipeNativeSTDOUT[1] >= 0) {
    /* Use the given descriptor for stdout.  */
    if (!kwsysProcessSetupOutputPipeNative(&cp->PipeChildStd[1],
                                           cp->PipeNativeSTDOUT)) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  }

  /* Create stderr pipe to be shared by all processes in the pipeline.
     We always create this so the pipe can be passed to select even if
     it will report closed immediately.  */
  {
    /* Create the pipe.  */
    int p[2];
    if (pipe(p KWSYSPE_VMS_NONBLOCK) < 0) {
      kwsysProcessCleanup(cp, 1);
      return;
    }

    /* Store the pipe.  */
    cp->PipeReadEnds[KWSYSPE_PIPE_STDERR] = p[0];
    cp->PipeChildStd[2] = p[1];

    /* Set close-on-exec flag on the pipe's ends.  */
    if ((fcntl(p[0], F_SETFD, FD_CLOEXEC) < 0) ||
        (fcntl(p[1], F_SETFD, FD_CLOEXEC) < 0)) {
      kwsysProcessCleanup(cp, 1);
      return;
    }

    /* Set to non-blocking in case select lies, or for the polling
       implementation.  */
    if (!kwsysProcessSetNonBlocking(p[0])) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  }

  if (cp->PipeFileSTDERR) {
    /* Use a file for stderr.  */
    if (!kwsysProcessSetupOutputPipeFile(&cp->PipeChildStd[2],
                                         cp->PipeFileSTDERR)) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  } else if (cp->PipeSharedSTDERR) {
    /* Use the parent stderr.  */
    kwsysProcessCleanupDescriptor(&cp->PipeChildStd[2]);
    cp->PipeChildStd[2] = 2;
  } else if (cp->PipeNativeSTDERR[1] >= 0) {
    /* Use the given handle for stderr.  */
    if (!kwsysProcessSetupOutputPipeNative(&cp->PipeChildStd[2],
                                           cp->PipeNativeSTDERR)) {
      kwsysProcessCleanup(cp, 1);
      return;
    }
  }

  /* The timeout period starts now.  */
  cp->StartTime = kwsysProcessTimeGetCurrent();
  cp->TimeoutTime.tv_sec = -1;
  cp->TimeoutTime.tv_usec = -1;

  /* Create the pipeline of processes.  */
  {
    kwsysProcessCreateInformation si = { -1, -1, -1, { -1, -1 } };
    int nextStdIn = cp->PipeChildStd[0];
    for (i = 0; i < cp->NumberOfCommands; ++i) {
      /* Setup the process's pipes.  */
      si.StdIn = nextStdIn;
      if (i == cp->NumberOfCommands - 1) {
        nextStdIn = -1;
        si.StdOut = cp->PipeChildStd[1];
      } else {
        /* Create a pipe to sit between the children.  */
        int p[2] = { -1, -1 };
        if (pipe(p KWSYSPE_VMS_NONBLOCK) < 0) {
          if (nextStdIn != cp->PipeChildStd[0]) {
            kwsysProcessCleanupDescriptor(&nextStdIn);
          }
          kwsysProcessCleanup(cp, 1);
          return;
        }

        /* Set close-on-exec flag on the pipe's ends.  */
        if ((fcntl(p[0], F_SETFD, FD_CLOEXEC) < 0) ||
            (fcntl(p[1], F_SETFD, FD_CLOEXEC) < 0)) {
          close(p[0]);
          close(p[1]);
          if (nextStdIn != cp->PipeChildStd[0]) {
            kwsysProcessCleanupDescriptor(&nextStdIn);
          }
          kwsysProcessCleanup(cp, 1);
          return;
        }
        nextStdIn = p[0];
        si.StdOut = p[1];
      }
      si.StdErr = cp->MergeOutput ? cp->PipeChildStd[1] : cp->PipeChildStd[2];

      {
        int res = kwsysProcessCreate(cp, i, &si);

        /* Close our copies of pipes used between children.  */
        if (si.StdIn != cp->PipeChildStd[0]) {
          kwsysProcessCleanupDescriptor(&si.StdIn);
        }
        if (si.StdOut != cp->PipeChildStd[1]) {
          kwsysProcessCleanupDescriptor(&si.StdOut);
        }
        if (si.StdErr != cp->PipeChildStd[2] && !cp->MergeOutput) {
          kwsysProcessCleanupDescriptor(&si.StdErr);
        }

        if (!res) {
          kwsysProcessCleanupDescriptor(&si.ErrorPipe[0]);
          kwsysProcessCleanupDescriptor(&si.ErrorPipe[1]);
          if (nextStdIn != cp->PipeChildStd[0]) {
            kwsysProcessCleanupDescriptor(&nextStdIn);
          }
          kwsysProcessCleanup(cp, 1);
          return;
        }
      }
    }
  }

  /* The parent process does not need the child's pipe ends.  */
  for (i = 0; i < 3; ++i) {
    kwsysProcessCleanupDescriptor(&cp->PipeChildStd[i]);
  }

  /* Restore the working directory. */
  if (cp->RealWorkingDirectory) {
    /* Some platforms specify that the chdir call may be
       interrupted.  Repeat the call until it finishes.  */
    while ((chdir(cp->RealWorkingDirectory) < 0) && (errno == EINTR))
      ;
    free(cp->RealWorkingDirectory);
    cp->RealWorkingDirectory = 0;
  }

  /* All the pipes are now open.  */
  cp->PipesLeft = KWSYSPE_PIPE_COUNT;

  /* The process has now started.  */
  cp->State = kwsysProcess_State_Executing;
  cp->Detached = cp->OptionDetach;
}

kwsysEXPORT void kwsysProcess_Disown(kwsysProcess* cp)
{
  /* Make sure a detached child process is running.  */
  if (!cp || !cp->Detached || cp->State != kwsysProcess_State_Executing ||
      cp->TimeoutExpired || cp->Killed) {
    return;
  }

  /* Close all the pipes safely.  */
  kwsysProcessClosePipes(cp);

  /* We will not wait for exit, so cleanup now.  */
  kwsysProcessCleanup(cp, 0);

  /* The process has been disowned.  */
  cp->State = kwsysProcess_State_Disowned;
}

typedef struct kwsysProcessWaitData_s
{
  int Expired;
  int PipeId;
  int User;
  double* UserTimeout;
  kwsysProcessTime TimeoutTime;
} kwsysProcessWaitData;
static int kwsysProcessWaitForPipe(kwsysProcess* cp, char** data, int* length,
                                   kwsysProcessWaitData* wd);

int kwsysProcess_WaitForData(kwsysProcess* cp, char** data, int* length,
                             double* userTimeout)
{
  kwsysProcessTime userStartTime = { 0, 0 };
  kwsysProcessWaitData wd = { 0, kwsysProcess_Pipe_None, 0, 0, { 0, 0 } };
  wd.UserTimeout = userTimeout;
  /* Make sure we are executing a process.  */
  if (!cp || cp->State != kwsysProcess_State_Executing || cp->Killed ||
      cp->TimeoutExpired) {
    return kwsysProcess_Pipe_None;
  }

  /* Record the time at which user timeout period starts.  */
  if (userTimeout) {
    userStartTime = kwsysProcessTimeGetCurrent();
  }

  /* Calculate the time at which a timeout will expire, and whether it
     is the user or process timeout.  */
  wd.User = kwsysProcessGetTimeoutTime(cp, userTimeout, &wd.TimeoutTime);

  /* Data can only be available when pipes are open.  If the process
     is not running, cp->PipesLeft will be 0.  */
  while (cp->PipesLeft > 0 &&
         !kwsysProcessWaitForPipe(cp, data, length, &wd)) {
  }

  /* Update the user timeout.  */
  if (userTimeout) {
    kwsysProcessTime userEndTime = kwsysProcessTimeGetCurrent();
    kwsysProcessTime difference =
      kwsysProcessTimeSubtract(userEndTime, userStartTime);
    double d = kwsysProcessTimeToDouble(difference);
    *userTimeout -= d;
    if (*userTimeout < 0) {
      *userTimeout = 0;
    }
  }

  /* Check what happened.  */
  if (wd.PipeId) {
    /* Data are ready on a pipe.  */
    return wd.PipeId;
  } else if (wd.Expired) {
    /* A timeout has expired.  */
    if (wd.User) {
      /* The user timeout has expired.  It has no time left.  */
      return kwsysProcess_Pipe_Timeout;
    } else {
      /* The process timeout has expired.  Kill the children now.  */
      kwsysProcess_Kill(cp);
      cp->Killed = 0;
      cp->TimeoutExpired = 1;
      return kwsysProcess_Pipe_None;
    }
  } else {
    /* No pipes are left open.  */
    return kwsysProcess_Pipe_None;
  }
}

static int kwsysProcessWaitForPipe(kwsysProcess* cp, char** data, int* length,
                                   kwsysProcessWaitData* wd)
{
  int i;
  kwsysProcessTimeNative timeoutLength;

#if KWSYSPE_USE_SELECT
  int numReady = 0;
  int max = -1;
  kwsysProcessTimeNative* timeout = 0;

  /* Check for any open pipes with data reported ready by the last
     call to select.  According to "man select_tut" we must deal
     with all descriptors reported by a call to select before
     passing them to another select call.  */
  for (i = 0; i < KWSYSPE_PIPE_COUNT; ++i) {
    if (cp->PipeReadEnds[i] >= 0 &&
        FD_ISSET(cp->PipeReadEnds[i], &cp->PipeSet)) {
      kwsysProcess_ssize_t n;

      /* We are handling this pipe now.  Remove it from the set.  */
      FD_CLR(cp->PipeReadEnds[i], &cp->PipeSet);

      /* The pipe is ready to read without blocking.  Keep trying to
         read until the operation is not interrupted.  */
      while (((n = read(cp->PipeReadEnds[i], cp->PipeBuffer,
                        KWSYSPE_PIPE_BUFFER_SIZE)) < 0) &&
             (errno == EINTR))
        ;
      if (n > 0) {
        /* We have data on this pipe.  */
        if (i == KWSYSPE_PIPE_SIGNAL) {
          /* A child process has terminated.  */
          kwsysProcessDestroy(cp);
        } else if (data && length) {
          /* Report this data.  */
          *data = cp->PipeBuffer;
          *length = (int)(n);
          switch (i) {
            case KWSYSPE_PIPE_STDOUT:
              wd->PipeId = kwsysProcess_Pipe_STDOUT;
              break;
            case KWSYSPE_PIPE_STDERR:
              wd->PipeId = kwsysProcess_Pipe_STDERR;
              break;
          };
          return 1;
        }
      } else if (n < 0 && errno == EAGAIN) {
        /* No data are really ready.  The select call lied.  See the
           "man select" page on Linux for cases when this occurs.  */
      } else {
        /* We are done reading from this pipe.  */
        kwsysProcessCleanupDescriptor(&cp->PipeReadEnds[i]);
        --cp->PipesLeft;
      }
    }
  }

  /* If we have data, break early.  */
  if (wd->PipeId) {
    return 1;
  }

  /* Make sure the set is empty (it should always be empty here
     anyway).  */
  FD_ZERO(&cp->PipeSet);

  /* Setup a timeout if required.  */
  if (wd->TimeoutTime.tv_sec < 0) {
    timeout = 0;
  } else {
    timeout = &timeoutLength;
  }
  if (kwsysProcessGetTimeoutLeft(
        &wd->TimeoutTime, wd->User ? wd->UserTimeout : 0, &timeoutLength, 0)) {
    /* Timeout has already expired.  */
    wd->Expired = 1;
    return 1;
  }

  /* Add the pipe reading ends that are still open.  */
  max = -1;
  for (i = 0; i < KWSYSPE_PIPE_COUNT; ++i) {
    if (cp->PipeReadEnds[i] >= 0) {
      FD_SET(cp->PipeReadEnds[i], &cp->PipeSet);
      if (cp->PipeReadEnds[i] > max) {
        max = cp->PipeReadEnds[i];
      }
    }
  }

  /* Make sure we have a non-empty set.  */
  if (max < 0) {
    /* All pipes have closed.  Child has terminated.  */
    return 1;
  }

  /* Run select to block until data are available.  Repeat call
     until it is not interrupted.  */
  while (((numReady = select(max + 1, &cp->PipeSet, 0, 0, timeout)) < 0) &&
         (errno == EINTR))
    ;

  /* Check result of select.  */
  if (numReady == 0) {
    /* Select's timeout expired.  */
    wd->Expired = 1;
    return 1;
  } else if (numReady < 0) {
    /* Select returned an error.  Leave the error description in the
       pipe buffer.  */
    strncpy(cp->ErrorMessage, strerror(errno), KWSYSPE_PIPE_BUFFER_SIZE);

    /* Kill the children now.  */
    kwsysProcess_Kill(cp);
    cp->Killed = 0;
    cp->SelectError = 1;
  }

  return 0;
#else
  /* Poll pipes for data since we do not have select.  */
  for (i = 0; i < KWSYSPE_PIPE_COUNT; ++i) {
    if (cp->PipeReadEnds[i] >= 0) {
      const int fd = cp->PipeReadEnds[i];
      int n = read(fd, cp->PipeBuffer, KWSYSPE_PIPE_BUFFER_SIZE);
      if (n > 0) {
        /* We have data on this pipe.  */
        if (i == KWSYSPE_PIPE_SIGNAL) {
          /* A child process has terminated.  */
          kwsysProcessDestroy(cp);
        } else if (data && length) {
          /* Report this data.  */
          *data = cp->PipeBuffer;
          *length = n;
          switch (i) {
            case KWSYSPE_PIPE_STDOUT:
              wd->PipeId = kwsysProcess_Pipe_STDOUT;
              break;
            case KWSYSPE_PIPE_STDERR:
              wd->PipeId = kwsysProcess_Pipe_STDERR;
              break;
          };
        }
        return 1;
      } else if (n == 0) /* EOF */
      {
/* We are done reading from this pipe.  */
#if defined(__VMS)
        if (!cp->CommandsLeft)
#endif
        {
          kwsysProcessCleanupDescriptor(&cp->PipeReadEnds[i]);
          --cp->PipesLeft;
        }
      } else if (n < 0) /* error */
      {
#if defined(__VMS)
        if (!cp->CommandsLeft) {
          kwsysProcessCleanupDescriptor(&cp->PipeReadEnds[i]);
          --cp->PipesLeft;
        } else
#endif
          if ((errno != EINTR) && (errno != EAGAIN)) {
          strncpy(cp->ErrorMessage, strerror(errno), KWSYSPE_PIPE_BUFFER_SIZE);
          /* Kill the children now.  */
          kwsysProcess_Kill(cp);
          cp->Killed = 0;
          cp->SelectError = 1;
          return 1;
        }
      }
    }
  }

  /* If we have data, break early.  */
  if (wd->PipeId) {
    return 1;
  }

  if (kwsysProcessGetTimeoutLeft(
        &wd->TimeoutTime, wd->User ? wd->UserTimeout : 0, &timeoutLength, 1)) {
    /* Timeout has already expired.  */
    wd->Expired = 1;
    return 1;
  }

  /* Sleep a little, try again. */
  {
    unsigned int msec =
      ((timeoutLength.tv_sec * 1000) + (timeoutLength.tv_usec / 1000));
    if (msec > 100000) {
      msec = 100000; /* do not sleep more than 100 milliseconds at a time */
    }
    kwsysProcess_usleep(msec);
  }
  return 0;
#endif
}

int kwsysProcess_WaitForExit(kwsysProcess* cp, double* userTimeout)
{
  int prPipe = 0;

  /* Make sure we are executing a process.  */
  if (!cp || cp->State != kwsysProcess_State_Executing) {
    return 1;
  }

  /* Wait for all the pipes to close.  Ignore all data.  */
  while ((prPipe = kwsysProcess_WaitForData(cp, 0, 0, userTimeout)) > 0) {
    if (prPipe == kwsysProcess_Pipe_Timeout) {
      return 0;
    }
  }

  /* Check if there was an error in one of the waitpid calls.  */
  if (cp->State == kwsysProcess_State_Error) {
    /* The error message is already in its buffer.  Tell
       kwsysProcessCleanup to not create it.  */
    kwsysProcessCleanup(cp, 0);
    return 1;
  }

  /* Check whether the child reported an error invoking the process.  */
  if (cp->SelectError) {
    /* The error message is already in its buffer.  Tell
       kwsysProcessCleanup to not create it.  */
    kwsysProcessCleanup(cp, 0);
    cp->State = kwsysProcess_State_Error;
    return 1;
  }
  /* Determine the outcome.  */
  if (cp->Killed) {
    /* We killed the child.  */
    cp->State = kwsysProcess_State_Killed;
  } else if (cp->TimeoutExpired) {
    /* The timeout expired.  */
    cp->State = kwsysProcess_State_Expired;
  } else {
    /* The children exited.  Report the outcome of the child processes.  */
    for (prPipe = 0; prPipe < cp->NumberOfCommands; ++prPipe) {
      cp->ProcessResults[prPipe].ExitCode = cp->CommandExitCodes[prPipe];
      if (WIFEXITED(cp->ProcessResults[prPipe].ExitCode)) {
        /* The child exited normally.  */
        cp->ProcessResults[prPipe].State = kwsysProcess_StateByIndex_Exited;
        cp->ProcessResults[prPipe].ExitException = kwsysProcess_Exception_None;
        cp->ProcessResults[prPipe].ExitValue =
          (int)WEXITSTATUS(cp->ProcessResults[prPipe].ExitCode);
      } else if (WIFSIGNALED(cp->ProcessResults[prPipe].ExitCode)) {
        /* The child received an unhandled signal.  */
        cp->ProcessResults[prPipe].State = kwsysProcess_State_Exception;
        kwsysProcessSetExitExceptionByIndex(
          cp, (int)WTERMSIG(cp->ProcessResults[prPipe].ExitCode), prPipe);
      } else {
        /* Error getting the child return code.  */
        strcpy(cp->ProcessResults[prPipe].ExitExceptionString,
               "Error getting child return code.");
        cp->ProcessResults[prPipe].State = kwsysProcess_StateByIndex_Error;
      }
    }
    /* support legacy state status value */
    cp->State = cp->ProcessResults[cp->NumberOfCommands - 1].State;
  }
  /* Normal cleanup.  */
  kwsysProcessCleanup(cp, 0);
  return 1;
}

void kwsysProcess_Interrupt(kwsysProcess* cp)
{
  int i;
  /* Make sure we are executing a process.  */
  if (!cp || cp->State != kwsysProcess_State_Executing || cp->TimeoutExpired ||
      cp->Killed) {
    return;
  }

  /* Interrupt the children.  */
  if (cp->CreateProcessGroup) {
    if (cp->ForkPIDs) {
      for (i = 0; i < cp->NumberOfCommands; ++i) {
        /* Make sure the PID is still valid. */
        if (cp->ForkPIDs[i]) {
          /* The user created a process group for this process.  The group ID
             is the process ID for the original process in the group.  */
          kill(-cp->ForkPIDs[i], SIGINT);
        }
      }
    }
  } else {
    /* No process group was created.  Kill our own process group.
       NOTE:  While one could argue that we could call kill(cp->ForkPIDs[i],
       SIGINT) as a way to still interrupt the process even though it's not in
       a special group, this is not an option on Windows.  Therefore, we kill
       the current process group for consistency with Windows.  */
    kill(0, SIGINT);
  }
}

void kwsysProcess_Kill(kwsysProcess* cp)
{
  int i;

  /* Make sure we are executing a process.  */
  if (!cp || cp->State != kwsysProcess_State_Executing) {
    return;
  }

  /* First close the child exit report pipe write end to avoid causing a
     SIGPIPE when the child terminates and our signal handler tries to
     report it after we have already closed the read end.  */
  kwsysProcessCleanupDescriptor(&cp->SignalPipe);

#if !defined(__APPLE__)
  /* Close all the pipe read ends.  Do this before killing the
     children because Cygwin has problems killing processes that are
     blocking to wait for writing to their output pipes.  */
  kwsysProcessClosePipes(cp);
#endif

  /* Kill the children.  */
  cp->Killed = 1;
  for (i = 0; i < cp->NumberOfCommands; ++i) {
    int status;
    if (cp->ForkPIDs[i]) {
      /* Kill the child.  */
      kwsysProcessKill(cp->ForkPIDs[i]);

      /* Reap the child.  Keep trying until the call is not
         interrupted.  */
      while ((waitpid(cp->ForkPIDs[i], &status, 0) < 0) && (errno == EINTR))
        ;
    }
  }

#if defined(__APPLE__)
  /* Close all the pipe read ends.  Do this after killing the
     children because OS X has problems closing pipe read ends whose
     pipes are full and still have an open write end.  */
  kwsysProcessClosePipes(cp);
#endif

  cp->CommandsLeft = 0;
}

/* Call the free() function with a pointer to volatile without causing
   compiler warnings.  */
static void kwsysProcessVolatileFree(volatile void* p)
{
/* clang has made it impossible to free memory that points to volatile
   without first using special pragmas to disable a warning...  */
#if defined(__clang__) && !defined(__INTEL_COMPILER)
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wcast-qual"
#endif
  free((void*)p); /* The cast will silence most compilers, but not clang.  */
#if defined(__clang__) && !defined(__INTEL_COMPILER)
#pragma clang diagnostic pop
#endif
}

/* Initialize a process control structure for kwsysProcess_Execute.  */
static int kwsysProcessInitialize(kwsysProcess* cp)
{
  int i;
  volatile pid_t* oldForkPIDs;
  for (i = 0; i < KWSYSPE_PIPE_COUNT; ++i) {
    cp->PipeReadEnds[i] = -1;
  }
  for (i = 0; i < 3; ++i) {
    cp->PipeChildStd[i] = -1;
  }
  cp->SignalPipe = -1;
  cp->SelectError = 0;
  cp->StartTime.tv_sec = -1;
  cp->StartTime.tv_usec = -1;
  cp->TimeoutTime.tv_sec = -1;
  cp->TimeoutTime.tv_usec = -1;
  cp->TimeoutExpired = 0;
  cp->PipesLeft = 0;
  cp->CommandsLeft = 0;
#if KWSYSPE_USE_SELECT
  FD_ZERO(&cp->PipeSet);
#endif
  cp->State = kwsysProcess_State_Starting;
  cp->Killed = 0;
  cp->ErrorMessage[0] = 0;

  oldForkPIDs = cp->ForkPIDs;
  cp->ForkPIDs = (volatile pid_t*)malloc(sizeof(volatile pid_t) *
                                         (size_t)(cp->NumberOfCommands));
  if (oldForkPIDs) {
    kwsysProcessVolatileFree(oldForkPIDs);
  }
  if (!cp->ForkPIDs) {
    return 0;
  }
  for (i = 0; i < cp->NumberOfCommands; ++i) {
    cp->ForkPIDs[i] = 0; /* can't use memset due to volatile */
  }

  if (cp->CommandExitCodes) {
    free(cp->CommandExitCodes);
  }
  cp->CommandExitCodes =
    (int*)malloc(sizeof(int) * (size_t)(cp->NumberOfCommands));
  if (!cp->CommandExitCodes) {
    return 0;
  }
  memset(cp->CommandExitCodes, 0,
         sizeof(int) * (size_t)(cp->NumberOfCommands));

  /* Allocate process result information for each process.  */
  free(cp->ProcessResults);
  cp->ProcessResults = (kwsysProcessResults*)malloc(
    sizeof(kwsysProcessResults) * (size_t)(cp->NumberOfCommands));
  if (!cp->ProcessResults) {
    return 0;
  }
  memset(cp->ProcessResults, 0,
         sizeof(kwsysProcessResults) * (size_t)(cp->NumberOfCommands));
  for (i = 0; i < cp->NumberOfCommands; i++) {
    cp->ProcessResults[i].ExitException = kwsysProcess_Exception_None;
    cp->ProcessResults[i].State = kwsysProcess_StateByIndex_Starting;
    cp->ProcessResults[i].ExitCode = 1;
    cp->ProcessResults[i].ExitValue = 1;
    strcpy(cp->ProcessResults[i].ExitExceptionString, "No exception");
  }

  /* Allocate memory to save the real working directory.  */
  if (cp->WorkingDirectory) {
#if defined(MAXPATHLEN)
    cp->RealWorkingDirectoryLength = MAXPATHLEN;
#elif defined(PATH_MAX)
    cp->RealWorkingDirectoryLength = PATH_MAX;
#else
    cp->RealWorkingDirectoryLength = 4096;
#endif
    cp->RealWorkingDirectory =
      (char*)malloc((size_t)(cp->RealWorkingDirectoryLength));
    if (!cp->RealWorkingDirectory) {
      return 0;
    }
  }

  return 1;
}

/* Free all resources used by the given kwsysProcess instance that were
   allocated by kwsysProcess_Execute.  */
static void kwsysProcessCleanup(kwsysProcess* cp, int error)
{
  int i;

  if (error) {
    /* We are cleaning up due to an error.  Report the error message
       if one has not been provided already.  */
    if (cp->ErrorMessage[0] == 0) {
      strncpy(cp->ErrorMessage, strerror(errno), KWSYSPE_PIPE_BUFFER_SIZE);
    }

    /* Set the error state.  */
    cp->State = kwsysProcess_State_Error;

    /* Kill any children already started.  */
    if (cp->ForkPIDs) {
      int status;
      for (i = 0; i < cp->NumberOfCommands; ++i) {
        if (cp->ForkPIDs[i]) {
          /* Kill the child.  */
          kwsysProcessKill(cp->ForkPIDs[i]);

          /* Reap the child.  Keep trying until the call is not
             interrupted.  */
          while ((waitpid(cp->ForkPIDs[i], &status, 0) < 0) &&
                 (errno == EINTR))
            ;
        }
      }
    }

    /* Restore the working directory.  */
    if (cp->RealWorkingDirectory) {
      while ((chdir(cp->RealWorkingDirectory) < 0) && (errno == EINTR))
        ;
    }
  }

  /* If not creating a detached child, remove this object from the
     global set of process objects that wish to be notified when a
     child exits.  */
  if (!cp->OptionDetach) {
    kwsysProcessesRemove(cp);
  }

  /* Free memory.  */
  if (cp->ForkPIDs) {
    kwsysProcessVolatileFree(cp->ForkPIDs);
    cp->ForkPIDs = 0;
  }
  if (cp->RealWorkingDirectory) {
    free(cp->RealWorkingDirectory);
    cp->RealWorkingDirectory = 0;
  }

  /* Close pipe handles.  */
  for (i = 0; i < KWSYSPE_PIPE_COUNT; ++i) {
    kwsysProcessCleanupDescriptor(&cp->PipeReadEnds[i]);
  }
  for (i = 0; i < 3; ++i) {
    kwsysProcessCleanupDescriptor(&cp->PipeChildStd[i]);
  }
}

/* Close the given file descriptor if it is open.  Reset its value to -1.  */
static void kwsysProcessCleanupDescriptor(int* pfd)
{
  if (pfd && *pfd > 2) {
    /* Keep trying to close until it is not interrupted by a
     * signal.  */
    while ((close(*pfd) < 0) && (errno == EINTR))
      ;
    *pfd = -1;
  }
}

static void kwsysProcessClosePipes(kwsysProcess* cp)
{
  int i;

  /* Close any pipes that are still open.  */
  for (i = 0; i < KWSYSPE_PIPE_COUNT; ++i) {
    if (cp->PipeReadEnds[i] >= 0) {
#if KWSYSPE_USE_SELECT
      /* If the pipe was reported by the last call to select, we must
         read from it.  This is needed to satisfy the suggestions from
         "man select_tut" and is not needed for the polling
         implementation.  Ignore the data.  */
      if (FD_ISSET(cp->PipeReadEnds[i], &cp->PipeSet)) {
        /* We are handling this pipe now.  Remove it from the set.  */
        FD_CLR(cp->PipeReadEnds[i], &cp->PipeSet);

        /* The pipe is ready to read without blocking.  Keep trying to
           read until the operation is not interrupted.  */
        while ((read(cp->PipeReadEnds[i], cp->PipeBuffer,
                     KWSYSPE_PIPE_BUFFER_SIZE) < 0) &&
               (errno == EINTR))
          ;
      }
#endif

      /* We are done reading from this pipe.  */
      kwsysProcessCleanupDescriptor(&cp->PipeReadEnds[i]);
      --cp->PipesLeft;
    }
  }
}

static int kwsysProcessSetNonBlocking(int fd)
{
  int flags = fcntl(fd, F_GETFL);
  if (flags >= 0) {
    flags = fcntl(fd, F_SETFL, flags | O_NONBLOCK);
  }
  return flags >= 0;
}

#if defined(__VMS)
int decc$set_child_standard_streams(int fd1, int fd2, int fd3);
#endif

static int kwsysProcessCreate(kwsysProcess* cp, int prIndex,
                              kwsysProcessCreateInformation* si)
{
  sigset_t mask, old_mask;
  int pgidPipe[2];
  char tmp;
  ssize_t readRes;

  /* Create the error reporting pipe.  */
  if (pipe(si->ErrorPipe) < 0) {
    return 0;
  }

  /* Create a pipe for detecting that the child process has created a process
     group and session.  */
  if (pipe(pgidPipe) < 0) {
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[0]);
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[1]);
    return 0;
  }

  /* Set close-on-exec flag on the pipe's write end.  */
  if (fcntl(si->ErrorPipe[1], F_SETFD, FD_CLOEXEC) < 0 ||
      fcntl(pgidPipe[1], F_SETFD, FD_CLOEXEC) < 0) {
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[0]);
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[1]);
    kwsysProcessCleanupDescriptor(&pgidPipe[0]);
    kwsysProcessCleanupDescriptor(&pgidPipe[1]);
    return 0;
  }

  /* Block SIGINT / SIGTERM while we start.  The purpose is so that our signal
     handler doesn't get called from the child process after the fork and
     before the exec, and subsequently start kill()'ing PIDs from ForkPIDs. */
  sigemptyset(&mask);
  sigaddset(&mask, SIGINT);
  sigaddset(&mask, SIGTERM);
  if (sigprocmask(SIG_BLOCK, &mask, &old_mask) < 0) {
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[0]);
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[1]);
    kwsysProcessCleanupDescriptor(&pgidPipe[0]);
    kwsysProcessCleanupDescriptor(&pgidPipe[1]);
    return 0;
  }

/* Fork off a child process.  */
#if defined(__VMS)
  /* VMS needs vfork and execvp to be in the same function because
     they use setjmp/longjmp to run the child startup code in the
     parent!  TODO: OptionDetach.  Also
     TODO:  CreateProcessGroup.  */
  cp->ForkPIDs[prIndex] = vfork();
#else
  cp->ForkPIDs[prIndex] = kwsysProcessFork(cp, si);
#endif
  if (cp->ForkPIDs[prIndex] < 0) {
    sigprocmask(SIG_SETMASK, &old_mask, 0);
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[0]);
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[1]);
    kwsysProcessCleanupDescriptor(&pgidPipe[0]);
    kwsysProcessCleanupDescriptor(&pgidPipe[1]);
    return 0;
  }

  if (cp->ForkPIDs[prIndex] == 0) {
#if defined(__VMS)
    /* Specify standard pipes for child process.  */
    decc$set_child_standard_streams(si->StdIn, si->StdOut, si->StdErr);
#else
    /* Close the read end of the error reporting / process group
       setup pipe.  */
    close(si->ErrorPipe[0]);
    close(pgidPipe[0]);

    /* Setup the stdin, stdout, and stderr pipes.  */
    if (si->StdIn > 0) {
      dup2(si->StdIn, 0);
    } else if (si->StdIn < 0) {
      close(0);
    }
    if (si->StdOut != 1) {
      dup2(si->StdOut, 1);
    }
    if (si->StdErr != 2) {
      dup2(si->StdErr, 2);
    }

    /* Clear the close-on-exec flag for stdin, stdout, and stderr.
       All other pipe handles will be closed when exec succeeds.  */
    fcntl(0, F_SETFD, 0);
    fcntl(1, F_SETFD, 0);
    fcntl(2, F_SETFD, 0);

    /* Restore all default signal handlers. */
    kwsysProcessRestoreDefaultSignalHandlers();

    /* Now that we have restored default signal handling and created the
       process group, restore mask.  */
    sigprocmask(SIG_SETMASK, &old_mask, 0);

    /* Create new process group.  We use setsid instead of setpgid to avoid
       the child getting hung up on signals like SIGTTOU.  (In the real world,
       this has been observed where "git svn" ends up calling the "resize"
       program which opens /dev/tty.  */
    if (cp->CreateProcessGroup && setsid() < 0) {
      kwsysProcessChildErrorExit(si->ErrorPipe[1]);
    }
#endif

    /* Execute the real process.  If successful, this does not return.  */
    execvp(cp->Commands[prIndex][0], cp->Commands[prIndex]);
    /* TODO: What does VMS do if the child fails to start?  */
    /* TODO: On VMS, how do we put the process in a new group?  */

    /* Failure.  Report error to parent and terminate.  */
    kwsysProcessChildErrorExit(si->ErrorPipe[1]);
  }

#if defined(__VMS)
  /* Restore the standard pipes of this process.  */
  decc$set_child_standard_streams(0, 1, 2);
#endif

  /* We are done with the error reporting pipe and process group setup pipe
     write end.  */
  kwsysProcessCleanupDescriptor(&si->ErrorPipe[1]);
  kwsysProcessCleanupDescriptor(&pgidPipe[1]);

  /* Make sure the child is in the process group before we proceed.  This
     avoids race conditions with calls to the kill function that we make for
     signalling process groups.  */
  while ((readRes = read(pgidPipe[0], &tmp, 1)) > 0)
    ;
  if (readRes < 0) {
    sigprocmask(SIG_SETMASK, &old_mask, 0);
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[0]);
    kwsysProcessCleanupDescriptor(&pgidPipe[0]);
    return 0;
  }
  kwsysProcessCleanupDescriptor(&pgidPipe[0]);

  /* Unmask signals.  */
  if (sigprocmask(SIG_SETMASK, &old_mask, 0) < 0) {
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[0]);
    return 0;
  }

  /* A child has been created.  */
  ++cp->CommandsLeft;

  /* Block until the child's exec call succeeds and closes the error
     pipe or writes data to the pipe to report an error.  */
  {
    kwsysProcess_ssize_t total = 0;
    kwsysProcess_ssize_t n = 1;
    /* Read the entire error message up to the length of our buffer.  */
    while (total < KWSYSPE_PIPE_BUFFER_SIZE && n > 0) {
      /* Keep trying to read until the operation is not interrupted.  */
      while (((n = read(si->ErrorPipe[0], cp->ErrorMessage + total,
                        (size_t)(KWSYSPE_PIPE_BUFFER_SIZE - total))) < 0) &&
             (errno == EINTR))
        ;
      if (n > 0) {
        total += n;
      }
    }

    /* We are done with the error reporting pipe read end.  */
    kwsysProcessCleanupDescriptor(&si->ErrorPipe[0]);

    if (total > 0) {
      /* The child failed to execute the process.  */
      return 0;
    }
  }

  return 1;
}

static void kwsysProcessDestroy(kwsysProcess* cp)
{
  /* A child process has terminated.  Reap it if it is one handled by
     this object.  */
  int i;
  /* Temporarily disable signals that access ForkPIDs.  We don't want them to
     read a reaped PID, and writes to ForkPIDs are not atomic.  */
  sigset_t mask, old_mask;
  sigemptyset(&mask);
  sigaddset(&mask, SIGINT);
  sigaddset(&mask, SIGTERM);
  if (sigprocmask(SIG_BLOCK, &mask, &old_mask) < 0) {
    return;
  }

  for (i = 0; i < cp->NumberOfCommands; ++i) {
    if (cp->ForkPIDs[i]) {
      int result;
      while (((result = waitpid(cp->ForkPIDs[i], &cp->CommandExitCodes[i],
                                WNOHANG)) < 0) &&
             (errno == EINTR))
        ;
      if (result > 0) {
        /* This child has termianted.  */
        cp->ForkPIDs[i] = 0;
        if (--cp->CommandsLeft == 0) {
          /* All children have terminated.  Close the signal pipe
             write end so that no more notifications are sent to this
             object.  */
          kwsysProcessCleanupDescriptor(&cp->SignalPipe);

          /* TODO: Once the children have terminated, switch
             WaitForData to use a non-blocking read to get the
             rest of the data from the pipe.  This is needed when
             grandchildren keep the output pipes open.  */
        }
      } else if (result < 0 && cp->State != kwsysProcess_State_Error) {
        /* Unexpected error.  Report the first time this happens.  */
        strncpy(cp->ErrorMessage, strerror(errno), KWSYSPE_PIPE_BUFFER_SIZE);
        cp->State = kwsysProcess_State_Error;
      }
    }
  }

  /* Re-enable signals.  */
  sigprocmask(SIG_SETMASK, &old_mask, 0);
}

static int kwsysProcessSetupOutputPipeFile(int* p, const char* name)
{
  int fout;
  if (!name) {
    return 1;
  }

  /* Close the existing descriptor.  */
  kwsysProcessCleanupDescriptor(p);

  /* Open a file for the pipe to write.  */
  if ((fout = open(name, O_WRONLY | O_CREAT | O_TRUNC, 0666)) < 0) {
    return 0;
  }

  /* Set close-on-exec flag on the pipe's end.  */
  if (fcntl(fout, F_SETFD, FD_CLOEXEC) < 0) {
    return 0;
  }

  /* Assign the replacement descriptor.  */
  *p = fout;
  return 1;
}

static int kwsysProcessSetupOutputPipeNative(int* p, int des[2])
{
  /* Close the existing descriptor.  */
  kwsysProcessCleanupDescriptor(p);

  /* Set close-on-exec flag on the pipe's ends.  The proper end will
     be dup2-ed into the standard descriptor number after fork but
     before exec.  */
  if ((fcntl(des[0], F_SETFD, FD_CLOEXEC) < 0) ||
      (fcntl(des[1], F_SETFD, FD_CLOEXEC) < 0)) {
    return 0;
  }

  /* Assign the replacement descriptor.  */
  *p = des[1];
  return 1;
}

/* Get the time at which either the process or user timeout will
   expire.  Returns 1 if the user timeout is first, and 0 otherwise.  */
static int kwsysProcessGetTimeoutTime(kwsysProcess* cp, double* userTimeout,
                                      kwsysProcessTime* timeoutTime)
{
  /* The first time this is called, we need to calculate the time at
     which the child will timeout.  */
  if (cp->Timeout > 0 && cp->TimeoutTime.tv_sec < 0) {
    kwsysProcessTime length = kwsysProcessTimeFromDouble(cp->Timeout);
    cp->TimeoutTime = kwsysProcessTimeAdd(cp->StartTime, length);
  }

  /* Start with process timeout.  */
  *timeoutTime = cp->TimeoutTime;

  /* Check if the user timeout is earlier.  */
  if (userTimeout) {
    kwsysProcessTime currentTime = kwsysProcessTimeGetCurrent();
    kwsysProcessTime userTimeoutLength =
      kwsysProcessTimeFromDouble(*userTimeout);
    kwsysProcessTime userTimeoutTime =
      kwsysProcessTimeAdd(currentTime, userTimeoutLength);
    if (timeoutTime->tv_sec < 0 ||
        kwsysProcessTimeLess(userTimeoutTime, *timeoutTime)) {
      *timeoutTime = userTimeoutTime;
      return 1;
    }
  }
  return 0;
}

/* Get the length of time before the given timeout time arrives.
   Returns 1 if the time has already arrived, and 0 otherwise.  */
static int kwsysProcessGetTimeoutLeft(kwsysProcessTime* timeoutTime,
                                      double* userTimeout,
                                      kwsysProcessTimeNative* timeoutLength,
                                      int zeroIsExpired)
{
  if (timeoutTime->tv_sec < 0) {
    /* No timeout time has been requested.  */
    return 0;
  } else {
    /* Calculate the remaining time.  */
    kwsysProcessTime currentTime = kwsysProcessTimeGetCurrent();
    kwsysProcessTime timeLeft =
      kwsysProcessTimeSubtract(*timeoutTime, currentTime);
    if (timeLeft.tv_sec < 0 && userTimeout && *userTimeout <= 0) {
      /* Caller has explicitly requested a zero timeout.  */
      timeLeft.tv_sec = 0;
      timeLeft.tv_usec = 0;
    }

    if (timeLeft.tv_sec < 0 ||
        (timeLeft.tv_sec == 0 && timeLeft.tv_usec == 0 && zeroIsExpired)) {
      /* Timeout has already expired.  */
      return 1;
    } else {
      /* There is some time left.  */
      timeoutLength->tv_sec = timeLeft.tv_sec;
      timeoutLength->tv_usec = timeLeft.tv_usec;
      return 0;
    }
  }
}

static kwsysProcessTime kwsysProcessTimeGetCurrent(void)
{
  kwsysProcessTime current;
  kwsysProcessTimeNative current_native;
  gettimeofday(&current_native, 0);
  current.tv_sec = (long)current_native.tv_sec;
  current.tv_usec = (long)current_native.tv_usec;
  return current;
}

static double kwsysProcessTimeToDouble(kwsysProcessTime t)
{
  return (double)t.tv_sec + (double)(t.tv_usec) * 0.000001;
}

static kwsysProcessTime kwsysProcessTimeFromDouble(double d)
{
  kwsysProcessTime t;
  t.tv_sec = (long)d;
  t.tv_usec = (long)((d - (double)(t.tv_sec)) * 1000000);
  return t;
}

static int kwsysProcessTimeLess(kwsysProcessTime in1, kwsysProcessTime in2)
{
  return ((in1.tv_sec < in2.tv_sec) ||
          ((in1.tv_sec == in2.tv_sec) && (in1.tv_usec < in2.tv_usec)));
}

static kwsysProcessTime kwsysProcessTimeAdd(kwsysProcessTime in1,
                                            kwsysProcessTime in2)
{
  kwsysProcessTime out;
  out.tv_sec = in1.tv_sec + in2.tv_sec;
  out.tv_usec = in1.tv_usec + in2.tv_usec;
  if (out.tv_usec >= 1000000) {
    out.tv_usec -= 1000000;
    out.tv_sec += 1;
  }
  return out;
}

static kwsysProcessTime kwsysProcessTimeSubtract(kwsysProcessTime in1,
                                                 kwsysProcessTime in2)
{
  kwsysProcessTime out;
  out.tv_sec = in1.tv_sec - in2.tv_sec;
  out.tv_usec = in1.tv_usec - in2.tv_usec;
  if (out.tv_usec < 0) {
    out.tv_usec += 1000000;
    out.tv_sec -= 1;
  }
  return out;
}

#define KWSYSPE_CASE(type, str)                                               \
  cp->ProcessResults[idx].ExitException = kwsysProcess_Exception_##type;      \
  strcpy(cp->ProcessResults[idx].ExitExceptionString, str)
static void kwsysProcessSetExitExceptionByIndex(kwsysProcess* cp, int sig,
                                                int idx)
{
  switch (sig) {
#ifdef SIGSEGV
    case SIGSEGV:
      KWSYSPE_CASE(Fault, "Segmentation fault");
      break;
#endif
#ifdef SIGBUS
#if !defined(SIGSEGV) || SIGBUS != SIGSEGV
    case SIGBUS:
      KWSYSPE_CASE(Fault, "Bus error");
      break;
#endif
#endif
#ifdef SIGFPE
    case SIGFPE:
      KWSYSPE_CASE(Numerical, "Floating-point exception");
      break;
#endif
#ifdef SIGILL
    case SIGILL:
      KWSYSPE_CASE(Illegal, "Illegal instruction");
      break;
#endif
#ifdef SIGINT
    case SIGINT:
      KWSYSPE_CASE(Interrupt, "User interrupt");
      break;
#endif
#ifdef SIGABRT
    case SIGABRT:
      KWSYSPE_CASE(Other, "Child aborted");
      break;
#endif
#ifdef SIGKILL
    case SIGKILL:
      KWSYSPE_CASE(Other, "Child killed");
      break;
#endif
#ifdef SIGTERM
    case SIGTERM:
      KWSYSPE_CASE(Other, "Child terminated");
      break;
#endif
#ifdef SIGHUP
    case SIGHUP:
      KWSYSPE_CASE(Other, "SIGHUP");
      break;
#endif
#ifdef SIGQUIT
    case SIGQUIT:
      KWSYSPE_CASE(Other, "SIGQUIT");
      break;
#endif
#ifdef SIGTRAP
    case SIGTRAP:
      KWSYSPE_CASE(Other, "SIGTRAP");
      break;
#endif
#ifdef SIGIOT
#if !defined(SIGABRT) || SIGIOT != SIGABRT
    case SIGIOT:
      KWSYSPE_CASE(Other, "SIGIOT");
      break;
#endif
#endif
#ifdef SIGUSR1
    case SIGUSR1:
      KWSYSPE_CASE(Other, "SIGUSR1");
      break;
#endif
#ifdef SIGUSR2
    case SIGUSR2:
      KWSYSPE_CASE(Other, "SIGUSR2");
      break;
#endif
#ifdef SIGPIPE
    case SIGPIPE:
      KWSYSPE_CASE(Other, "SIGPIPE");
      break;
#endif
#ifdef SIGALRM
    case SIGALRM:
      KWSYSPE_CASE(Other, "SIGALRM");
      break;
#endif
#ifdef SIGSTKFLT
    case SIGSTKFLT:
      KWSYSPE_CASE(Other, "SIGSTKFLT");
      break;
#endif
#ifdef SIGCHLD
    case SIGCHLD:
      KWSYSPE_CASE(Other, "SIGCHLD");
      break;
#elif defined(SIGCLD)
    case SIGCLD:
      KWSYSPE_CASE(Other, "SIGCLD");
      break;
#endif
#ifdef SIGCONT
    case SIGCONT:
      KWSYSPE_CASE(Other, "SIGCONT");
      break;
#endif
#ifdef SIGSTOP
    case SIGSTOP:
      KWSYSPE_CASE(Other, "SIGSTOP");
      break;
#endif
#ifdef SIGTSTP
    case SIGTSTP:
      KWSYSPE_CASE(Other, "SIGTSTP");
      break;
#endif
#ifdef SIGTTIN
    case SIGTTIN:
      KWSYSPE_CASE(Other, "SIGTTIN");
      break;
#endif
#ifdef SIGTTOU
    case SIGTTOU:
      KWSYSPE_CASE(Other, "SIGTTOU");
      break;
#endif
#ifdef SIGURG
    case SIGURG:
      KWSYSPE_CASE(Other, "SIGURG");
      break;
#endif
#ifdef SIGXCPU
    case SIGXCPU:
      KWSYSPE_CASE(Other, "SIGXCPU");
      break;
#endif
#ifdef SIGXFSZ
    case SIGXFSZ:
      KWSYSPE_CASE(Other, "SIGXFSZ");
      break;
#endif
#ifdef SIGVTALRM
    case SIGVTALRM:
      KWSYSPE_CASE(Other, "SIGVTALRM");
      break;
#endif
#ifdef SIGPROF
    case SIGPROF:
      KWSYSPE_CASE(Other, "SIGPROF");
      break;
#endif
#ifdef SIGWINCH
    case SIGWINCH:
      KWSYSPE_CASE(Other, "SIGWINCH");
      break;
#endif
#ifdef SIGPOLL
    case SIGPOLL:
      KWSYSPE_CASE(Other, "SIGPOLL");
      break;
#endif
#ifdef SIGIO
#if !defined(SIGPOLL) || SIGIO != SIGPOLL
    case SIGIO:
      KWSYSPE_CASE(Other, "SIGIO");
      break;
#endif
#endif
#ifdef SIGPWR
    case SIGPWR:
      KWSYSPE_CASE(Other, "SIGPWR");
      break;
#endif
#ifdef SIGSYS
    case SIGSYS:
      KWSYSPE_CASE(Other, "SIGSYS");
      break;
#endif
#ifdef SIGUNUSED
#if !defined(SIGSYS) || SIGUNUSED != SIGSYS
    case SIGUNUSED:
      KWSYSPE_CASE(Other, "SIGUNUSED");
      break;
#endif
#endif
    default:
      cp->ProcessResults[idx].ExitException = kwsysProcess_Exception_Other;
      sprintf(cp->ProcessResults[idx].ExitExceptionString, "Signal %d", sig);
      break;
  }
}
#undef KWSYSPE_CASE

/* When the child process encounters an error before its program is
   invoked, this is called to report the error to the parent and
   exit.  */
static void kwsysProcessChildErrorExit(int errorPipe)
{
  /* Construct the error message.  */
  char buffer[KWSYSPE_PIPE_BUFFER_SIZE];
  kwsysProcess_ssize_t result;
  strncpy(buffer, strerror(errno), KWSYSPE_PIPE_BUFFER_SIZE);

  /* Report the error to the parent through the special pipe.  */
  result = write(errorPipe, buffer, strlen(buffer));
  (void)result;

  /* Terminate without cleanup.  */
  _exit(1);
}

/* Restores all signal handlers to their default values.  */
static void kwsysProcessRestoreDefaultSignalHandlers(void)
{
  struct sigaction act;
  memset(&act, 0, sizeof(struct sigaction));
  act.sa_handler = SIG_DFL;
#ifdef SIGHUP
  sigaction(SIGHUP, &act, 0);
#endif
#ifdef SIGINT
  sigaction(SIGINT, &act, 0);
#endif
#ifdef SIGQUIT
  sigaction(SIGQUIT, &act, 0);
#endif
#ifdef SIGILL
  sigaction(SIGILL, &act, 0);
#endif
#ifdef SIGTRAP
  sigaction(SIGTRAP, &act, 0);
#endif
#ifdef SIGABRT
  sigaction(SIGABRT, &act, 0);
#endif
#ifdef SIGIOT
  sigaction(SIGIOT, &act, 0);
#endif
#ifdef SIGBUS
  sigaction(SIGBUS, &act, 0);
#endif
#ifdef SIGFPE
  sigaction(SIGFPE, &act, 0);
#endif
#ifdef SIGUSR1
  sigaction(SIGUSR1, &act, 0);
#endif
#ifdef SIGSEGV
  sigaction(SIGSEGV, &act, 0);
#endif
#ifdef SIGUSR2
  sigaction(SIGUSR2, &act, 0);
#endif
#ifdef SIGPIPE
  sigaction(SIGPIPE, &act, 0);
#endif
#ifdef SIGALRM
  sigaction(SIGALRM, &act, 0);
#endif
#ifdef SIGTERM
  sigaction(SIGTERM, &act, 0);
#endif
#ifdef SIGSTKFLT
  sigaction(SIGSTKFLT, &act, 0);
#endif
#ifdef SIGCLD
  sigaction(SIGCLD, &act, 0);
#endif
#ifdef SIGCHLD
  sigaction(SIGCHLD, &act, 0);
#endif
#ifdef SIGCONT
  sigaction(SIGCONT, &act, 0);
#endif
#ifdef SIGTSTP
  sigaction(SIGTSTP, &act, 0);
#endif
#ifdef SIGTTIN
  sigaction(SIGTTIN, &act, 0);
#endif
#ifdef SIGTTOU
  sigaction(SIGTTOU, &act, 0);
#endif
#ifdef SIGURG
  sigaction(SIGURG, &act, 0);
#endif
#ifdef SIGXCPU
  sigaction(SIGXCPU, &act, 0);
#endif
#ifdef SIGXFSZ
  sigaction(SIGXFSZ, &act, 0);
#endif
#ifdef SIGVTALRM
  sigaction(SIGVTALRM, &act, 0);
#endif
#ifdef SIGPROF
  sigaction(SIGPROF, &act, 0);
#endif
#ifdef SIGWINCH
  sigaction(SIGWINCH, &act, 0);
#endif
#ifdef SIGPOLL
  sigaction(SIGPOLL, &act, 0);
#endif
#ifdef SIGIO
  sigaction(SIGIO, &act, 0);
#endif
#ifdef SIGPWR
  sigaction(SIGPWR, &act, 0);
#endif
#ifdef SIGSYS
  sigaction(SIGSYS, &act, 0);
#endif
#ifdef SIGUNUSED
  sigaction(SIGUNUSED, &act, 0);
#endif
}

static void kwsysProcessExit(void)
{
  _exit(0);
}

#if !defined(__VMS)
static pid_t kwsysProcessFork(kwsysProcess* cp,
                              kwsysProcessCreateInformation* si)
{
  /* Create a detached process if requested.  */
  if (cp->OptionDetach) {
    /* Create an intermediate process.  */
    pid_t middle_pid = fork();
    if (middle_pid < 0) {
      /* Fork failed.  Return as if we were not detaching.  */
      return middle_pid;
    } else if (middle_pid == 0) {
      /* This is the intermediate process.  Create the real child.  */
      pid_t child_pid = fork();
      if (child_pid == 0) {
        /* This is the real child process.  There is nothing to do here.  */
        return 0;
      } else {
        /* Use the error pipe to report the pid to the real parent.  */
        while ((write(si->ErrorPipe[1], &child_pid, sizeof(child_pid)) < 0) &&
               (errno == EINTR))
          ;

        /* Exit without cleanup.  The parent holds all resources.  */
        kwsysProcessExit();
        return 0; /* Never reached, but avoids SunCC warning.  */
      }
    } else {
      /* This is the original parent process.  The intermediate
         process will use the error pipe to report the pid of the
         detached child.  */
      pid_t child_pid;
      int status;
      while ((read(si->ErrorPipe[0], &child_pid, sizeof(child_pid)) < 0) &&
             (errno == EINTR))
        ;

      /* Wait for the intermediate process to exit and clean it up.  */
      while ((waitpid(middle_pid, &status, 0) < 0) && (errno == EINTR))
        ;
      return child_pid;
    }
  } else {
    /* Not creating a detached process.  Use normal fork.  */
    return fork();
  }
}
#endif

/* We try to obtain process information by invoking the ps command.
   Here we define the command to call on each platform and the
   corresponding parsing format string.  The parsing format should
   have two integers to store: the pid and then the ppid.  */
#if defined(__linux__) || defined(__APPLE__) || defined(__FreeBSD__) ||       \
  defined(__OpenBSD__) || defined(__GLIBC__) || defined(__GNU__)
#define KWSYSPE_PS_COMMAND "ps axo pid,ppid"
#define KWSYSPE_PS_FORMAT "%d %d\n"
#elif defined(__sun) && (defined(__SVR4) || defined(__svr4__)) /* Solaris */
#define KWSYSPE_PS_COMMAND "ps -e -o pid,ppid"
#define KWSYSPE_PS_FORMAT "%d %d\n"
#elif defined(__hpux) || defined(__sun__) || defined(__sgi) ||                \
  defined(_AIX) || defined(__sparc)
#define KWSYSPE_PS_COMMAND "ps -ef"
#define KWSYSPE_PS_FORMAT "%*s %d %d %*[^\n]\n"
#elif defined(__QNX__)
#define KWSYSPE_PS_COMMAND "ps -Af"
#define KWSYSPE_PS_FORMAT "%*d %d %d %*[^\n]\n"
#elif defined(__CYGWIN__)
#define KWSYSPE_PS_COMMAND "ps aux"
#define KWSYSPE_PS_FORMAT "%d %d %*[^\n]\n"
#endif

static void kwsysProcessKill(pid_t process_id)
{
#if defined(__linux__) || defined(__CYGWIN__)
  DIR* procdir;
#endif

  /* Suspend the process to be sure it will not create more children.  */
  kill(process_id, SIGSTOP);

#if defined(__CYGWIN__)
  /* Some Cygwin versions seem to need help here.  Give up our time slice
     so that the child can process SIGSTOP before we send SIGKILL.  */
  usleep(1);
#endif

/* Kill all children if we can find them.  */
#if defined(__linux__) || defined(__CYGWIN__)
  /* First try using the /proc filesystem.  */
  if ((procdir = opendir("/proc")) != NULL) {
#if defined(MAXPATHLEN)
    char fname[MAXPATHLEN];
#elif defined(PATH_MAX)
    char fname[PATH_MAX];
#else
    char fname[4096];
#endif
    char buffer[KWSYSPE_PIPE_BUFFER_SIZE + 1];
    struct dirent* d;

    /* Each process has a directory in /proc whose name is the pid.
       Within this directory is a file called stat that has the
       following format:

         pid (command line) status ppid ...

       We want to get the ppid for all processes.  Those that have
       process_id as their parent should be recursively killed.  */
    for (d = readdir(procdir); d; d = readdir(procdir)) {
      int pid;
      if (sscanf(d->d_name, "%d", &pid) == 1 && pid != 0) {
        struct stat finfo;
        sprintf(fname, "/proc/%d/stat", pid);
        if (stat(fname, &finfo) == 0) {
          FILE* f = fopen(fname, "r");
          if (f) {
            size_t nread = fread(buffer, 1, KWSYSPE_PIPE_BUFFER_SIZE, f);
            fclose(f);
            buffer[nread] = '\0';
            if (nread > 0) {
              const char* rparen = strrchr(buffer, ')');
              int ppid;
              if (rparen && (sscanf(rparen + 1, "%*s %d", &ppid) == 1)) {
                if (ppid == process_id) {
                  /* Recursively kill this child and its children.  */
                  kwsysProcessKill(pid);
                }
              }
            }
          }
        }
      }
    }
    closedir(procdir);
  } else
#endif
  {
#if defined(KWSYSPE_PS_COMMAND)
    /* Try running "ps" to get the process information.  */
    FILE* ps = popen(KWSYSPE_PS_COMMAND, "r");

    /* Make sure the process started and provided a valid header.  */
    if (ps && fscanf(ps, "%*[^\n]\n") != EOF) {
      /* Look for processes whose parent is the process being killed.  */
      int pid, ppid;
      while (fscanf(ps, KWSYSPE_PS_FORMAT, &pid, &ppid) == 2) {
        if (ppid == process_id) {
          /* Recursively kill this child and its children.  */
          kwsysProcessKill(pid);
        }
      }
    }

    /* We are done with the ps process.  */
    if (ps) {
      pclose(ps);
    }
#endif
  }

  /* Kill the process.  */
  kill(process_id, SIGKILL);

#if defined(__APPLE__)
  /* On OS X 10.3 the above SIGSTOP occasionally prevents the SIGKILL
     from working.  Just in case, we resume the child and kill it
     again.  There is a small race condition in this obscure case.  If
     the child manages to fork again between these two signals, we
     will not catch its children.  */
  kill(process_id, SIGCONT);
  kill(process_id, SIGKILL);
#endif
}

#if defined(__VMS)
int decc$feature_get_index(const char* name);
int decc$feature_set_value(int index, int mode, int value);
static int kwsysProcessSetVMSFeature(const char* name, int value)
{
  int i;
  errno = 0;
  i = decc$feature_get_index(name);
  return i >= 0 && (decc$feature_set_value(i, 1, value) >= 0 || errno == 0);
}
#endif

/* Global set of executing processes for use by the signal handler.
   This global instance will be zero-initialized by the compiler.  */
typedef struct kwsysProcessInstances_s
{
  int Count;
  int Size;
  kwsysProcess** Processes;
} kwsysProcessInstances;
static kwsysProcessInstances kwsysProcesses;

/* The old SIGCHLD / SIGINT / SIGTERM handlers.  */
static struct sigaction kwsysProcessesOldSigChldAction;
static struct sigaction kwsysProcessesOldSigIntAction;
static struct sigaction kwsysProcessesOldSigTermAction;

static void kwsysProcessesUpdate(kwsysProcessInstances* newProcesses)
{
  /* Block signals while we update the set of pipes to check.
     TODO: sigprocmask is undefined for threaded apps.  See
     pthread_sigmask.  */
  sigset_t newset;
  sigset_t oldset;
  sigemptyset(&newset);
  sigaddset(&newset, SIGCHLD);
  sigaddset(&newset, SIGINT);
  sigaddset(&newset, SIGTERM);
  sigprocmask(SIG_BLOCK, &newset, &oldset);

  /* Store the new set in that seen by the signal handler.  */
  kwsysProcesses = *newProcesses;

  /* Restore the signal mask to the previous setting.  */
  sigprocmask(SIG_SETMASK, &oldset, 0);
}

static int kwsysProcessesAdd(kwsysProcess* cp)
{
  /* Create a pipe through which the signal handler can notify the
     given process object that a child has exited.  */
  {
    /* Create the pipe.  */
    int p[2];
    if (pipe(p KWSYSPE_VMS_NONBLOCK) < 0) {
      return 0;
    }

    /* Store the pipes now to be sure they are cleaned up later.  */
    cp->PipeReadEnds[KWSYSPE_PIPE_SIGNAL] = p[0];
    cp->SignalPipe = p[1];

    /* Switch the pipe to non-blocking mode so that reading a byte can
       be an atomic test-and-set.  */
    if (!kwsysProcessSetNonBlocking(p[0]) ||
        !kwsysProcessSetNonBlocking(p[1])) {
      return 0;
    }

    /* The children do not need this pipe.  Set close-on-exec flag on
       the pipe's ends.  */
    if ((fcntl(p[0], F_SETFD, FD_CLOEXEC) < 0) ||
        (fcntl(p[1], F_SETFD, FD_CLOEXEC) < 0)) {
      return 0;
    }
  }

  /* Attempt to add the given signal pipe to the signal handler set.  */
  {

    /* Make sure there is enough space for the new signal pipe.  */
    kwsysProcessInstances oldProcesses = kwsysProcesses;
    kwsysProcessInstances newProcesses = oldProcesses;
    if (oldProcesses.Count == oldProcesses.Size) {
      /* Start with enough space for a small number of process instances
         and double the size each time more is needed.  */
      newProcesses.Size = oldProcesses.Size ? oldProcesses.Size * 2 : 4;

      /* Try allocating the new block of memory.  */
      if ((newProcesses.Processes = ((kwsysProcess**)malloc(
             (size_t)(newProcesses.Size) * sizeof(kwsysProcess*))))) {
        /* Copy the old pipe set to the new memory.  */
        if (oldProcesses.Count > 0) {
          memcpy(newProcesses.Processes, oldProcesses.Processes,
                 ((size_t)(oldProcesses.Count) * sizeof(kwsysProcess*)));
        }
      } else {
        /* Failed to allocate memory for the new signal pipe set.  */
        return 0;
      }
    }

    /* Append the new signal pipe to the set.  */
    newProcesses.Processes[newProcesses.Count++] = cp;

    /* Store the new set in that seen by the signal handler.  */
    kwsysProcessesUpdate(&newProcesses);

    /* Free the original pipes if new ones were allocated.  */
    if (newProcesses.Processes != oldProcesses.Processes) {
      free(oldProcesses.Processes);
    }

    /* If this is the first process, enable the signal handler.  */
    if (newProcesses.Count == 1) {
      /* Install our handler for SIGCHLD.  Repeat call until it is not
         interrupted.  */
      struct sigaction newSigAction;
      memset(&newSigAction, 0, sizeof(struct sigaction));
#if KWSYSPE_USE_SIGINFO
      newSigAction.sa_sigaction = kwsysProcessesSignalHandler;
      newSigAction.sa_flags = SA_NOCLDSTOP | SA_SIGINFO;
#ifdef SA_RESTART
      newSigAction.sa_flags |= SA_RESTART;
#endif
#else
      newSigAction.sa_handler = kwsysProcessesSignalHandler;
      newSigAction.sa_flags = SA_NOCLDSTOP;
#endif
      sigemptyset(&newSigAction.sa_mask);
      while ((sigaction(SIGCHLD, &newSigAction,
                        &kwsysProcessesOldSigChldAction) < 0) &&
             (errno == EINTR))
        ;

      /* Install our handler for SIGINT / SIGTERM.  Repeat call until
         it is not interrupted.  */
      sigemptyset(&newSigAction.sa_mask);
      sigaddset(&newSigAction.sa_mask, SIGTERM);
      while ((sigaction(SIGINT, &newSigAction,
                        &kwsysProcessesOldSigIntAction) < 0) &&
             (errno == EINTR))
        ;

      sigemptyset(&newSigAction.sa_mask);
      sigaddset(&newSigAction.sa_mask, SIGINT);
      while ((sigaction(SIGTERM, &newSigAction,
                        &kwsysProcessesOldSigIntAction) < 0) &&
             (errno == EINTR))
        ;
    }
  }

  return 1;
}

static void kwsysProcessesRemove(kwsysProcess* cp)
{
  /* Attempt to remove the given signal pipe from the signal handler set.  */
  {
    /* Find the given process in the set.  */
    kwsysProcessInstances newProcesses = kwsysProcesses;
    int i;
    for (i = 0; i < newProcesses.Count; ++i) {
      if (newProcesses.Processes[i] == cp) {
        break;
      }
    }
    if (i < newProcesses.Count) {
      /* Remove the process from the set.  */
      --newProcesses.Count;
      for (; i < newProcesses.Count; ++i) {
        newProcesses.Processes[i] = newProcesses.Processes[i + 1];
      }

      /* If this was the last process, disable the signal handler.  */
      if (newProcesses.Count == 0) {
        /* Restore the signal handlers.  Repeat call until it is not
           interrupted.  */
        while ((sigaction(SIGCHLD, &kwsysProcessesOldSigChldAction, 0) < 0) &&
               (errno == EINTR))
          ;
        while ((sigaction(SIGINT, &kwsysProcessesOldSigIntAction, 0) < 0) &&
               (errno == EINTR))
          ;
        while ((sigaction(SIGTERM, &kwsysProcessesOldSigTermAction, 0) < 0) &&
               (errno == EINTR))
          ;

        /* Free the table of process pointers since it is now empty.
           This is safe because the signal handler has been removed.  */
        newProcesses.Size = 0;
        free(newProcesses.Processes);
        newProcesses.Processes = 0;
      }

      /* Store the new set in that seen by the signal handler.  */
      kwsysProcessesUpdate(&newProcesses);
    }
  }

  /* Close the pipe through which the signal handler may have notified
     the given process object that a child has exited.  */
  kwsysProcessCleanupDescriptor(&cp->SignalPipe);
}

static void kwsysProcessesSignalHandler(int signum
#if KWSYSPE_USE_SIGINFO
                                        ,
                                        siginfo_t* info, void* ucontext
#endif
                                        )
{
  int i, j, procStatus, old_errno = errno;
#if KWSYSPE_USE_SIGINFO
  (void)info;
  (void)ucontext;
#endif

  /* Signal all process objects that a child has terminated.  */
  switch (signum) {
    case SIGCHLD:
      for (i = 0; i < kwsysProcesses.Count; ++i) {
        /* Set the pipe in a signalled state.  */
        char buf = 1;
        kwsysProcess* cp = kwsysProcesses.Processes[i];
        kwsysProcess_ssize_t pipeStatus =
          read(cp->PipeReadEnds[KWSYSPE_PIPE_SIGNAL], &buf, 1);
        (void)pipeStatus;
        pipeStatus = write(cp->SignalPipe, &buf, 1);
        (void)pipeStatus;
      }
      break;
    case SIGINT:
    case SIGTERM:
      /* Signal child processes that are running in new process groups.  */
      for (i = 0; i < kwsysProcesses.Count; ++i) {
        kwsysProcess* cp = kwsysProcesses.Processes[i];
        /* Check Killed to avoid data race condition when killing.
           Check State to avoid data race condition in kwsysProcessCleanup
           when there is an error (it leaves a reaped PID).  */
        if (cp->CreateProcessGroup && !cp->Killed &&
            cp->State != kwsysProcess_State_Error && cp->ForkPIDs) {
          for (j = 0; j < cp->NumberOfCommands; ++j) {
            /* Make sure the PID is still valid. */
            if (cp->ForkPIDs[j]) {
              /* The user created a process group for this process.  The group
                 ID
                 is the process ID for the original process in the group.  */
              kill(-cp->ForkPIDs[j], SIGINT);
            }
          }
        }
      }

      /* Wait for all processes to terminate.  */
      while (wait(&procStatus) >= 0 || errno != ECHILD) {
      }

      /* Terminate the process, which is now in an inconsistent state
         because we reaped all the PIDs that it may have been reaping
         or may have reaped in the future.  Reraise the signal so that
         the proper exit code is returned.  */
      {
        /* Install default signal handler.  */
        struct sigaction defSigAction;
        sigset_t unblockSet;
        memset(&defSigAction, 0, sizeof(defSigAction));
        defSigAction.sa_handler = SIG_DFL;
        sigemptyset(&defSigAction.sa_mask);
        while ((sigaction(signum, &defSigAction, 0) < 0) && (errno == EINTR))
          ;
        /* Unmask the signal.  */
        sigemptyset(&unblockSet);
        sigaddset(&unblockSet, signum);
        sigprocmask(SIG_UNBLOCK, &unblockSet, 0);
        /* Raise the signal again.  */
        raise(signum);
        /* We shouldn't get here... but if we do... */
        _exit(1);
      }
      /* break omitted to silence unreachable code clang compiler warning.  */
  }

#if !KWSYSPE_USE_SIGINFO
  /* Re-Install our handler.  Repeat call until it is not interrupted.  */
  {
    struct sigaction newSigAction;
    struct sigaction& oldSigAction;
    memset(&newSigAction, 0, sizeof(struct sigaction));
    newSigChldAction.sa_handler = kwsysProcessesSignalHandler;
    newSigChldAction.sa_flags = SA_NOCLDSTOP;
    sigemptyset(&newSigAction.sa_mask);
    switch (signum) {
      case SIGCHLD:
        oldSigAction = &kwsysProcessesOldSigChldAction;
        break;
      case SIGINT:
        sigaddset(&newSigAction.sa_mask, SIGTERM);
        oldSigAction = &kwsysProcessesOldSigIntAction;
        break;
      case SIGTERM:
        sigaddset(&newSigAction.sa_mask, SIGINT);
        oldSigAction = &kwsysProcessesOldSigTermAction;
        break;
      default:
        return 0;
    }
    while ((sigaction(signum, &newSigAction, oldSigAction) < 0) &&
           (errno == EINTR))
      ;
  }
#endif

  errno = old_errno;
}

void kwsysProcess_ResetStartTime(kwsysProcess* cp)
{
  if (!cp) {
    return;
  }
  /* Reset start time. */
  cp->StartTime = kwsysProcessTimeGetCurrent();
}
