/* Install modified versions of certain ANSI-incompatible system header
   files which are fixed to work correctly with ANSI C and placed in a
   directory that GCC will search.

   Copyright (C) 1997, 1998, 1999, 2000, 2004, 2009, 2012
   Free Software Foundation, Inc.

This file is part of GCC.

GCC is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3, or (at your option)
any later version.

GCC 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 General Public License for more details.

You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3.  If not see
<http://www.gnu.org/licenses/>.  */

#include "fixlib.h"

#include <fnmatch.h>
#include <sys/stat.h>
#ifndef SEPARATE_FIX_PROC
#include <sys/wait.h>
#endif

#if defined( HAVE_MMAP_FILE )
#include <sys/mman.h>
#define  BAD_ADDR ((void*)-1)
#endif

#ifndef SEPARATE_FIX_PROC
#include "server.h"
#endif

/*  The contents of this string are not very important.  It is mostly
    just used as part of the "I am alive and working" test.  */

static const char program_id[] = "fixincl version 1.1";

/*  This format will be used at the start of every generated file */

static const char z_std_preamble[] =
"/*  DO NOT EDIT THIS FILE.\n\n\
    It has been auto-edited by fixincludes from:\n\n\
\t\"%s/%s\"\n\n\
    This had to be done to correct non-standard usages in the\n\
    original, manufacturer supplied header file.  */\n\n";

int find_base_len = 0;
int have_tty = 0;

pid_t process_chain_head = (pid_t) -1;

char*  pz_curr_file;  /*  name of the current file under test/fix  */
char*  pz_curr_data;  /*  original contents of that file  */
char*  pz_temp_file;  /*  for DOS, a place to stash the temporary
                          fixed data between system(3) calls  */
t_bool curr_data_mapped;
int    data_map_fd;
size_t data_map_size;
size_t ttl_data_size = 0;

#ifdef DO_STATS
int process_ct = 0;
int apply_ct = 0;
int fixed_ct = 0;
int altered_ct = 0;
#endif /* DO_STATS */

const char incl_quote_pat[] = "^[ \t]*#[ \t]*include[ \t]*\"[^/]";
regex_t incl_quote_re;

#ifndef SEPARATE_FIX_PROC
tSCC z_fork_err[] = "Error %d (%s) starting filter process for %s\n";
#endif

static void do_version (void) ATTRIBUTE_NORETURN;
char *load_file (const char *);
void run_compiles (void);
void initialize (int argc, char** argv);
void process (void);

/*  External Source Code */

#include "fixincl.x"

/* * * * * * * * * * * * * * * * * * *
 *
 *  MAIN ROUTINE
 */
extern int main (int, char **);
int
main (int argc, char** argv)
{
  char *file_name_buf;

  initialize ( argc, argv );

  have_tty = isatty (fileno (stderr));

  /* Before anything else, ensure we can allocate our file name buffer. */
  file_name_buf = load_file_data (stdin);

  /*  Because of the way server shells work, you have to keep stdin, out
      and err open so that the proper input file does not get closed
      by accident  */

  freopen ("/dev/null", "r", stdin);

  if (file_name_buf == (char *) NULL)
    {
      fputs ("No file names listed for fixing\n", stderr);
      exit (EXIT_FAILURE);
    }

  for (;;)
    {
      char* pz_end;

      /*  skip to start of name, past any "./" prefixes */

      while (ISSPACE (*file_name_buf))  file_name_buf++;
      while ((file_name_buf[0] == '.') && (file_name_buf[1] == '/'))
        file_name_buf += 2;

      /*  Check for end of list  */

      if (*file_name_buf == NUL)
        break;

      /*  Set global file name pointer and find end of name */

      pz_curr_file = file_name_buf;
      pz_end = strchr( pz_curr_file, '\n' );
      if (pz_end == (char*)NULL)
        pz_end = file_name_buf = pz_curr_file + strlen (pz_curr_file);
      else
        file_name_buf = pz_end + 1;

      while ((pz_end > pz_curr_file) && ISSPACE( pz_end[-1]))  pz_end--;

      /*  IF no name is found (blank line) or comment marker, skip line  */

      if ((pz_curr_file == pz_end) || (*pz_curr_file == '#'))
        continue;
      *pz_end = NUL;

      process ();
    } /*  for (;;) */

#ifdef DO_STATS
  if (VLEVEL( VERB_PROGRESS )) {
    tSCC zFmt[] =
      "\
Processed %5d files containing %d bytes    \n\
Applying  %5d fixes to %d files\n\
Altering  %5d of them\n";

    fprintf (stderr, zFmt, process_ct, ttl_data_size, apply_ct,
             fixed_ct, altered_ct);
  }
#endif /* DO_STATS */

# ifdef SEPARATE_FIX_PROC
  unlink( pz_temp_file );
# endif
  exit (EXIT_SUCCESS);
}


static void
do_version (void)
{
  static const char zFmt[] = "echo '%s'";
  char zBuf[ 1024 ];

  /* The 'version' option is really used to test that:
     1.  The program loads correctly (no missing libraries)
     2.  that we can compile all the regular expressions.
     3.  we can correctly run our server shell process
  */
  run_compiles ();
  sprintf (zBuf, zFmt, program_id);
#ifndef SEPARATE_FIX_PROC
  puts (zBuf + 5);
  exit (strcmp (run_shell (zBuf), program_id));
#else
  exit (system_with_shell (zBuf));
#endif
}

