diff options
author | Stefan Liebler <stli@linux.vnet.ibm.com> | 2016-10-07 09:56:47 +0200 |
---|---|---|
committer | Stefan Liebler <stli@linux.vnet.ibm.com> | 2016-10-07 10:11:21 +0200 |
commit | 18d6c45e12127ea88a704c0915de2ba13d3af998 (patch) | |
tree | 0965fdaae17a22452a8938530f5435e68eb91edb /sysdeps/s390/multiarch/ifunc-resolve.h | |
parent | 00980d845f8f2ec3ed4ad161a1e5b97704be1929 (diff) | |
download | glibc-18d6c45e12127ea88a704c0915de2ba13d3af998.tar.gz glibc-18d6c45e12127ea88a704c0915de2ba13d3af998.tar.xz glibc-18d6c45e12127ea88a704c0915de2ba13d3af998.zip |
s390: Refactor ifunc resolvers due to false debuginfo.
This patch adjusts the s390 specific ifunc helper macros in ifunc-resolve.h to use the common __ifunc macro, which uses gcc attribute ifunc to get rid of the false debuginfo. Therefore the redirection construct is applied where needed. Perhaps in future we can switch some of the internal symbols __GI_* from the fallback variant to the ifunc function. But this change is not straightforward due to a segmentation fault while linking libc.so with older binutils on s390. ChangeLog: [BZ #20478] * sysdeps/s390/multiarch/ifunc-resolve.h (s390_vx_libc_ifunc2, s390_libc_ifunc): Use __ifunc from libc-symbols.h to create ifunc symbols. (s390_vx_libc_ifunc_init, s390_vx_libc_ifunc_redirected , s390_vx_libc_ifunc2_redirected, s390_libc_ifunc_init): New define. * sysdeps/s390/multiarch/memchr.c: Redirect ifunced function in header for using it as type for ifunc function. * sysdeps/s390/multiarch/mempcpy.c: Likewise. * sysdeps/s390/multiarch/rawmemchr.c: Likewise. * sysdeps/s390/multiarch/stpcpy.c: Likewise. * sysdeps/s390/multiarch/stpncpy.c: Likewise. * sysdeps/s390/multiarch/strcat.c: Likewise. * sysdeps/s390/multiarch/strchr.c: Likewise. * sysdeps/s390/multiarch/strcmp.c: Likewise. * sysdeps/s390/multiarch/strcpy.c: Likewise. * sysdeps/s390/multiarch/strcspn.c: Likewise. * sysdeps/s390/multiarch/strlen.c: Likewise. * sysdeps/s390/multiarch/strncmp.c: Likewise. * sysdeps/s390/multiarch/strncpy.c: Likewise. * sysdeps/s390/multiarch/strnlen.c: Likewise. * sysdeps/s390/multiarch/strpbrk.c: Likewise. * sysdeps/s390/multiarch/strrchr.c: Likewise. * sysdeps/s390/multiarch/strspn.c: Likewise. * sysdeps/s390/multiarch/wcschr.c: Likewise. * sysdeps/s390/multiarch/wcscmp.c: Likewise. * sysdeps/s390/multiarch/wcspbrk.c: Likewise. * sysdeps/s390/multiarch/wcsspn.c: Likewise. * sysdeps/s390/multiarch/wmemchr.c: Likewise. * sysdeps/s390/multiarch/wmemset.c: Likewise. * sysdeps/s390/s390-32/multiarch/memcmp.c: Likewise. * sysdeps/s390/s390-32/multiarch/memcpy.c: Likewise. * sysdeps/s390/s390-32/multiarch/memset.c: Likewise. * sysdeps/s390/s390-64/multiarch/memcmp.c: Likewise. * sysdeps/s390/s390-64/multiarch/memcpy.c: Likewise. * sysdeps/s390/s390-64/multiarch/memset.c: Likewise.
Diffstat (limited to 'sysdeps/s390/multiarch/ifunc-resolve.h')
-rw-r--r-- | sysdeps/s390/multiarch/ifunc-resolve.h | 77 |
1 files changed, 35 insertions, 42 deletions
diff --git a/sysdeps/s390/multiarch/ifunc-resolve.h b/sysdeps/s390/multiarch/ifunc-resolve.h index 26e097ad6e..768829b39b 100644 --- a/sysdeps/s390/multiarch/ifunc-resolve.h +++ b/sysdeps/s390/multiarch/ifunc-resolve.h @@ -40,53 +40,46 @@ ".machine pop" "\n" \ : "=QS" (STFLE_BITS), "+d" (reg0) \ : : "cc"); +#define s390_libc_ifunc_init() \ + unsigned long long stfle_bits = 0ULL; \ + if (__glibc_likely((dl_hwcap & HWCAP_S390_STFLE) \ + && (dl_hwcap & HWCAP_S390_ZARCH) \ + && (dl_hwcap & HWCAP_S390_HIGH_GPRS))) \ + { \ + S390_STORE_STFLE (stfle_bits); \ + } -#define s390_libc_ifunc(FUNC) \ - __asm__ (".globl " #FUNC "\n\t" \ - ".type " #FUNC ",@gnu_indirect_function\n\t" \ - ".set " #FUNC ",__resolve_" #FUNC "\n\t"); \ - \ +#define s390_libc_ifunc(TYPE_FUNC, RESOLVERFUNC, FUNC) \ /* Make the declarations of the optimized functions hidden in order to prevent GOT slots being generated for them. */ \ - extern void *__##FUNC##_z196 attribute_hidden; \ - extern void *__##FUNC##_z10 attribute_hidden; \ - extern void *__##FUNC##_default attribute_hidden; \ - \ - void *__resolve_##FUNC (unsigned long int dl_hwcap) \ - { \ - if ((dl_hwcap & HWCAP_S390_STFLE) \ - && (dl_hwcap & HWCAP_S390_ZARCH) \ - && (dl_hwcap & HWCAP_S390_HIGH_GPRS)) \ - { \ - unsigned long long stfle_bits; \ - S390_STORE_STFLE (stfle_bits); \ - \ - if (S390_IS_Z196 (stfle_bits)) \ - return &__##FUNC##_z196; \ - else if (S390_IS_Z10 (stfle_bits)) \ - return &__##FUNC##_z10; \ - else \ - return &__##FUNC##_default; \ - } \ - else \ - return &__##FUNC##_default; \ - } + extern __typeof (TYPE_FUNC) RESOLVERFUNC##_z196 attribute_hidden; \ + extern __typeof (TYPE_FUNC) RESOLVERFUNC##_z10 attribute_hidden; \ + extern __typeof (TYPE_FUNC) RESOLVERFUNC##_default attribute_hidden; \ + __ifunc (TYPE_FUNC, FUNC, \ + __glibc_likely (S390_IS_Z196 (stfle_bits)) \ + ? RESOLVERFUNC##_z196 \ + : __glibc_likely (S390_IS_Z10 (stfle_bits)) \ + ? RESOLVERFUNC##_z10 \ + : RESOLVERFUNC##_default, \ + unsigned long int dl_hwcap, s390_libc_ifunc_init); #define s390_vx_libc_ifunc(FUNC) \ - s390_vx_libc_ifunc2(FUNC, FUNC) + s390_vx_libc_ifunc2_redirected(FUNC, FUNC, FUNC) -#define s390_vx_libc_ifunc2(RESOLVERFUNC, FUNC) \ +#define s390_vx_libc_ifunc_redirected(TYPE_FUNC, FUNC) \ + s390_vx_libc_ifunc2_redirected(TYPE_FUNC, FUNC, FUNC) + +#define s390_vx_libc_ifunc2(RESOLVERFUNC, FUNC) \ + s390_vx_libc_ifunc2_redirected(FUNC, RESOLVERFUNC, FUNC) + +#define s390_vx_libc_ifunc_init() +#define s390_vx_libc_ifunc2_redirected(TYPE_FUNC, RESOLVERFUNC, FUNC) \ /* Make the declarations of the optimized functions hidden in order to prevent GOT slots being generated for them. */ \ - extern __typeof (FUNC) RESOLVERFUNC##_vx attribute_hidden; \ - extern __typeof (FUNC) RESOLVERFUNC##_c attribute_hidden; \ - extern void *__resolve_##RESOLVERFUNC (unsigned long int) __asm__ (#FUNC); \ - \ - void *__resolve_##RESOLVERFUNC (unsigned long int dl_hwcap) \ - { \ - if (dl_hwcap & HWCAP_S390_VX) \ - return &RESOLVERFUNC##_vx; \ - else \ - return &RESOLVERFUNC##_c; \ - } \ - __asm__ (".type " #FUNC ", %gnu_indirect_function"); + extern __typeof (TYPE_FUNC) RESOLVERFUNC##_vx attribute_hidden; \ + extern __typeof (TYPE_FUNC) RESOLVERFUNC##_c attribute_hidden; \ + __ifunc (TYPE_FUNC, FUNC, \ + (dl_hwcap & HWCAP_S390_VX) \ + ? RESOLVERFUNC##_vx \ + : RESOLVERFUNC##_c, \ + unsigned long int dl_hwcap, s390_vx_libc_ifunc_init); |