/* Utilities to execute a program in a subprocess (possibly linked by pipes
   with other subprocesses), and wait for it.
   Copyright (C) 2004-2021 Free Software Foundation, Inc.

This file is part of the libiberty library.
Libiberty is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 of the License, or (at your option) any later version.

Libiberty is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
Library General Public License for more details.

You should have received a copy of the GNU Library General Public
License along with libiberty; see the file COPYING.LIB.  If not,
write to the Free Software Foundation, Inc., 51 Franklin Street - Fifth Floor,
Boston, MA 02110-1301, USA.  */

/* pexecute is an old routine.  This implementation uses the newer
   pex_init/pex_run/pex_get_status/pex_free routines.  Don't use
   pexecute in new code.  Use the newer routines instead.  */

#include "config.h"
#include "libiberty.h"

#ifdef HAVE_STDLIB_H
#include <stdlib.h>
#endif

/* We only permit a single pexecute chain to execute at a time.  This
   was always true anyhow, though it wasn't documented.  */

static struct pex_obj *pex;
static int idx;

int
pexecute (const char *program, char * const *argv, const char *pname,
	  const char *temp_base, char **errmsg_fmt, char **errmsg_arg,
	  int flags)
{
  const char *errmsg;
  int err;

  if ((flags & PEXECUTE_FIRST) != 0)
    {
      if (pex != NULL)
	{
	  *errmsg_fmt = (char *) "pexecute already in progress";
	  *errmsg_arg = NULL;
	  return -1;
	}
      pex = pex_init (PEX_USE_PIPES, pname, temp_base);
      idx = 0;
    }
  else
    {
      if (pex == NULL)
	{
	  *errmsg_fmt = (char *) "pexecute not in progress";
	  *errmsg_arg = NULL;
	  return -1;
	}
    }

  errmsg = pex_run (pex,
		    (((flags & PEXECUTE_LAST) != 0 ? PEX_LAST : 0)
		     | ((flags & PEXECUTE_SEARCH) != 0 ? PEX_SEARCH : 0)),
		    program, argv, NULL, NULL, &err);
  if (errmsg != NULL)
    {
      *errmsg_fmt = (char *) errmsg;
      *errmsg_arg = NULL;
      return -1;
    }

  /* Instead of a PID, we just return a one-based index into the
     status values.  We avoid zero just because the old pexecute would
     never return it.  */
  return ++idx;
}

int
pwait (int pid, int *status, int flags ATTRIBUTE_UNUSED)
{
  /* The PID returned by pexecute is one-based.  */
  --pid;

  if (pex == NULL || pid < 0 || pid >= idx)
    return -1;

  if (pid == 0 && idx == 1)
    {
      if (!pex_get_status (pex, 1, status))
	return -1;
    }
  else
    {
      int *vector;

      vector = XNEWVEC (int, idx);
      if (!pex_get_status (pex, idx, vector))
	{
	  free (vector);
	  return -1;
	}
      *status = vector[pid];
      free (vector);
    }

  /* Assume that we are done after the caller has retrieved the last
     exit status.  The original implementation did not require that
     the exit statuses be retrieved in order, but this implementation
     does.  */
  if (pid + 1 == idx)
    {
      pex_free (pex);
      pex = NULL;
      idx = 0;
    }

  return pid + 1;
}