/* * * * * * * * * * * * */

void
initialize ( int argc, char** argv )
{
  xmalloc_set_program_name (argv[0]);

  switch (argc)
    {
    case 1:
      break;

    case 2:
      if (strcmp (argv[1], "-v") == 0)
        do_version ();
      if (freopen (argv[1], "r", stdin) == (FILE*)NULL)
        {
          fprintf (stderr, "Error %d (%s) reopening %s as stdin\n",
                   errno, xstrerror (errno), argv[1] );
          exit (EXIT_FAILURE);
        }
      break;

    default:
      fputs ("fixincl ERROR:  too many command line arguments\n", stderr);
      exit (EXIT_FAILURE);
    }

#ifdef SIGCHLD
  /* We *MUST* set SIGCHLD to SIG_DFL so that the wait4() call will
     receive the signal.  A different setting is inheritable */
  signal (SIGCHLD, SIG_DFL);
#endif

  initialize_opts ();

  if (ISDIGIT ( *pz_verbose ))
    verbose_level = (te_verbose)atoi( pz_verbose );
  else
    switch (*pz_verbose) {
    case 's':
    case 'S':
      verbose_level = VERB_SILENT;     break;

    case 'f':
    case 'F':
      verbose_level = VERB_FIXES;      break;

    case 'a':
    case 'A':
      verbose_level = VERB_APPLIES;    break;

    default:
    case 'p':
    case 'P':
      verbose_level = VERB_PROGRESS;   break;

    case 't':
    case 'T':
      verbose_level = VERB_TESTS;      break;

    case 'e':
    case 'E':
      verbose_level = VERB_EVERYTHING; break;
    }
  if (verbose_level >= VERB_EVERYTHING) {
    verbose_level = VERB_EVERYTHING;
    fputs ("fixinc verbosity:  EVERYTHING\n", stderr);
  }
  while ((pz_find_base[0] == '.') && (pz_find_base[1] == '/'))
    pz_find_base += 2;
  if ((pz_find_base[0] != '.') || (pz_find_base[1] != NUL))
    find_base_len = strlen( pz_find_base );

  /*  Compile all the regular expressions now.
      That way, it is done only once for the whole run.
      */
  run_compiles ();

# ifdef SEPARATE_FIX_PROC
  /* NULL as the first argument to `tempnam' causes it to DTRT
     wrt the temporary directory where the file will be created.  */
  pz_temp_file = tempnam( NULL, "fxinc" );

#if defined(__MINGW32__)
  fix_path_separators (pz_temp_file);
#endif

# endif

  signal (SIGQUIT, SIG_IGN);
  signal (SIGIOT,  SIG_IGN);
  signal (SIGPIPE, SIG_IGN);
  signal (SIGALRM, SIG_IGN);
  signal (SIGTERM, SIG_IGN);
}

/* * * * * * * * * * * * *

   load_file loads all the contents of a file into malloc-ed memory.
   Its argument is the name of the file to read in; the returned
   result is the NUL terminated contents of the file.  The file
   is presumed to be an ASCII text file containing no NULs.  */
char *
load_file ( const char* fname )
{
  struct stat stbf;
  char* res;

  if (stat (fname, &stbf) != 0)
    {
      if (NOT_SILENT)
        fprintf (stderr, "error %d (%s) stat-ing %s\n",
                 errno, xstrerror (errno), fname );
      return (char *) NULL;
    }
  if (stbf.st_size == 0)
    return (char*)NULL;

  /*  Make the data map size one larger than the file size for documentation
      purposes.  Truth is that there will be a following NUL character if
      the file size is not a multiple of the page size.  If it is a multiple,
      then this adjustment sometimes fails anyway.  */
  data_map_size = stbf.st_size+1;
  data_map_fd   = open (fname, O_RDONLY);
  ttl_data_size += data_map_size-1;

  if (data_map_fd < 0)
    {
      if (NOT_SILENT)
        fprintf (stderr, "error %d (%s) opening %s for read\n",
                 errno, xstrerror (errno), fname);
      return (char*)NULL;
    }

#ifdef HAVE_MMAP_FILE
  curr_data_mapped = BOOL_TRUE;

  /*  IF the file size is a multiple of the page size,
      THEN sometimes you will seg fault trying to access a trailing byte */
  if ((stbf.st_size & (getpagesize()-1)) == 0)
    res = (char*)BAD_ADDR;
  else
    res = (char*)mmap ((void*)NULL, data_map_size, PROT_READ,
                       MAP_PRIVATE, data_map_fd, 0);
  if (res == (char*)BAD_ADDR)
#endif
    {
      FILE* fp = fdopen (data_map_fd, "r");
      curr_data_mapped = BOOL_FALSE;
      res = load_file_data (fp);
      fclose (fp);
    }

  return res;
}

static int
machine_matches( tFixDesc* p_fixd )
{
  char const ** papz_machs = p_fixd->papz_machs;
  int have_match = BOOL_FALSE;

  for (;;)
    {
      char const * pz_mpat = *(papz_machs++);
      if (pz_mpat == NULL)
        break;
      if (fnmatch(pz_mpat, pz_machine, 0) == 0)
        {
          have_match = BOOL_TRUE;
          break;
        }
    }

  /* Check for sense inversion then set the "skip test" flag, if needed */
  if (p_fixd->fd_flags & FD_MACH_IFNOT)
    have_match = ! have_match;

  if (! have_match)
    p_fixd->fd_flags |= FD_SKIP_TEST;

  return have_match;
}

