This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[RFC PATCH] GCC multilib vs. OS multilib naming


Hi!

The following patch tries to deal with diferrent GCC and OS multlib schemes.
Particularly on sparc64/x86_64/ppc64/s390x/irix 64-bit libs are put into
*/lib64 directories, not */lib/64 resp. */lib depending on
what the configured GCC MULTILIB_DEFAULT is. Similarly 32-bit libs are put
into */lib directories, not into */lib/32 as GCC does for some
MULTILIB_DEFAULT settings. On Solaris if GCC MULTILIB_DEFAULT is m32,
GCC naming scheme matches OS one, but if MULTILIB_DEFAULT is m64,
OS still uses */lib/sparcv9 for 64-bit and */lib for 32-bit while GCC wants
to use */lib for 64-bit and */lib/sparcv7 for 32-bit.
This patch should also fix the --without-multilib Solaris problems,
as mklibgcc now uses new gcc option to query the information.

The patch introduces new variable (multilib_os_dir) and new option
to query it. Unless the OS multilib scheme differs from GCC one, it is the same
as multilib_dir. On sparc64-linux --with-cpu=v7:
gcc -print-multi-directory
.
gcc -print-multi-os-directory
../lib
gcc -print-multi-directory -m32
.
gcc -print-multi-os-directory -m32
../lib
gcc -print-multi-directory -m64
64
gcc -print-multi-os-directory -m64
../lib64
gcc -print-multi-directory -m64 -mcmodel=medany
64/alt
gcc -print-multi-os-directory -m64 -mcmodel=medany
../lib64/alt

On sparc64-linux --with-cpu=ultrasparc:
gcc -print-multi-directory
.
gcc -print-multi-os-directory
../lib64
gcc -print-multi-directory -m32
32
gcc -print-multi-os-directory -m32
../lib
gcc -print-multi-directory -m64
.
gcc -print-multi-os-directory -m64
../lib64
gcc -print-multi-directory -m64 -mcmodel=medany
alt
gcc -print-multi-os-directory -m64 -mcmodel=medany
../lib64/alt

It also flags prefixes as using or not using OS multilib scheme.
E.g. /usr/lib/gcc-lib/<platform>/<version>/ and similar prefixes
are GCC thing and as such use GCC multilib scheme.
On the other hand, directories
like /usr/lib/gcc-lib/<platform>/<version>/../../..
/lib /usr/lib are owned by OS and thus use OS multilib scheme.

It changes %D spec handling and searching for crt* files, so
that in OS multilib scheme flagged prefixes multilib_os_dir
is tried while in GCC owned prefixes multilib_dir is tried.

I've only changed sparc64-linux config for this, but if you agree this
is the way to go I'll change solaris, x86_64, ppc64 and s390x too.
On x86_64/ppc64 they'd be able to stop using STARTFILE_PREFIX_SPEC,
which has the disadvantage that it is only suitable for --prefix /usr/local
or --prefix /usr native gcc and only solves part of the thing.

A follow-up patch would be modifying libstdc++/libgcj etc. configury to
install libs which go to OS owned directories into
--print-multi-os-directory, not --print-multi-directory directories.
Say with --prefix /usr, libstdc++.so.5.0.1 should be installed into
/usr/lib/`gcc $flags -print-multi-os-directory`/libstdc++.so.5.0.1.

Comments?

2002-09-20  Jakub Jelinek  <jakub@redhat.com>

	* gcc.c (print_multi_os_directory): New variable.
	(option_map): Support --print-multi-os-directory.
	(struct prefix_list): Add os_multilib field.
	(multilib_os_dir): New variable.
	(static_specs): Add multilib_options.
	(find_a_file): Add multilib argument.  Search in GCC or OS multilib
	subdirs if non-zero.
	(read_specs, execute): Update callers.
	(find_file): Likewise.  Don't prefix name with multilib_dir, instead
	pass 1 as multilib option.
	(display_help): Include --print-multi-os-directory.
	(add_prefix): Add os_multilib argument.  Initialize pl->os_multilib.
	(process_command): Update callers.  Handle --print-multi-os-directory.
	(do_spec_1) ['D']: Use multilib_os_directory if pl->os_multilib is
	set.
	(main): Update find_a_file and add_prefix callers.
	Handle print_multi_os_directory.
	(struct mdswitchstr): New.
	(mdswitches, n_mdswitches): New variables.
	(used_arg): Add MULTILIB_DEFAULT switches too if they are not
	present on the command line nor their mutually incompatible
	switches.
	(default_arg): Optimize.
	(set_multilib_dir): Compute multilib_os_dir.  Initialize mdswitches
	array.
	(print_multilib_info): Only print GCC multilib dir name, not OS
	multilib dirname.
	* genmultilib: Add osdirnames parameter.  Output multilib_options
	variable.  If osdirnames is specified, output dirnames as
	dirname:osdirname.
	* mklibgcc.in: Use MULTILIB_OSDIRNAMES, --print-multi-directory
	and --print-multi-os-directory instead of SHLIB_SLIBDIR_SUFFIXES
	to compute libgcc_s soname and install path.
	* Makefile.in (libgcc.mk): Pass MULTILIB_OSDIRNAMES instead of
	SHLIB_SLIBDIR_SUFFIXES to mklibgcc.
	(s_mlib): Pass MULTILIB_OSDIRNAMES or nothing as last genmultilib
	argument.

	* config/sparc/t-linux64 (MULTILIB_OSDIRNAMES): Set.
	(SHLIB_SLIBDIR_SUFFIXES): Remove.
	* config/sparc/linux64.h (STARTFILE_SPEC32, STARTFILE_SPEC64,
	ENDFILE_SPEC32, ENDFILE_SPEC64, ENDFILE_COMMON): Remove.
	(STARTFILE_SPEC, ENDFILE_SPEC): Don't distinguish between -m32
	and -m64.

--- gcc/genmultilib.jj	Thu Oct 11 13:59:45 2001
+++ gcc/genmultilib	Fri Sep 20 09:32:51 2002
@@ -63,6 +63,11 @@
 # for the rule to exclude a set. Options can be preceded with a '!' to
 # match a logical NOT.
 
+# The optional sevenths argument is a list of OS subdirectory names.
+# The format is the same as of the second argument.
+# The difference is that second argument describes multilib directories
+# in GCC conventions, while this one the OS multilib convention.
+
 # The output looks like
 #   #define MULTILIB_MATCHES "\
 #   SUBDIRECTORY OPTIONS;\
@@ -79,17 +84,18 @@
 # Here is an example (this is from the actual sparc64 case):
 #   genmultilib 'm64/m32 mno-app-regs|mcmodel=medany' '64 32 alt'
 #		'mcmodel?medany=mcmodel?medmid' 'm32/mno-app-regs* m32/mcmodel=*'
-#		'm32/!m64/mno-app-regs m32/!m64/mcmodel=medany'
+#		'' 'm32/!m64/mno-app-regs m32/!m64/mcmodel=medany'
+#		'../lib64 ../lib32 alt'
 # This produces:
 #   ". !m64 !m32 !mno-app-regs !mcmodel=medany;",
