OSDN Git Service

* rtl.h (addr_diff_vec_flags): New typedef.
[pf3gnuchains/gcc-fork.git] / gcc / gcc.c
index 2027d28..5f53c24 100644 (file)
--- a/gcc/gcc.c
+++ b/gcc/gcc.c
@@ -1,5 +1,5 @@
 /* Compiler driver program that can handle many languages.
-   Copyright (C) 1987, 89, 92-96, 1997 Free Software Foundation, Inc.
+   Copyright (C) 1987, 89, 92-97, 1998 Free Software Foundation, Inc.
 
 This file is part of GNU CC.
 
@@ -31,37 +31,27 @@ CC recognizes how to compile each input file by suffixes in the file names.
 Once it knows which kind of compilation to perform, the procedure for
 compilation is specified by a string called a "spec".  */
 \f
-#include <sys/types.h>
-#include <ctype.h>
-#include <signal.h>
-#include <sys/stat.h>
-#include <errno.h>
-
-#ifndef NO_SYS_FILE_H
-#include <sys/file.h>   /* May get R_OK, etc. on some systems.  */
-#endif
-
 #include "config.h"
-#include "obstack.h"
+
 #include "gansidecl.h"
+#include "system.h"
 
+#include <signal.h>
+#include <sys/stat.h>
 #ifdef __STDC__
 #include <stdarg.h>
 #else
 #include <varargs.h>
 #endif
-#include <stdio.h>
 
-#ifndef R_OK
-#define R_OK 4
-#define W_OK 2
-#define X_OK 1
-#endif
+#include "obstack.h"
+
 
 /* ??? Need to find a GCC header to put these in.  */
 extern int pexecute PROTO ((const char *, char * const *, const char *,
                            const char *, char **, char **, int));
 extern int pwait PROTO ((int, int *, int));
+extern char *update_path PROTO((char *, char *));
 /* Flag arguments to pexecute.  */
 #define PEXECUTE_FIRST   1
 #define PEXECUTE_LAST    2
@@ -132,26 +122,19 @@ static char dir_separator_str[] = {DIR_SEPARATOR, 0};
 #define obstack_chunk_alloc xmalloc
 #define obstack_chunk_free free
 
-extern void free ();
-extern char *getenv ();
-
 extern char *choose_temp_base PROTO((void));
 
-#ifndef errno
-extern int errno;
-#endif
-
 #ifndef HAVE_STRERROR
 extern int sys_nerr;
-#if defined(bsd4_4)
-extern const char *const sys_errlist[];
-#else
 extern char *sys_errlist[];
-#endif
 #else
 extern char *strerror();
 #endif
 
+#ifndef HAVE_KILL
+#define kill(p,s) raise(s)
+#endif
+
 /* If a stage of compilation returns an exit status >= 1,
    compilation of that file ceases.  */
 
@@ -238,7 +221,8 @@ static struct compiler *lookup_compiler PROTO((char *, int, char *));
 static char *build_search_list PROTO((struct path_prefix *, char *, int));
 static void putenv_from_prefixes PROTO((struct path_prefix *, char *));
 static char *find_a_file       PROTO((struct path_prefix *, char *, int));
-static void add_prefix         PROTO((struct path_prefix *, char *, int, int, int *));
+static void add_prefix         PROTO((struct path_prefix *, char *, char *,
+                                      int, int, int *));
 static char *skip_whitespace   PROTO((char *));
 static void record_temp_file   PROTO((char *, int, int));
 static void delete_if_ordinary PROTO((char *));
@@ -525,11 +509,12 @@ static struct user_specs *user_specs_head, *user_specs_tail;
 
 /* This defines which switch letters take arguments.  */
 
-#define DEFAULT_SWITCH_TAKES_ARG(CHAR)      \
+#define DEFAULT_SWITCH_TAKES_ARG(CHAR) \
   ((CHAR) == 'D' || (CHAR) == 'U' || (CHAR) == 'o' \
    || (CHAR) == 'e' || (CHAR) == 'T' || (CHAR) == 'u' \
    || (CHAR) == 'I' || (CHAR) == 'm' || (CHAR) == 'x' \
-   || (CHAR) == 'L' || (CHAR) == 'A')
+   || (CHAR) == 'L' || (CHAR) == 'A' || (CHAR) == 'V' \
+   || (CHAR) == 'B' || (CHAR) == 'b')
 
 #ifndef SWITCH_TAKES_ARG
 #define SWITCH_TAKES_ARG(CHAR) DEFAULT_SWITCH_TAKES_ARG(CHAR)
@@ -580,13 +565,14 @@ static int n_compilers;
 static struct compiler default_compilers[] =
 {
   /* Add lists of suffixes of known languages here.  If those languages
-     were no present when we built the driver, we will hit these copies
-     and given a more meaningful error than "file not used since
+     were not present when we built the driver, we will hit these copies
+     and be given a more meaningful error than "file not used since
      linking is not done".  */
   {".cc", "#C++"}, {".cxx", "#C++"}, {".cpp", "#C++"}, {".c++", "#C++"},
   {".C", "#C++"}, {".ads", "#Ada"}, {".adb", "#Ada"}, {".ada", "#Ada"},
   {".f", "#Fortran"}, {".for", "#Fortran"}, {".F", "#Fortran"},
   {".fpp", "#Fortran"},
+  {".p", "#Pascal"}, {".pas", "#Pascal"},
   /* Next come the entries for C.  */
   {".c", "@c"},
   {"@c",
@@ -596,7 +582,8 @@ static struct compiler default_compilers[] =
         -undef -D__GNUC__=%v1 -D__GNUC_MINOR__=%v2\
        %{ansi:-trigraphs -D__STRICT_ANSI__}\
        %{!undef:%{!ansi:%p} %P} %{trigraphs} \
-        %c %{O*:%{!O0:-D__OPTIMIZE__}} %{traditional} %{ftraditional:-traditional}\
+        %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+        %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*} %Z\
         %i %{!M:%{!MM:%{!E:%{!pipe:%g.i}}}}%{E:%W{o*}}%{M:%W{o*}}%{MM:%W{o*}} |\n",
@@ -617,7 +604,8 @@ static struct compiler default_compilers[] =
         -undef -D__GNUC__=%v1 -D__GNUC_MINOR__=%v2\
        %{ansi:-trigraphs -D__STRICT_ANSI__}\
        %{!undef:%{!ansi:%p} %P} %{trigraphs}\
-        %c %{O*:%{!O0:-D__OPTIMIZE__}} %{traditional} %{ftraditional:-traditional}\
+        %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+        %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*} %Z\
         %i %W{o*}}\