/* * * * * * * * * * * * *
 *
 *  run_compiles   run all the regexp compiles for all the fixes once.
 */
void
run_compiles (void)
{
  tFixDesc *p_fixd = fixDescList;
  int fix_ct = FIX_COUNT;
  regex_t *p_re = XCNEWVEC (regex_t, REGEX_COUNT);

  /*  Make sure compile_re does not stumble across invalid data */

  memset (&incl_quote_re, '\0', sizeof (regex_t));

  compile_re (incl_quote_pat, &incl_quote_re, 1,
              "quoted include", "run_compiles");

  /*  Allow machine name tests to be ignored (testing, mainly) */

  if (pz_machine && ((*pz_machine == '\0') || (*pz_machine == '*')))
    pz_machine = (char*)NULL;

  /* FOR every fixup, ...  */
  do
    {
      tTestDesc *p_test;
      int test_ct;

      if (fixinc_mode && (p_fixd->fd_flags & FD_REPLACEMENT))
        {
          p_fixd->fd_flags |= FD_SKIP_TEST;
          continue;
        }

      p_test = p_fixd->p_test_desc;
      test_ct = p_fixd->test_ct;

      /*  IF the machine type pointer is not NULL (we are not in test mode)
             AND this test is for or not done on particular machines
          THEN ...   */

      if (  (pz_machine != NULL)
         && (p_fixd->papz_machs != (const char**) NULL)
         && ! machine_matches (p_fixd) )
        continue;

      /* FOR every test for the fixup, ...  */

      while (--test_ct >= 0)
        {
          switch (p_test->type)
            {
            case TT_EGREP:
            case TT_NEGREP:
              p_test->p_test_regex = p_re++;
              compile_re (p_test->pz_test_text, p_test->p_test_regex, 0,
                          "select test", p_fixd->fix_name);
            default: break;
            }
          p_test++;
        }
    }
  while (p_fixd++, --fix_ct > 0);
}


/* * * * * * * * * * * * *

   create_file  Create the output modified file.
   Input:    the name of the file to create
   Returns:  a file pointer to the new, open file  */

#if defined(S_IRUSR) && defined(S_IWUSR) && \
    defined(S_IRGRP) && defined(S_IROTH)

#   define S_IRALL (S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH)
#else
#   define S_IRALL 0644
#endif

#if defined(S_IRWXU) && defined(S_IRGRP) && defined(S_IXGRP) && \
    defined(S_IROTH) && defined(S_IXOTH)

#   define S_DIRALL (S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH)
#else
#   define S_DIRALL 0755
#endif


static FILE *
create_file (void)
{
  int fd;
  FILE *pf;
  char fname[MAXPATHLEN];

  sprintf (fname, "%s/%s", pz_dest_dir, pz_curr_file + find_base_len);

  fd = open (fname, O_WRONLY | O_CREAT | O_TRUNC, S_IRALL);

  /*  We may need to create the directories needed... */
  if ((fd < 0) && (errno == ENOENT))
    {
      char *pz_dir = strchr (fname + 1, '/');
      struct stat stbf;

      while (pz_dir != (char *) NULL)
        {
          *pz_dir = NUL;
          if (stat (fname, &stbf) < 0)
            {
#ifdef _WIN32
              mkdir (fname);
#else
              mkdir (fname, S_IFDIR | S_DIRALL);
#endif
            }

          *pz_dir = '/';
          pz_dir = strchr (pz_dir + 1, '/');
        }

      /*  Now, lets try the open again... */
      fd = open (fname, O_WRONLY | O_CREAT | O_TRUNC, S_IRALL);
    }
  if (fd < 0)
    {
      fprintf (stderr, "Error %d (%s) creating %s\n",
               errno, xstrerror (errno), fname);
      exit (EXIT_FAILURE);
    }
  if (NOT_SILENT)
    fprintf (stderr, "Fixed:  %s\n", pz_curr_file);
  pf = fdopen (fd, "w");

  /*
   *  IF pz_machine is NULL, then we are in some sort of test mode.
   *  Do not insert the current directory name.  Use a constant string.
   */
  fprintf (pf, z_std_preamble,
           (pz_machine == NULL)
           ? "fixinc/tests/inc"
           : pz_input_dir,
           pz_curr_file);

  return pf;
}


/* * * * * * * * * * * * *

  test_test   make sure a shell-style test expression passes.
  Input:  a pointer to the descriptor of the test to run and
          the name of the file that we might want to fix
  Result: APPLY_FIX or SKIP_FIX, depending on the result of the
          shell script we run.  */