-#   "64 m64 !m32 !mno-app-regs !mcmodel=medany;",
-#   "32 !m64 m32 !mno-app-regs !mcmodel=medany;",
+#   "64:../lib64 m64 !m32 !mno-app-regs !mcmodel=medany;",
+#   "32:../lib32 !m64 m32 !mno-app-regs !mcmodel=medany;",
 #   "alt !m64 !m32 mno-app-regs mcmodel=medany;",
 #   "alt !m64 !m32 mno-app-regs !mcmodel=medany;",
 #   "alt !m64 !m32 !mno-app-regs mcmodel=medany;",
-#   "64/alt m64 !m32 mno-app-regs mcmodel=medany;",
-#   "64/alt m64 !m32 mno-app-regs !mcmodel=medany;",
-#   "64/alt m64 !m32 !mno-app-regs mcmodel=medany;",
+#   "64/alt:../lib64/alt m64 !m32 mno-app-regs mcmodel=medany;",
+#   "64/alt:../lib64/alt m64 !m32 mno-app-regs !mcmodel=medany;",
+#   "64/alt:../lib64/alt m64 !m32 !mno-app-regs mcmodel=medany;",
 #
 # The effect is that `gcc -mno-app-regs' (for example) will append "alt"
 # to the directory name when searching for libraries or startup files and
@@ -106,6 +112,7 @@ matches=$3
 exceptions=$4
 extra=$5
 exclusions=$6
+osdirnames=$7
 
 echo "static const char *const multilib_raw[] = {"
 
@@ -202,6 +209,29 @@ if [ -n "${dirnames}" ]; then
   done
 fi
 
+# Construct a sed pattern which will convert option names to OS directory
+# names.
+toosdirnames=
+if [ -n "${osdirnames}" ]; then
+  set x ${osdirnames}
+  shift
+  for set in ${options}; do
+    for opts in `echo ${set} | sed -e 's|/| |'g`; do
+      patt="/"
+      for opt in `echo ${opts} | sed -e 's_|_ _'g`; do
+        if [ "$1" != "${opt}" ]; then
+          toosdirnames="${toosdirnames} -e s|/${opt}/|/${1}/|g"
+	  patt="${patt}${1}/"
+	  if [ "${patt}" != "/${1}/" ]; then
+	    toosdirnames="${toosdirnames} -e s|${patt}|/${1}/|g"
+          fi
+        fi
+      done
+      shift
+    done
+  done
+fi
+
 # We need another recursive shell script to correctly handle positive
 # matches.  If we are invoked as
 #   genmultilib "opt1 opt2" "" "opt1=nopt1 opt2=nopt2"
@@ -257,6 +287,16 @@ for combo in ${combinations}; do
   # Remove the leading and trailing slashes.
   dirout=`echo ${dirout} | sed -e 's|^/||' -e 's|/$||g'`
 
+  # Use the OS directory names rather than the option names.
+  if [ -n "${toosdirnames}" ]; then
+    osdirout=`echo ${combo} | sed ${toosdirnames}`
+    # Remove the leading and trailing slashes.
+    osdirout=`echo ${osdirout} | sed -e 's|^/||' -e 's|/$||g'`
+    if [ "x${dirout}" != "x${osdirout}" ]; then
+      dirout="${dirout}:${osdirout}"
+    fi
+  fi
+
   # Look through the options.  We must output each option that is
   # present, and negate each option that is not present.
   optout=
@@ -313,6 +353,11 @@ done
 echo "NULL"
 echo "};"
 
+# Output the options now
+moptions=`echo ${options} | sed -e 's,[ 	][ 	]*, ,g'`
+echo ""
+echo "static const char *multilib_options = \"${moptions}\";"
+
 rm -f tmpmultilib2
 
 exit 0
--- gcc/gcc.c.jj	Thu Aug  1 17:41:31 2002
+++ gcc/gcc.c	Fri Sep 20 10:05:06 2002
@@ -172,6 +172,11 @@ static const char *print_prog_name = NUL
 
 static int print_multi_directory;
 
+/* Flag saying to print the relative path we'd use to
+   find OS libraries given the current compiler flags.  */
+
+static int print_multi_os_directory;
+
 /* Flag saying to print the list of subdirectories and
    compiler flags used to select them in a standard form.  */
 
@@ -285,9 +290,10 @@ static struct compiler *lookup_compiler 
 static char *build_search_list	PARAMS ((struct path_prefix *, const char *, int));
 static void putenv_from_prefixes PARAMS ((struct path_prefix *, const char *));
 static int access_check		PARAMS ((const char *, int));
-static char *find_a_file	PARAMS ((struct path_prefix *, const char *, int));
+static char *find_a_file	PARAMS ((struct path_prefix *, const char *,
+					 int, int));
 static void add_prefix		PARAMS ((struct path_prefix *, const char *,
-					 const char *, int, int, int *));
+					 const char *, int, int, int *, int));
 static void translate_options	PARAMS ((int *, const char *const **));
 static char *skip_whitespace	PARAMS ((char *));
 static void delete_if_ordinary	PARAMS ((const char *));
@@ -963,6 +969,7 @@ static const struct option_map option_ma
    {"--print-missing-file-dependencies", "-MG", 0},
    {"--print-multi-lib", "-print-multi-lib", 0},
    {"--print-multi-directory", "-print-multi-directory", 0},
+   {"--print-multi-os-directory", "-print-multi-os-directory", 0},
    {"--print-prog-name", "-print-prog-name=", "aj"},
    {"--profile", "-p", 0},
    {"--profile-blocks", "-a", 0},
@@ -1248,7 +1255,9 @@ struct prefix_list
   int require_machine_suffix; /* Don't use without machine_suffix.  */
   /* 2 means try both machine_suffix and just_machine_suffix.  */
   int *used_flag_ptr;	      /* 1 if a file was found with this prefix.  */
-  int priority;		      /* Sort key - priority within list */
+  int priority;		      /* Sort key - priority within list.  */
+  int os_multilib;	      /* 1 if OS multilib scheme should be used,
+				 0 for GCC multilib scheme.  */
 };
 
 struct path_prefix
@@ -1337,6 +1346,11 @@ static const char *const standard_bindir
    set_multilib_dir based on the compilation options.  */
 
 static const char *multilib_dir;
+
+/* Subdirectory to use for locating libraries in OS conventions.  Set by
+   set_multilib_dir based on the compilation options.  */
+
+static const char *multilib_os_dir;
 
 /* Structure to keep track of the specs that have been defined so far.
    These are accessed using %(specname) or %[specname] in a compiler
@@ -1390,6 +1404,7 @@ static struct spec_list static_specs[] =
   INIT_STATIC_SPEC ("multilib_extra",		&multilib_extra),
   INIT_STATIC_SPEC ("multilib_matches",		&multilib_matches),
   INIT_STATIC_SPEC ("multilib_exclusions",	&multilib_exclusions),
+  INIT_STATIC_SPEC ("multilib_options",		&multilib_options),
   INIT_STATIC_SPEC ("linker",			&linker_name_spec),
   INIT_STATIC_SPEC ("link_libgcc",		&link_libgcc_spec),
   INIT_STATIC_SPEC ("md_exec_prefix",		&md_exec_prefix),
@@ -1832,7 +1847,7 @@ read_specs (filename, main_p)
 		       (long) (p1 - buffer + 1));
 
 	      p[-2] = '\0';
-	      new_filename = find_a_file (&startfile_prefixes, p1, R_OK);
+	      new_filename = find_a_file (&startfile_prefixes, p1, R_OK, 0);
 	      read_specs (new_filename ? new_filename : p1, FALSE);
 	      continue;
 	    }
@@ -1851,7 +1866,7 @@ read_specs (filename, main_p)
 		       (long) (p1 - buffer + 1));
 
 	      p[-2] = '\0';
-	      new_filename = find_a_file (&startfile_prefixes, p1, R_OK);
+	      new_filename = find_a_file (&startfile_prefixes, p1, R_OK, 0);
 	      if (new_filename)
 		read_specs (new_filename, FALSE);
 	      else if (verbose_flag)
@@ -2480,16 +2495,17 @@ access_check (name, mode)
    Return 0 if not found, otherwise return its name, allocated with malloc.  */
 
 static char *