@@ -630,7 +618,8 @@ static struct compiler default_compilers[] =
         -undef -D__OBJC__ -D__GNUC__=%v1 -D__GNUC_MINOR__=%v2\
         %{ansi:-trigraphs -D__STRICT_ANSI__}\
        %{!undef:%{!ansi:%p} %P} %{trigraphs}\
-        %c %{O*:%{!O0:-D__OPTIMIZE__}} %{traditional} %{ftraditional:-traditional}\
+        %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+        %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*} %Z\
         %i %{!M:%{!MM:%{!E:%{!pipe:%g.i}}}}%{E:%W{o*}}%{M:%W{o*}}%{MM:%W{o*}} |\n",
@@ -654,7 +643,8 @@ static struct compiler default_compilers[] =
         -undef -D__GNUC__=%v1 -D__GNUC_MINOR__=%v2\
         %{ansi:-trigraphs -D__STRICT_ANSI__}\
        %{!undef:%{!ansi:%p} %P} %{trigraphs}\
-        %c %{O*:%{!O0:-D__OPTIMIZE__}} %{traditional} %{ftraditional:-traditional}\
+        %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+        %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*} %Z\
         %i %W{o*}"},
@@ -680,7 +670,8 @@ static struct compiler default_compilers[] =
        %{C:%{!E:%eGNU C does not support -C without using -E}}\
        %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d} %{MG} %{trigraphs}\
         -undef -$ %{!undef:%p %P} -D__ASSEMBLER__ \
-        %c %{O*:%{!O0:-D__OPTIMIZE__}} %{traditional} %{ftraditional:-traditional}\
+        %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+        %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*} %Z\
         %i %{!M:%{!MM:%{!E:%{!pipe:%g.s}}}}%{E:%W{o*}}%{M:%W{o*}}%{MM:%W{o*}} |\n",
