OSDN Git Service

* Makefile.in (gcc.o, gccspec.o, cppspec.o): Depend on gcc.h.
[pf3gnuchains/gcc-fork.git] / gcc / gcc.c
index d269395..ff61c1c 100644 (file)
--- a/gcc/gcc.c
+++ b/gcc/gcc.c
@@ -30,14 +30,15 @@ and deleting the temporary files at the end.
 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 "config.h"
 #include "system.h"
 #include <signal.h>
-
 #include "obstack.h"
 #include "intl.h"
 #include "prefix.h"
+#include "gcc.h"
 
 #ifdef VMS
 #define exit __posix_exit
@@ -66,6 +67,14 @@ compilation is specified by a string called a "spec".  */
 #define DIR_SEPARATOR '/'
 #endif
 
+/* Define IS_DIR_SEPARATOR.  */
+#ifndef DIR_SEPARATOR_2
+# define IS_DIR_SEPARATOR(ch) ((ch) == DIR_SEPARATOR)
+#else /* DIR_SEPARATOR_2 */
+# define IS_DIR_SEPARATOR(ch) \
+       (((ch) == DIR_SEPARATOR) || ((ch) == DIR_SEPARATOR_2))
+#endif /* DIR_SEPARATOR_2 */
+
 static char dir_separator_str[] = {DIR_SEPARATOR, 0};
 
 #define obstack_chunk_alloc xmalloc
@@ -92,11 +101,11 @@ static int print_search_dirs;
 /* Flag saying to print the full filename of this file
    as found through our usual search mechanism.  */
 
-static char *print_file_name = NULL;
+static const char *print_file_name = NULL;
 
 /* As print_file_name, but search for executable file.  */
 
-static char *print_prog_name = NULL;
+static const char *print_prog_name = NULL;
 
 /* Flag saying to print the relative path we'd use to
    find libgcc.a given the current compiler flags.  */
@@ -132,7 +141,7 @@ static char *spec_version = DEFAULT_TARGET_VERSION;
 
 /* The target machine specified with -b.  */
 
-static char *spec_machine = DEFAULT_TARGET_MACHINE;
+static const char *spec_machine = DEFAULT_TARGET_MACHINE;
 
 /* Nonzero if cross-compiling.
    When -b is used, the value comes from the `specs' file.  */
@@ -164,57 +173,51 @@ extern char *version_string;
 struct path_prefix;
 
 static void init_spec          PROTO((void));
-static void read_specs         PROTO((char *, int));
-static void set_spec           PROTO((char *, char *));
-static struct compiler *lookup_compiler PROTO((char *, size_t, 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 read_specs         PROTO((const char *, int));
+static void set_spec           PROTO((const char *, const char *));
+static struct compiler *lookup_compiler PROTO((const char *, size_t, const char *));
+static char *build_search_list PROTO((struct path_prefix *, const char *, int));
+static void putenv_from_prefixes PROTO((struct path_prefix *, const char *));
+static int access_check                PROTO((const char *, int));
+static char *find_a_file       PROTO((struct path_prefix *, const char *, int));
 static void add_prefix         PROTO((struct path_prefix *, const char *,
                                       const 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 *));
+static void record_temp_file   PROTO((const char *, int, int));
+static void delete_if_ordinary PROTO((const char *));
 static void delete_temp_files  PROTO((void));
 static void delete_failure_queue PROTO((void));
 static void clear_failure_queue PROTO((void));
 static int check_live_switch   PROTO((int, int));
-static char *handle_braces     PROTO((char *));
+static const char *handle_braces PROTO((const char *));
 static char *save_string       PROTO((const char *, int));
-extern int do_spec             PROTO((char *));
-static int do_spec_1           PROTO((char *, int, char *));
-static char *find_file         PROTO((char *));
-static int is_directory                PROTO((char *, char *, int));
-static void validate_switches  PROTO((char *));
+static int do_spec_1           PROTO((const char *, int, const char *));
+static const char *find_file   PROTO((const char *));
+static int is_directory                PROTO((const char *, const char *, int));
+static void validate_switches  PROTO((const char *));
 static void validate_all_switches PROTO((void));
 static void give_switch                PROTO((int, int, int));
-static int used_arg            PROTO((char *, int));
-static int default_arg         PROTO((char *, int));
+static int used_arg            PROTO((const char *, int));
+static int default_arg         PROTO((const char *, int));
 static void set_multilib_dir   PROTO((void));
 static void print_multilib_info        PROTO((void));
-static void pfatal_with_name   PROTO((char *)) ATTRIBUTE_NORETURN;
-static void perror_with_name   PROTO((char *));
-static void pfatal_pexecute    PROTO((char *, char *)) ATTRIBUTE_NORETURN;
-static void fatal              PVPROTO((char *, ...)) ATTRIBUTE_NORETURN;
-static void error              PVPROTO((char *, ...));
-static void fatal              PVPROTO((char *, ...))
-  ATTRIBUTE_NORETURN ATTRIBUTE_PRINTF_1;
-static void error              PVPROTO((char *, ...)) ATTRIBUTE_PRINTF_1;
-static void notice             PVPROTO((char *, ...));
+static void pfatal_with_name   PROTO((const char *)) ATTRIBUTE_NORETURN;
+static void perror_with_name   PROTO((const char *));
+static void pfatal_pexecute    PROTO((const char *, const char *))
+  ATTRIBUTE_NORETURN;
+static void error              PVPROTO((const char *, ...))
+  ATTRIBUTE_PRINTF_1;
+static void notice             PVPROTO((const char *, ...))
+  ATTRIBUTE_PRINTF_1;
 static void display_help       PROTO((void));
-
-void fancy_abort               PROTO((void)) ATTRIBUTE_NORETURN;
-
-#ifdef LANG_SPECIFIC_DRIVER
-/* Called before processing to change/add/remove arguments. */
-extern void lang_specific_driver PROTO ((void (*) PVPROTO((char *, ...)), int *, char ***, int *));
-
-/* Called before linking.  Returns 0 on success and -1 on failure. */
-extern int lang_specific_pre_link ();
-
-/* Number of extra output files that lang_specific_pre_link may generate. */
-extern int lang_specific_extra_outfiles;
-#endif
+static void add_preprocessor_option    PROTO ((const char *, int));
+static void add_assembler_option       PROTO ((const char *, int));
+static void add_linker_option          PROTO ((const char *, int));
+static void process_command            PROTO ((int, char **));
+static int execute                     PROTO ((void));
+static void unused_prefix_warnings     PROTO ((struct path_prefix *));
+static void clear_args                 PROTO ((void));
+static void fatal_error                        PROTO ((int));
 \f
 /* Specs are strings containing lines, each of which (if not blank)
 is made up of a program name, and arguments separated by spaces.
@@ -486,11 +489,11 @@ static char *multilib_defaults;
 #define MULTILIB_DEFAULTS { "" }
 #endif
 
-static char *multilib_defaults_raw[] = MULTILIB_DEFAULTS;
+static const  char *const multilib_defaults_raw[] = MULTILIB_DEFAULTS;
 
 struct user_specs {
   struct user_specs *next;
-  char *filename;
+  const char *filename;
 };
 
 static struct user_specs *user_specs_head, *user_specs_tail;
@@ -538,10 +541,10 @@ static struct user_specs *user_specs_head, *user_specs_tail;
 
 struct compiler
 {
-  char *suffix;                        /* Use this compiler for input files
+  const char *suffix;          /* Use this compiler for input files
                                   whose names end in this suffix.  */
 
-  char *spec[4];               /* To use this compiler, concatenate these
+  const char *spec[4];         /* To use this compiler, concatenate these
                                   specs and pass to do_spec.  */
 };
 
@@ -581,13 +584,14 @@ static struct compiler default_compilers[] =
    {
 #if USE_CPPLIB
      "%{E|M|MM:cpp -lang-c %{ansi:-std=c89} %{std*} %{nostdinc*}\
-       %{C} %{v} %{A*} %{I*} %{P} %I\
+       %{C} %{v} %{A*} %{I*} %{P} %{$} %I\
        %{C:%{!E:%eGNU C does not support -C without using -E}}\
        %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d} %{MG}\
-        -undef -D__GNUC__=%v1 -D__GNUC_MINOR__=%v2\
+        %{!no-gcc:-D__GNUC__=%v1 -D__GNUC_MINOR__=%v2}\
        %{ansi|std=*:%{!std=gnu*:-trigraphs -D__STRICT_ANSI__}}\
        %{!undef:%{!ansi:%{!std=*:%p}%{std=gnu*:%p}} %P} %{trigraphs}\
         %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+       %{ffast-math:-D__FAST_MATH__}\
         %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{fleading-underscore} %{fno-leading-underscore}\
@@ -597,10 +601,11 @@ static struct compiler default_compilers[] =
                   %{std*} %{nostdinc*} %{A*} %{I*} %I\
                   %{!Q:-quiet} -dumpbase %b.c %{d*} %{m*} %{a*}\
                   %{MD:-MD %b.d} %{MMD:-MMD %b.d} %{MG}\
-                  -undef -D__GNUC__=%v1 -D__GNUC_MINOR__=%v2\
+                  %{!no-gcc:-D__GNUC__=%v1 -D__GNUC_MINOR__=%v2}\
                  %{ansi|std=*:%{!std=gnu*:-trigraphs -D__STRICT_ANSI__}}\
                  %{!undef:%{!ansi:%{!std=*:%p}%{std=gnu*:%p}} %P} %{trigraphs}\
                   %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+                 %{ffast-math:-D__FAST_MATH__}\
                   %{H} %C %{D*} %{U*} %{i*} %Z\
                   %{ftraditional:-traditional}\
                   %{traditional-cpp:-traditional}\
@@ -613,16 +618,16 @@ static struct compiler default_compilers[] =
                   %{!S:as %a %Y\
                     %{c:%W{o*}%{!o*:-o %w%b%O}}%{!c:-o %d%w%u%O}\
                      %{!pipe:%g.s} %A\n }}}}"
