[PATCH] Fix linking C executables/shared libraries which use __attribute__((cleanup ())) (take 2)

Jakub Jelinek jakub@redhat.com
Sat Mar 27 22:28:00 GMT 2004


On Sat, Mar 27, 2004 at 02:50:02PM +0100, Jakub Jelinek wrote:
> For 3.4/3.3 as well (bootstrapped/regtested in 3.4 on x86_64-redhat-linux
> so far)?

Actually further testing on gcc 3.3 revealed a problem: when using a stageN/
compiler -lgcc_s couldn't be found, if the same version of the compiler
hasn't been installed.
So below are new patches which copy libgcc_s*.so to stageN/ directories
(both gcc-3_3-branch and gcc-3_4-branch versions).
Ok?

	Jakub
-------------- next part --------------
2004-03-27  Alan Modra  <amodra@bigpond.net.au>
	    Jakub Jelinek  <jakub@redhat.com>

	* gcc.c (init_gcc_specs): If HAVE_LD_AS_NEEDED, link with
	-lgcc --as-needed -lgcc_s --no-as-needed by default.
	* configure.ac (HAVE_LD_AS_NEEDED): Check for ld --as-needed.
	* configure: Rebuilt.
	* config.in: Rebuilt.
	* Makefile.in (stage1-start): Copy also libgcc_s*$(SHLIB_EXT).
	(stage2-start, stage3-start, stage4-start): Likewise.
	(stageprofile-start, stagefeedback-start): Likewise.