@@ -1160,7 +1151,8 @@ set_spec (name, spec)
   if (!specs)
     {
       struct spec_list *next = (struct spec_list *)0;
-      for (i = (sizeof (static_specs) / sizeof (static_specs[0])) - 1; i >= 0; i--)
+      for (i = (sizeof (static_specs) / sizeof (static_specs[0])) - 1;
+          i >= 0; i--)
        {
          sl = &static_specs[i];
          sl->next = next;
@@ -1188,7 +1180,7 @@ set_spec (name, spec)
     }
 
   old_spec = *(sl->ptr_spec);
-  *(sl->ptr_spec) = ((spec[0] == '+' && isspace (spec[1]))
+  *(sl->ptr_spec) = ((spec[0] == '+' && ISSPACE (spec[1]))
                     ? concat (old_spec, spec + 1, NULL_PTR)
                     : save_string (spec, strlen (spec)));
 
@@ -1350,9 +1342,8 @@ store_arg (arg, delete_always, delete_failure)
      int delete_always, delete_failure;
 {
   if (argbuf_index + 1 == argbuf_length)
-    {
-      argbuf = (char **) xrealloc (argbuf, (argbuf_length *= 2) * sizeof (char *));
-    }
+    argbuf
+      = (char **) xrealloc (argbuf, (argbuf_length *= 2) * sizeof (char *));
 
   argbuf[argbuf_index++] = arg;
   argbuf[argbuf_index] = 0;
@@ -1420,17 +1411,20 @@ read_specs (filename, main_p)
       if (*p == '%' && !main_p)
        {
          p1 = p;
-         while (*p && *p != '\n') p++;
-         p++;                  /* skip \n */
+         while (*p && *p != '\n')
+           p++;
+
+         p++;                  /* Skip '\n' */
 
          if (!strncmp (p1, "%include", sizeof ("%include")-1)
-             && (p1[ sizeof ("%include")-1 ] == ' '
-                 || p1[ sizeof ("%include")-1 ] == '\t'))
+             && (p1[sizeof "%include" - 1] == ' '
+                 || p1[sizeof "%include" - 1] == '\t'))
            {
              char *new_filename;
 
              p1 += sizeof ("%include");
-             while (*p1 == ' ' || *p1 == '\t') p1++;
+             while (*p1 == ' ' || *p1 == '\t')
+               p1++;
 
              if (*p1++ != '<' || p[-2] != '>')
                fatal ("specs %%include syntax malformed after %d characters",
@@ -1441,13 +1435,13 @@ read_specs (filename, main_p)
              read_specs (new_filename ? new_filename : p1, FALSE);
              continue;
            }
-         else if (!strncmp (p1, "%include_noerr", sizeof ("%include_noerr")-1)
-             && (p1[ sizeof ("%include_noerr")-1 ] == ' '
-                 || p1[ sizeof ("%include_noerr")-1 ] == '\t'))
+         else if (!strncmp (p1, "%include_noerr", sizeof "%include_noerr" - 1)
+                  && (p1[sizeof "%include_noerr" - 1] == ' '
+                      || p1[sizeof "%include_noerr" - 1] == '\t'))
            {
              char *new_filename;
 
-             p1 += sizeof ("%include_noerr");
+             p1 += sizeof "%include_noerr";
              while (*p1 == ' ' || *p1 == '\t') p1++;
 
              if (*p1++ != '<' || p[-2] != '>')
@@ -1462,36 +1456,44 @@ read_specs (filename, main_p)
                fprintf (stderr, "Could not find specs file %s\n", p1);
              continue;
            }
-         else if (!strncmp (p1, "%rename", sizeof ("%rename")-1)
-                  && (p1[ sizeof ("%rename")-1 ] == ' '
-                      || p1[ sizeof ("%rename")-1 ] == '\t'))
+         else if (!strncmp (p1, "%rename", sizeof "%rename" - 1)
+                  && (p1[sizeof "%rename" - 1] == ' '
+                      || p1[sizeof "%rename" - 1] == '\t'))
            {
              int name_len;
              struct spec_list *sl;
 
              /* Get original name */
-             p1 += sizeof ("%rename");
-             while (*p1 == ' ' || *p1 == '\t') p1++;
-             if (!isalpha (*p1))
+             p1 += sizeof "%rename";
+             while (*p1 == ' ' || *p1 == '\t')
+               p1++;
+
+             if (! ISALPHA (*p1))
                fatal ("specs %%rename syntax malformed after %d characters",
                       p1 - buffer);
 
              p2 = p1;
-             while (*p2 && !isspace (*p2)) p2++;
+             while (*p2 && !ISSPACE (*p2))
+               p2++;
+
              if (*p2 != ' ' && *p2 != '\t')
                fatal ("specs %%rename syntax malformed after %d characters",
                       p2 - buffer);
 
              name_len = p2 - p1;
              *p2++ = '\0';
-             while (*p2 == ' ' || *p2 == '\t') p2++;
-             if (!isalpha (*p2))
+             while (*p2 == ' ' || *p2 == '\t')
+               p2++;
+
+             if (! ISALPHA (*p2))
                fatal ("specs %%rename syntax malformed after %d characters",
                       p2 - buffer);
 
              /* Get new spec name */
              p3 = p2;
-             while (*p3 && !isspace (*p3)) p3++;
+             while (*p3 && !ISSPACE (*p3))
+               p3++;
+
              if (p3 != p-1)
                fatal ("specs %%rename syntax malformed after %d characters",
                       p3 - buffer);
@@ -1504,7 +1506,7 @@ read_specs (filename, main_p)
              if (!sl)
                fatal ("specs %s spec was not found to be renamed", p1);
 
-             if (!strcmp (p1, p2))
+             if (strcmp (p1, p2) == 0)
                continue;
 
              if (verbose_flag)
@@ -1530,22 +1532,30 @@ read_specs (filename, main_p)
 
       /* Find the colon that should end the suffix.  */
       p1 = p;
-      while (*p1 && *p1 != ':' && *p1 != '\n') p1++;
+      while (*p1 && *p1 != ':' && *p1 != '\n')
+       p1++;
+
       /* The colon shouldn't be missing.  */
       if (*p1 != ':')
        fatal ("specs file malformed after %d characters", p1 - buffer);
+
       /* Skip back over trailing whitespace.  */
       p2 = p1;
-      while (p2 > buffer && (p2[-1] == ' ' || p2[-1] == '\t')) p2--;
+      while (p2 > buffer && (p2[-1] == ' ' || p2[-1] == '\t'))
+       p2--;
+
       /* Copy the suffix to a string.  */
       suffix = save_string (p, p2 - p);
       /* Find the next line.  */
       p = skip_whitespace (p1 + 1);
       if (p[1] == 0)
        fatal ("specs file malformed after %d characters", p - buffer);
+
       p1 = p;
       /* Find next blank line.  */
-      while (*p1 && !(*p1 == '\n' && p1[1] == '\n')) p1++;
+      while (*p1 && !(*p1 == '\n' && p1[1] == '\n'))
+       p1++;
+
       /* Specs end at the blank line and do not include the newline.  */
       spec = save_string (p, p1 - p);
       p = p1;
@@ -1558,9 +1568,9 @@ read_specs (filename, main_p)
          if (in[0] == '\\' && in[1] == '\n')
            in += 2;
          else if (in[0] == '#')
-           {
-             while (*in && *in != '\n') in++;
-           }
+           while (*in && *in != '\n')
+             in++;
+
          else
            *out++ = *in++;
        }
@@ -1578,7 +1588,9 @@ read_specs (filename, main_p)
          /* Add this pair to the vector.  */
          compilers
            = ((struct compiler *)
-              xrealloc (compilers, (n_compilers + 2) * sizeof (struct compiler)));
+              xrealloc (compilers,
+                        (n_compilers + 2) * sizeof (struct compiler)));
+
          compilers[n_compilers].suffix = suffix;
          bzero ((char *) compilers[n_compilers].spec,
                 sizeof compilers[n_compilers].spec);
@@ -1651,10 +1663,12 @@ record_temp_file (filename, always_delete, fail_delete)
       for (temp = always_delete_queue; temp; temp = temp->next)
        if (! strcmp (name, temp->name))
          goto already1;
+
       temp = (struct temp_file *) xmalloc (sizeof (struct temp_file));
       temp->next = always_delete_queue;
       temp->name = name;
       always_delete_queue = temp;
+
     already1:;
     }
 
@@ -1664,10 +1678,12 @@ record_temp_file (filename, always_delete, fail_delete)
       for (temp = failure_delete_queue; temp; temp = temp->next)
        if (! strcmp (name, temp->name))
          goto already2;
+
       temp = (struct temp_file *) xmalloc (sizeof (struct temp_file));
       temp->next = failure_delete_queue;
       temp->name = name;
       failure_delete_queue = temp;
+
     already2:;
     }
 }