-  }},
 #else /* ! USE_CPPLIB */
     "cpp -lang-c %{ansi:-std=c89} %{std*} %{nostdinc*}\
-       %{C} %{v} %{A*} %{I*} %{P} %I\
+       %{C} %{v} %{A*} %{I*} %{P} %{$} %I\
        %{C:%{!E:%eGNU C does not support -C without using -E}}\
        %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d} %{MG}\
-        -undef -D__GNUC__=%v1 -D__GNUC_MINOR__=%v2\
+        %{!no-gcc:-D__GNUC__=%v1 -D__GNUC_MINOR__=%v2}\
        %{ansi|std=*:%{!std=gnu*:-trigraphs -D__STRICT_ANSI__}}\
        %{!undef:%{!ansi:%{!std=*:%p}%{std=gnu*:%p}} %P} %{trigraphs}\
         %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+       %{ffast-math:-D__FAST_MATH__}\
         %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{fleading-underscore} %{fno-leading-underscore}\
@@ -639,17 +644,18 @@ static struct compiler default_compilers[] =
               %{!S:as %a %Y\
                      %{c:%W{o*}%{!o*:-o %w%b%O}}%{!c:-o %d%w%u%O}\
                       %{!pipe:%g.s} %A\n }}}}"
-  }},
 #endif /* ! USE_CPPLIB */
