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]

PATCH: Make -shared-libgcc default in some situations



In private email, David Edelsohn, Richard Henderson, and I agreed that
making -shared-libgcc the default when:

  - Building a shared library, or

  - When linking with g++

In particular, building libstdc++.so with a static libgcc (which is
what we were doing everywhere) is wrong -- and completely disastrous
on AIX where the different linker binding rules mean that you get two
copies of certain key exception-handling functions.

Here's a patch to accomplish that.

--
Mark Mitchell                   mark@codesourcery.com
CodeSourcery, LLC               http://www.codesourcery.com

2001-02-02  Mark Mitchell  <mark@codesourcery.com>

	* gcc.c (init_gcc_specs): New function.  Make -shared-libgcc 
	the default when building a shared object.
	(init_spec): Use it.
	* testsuite/lib/g++.exp: Include the directory where libgcc
	is located to the LD_LIBRARY_PATH list.
	* inovke.texi (-shared-libgcc): Document the cases in which
	GCC defaults to using the shared libgcc.
	
2001-02-02  Mark Mitchell  <mark@codesourcery.com>

	* Make-lang.in (g++spec.o): Add DRIVER_DEFINES to the list
	of macros used when compiling g++spec.c.
	* g++spec.c (lang_specific_driver): Link with the shared
	libgcc by default.

Index: gcc/gcc.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/gcc.c,v
retrieving revision 1.202
diff -c -p -r1.202 gcc.c
*** gcc.c	2001/01/16 18:02:01	1.202
--- gcc.c	2001/02/02 17:26:25
*************** static int execute			PARAMS ((void));
*** 268,273 ****
--- 268,276 ----
  static void clear_args			PARAMS ((void));
  static void fatal_error			PARAMS ((int));
  static void set_input			PARAMS ((const char *));
+ static void init_gcc_specs              PARAMS ((struct obstack *,
+ 						 const char *,
+ 						 const char *));
  
  /* Specs are strings containing lines, each of which (if not blank)
  is made up of a program name, and arguments separated by spaces.
*************** static struct spec_list *extra_specs = (
*** 1252,1257 ****
--- 1255,1289 ----
  
  static struct spec_list *specs = (struct spec_list *) 0;
  
+ /* Add appropriate libgcc specs to OBSTACK, taking into account
+    various permutations of -shared-libgcc, -shared, and such.  */
+ 
+ static void
+ init_gcc_specs (obstack, shared_name, static_name)
+      struct obstack *obstack;
+      const char *shared_name;
+      const char *static_name;
+ {
+   char buffer[128];
+ 
+   /* If we see -shared-libgcc, then use the shared version.  */
+   sprintf (buffer, "%%{shared-libgcc:%s}", shared_name);
+   obstack_grow (obstack, buffer, strlen (buffer));
+   /* If we see -static-libgcc, then use the shared version.  */
+   sprintf (buffer, "%%{static-libgcc:%s}", static_name);
+   obstack_grow (obstack, buffer, strlen (buffer));
+   /* Otherwise, if we see -shared, then use the shared version.  */
+   sprintf (buffer,
+ 	   "%%{!shared-libgcc:%%{!static-libgcc:%%{shared:%s}}}", 
+ 	   shared_name);
+   obstack_grow (obstack, buffer, strlen (buffer));
+   /* Otherwise, use the static version.  */
+   sprintf (buffer, 
+ 	   "%%{!shared-libgcc:%%{!static-libgcc:%%{!shared:%s}}}", 
+ 	   static_name);
+   obstack_grow (obstack, buffer, strlen (buffer));
+ }
+ 
  /* Initialize the specs lookup routines.  */
  
  static void