@@ -1686,7 +1702,9 @@ delete_if_ordinary (name)
   fflush (stdout);
   i = getchar ();
   if (i != '\n')
-    while ((c = getchar ()) != '\n' && c != EOF) ;
+    while ((c = getchar ()) != '\n' && c != EOF)
+      ;
+
   if (i == 'y' || i == 'Y')
 #endif /* DEBUG */
     if (stat (name, &st) >= 0 && S_ISREG (st.st_mode))
@@ -1802,7 +1820,7 @@ build_search_list (paths, prefix, check_dir_p)
       int len = strlen (pprefix->prefix);
 
       if (machine_suffix
-         && (!check_dir_p
+         && (! check_dir_p
              || is_directory (pprefix->prefix, machine_suffix, 0)))
        {
          if (!first_time)
@@ -1815,10 +1833,10 @@ build_search_list (paths, prefix, check_dir_p)
 
       if (just_machine_suffix
          && pprefix->require_machine_suffix == 2
-         && (!check_dir_p
+         && (! check_dir_p
              || is_directory (pprefix->prefix, just_machine_suffix, 0)))
        {
-         if (!first_time)
+         if (! first_time)
            obstack_1grow (&collect_obstack, PATH_SEPARATOR);
            
          first_time = FALSE;
@@ -1827,15 +1845,16 @@ build_search_list (paths, prefix, check_dir_p)
                        just_suffix_len);
        }
 
-      if (!pprefix->require_machine_suffix)
+      if (! pprefix->require_machine_suffix)
        {
-         if (!first_time)
+         if (! first_time)
            obstack_1grow (&collect_obstack, PATH_SEPARATOR);
 
          first_time = FALSE;
          obstack_grow (&collect_obstack, pprefix->prefix, len);
        }
     }
+
   obstack_1grow (&collect_obstack, '\0');
   return obstack_finish (&collect_obstack);
 }
@@ -1873,7 +1892,10 @@ find_a_file (pprefix, name, mode)
 
   /* Determine the filename to execute (special case for absolute paths).  */
 