#ifndef SEPARATE_FIX_PROC
static int
test_test (tTestDesc* p_test, char* pz_test_file)
{
  tSCC cmd_fmt[] =
"file=%s\n\
if ( test %s ) > /dev/null 2>&1\n\
then echo TRUE\n\
else echo FALSE\n\
fi";

  char *pz_res;
  int res;

  static char cmd_buf[4096];

  sprintf (cmd_buf, cmd_fmt, pz_test_file, p_test->pz_test_text);
  pz_res = run_shell (cmd_buf);

  switch (*pz_res) {
  case 'T':
    res = APPLY_FIX;
    break;

  case 'F':
    res = SKIP_FIX;
    break;

  default:
    fprintf (stderr, "Script yielded bogus result of `%s':\n%s\n\n",
             pz_res, cmd_buf );
    res = SKIP_FIX;
  }

  free ((void *) pz_res);
  return res;
}
#elif defined(__MINGW32__) || defined(__DJGPP__)
static int
test_test (tTestDesc* p_test, char* pz_test_file)
{
  tSCC cmd_fmt[] =
#if defined(__DJGPP__)
    "file=%s; test %s >/dev/null 2>/dev/null";
#else
    "file=%s; test %s > /dev/null 2>&1";
#endif
  int res;

  char *cmd_buf = XNEWVEC (char, strlen(cmd_fmt) + strlen(pz_test_file) + strlen(p_test->pz_test_text));

  sprintf (cmd_buf, cmd_fmt, pz_test_file, p_test->pz_test_text);
  res = system_with_shell (cmd_buf);

  free (cmd_buf);
  return res ? SKIP_FIX : APPLY_FIX;
}
#else
/*
 *  IF we are in MS-DOS land, then whatever shell-type test is required
 *  will, by definition, fail
 */
#define test_test(t,tf)  SKIP_FIX
#endif

/* * * * * * * * * * * * *

  egrep_test   make sure an egrep expression is found in the file text.
  Input:  a pointer to the descriptor of the test to run and
          the pointer to the contents of the file under suspicion
  Result: APPLY_FIX if the pattern is found, SKIP_FIX otherwise

  The caller may choose to reverse meaning if the sense of the test
  is inverted.  */

static int
egrep_test (char* pz_data, tTestDesc* p_test)
{
#ifdef DEBUG
  if (p_test->p_test_regex == 0)
    fprintf (stderr, "fixincl ERROR RE not compiled:  `%s'\n",
             p_test->pz_test_text);
#endif
  if (xregexec (p_test->p_test_regex, pz_data, 0, 0, 0) == 0)
    return APPLY_FIX;
  return SKIP_FIX;
}

/* * * * * * * * * * * * *

  cksum_test   check the sum of the candidate file
  Input:  the original file contents and the file name
  Result: APPLY_FIX if the check sum matches, SKIP_FIX otherwise

  The caller may choose to reverse meaning if the sense of the test
  is inverted.  */

static int
cksum_test (char * pz_data, tTestDesc * p_test, char * fname)
{
  unsigned int cksum;

  /*
   * Testing is off in normal operation mode.
   * So, in testing mode, APPLY_FIX is always returned.
   */
  if (fixinc_mode != TESTING_OFF)
    return APPLY_FIX;

  {
    char * fnm = strrchr(fname, '/');
    if (fnm != NULL)
      fname = fnm + 1;
    
    errno = 0;
    cksum = (unsigned int)strtoul(p_test->pz_test_text, &fnm, 10);
    if (errno != 0)
      return SKIP_FIX;

    if (! ISSPACE(*fnm++))
      return SKIP_FIX;
    while (ISSPACE(*fnm)) fnm++;

    if (! ISDIGIT(*fnm++))
      return SKIP_FIX;
    while (ISDIGIT(*fnm)) fnm++;

    if (! ISSPACE(*fnm++))
      return SKIP_FIX;
    while (ISSPACE(*fnm)) fnm++;

    if (strcmp(fnm, fname) != 0)
      return SKIP_FIX;
  }

  {
    unsigned int sum = 0;
    while (*pz_data != NUL) {
      sum = (sum >> 1) + ((sum & 1) << 15) + (unsigned)(*pz_data++);
      sum &= 0xFFFF;
    }

    return (sum == cksum) ? APPLY_FIX : SKIP_FIX;
  }
}

/* * * * * * * * * * * * *

  quoted_file_exists  Make sure that a file exists before we emit
  the file name.  If we emit the name, our invoking shell will try
  to copy a non-existing file into the destination directory.  */

static int
quoted_file_exists (const char* pz_src_path,
                    const char* pz_file_path, 
                    const char* pz_file)
{
  char z[ MAXPATHLEN ];
  char* pz;
  sprintf (z, "%s/%s/", pz_src_path, pz_file_path);
  pz = z + strlen ( z );

  for (;;) {
    char ch = *pz_file++;
    if (! ISGRAPH( ch ))
      return 0;
    if (ch == '"')
      break;
    *pz++ = ch;
  }
  *pz = '\0';
  {
    struct stat s;
    if (stat (z, &s) != 0)
      return 0;
    return S_ISREG( s.st_mode );
  }
}


/* * * * * * * * * * * * *
 *
   extract_quoted_files

   The syntax, `#include "file.h"' specifies that the compiler is to
   search the local directory of the current file before the include
   list.  Consequently, if we have modified a header and stored it in
   another directory, any files that are included by that modified
   file in that fashion must also be copied into this new directory.
   This routine finds those flavors of #include and for each one found
   emits a triple of:

    1.  source directory of the original file
    2.  the relative path file name of the #includ-ed file
    3.  the full destination path for this file

   Input:  the text of the file, the file name and a pointer to the
           match list where the match information was stored.
   Result: internally nothing.  The results are written to stdout
           for interpretation by the invoking shell  */


