Exemple #1
0
int execute (const char *name,
             const char **argv,
             const char *input,
             const char *output,
             const char **errmsg,
             int *waitstatus)
{
    int errnum;

    if(input != NULL || output != NULL) {
        *errmsg = "execute input/output NYI";
        return -1;
    }

    struct pex_obj *pex = pex_init(0, name, NULL);
    if (pex == NULL) {
        *errmsg = "pex_init failed";
        return -1;
    }

    *errmsg = pex_run(pex, PEX_LAST, name, (char * const *)argv, output, NULL, &errnum);
    if (*errmsg != NULL || !pex_get_status(pex, 1, waitstatus)) {
        if (&errmsg == NULL) {
            *errmsg = "can't get program status";
        }
        pex_free(pex);
        return -1;
    }

    pex_free(pex);
    return 0;
}
Exemple #2
0
int
collect_wait (const char *prog, struct pex_obj *pex)
{
  int status;

  if (!pex_get_status (pex, 1, &status))
    fatal_error (input_location, "can't get program status: %m");
  pex_free (pex);

  if (response_file && !save_temps)
    {
      unlink (response_file);
      response_file = NULL;
    }

  if (status)
    {
      if (WIFSIGNALED (status))
	{
	  int sig = WTERMSIG (status);
	  fatal_error (input_location, "%s terminated with signal %d [%s]%s",
		       prog, sig, strsignal (sig),
		       WCOREDUMP (status) ? ", core dumped" : "");
	}

      if (WIFEXITED (status))
	return WEXITSTATUS (status);
    }
  return 0;
}
/* Closes CYGPATH_PEX and frees all associated
   resoures.  */
