This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[PATCH] Fix sparc64-linux ABI problem
- From: Jakub Jelinek <jakub at redhat dot com>
- To: mark at codesourcery dot com, davem at redhat dot com, rth at redhat dot com
- Cc: gcc-patches at gcc dot gnu dot org
- Date: Tue, 7 May 2002 18:27:30 +0200
- Subject: [PATCH] Fix sparc64-linux ABI problem
- Reply-to: Jakub Jelinek <jakub at redhat dot com>
Hi!
As I found during testing my previous patch, libgcc_s uses GLIBC_2.0
symbol versions for __*register_frame* functions, but glibc has no
such symbol version on sparc64 (it has GLIBC_2.2 and up). The problem
I was seeing was that libm wanted __register_frame_info@GLIBC_2.2 and
__deregister_frame_info@GLIBC_2.2, so used the glibc version eventhough
it should have used the libgcc_s version. __register_frame_info calls
__register_frame_info_bases and this call was inlined, so registration went
in glibc, but deregistration was not inlined and
__deregister_frame_info_bases@GCC_3.0 symbol in libgcc_s was earlier than
glibc's __deregister_frame_info_bases@GCC_3.0.
Unfortunately, on sparc-linux we want @GLIBC_2.0.
Fixed below by running the *.ver files through preprocessor first (with
proper multilib options) before they are passed to the mkmap script.
As .ver script use # as comment character, I chose
%ifdef/%define/%else/%elif/%define/%endif (before being fed through
the preprocessor, # comments are stripped and for the above % is
replaced with #).
Tested on sparc64-linux.
2002-05-07 Jakub Jelinek <jakub@redhat.com>
* config/sparc/t-linux64 (SHLIB_MAPFILES): Set.
* config/sparc/libgcc-sparc-glibc.ver: New file.
* mklibgcc.in: Preprocess SHLIB_MAPFILES with ml flags.
--- gcc/config/sparc/libgcc-sparc-glibc.ver.jj Tue May 7 17:33:41 2002
+++ gcc/config/sparc/libgcc-sparc-glibc.ver Tue May 7 17:34:50 2002
@@ -0,0 +1,28 @@
+# In order to work around the very problems that force us to now generally
+# create a libgcc.so, glibc reexported a number of routines from libgcc.a.
+# By now choosing the same version tags for these specific routines, we
+# maintain enough binary compatibility to allow future versions of glibc
+# to defer implementation of these routines to libgcc.so via DT_AUXILIARY.
+
+%ifdef __arch64__
+%define GLIBC_VER GLIBC_2.2
+%else
+%define GLIBC_VER GLIBC_2.0
+%endif
+%inherit GCC_3.0 GLIBC_VER
+GLIBC_VER {
+ # Sampling of DImode arithmetic used by (at least) i386 and m68k.
+ __divdi3
+ __moddi3
+ __udivdi3
+ __umoddi3
+
+ # Exception handling support functions used by most everyone.
+ __register_frame
+ __register_frame_table
+ __deregister_frame
+ __register_frame_info
+ __deregister_frame_info
+ __frame_state_for
+ __register_frame_info_table
+}
--- gcc/config/sparc/t-linux64.jj Mon May 6 15:07:12 2002
+++ gcc/config/sparc/t-linux64 Tue May 7 17:37:35 2002
@@ -10,3 +10,9 @@ INSTALL_LIBGCC = install-multilib
EXTRA_MULTILIB_PARTS=crtbegin.o crtend.o crtbeginS.o crtendS.o crtbeginT.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.
+SHLIB_MAPFILES = $(srcdir)/libgcc-std.ver \
+ $(srcdir)/config/sparc/libgcc-sparc-glibc.ver
--- gcc/mklibgcc.in.jj Mon May 6 18:02:06 2002
+++ gcc/mklibgcc.in Tue May 7 18:10:27 2002
@@ -263,7 +263,10 @@ for ml in $MULTILIBS; do
tmpmapfile="libgcc/${dir}/tmp-libgcc.map"
echo ""
echo "${mapfile}: $SHLIB_MKMAP $SHLIB_MAPFILES $libgcc_sh_objs"
- echo ' { $(NM_FOR_TARGET)'" $SHLIB_NM_FLAGS $libgcc_sh_objs; echo %%; cat $SHLIB_MAPFILES; } | "'$(AWK)'" -f $SHLIB_MKMAP $SHLIB_MKMAP_OPTS > ${tmpmapfile}"
+ echo ' { $(NM_FOR_TARGET)'" $SHLIB_NM_FLAGS $libgcc_sh_objs; echo %%; \\"
+ echo " cat $SHLIB_MAPFILES | sed -e "'"/^[ ]*#/d" -e '\''s/^%\(if\|else\|elif\|endif\|define\)/#\1/'\'" \\"
+ echo " | $gcc_compile $flags -E -xassembler-with-cpp -; \\"
+ echo ' } | $(AWK)'" -f $SHLIB_MKMAP $SHLIB_MKMAP_OPTS > ${tmpmapfile}"
echo ' mv '"$tmpmapfile"' $@'
fi
shlib_deps="$shlib_deps $mapfile"
Jakub