static void
extract_quoted_files (char* pz_data, 
                      const char* pz_fixed_file,
                      regmatch_t* p_re_match)
{
  char *pz_dir_end = strrchr (pz_fixed_file, '/');
  char *pz_incl_quot = pz_data;

  if (VLEVEL( VERB_APPLIES ))
    fprintf (stderr, "Quoted includes in %s\n", pz_fixed_file);

  /*  Set "pz_fixed_file" to point to the containing subdirectory of the source
      If there is none, then it is in our current directory, ".".   */

  if (pz_dir_end == (char *) NULL)
    pz_fixed_file = ".";
  else
    *pz_dir_end = '\0';

  for (;;)
    {
      pz_incl_quot += p_re_match->rm_so;

      /*  Skip forward to the included file name */
      while (*pz_incl_quot != '"')
        pz_incl_quot++;

      if (quoted_file_exists (pz_src_dir, pz_fixed_file, pz_incl_quot))
        {
          /* Print the source directory and the subdirectory
             of the file in question.  */
          printf ("%s  %s/", pz_src_dir, pz_fixed_file);
          pz_dir_end = pz_incl_quot;

          /* Append to the directory the relative path of the desired file */
          while (*pz_incl_quot != '"')
            putc (*pz_incl_quot++, stdout);

          /* Now print the destination directory appended with the
             relative path of the desired file */
          printf ("  %s/%s/", pz_dest_dir, pz_fixed_file);
          while (*pz_dir_end != '"')
            putc (*pz_dir_end++, stdout);

          /* End of entry */
          putc ('\n', stdout);
        }

      /* Find the next entry */
      if (xregexec (&incl_quote_re, pz_incl_quot, 1, p_re_match, 0) != 0)
        break;
    }
}


/* * * * * * * * * * * * *

    Somebody wrote a *_fix subroutine that we must call.
    */
#ifndef SEPARATE_FIX_PROC
static int
internal_fix (int read_fd, tFixDesc* p_fixd)
{
  int fd[2];

  if (pipe( fd ) != 0)
    {
      fprintf (stderr, "Error %d on pipe(2) call\n", errno );
      exit (EXIT_FAILURE);
    }

  for (;;)
    {
      pid_t childid = fork();

      switch (childid)
        {
        case -1:
          break;

        case 0:
          close (fd[0]);
          goto do_child_task;

        default:
          /*
           *  Parent process
           */
          close (read_fd);
          close (fd[1]);
          return fd[0];
        }

      /*
       *  Parent in error
       */
      fprintf (stderr, z_fork_err, errno, xstrerror (errno),
               p_fixd->fix_name);
      {
        static int failCt = 0;
        if ((errno != EAGAIN) || (++failCt > 10))
          exit (EXIT_FAILURE);
        sleep (1);
      }
    } do_child_task:;

  /*
   *  Close our current stdin and stdout
   */
  close (STDIN_FILENO);
  close (STDOUT_FILENO);
  UNLOAD_DATA();

  /*
   *  Make the fd passed in the stdin, and the write end of
   *  the new pipe become the stdout.
   */
  dup2 (fd[1], STDOUT_FILENO);
  dup2 (read_fd, STDIN_FILENO);

  apply_fix (p_fixd, pz_curr_file);
  exit (0);
}
#endif /* !SEPARATE_FIX_PROC */