*************** init_spec ()
*** 1326,1340 ****
         when given the proper command line arguments.  */
      while (*p)
        {
- 	const char *r;
          if (in_sep && *p == '-' && strncmp (p, "-lgcc", 5) == 0)
  	  {
  #ifdef NO_SHARED_LIBGCC_MULTILIB
! 	    r = "%{shared-libgcc:-lgcc_s}%{!shared-libgcc:-lgcc}";
  #else
! 	    r = "%{shared-libgcc:-lgcc_s%M}%{!shared-libgcc:-lgcc}";
  #endif
! 	    obstack_grow (&obstack, r, strlen(r));
  	    p += 5;
  	    in_sep = 0;
  	  }
--- 1358,1373 ----
         when given the proper command line arguments.  */
      while (*p)
        {
          if (in_sep && *p == '-' && strncmp (p, "-lgcc", 5) == 0)
  	  {
+ 	    init_gcc_specs (&obstack,
  #ifdef NO_SHARED_LIBGCC_MULTILIB
! 			    "-lgcc_s"
  #else
! 			    "-lgcc_s%M"
  #endif
! 			    ,
! 			    "-lgcc");
  	    p += 5;
  	    in_sep = 0;
  	  }
*************** init_spec ()
*** 1342,1353 ****
  	  {
  	    /* Ug.  We don't know shared library extensions.  Hope that
  	       systems that use this form don't do shared libraries.  */
  #ifdef NO_SHARED_LIBGCC_MULTILIB
! 	    r = "%{shared-libgcc:-lgcc_s}%{!shared-libgcc:libgcc.a%s}";
  #else
! 	    r = "%{shared-libgcc:-lgcc_s%M}%{!shared-libgcc:libgcc.a%s}";
  #endif
! 	    obstack_grow (&obstack, r, strlen(r));
  	    p += 10;
  	    in_sep = 0;
  	  }
--- 1375,1388 ----
  	  {
  	    /* Ug.  We don't know shared library extensions.  Hope that
  	       systems that use this form don't do shared libraries.  */
+ 	    init_gcc_specs (&obstack,
  #ifdef NO_SHARED_LIBGCC_MULTILIB
! 			    "-lgcc_s"
  #else
! 			    "-lgcc_s%M"
  #endif
! 			    ,
! 			    "libgcc.a%s");
  	    p += 10;
  	    in_sep = 0;
  	  }
Index: gcc/cp/Make-lang.in
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/Make-lang.in,v
retrieving revision 1.74
diff -c -p -r1.74 Make-lang.in
*** Make-lang.in	2001/01/28 01:50:08	1.74
--- Make-lang.in	2001/02/02 17:26:36
*************** C++ c++: cc1plus$(exeext)
*** 61,67 ****
  .PHONY: C++ c++
  
  g++spec.o: $(srcdir)/cp/g++spec.c system.h $(GCC_H) $(CONFIG_H)
! 	$(CC) -c $(ALL_CFLAGS) $(ALL_CPPFLAGS) $(INCLUDES) $(srcdir)/cp/g++spec.c
  
  $(INTL_TARGETS): $(srcdir)/cp/parse.c
  
--- 61,68 ----
  .PHONY: C++ c++
  
  g++spec.o: $(srcdir)/cp/g++spec.c system.h $(GCC_H) $(CONFIG_H)
! 	$(CC) -c $(ALL_CFLAGS) $(ALL_CPPFLAGS) $(DRIVER_DEFINES) \
! 		$(INCLUDES) $(srcdir)/cp/g++spec.c
  
  $(INTL_TARGETS): $(srcdir)/cp/parse.c
  
Index: gcc/cp/g++spec.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/g++spec.c,v
retrieving revision 1.23
diff -c -p -r1.23 g++spec.c
*** g++spec.c	2001/01/19 15:12:33	1.23
--- g++spec.c	2001/02/02 17:26:43
***************
*** 1,5 ****
  /* Specific flags and argument handling of the C++ front-end.
!    Copyright (C) 1996, 1997, 1998, 1999, 2000 Free Software Foundation, Inc.
  
  This file is part of GNU CC.
  
--- 1,5 ----
  /* Specific flags and argument handling of the C++ front-end.
!    Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001 Free Software Foundation, Inc.
  
  This file is part of GNU CC.
  
*************** lang_specific_driver (in_argc, in_argv, 
*** 82,87 ****
--- 82,90 ----
    /* By default, we throw on the math library if we have one.  */
    int need_math = (MATH_LIBRARY[0] != '\0');
  
+   /* True if we should add -shared-libgcc to the command-line.  */
+   int shared_libgcc = 1;
+ 
    /* The total number of arguments with the new stuff.  */
    int argc;
  
*************** lang_specific_driver (in_argc, in_argv, 
*** 160,165 ****
--- 163,171 ----
  	      library = 0;
  	      added -= 2;
  	    }
+ 	  else if (strcmp (argv[i], "-static-libgcc") == 0 
+ 		   || strcmp (argv[i], "-static") == 0)
+ 	    shared_libgcc = 0;
  	  else
  	    /* Pass other options through.  */
  	    continue;
*************** lang_specific_driver (in_argc, in_argv, 
*** 197,204 ****
        return;
      }
  
    /* Make sure to have room for the trailing NULL argument.  */
!   num_args = argc + added + need_math + 1;
    arglist = (const char **) xmalloc (num_args * sizeof (char *));
  
    i = 0;
--- 203,216 ----
        return;
      }
  
+   /* There's no point adding -shared-libgcc if we don't have a shared
+      libgcc.  */
+ #ifndef ENABLE_SHARED_LIBGCC
+   shared_libgcc = 0;
+ #endif
+ 
    /* Make sure to have room for the trailing NULL argument.  */
!   num_args = argc + added + need_math + shared_libgcc + 1;
    arglist = (const char **) xmalloc (num_args * sizeof (char *));
  
    i = 0;
*************** lang_specific_driver (in_argc, in_argv, 
*** 258,263 ****
--- 270,277 ----
      }
    if (saw_libc)
      arglist[j++] = saw_libc;
+   if (shared_libgcc)
+     arglist[j++] = "-shared-libgcc";
  
    arglist[j] = NULL;
  
Index: gcc/testsuite/lib/g++.exp
===================================================================
RCS file: /cvs/gcc/gcc/gcc/testsuite/lib/g++.exp,v
retrieving revision 1.15
diff -c -p -r1.15 g++.exp
*** g++.exp	2000/12/29 22:25:57	1.15
--- g++.exp	2001/02/02 17:26:50
***************
*** 1,4 ****
! # Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 2000 Free Software Foundation, Inc.
  
  # This program is free software; you can redistribute it and/or modify
  # it under the terms of the GNU General Public License as published by
--- 1,4 ----
! # Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 2000, 2001 Free Software Foundation, Inc.
  
  # This program is free software; you can redistribute it and/or modify
  # it under the terms of the GNU General Public License as published by
*************** proc g++_include_flags { args } {
*** 97,102 ****
--- 97,103 ----
  }
  
  proc g++_link_flags { args } {
+     global rootme
      global srcdir
      global ld_library_path
  
*************** proc g++_link_flags { args } {
*** 127,132 ****
--- 128,134 ----
        if [file exists "${gccpath}/librx/librx.a"] {
            append flags "-L${gccpath}/librx "
        }
+       append ld_library_path ":${rootme}"
      } else {
        global tool_root_dir;
  
Index: invoke.texi
===================================================================
RCS file: /cvs/gcc/gcc/gcc/invoke.texi,v
retrieving revision 1.270
diff -c -p -r1.270 invoke.texi
*** invoke.texi	2001/01/23 21:35:15	1.270
--- invoke.texi	2001/02/02 17:34:36
*************** of these is when the application wishes 
*** 3688,3698 ****
  across different shared libraries.  In that case, each of the libraries
  as well as the application itself should use the shared @file{libgcc}.
  
! At present the GCC driver makes no attempt to recognize the situations
! in which the shared @file{libgcc} should be used, and defaults to using
! the static @file{libgcc} always.  This will likely change in the future,
! at which time @samp{-static-libgcc} becomes useful as a means for 
! overriding GCC's choice.
  
  @item -symbolic
  Bind references to global symbols when building a shared object.  Warn
--- 3688,3703 ----
  across different shared libraries.  In that case, each of the libraries
  as well as the application itself should use the shared @file{libgcc}.
  
! Therefore, whenever you specify the @samp{-shared} option, the GCC
! driver automatically adds @samp{-shared-libgcc}, unless you explicitly
! specify @samp{-static-libgcc}.  The G++ driver automatically adds
! @samp{-shared-libgcc} when you build a main executable as well because
! for C++ programs that is typically the right thing to do.
! (Exception-handling will not work reliably otherwise.)
! 
! However, when linking a main executable written in C, you must
! explicitly say @samp{-shared-libgcc} if you want to use the shared
! @file{libgcc}.
  
  @item -symbolic
  Bind references to global symbols when building a shared object.  Warn

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