-find_a_file (pprefix, name, mode)
+find_a_file (pprefix, name, mode, multilib)
      struct path_prefix *pprefix;
      const char *name;
-     int mode;
+     int mode, multilib;
 {
   char *temp;
   const char *const file_suffix =
     ((mode & X_OK) != 0 ? HOST_EXECUTABLE_SUFFIX : "");
   struct prefix_list *pl;
   int len = pprefix->max_len + strlen (name) + strlen (file_suffix) + 1;
+  const char *multilib_name = NULL, *multilib_os_name = NULL;
 
 #ifdef DEFAULT_ASSEMBLER
   if (! strcmp (name, "as") && access (DEFAULT_ASSEMBLER, mode) == 0)
@@ -2504,6 +2520,17 @@ find_a_file (pprefix, name, mode)
   if (machine_suffix)
     len += strlen (machine_suffix);
 
+  if (multilib && multilib_dir)
+    {
+      int len1 = strlen (multilib_dir) + 1;
+      int len2 = strlen (multilib_os_dir) + 1;
+
+      len += len1 > len2 ? len1 : len2;
+      multilib_name = ACONCAT ((multilib_dir, dir_separator_str, name, NULL));
+      multilib_os_name = ACONCAT ((multilib_os_dir, dir_separator_str, name,
+				   NULL));
+    }
+
   temp = xmalloc (len);
 
   /* Determine the filename to execute (special case for absolute paths).  */
@@ -2519,6 +2546,11 @@ find_a_file (pprefix, name, mode)
   else
     for (pl = pprefix->plist; pl; pl = pl->next)
       {
+	const char *this_name = name;
+
+	if (multilib_name)
+	  this_name = pl->os_multilib ? multilib_os_name : multilib_name;
+
 	if (machine_suffix)
 	  {
 	    /* Some systems have a suffix for executable files.
@@ -2527,7 +2559,7 @@ find_a_file (pprefix, name, mode)
 	      {
 		strcpy (temp, pl->prefix);
 		strcat (temp, machine_suffix);
-		strcat (temp, name);
+		strcat (temp, this_name);
 		strcat (temp, file_suffix);
 		if (access_check (temp, mode) == 0)
 		  {
@@ -2537,10 +2569,10 @@ find_a_file (pprefix, name, mode)
 		  }
 	      }
 
-	    /* Now try just the name.  */
+	    /* Now try just the this_name.  */
 	    strcpy (temp, pl->prefix);
 	    strcat (temp, machine_suffix);
-	    strcat (temp, name);
+	    strcat (temp, this_name);
 	    if (access_check (temp, mode) == 0)
 	      {
 		if (pl->used_flag_ptr != 0)
@@ -2559,7 +2591,7 @@ find_a_file (pprefix, name, mode)
 	      {
 		strcpy (temp, pl->prefix);
 		strcat (temp, just_machine_suffix);
-		strcat (temp, name);
+		strcat (temp, this_name);
 		strcat (temp, file_suffix);
 		if (access_check (temp, mode) == 0)
 		  {
@@ -2571,7 +2603,7 @@ find_a_file (pprefix, name, mode)
 
 	    strcpy (temp, pl->prefix);
 	    strcat (temp, just_machine_suffix);
-	    strcat (temp, name);
+	    strcat (temp, this_name);
 	    if (access_check (temp, mode) == 0)
 	      {
 		if (pl->used_flag_ptr != 0)
@@ -2589,7 +2621,7 @@ find_a_file (pprefix, name, mode)
 	    if (file_suffix[0] != 0)
 	      {
 		strcpy (temp, pl->prefix);
-		strcat (temp, name);
+		strcat (temp, this_name);
 		strcat (temp, file_suffix);
 		if (access_check (temp, mode) == 0)
 		  {
@@ -2600,7 +2632,7 @@ find_a_file (pprefix, name, mode)
 	      }
 
 	    strcpy (temp, pl->prefix);
-	    strcat (temp, name);
+	    strcat (temp, this_name);
 	    if (access_check (temp, mode) == 0)
 	      {
 		if (pl->used_flag_ptr != 0)
@@ -2638,13 +2670,15 @@ enum path_prefix_priority
    2 means try both machine_suffix and just_machine_suffix.  */
 
 static void
-add_prefix (pprefix, prefix, component, priority, require_machine_suffix, warn)
+add_prefix (pprefix, prefix, component, priority, require_machine_suffix,
+	    warn, os_multilib)
      struct path_prefix *pprefix;
      const char *prefix;
      const char *component;
      /* enum prefix_priority */ int priority;
      int require_machine_suffix;
      int *warn;
+     int os_multilib;
 {
   struct prefix_list *pl, **prev;
   int len;
@@ -2666,6 +2700,7 @@ add_prefix (pprefix, prefix, component, 
   pl->require_machine_suffix = require_machine_suffix;
   pl->used_flag_ptr = warn;
   pl->priority = priority;
+  pl->os_multilib = os_multilib;
   if (warn)
     *warn = 0;
 
@@ -2709,7 +2744,7 @@ execute ()
 
   commands[0].prog = argbuf[0]; /* first command.  */
   commands[0].argv = &argbuf[0];
-  string = find_a_file (&exec_prefixes, commands[0].prog, X_OK);
+  string = find_a_file (&exec_prefixes, commands[0].prog, X_OK, 0);
 
   if (string)
     commands[0].argv[0] = string;
@@ -2723,7 +2758,8 @@ execute ()
 	argbuf[i] = 0;	/* termination of command args.  */
 	commands[n_commands].prog = argbuf[i + 1];
 	commands[n_commands].argv = &argbuf[i + 1];
-	string = find_a_file (&exec_prefixes, commands[n_commands].prog, X_OK);
+	string = find_a_file (&exec_prefixes, commands[n_commands].prog,
+			      X_OK, 0);
 	if (string)
 	  commands[n_commands].argv[0] = string;
 	n_commands++;
@@ -3041,6 +3077,7 @@ display_help ()
   fputs (_("\
   -print-multi-lib         Display the mapping between command line options and\n\
                            multiple library search directories\n"), stdout);
+  fputs (_("  -print-multi-os-directory Display the relative path to OS libraries\n"), stdout);
   fputs (_("  -Wa,<options>            Pass comma-separated <options> on to the assembler\n"), stdout);
   fputs (_("  -Wp,<options>            Pass comma-separated <options> on to the preprocessor\n"), stdout);
   fputs (_("  -Wl,<options>            Pass comma-separated <options> on to the linker\n"), stdout);
@@ -3202,9 +3239,9 @@ process_command (argc, argv)
 
       set_std_prefix (gcc_exec_prefix, len);
       add_prefix (&exec_prefixes, gcc_exec_prefix, "GCC",
-		  PREFIX_PRIORITY_LAST, 0, NULL);
+		  PREFIX_PRIORITY_LAST, 0, NULL, 0);
       add_prefix (&startfile_prefixes, gcc_exec_prefix, "GCC",
-		  PREFIX_PRIORITY_LAST, 0, NULL);
+		  PREFIX_PRIORITY_LAST, 0, NULL, 0);
     }
 
   /* COMPILER_PATH and LIBRARY_PATH have values
@@ -3232,10 +3269,10 @@ process_command (argc, argv)
 	      else
 		nstore[endp - startp] = 0;
 	      add_prefix (&exec_prefixes, nstore, 0,
-			  PREFIX_PRIORITY_LAST, 0, NULL);
+			  PREFIX_PRIORITY_LAST, 0, NULL, 0);
 	      add_prefix (&include_prefixes,
 			  concat (nstore, "include", NULL),
-			  0, PREFIX_PRIORITY_LAST, 0, NULL);
+			  0, PREFIX_PRIORITY_LAST, 0, NULL, 0);
 	      if (*endp == 0)
 		break;
 	      endp = startp = endp + 1;
@@ -3267,7 +3304,7 @@ process_command (argc, argv)
 	      else
 		nstore[endp - startp] = 0;
 	      add_prefix (&startfile_prefixes, nstore, NULL,
-			  PREFIX_PRIORITY_LAST, 0, NULL);
+			  PREFIX_PRIORITY_LAST, 0, NULL, 1);
 	      if (*endp == 0)
 		break;
 	      endp = startp = endp + 1;
@@ -3300,7 +3337,7 @@ process_command (argc, argv)
 	      else
 		nstore[endp - startp] = 0;
 	      add_prefix (&startfile_prefixes, nstore, NULL,
-			  PREFIX_PRIORITY_LAST, 0, NULL);
+			  PREFIX_PRIORITY_LAST, 0, NULL, 1);
 	      if (*endp == 0)
 		break;
 	      endp = startp = endp + 1;
@@ -3401,6 +3438,8 @@ warranty; not even for MERCHANTABILITY o
 	print_multi_lib = 1;
       else if (! strcmp (argv[i], "-print-multi-directory"))
 	print_multi_directory = 1;
+      else if (! strcmp (argv[i], "-print-multi-os-directory"))
+	print_multi_os_directory = 1;
       else if (! strncmp (argv[i], "-Wa,", 4))
 	{
 	  int prev, j;
@@ -3570,7 +3609,7 @@ warranty; not even for MERCHANTABILITY o
 		  {
 		    if (len == 7)
 		      add_prefix (&include_prefixes, "include", NULL,
-				  PREFIX_PRIORITY_B_OPT, 0, NULL);
+				  PREFIX_PRIORITY_B_OPT, 0, NULL, 0);
 		    else
 		      {
 			char * string = xmalloc (len + 1);
@@ -3578,16 +3617,16 @@ warranty; not even for MERCHANTABILITY o
 			strncpy (string, value, len - 7);
 			strcpy (string + len - 7, "include");
 			add_prefix (&include_prefixes, string, NULL,
-				    PREFIX_PRIORITY_B_OPT, 0, NULL);
+				    PREFIX_PRIORITY_B_OPT, 0, NULL, 0);
 		      }
 		  }
 
 		add_prefix (&exec_prefixes, value, NULL,
-			    PREFIX_PRIORITY_B_OPT, 0, &warn_B);
+			    PREFIX_PRIORITY_B_OPT, 0, &warn_B, 0);
 		add_prefix (&startfile_prefixes, value, NULL,
-			    PREFIX_PRIORITY_B_OPT, 0, &warn_B);
+			    PREFIX_PRIORITY_B_OPT, 0, &warn_B, 0);
 		add_prefix (&include_prefixes, concat (value, "include", NULL),
-			    NULL, PREFIX_PRIORITY_B_OPT, 0, NULL);
+			    NULL, PREFIX_PRIORITY_B_OPT, 0, NULL, 0);
 		n_switches++;
 	      }
 	      break;
@@ -3760,17 +3799,17 @@ warranty; not even for MERCHANTABILITY o
      as well as trying the machine and the version.  */
 #ifndef OS2
   add_prefix (&exec_prefixes, standard_exec_prefix, "GCC",
-	      PREFIX_PRIORITY_LAST, 1, warn_std_ptr);
+	      PREFIX_PRIORITY_LAST, 1, warn_std_ptr, 0);
   add_prefix (&exec_prefixes, standard_exec_prefix, "BINUTILS",
-	      PREFIX_PRIORITY_LAST, 2, warn_std_ptr);
+	      PREFIX_PRIORITY_LAST, 2, warn_std_ptr, 0);
   add_prefix (&exec_prefixes, standard_exec_prefix_1, "BINUTILS",
-	      PREFIX_PRIORITY_LAST, 2, warn_std_ptr);
+	      PREFIX_PRIORITY_LAST, 2, warn_std_ptr, 0);
 #endif
 
   add_prefix (&startfile_prefixes, standard_exec_prefix, "BINUTILS",
-	      PREFIX_PRIORITY_LAST, 1, warn_std_ptr);
+	      PREFIX_PRIORITY_LAST, 1, warn_std_ptr, 0);
   add_prefix (&startfile_prefixes, standard_exec_prefix_1, "BINUTILS",
-	      PREFIX_PRIORITY_LAST, 1, warn_std_ptr);
+	      PREFIX_PRIORITY_LAST, 1, warn_std_ptr, 0);
 
   tooldir_prefix = concat (tooldir_base_prefix, spec_machine,
 			   dir_separator_str, NULL);
@@ -3793,11 +3832,11 @@ warranty; not even for MERCHANTABILITY o
 	  add_prefix (&exec_prefixes,
 		      concat (gcc_exec_tooldir_prefix, "bin",
 			      dir_separator_str, NULL),
-		      NULL, PREFIX_PRIORITY_LAST, 0, NULL);
+		      NULL, PREFIX_PRIORITY_LAST, 0, NULL, 0);
 	  add_prefix (&startfile_prefixes,
 		      concat (gcc_exec_tooldir_prefix, "lib",
 			      dir_separator_str, NULL),
-		      NULL, PREFIX_PRIORITY_LAST, 0, NULL);
+		      NULL, PREFIX_PRIORITY_LAST, 0, NULL, 1);
 	}
 
       tooldir_prefix = concat (standard_exec_prefix, spec_machine,
@@ -3807,10 +3846,10 @@ warranty; not even for MERCHANTABILITY o
 
   add_prefix (&exec_prefixes,
 	      concat (tooldir_prefix, "bin", dir_separator_str, NULL),
-	      "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL);
+	      "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL, 0);
   add_prefix (&startfile_prefixes,
 	      concat (tooldir_prefix, "lib", dir_separator_str, NULL),
-	      "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL);
+	      "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL, 1);
 
   /* More prefixes are enabled in main, after we read the specs file
      and determine whether this is cross-compilation or not.  */
@@ -3860,6 +3899,8 @@ warranty; not even for MERCHANTABILITY o
 	;
       else if (! strcmp (argv[i], "-print-multi-directory"))
 	;
+      else if (! strcmp (argv[i], "-print-multi-os-directory"))
+	;
       else if (! strcmp (argv[i], "-ftarget-help"))
 	;
       else if (! strcmp (argv[i], "-fhelp"))
@@ -4365,6 +4406,10 @@ do_spec_1 (spec, inswitch, soft_matched_
 		  /* Try subdirectory if there is one.  */
 		  if (multilib_dir != NULL)
 		    {
+		      const char *multi_dir;
+
+		      multi_dir = pl->os_multilib ? multilib_os_dir
+						  : multilib_dir;
 		      if (machine_suffix)
 			{
 			  if (strlen (pl->prefix) + strlen (machine_suffix)
@@ -4388,14 +4433,14 @@ do_spec_1 (spec, inswitch, soft_matched_
 			}
 		      if (!pl->require_machine_suffix)
 			{
-			  if (is_directory (pl->prefix, multilib_dir, 1))
+			  if (is_directory (pl->prefix, multi_dir, 1))
 			    {
 			      do_spec_1 ("-L", 0, NULL);
 #ifdef SPACE_AFTER_L_OPTION
 			      do_spec_1 (" ", 0, NULL);
 #endif
 			      do_spec_1 (pl->prefix, 1, NULL);
-			      do_spec_1 (multilib_dir, 1, NULL);
+			      do_spec_1 (multi_dir, 1, NULL);
 			      /* Make this a separate argument.  */
 			      do_spec_1 (" ", 0, NULL);
 			    }
@@ -5618,9 +5663,7 @@ find_file (name)
   /* Try multilib_dir if it is defined.  */
   if (multilib_dir != NULL)
     {
-      const char *const try = ACONCAT ((multilib_dir, dir_separator_str, name, NULL));
-
-      newname = find_a_file (&startfile_prefixes, try, R_OK);
+      newname = find_a_file (&startfile_prefixes, name, R_OK, 1);
 
       /* If we don't find it in the multi library dir, then fall
 	 through and look for it in the normal places.  */
@@ -5628,7 +5671,7 @@ find_file (name)
 	return newname;
     }
 
-  newname = find_a_file (&startfile_prefixes, name, R_OK);
+  newname = find_a_file (&startfile_prefixes, name, R_OK, 0);
   return newname ? newname : name;
 }
 
@@ -5863,7 +5906,7 @@ main (argc, argv)
 			   spec_version, dir_separator_str, NULL);
   just_machine_suffix = concat (spec_machine, dir_separator_str, NULL);
 
-  specs_file = find_a_file (&startfile_prefixes, "specs", R_OK);
+  specs_file = find_a_file (&startfile_prefixes, "specs", R_OK, 0);
   /* Read the specs file unless it is a default one.  */
   if (specs_file != 0 && strcmp (specs_file, "specs"))
     read_specs (specs_file, TRUE);
@@ -5888,18 +5931,18 @@ main (argc, argv)
       if (*md_exec_prefix)
 	{
 	  add_prefix (&exec_prefixes, md_exec_prefix, "GCC",
-		      PREFIX_PRIORITY_LAST, 0, NULL);
+		      PREFIX_PRIORITY_LAST, 0, NULL, 0);
 	  add_prefix (&startfile_prefixes, md_exec_prefix, "GCC",
-		      PREFIX_PRIORITY_LAST, 0, NULL);
+		      PREFIX_PRIORITY_LAST, 0, NULL, 0);
 	}
 
       if (*md_startfile_prefix)
 	add_prefix (&startfile_prefixes, md_startfile_prefix, "GCC",
-		    PREFIX_PRIORITY_LAST, 0, NULL);
+		    PREFIX_PRIORITY_LAST, 0, NULL, 1);
 
       if (*md_startfile_prefix_1)
 	add_prefix (&startfile_prefixes, md_startfile_prefix_1, "GCC",
-		    PREFIX_PRIORITY_LAST, 0, NULL);
+		    PREFIX_PRIORITY_LAST, 0, NULL, 1);
 
       /* If standard_startfile_prefix is relative, base it on
 	 standard_exec_prefix.  This lets us move the installed tree
@@ -5907,28 +5950,28 @@ main (argc, argv)
 	 standard_startfile_prefix on that as well.  */
       if (IS_ABSOLUTE_PATHNAME (standard_startfile_prefix))
 	add_prefix (&startfile_prefixes, standard_startfile_prefix, "BINUTILS",
-		    PREFIX_PRIORITY_LAST, 0, NULL);
+		    PREFIX_PRIORITY_LAST, 0, NULL, 1);
       else
 	{
 	  if (gcc_exec_prefix)
 	    add_prefix (&startfile_prefixes,
 			concat (gcc_exec_prefix, machine_suffix,
 				standard_startfile_prefix, NULL),
-			NULL, PREFIX_PRIORITY_LAST, 0, NULL);
+			NULL, PREFIX_PRIORITY_LAST, 0, NULL, 1);
 	  add_prefix (&startfile_prefixes,
 		      concat (standard_exec_prefix,
 			      machine_suffix,
 			      standard_startfile_prefix, NULL),
-		      NULL, PREFIX_PRIORITY_LAST, 0, NULL);
+		      NULL, PREFIX_PRIORITY_LAST, 0, NULL, 1);
 	}
 
       add_prefix (&startfile_prefixes, standard_startfile_prefix_1,
-		  "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL);
+		  "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL, 1);
       add_prefix (&startfile_prefixes, standard_startfile_prefix_2,
-		  "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL);
+		  "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL, 1);
 #if 0 /* Can cause surprises, and one can use -B./ instead.  */
       add_prefix (&startfile_prefixes, "./", NULL,
-		  PREFIX_PRIORITY_LAST, 1, NULL);
+		  PREFIX_PRIORITY_LAST, 1, NULL, 0);
 #endif
     }
   else