-  if (*name == '/' || *name == DIR_SEPARATOR)
+  if (*name == '/' || *name == DIR_SEPARATOR
+      /* Check for disk name on MS-DOS-based systems.  */
+      || (DIR_SEPARATOR == '\\' && name[1] == ':'
+         && (name[2] == DIR_SEPARATOR || name[2] == '/')))
     {
       if (access (name, mode))
        {
@@ -1947,7 +1969,7 @@ find_a_file (pprefix, name, mode)
 
        /* Certain prefixes can't be used without the machine suffix
           when the machine or version is explicitly specified.  */
-       if (!pl->require_machine_suffix)
+       if (! pl->require_machine_suffix)
          {
            /* Some systems have a suffix for executable files.
               So try appending that first.  */
@@ -1986,14 +2008,17 @@ find_a_file (pprefix, name, mode)
    through this prefix.  WARN should point to an int
    which will be set to 1 if this entry is used.
 
+   COMPONENT is the value to be passed to update_path.
+
    REQUIRE_MACHINE_SUFFIX is 1 if this prefix can't be used without
    the complete value of machine_suffix.
    2 means try both machine_suffix and just_machine_suffix.  */
 
 static void
-add_prefix (pprefix, prefix, first, require_machine_suffix, warn)
+add_prefix (pprefix, prefix, component, first, require_machine_suffix, warn)
      struct path_prefix *pprefix;
      char *prefix;
+     char *component;
      int first;
      int require_machine_suffix;
      int *warn;
@@ -2001,7 +2026,7 @@ add_prefix (pprefix, prefix, first, require_machine_suffix, warn)
   struct prefix_list *pl, **prev;
   int len;
 
-  if (!first && pprefix->plist)
+  if (! first && pprefix->plist)
     {
       for (pl = pprefix->plist; pl->next; pl = pl->next)
        ;
@@ -2012,6 +2037,7 @@ add_prefix (pprefix, prefix, first, require_machine_suffix, warn)
 
   /* Keep track of the longest prefix */
 
+  prefix = update_path (prefix, component);
   len = strlen (prefix);
   if (len > pprefix->max_len)
     pprefix->max_len = len;
@@ -2051,28 +2077,11 @@ unused_prefix_warnings (pprefix)
          /* Prevent duplicate warnings.  */
          *pl->used_flag_ptr = 1;
        }
-      pl = pl->next;
-    }
-}
-
-/* Get rid of all prefixes built up so far in *PLISTP.  */
 
-static void
-free_path_prefix (pprefix)
-     struct path_prefix *pprefix;
-{
-  struct prefix_list *pl = pprefix->plist;
-  struct prefix_list *temp;
-
-  while (pl)
-    {
-      temp = pl;
       pl = pl->next;
-      free (temp->prefix);
-      free ((char *) temp);
     }
-  pprefix->plist = (struct prefix_list *) 0;
 }
+
 \f
 /* Execute the command specified by the arguments on the current line of spec.
    When using pipes, this includes several piped-together commands
@@ -2117,7 +2126,7 @@ execute ()
   for (n_commands = 1, i = 0; i < argbuf_index; i++)
     if (strcmp (argbuf[i], "|") == 0)
       {                                /* each command.  */
-#if defined (__MSDOS__) || (defined (_WIN32) && ! defined (__CYGWIN32__)) || defined (OS2)
+#if defined (__MSDOS__) || (defined (_WIN32) && defined (__CYGWIN32_)) || defined (OS2) || defined (VMS)
         fatal ("-pipe not supported");
 #endif
        argbuf[i] = 0;  /* termination of command args.  */
@@ -2154,7 +2163,9 @@ execute ()
       fflush (stderr);
       i = getchar ();
       if (i != '\n')
-       while (getchar () != '\n') ;
+       while (getchar () != '\n')
+         ;
+
       if (i != 'y' && i != 'Y')
        return 0;
 #endif /* DEBUG */
@@ -2362,8 +2373,8 @@ process_command (argc, argv)
 
   if (gcc_exec_prefix)
     {
-      add_prefix (&exec_prefixes, gcc_exec_prefix, 0, 0, NULL_PTR);
-      add_prefix (&startfile_prefixes, gcc_exec_prefix, 0, 0, NULL_PTR);
+      add_prefix (&exec_prefixes, gcc_exec_prefix, "GCC", 0, 0, NULL_PTR);
+      add_prefix (&startfile_prefixes, gcc_exec_prefix, "GCC", 0, 0, NULL_PTR);
     }
 
   /* COMPILER_PATH and LIBRARY_PATH have values
@@ -2390,7 +2401,10 @@ process_command (argc, argv)
                }
              else
                nstore[endp-startp] = 0;
-             add_prefix (&exec_prefixes, nstore, 0, 0, NULL_PTR);
+             add_prefix (&exec_prefixes, nstore, 0, 0, 0, NULL_PTR);
+             add_prefix (&include_prefixes,
+                         concat (nstore, "include", NULL_PTR),
+                         0, 0, 0, NULL_PTR);
              if (*endp == 0)
                break;
              endp = startp = endp + 1;
@@ -2421,7 +2435,8 @@ process_command (argc, argv)
                }
              else
                nstore[endp-startp] = 0;
-             add_prefix (&startfile_prefixes, nstore, 0, 0, NULL_PTR);
+             add_prefix (&startfile_prefixes, nstore, NULL_PTR,
+                         0, 0, NULL_PTR);
              if (*endp == 0)
                break;
              endp = startp = endp + 1;
@@ -2453,7 +2468,8 @@ process_command (argc, argv)
                }
              else
                nstore[endp-startp] = 0;
-             add_prefix (&startfile_prefixes, nstore, 0, 0, NULL_PTR);
+             add_prefix (&startfile_prefixes, nstore, NULL_PTR,
+                         0, 0, NULL_PTR);
              if (*endp == 0)
                break;
              endp = startp = endp + 1;
@@ -2468,7 +2484,7 @@ process_command (argc, argv)
 
 #ifdef LANG_SPECIFIC_DRIVER
   /* Do language-specific adjustment/addition of flags.  */
-  lang_specific_driver (&fatal, &argc, &argv);
+  lang_specific_driver (fatal, &argc, &argv);
 #endif
 
   /* Scan argv twice.  Here, the first time, just count how many switches
@@ -2630,6 +2646,7 @@ process_command (argc, argv)
          switch (c)
            {
            case 'b':
+              n_switches++;
              if (p[1] == 0 && i + 1 == argc)
                fatal ("argument to `-b' is missing");
              if (p[1] == 0)
@@ -2642,7 +2659,6 @@ process_command (argc, argv)
 
            case 'B':
              {
-               int *temp = (int *) xmalloc (sizeof (int));
                char *value;
                if (p[1] == 0 && i + 1 == argc)
                  fatal ("argument to `-B' is missing");
@@ -2650,10 +2666,12 @@ process_command (argc, argv)
                  value = argv[++i];
                else
                  value = p + 1;
-               add_prefix (&exec_prefixes, value, 1, 0, &warn_B);
-               add_prefix (&startfile_prefixes, value, 1, 0, &warn_B);
-               add_prefix (&include_prefixes, concat (value, "include", NULL_PTR),
-                           1, 0, NULL_PTR);
+               add_prefix (&exec_prefixes, value, NULL_PTR, 1, 0, &warn_B);
+               add_prefix (&startfile_prefixes, value, NULL_PTR,
+                           1, 0, &warn_B);
+               add_prefix (&include_prefixes, concat (value, "include",
+                                                      NULL_PTR),
+                           NULL_PTR, 1, 0, NULL_PTR);
 
                /* As a kludge, if the arg is "[foo/]stageN/", just add
                   "[foo/]include" to the include prefix.  */
@@ -2664,23 +2682,24 @@ process_command (argc, argv)
                           && (value[len - 8] == '/'
                               || value[len - 8] == DIR_SEPARATOR)))
                      && strncmp (value + len - 7, "stage", 5) == 0
-                     && isdigit (value[len - 2])
+                     && ISDIGIT (value[len - 2])
                      && (value[len - 1] == '/'
                          || value[len - 1] == DIR_SEPARATOR))
                    {
                      if (len == 7)
-                       add_prefix (&include_prefixes, "include",
+                       add_prefix (&include_prefixes, "include", NULL_PTR,
                                    1, 0, NULL_PTR);
                      else
                        {
                          char *string = xmalloc (len + 1);
                          strncpy (string, value, len-7);
                          strcpy (string+len-7, "include");
-                         add_prefix (&include_prefixes, string,
+                         add_prefix (&include_prefixes, string, NULL_PTR,
                                      1, 0, NULL_PTR);
                        }
                    }
                }
+                n_switches++;
              }
              break;
 