#ifdef SEPARATE_FIX_PROC
static void
fix_with_system (tFixDesc* p_fixd,
                 tCC* pz_fix_file,
                 tCC* pz_file_source,
                 tCC* pz_temp_file)
{
  char*  pz_cmd;
  char*  pz_scan;
  size_t argsize;

  if (p_fixd->fd_flags & FD_SUBROUTINE)
    {
      static const char z_applyfix_prog[] =
        "/../fixincludes/applyfix" EXE_EXT;

      struct stat buf;
      argsize = 32
              + strlen (pz_orig_dir)
              + sizeof (z_applyfix_prog)
              + strlen (pz_fix_file)
              + strlen (pz_file_source)
              + strlen (pz_temp_file);

      /* Allocate something sure to be big enough for our purposes */
      pz_cmd = XNEWVEC (char, argsize);
      strcpy (pz_cmd, pz_orig_dir);
      pz_scan = pz_cmd + strlen (pz_orig_dir);

      strcpy (pz_scan, z_applyfix_prog);

      /* IF we can't find the "applyfix" executable file at the first guess,
         try one level higher up  */
      if (stat (pz_cmd, &buf) == -1)
        {
          strcpy (pz_scan, "/..");
          strcpy (pz_scan+3, z_applyfix_prog);
        }

      pz_scan += strlen (pz_scan);

      /*
       *  Now add the fix number and file names that may be needed
       */
      sprintf (pz_scan, " %ld '%s' '%s' '%s'", (long) (p_fixd - fixDescList),
               pz_fix_file, pz_file_source, pz_temp_file);
    }
  else /* NOT an "internal" fix: */
    {
      size_t parg_size;
#if defined(__MSDOS__) && !defined(__DJGPP__)
      /* Don't use the "src > dstX; rm -f dst; mv -f dstX dst" trick:
         dst is a temporary file anyway, so we know there's no other
         file by that name; and DOS's system(3) doesn't mind to
         clobber existing file in redirection.  Besides, with DOS 8+3
         limited file namespace, we can easily lose if dst already has
         an extension that is 3 or more characters long.

         I do not think the 8+3 issue is relevant because all the files
         we operate on are named "*.h", making 8+2 adequate.  Anyway,
         the following bizarre use of 'cat' only works on DOS boxes.
         It causes the file to be dropped into a temporary file for
         'cat' to read (pipes do not work on DOS).  */
      tSCC   z_cmd_fmt[] = " '%s' | cat > '%s'";
#else
      /* Don't use positional formatting arguments because some lame-o
         implementations cannot cope  :-(.  */
      tSCC   z_cmd_fmt[] = " %s > %sX ; rm -f %s; mv -f %sX %s";
#endif
      tSCC   z_subshell_start[] = "( ";
      tSCC   z_subshell_end[] = " ) < ";
      tCC**  ppArgs = p_fixd->patch_args;

      argsize = sizeof( z_cmd_fmt ) + strlen( pz_temp_file )
              + strlen( pz_file_source );
      parg_size = argsize;
      
      if (p_fixd->fd_flags & FD_SHELL_SCRIPT)
        {
          argsize += strlen( z_subshell_start ) + strlen ( z_subshell_end );
        }

      /*
       *  Compute the size of the command line.  Add lotsa extra space
       *  because some of the args to sed use lotsa single quotes.
       *  (This requires three extra bytes per quote.  Here we allow
       *  for up to 8 single quotes for each argument, including the
       *  command name "sed" itself.  Nobody will *ever* need more. :)
       */
      for (;;)
        {
          tCC* p_arg = *(ppArgs++);
          if (p_arg == NULL)
            break;
          argsize += 24 + strlen( p_arg );
        }

      /* Estimated buffer size we will need.  */
      pz_scan = pz_cmd = XNEWVEC (char, argsize);
      /* How much of it do we allot to the program name and its
         arguments.  */
      parg_size = argsize - parg_size;

      ppArgs = p_fixd->patch_args;

      /*
       * If it's shell script, enclose it in parentheses and skip "sh -c".
       */
      if (p_fixd->fd_flags & FD_SHELL_SCRIPT)
        {
          strcpy (pz_scan, z_subshell_start);
          pz_scan += strlen (z_subshell_start);
          ppArgs += 2;
        }

      /*
       *  Copy the program name, unquoted
       */
      {
        tCC*   pArg = *(ppArgs++);
        for (;;)
          {
            char ch = *(pArg++);
            if (ch == NUL)
              break;
            *(pz_scan++) = ch;
          }
      }

      /*
       *  Copy the program arguments, quoted
       */
      for (;;)
        {
          tCC*   pArg = *(ppArgs++);
          char*  pz_scan_save;
          if (pArg == NULL)
            break;
          *(pz_scan++) = ' ';
          pz_scan = make_raw_shell_str( pz_scan_save = pz_scan, pArg,
                                        parg_size - (pz_scan - pz_cmd) );
          /*
           *  Make sure we don't overflow the buffer due to sloppy
           *  size estimation.
           */
          while (pz_scan == (char*)NULL)
            {
              size_t already_filled = pz_scan_save - pz_cmd;
              pz_cmd = xrealloc (pz_cmd, argsize += 100);
              pz_scan_save = pz_scan = pz_cmd + already_filled;
              parg_size += 100;
              pz_scan = make_raw_shell_str( pz_scan, pArg,
                                            parg_size - (pz_scan - pz_cmd) );
            }
        }

      /*
       * Close parenthesis if it's shell script.
       */
      if (p_fixd->fd_flags & FD_SHELL_SCRIPT)
        {
          strcpy (pz_scan, z_subshell_end);
          pz_scan += strlen (z_subshell_end);
        }

      /*
       *  add the file machinations.
       */
#if defined(__MSDOS__) && !defined(__DJGPP__)
      sprintf (pz_scan, z_cmd_fmt, pz_file_source, pz_temp_file );
#else
      sprintf (pz_scan, z_cmd_fmt, pz_file_source, pz_temp_file,
               pz_temp_file, pz_temp_file, pz_temp_file);
#endif
    }
  system_with_shell (pz_cmd);
  free (pz_cmd);
}

/* * * * * * * * * * * * *

    This loop should only cycle for 1/2 of one loop.
    "chain_open" starts a process that uses "read_fd" as
    its stdin and returns the new fd this process will use
    for stdout.  */

#else /* is *NOT* SEPARATE_FIX_PROC */
static int
start_fixer (int read_fd, tFixDesc* p_fixd, char* pz_fix_file)
{
  tCC* pz_cmd_save;
  char* pz_cmd;

  if ((p_fixd->fd_flags & FD_SUBROUTINE) != 0)
    return internal_fix (read_fd, p_fixd);

  if ((p_fixd->fd_flags & FD_SHELL_SCRIPT) == 0)
    {
      pz_cmd = NULL;
      pz_cmd_save = NULL;
    }
  else
    {
      tSCC z_cmd_fmt[] = "file='%s'\n%s";
      pz_cmd = XNEWVEC (char, strlen (p_fixd->patch_args[2])
                        + sizeof (z_cmd_fmt) + strlen (pz_fix_file));
      sprintf (pz_cmd, z_cmd_fmt, pz_fix_file, p_fixd->patch_args[2]);
      pz_cmd_save = p_fixd->patch_args[2];
      p_fixd->patch_args[2] = pz_cmd;
    }

  /*  Start a fix process, handing off the  previous read fd for its
      stdin and getting a new fd that reads from the fix process' stdout.
      We normally will not loop, but we will up to 10 times if we keep
      getting "EAGAIN" errors.

      */
  for (;;)
    {
      static int failCt = 0;
      int fd;

      fd = chain_open (read_fd,
                       (tCC **) p_fixd->patch_args,
                       (process_chain_head == -1)
                       ? &process_chain_head : (pid_t *) NULL);

      if (fd != -1)
        {
          read_fd = fd;
          break;
        }

      fprintf (stderr, z_fork_err, errno, xstrerror (errno),
               p_fixd->fix_name);

      if ((errno != EAGAIN) || (++failCt > 10))
        exit (EXIT_FAILURE);
      sleep (1);
    }

  /*  IF we allocated a shell script command,
      THEN free it and restore the command format to the fix description */
  if (pz_cmd != (char*)NULL)
    {
      free ((void*)pz_cmd);
      p_fixd->patch_args[2] = pz_cmd_save;
    }

  return read_fd;
}
#endif
#ifdef DEBUG
# define NOTE_SKIP(_ttyp)  do {                                         \
            if (VLEVEL( VERB_EVERYTHING ))                              \
              fprintf (stderr, z_failed, _ttyp, p_fixd->fix_name,       \
                       pz_fname, p_fixd->test_ct - test_ct);            \
          } while (0)