@@ -5938,14 +5981,15 @@ main (argc, argv)
 	add_prefix (&startfile_prefixes,
 		    concat (gcc_exec_prefix, machine_suffix,
 			    standard_startfile_prefix, NULL),
-		    "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL);
+		    "BINUTILS", PREFIX_PRIORITY_LAST, 0, NULL, 1);
     }
 
   /* 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);
+      char *filename = find_a_file (&startfile_prefixes, uptr->filename,
+				    R_OK, 0);
       read_specs (filename ? filename : uptr->filename, FALSE);
     }
 
@@ -5987,7 +6031,7 @@ main (argc, argv)
 
   if (print_prog_name)
     {
-      char *newname = find_a_file (&exec_prefixes, print_prog_name, X_OK);
+      char *newname = find_a_file (&exec_prefixes, print_prog_name, X_OK, 0);
       printf ("%s\n", (newname ? newname : print_prog_name));
       return (0);
     }
@@ -6007,6 +6051,15 @@ main (argc, argv)
       return (0);
     }
 
+  if (print_multi_os_directory)
+    {
+      if (multilib_os_dir == NULL)
+	printf (".\n");
+      else
+	printf ("%s\n", multilib_os_dir);
+      return (0);
+    }
+
   if (target_help_flag)
    {
       /* Print if any target specific options.  */