@@ -2694,6 +2713,7 @@ process_command (argc, argv)
              break;
 
            case 'V':
+             n_switches++;
              if (p[1] == 0 && i + 1 == argc)
                fatal ("argument to `-V' is missing");
              if (p[1] == 0)
@@ -2749,12 +2769,16 @@ process_command (argc, argv)
   /* Use 2 as fourth arg meaning try just the machine as a suffix,
      as well as trying the machine and the version.  */
 #ifndef OS2
-  add_prefix (&exec_prefixes, standard_exec_prefix, 0, 2, warn_std_ptr);
-  add_prefix (&exec_prefixes, standard_exec_prefix_1, 0, 2, warn_std_ptr);
+  add_prefix (&exec_prefixes, standard_exec_prefix, "BINUTILS",
+             0, 2, warn_std_ptr);
+  add_prefix (&exec_prefixes, standard_exec_prefix_1, "BINUTILS",
+             0, 2, warn_std_ptr);
 #endif
 
-  add_prefix (&startfile_prefixes, standard_exec_prefix, 0, 1, warn_std_ptr);
-  add_prefix (&startfile_prefixes, standard_exec_prefix_1, 0, 1, warn_std_ptr);
+  add_prefix (&startfile_prefixes, standard_exec_prefix, "BINUTILS",
+             0, 1, warn_std_ptr);
+  add_prefix (&startfile_prefixes, standard_exec_prefix_1, "BINUTILS",
+             0, 1, warn_std_ptr);
 
   tooldir_prefix = concat (tooldir_base_prefix, spec_machine, 
                           dir_separator_str, NULL_PTR);
@@ -2777,11 +2801,11 @@ process_command (argc, argv)
          add_prefix (&exec_prefixes,
                      concat (gcc_exec_tooldir_prefix, "bin", 
                              dir_separator_str, NULL_PTR),
-                     0, 0, NULL_PTR);
+                     NULL_PTR, 0, 0, NULL_PTR);
          add_prefix (&startfile_prefixes,
                      concat (gcc_exec_tooldir_prefix, "lib", 
                              dir_separator_str, NULL_PTR),
-                     0, 0, NULL_PTR);
+                     NULL_PTR, 0, 0, NULL_PTR);
        }
 
       tooldir_prefix = concat (standard_exec_prefix, spec_machine,
@@ -2791,10 +2815,10 @@ process_command (argc, argv)
 
   add_prefix (&exec_prefixes, 
               concat (tooldir_prefix, "bin", dir_separator_str, NULL_PTR),
-             0, 0, NULL_PTR);
+             "BINUTILS", 0, 0, NULL_PTR);
   add_prefix (&startfile_prefixes,
              concat (tooldir_prefix, "lib", dir_separator_str, NULL_PTR),
-             0, 0, NULL_PTR);
+             "BINUTILS", 0, 0, NULL_PTR);
 
   /* More prefixes are enabled in main, after we read the specs file
      and determine whether this is cross-compilation or not.  */
@@ -2884,13 +2908,6 @@ process_command (argc, argv)
          register char *p = &argv[i][1];
          register int c = *p;
 
-         if (c == 'B' || c == 'b' || c == 'V')
-           {
-             /* Skip a separate arg, if any.  */
-             if (p[1] == 0)
-               i++;
-             continue;
-           }
          if (c == 'x')
            {
              if (p[1] == 0 && i + 1 == argc)
@@ -2952,6 +2969,12 @@ process_command (argc, argv)
          /* This is always valid, since gcc.c itself understands it.  */
          if (!strcmp (p, "save-temps"))
            switches[n_switches].valid = 1;
+          else
+            {
+              char ch = switches[n_switches].part1[0];
+              if (ch == 'V' || ch == 'b' || ch == 'B')
+                switches[n_switches].valid = 1;
+            }
          n_switches++;
        }
       else
@@ -3074,7 +3097,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
   char *string;
   int value;
 
-  while (c = *p++)
+  while ((c = *p++))
     /* If substituting a switch, treat all chars like letters.
        Otherwise, NL, SPC, TAB and % are special.  */
     switch (inswitch ? 'a' : c)
@@ -3323,7 +3346,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
                   In 2.4, do something about that.  */
                struct temp_name *t;
                char *suffix = p;