+  }},
   {"-",
    {"%{E:cpp -lang-c %{ansi:-std=c89} %{std*} %{nostdinc*}\
-       %{C} %{v} %{A*} %{I*} %{P} %I\
+       %{C} %{v} %{A*} %{I*} %{P} %{$} %I\
        %{C:%{!E:%eGNU C does not support -C without using -E}}\
        %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d} %{MG}\
-        -undef -D__GNUC__=%v1 -D__GNUC_MINOR__=%v2\
+        %{!no-gcc:-D__GNUC__=%v1 -D__GNUC_MINOR__=%v2}\
        %{ansi|std=*:%{!std=gnu*:-trigraphs -D__STRICT_ANSI__}}\
        %{!undef:%{!ansi:%{!std=*:%p}%{std=gnu*:%p}} %P} %{trigraphs}\
         %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+       %{ffast-math:-D__FAST_MATH__}\
         %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{fleading-underscore} %{fno-leading-underscore}\
@@ -659,13 +665,14 @@ static struct compiler default_compilers[] =
   {".h", {"@c-header"}},
   {"@c-header",
    {"%{!E:%eCompilation of header file requested} \
-    cpp %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %I\
+    cpp %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %{$} %I\
        %{C:%{!E:%eGNU C does not support -C without using -E}}\
-        %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d} %{MG}\
-        -undef -D__GNUC__=%v1 -D__GNUC_MINOR__=%v2\
+       %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d} %{MG}\
+        %{!no-gcc:-D__GNUC__=%v1 -D__GNUC_MINOR__=%v2}\
        %{std=*:%{!std=gnu*:-trigraphs -D__STRICT_ANSI__}}\
        %{!undef:%{!std=*:%p}%{std=gnu*:%p} %P} %{trigraphs}\
         %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+       %{ffast-math:-D__FAST_MATH__}\
         %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{fleading-underscore} %{fno-leading-underscore}\
@@ -676,7 +683,7 @@ static struct compiler default_compilers[] =
    {"%{!M:%{!MM:%{!E:cc1 %i %1 %{!Q:-quiet} %{d*} %{m*} %{a*}\
                        %{g*} %{O*} %{W*} %{w} %{pedantic*} %{std*}\
                        %{traditional} %{v:-version} %{pg:-p} %{p} %{f*}\
-                       %{aux-info*} %{Qn:-fno-ident}\
+                       %{aux-info*} %{Qn:-fno-ident} -fpreprocessed\
                        %{pg:%{fomit-frame-pointer:%e-pg and -fomit-frame-pointer are incompatible}}\
                        %{S:%W{o*}%{!o*:-o %b.s}}%{!S:-o %{|!pipe:%g.s}} |\n\
                     %{!S:as %a %Y\
@@ -689,11 +696,12 @@ static struct compiler default_compilers[] =
                            %i %A\n }}}}"}},
   {".S", {"@assembler-with-cpp"}},
   {"@assembler-with-cpp",
-   {"cpp -lang-asm %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %I\
+   {"cpp -lang-asm %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %{$} %I\
        %{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__ \
+        -$ %{!undef:%p %P} -D__ASSEMBLER__ \
         %c %{Os:-D__OPTIMIZE_SIZE__} %{O*:%{!O0:-D__OPTIMIZE__}}\
+       %{ffast-math:-D__FAST_MATH__}\
         %{traditional} %{ftraditional:-traditional}\
         %{traditional-cpp:-traditional}\
        %{fleading-underscore} %{fno-leading-underscore}\
@@ -723,12 +731,12 @@ static int n_default_compilers
 #ifdef LINK_COMMAND_SPEC
 /* Provide option to override link_command_spec from machine specific
    configuration files.  */
-static char *link_command_spec = 
+static const char *link_command_spec = 
        LINK_COMMAND_SPEC;
 #else
 #ifdef LINK_LIBGCC_SPECIAL
 /* Don't generate -L options.  */
-static char *link_command_spec = "\
+static const char *link_command_spec = "\
 %{!fsyntax-only: \
  %{!c:%{!M:%{!MM:%{!E:%{!S:%(linker) %l %X %{o*} %{A} %{d} %{e*} %{m} %{N} %{n} \
                        %{r} %{s} %{t} %{u*} %{x} %{z} %{Z}\
@@ -740,7 +748,7 @@ static char *link_command_spec = "\
                        \n }}}}}}";
 #else
 /* Use -L.  */
-static char *link_command_spec = "\
+static const char *link_command_spec = "\
 %{!fsyntax-only: \
  %{!c:%{!M:%{!MM:%{!E:%{!S:%(linker) %l %X %{o*} %{A} %{d} %{e*} %{m} %{N} %{n} \
                        %{r} %{s} %{t} %{u*} %{x} %{z} %{Z}\
@@ -777,15 +785,15 @@ static char **preprocessor_options;
 struct option_map
 {
   /* The long option's name.  */
-  char *name;
+  const char *name;
   /* The equivalent short option.  */
-  char *equivalent;
+  const char *equivalent;
   /* Argument info.  A string of flag chars; NULL equals no options.
      a => argument required.
      o => argument optional.
      j => join argument to equivalent, making one word.
      * => require other text after NAME as an argument.  */
-  char *arg_info;
+  const char *arg_info;
 };
 
 /* This is the table of mappings.  Mappings are tried sequentially
@@ -877,12 +885,13 @@ struct option_map option_map[] =
 static void
 translate_options (argcp, argvp)
      int *argcp;
-     char ***argvp;
+     const char ***argvp;
 {
   int i;
   int argc = *argcp;
-  char **argv = *argvp;
-  char **newv = (char **) xmalloc ((argc + 2) * 2 * sizeof (char *));
+  const char **argv = *argvp;
+  const char **newv =
+    (const char **) xmalloc ((argc + 2) * 2 * sizeof (const char *));
   int newindex = 0;
 
   i = 0;
@@ -900,14 +909,14 @@ translate_options (argcp, argvp)
              size_t optlen = strlen (option_map[j].name);
              size_t arglen = strlen (argv[i]);
              size_t complen = arglen > optlen ? optlen : arglen;
-             char *arginfo = option_map[j].arg_info;
+             const char *arginfo = option_map[j].arg_info;
 
              if (arginfo == 0)
                arginfo = "";
 
              if (!strncmp (argv[i], option_map[j].name, complen))
                {
-                 char *arg = 0;
+                 const char *arg = 0;
 
                  if (arglen < optlen)
                    {
@@ -996,7 +1005,7 @@ translate_options (argcp, argvp)
         with their arguments.  */
       else if (argv[i][0] == '-')
        {
-         char *p = argv[i] + 1;
+         const char *p = argv[i] + 1;
          int c = *p;
          int nskip = 1;
 
@@ -1033,26 +1042,6 @@ translate_options (argcp, argvp)
   *argcp = newindex;
 }
 \f
-char *
-xstrerror(e)
-     int e;
-{
-#ifdef HAVE_STRERROR
-
-  return strerror(e);
-
-#else
-
-  if (!e)
-    return "errno = 0";
-
-  if (e > 0 && e < sys_nerr)
-    return sys_errlist[e];
-
-  return "errno = ?";
-#endif
-}
-\f
 static char *
 skip_whitespace (p)
      char *p;
@@ -1158,10 +1147,8 @@ init_spec ()
 
 #ifdef EXTRA_SPECS
   extra_specs = (struct spec_list *)
-    xmalloc (sizeof(struct spec_list) *
+    xcalloc (sizeof(struct spec_list),
             (sizeof(extra_specs_1)/sizeof(extra_specs_1[0])));
-  bzero ((PTR) extra_specs, sizeof(struct spec_list) *
-        (sizeof(extra_specs_1)/sizeof(extra_specs_1[0])));
   
   for (i = (sizeof(extra_specs_1) / sizeof(extra_specs_1[0])) - 1; i >= 0; i--)
     {
@@ -1192,8 +1179,8 @@ init_spec ()
 
 static void
 set_spec (name, spec)
-     char *name;
-     char *spec;
+     const char *name;
+     const char *spec;
 {
   struct spec_list *sl;
   char *old_spec;
@@ -1223,7 +1210,7 @@ set_spec (name, spec)
     {
       /* Not found - make it */
       sl = (struct spec_list *) xmalloc (sizeof (struct spec_list));
-      sl->name = save_string (name, strlen (name));
+      sl->name = xstrdup (name);
       sl->name_len = name_len;
       sl->ptr_spec = &sl->ptr;
       sl->alloc_p = 0;
@@ -1235,7 +1222,7 @@ set_spec (name, spec)
   old_spec = *(sl->ptr_spec);
   *(sl->ptr_spec) = ((spec[0] == '+' && ISSPACE ((unsigned char)spec[1]))
                     ? concat (old_spec, spec + 1, NULL_PTR)
-                    : save_string (spec, strlen (spec)));
+                    : xstrdup (spec));
 
 #ifdef DEBUG_SPECS
   if (verbose_flag)
@@ -1268,16 +1255,16 @@ static int argbuf_index;
 
 #ifdef MKTEMP_EACH_FILE
 
-extern char *make_temp_file PROTO((char *));
+extern char *make_temp_file PROTO((const char *));
 
 /* This is the list of suffixes and codes (%g/%u/%U) and the associated
    temp file.  */
 
 static struct temp_name {
-  char *suffix;                /* suffix associated with the code.  */
+  const char *suffix;  /* suffix associated with the code.  */
   int length;          /* strlen (suffix).  */
   int unique;          /* Indicates whether %g or %u/%U was used.  */
-  char *filename;      /* associated filename.  */
+  const char *filename;        /* associated filename.  */
   int filename_length; /* strlen (filename).  */
   struct temp_name *next;
 } *temp_names;
@@ -1294,7 +1281,7 @@ static int signal_count;
 
 /* Name with which this program was invoked.  */
 
-static char *programname;
+static const char *programname;
 \f
 /* Structures to keep track of prefixes to try when looking for files.  */
 
@@ -1311,7 +1298,7 @@ struct path_prefix
 {
   struct prefix_list *plist;  /* List of prefixes to try */
   int max_len;                /* Max length of a prefix in PLIST */
-  char *name;                 /* Name of this list (used in config stuff) */
+  const char *name;           /* Name of this list (used in config stuff) */
 };
 
 /* List of prefixes to try when looking for executables.  */
@@ -1329,16 +1316,16 @@ static struct path_prefix include_prefixes = { 0, 0, "include" };
 /* Suffix to attach to directories searched for commands.
    This looks like `MACHINE/VERSION/'.  */
 
-static char *machine_suffix = 0;
+static const char *machine_suffix = 0;
 
 /* Suffix to attach to directories searched for commands.
    This is just `MACHINE/'.  */
 
-static char *just_machine_suffix = 0;
+static const char *just_machine_suffix = 0;
 
 /* Adjusted value of GCC_EXEC_PREFIX envvar.  */
 
-static char *gcc_exec_prefix;
+static const char *gcc_exec_prefix;
 
 /* Default prefixes to attach to command names.  */
 
@@ -1352,10 +1339,10 @@ static char *gcc_exec_prefix;
 #define STANDARD_EXEC_PREFIX "/usr/local/lib/gcc-lib/"
 #endif /* !defined STANDARD_EXEC_PREFIX */
 
-static char *standard_exec_prefix = STANDARD_EXEC_PREFIX;
-static char *standard_exec_prefix_1 = "/usr/lib/gcc/";
+static const char *standard_exec_prefix = STANDARD_EXEC_PREFIX;
+static const char *standard_exec_prefix_1 = "/usr/lib/gcc/";
 #ifdef MD_EXEC_PREFIX
-static char *md_exec_prefix = MD_EXEC_PREFIX;
+static const char *md_exec_prefix = MD_EXEC_PREFIX;
 #endif
 
 #ifndef STANDARD_STARTFILE_PREFIX
@@ -1363,25 +1350,25 @@ static char *md_exec_prefix = MD_EXEC_PREFIX;
 #endif /* !defined STANDARD_STARTFILE_PREFIX */
 
 #ifdef MD_STARTFILE_PREFIX
-static char *md_startfile_prefix = MD_STARTFILE_PREFIX;
+static const char *md_startfile_prefix = MD_STARTFILE_PREFIX;
 #endif
 #ifdef MD_STARTFILE_PREFIX_1
-static char *md_startfile_prefix_1 = MD_STARTFILE_PREFIX_1;
+static const char *md_startfile_prefix_1 = MD_STARTFILE_PREFIX_1;
 #endif
-static char *standard_startfile_prefix = STANDARD_STARTFILE_PREFIX;
-static char *standard_startfile_prefix_1 = "/lib/";
-static char *standard_startfile_prefix_2 = "/usr/lib/";
+static const char *standard_startfile_prefix = STANDARD_STARTFILE_PREFIX;
+static const char *standard_startfile_prefix_1 = "/lib/";
+static const char *standard_startfile_prefix_2 = "/usr/lib/";
 
 #ifndef TOOLDIR_BASE_PREFIX
 #define TOOLDIR_BASE_PREFIX "/usr/local/"
 #endif
-static char *tooldir_base_prefix = TOOLDIR_BASE_PREFIX;
-static char *tooldir_prefix;
+static const char *tooldir_base_prefix = TOOLDIR_BASE_PREFIX;
+static const char *tooldir_prefix;
 
 /* Subdirectory to use for locating libraries.  Set by
    set_multilib_dir based on the compilation options.  */
 
-static char *multilib_dir;
+static const char *multilib_dir;
 
 /* Clear out the vector of arguments (after a command is executed).  */
 
@@ -1427,7 +1414,7 @@ store_arg (arg, delete_always, delete_failure)
 
 static void
 read_specs (filename, main_p)
-     char *filename;
+     const char *filename;
      int main_p;
 {
   int desc;
@@ -1656,12 +1643,11 @@ read_specs (filename, main_p)
                         (n_compilers + 2) * sizeof (struct compiler)));
 
          compilers[n_compilers].suffix = suffix;
-         bzero ((char *) compilers[n_compilers].spec,
-                sizeof compilers[n_compilers].spec);
+         memset (compilers[n_compilers].spec, 0,
+                 sizeof compilers[n_compilers].spec);
          compilers[n_compilers].spec[0] = spec;
          n_compilers++;
-         bzero ((char *) &compilers[n_compilers],
-                sizeof compilers[n_compilers]);
+         memset (&compilers[n_compilers], 0, sizeof compilers[n_compilers]);
        }
 
       if (*suffix == 0)
@@ -1686,7 +1672,7 @@ read_specs (filename, main_p)
    otherwise, in /usr/tmp or /tmp;
    or finally the current directory if all else fails.  */
 
-static char *temp_filename;
+static const char *temp_filename;
 
 /* Length of the prefix.  */
 
@@ -1696,7 +1682,7 @@ static int temp_filename_length;
 
 struct temp_file
 {
-  char *name;
+  const char *name;
   struct temp_file *next;
 };
 
@@ -1713,13 +1699,11 @@ static struct temp_file *failure_delete_queue;
 
 static void
 record_temp_file (filename, always_delete, fail_delete)
-     char *filename;
+     const char *filename;
      int always_delete;
      int fail_delete;
 {
-  register char *name;
-  name = xmalloc (strlen (filename) + 1);
-  strcpy (name, filename);
+  register char * const name = xstrdup (filename);
 
   if (always_delete)
     {
@@ -1756,7 +1740,7 @@ record_temp_file (filename, always_delete, fail_delete)
 
 static void
 delete_if_ordinary (name)
-     char *name;
+     const char *name;
 {
   struct stat st;
 #ifdef DEBUG
@@ -1868,7 +1852,7 @@ putenv (str)
 static char *
 build_search_list (paths, prefix, check_dir_p)
      struct path_prefix *paths;
-     char *prefix;
+     const char *prefix;
      int check_dir_p;
 {
   int suffix_len = (machine_suffix) ? strlen (machine_suffix) : 0;
@@ -1929,11 +1913,31 @@ build_search_list (paths, prefix, check_dir_p)
 static void
 putenv_from_prefixes (paths, env_var)
      struct path_prefix *paths;
-     char *env_var;
+     const char *env_var;
 {
   putenv (build_search_list (paths, env_var, 1));
 }
 \f
+/* Check whether NAME can be accessed in MODE.  This is like access,
+   except that it never considers directories to be executable.  */
+
+static int
+access_check (name, mode)
+     const char *name;
+     int mode;
+{
+  if (mode == X_OK)
+    {
+      struct stat st;
+
+      if (stat (name, &st) < 0
+         || S_ISDIR (st.st_mode))
+       return -1;
+    }
+
+  return access (name, mode);
+}
+
 /* Search for NAME using the prefix list PREFIXES.  MODE is passed to
    access to check permissions.
    Return 0 if not found, otherwise return its name, allocated with malloc.  */
@@ -1941,32 +1945,22 @@ putenv_from_prefixes (paths, env_var)
 static char *
 find_a_file (pprefix, name, mode)
      struct path_prefix *pprefix;
-     char *name;
+     const char *name;
      int mode;
 {
   char *temp;
-  char *file_suffix = ((mode & X_OK) != 0 ? EXECUTABLE_SUFFIX : "");
+  const char *file_suffix = ((mode & X_OK) != 0 ? EXECUTABLE_SUFFIX : "");
   struct prefix_list *pl;
   int len = pprefix->max_len + strlen (name) + strlen (file_suffix) + 1;
 
 #ifdef DEFAULT_ASSEMBLER
-  if (! strcmp(name, "as") && access (DEFAULT_ASSEMBLER, mode) == 0) {
-    name = DEFAULT_ASSEMBLER;
-    len = strlen(name)+1;
-    temp = xmalloc (len);
-    strcpy (temp, name);
-    return temp;
-  }
+  if (! strcmp(name, "as") && access (DEFAULT_ASSEMBLER, mode) == 0)
+    return xstrdup (DEFAULT_ASSEMBLER);
 #endif
 
 #ifdef DEFAULT_LINKER
-  if (! strcmp(name, "ld") && access (DEFAULT_LINKER, mode) == 0) {
-    name = DEFAULT_LINKER;
-    len = strlen(name)+1;
-    temp = xmalloc (len);
-    strcpy (temp, name);
-    return temp;
-  }
+  if (! strcmp(name, "ld") && access (DEFAULT_LINKER, mode) == 0)
+    return xstrdup (DEFAULT_LINKER);
 #endif
 
   if (machine_suffix)
@@ -1976,10 +1970,12 @@ find_a_file (pprefix, name, mode)
 
   /* Determine the filename to execute (special case for absolute paths).  */
 
-  if (*name == '/' || *name == DIR_SEPARATOR
+  if (IS_DIR_SEPARATOR (*name)
+#ifdef HAVE_DOS_BASED_FILESYSTEM
       /* Check for disk name on MS-DOS-based systems.  */
-      || (DIR_SEPARATOR == '\\' && name[1] == ':'
-         && (name[2] == DIR_SEPARATOR || name[2] == '/')))
+      || (name[0] && name[1] == ':' && IS_DIR_SEPARATOR (name[2]))
+#endif
+      )
     {
       if (access (name, mode) == 0)
        {
@@ -2000,7 +1996,7 @@ find_a_file (pprefix, name, mode)
                strcat (temp, machine_suffix);
                strcat (temp, name);
                strcat (temp, file_suffix);
-               if (access (temp, mode) == 0)
+               if (access_check (temp, mode) == 0)
                  {
                    if (pl->used_flag_ptr != 0)
                      *pl->used_flag_ptr = 1;
@@ -2012,7 +2008,7 @@ find_a_file (pprefix, name, mode)
            strcpy (temp, pl->prefix);
            strcat (temp, machine_suffix);
            strcat (temp, name);
-           if (access (temp, mode) == 0)
+           if (access_check (temp, mode) == 0)
              {
                if (pl->used_flag_ptr != 0)
                  *pl->used_flag_ptr = 1;
@@ -2032,7 +2028,7 @@ find_a_file (pprefix, name, mode)
                strcat (temp, just_machine_suffix);
                strcat (temp, name);
                strcat (temp, file_suffix);
-               if (access (temp, mode) == 0)
+               if (access_check (temp, mode) == 0)
                  {
                    if (pl->used_flag_ptr != 0)
                      *pl->used_flag_ptr = 1;
@@ -2043,7 +2039,7 @@ find_a_file (pprefix, name, mode)
            strcpy (temp, pl->prefix);
            strcat (temp, just_machine_suffix);
            strcat (temp, name);
-           if (access (temp, mode) == 0)
+           if (access_check (temp, mode) == 0)
              {
                if (pl->used_flag_ptr != 0)
                  *pl->used_flag_ptr = 1;
@@ -2062,7 +2058,7 @@ find_a_file (pprefix, name, mode)
                strcpy (temp, pl->prefix);
                strcat (temp, name);
                strcat (temp, file_suffix);
-               if (access (temp, mode) == 0)
+               if (access_check (temp, mode) == 0)
                  {
                    if (pl->used_flag_ptr != 0)
                      *pl->used_flag_ptr = 1;
@@ -2072,7 +2068,7 @@ find_a_file (pprefix, name, mode)
 
            strcpy (temp, pl->prefix);
            strcat (temp, name);
-           if (access (temp, mode) == 0)
+           if (access_check (temp, mode) == 0)
              {
                if (pl->used_flag_ptr != 0)
                  *pl->used_flag_ptr = 1;
@@ -2181,8 +2177,8 @@ execute ()
   char *string;
   struct command
     {
-      char *prog;              /* program name.  */
-      char **argv;             /* vector of args.  */
+      const char *prog;                /* program name.  */
+      char **argv;     /* vector of args.  */
       int pid;                 /* pid of process for this command.  */
     };
 
@@ -2341,7 +2337,7 @@ execute ()
 
 struct switchstr
 {
-  char *part1;
+  const char *part1;
   char **args;
   int live_cond;
   int validated;
@@ -2353,8 +2349,8 @@ static int n_switches;
 
 struct infile
 {
-  char *name;
-  char *language;
+  const char *name;
+  const char *language;
 };
 
 /* Also a vector of input files specified.  */
@@ -2363,14 +2359,14 @@ static struct infile *infiles;
 
 static int n_infiles;
 
-/* This counts the number of libraries added by LANG_SPECIFIC_DRIVER, so that
+/* This counts the number of libraries added by lang_specific_driver, so that
    we can tell if there were any user supplied any files or libraries.  */
 
 static int added_libraries;
 
 /* And a vector of corresponding output files is made up later.  */
 
-static char **outfiles;
+static const char **outfiles;
 
 /* Used to track if none of the -B paths are used.  */
 static int warn_B;
@@ -2419,7 +2415,7 @@ convert_filename (name, do_exe)
     return name;
 
   for (i = len - 1; i >= 0; i--)
-    if (name[i] == '/' || name[i] == DIR_SEPARATOR)
+    if (IS_DIR_SEPARATOR (name[i]))
       break;
 
   for (i++; i < len; i++)
@@ -2487,56 +2483,57 @@ display_help ()
 
 static void                                                            
 add_preprocessor_option (option, len)                                  
-     char * option;                                                    
-     int    len;                                                       
+     const char * option;
+     int len;
 {                                                                      
-  n_preprocessor_options++;                                                    
+  n_preprocessor_options++;
                                                                        
-  if (! preprocessor_options)                                          
-    preprocessor_options                                                       
-      = (char **) xmalloc (n_preprocessor_options * sizeof (char *));  
-  else                                                                 
-    preprocessor_options                                                       
-      = (char **) xrealloc (preprocessor_options,                              
-                           n_preprocessor_options * sizeof (char *));  
+  if (! preprocessor_options)
+    preprocessor_options
+      = (char **) xmalloc (n_preprocessor_options * sizeof (char *));
+  else
+    preprocessor_options
+      = (char **) xrealloc (preprocessor_options,
+                           n_preprocessor_options * sizeof (char *));
                                                                        
-  preprocessor_options [n_preprocessor_options - 1] = save_string (option, len);  
+  preprocessor_options [n_preprocessor_options - 1] =
+    save_string (option, len);
 }
      
 static void                                                            
 add_assembler_option (option, len)                                     
-     char * option;                                                    
-     int    len;                                                       
-{                                                                      
-  n_assembler_options++;                                                       
-                                                                       
-  if (! assembler_options)                                             
-    assembler_options                                                  
-      = (char **) xmalloc (n_assembler_options * sizeof (char *));     
-  else                                                                 
-    assembler_options                                                  
-      = (char **) xrealloc (assembler_options,                         
-                           n_assembler_options * sizeof (char *));     
-                                                                       
-  assembler_options [n_assembler_options - 1] = save_string (option, len);  
+     const char * option;
+     int len;
+{
+  n_assembler_options++;
+
+  if (! assembler_options)
+    assembler_options
+      = (char **) xmalloc (n_assembler_options * sizeof (char *));
+  else
+    assembler_options
+      = (char **) xrealloc (assembler_options,
+                           n_assembler_options * sizeof (char *));
+
+  assembler_options [n_assembler_options - 1] = save_string (option, len);
 }
      
 static void                                                            
 add_linker_option (option, len)                                        
-     char * option;                                                    
-     int    len;                                                       
-{                                                                      
-  n_linker_options++;                                                  
-                                                                       
-  if (! linker_options)                                                
-    linker_options                                                     
-      = (char **) xmalloc (n_linker_options * sizeof (char *));        
-  else                                                                 
-    linker_options                                                     
-      = (char **) xrealloc (linker_options,                            
-                           n_linker_options * sizeof (char *));        
-                                                                       
-  linker_options [n_linker_options - 1] = save_string (option, len);  
+     const char * option;
+     int    len;
+{
+  n_linker_options++;
+
+  if (! linker_options)
+    linker_options
+      = (char **) xmalloc (n_linker_options * sizeof (char *));
+  else
+    linker_options
+      = (char **) xrealloc (linker_options,
+                           n_linker_options * sizeof (char *));
+
+  linker_options [n_linker_options - 1] = save_string (option, len);
 }
 \f
 /* Create the vector `switches' and its contents.
@@ -2548,7 +2545,8 @@ process_command (argc, argv)
      char **argv;
 {
   register int i;
-  char *temp;
+  const char *temp;
+  char *temp1;
   char *spec_lang = 0;
   int last_language_n_infiles;
   int have_c = 0;
@@ -2563,12 +2561,13 @@ process_command (argc, argv)
 
   /* Figure compiler version from version string.  */
 
-  compiler_version = save_string (version_string, strlen (version_string));
-  for (temp = compiler_version; *temp; ++temp)
+  compiler_version = temp1 = xstrdup (version_string); 
+
+  for (; *temp1; ++temp1)
     {
-      if (*temp == ' ')
+      if (*temp1 == ' ')
        {
-         *temp = '\0';
+         *temp1 = '\0';
          break;
        }
     }
@@ -2579,13 +2578,12 @@ process_command (argc, argv)
     {
       int len = strlen (gcc_exec_prefix);
       if (len > (int) sizeof ("/lib/gcc-lib/")-1
-         && (gcc_exec_prefix[len-1] == '/'
-             || gcc_exec_prefix[len-1] == DIR_SEPARATOR))
+         && (IS_DIR_SEPARATOR (gcc_exec_prefix[len-1])))
        {
          temp = gcc_exec_prefix + len - sizeof ("/lib/gcc-lib/") + 1;
-         if ((*temp == '/' || *temp == DIR_SEPARATOR)
+         if (IS_DIR_SEPARATOR (*temp)
              && strncmp (temp+1, "lib", 3) == 0
-             && (temp[4] == '/' || temp[4] == DIR_SEPARATOR)
+             && IS_DIR_SEPARATOR (temp[4])
              && strncmp (temp+5, "gcc-lib", 7) == 0)
            len -= sizeof ("/lib/gcc-lib/") - 1;
        }
@@ -2601,7 +2599,7 @@ process_command (argc, argv)
   GET_ENV_PATH_LIST (temp, "COMPILER_PATH");
   if (temp)
     {
-      char *startp, *endp;
+      const char *startp, *endp;
       char *nstore = (char *) alloca (strlen (temp) + 3);
 
       startp = endp = temp;
@@ -2612,7 +2610,7 @@ process_command (argc, argv)
              strncpy (nstore, startp, endp-startp);
              if (endp == startp)
                strcpy (nstore, concat (".", dir_separator_str, NULL_PTR));
-             else if (endp[-1] != '/' && endp[-1] != DIR_SEPARATOR)
+             else if (!IS_DIR_SEPARATOR (endp[-1]))
                {
                  nstore[endp-startp] = DIR_SEPARATOR;
                  nstore[endp-startp+1] = 0;
@@ -2635,7 +2633,7 @@ process_command (argc, argv)
   GET_ENV_PATH_LIST (temp, "LIBRARY_PATH");
   if (temp && *cross_compile == '0')
     {
-      char *startp, *endp;
+      const char *startp, *endp;
       char *nstore = (char *) alloca (strlen (temp) + 3);
 
       startp = endp = temp;
@@ -2646,7 +2644,7 @@ process_command (argc, argv)
              strncpy (nstore, startp, endp-startp);
              if (endp == startp)
                strcpy (nstore, concat (".", dir_separator_str, NULL_PTR));
-             else if (endp[-1] != '/' && endp[-1] != DIR_SEPARATOR)
+             else if (!IS_DIR_SEPARATOR (endp[-1]))
                {
                  nstore[endp-startp] = DIR_SEPARATOR;
                  nstore[endp-startp+1] = 0;
@@ -2668,7 +2666,7 @@ process_command (argc, argv)
   GET_ENV_PATH_LIST (temp, "LPATH");
   if (temp && *cross_compile == '0')
     {
-      char *startp, *endp;
+      const char *startp, *endp;
       char *nstore = (char *) alloca (strlen (temp) + 3);
 
       startp = endp = temp;
@@ -2679,7 +2677,7 @@ process_command (argc, argv)
              strncpy (nstore, startp, endp-startp);
              if (endp == startp)
                strcpy (nstore, concat (".", dir_separator_str, NULL_PTR));
-             else if (endp[-1] != '/' && endp[-1] != DIR_SEPARATOR)
+             else if (!IS_DIR_SEPARATOR (endp[-1]))
                {
                  nstore[endp-startp] = DIR_SEPARATOR;
                  nstore[endp-startp+1] = 0;
@@ -2700,10 +2698,8 @@ process_command (argc, argv)
   /* Convert new-style -- options to old-style.  */
   translate_options (&argc, &argv);
 
-#ifdef LANG_SPECIFIC_DRIVER
   /* Do language-specific adjustment/addition of flags.  */
-  lang_specific_driver (fatal, &argc, &argv, &added_libraries);
-#endif
+  lang_specific_driver (&argc, &argv, &added_libraries);
 
   /* Scan argv twice.  Here, the first time, just count how many switches
      there will be in their vector, and how many input files in theirs.
@@ -2717,6 +2713,8 @@ process_command (argc, argv)
          init_spec ();
          for (sl = specs; sl; sl = sl->next)
            printf ("*%s:\n%s\n\n", sl->name, *(sl->ptr_spec));
+          if (link_command_spec)
+            printf ("*link_command:\n%s\n\n", link_command_spec);
          exit (0);
        }
       else if (! strcmp (argv[i], "-dumpversion"))
@@ -2884,12 +2882,10 @@ process_command (argc, argv)
                  int len = strlen (value);
                  if ((len == 7
                       || (len > 7
-                          && (value[len - 8] == '/'
-                              || value[len - 8] == DIR_SEPARATOR)))
+                          && (IS_DIR_SEPARATOR (value[len - 8]))))
                      && strncmp (value + len - 7, "stage", 5) == 0
                      && ISDIGIT (value[len - 2])
-                     && (value[len - 1] == '/'
-                         || value[len - 1] == DIR_SEPARATOR))
+                     && (IS_DIR_SEPARATOR (value[len - 1])))
                    {
                      if (len == 7)
                        add_prefix (&include_prefixes, "include", NULL_PTR,
@@ -2934,7 +2930,7 @@ process_command (argc, argv)
                 The format of the version string is
                 ([^0-9]*-)?[0-9]+[.][0-9]+([.][0-9]+)?([- ].*)?  */
              {
-               char *v = compiler_version;
+               const char *v = compiler_version;
 
                /* Ignore leading non-digits.  i.e. "foo-" in "foo-2.7.2".  */
                while (! ISDIGIT (*v))
@@ -3056,7 +3052,7 @@ process_command (argc, argv)
      directories, so that we can search both the user specified directory
      and the standard place.  */
 
-  if (*tooldir_prefix != '/' && *tooldir_prefix != DIR_SEPARATOR)
+  if (!IS_DIR_SEPARATOR (*tooldir_prefix))
     {
       if (gcc_exec_prefix)
        {
@@ -3297,12 +3293,12 @@ process_command (argc, argv)
    sans all directory names, and basename_length is the number
    of characters starting there excluding the suffix .c or whatever.  */
 
-char *input_filename;
+const char *input_filename;
 static int input_file_number;
 size_t input_filename_length;
 static int basename_length;
-static char *input_basename;
-static char *input_suffix;
+static const char *input_basename;
+static const char *input_suffix;
 
 /* These are variables used within do_spec and do_spec_1.  */
 
@@ -3331,7 +3327,7 @@ static int input_from_pipe;
 
 int
 do_spec (spec)
-     char *spec;
+     const char *spec;
 {
   int value;
 
@@ -3372,14 +3368,14 @@ do_spec (spec)
 
 static int
 do_spec_1 (spec, inswitch, soft_matched_part)
-     char *spec;
+     const char *spec;
      int inswitch;
-     char *soft_matched_part;
+     const char *soft_matched_part;
 {
-  register char *p = spec;
+  register const char *p = spec;
   register int c;
   int i;
-  char *string;
+  const char *string;
   int value;
 
   while ((c = *p++))
@@ -3507,7 +3503,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
                  /* Relative directories always come from -B,
                     and it is better not to use them for searching
                     at run time.  In particular, stage1 loses  */
-                 if (pl->prefix[0] != '/' && pl->prefix[0] != DIR_SEPARATOR)
+                 if (!IS_DIR_SEPARATOR (pl->prefix[0]))
                    continue;
 #endif
                  /* Try subdirectory if there is one.  */
@@ -3564,8 +3560,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
                          buffer = (char *) xrealloc (buffer, bufsize);
                          strcpy (buffer, machine_suffix);
                          idx = strlen (buffer);
-                         if (buffer[idx - 1] == '/'
-                             || buffer[idx - 1] == DIR_SEPARATOR)
+                         if (IS_DIR_SEPARATOR (buffer[idx - 1]))
                            buffer[idx - 1] = 0;
                          do_spec_1 (buffer, 1, NULL_PTR);
                          /* Make this a separate argument.  */
@@ -3586,8 +3581,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
                          buffer = (char *) xrealloc (buffer, bufsize);
                          strcpy (buffer, pl->prefix);
                          idx = strlen (buffer);
-                         if (buffer[idx - 1] == '/'
-                             || buffer[idx - 1] == DIR_SEPARATOR)
+                         if (IS_DIR_SEPARATOR (buffer[idx - 1]))
                            buffer[idx - 1] = 0;
                          do_spec_1 (buffer, 1, NULL_PTR);
                          /* Make this a separate argument.  */
@@ -3603,7 +3597,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
            /* %efoo means report an error with `foo' as error message
               and don't execute any more commands for this file.  */
            {
-             char *q = p;
+             const char *q = p;
              char *buf;
              while (*p != 0 && *p != '\n') p++;
              buf = (char *) alloca (p - q + 1);
@@ -3631,7 +3625,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
                   In 2.4, do something about that.  */
                struct temp_name *t;
                int suffix_length;
-               char *suffix = p;
+               const char *suffix = p;
 
                if (p[0] == '%' && p[1] == 'O')
                  {
@@ -3726,9 +3720,8 @@ do_spec_1 (spec, inswitch, soft_matched_part)
          case 'o':
            {
              int max = n_infiles;
-#ifdef LANG_SPECIFIC_DRIVER
              max += lang_specific_extra_outfiles;
-#endif
+
              for (i = 0; i < max; i++)
                if (outfiles[i])
                  store_arg (outfiles[i], 0, 0);
@@ -3767,7 +3760,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
          /* %x{OPTION} records OPTION for %X to output.  */
          case 'x':
            {
-             char *p1 = p;
+             const char *p1 = p;
              char *string;
 
              /* Skip past the option value and make a copy.  */
@@ -4064,7 +4057,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
            error ("Warning: use of obsolete %%[ operator in specs");
          case '(':
            {
-             char *name = p;
+             const char *name = p;
              struct spec_list *sl;
              int len;
 
@@ -4097,7 +4090,7 @@ do_spec_1 (spec, inswitch, soft_matched_part)
                    {
                      char *x = (char *) alloca (strlen (name) * 2 + 1);
                      char *buf = x;
-                     char *y = name;
+                     const char *y = name;
                      int flag = 0;
 
                      /* Copy all of NAME into BUF, but put __ after
@@ -4205,11 +4198,11 @@ do_spec_1 (spec, inswitch, soft_matched_part)
 
 /* Return 0 if we call do_spec_1 and that returns -1.  */
 
-static char *
+static const char *
 handle_braces (p)
-     register char *p;
+     register const char *p;
 {
-  char *filter, *body = NULL, *endbody;
+  const char *filter, *body = NULL, *endbody = NULL;
   int pipe_p = 0;
   int negate;
   int suffix;
@@ -4254,7 +4247,7 @@ next_member:
       if (*p != '}')
         {
          register int count = 1;
-         register char *q = p;
+         register const char *q = p;
 
          while (*q++ != ':') continue;
          body = q;
@@ -4309,7 +4302,7 @@ next_member:
       if (p[-1] == '*' && !negate)
        {
          int substitution;
-         char *r = body;
+         const char *r = body;
 
          /* First see whether we have %*.  */
          substitution = 0;
@@ -4420,7 +4413,7 @@ check_live_switch (switchnum, prefix_length)
      int switchnum;
      int prefix_length;
 {
-  char *name = switches[switchnum].part1;
+  const char *name = switches[switchnum].part1;
   int i;
 
   /* In the common case of {<at-most-one-letter>*}, a negating
@@ -4525,9 +4518,9 @@ give_switch (switchnum, omit_first_word, include_blanks)
    user's -B prefix and some standard ones.
    Return the absolute file name found.  If nothing is found, return NAME.  */
 
-static char *
+static const char *
 find_file (name)
-     char *name;
+     const char *name;
 {
   char *newname;
 
@@ -4560,8 +4553,8 @@ find_file (name)
 
 static int
 is_directory (path1, path2, linker)
-     char *path1;
-     char *path2;
+     const char *path1;
+     const char *path2;
      int linker;
 {
   int len1 = strlen (path1);
@@ -4581,7 +4574,7 @@ is_directory (path1, path2, linker)
   memcpy (path, path1, len1);
   memcpy (path + len1, path2, len2);
   cp = path + len1 + len2;
-  if (cp[-1] != '/' && cp[-1] != DIR_SEPARATOR)
+  if (!IS_DIR_SEPARATOR (cp[-1]))
     *cp++ = DIR_SEPARATOR;
   *cp++ = '.';
   *cp = '\0';
@@ -4625,18 +4618,19 @@ main (argc, argv)
   int linker_was_run = 0;
   char *explicit_link_files;
   char *specs_file;
-  char *p;
+  const char *p;
   struct user_specs *uptr;
 
   p = argv[0] + strlen (argv[0]);
-  while (p != argv[0] && p[-1] != '/' && p[-1] != DIR_SEPARATOR) --p;
+  while (p != argv[0] && !IS_DIR_SEPARATOR (p[-1]))
+    --p;
   programname = p;
 
 #ifdef HAVE_LC_MESSAGES
   setlocale (LC_MESSAGES, "");
 #endif
-  bindtextdomain (PACKAGE, localedir);
-  textdomain (PACKAGE);
+  (void) bindtextdomain (PACKAGE, localedir);
+  (void) textdomain (PACKAGE);
 
   if (signal (SIGINT, SIG_IGN) != SIG_IGN)
     signal (SIGINT, fatal_error);
@@ -4731,7 +4725,7 @@ main (argc, argv)
     for (i = 0; (int)i < n_switches; i++)
       {
        char **args;
-       char *p, *q;
+       const char *p, *q;
        if (!first_time)
          obstack_grow (&collect_obstack, " ", 1);
 
@@ -4798,18 +4792,7 @@ main (argc, argv)
   if (access (specs_file, R_OK) == 0)
     read_specs (specs_file, TRUE);
  
-  /* Process any user specified specs in the order given on the command
-     line.  */
-  for (uptr = user_specs_head; uptr; uptr = uptr->next)
-    {
-      char *filename = find_a_file (&startfile_prefixes, uptr->filename, R_OK);
-      read_specs (filename ? filename : uptr->filename, FALSE);
-    }
-
   /* If not cross-compiling, look for startfiles in the standard places.  */
-  /* The fact that these are done here, after reading the specs file,
-     means that it cannot be found in these directories.
-     But that's okay.  It should never be there anyway.  */
   if (*cross_compile == '0')
     {
 #ifdef MD_EXEC_PREFIX
@@ -4831,14 +4814,12 @@ main (argc, argv)
         standard_exec_prefix.  This lets us move the installed tree
         as a unit.  If GCC_EXEC_PREFIX is defined, base
         standard_startfile_prefix on that as well.  */
-      if (*standard_startfile_prefix == '/'
-         || *standard_startfile_prefix == DIR_SEPARATOR
-         || *standard_startfile_prefix == '$'
-#ifdef __MSDOS__
-         /* Check for disk name on MS-DOS-based systems.  */
+      if (IS_DIR_SEPARATOR (*standard_startfile_prefix)
+           || *standard_startfile_prefix == '$'
+#ifdef HAVE_DOS_BASED_FILESYSTEM
+           /* Check for disk name on MS-DOS-based systems.  */
           || (standard_startfile_prefix[1] == ':'
-             && (standard_startfile_prefix[2] == DIR_SEPARATOR
-                 || standard_startfile_prefix[2] == '/'))
+             && (IS_DIR_SEPARATOR (standard_startfile_prefix[2])))
 #endif
          )
        add_prefix (&startfile_prefixes, standard_startfile_prefix, "BINUTILS",
@@ -4867,13 +4848,21 @@ main (argc, argv)
     }
   else
     {
-      if (*standard_startfile_prefix != DIR_SEPARATOR && gcc_exec_prefix)
+      if (!IS_DIR_SEPARATOR (*standard_startfile_prefix) && gcc_exec_prefix)
        add_prefix (&startfile_prefixes,
                    concat (gcc_exec_prefix, machine_suffix,
                            standard_startfile_prefix, NULL_PTR),
                    "BINUTILS", 0, 0, NULL_PTR);
     }
 
+  /* Process any user specified specs in the order given on the command
+     line.  */
+  for (uptr = user_specs_head; uptr; uptr = uptr->next)
+    {
+      char *filename = find_a_file (&startfile_prefixes, uptr->filename, R_OK);
+      read_specs (filename ? filename : uptr->filename, FALSE);
+    }
+
   /* If we have a GCC_EXEC_PREFIX envvar, modify it for cpp's sake.  */
   if (gcc_exec_prefix)
     {
@@ -4910,26 +4899,26 @@ main (argc, argv)
       printf ("install: %s%s\n", standard_exec_prefix, machine_suffix);
       printf ("programs: %s\n", build_search_list (&exec_prefixes, "", 0));
       printf ("libraries: %s\n", build_search_list (&startfile_prefixes, "", 0));
-      exit (0);
+      return (0);
     }
 
   if (print_file_name)
     {
       printf ("%s\n", find_file (print_file_name));
-      exit (0);
+      return (0);
     }
 
   if (print_prog_name)
     {
       char *newname = find_a_file (&exec_prefixes, print_prog_name, X_OK);
       printf ("%s\n", (newname ? newname : print_prog_name));
-      exit (0);
+      return (0);
     }
 
   if (print_multi_lib)
     {
       print_multilib_info ();
-      exit (0);
+      return (0);
     }
 
   if (print_multi_directory)
@@ -4938,7 +4927,7 @@ main (argc, argv)
        printf (".\n");
       else
        printf ("%s\n", multilib_dir);
-      exit (0);
+      return (0);
     }
 
   if (print_help_list)
@@ -4947,10 +4936,10 @@ main (argc, argv)
 
       if (! verbose_flag)
        {
-         printf ("\nReport bugs to egcs-bugs@egcs.cygnus.com.\n");
-         printf ("Please see the file BUGS (included with the sources) first.\n");
+         printf ("\nFor bug reporting instructions, please see:\n");
+         printf ("<URL:http://www.gnu.org/software/gcc/faq.html#bugreport>.\n");
          
-         exit (0);
+         return (0);
        }
 
       /* We do not exit here.  Instead we have created a fake input file
@@ -4977,7 +4966,7 @@ main (argc, argv)
                version_string, compiler_version);
 
       if (n_infiles == 0)
-       exit (0);
+       return (0);
     }
 
   if (n_infiles == added_libraries)
@@ -4987,16 +4976,12 @@ main (argc, argv)
      that correspond to the input files.  */
 
   i = n_infiles;
-#ifdef LANG_SPECIFIC_DRIVER
   i += lang_specific_extra_outfiles;
-#endif
-  outfiles = (char **) xmalloc (i * sizeof (char *));
-  bzero ((char *) outfiles, i * sizeof (char *));
+  outfiles = (const char **) xcalloc (i, sizeof (char *));
 
   /* Record which files were specified explicitly as link input.  */
 
-  explicit_link_files = xmalloc (n_infiles);
-  bzero (explicit_link_files, n_infiles);
+  explicit_link_files = xcalloc (1, n_infiles);
 
   for (i = 0; (int)i < n_infiles; i++)
     {
@@ -5022,7 +5007,7 @@ main (argc, argv)
        {
          /* Ok, we found an applicable compiler.  Run its spec.  */
          /* First say how much of input_filename to substitute for %b  */
-         register char *p;
+         register const char *p;
          int len;
 
          if (cp->spec[0][0] == '#')
@@ -5031,7 +5016,7 @@ main (argc, argv)
 
          input_basename = input_filename;
          for (p = input_filename; *p; p++)
-           if (*p == '/' || *p == DIR_SEPARATOR)
+           if (IS_DIR_SEPARATOR (*p))
              input_basename = p + 1;
 
          /* Find a suffix starting with the last period,
@@ -5052,18 +5037,20 @@ main (argc, argv)
            if (cp->spec[j])
              len += strlen (cp->spec[j]);
 
-         p = (char *) xmalloc (len + 1);
-
-         len = 0;
-         for (j = 0; j < sizeof cp->spec / sizeof cp->spec[0]; j++)
-           if (cp->spec[j])
-             {
-               strcpy (p + len, cp->spec[j]);
-               len += strlen (cp->spec[j]);
-             }
-
-         value = do_spec (p);
-         free (p);
+         {
+           char *p1 = (char *) xmalloc (len + 1);
+           
+           len = 0;
+           for (j = 0; j < sizeof cp->spec / sizeof cp->spec[0]; j++)
+             if (cp->spec[j])
+               {
+                 strcpy (p1 + len, cp->spec[j]);
+                 len += strlen (cp->spec[j]);
+               }
+           
+           value = do_spec (p1);
+           free (p1);
+         }
          if (value < 0)
            this_file_error = 1;
        }
@@ -5086,7 +5073,6 @@ main (argc, argv)
       clear_failure_queue ();
     }
 
-#ifdef LANG_SPECIFIC_DRIVER
   if (error_count == 0)
     {
       /* Make sure INPUT_FILE_NUMBER points to first available open
@@ -5095,7 +5081,6 @@ main (argc, argv)
       if (lang_specific_pre_link ())
        error_count++;
     }
-#endif
 
   /* Run ld to link all the compiler output files.  */
 
@@ -5142,13 +5127,11 @@ main (argc, argv)
 
   if (print_help_list)
     {
-      printf ("\nReport bugs to egcs-bugs@egcs.cygnus.com.\n");
-      printf ("Please see the file BUGS (included with the sources) first.\n");
+      printf ("\nFor bug reporting instructions, please see:\n");
+      printf ("<URL:http://www.gnu.org/software/gcc/faq.html#bugreport>\n");
     }
   
-  exit (error_count > 0 ? (signal_count ? 2 : 1) : 0);
-  /* NOTREACHED */
-  return 0;
+  return (error_count > 0 ? (signal_count ? 2 : 1) : 0);
 }
 
 /* Find the proper compilation spec for the file name NAME,
@@ -5157,9 +5140,9 @@ main (argc, argv)
 
 static struct compiler *
 lookup_compiler (name, length, language)
-     char *name;
+     const char *name;
      size_t length;
-     char *language;
+     const char *language;
 {
   struct compiler *cp;
 
@@ -5208,8 +5191,9 @@ lookup_compiler (name, length, language)
              language = cp->spec[0] + 1;
              new = (struct compiler *) xmalloc (sizeof (struct compiler));
              new->suffix = cp->suffix;
-             bcopy ((char *) lookup_compiler (NULL_PTR, 0, language)->spec,
-                    (char *) new->spec, sizeof new->spec);
+             memcpy (new->spec,
+                     lookup_compiler (NULL_PTR, 0, language)->spec,
+                     sizeof new->spec);
              return new;
            }
 
@@ -5221,31 +5205,6 @@ lookup_compiler (name, length, language)
   return 0;
 }
 \f
-PTR
-xmalloc (size)
-  size_t size;
-{
-  register PTR value = (PTR) malloc (size);
-  if (value == 0)
-    fatal ("virtual memory exhausted");
-  return value;
-}
-
-PTR
-xrealloc (old, size)
-  PTR old;
-  size_t size;
-{
-  register PTR ptr;
-  if (old)
-    ptr = (PTR) realloc (old, size);
-  else
-    ptr = (PTR) malloc (size);
-  if (ptr == 0)
-    fatal ("virtual memory exhausted");
-  return ptr;
-}
-
 static char *
 save_string (s, len)
   const char *s;
@@ -5260,7 +5219,7 @@ save_string (s, len)
 
 static void
 pfatal_with_name (name)
-     char *name;
+     const char *name;
 {
   perror_with_name (name);
   delete_temp_files ();
@@ -5269,15 +5228,15 @@ pfatal_with_name (name)
 
 static void
 perror_with_name (name)
-     char *name;
+     const char *name;
 {
   error ("%s: %s", name, xstrerror (errno));
 }
 
 static void
 pfatal_pexecute (errmsg_fmt, errmsg_arg)
-     char *errmsg_fmt;
-     char *errmsg_arg;
+     const char *errmsg_fmt;
+     const char *errmsg_arg;
 {
   if (errmsg_arg)
     {
@@ -5305,18 +5264,18 @@ fancy_abort ()
 \f
 /* Output an error message and exit */
 
-static void
-fatal VPROTO((char *msgid, ...))
+void
+fatal VPROTO((const char *msgid, ...))
 {
 #ifndef ANSI_PROTOTYPES
-  char *msgid;
+  const char *msgid;
 #endif
   va_list ap;
 
   VA_START (ap, msgid);
 
 #ifndef ANSI_PROTOTYPES
-  msgid = va_arg (ap, char *);
+  msgid = va_arg (ap, const char *);
 #endif
 
   fprintf (stderr, "%s: ", programname);
@@ -5328,17 +5287,17 @@ fatal VPROTO((char *msgid, ...))
 }
 
 static void
-error VPROTO((char *msgid, ...))
+error VPROTO((const char *msgid, ...))
 {
 #ifndef ANSI_PROTOTYPES
-  char *msgid;
+  const char *msgid;
 #endif
   va_list ap;
 
   VA_START (ap, msgid);
 
 #ifndef ANSI_PROTOTYPES
-  msgid = va_arg (ap, char *);
+  msgid = va_arg (ap, const char *);
 #endif
 
   fprintf (stderr, "%s: ", programname);
@@ -5349,17 +5308,17 @@ error VPROTO((char *msgid, ...))
 }
 
 static void
-notice VPROTO((char *msgid, ...))
+notice VPROTO((const char *msgid, ...))
 {
 #ifndef ANSI_PROTOTYPES
-  char *msgid;
+  const char *msgid;
 #endif
   va_list ap;
 
   VA_START (ap, msgid);
 
 #ifndef ANSI_PROTOTYPES
-  msgid = va_arg (ap, char *);
+  msgid = va_arg (ap, const char *);
 #endif
 
   vfprintf (stderr, _(msgid), ap);
@@ -5371,7 +5330,7 @@ static void
 validate_all_switches ()
 {
   struct compiler *comp;
-  register char *p;
+  register const char *p;
   register char c;
   struct spec_list *spec;
 
@@ -5410,10 +5369,10 @@ validate_all_switches ()
 
 static void
 validate_switches (start)
-     char *start;
+     const char *start;
 {
-  register char *p = start;
-  char *filter;
+  register const char *p = start;
+  const char *filter;
   register int i;
   int suffix = 0;
 
@@ -5456,7 +5415,7 @@ validate_switches (start)
 
 static int
 used_arg (p, len)
-     char *p;
+     const char *p;
      int len;
 {
   struct mswitchstr {
@@ -5544,7 +5503,7 @@ used_arg (p, len)
 
 static int
 default_arg (p, len)
-     char *p;
+     const char *p;
      int len;
 {
   char *start, *end;
@@ -5659,9 +5618,10 @@ set_multilib_dir ()
          if (this_path_len != 1
              || this_path[0] != '.')
            {
-             multilib_dir = xmalloc (this_path_len + 1);
-             strncpy (multilib_dir, this_path, this_path_len);
-             multilib_dir[this_path_len] = '\0';
+             char * new_multilib_dir = xmalloc (this_path_len + 1);
+             strncpy (new_multilib_dir, this_path, this_path_len);
+             new_multilib_dir[this_path_len] = '\0';
+             multilib_dir = new_multilib_dir;
            }
          break;
        }