@@ -6166,7 +6219,7 @@ main (argc, argv)
       /* We'll use ld if we can't find collect2.  */
       if (! strcmp (linker_name_spec, "collect2"))
 	{
-	  char *s = find_a_file (&exec_prefixes, "collect2", X_OK);
+	  char *s = find_a_file (&exec_prefixes, "collect2", X_OK, 0);
 	  if (s == NULL)
 	    linker_name_spec = "ld";
 	}
@@ -6460,6 +6513,15 @@ next_member:
     goto next_member;
 }
 
+struct mdswitchstr
+{
+  const char *str;
+  int len;
+};
+
+static struct mdswitchstr *mdswitches;
+static int n_mdswitches;
+
 /* Check whether a particular argument was used.  The first time we
    canonicalize the switches to keep only the ones we care about.  */
 
@@ -6525,8 +6587,9 @@ used_arg (p, len)
 	 xmalloc from calling fatal, and prevents us from re-executing this
 	 block of code.  */
       mswitches
-	= (struct mswitchstr *) xmalloc ((sizeof (struct mswitchstr))
-					 * (n_switches ? n_switches : 1));
+	= (struct mswitchstr *)
+	  xmalloc (sizeof (struct mswitchstr)
+		   * (n_mdswitches + (n_switches ? n_switches : 1)));
       for (i = 0; i < n_switches; i++)
 	{
 	  int xlen = strlen (switches[i].part1);
@@ -6542,6 +6605,57 @@ used_arg (p, len)
 		break;
 	      }
 	}