static void
cygpath_close (void)
{
  /* Free resources.  */
  if (cygpath_out)
    {
      fclose (cygpath_out);
      cygpath_out = NULL;
    }
  if (cygpath_in)
    {
      fclose (cygpath_in);
      cygpath_in = NULL;
    }
  if (cygpath_pex)
    {
      pex_free (cygpath_pex);
      cygpath_pex = NULL;
    }
  if (cygpath_log)
    {
      cygpath_log_msg ("end");
      cygpath_log = NULL;
    }
}
Exemple #4
0
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;
}
static void
exec_lto_wrapper (char *argv[])
{
  int t, i;
  int status;
  char *at_args;
  FILE *args;
  FILE *wrapper_output;
  char *new_argv[3];
  struct pex_obj *pex;
  const char *errmsg;

  /* Write argv to a file to avoid a command line that is too long. */
  arguments_file_name = make_temp_file ("");
  check (arguments_file_name, LDPL_FATAL,
         "Failed to generate a temorary file name");

  args = fopen (arguments_file_name, "w");
  check (args, LDPL_FATAL, "could not open arguments file");

  t = writeargv (&argv[1], args);
  check (t == 0, LDPL_FATAL, "could not write arguments");
  t = fclose (args);
  check (t == 0, LDPL_FATAL, "could not close arguments file");

  at_args = concat ("@", arguments_file_name, NULL);
  check (at_args, LDPL_FATAL, "could not allocate");

  for (i = 1; argv[i]; i++)
    {
      char *a = argv[i];
      if (a[0] == '-' && a[1] == 'v' && a[2] == '\0')
	{
	  for (i = 0; argv[i]; i++)
	    fprintf (stderr, "%s ", argv[i]);
	  fprintf (stderr, "\n");
	  break;
	}
    }

  new_argv[0] = argv[0];
  new_argv[1] = at_args;
  new_argv[2] = NULL;

  if (debug)
    {
      for (i = 0; new_argv[i]; i++)
	fprintf (stderr, "%s ", new_argv[i]);
      fprintf (stderr, "\n");
    }


  pex = pex_init (PEX_USE_PIPES, "lto-wrapper", NULL);
  check (pex != NULL, LDPL_FATAL, "could not pex_init lto-wrapper");

  errmsg = pex_run (pex, 0, new_argv[0], new_argv, NULL, NULL, &t);
  check (errmsg == NULL, LDPL_FATAL, "could not run lto-wrapper");
  check (t == 0, LDPL_FATAL, "could not run lto-wrapper");

  wrapper_output = pex_read_output (pex, 0);
  check (wrapper_output, LDPL_FATAL, "could not read lto-wrapper output");

  add_output_files (wrapper_output);

  t = pex_get_status (pex, 1, &status);
  check (t == 1, LDPL_FATAL, "could not get lto-wrapper exit status");
  check (WIFEXITED (status) && WEXITSTATUS (status) == 0, LDPL_FATAL,
         "lto-wrapper failed");

  pex_free (pex);

  free (at_args);
}
Exemple #6
0
int
main (int argc, char **argv)
{
  int trace;
  struct pex_obj *test_pex_tmp;
  int test_pex_status;
  FILE *test_pex_file;
  struct pex_obj *pex1;
  char *subargv[10];
  int status;
  FILE *e;
  int statuses[10];

  trace = 0;
  if (argc > 1 && strcmp (argv[1], "-t") == 0)
    {
      trace = 1;
      --argc;
      ++argv;
    }

  if (argc > 1)
    do_cmd (argc, argv);

#define TEST_PEX_INIT(FLAGS, TEMPBASE)					\
  (((test_pex_tmp = pex_init (FLAGS, "test-pexecute", TEMPBASE))	\
    != NULL)								\
   ? test_pex_tmp							\
   : (FATAL_ERROR ("pex_init failed", 0), NULL))

#define TEST_PEX_RUN(PEXOBJ, FLAGS, EXECUTABLE, ARGV, OUTNAME, ERRNAME)	\
  do									\
    {									\
      int err;								\
      const char *pex_run_err;						\
      if (trace)							\
	fprintf (stderr, "Line %d: running %s %s\n",			\
		 __LINE__, EXECUTABLE, ARGV[0]);			\
      pex_run_err = pex_run (PEXOBJ, FLAGS, EXECUTABLE, ARGV, OUTNAME,	\
			     ERRNAME, &err);				\
      if (pex_run_err != NULL)						\
	FATAL_ERROR (pex_run_err, err);					\
    }									\
  while (0)

#define TEST_PEX_GET_STATUS_1(PEXOBJ)					\
  (pex_get_status (PEXOBJ, 1, &test_pex_status)				\
   ? test_pex_status							\
   : (FATAL_ERROR ("pex_get_status failed", errno), 1))

#define TEST_PEX_GET_STATUS(PEXOBJ, COUNT, VECTOR)			\
  do									\
    {									\
      if (!pex_get_status (PEXOBJ, COUNT, VECTOR))			\
	FATAL_ERROR ("pex_get_status failed", errno);			\
    }									\
  while (0)

#define TEST_PEX_READ_OUTPUT(PEXOBJ)					\
  ((test_pex_file = pex_read_output (PEXOBJ, 0)) != NULL		\
   ? test_pex_file							\
   : (FATAL_ERROR ("pex_read_output failed", errno), NULL))

  remove ("temp.x");
  remove ("temp.y");

  memset (subargv, 0, sizeof subargv);

  subargv[0] = "./test-pexecute";

  pex1 = TEST_PEX_INIT (PEX_USE_PIPES, NULL);
  subargv[1] = "exit";
  subargv[2] = NULL;
  TEST_PEX_RUN (pex1, PEX_LAST, "./test-pexecute", subargv, NULL, NULL);
  status = TEST_PEX_GET_STATUS_1 (pex1);
  if (!WIFEXITED (status) || WEXITSTATUS (status) != EXIT_SUCCESS)
    ERROR ("exit failed");
  pex_free (pex1);

  pex1 = TEST_PEX_INIT (PEX_USE_PIPES, NULL);
  subargv[1] = "error";
  subargv[2] = NULL;
  TEST_PEX_RUN (pex1, PEX_LAST, "./test-pexecute", subargv, NULL, NULL);
  status = TEST_PEX_GET_STATUS_1 (pex1);
  if (!WIFEXITED (status) || WEXITSTATUS (status) != EXIT_FAILURE)
    ERROR ("error test failed");
  pex_free (pex1);

  /* We redirect stderr to a file to avoid an error message which is
     printed on mingw32 when the child calls abort.  */
  pex1 = TEST_PEX_INIT (PEX_USE_PIPES, NULL);
  subargv[1] = "abort";
  subargv[2] = NULL;
  TEST_PEX_RUN (pex1, PEX_LAST, "./test-pexecute", subargv, NULL, "temp.z");
  status = TEST_PEX_GET_STATUS_1 (pex1);
  if (!WIFSIGNALED (status) || WTERMSIG (status) != SIGABRT)
    ERROR ("abort failed");
  pex_free (pex1);
  remove ("temp.z");

  pex1 = TEST_PEX_INIT (PEX_USE_PIPES, "temp");
  subargv[1] = "echo";
  subargv[2] = "foo";
  subargv[3] = NULL;
  TEST_PEX_RUN (pex1, 0, "./test-pexecute", subargv, NULL, NULL);
  e = TEST_PEX_READ_OUTPUT (pex1);
  CHECK_LINE (e, "foo");
  if (TEST_PEX_GET_STATUS_1 (pex1) != 0)
    ERROR ("echo exit status failed");
  pex_free (pex1);

  pex1 = TEST_PEX_INIT (PEX_USE_PIPES, "temp");
  subargv[1] = "echo";
  subargv[2] = "bar";
  subargv[3] = NULL;
  TEST_PEX_RUN (pex1, PEX_SUFFIX, "./test-pexecute", subargv, ".x", NULL);
  subargv[1] = "copy";
  subargv[2] = NULL;
  TEST_PEX_RUN (pex1, PEX_SUFFIX, "./test-pexecute", subargv, ".y", NULL);
  e = TEST_PEX_READ_OUTPUT (pex1);
  CHECK_LINE (e, "bar");
  TEST_PEX_GET_STATUS (pex1, 2, statuses);
  if (!WIFEXITED (statuses[0]) || WEXITSTATUS (statuses[0]) != EXIT_SUCCESS
      || !WIFEXITED (statuses[1]) || WEXITSTATUS (statuses[1]) != EXIT_SUCCESS)
    ERROR ("copy exit status failed");
  pex_free (pex1);
  if (fopen ("temp.x", "r") != NULL || fopen ("temp.y", "r") != NULL)
    ERROR ("temporary files exist");

  pex1 = TEST_PEX_INIT (0, "temp");
  subargv[1] = "echo";
  subargv[2] = "bar";
  subargv[3] = NULL;
  TEST_PEX_RUN (pex1, PEX_SUFFIX, "./test-pexecute", subargv, ".x", NULL);
  subargv[1] = "copy";
  subargv[2] = NULL;
  TEST_PEX_RUN (pex1, PEX_SUFFIX, "./test-pexecute", subargv, ".y", NULL);
  e = TEST_PEX_READ_OUTPUT (pex1);
  CHECK_LINE (e, "bar");
  TEST_PEX_GET_STATUS (pex1, 2, statuses);
  if (!WIFEXITED (statuses[0]) || WEXITSTATUS (statuses[0]) != EXIT_SUCCESS
      || !WIFEXITED (statuses[1]) || WEXITSTATUS (statuses[1]) != EXIT_SUCCESS)
    ERROR ("copy exit status failed");
  pex_free (pex1);
  if (fopen ("temp.x", "r") != NULL || fopen ("temp.y", "r") != NULL)
    ERROR ("temporary files exist");

  pex1 = TEST_PEX_INIT (PEX_SAVE_TEMPS, "temp");
  subargv[1] = "echo";
  subargv[2] = "quux";
  subargv[3] = NULL;
  TEST_PEX_RUN (pex1, PEX_SUFFIX, "./test-pexecute", subargv, ".x", NULL);
  subargv[1] = "copy";
  subargv[2] = NULL;
  TEST_PEX_RUN (pex1, PEX_SUFFIX, "./test-pexecute", subargv, ".y", NULL);
  e = TEST_PEX_READ_OUTPUT (pex1);
  CHECK_LINE (e, "quux");
  TEST_PEX_GET_STATUS (pex1, 2, statuses);
  if (!WIFEXITED (statuses[0]) || WEXITSTATUS (statuses[0]) != EXIT_SUCCESS
      || !WIFEXITED (statuses[1]) || WEXITSTATUS (statuses[1]) != EXIT_SUCCESS)
    ERROR ("copy temp exit status failed");
  e = fopen ("temp.x", "r");
  if (e == NULL)
    FATAL_ERROR ("fopen temp.x failed in copy temp", errno);
  CHECK_LINE (e, "quux");
  fclose (e);
  e = fopen ("temp.y", "r");
  if (e == NULL)
    FATAL_ERROR ("fopen temp.y failed in copy temp", errno);
  CHECK_LINE (e, "quux");
  fclose (e);
  pex_free (pex1);
  remove ("temp.x");
  remove ("temp.y");

  pex1 = TEST_PEX_INIT (PEX_USE_PIPES, "temp");
  subargv[1] = "echoerr";
  subargv[2] = "one";
  subargv[3] = "two";
  subargv[4] = NULL;
  TEST_PEX_RUN (pex1, PEX_SUFFIX, "./test-pexecute", subargv, ".x", "temp2.x");
  subargv[1] = "write";
  subargv[2] = "temp2.y";
  subargv[3] = NULL;
  TEST_PEX_RUN (pex1, PEX_SUFFIX, "./test-pexecute", subargv, ".y", NULL);
  TEST_PEX_GET_STATUS (pex1, 2, statuses);
  if (!WIFEXITED (statuses[0]) || WEXITSTATUS (statuses[0]) != EXIT_SUCCESS
      || !WIFEXITED (statuses[1]) || WEXITSTATUS (statuses[1]) != EXIT_SUCCESS)
    ERROR ("echoerr exit status failed");
  pex_free (pex1);
  if (fopen ("temp.x", "r") != NULL || fopen ("temp.y", "r") != NULL)
    ERROR ("temporary files exist");
  e = fopen ("temp2.x", "r");
  if (e == NULL)
    FATAL_ERROR ("fopen temp2.x failed in echoerr", errno);
  CHECK_LINE (e, "two");
  fclose (e);
  e = fopen ("temp2.y", "r");
  if (e == NULL)
    FATAL_ERROR ("fopen temp2.y failed in echoerr", errno);
  CHECK_LINE (e, "one");
  fclose (e);
  remove ("temp2.x");
  remove ("temp2.y");

  /* Test the old pexecute interface.  */
  {
    int pid1, pid2;
    char *errmsg_fmt;
    char *errmsg_arg;
    char errbuf1[1000];
    char errbuf2[1000];

    subargv[1] = "echo";
    subargv[2] = "oldpexecute";
    subargv[3] = NULL;
    pid1 = pexecute ("./test-pexecute", subargv, "test-pexecute", "temp",
		     &errmsg_fmt, &errmsg_arg, PEXECUTE_FIRST);
    if (pid1 < 0)
      {
	snprintf (errbuf1, sizeof errbuf1, errmsg_fmt, errmsg_arg);
	snprintf (errbuf2, sizeof errbuf2, "pexecute 1 failed: %s", errbuf1);
	FATAL_ERROR (errbuf2, 0);
      }

    subargv[1] = "write";
    subargv[2] = "temp.y";
    subargv[3] = NULL;
    pid2 = pexecute ("./test-pexecute", subargv, "test-pexecute", "temp",
		     &errmsg_fmt, &errmsg_arg, PEXECUTE_LAST);
    if (pid2 < 0)
      {
	snprintf (errbuf1, sizeof errbuf1, errmsg_fmt, errmsg_arg);
	snprintf (errbuf2, sizeof errbuf2, "pexecute 2 failed: %s", errbuf1);
	FATAL_ERROR (errbuf2, 0);
      }

    if (pwait (pid1, &status, 0) < 0)
      FATAL_ERROR ("write pwait 1 failed", errno);
    if (!WIFEXITED (status) || WEXITSTATUS (status) != EXIT_SUCCESS)
      ERROR ("write exit status 1 failed");

    if (pwait (pid2, &status, 0) < 0)
      FATAL_ERROR ("write pwait 1 failed", errno);
    if (!WIFEXITED (status) || WEXITSTATUS (status) != EXIT_SUCCESS)
      ERROR ("write exit status 2 failed");

    e = fopen ("temp.y", "r");
    if (e == NULL)
      FATAL_ERROR ("fopen temp.y failed in copy temp", errno);
    CHECK_LINE (e, "oldpexecute");
    fclose (e);

    remove ("temp.y");
  }

  if (trace)
    fprintf (stderr, "Exiting with status %d\n", error_count);

  return error_count;
}