--- gcc/gcc.c.jj	2004-03-08 18:49:01.000000000 +0100
+++ gcc/gcc.c	2004-03-27 10:20:10.651163833 +0100
@@ -1531,6 +1531,12 @@ init_gcc_specs (struct obstack *obstack,
 
   buf = concat ("%{static|static-libgcc:", static_name, " ", eh_name,
 		"}%{!static:%{!static-libgcc:",
+#ifdef HAVE_LD_AS_NEEDED
+		"%{!shared-libgcc:", static_name,
+		" --as-needed ", shared_name, " --no-as-needed}"
+		"%{shared-libgcc:", shared_name, "%{!shared: ", static_name,
+		"}",
+#else
 		"%{!shared:%{!shared-libgcc:", static_name, " ",
 		eh_name, "}%{shared-libgcc:", shared_name, " ",
 		static_name, "}}%{shared:",
@@ -1540,6 +1546,7 @@ init_gcc_specs (struct obstack *obstack,
 #else
 		shared_name,
 #endif
+#endif
 		"}}}", NULL);
 
   obstack_grow (obstack, buf, strlen (buf));
--- gcc/configure.ac.jj	2004-03-08 18:49:00.000000000 +0100
+++ gcc/configure.ac	2004-03-27 09:53:42.912708012 +0100
@@ -2627,6 +2627,25 @@ if test x"$gcc_cv_ld_pie" = xyes; then
 fi
 AC_MSG_RESULT($gcc_cv_ld_pie)
 
+AC_MSG_CHECKING(linker --as-needed support)
+gcc_cv_ld_as_needed=no
+if test $in_tree_ld = yes ; then
+  if test "$gcc_cv_gld_major_version" -eq 2 -a "$gcc_cv_gld_minor_version" -ge 16 -o "$gcc_cv_gld_major_version" -gt 2 \
+     && test $in_tree_ld_is_elf = yes; then
+    gcc_cv_ld_as_needed=yes
+  fi
+elif test x$gcc_cv_ld != x; then
+	# Check if linker supports --as-needed and --no-as-needed options
+	if $gcc_cv_ld --help 2>/dev/null | grep as-needed > /dev/null; then
+		gcc_cv_ld_as_needed=yes
+	fi
+fi
+if test x"$gcc_cv_ld_as_needed" = xyes; then
+	AC_DEFINE(HAVE_LD_AS_NEEDED, 1,
+[Define if your linker supports --as-needed and --no-as-needed options.])
+fi
+AC_MSG_RESULT($gcc_cv_ld_as_needed)
+
 if test x$with_sysroot = x && test x$host = x$target \
    && test "$prefix" != "/usr" && test "x$prefix" != "x$local_prefix" ; then
   AC_DEFINE_UNQUOTED(PREFIX_INCLUDE_DIR, "$prefix/include",
--- gcc/configure.jj	2004-03-16 16:24:42.000000000 +0100
+++ gcc/configure	2004-03-27 09:56:51.886841295 +0100
@@ -11311,6 +11311,30 @@ fi
 echo "$as_me:$LINENO: result: $gcc_cv_ld_pie" >&5
 echo "${ECHO_T}$gcc_cv_ld_pie" >&6
 
+echo "$as_me:$LINENO: checking linker --as-needed support" >&5
+echo $ECHO_N "checking linker --as-needed support... $ECHO_C" >&6
+gcc_cv_ld_as_needed=no
+if test $in_tree_ld = yes ; then
+  if test "$gcc_cv_gld_major_version" -eq 2 -a "$gcc_cv_gld_minor_version" -ge 16 -o "$gcc_cv_gld_major_version" -gt 2 \
+     && test $in_tree_ld_is_elf = yes; then
+    gcc_cv_ld_as_needed=yes
+  fi
+elif test x$gcc_cv_ld != x; then
+	# Check if linker supports --as-needed and --no-as-needed options
+	if $gcc_cv_ld --help 2>/dev/null | grep as-needed > /dev/null; then
+		gcc_cv_ld_as_needed=yes
+	fi
+fi
+if test x"$gcc_cv_ld_as_needed" = xyes; then
+
+cat >>confdefs.h <<\_ACEOF
+#define HAVE_LD_AS_NEEDED 1
+_ACEOF
+
+fi
+echo "$as_me:$LINENO: result: $gcc_cv_ld_as_needed" >&5
+echo "${ECHO_T}$gcc_cv_ld_as_needed" >&6
+
 if test x$with_sysroot = x && test x$host = x$target \
    && test "$prefix" != "/usr" && test "x$prefix" != "x$local_prefix" ; then
 
--- gcc/config.in.jj	2004-03-16 16:24:41.000000000 +0100
+++ gcc/config.in	2004-03-27 09:55:54.922050155 +0100
@@ -306,6 +306,9 @@
 /* Define to 1 if you have the <ldfcn.h> header file. */
 #undef HAVE_LDFCN_H
 
+/* Define if your linker supports --as-needed and --no-as-needed options. */
+#undef HAVE_LD_AS_NEEDED
+
 /* Define if your linker supports --eh-frame-hdr option. */
 #undef HAVE_LD_EH_FRAME_HDR
 
--- gcc/Makefile.in.jj	2004-03-02 18:56:53.000000000 +0100
+++ gcc/Makefile.in	2004-03-27 23:18:18.435082287 +0100
@@ -3605,6 +3605,7 @@ stage1-start:
 	-if [ -f ld$(exeext) ] ; then (cd stage1 && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stage1 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
 	-rm -f stage1/libgcc.a stage1/libgcc_eh.a stage1/libgcov.a
+	-rm -f stage1/libgcc_s*$(SHLIB_EXT)
 	-cp libgcc.a stage1
 	-$(RANLIB_FOR_TARGET) stage1/libgcc.a
 	-cp libgcov.a stage1
@@ -3612,6 +3613,7 @@ stage1-start:
 	-if [ -f libgcc_eh.a ] ; then cp libgcc_eh.a stage1; \
 	   $(RANLIB_FOR_TARGET) stage1/libgcc_eh.a; \
 	fi
+	-cp libgcc_s*$(SHLIB_EXT) stage1
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stage1/$${f} . ; \
 	else true; \
@@ -3638,6 +3640,7 @@ stage2-start:
 	-if [ -f ld$(exeext) ] ; then (cd stage2 && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stage2 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
 	-rm -f stage2/libgcc.a stage2/libgcov.a stage2/libgcc_eh.a
+	-rm -f stage2/libgcc_s*$(SHLIB_EXT)
 	-cp libgcc.a stage2
 	-$(RANLIB_FOR_TARGET) stage2/libgcc.a
 	-cp libgcov.a stage2
@@ -3645,6 +3648,7 @@ stage2-start:
 	-if [ -f libgcc_eh.a ] ; then cp libgcc_eh.a stage2; \
 	   $(RANLIB_FOR_TARGET) stage2/libgcc_eh.a; \
 	fi
+	-cp libgcc_s*$(SHLIB_EXT) stage2
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stage2/$${f} . ; \
 	else true; \
@@ -3667,6 +3671,7 @@ stage3-start:
 	-if [ -f ld$(exeext) ] ; then (cd stage3 && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stage3 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
 	-rm -f stage3/libgcc.a stage3/libgcov.a stage3/libgcc_eh.a
+	-rm -f stage3/libgcc_s*$(SHLIB_EXT)
 	-cp libgcc.a stage3
 	-$(RANLIB_FOR_TARGET) stage3/libgcc.a
 	-cp libgcov.a stage3
@@ -3674,6 +3679,7 @@ stage3-start:
 	-if [ -f libgcc_eh.a ] ; then cp libgcc_eh.a stage3; \
 	   $(RANLIB_FOR_TARGET) stage3/libgcc_eh.a; \
 	fi
+	-cp libgcc_s*$(SHLIB_EXT) stage3
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stage3/$${f} . ; \
 	else true; \
@@ -3696,6 +3702,7 @@ stage4-start:
 	-if [ -f ld$(exeext) ] ; then (cd stage4 && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stage4 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
 	-rm -f stage4/libgcc.a stage4/libgcov.a stage4/libgcc_eh.a
+	-rm -f stage4/libgcc_s*$(SHLIB_EXT)
 	-cp libgcc.a stage4
 	-$(RANLIB_FOR_TARGET) stage4/libgcc.a
 	-cp libgcov.a stage4
@@ -3703,6 +3710,7 @@ stage4-start:
 	-if [ -f libgcc_eh.a ] ; then cp libgcc_eh.a stage4; \
 	   $(RANLIB_FOR_TARGET) stage4/libgcc_eh.a; \
 	fi
+	-cp libgcc_s*$(SHLIB_EXT) stage4
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stage4/$${f} . ; \
 	else true; \
@@ -3723,6 +3731,7 @@ stageprofile-start:
 	-if [ -f ld$(exeext) ] ; then (cd stageprofile && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stageprofile && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
 	-rm -f stageprofile/libgcc.a stageprofile/libgcov.a stageprofile/libgcc_eh.a
+	-rm -f stageprofile/libgcc_s*$(SHLIB_EXT)
 	-cp libgcc.a stageprofile
 	-$(RANLIB_FOR_TARGET) stageprofile/libgcc.a
 	-cp libgcov.a stageprofile
@@ -3730,6 +3739,7 @@ stageprofile-start:
 	-if [ -f libgcc_eh.a ] ; then cp libgcc_eh.a stageprofile; \
 	   $(RANLIB_FOR_TARGET) stageprofile/libgcc_eh.a; \
 	fi
+	-cp libgcc_s*$(SHLIB_EXT) stageprofile
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stageprofile/$${f} . ; \
 	else true; \
@@ -3750,6 +3760,7 @@ stagefeedback-start:
 	-if [ -f ld$(exeext) ] ; then (cd stagefeedback && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stagefeedback && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
 	-rm -f stagefeedback/libgcc.a stagefeedback/libgcov.a stagefeedback/libgcc_eh.a
+	-rm -f stagefeedback/libgcc_s*$(SHLIB_EXT)
 	-rm -f *.da
 	-for dir in fixinc po testsuite $(SUBDIRS); \
 	 do \
@@ -3762,6 +3773,7 @@ stagefeedback-start:
 	-if [ -f libgcc_eh.a ] ; then cp libgcc_eh.a stagefeedback; \
 	   $(RANLIB_FOR_TARGET) stagefeedback/libgcc_eh.a; \
 	fi
+	-cp libgcc_s*$(SHLIB_EXT) stagefeedback
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stagefeedback/$${f} . ; \
 	else true; \
-------------- next part --------------
2004-03-27  Alan Modra  <amodra@bigpond.net.au>
	    Jakub Jelinek  <jakub@redhat.com>

	* gcc.c (init_gcc_specs): If HAVE_LD_AS_NEEDED, link with
	-lgcc --as-needed -lgcc_s --no-as-needed by default.
	* configure.ac (HAVE_LD_AS_NEEDED): Check for ld --as-needed.
	* configure: Rebuilt.
	* config.in: Rebuilt.
	* Makefile.in (stage1-start): Copy also libgcc_s*$(SHLIB_EXT).
	(stage2-start, stage3-start, stage4-start): Likewise.

--- gcc/gcc.c.jj	2003-12-19 10:16:22.000000000 +0100
+++ gcc/gcc.c	2004-03-27 17:43:12.080412644 +0100
@@ -1477,6 +1477,12 @@ init_gcc_specs (obstack, shared_name, st
 
   buf = concat ("%{static|static-libgcc:", static_name, " ", eh_name,
 		"}%{!static:%{!static-libgcc:",
+#ifdef HAVE_LD_AS_NEEDED
+		"%{!shared-libgcc:", static_name,
+		" --as-needed ", shared_name, " --no-as-needed}"
+		"%{shared-libgcc:", shared_name, "%{!shared: ", static_name,
+		"}",
+#else
 		"%{!shared:%{!shared-libgcc:", static_name, " ",
 		eh_name, "}%{shared-libgcc:", shared_name, " ",
 		static_name, "}}%{shared:",
@@ -1486,6 +1492,7 @@ init_gcc_specs (obstack, shared_name, st
 #else
 		shared_name,
 #endif
+#endif
 		"}}}", NULL);
 
   obstack_grow (obstack, buf, strlen (buf));
--- gcc/config.in.jj	2003-12-03 13:30:48.000000000 +0100
+++ gcc/config.in	2004-03-27 17:46:52.162970877 +0100
@@ -624,6 +624,9 @@
 /* Define if your linker supports -pie option. */
 #undef HAVE_LD_PIE
 
+/* Define if your linker supports --as-needed and --no-as-needed options. */
+#undef HAVE_LD_AS_NEEDED
+
 /* Define if your MIPS libgloss linker scripts consistently include STARTUP directives. */
 #undef HAVE_MIPS_LIBGLOSS_STARTUP_DIRECTIVES
 
--- gcc/configure.in.jj	2003-12-03 13:30:52.000000000 +0100
+++ gcc/configure.in	2004-03-27 17:45:25.649475264 +0100
@@ -2560,6 +2560,24 @@ if test x"$gcc_cv_ld_pie" = xyes; then
 fi
 AC_MSG_RESULT($gcc_cv_ld_pie)
 
+AC_MSG_CHECKING(linker --as-needed support)
+gcc_cv_ld_as_needed=no
+if test x$gcc_cv_gld_major_version != x -a x$gcc_cv_gld_minor_version != x; then
+  if test "$gcc_cv_gld_major_version" -eq 2 -a "$gcc_cv_gld_minor_version" -ge 16 -o "$gcc_cv_gld_major_version" -gt 2 && grep 'EMUL = elf' ../ld/Makefile > /dev/null; then
+    gcc_cv_ld_as_needed=yes
+  fi
+elif test x$gcc_cv_ld != x; then
+	# Check if linker supports --as-needed and --no-as-needed options
+	if $gcc_cv_ld --help 2>/dev/null | grep as-needed > /dev/null; then
+		gcc_cv_ld_as_needed=yes
+	fi
+fi
+if test x"$gcc_cv_ld_as_needed" = xyes; then
+	AC_DEFINE(HAVE_LD_AS_NEEDED, 1,
+[Define if your linker supports --as-needed and --no-as-needed options.])
+fi
+AC_MSG_RESULT($gcc_cv_ld_as_needed)
+
 # Miscellaneous target-specific checks.
 case "$target" in
   mips*-*-*)
--- gcc/configure.jj	2003-12-03 13:30:52.000000000 +0100
+++ gcc/configure	2004-03-27 17:48:03.094259032 +0100
@@ -8245,6 +8245,27 @@ EOF
 fi
 echo "$ac_t""$gcc_cv_ld_pie" 1>&6
 
+echo $ac_n "checking linker --as-needed support""... $ac_c" 1>&6
+echo "configure:8250: checking linker --as-needed support" >&5
+gcc_cv_ld_as_needed=no
+if test x$gcc_cv_gld_major_version != x -a x$gcc_cv_gld_minor_version != x; then
+  if test "$gcc_cv_gld_major_version" -eq 2 -a "$gcc_cv_gld_minor_version" -ge 16 -o "$gcc_cv_gld_major_version" -gt 2 && grep 'EMUL = elf' ../ld/Makefile > /dev/null; then
+    gcc_cv_ld_as_needed=yes
+  fi
+elif test x$gcc_cv_ld != x; then
+	# Check if linker supports --as-needed and --no-as-needed options
+	if $gcc_cv_ld --help 2>/dev/null | grep as-needed > /dev/null; then
+		gcc_cv_ld_as_needed=yes
+	fi
+fi
+if test x"$gcc_cv_ld_as_needed" = xyes; then
+	cat >> confdefs.h <<\EOF
+#define HAVE_LD_AS_NEEDED 1
+EOF
+
+fi
+echo "$ac_t""$gcc_cv_ld_as_needed" 1>&6
+
 # Miscellaneous target-specific checks.
 case "$target" in
   mips*-*-*)
--- gcc/Makefile.in.jj	2004-03-12 14:12:26.000000000 +0100
+++ gcc/Makefile.in	2004-03-27 20:20:53.646772144 +0100
@@ -3549,7 +3549,7 @@ stage1-start:
 	-if [ -f as$(exeext) ] ; then (cd stage1 && $(LN_S) ../as$(exeext) .) ; else true ; fi
 	-if [ -f ld$(exeext) ] ; then (cd stage1 && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stage1 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
-	-rm -f stage1/libgcc.a stage1/libgcc_eh.a
+	-rm -f stage1/libgcc.a stage1/libgcc_eh.a stage1/libgcc_s*$(SHLIB_EXT)
 	-cp libgcc.a stage1
 	-if $(RANLIB_TEST_FOR_TARGET) ; then \
 	  $(RANLIB_FOR_TARGET) stage1/libgcc.a; \
@@ -3558,6 +3558,7 @@ stage1-start:
 	  if $(RANLIB_TEST_FOR_TARGET) ; then \
 	   $(RANLIB_FOR_TARGET) stage1/libgcc_eh.a; \
 	  else true; fi; fi
+	-cp libgcc_s*$(SHLIB_EXT) stage1/
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stage1/$${f} . ; \
 	else true; \
@@ -3578,7 +3579,7 @@ stage2-start:
 	-if [ -f as$(exeext) ] ; then (cd stage2 && $(LN_S) ../as$(exeext) .) ; else true ; fi
 	-if [ -f ld$(exeext) ] ; then (cd stage2 && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stage2 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
-	-rm -f stage2/libgcc.a stage2/libgcc_eh.a
+	-rm -f stage2/libgcc.a stage2/libgcc_eh.a stage2/libgcc_s*$(SHLIB_EXT)
 	-cp libgcc.a stage2
 	-if $(RANLIB_TEST_FOR_TARGET) ; then \
 	  $(RANLIB_FOR_TARGET) stage2/libgcc.a; \
@@ -3587,6 +3588,7 @@ stage2-start:
 	  if $(RANLIB_TEST_FOR_TARGET) ; then \
 	   $(RANLIB_FOR_TARGET) stage2/libgcc_eh.a; \
 	  else true; fi; fi
+	-cp libgcc_s*$(SHLIB_EXT) stage2/
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stage2/$${f} . ; \
 	else true; \
@@ -3607,7 +3609,7 @@ stage3-start:
 	-if [ -f as$(exeext) ] ; then (cd stage3 && $(LN_S) ../as$(exeext) .) ; else true ; fi
 	-if [ -f ld$(exeext) ] ; then (cd stage3 && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stage3 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
-	-rm -f stage3/libgcc.a stage3/libgcc_eh.a
+	-rm -f stage3/libgcc.a stage3/libgcc_eh.a stage3/libgcc_s*$(SHLIB_EXT)
 	-cp libgcc.a stage3
 	-if $(RANLIB_TEST_FOR_TARGET) ; then \
 	  $(RANLIB_FOR_TARGET) stage3/libgcc.a; \
@@ -3616,6 +3618,7 @@ stage3-start:
 	  if $(RANLIB_TEST_FOR_TARGET) ; then \
 	   $(RANLIB_FOR_TARGET) stage3/libgcc_eh.a; \
 	  else true; fi; fi
+	-cp libgcc_s*$(SHLIB_EXT) stage3/
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stage3/$${f} . ; \
 	else true; \
@@ -3636,7 +3639,7 @@ stage4-start:
 	-if [ -f as$(exeext) ] ; then (cd stage4 && $(LN_S) ../as$(exeext) .) ; else true ; fi
 	-if [ -f ld$(exeext) ] ; then (cd stage4 && $(LN_S) ../ld$(exeext) .) ; else true ; fi
 	-if [ -f collect-ld$(exeext) ] ; then (cd stage4 && $(LN_S) ../collect-ld$(exeext) .) ; else true ; fi
-	-rm -f stage4/libgcc.a stage4/libgcc_eh.a
+	-rm -f stage4/libgcc.a stage4/libgcc_eh.a stage4/libgcc_s*$(SHLIB_EXT)
 	-cp libgcc.a stage4
 	-if $(RANLIB_TEST_FOR_TARGET) ; then \
 	  $(RANLIB_FOR_TARGET) stage4/libgcc.a; \
@@ -3645,6 +3648,7 @@ stage4-start:
 	  if $(RANLIB_TEST_FOR_TARGET) ; then \
 	   $(RANLIB_FOR_TARGET) stage4/libgcc_eh.a; \
 	  else true; fi; fi
+	-cp libgcc_s*$(SHLIB_EXT) stage4/
 	-for f in .. $(EXTRA_MULTILIB_PARTS); do if [ x$${f} != x.. ]; then \
 	  cp stage4/$${f} . ; \
 	else true; \


More information about the Gcc-patches mailing list