+
+      /* Add MULTILIB_DEFAULTS switches too, as long as they were not present
+	 on the command line nor any options mutually incompatible with
+	 them.  */
+      for (i = 0; i < n_mdswitches; i++)
+	{
+	  const char *r;
+
+	  for (q = multilib_options; *q != '\0'; q++)
+	    {
+	      while (*q == ' ')
+		q++;
+
+	      r = q;
+	      while (strncmp (q, mdswitches[i].str, mdswitches[i].len) != 0
+		     || strchr (" /", q[mdswitches[i].len]) == NULL)
+		{
+		  while (*q != ' ' && *q != '/' && *q != '\0')
+		    q++;
+		  if (*q != '/')
+		    break;
+		  q++;
+		}
+
+	      if (*q != ' ' && *q != '\0')
+		{
+		  while (*r != ' ' && *r != '\0')
+		    {
+		      q = r;
+		      while (*q != ' ' && *q != '/' && *q != '\0')
+			q++;
+
+		      if (used_arg (r, q - r))
+			break;
+
+		      if (*q != '/')
+			{
+			  mswitches[n_mswitches].str = mdswitches[i].str;
+			  mswitches[n_mswitches].len = mdswitches[i].len;
+			  mswitches[n_mswitches].replace = (char *) 0;
+			  mswitches[n_mswitches].rep_len = 0;
+			  n_mswitches++;
+			  break;
+			}
+
+		      r = q + 1;
+		    }
+		  break;
+		}
+	    }
+	}
     }
 
   for (i = 0; i < n_mswitches; i++)
@@ -6556,25 +6670,11 @@ default_arg (p, len)
      const char *p;
      int len;
 {
-  const char *start, *end;
-
-  for (start = multilib_defaults; *start != '\0'; start = end + 1)
-    {
-      while (*start == ' ' || *start == '\t')
-	start++;
-
-      if (*start == '\0')
-	break;
-
-      for (end = start + 1; *end != ' ' && *end != '\t' && *end != '\0'; end++)
-	;
-
-      if ((end - start) == len && strncmp (p, start, len) == 0)
-	return 1;
+  int i;
 
-      if (*end == '\0')
-	break;
-    }
+  for (i = 0; i < n_mdswitches; i++)
+    if (len == mdswitches[i].len && ! strncmp (p, mdswitches[i].str, len))
+      return 1;
 
   return 0;
 }
@@ -6596,8 +6696,51 @@ set_multilib_dir ()
   const char *p;
   unsigned int this_path_len;
   const char *this_path, *this_arg;
+  const char *start, *end;
   int not_arg;
-  int ok;
+  int ok, ndfltok, first;
+
+  n_mdswitches = 0;
+  start = multilib_defaults;
+  while (*start == ' ' || *start == '\t')
+    start++;
+  while (*start != '\0')
+    {
+      n_mdswitches++;
+      while (*start != ' ' && *start != '\t' && *start != '\0')
+	start++;
+      while (*start == ' ' || *start == '\t')
+        start++;
+    }
+
+  if (n_mdswitches)
+    {
+      int i = 0;
+
+      mdswitches
+        = (struct mdswitchstr *) xmalloc (sizeof (struct mdswitchstr)
+					  * n_mdswitches);
+      for (start = multilib_defaults; *start != '\0'; start = end + 1)
+	{
+	  while (*start == ' ' || *start == '\t')
+	    start++;
+
+	  if (*start == '\0')
+	    break;
+                                  
+	  for (end = start + 1;
+	       *end != ' ' && *end != '\t' && *end != '\0'; end++)
+	    ;
+
+	  obstack_grow (&multilib_obstack, start, end - start);
+	  obstack_1grow (&multilib_obstack, 0);
+	  mdswitches[i].str = obstack_finish (&multilib_obstack);
+	  mdswitches[i++].len = end - start;
+
+	  if (*end == '\0')
+	    break;
+	}
+    }
 
   p = multilib_exclusions;
   while (*p != '\0')
@@ -6652,6 +6795,7 @@ set_multilib_dir ()
       ++p;
     }
 
+  first = 1;
   p = multilib_select;
   while (*p != '\0')
     {
@@ -6674,6 +6818,7 @@ set_multilib_dir ()
 
       /* Check the arguments.  */
       ok = 1;
+      ndfltok = 1;
       ++p;
       while (*p != ';')
 	{
@@ -6709,32 +6854,59 @@ set_multilib_dir ()
 	     there is a more specific library which uses this
 	     argument.  If this argument is a default, we need not
 	     consider that more specific library.  */
-	  if (! default_arg (this_arg, p - this_arg))
-	    {
-	      ok = used_arg (this_arg, p - this_arg);
-	      if (not_arg)
-		ok = ! ok;
-	    }
+	  ok = used_arg (this_arg, p - this_arg);
+	  if (not_arg)
+	    ok = ! ok;
+
+	  if (! ok)
+	    ndfltok = 0;
+
+	  if (default_arg (this_arg, p - this_arg))
+	    ok = 1;
 
 	  if (*p == ' ')
 	    ++p;
 	}
 
-      if (ok)
+      if (ok && first)
 	{
 	  if (this_path_len != 1
 	      || this_path[0] != '.')
 	    {
 	      char *new_multilib_dir = xmalloc (this_path_len + 1);
+	      char *q;
+
 	      strncpy (new_multilib_dir, this_path, this_path_len);
 	      new_multilib_dir[this_path_len] = '\0';
+	      q = strchr (new_multilib_dir, ':');
+	      if (q != NULL)
+		*q = '\0';
 	      multilib_dir = new_multilib_dir;
 	    }
-	  break;
+	  first = 0;
+	}
+
+      if (ndfltok)
+	{
+	  const char *q = this_path, *end = this_path + this_path_len;
+
+	  while (q < end && *q != ':')
+	    q++;
+	  if (*q == ':')
+	    {
+	      char *new_multilib_os_dir = xmalloc (end - q);
+	      strncpy (new_multilib_os_dir, q + 1, end - q - 1);
+	      new_multilib_os_dir[end - q] = '\0';
+	      multilib_os_dir = new_multilib_os_dir;
+	      break;
+	    }
 	}
 
       ++p;
     }