#else
# define NOTE_SKIP(_ttyp)
#endif

/* * * * * * * * * * * * *
 *
 *  Process the potential fixes for a particular include file.
 *  Input:  the original text of the file and the file's name
 *  Result: none.  A new file may or may not be created.
 */
static t_bool
fix_applies (tFixDesc* p_fixd)
{
  const char *pz_fname = pz_curr_file;
  const char *pz_scan = p_fixd->file_list;
  int test_ct;
  tTestDesc *p_test;
  t_bool saw_sum_test   = BOOL_FALSE;
  t_bool one_sum_passed = BOOL_FALSE;

#if defined(__MSDOS__) && !defined(__DJGPP__)
  /*
   *  There is only one fix that uses a shell script as of this writing.
   *  I hope to nuke it anyway, it does not apply to DOS and it would
   *  be painful to implement.  Therefore, no "shell" fixes for DOS.
   */
  if (p_fixd->fd_flags & (FD_SHELL_SCRIPT | FD_SKIP_TEST))
    return BOOL_FALSE;
#else
  if (p_fixd->fd_flags & FD_SKIP_TEST)
    return BOOL_FALSE;
#endif

  /*  IF there is a file name restriction,
      THEN ensure the current file name matches one in the pattern  */

  if (pz_scan != (char *) NULL)
    {
      while ((pz_fname[0] == '.') && (pz_fname[1] == '/'))
        pz_fname += 2;

      for (;;)
        {
          if (fnmatch (pz_scan, pz_fname, 0) == 0)
            break;
          pz_scan += strlen (pz_scan) + 1;
          if (*pz_scan == NUL)
            return BOOL_FALSE;
        }
    }

  /*  FOR each test, see if it fails.
      "sum" fails only if all "sum" tests fail.
      IF it does fail, then we go on to the next test */

  for (p_test = p_fixd->p_test_desc, test_ct = p_fixd->test_ct;
       test_ct-- > 0;
       p_test++)
    {
      switch (p_test->type)
        {
        case TT_TEST:
          if (test_test (p_test, pz_curr_file) != APPLY_FIX) {
            NOTE_SKIP("TEST");
            return BOOL_FALSE;
          }
          break;

        case TT_EGREP:
          if (egrep_test (pz_curr_data, p_test) != APPLY_FIX) {
            NOTE_SKIP("EGREP");
            return BOOL_FALSE;
          }
          break;

        case TT_NEGREP:
          if (egrep_test (pz_curr_data, p_test) == APPLY_FIX) {
            NOTE_SKIP("NEGREP");
            /*  Negated sense  */
            return BOOL_FALSE;
          }
          break;

        case TT_CKSUM:
	  if (one_sum_passed)
	    break; /*  No need to check any more  */

          saw_sum_test = BOOL_TRUE;
          if (cksum_test (pz_curr_data, p_test, pz_curr_file) != APPLY_FIX) {
            NOTE_SKIP("CKSUM");
          } else {
            one_sum_passed = BOOL_TRUE;
          }
          break;

        case TT_FUNCTION:
          if (run_test (p_test->pz_test_text, pz_curr_file, pz_curr_data)
              != APPLY_FIX) {
            NOTE_SKIP("FTEST");
            return BOOL_FALSE;
          }
          break;
        }
    }

  if (saw_sum_test)
    return one_sum_passed;

  return BOOL_TRUE;
}


/* * * * * * * * * * * * *

   Write out a replacement file  */

static void
write_replacement (tFixDesc* p_fixd)
{
   const char* pz_text = p_fixd->patch_args[0];

   if ((pz_text == (char*)NULL) || (*pz_text == NUL))
     return;

   {
     FILE* out_fp = create_file ();
     size_t sz = strlen (pz_text);
     fwrite (pz_text, sz, 1, out_fp);
     if (pz_text[ sz-1 ] != '\n')
       fputc ('\n', out_fp);
     fclose (out_fp);
   }
}


/* * * * * * * * * * * * *

    We have work to do.  Read back in the output
    of the filtering chain.  Compare each byte as we read it with
    the contents of the original file.  As soon as we find any
    difference, we will create the output file, write out all
    the matched text and then copy any remaining data from the
    output of the filter chain.
    */