-               while (*p == '.' || isalpha (*p)
+               while (*p == '.' || ISALPHA (*p)
                       || (p[0] == '%' && p[1] == 'O'))
                  p++;
 
@@ -3612,7 +3635,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
                      *x++ = *y++;
 
                      if (*y != '_'
-                         || (*(y+1) != '_' && ! isupper (*(y+1))))
+                         || (*(y+1) != '_' && ! ISUPPER (*(y+1))))
                        {
                          /* Stick __ at front of macro name.  */
                          *x++ = '_';
@@ -3654,7 +3677,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
                      y += 2;
 
                      if (*y != '_'
-                         || (*(y+1) != '_' && ! isupper (*(y+1))))
+                         || (*(y+1) != '_' && ! ISUPPER (*(y+1))))
                        {
                          /* Stick -D__ at front of macro name.  */
                          *x++ = '-';
@@ -3828,7 +3851,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
                 ([^0-9]*-)?[0-9]+[.][0-9]+([.][0-9]+)?([- ].*)?  */
 
              /* Ignore leading non-digits.  i.e. "foo-" in "foo-2.7.2".  */
-             while (! isdigit (*v))
+             while (! ISDIGIT (*v))
                v++;
              if (v > compiler_version && v[-1] != '-')
                abort ();
@@ -3837,7 +3860,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
              if (c1 == '2')
                {
                  /* Set V after the first period.  */
-                 while (isdigit (*v))
+                 while (ISDIGIT (*v))
                    v++;
                  if (*v != '.')
                    abort ();
@@ -3846,7 +3869,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
 
              /* Set Q at the next period or at the end.  */
              q = v;
-             while (isdigit (*q))
+             while (ISDIGIT (*q))
                q++;
              if (*q != 0 && *q != ' ' && *q != '.' && *q != '-')
                abort ();
@@ -4302,11 +4325,6 @@ main (argc, argv)
     signal (SIGPIPE, fatal_error);
 #endif
 
-  { /* Warn users they are using developmental software.  */
-    static void snapshot_warning ();
-    snapshot_warning ();
-  }
-
   argbuf_length = 10;
   argbuf = (char **) xmalloc (argbuf_length * sizeof (char *));
 
@@ -4373,6 +4391,53 @@ main (argc, argv)
 
   process_command (argc, argv);
 
+  {
+    int i;
+    int first_time;
+
+    /* Build COLLECT_GCC_OPTIONS to have all of the options specified to
+       the compiler.  */
+    obstack_grow (&collect_obstack, "COLLECT_GCC_OPTIONS=",
+                 sizeof ("COLLECT_GCC_OPTIONS=")-1);
+
+    first_time = TRUE;
+    for (i = 0; i < n_switches; i++)
+      {
+       char **args;
+       char *p, *q;
+       if (!first_time)
+         obstack_grow (&collect_obstack, " ", 1);
+
+       first_time = FALSE;
+       obstack_grow (&collect_obstack, "'-", 2);
+        q = switches[i].part1;
+       while ((p = (char *) index (q,'\'')))
+          {
+            obstack_grow (&collect_obstack, q, p-q);
+            obstack_grow (&collect_obstack, "'\\''", 4);
+            q = ++p;
+          }
+        obstack_grow (&collect_obstack, q, strlen (q));
+       obstack_grow (&collect_obstack, "'", 1);
+
+       for (args = switches[i].args; args && *args; args++)
+         {
+           obstack_grow (&collect_obstack, " '", 2);
+           q = *args;
+           while ((p = (char *) index (q,'\'')))
+             {
+               obstack_grow (&collect_obstack, q, p-q);
+               obstack_grow (&collect_obstack, "'\\''", 4);
+               q = ++p;
+             }
+           obstack_grow (&collect_obstack, q, strlen (q));
+           obstack_grow (&collect_obstack, "'", 1);
+         }
+      }
+    obstack_grow (&collect_obstack, "\0", 1);
+    putenv (obstack_finish (&collect_obstack));
+  }
+
   /* Initialize the vector of specs to just the default.
      This means one element containing 0s, as a terminator.  */
 
@@ -4421,16 +4486,18 @@ main (argc, argv)
   if (*cross_compile == '0')
     {
 #ifdef MD_EXEC_PREFIX
-      add_prefix (&exec_prefixes, md_exec_prefix, 0, 0, NULL_PTR);
-      add_prefix (&startfile_prefixes, md_exec_prefix, 0, 0, NULL_PTR);
+      add_prefix (&exec_prefixes, md_exec_prefix, "GCC", 0, 0, NULL_PTR);
+      add_prefix (&startfile_prefixes, md_exec_prefix, "GCC", 0, 0, NULL_PTR);
 #endif
 
 #ifdef MD_STARTFILE_PREFIX
-      add_prefix (&startfile_prefixes, md_startfile_prefix, 0, 0, NULL_PTR);
+      add_prefix (&startfile_prefixes, md_startfile_prefix, "GCC",
+                 0, 0, NULL_PTR);
 #endif
 
 #ifdef MD_STARTFILE_PREFIX_1
-      add_prefix (&startfile_prefixes, md_startfile_prefix_1, 0, 0, NULL_PTR);
+      add_prefix (&startfile_prefixes, md_startfile_prefix_1, "GCC",
+                 0, 0, NULL_PTR);
 #endif
 
       /* If standard_startfile_prefix is relative, base it on
@@ -4439,28 +4506,28 @@ main (argc, argv)
         standard_startfile_prefix on that as well.  */
       if (*standard_startfile_prefix == '/'
          || *standard_startfile_prefix == DIR_SEPARATOR)
-       add_prefix (&startfile_prefixes, standard_startfile_prefix, 0, 0,
-                   NULL_PTR);
+       add_prefix (&startfile_prefixes, standard_startfile_prefix, "BINUTILS",
+                   0, 0, NULL_PTR);
       else
        {
          if (gcc_exec_prefix)
            add_prefix (&startfile_prefixes,
                        concat (gcc_exec_prefix, machine_suffix,
                                standard_startfile_prefix, NULL_PTR),
-                       0, 0, NULL_PTR);
+                       NULL_PTR, 0, 0, NULL_PTR);
          add_prefix (&startfile_prefixes,
                      concat (standard_exec_prefix,
                              machine_suffix,
                              standard_startfile_prefix, NULL_PTR),
-                     0, 0, NULL_PTR);
+                     NULL_PTR, 0, 0, NULL_PTR);
        }                      
 
-      add_prefix (&startfile_prefixes, standard_startfile_prefix_1, 0, 0,
-                 NULL_PTR);
-      add_prefix (&startfile_prefixes, standard_startfile_prefix_2, 0, 0,
-                 NULL_PTR);
+      add_prefix (&startfile_prefixes, standard_startfile_prefix_1,
+                 "BINUTILS", 0, 0, NULL_PTR);
+      add_prefix (&startfile_prefixes, standard_startfile_prefix_2,
+                 "BINUTILS", 0, 0, NULL_PTR);
 #if 0 /* Can cause surprises, and one can use -B./ instead.  */
-      add_prefix (&startfile_prefixes, "./", 0, 1, NULL_PTR);
+      add_prefix (&startfile_prefixes, "./", NULL_PTR, 0, 1, NULL_PTR);
 #endif
     }
   else