+
+  if (multilib_dir && multilib_os_dir == NULL)
+    multilib_os_dir = multilib_dir;
 }
 
 /* Print out the multiple library subdirectory selection
@@ -6915,7 +7087,7 @@ print_multilib_info ()
 	{
 	  const char *p1;
 
-	  for (p1 = last_path; p1 < p; p1++)
+	  for (p1 = last_path; p1 < p && *p1 != ':'; p1++)
 	    putchar (*p1);
 	  putchar (';');
 	}
--- gcc/mklibgcc.in.jj	Thu May  9 10:00:23 2002
+++ gcc/mklibgcc.in	Fri Sep 20 12:07:09 2002
@@ -32,7 +32,7 @@
 # SHLIB_MAPFILES
 # SHLIB_NM_FLAGS
 # SHLIB_INSTALL
-# SHLIB_SLIBDIR_SUFFIXES
+# MULTILIB_OSDIRNAMES
 
 # Make needs VPATH to be literal.
 echo 'srcdir = @srcdir@'
@@ -317,22 +317,22 @@ for ml in $MULTILIBS; do
       fi
       shlib_so_name="$shlib_base_name"
       shlib_dir=
-      if [ -n "$SHLIB_SLIBDIR_SUFFIXES" ]; then
+      if [ -n "$MULTILIB_OSDIRNAMES" ]; then
 	if [ "$dir" != . ]; then
+	  gcc_multilib_dir=`./xgcc -B./ $flags --print-multi-directory`
+	  os_multilib_dir=`./xgcc -B./ $flags --print-multi-os-directory`
 	  shlib_dir="$dir"/
-	  for suffix_pair in $SHLIB_SLIBDIR_SUFFIXES ; do
-	    base_ml_dir=`echo ${suffix_pair} | sed -e 's/:.*$//' -e 's/=/$(EQ)/g'`
-	    if [ "$dir" = "$base_ml_dir" ]; then
-	      shlib_so_name=libgcc_s
-	      break
-	    else
-	      canon_dir=`echo $dir | sed -n -e "s:$base_ml_dir/::p"`
-	      if [ -n "$canon_dir" ]; then
-		shlib_so_name=libgcc_s_`echo $canon_dir | sed s,/,_,g`
-		break
-	      fi
-	    fi
-	  done
+	  if [ "x$gcc_multilib_dir" = "x$os_multilib_dir" ]; then
+	    echo '*** --print-multi-directory '$gcc_multilib_directory' equal to --print-multi-os-directory'
+	    exit 1
+	  fi
+	  gcc_multilib_sup=`echo $gcc_multilib_dir | sed 's~^[^/]*/~~'`
+	  os_multilib_base=`echo $os_multilib_dir | sed -n "s~/${gcc_multilib_sup}\$~~p"`
+	  if [ -z "$os_multilib_base" ]; then
+	    shlib_so_name=libgcc_s
+	  else
+	    shlib_so_name=libgcc_s_`echo $gcc_multilib_sup | sed s,/,_,g`
+	  fi
 	fi
       fi
       echo ""
@@ -438,6 +438,7 @@ echo ""
 echo "install: $all"
 for ml in $MULTILIBS; do
   dir=`echo ${ml} | sed -e 's/;.*$//' -e 's/=/$(EQ)/g'`
+  flags=`echo ${ml} | sed -e 's/^[^;]*;//' -e 's/@/ -/g'`;
   if [ $dir != . ]; then
     ldir='$(libsubdir)'/$dir
     echo "	if [ -d $ldir ]; then true; else mkdir $ldir; chmod a+rx $ldir; fi;"
@@ -460,39 +461,24 @@ for ml in $MULTILIBS; do
       shlib_so_name="$shlib_base_name"
       shlib_dir=
       shlib_slibdir_qual=
-      if [ -n "$SHLIB_SLIBDIR_SUFFIXES" ]; then
-	shlib_slibdir_qual=none
+      if [ -n "$MULTILIB_OSDIRNAMES" ]; then
+	gcc_multilib_dir=`./xgcc -B./ $flags --print-multi-directory`
+	os_multilib_dir=`./xgcc -B./ $flags --print-multi-os-directory`
 	if [ "$dir" != . ]; then
 	  shlib_dir="$dir"/
-	  for suffix_pair in $SHLIB_SLIBDIR_SUFFIXES ; do
-	    base_ml_dir=`echo ${suffix_pair} | sed -e 's/:.*$//' -e 's/=/$(EQ)/g'`
-	    if [ "$dir" = "$base_ml_dir" ]; then
-	      shlib_so_name=libgcc_s
-	      shlib_slibdir_qual=`echo ${suffix_pair} | sed -e 's/^[^:]*://'`
-	      break
-	    else
-	      canon_dir=`echo $dir | sed -n -e "s:$base_ml_dir/::p"`
-	      if [ -n "$canon_dir" ]; then
-		shlib_so_name=libgcc_s_`echo $canon_dir | sed s,/,_,g`
-		shlib_slibdir_qual=`echo ${suffix_pair} | sed -e 's/^[^:]*://'`
-		break
-	      fi
-	    fi
-	  done
 	fi
-	if [ "$shlib_slibdir_qual" = none ]; then
-	  for suffix_pair in $SHLIB_SLIBDIR_SUFFIXES ; do
-	    base_ml_dir=`echo ${suffix_pair} | sed -e 's/:.*$//' -e 's/=/$(EQ)/g'`
-	    shlib_slibdir_qual=`echo ${suffix_pair} | sed -e 's/^[^:]*://'`
-	    for ml2 in $MULTILIBS; do
-	      dir2=`echo ${ml2} | sed -e 's/;.*$//' -e 's/=/$(EQ)/g'`
-	      if [ "$base_ml_dir" = "$dir2" ]; then
-		shlib_slibdir_qual=
-		break
-	      fi
-	    done
-	    if [ -n "$shlib_slibdir_qual" ]; then break; fi
-	  done
+	if [ "x$gcc_multilib_dir" = "x$os_multilib_dir" ]; then
+	  echo '*** --print-multi-directory '$gcc_multilib_directory' equal to --print-multi-os-directory'
+	  exit 1
+	fi
+	gcc_multilib_sup=`echo $gcc_multilib_dir | sed 's~^[^/]*/~~'`
+	os_multilib_base=`echo $os_multilib_dir | sed -n "s~/${gcc_multilib_sup}\$~~p"`
+	if [ -z "$os_multilib_base" ]; then
+	  shlib_so_name=libgcc_s
+	  shlib_slibdir_qual="/$os_multilib_dir"
+	else
+	  shlib_so_name=libgcc_s_`echo $gcc_multilib_sup | sed s,/,_,g`
+	  shlib_slibdir_qual="/$os_multilib_base"
 	fi
       fi
       echo "	$SHLIB_INSTALL" \