static void
test_for_changes (int read_fd)
{
  FILE *in_fp = fdopen (read_fd, "r");
  FILE *out_fp = (FILE *) NULL;
  unsigned char *pz_cmp = (unsigned char*)pz_curr_data;

#ifdef DO_STATS
  fixed_ct++;
#endif
  for (;;)
    {
      int ch;

      ch = getc (in_fp);
      if (ch == EOF)
        break;
      ch &= 0xFF; /* all bytes are 8 bits */

      /*  IF we are emitting the output
          THEN emit this character, too.
      */
      if (out_fp != (FILE *) NULL)
        putc (ch, out_fp);

      /*  ELSE if this character does not match the original,
          THEN now is the time to start the output.
      */
      else if (ch != *pz_cmp)
        {
          out_fp = create_file ();

#ifdef DO_STATS
          altered_ct++;
#endif
          /*  IF there are matched data, write the matched part now. */
          if ((char*)pz_cmp != pz_curr_data)
            fwrite (pz_curr_data, (size_t)((char*)pz_cmp - pz_curr_data),
                    1, out_fp);

          /*  Emit the current unmatching character */
          putc (ch, out_fp);
        }
      else
        /*  ELSE the character matches.  Advance the compare ptr */
        pz_cmp++;
    }

  /*  IF we created the output file, ... */
  if (out_fp != (FILE *) NULL)
    {
      regmatch_t match;

      /* Close the file and see if we have to worry about
         `#include "file.h"' constructs.  */
      fclose (out_fp);
      if (xregexec (&incl_quote_re, pz_curr_data, 1, &match, 0) == 0)
        extract_quoted_files (pz_curr_data, pz_curr_file, &match);
    }

  fclose (in_fp);
  close (read_fd);  /* probably redundant, but I'm paranoid */
}


/* * * * * * * * * * * * *

   Process the potential fixes for a particular include file.
   Input:  the original text of the file and the file's name
   Result: none.  A new file may or may not be created.  */

void
process (void)
{
  tFixDesc *p_fixd = fixDescList;
  int todo_ct = FIX_COUNT;
  int read_fd = -1;
# ifndef SEPARATE_FIX_PROC
  int num_children = 0;
# else /* is SEPARATE_FIX_PROC */
  char* pz_file_source = pz_curr_file;
# endif

  if (access (pz_curr_file, R_OK) != 0)
    {
      int erno = errno;
      fprintf (stderr, "Cannot access %s from %s\n\terror %d (%s)\n",
               pz_curr_file, getcwd ((char *) NULL, MAXPATHLEN),
               erno, xstrerror (erno));
      return;
    }

  pz_curr_data = load_file (pz_curr_file);
  if (pz_curr_data == (char *) NULL)
    return;

#ifdef DO_STATS
  process_ct++;
#endif
  if (VLEVEL( VERB_PROGRESS ) && have_tty)
    fprintf (stderr, "%6lu %-50s   \r",
             (unsigned long) data_map_size, pz_curr_file);

# ifndef SEPARATE_FIX_PROC
  process_chain_head = NOPROCESS;

  /* For every fix in our fix list, ...  */
  for (; todo_ct > 0; p_fixd++, todo_ct--)
    {
      if (! fix_applies (p_fixd))
        continue;

      if (VLEVEL( VERB_APPLIES ))
        fprintf (stderr, "Applying %-24s to %s\n",
                 p_fixd->fix_name, pz_curr_file);

      if (p_fixd->fd_flags & FD_REPLACEMENT)
        {
          write_replacement (p_fixd);
          UNLOAD_DATA();
          return;
        }

      /*  IF we do not have a read pointer,
          THEN this is the first fix for the current file.
          Open the source file.  That will be used as stdin for
          the first fix.  Any subsequent fixes will use the
          stdout descriptor of the previous fix for its stdin.  */

      if (read_fd == -1)
        {
          read_fd = open (pz_curr_file, O_RDONLY);
          if (read_fd < 0)
            {
              fprintf (stderr, "Error %d (%s) opening %s\n", errno,
                       xstrerror (errno), pz_curr_file);
              exit (EXIT_FAILURE);
            }

          /*  Ensure we do not get duplicate output */

          fflush (stdout);
        }

      read_fd = start_fixer (read_fd, p_fixd, pz_curr_file);
      num_children++;
    }

  /*  IF we have a read-back file descriptor,
      THEN check for changes and write output if changed.   */

  if (read_fd >= 0)
    {
      test_for_changes (read_fd);
#ifdef DO_STATS
      apply_ct += num_children;
#endif
      /* Wait for child processes created by chain_open()
         to avoid leaving zombies.  */
      do  {
        wait ((int *) NULL);
      } while (--num_children > 0);
    }

# else /* is SEPARATE_FIX_PROC */

  for (; todo_ct > 0; p_fixd++, todo_ct--)
    {
      if (! fix_applies (p_fixd))
        continue;

      if (VLEVEL( VERB_APPLIES ))
        fprintf (stderr, "Applying %-24s to %s\n",
                 p_fixd->fix_name, pz_curr_file);

      if (p_fixd->fd_flags & FD_REPLACEMENT)
        {
          write_replacement (p_fixd);
          UNLOAD_DATA();
          return;
        }
      fix_with_system (p_fixd, pz_curr_file, pz_file_source, pz_temp_file);
      pz_file_source = pz_temp_file;
    }

  read_fd = open (pz_temp_file, O_RDONLY);
  if (read_fd < 0)
    {
      if (errno != ENOENT)
        fprintf (stderr, "error %d (%s) opening output (%s) for read\n",
                 errno, xstrerror (errno), pz_temp_file);
    }
  else
    {
      test_for_changes (read_fd);
      /* Unlinking a file while it is still open is a Bad Idea on
         DOS/Windows.  */
      close (read_fd);
      unlink (pz_temp_file);
    }

# endif
  UNLOAD_DATA();
}