@@ -4469,7 +4536,7 @@ main (argc, argv)
        add_prefix (&startfile_prefixes,
                    concat (gcc_exec_prefix, machine_suffix,
                            standard_startfile_prefix, NULL_PTR),
-                   0, 0, NULL_PTR);
+                   "BINUTILS", 0, 0, NULL_PTR);
     }
 
   /* If we have a GCC_EXEC_PREFIX envvar, modify it for cpp's sake.  */
@@ -4668,40 +4735,12 @@ main (argc, argv)
   if (error_count == 0)
     {
       int tmp = execution_count;
-      int i;
-      int first_time;
 
       /* Rebuild the COMPILER_PATH and LIBRARY_PATH environment variables
         for collect.  */
       putenv_from_prefixes (&exec_prefixes, "COMPILER_PATH=");
       putenv_from_prefixes (&startfile_prefixes, "LIBRARY_PATH=");
 
-      /* Build COLLECT_GCC_OPTIONS to have all of the options specified to
-        the compiler.  */
-      obstack_grow (&collect_obstack, "COLLECT_GCC_OPTIONS=",
-                   sizeof ("COLLECT_GCC_OPTIONS=")-1);
-
-      first_time = TRUE;
-      for (i = 0; i < n_switches; i++)
-       {
-         char **args;
-         if (!first_time)
-           obstack_grow (&collect_obstack, " ", 1);
-
-         first_time = FALSE;
-         obstack_grow (&collect_obstack, "-", 1);
-         obstack_grow (&collect_obstack, switches[i].part1,
-                       strlen (switches[i].part1));
-
-         for (args = switches[i].args; args && *args; args++)
-           {
-             obstack_grow (&collect_obstack, " ", 1);
-             obstack_grow (&collect_obstack, *args, strlen (*args));
-           }
-       }
-      obstack_grow (&collect_obstack, "\0", 1);
-      putenv (obstack_finish (&collect_obstack));
-
       value = do_spec (link_command_spec);
       if (value < 0)
        error_count = 1;
@@ -5010,7 +5049,7 @@ validate_all_switches ()
       for (i = 0; i < sizeof comp->spec / sizeof comp->spec[0] && comp->spec[i]; i++)
        {
          p = comp->spec[i];
-         while (c = *p++)
+         while ((c = *p++))
            if (c == '%' && *p == '{')
              /* We have a switch spec.  */
              validate_switches (p + 1);
@@ -5021,14 +5060,14 @@ validate_all_switches ()
   for (spec = specs; spec ; spec = spec->next)
     {
       p = *(spec->ptr_spec);
-      while (c = *p++)
+      while ((c = *p++))
        if (c == '%' && *p == '{')
          /* We have a switch spec.  */
          validate_switches (p + 1);
     }
 
   p = link_command_spec;
-  while (c = *p++)
+  while ((c = *p++))
     if (c == '%' && *p == '{')
       /* We have a switch spec.  */
       validate_switches (p + 1);
@@ -5081,7 +5120,7 @@ validate_switches (start)
 }
 \f
 /* Check whether a particular argument was used.  The first time we
-   canonialize the switches to keep only the ones we care about.  */
+   canonicalize the switches to keep only the ones we care about.  */
 
 static int
 used_arg (p, len)
@@ -5177,7 +5216,6 @@ default_arg (p, len)
      int len;
 {
   char *start, *end;
-  int i;
 
   for (start = multilib_defaults; *start != '\0'; start = end+1)
     {
@@ -5446,58 +5484,3 @@ print_multilib_info ()
       ++p;
     }
 }
-\f
-/* For snapshots only.
-   Warn the user that this version of gcc is for testing and developing only.
-   If this is unix, we can restrict the warning to once per day.
-   Otherwise always issue it.  */
-
-#define TIMESTAMP_FILE ".gcc-test-time"
-#define ONE_DAY (24*60*60)
-
-static void
-snapshot_warning ()
-{
-  char *home;
-  int print_p = 1;
-
-#ifdef unix
-  home = getenv ("HOME");
-  if (home != NULL)
-    {
-      char *file_name = (char *) alloca (strlen (home) + 1 + sizeof (TIMESTAMP_FILE));
-      struct stat statbuf;
-      time_t now = time (NULL);
-      int s;
-
-      sprintf (file_name, "%s/%s", home, TIMESTAMP_FILE);
-      s = stat (file_name, &statbuf);
-      if (s == 0
-         && (statbuf.st_mtime + ONE_DAY > now))
-       print_p = 0;
-      else
-       {
-         FILE *f;
-
-         if ((f = fopen (file_name, "w")) == NULL)
-           {
-             /* Ensure we have write access.  */
-             chmod (file_name, s == 0 ? (statbuf.st_mode + 0200) : 0644);
-             f = fopen (file_name, "w");
-           }
-         if (f != NULL)
-           {
-             fputc ('\n', f);
-             fclose (f);
-           }
-       }
-    }
-#endif
-
-  if (print_p)
-    {
-      fprintf (stderr, "*** This is a development snapshot of GCC.\n");
-      fprintf (stderr, "*** It is not reliable release, and the GCC developers\n");
-      fprintf (stderr, "*** warn you not to use it for anything except to test it.\n");
-    }
-}