--- gcc/Makefile.in.jj	Fri May 24 17:55:06 2002
+++ gcc/Makefile.in	Fri Sep 20 09:32:51 2002
@@ -1003,7 +1003,7 @@ libgcc.mk: config.status Makefile mklibg
 	SHLIB_MKMAP_OPTS='$(SHLIB_MKMAP_OPTS)' \
 	SHLIB_MAPFILES='$(SHLIB_MAPFILES)' \
 	SHLIB_NM_FLAGS='$(SHLIB_NM_FLAGS)' \
-	SHLIB_SLIBDIR_SUFFIXES='$(SHLIB_SLIBDIR_SUFFIXES)' \
+	MULTILIB_OSDIRNAMES='$(MULTILIB_OSDIRNAMES)' \
 	mkinstalldirs='$(SHELL) $(srcdir)/mkinstalldirs' \
 	  $(SHELL) mklibgcc > tmp-libgcc.mk
 	mv tmp-libgcc.mk libgcc.mk
@@ -1045,9 +1045,10 @@ s-mlib: $(srcdir)/genmultilib Makefile
 	    "$(MULTILIB_EXCEPTIONS)" \
 	    "$(MULTILIB_EXTRA_OPTS)" \
 	    "$(MULTILIB_EXCLUSIONS)" \
+	    "$(MULTILIB_OSDIRNAMES)" \
 	    > tmp-mlib.h; \
 	else \
-	  $(SHELL) $(srcdir)/genmultilib '' '' '' '' '' '' > tmp-mlib.h; \
+	  $(SHELL) $(srcdir)/genmultilib '' '' '' '' '' '' '' > tmp-mlib.h; \
 	fi
 	$(SHELL) $(srcdir)/move-if-change tmp-mlib.h multilib.h
 	$(STAMP) s-mlib
--- gcc/config/sparc/t-linux64.jj	Wed Jul 10 05:37:40 2002
+++ gcc/config/sparc/t-linux64	Fri Sep 20 09:32:51 2002
@@ -3,6 +3,7 @@ MULTILIB_DIRNAMES = 64 32 alt 
 MULTILIB_MATCHES = mcmodel?medany=mcmodel?medmid
 MULTILIB_EXCEPTIONS = m32/mno-app-regs* m32/mcmodel=*
 MULTILIB_EXCLUSIONS = m32/!m64/mno-app-regs m32/!m64/mcmodel=medany
+MULTILIB_OSDIRNAMES = ../lib64 ../lib alt
 
 LIBGCC = stmp-multilib
 INSTALL_LIBGCC = install-multilib
@@ -10,8 +11,6 @@ INSTALL_LIBGCC = install-multilib
 EXTRA_MULTILIB_PARTS=crtbegin.o crtend.o crtbeginS.o crtendS.o crtbeginT.o \
 	crtfastmath.o
 
-SHLIB_SLIBDIR_SUFFIXES = 64:64 32:
-
 # Override t-slibgcc-elf-ver to export some libgcc symbols with
 # the symbol versions that glibc used.
 # Avoid the t-linux version file.
--- gcc/config/sparc/linux64.h.jj	Mon Apr 29 10:22:40 2002
+++ gcc/config/sparc/linux64.h	Fri Sep 20 13:12:39 2002
@@ -56,38 +56,11 @@ Boston, MA 02111-1307, USA.  */
    
 #undef  STARTFILE_SPEC
 
-#define STARTFILE_SPEC32 \
-  "%{!shared: \
-     %{pg:/usr/lib/gcrt1.o%s} %{!pg:%{/usr/lib/p:gcrt1.o%s} %{!p:/usr/lib/crt1.o%s}}}\
-   /usr/lib/crti.o%s %{static:crtbeginT.o%s}\
+#define STARTFILE_SPEC \
+  "%{!shared:%{pg:gcrt1.o%s} %{!pg:%{p:gcrt1.o%s} %{!p:crt1.o%s}}}\
+   crti.o%s %{static:crtbeginT.o%s}\
    %{!static:%{!shared:crtbegin.o%s} %{shared:crtbeginS.o%s}}"
 
-#define STARTFILE_SPEC64 \
-  "%{!shared: \
-     %{pg:/usr/lib64/gcrt1.o%s} %{!pg:%{p:/usr/lib64/gcrt1.o%s} %{!p:/usr/lib64/crt1.o%s}}}\
-   /usr/lib64/crti.o%s %{static:crtbeginT.o%s}\
-   %{!static:%{!shared:crtbegin.o%s} %{shared:crtbeginS.o%s}}"
-
-#ifdef SPARC_BI_ARCH
-
-#if DEFAULT_ARCH32_P
-#define STARTFILE_SPEC "\
-%{m32:" STARTFILE_SPEC32 "} \
-%{m64:" STARTFILE_SPEC64 "} \
-%{!m32:%{!m64:" STARTFILE_SPEC32 "}}"
-#else
-#define STARTFILE_SPEC "\
-%{m32:" STARTFILE_SPEC32 "} \
-%{m64:" STARTFILE_SPEC64 "} \
-%{!m32:%{!m64:" STARTFILE_SPEC64 "}}"
-#endif
-
-#else
-
-#define STARTFILE_SPEC STARTFILE_SPEC64
-
-#endif
-
 /* Provide a ENDFILE_SPEC appropriate for GNU/Linux.  Here we tack on
    the GNU/Linux magical crtend.o file (see crtstuff.c) which
    provides part of the support for getting C++ file-scope static
@@ -96,36 +69,9 @@ Boston, MA 02111-1307, USA.  */
 
 #undef  ENDFILE_SPEC
 
-#define ENDFILE_SPEC32 \
-  "%{!shared:crtend.o%s} %{shared:crtendS.o%s} /usr/lib/crtn.o%s"
-
-#define ENDFILE_SPEC64 \
-  "%{!shared:crtend.o%s} %{shared:crtendS.o%s} /usr/lib64/crtn.o%s"
-  
-#define ENDFILE_SPEC_COMMON \
-  "%{ffast-math|funsafe-math-optimizations:crtfastmath.o%s}"
-
-#ifdef SPARC_BI_ARCH
-
-#if DEFAULT_ARCH32_P
-#define ENDFILE_SPEC "\
-%{m32:" ENDFILE_SPEC32 "} \
-%{m64:" ENDFILE_SPEC64 "} \
-%{!m32:%{!m64:" ENDFILE_SPEC32 "}} " \
-ENDFILE_SPEC_COMMON
-#else
-#define ENDFILE_SPEC "\
-%{m32:" ENDFILE_SPEC32 "} \
-%{m64:" ENDFILE_SPEC64 "} \
-%{!m32:%{!m64:" ENDFILE_SPEC64 "}} " \
-ENDFILE_SPEC_COMMON
-#endif
-
-#else
-
-#define ENDFILE_SPEC ENDFILE_SPEC64 " " ENDFILE_SPEC_COMMON
-
-#endif
+#define ENDFILE_SPEC \
+  "%{!shared:crtend.o%s} %{shared:crtendS.o%s} crtn.o%s\
+   %{ffast-math|funsafe-math-optimizations:crtfastmath.o%s}"
 
 /* The GNU C++ standard library requires that these macros be defined.  */
 #undef CPLUSPLUS_CPP_SPEC

	Jakub


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]