You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
314 lines
10 KiB
314 lines
10 KiB
From 9acd7055583a99e912d353ded6a3b4715ee2562a Mon Sep 17 00:00:00 2001 |
|
From: Stefan Liebler <stli@linux.vnet.ibm.com> |
|
Date: Thu, 27 Jul 2017 10:53:58 +0200 |
|
Subject: [PATCH 04/10] S390: Move utf16-utf32-z9.c to multiarch folder and use |
|
s390_libc_ifunc_expr macro. |
|
|
|
upstream-commit 85286aaf1dd7216a64964752d147c5ce3c4067d0 |
|
|
|
The utf16-utf32-z9.c iconv module is using ifunc and thus the ifunc part should |
|
be in multiarch folder. Otherwise ifunc is used even if you configure |
|
with --disable-multi-arch. |
|
|
|
This patch moves the ifunc resolvers to the new file |
|
sysdeps/s390/multiarch/utf16-utf32-z9.c. The resolvers are now implemented |
|
with s390_libc_ifunc_expr macro instead of using gcc attribute ifunc directly. |
|
|
|
The ifunc versions are implemented in sysdeps/s390/utf16-utf32-z9.c. |
|
Each version is only implemented if needed or supported. Therefore there is |
|
a block at beginning of the file which selects the versions which should be |
|
defined depending on support for multiarch, vector-support and used minimum |
|
architecture level. This block defines HAVE_[FROM|TO]_[C|VX] to 1 or 0. |
|
The code below is rearranged and surrounded |
|
by #if HAVE_[FROM|TO]_[C|VX] == 1. There is no functional change. |
|
|
|
ChangeLog: |
|
|
|
* sysdeps/s390/multiarch/utf16-utf32-z9.c: New File. |
|
* sysdeps/s390/utf16-utf32-z9.c: Move ifunc resolvers to multiarch |
|
folder and define ifunc versions depending on HAVE_[FROM|TO]_[C|VX]. |
|
(HAVE_FROM_C, HAVE_FROM_VX, HAVE_TO_C, HAVE_TO_VX, FROM_LOOP_DEFAULT, |
|
FROM_LOOP_C, FROM_LOOP_VX, TO_LOOP_DEFAULT, TO_LOOP_C, TO_LOOP_VX): |
|
New Define. |
|
--- |
|
sysdeps/s390/multiarch/utf16-utf32-z9.c | 44 ++++++++++ |
|
sysdeps/s390/utf16-utf32-z9.c | 142 ++++++++++++++++---------------- |
|
2 files changed, 114 insertions(+), 72 deletions(-) |
|
create mode 100644 sysdeps/s390/multiarch/utf16-utf32-z9.c |
|
|
|
diff --git a/sysdeps/s390/multiarch/utf16-utf32-z9.c b/sysdeps/s390/multiarch/utf16-utf32-z9.c |
|
new file mode 100644 |
|
index 0000000..6e64169 |
|
--- /dev/null |
|
+++ b/sysdeps/s390/multiarch/utf16-utf32-z9.c |
|
@@ -0,0 +1,44 @@ |
|
+/* Conversion between UTF-16 and UTF-32 BE/internal - multiarch s390 version. |
|
+ |
|
+ Copyright (C) 2017 Free Software Foundation, Inc. |
|
+ This file is part of the GNU C Library. |
|
+ |
|
+ The GNU C Library is free software; you can redistribute it and/or |
|
+ modify it under the terms of the GNU Lesser General Public |
|
+ License as published by the Free Software Foundation; either |
|
+ version 2.1 of the License, or (at your option) any later version. |
|
+ |
|
+ The GNU C Library is distributed in the hope that it will be useful, |
|
+ but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
|
+ Lesser General Public License for more details. |
|
+ |
|
+ You should have received a copy of the GNU Lesser General Public |
|
+ License along with the GNU C Library; if not, see |
|
+ <http://www.gnu.org/licenses/>. */ |
|
+ |
|
+#include <sysdeps/s390/utf16-utf32-z9.c> |
|
+#include <ifunc-resolve.h> |
|
+ |
|
+#undef FROM_LOOP |
|
+#define FROM_LOOP __from_utf16_loop |
|
+#undef TO_LOOP |
|
+#define TO_LOOP __to_utf16_loop |
|
+ |
|
+#define _SINGLE_NAME(NAME) NAME##_single |
|
+#define SINGLE_NAME(NAME) _SINGLE_NAME(NAME) |
|
+strong_alias (SINGLE_NAME (FROM_LOOP_DEFAULT), SINGLE_NAME (FROM_LOOP)) |
|
+strong_alias (SINGLE_NAME (TO_LOOP_DEFAULT), SINGLE_NAME (TO_LOOP)) |
|
+ |
|
+/* Generate ifunc'ed loop functions for FROM/TO_LOOP. */ |
|
+s390_libc_ifunc_expr (FROM_LOOP_DEFAULT, FROM_LOOP, |
|
+ (HAVE_FROM_VX && (hwcap & HWCAP_S390_VX)) |
|
+ ? FROM_LOOP_VX |
|
+ : FROM_LOOP_DEFAULT); |
|
+ |
|
+s390_libc_ifunc_expr (TO_LOOP_DEFAULT, TO_LOOP, |
|
+ (HAVE_TO_VX && (hwcap & HWCAP_S390_VX)) |
|
+ ? TO_LOOP_VX |
|
+ : TO_LOOP_DEFAULT); |
|
+ |
|
+#include <iconv/skeleton.c> |
|
diff --git a/sysdeps/s390/utf16-utf32-z9.c b/sysdeps/s390/utf16-utf32-z9.c |
|
index 5d2ac44..5a39d5d 100644 |
|
--- a/sysdeps/s390/utf16-utf32-z9.c |
|
+++ b/sysdeps/s390/utf16-utf32-z9.c |
|
@@ -27,8 +27,23 @@ |
|
#include <dlfcn.h> |
|
#include <stdint.h> |
|
#include <unistd.h> |
|
-#include <dl-procinfo.h> |
|
#include <gconv.h> |
|
+#include <string.h> |
|
+ |
|
+/* Select which versions should be defined depending on support |
|
+ for multiarch, vector and used minimum architecture level. */ |
|
+#define HAVE_FROM_C 1 |
|
+#define FROM_LOOP_DEFAULT FROM_LOOP_C |
|
+#define HAVE_TO_C 1 |
|
+#define TO_LOOP_DEFAULT TO_LOOP_C |
|
+ |
|
+#if defined HAVE_S390_VX_ASM_SUPPORT && defined USE_MULTIARCH |
|
+# define HAVE_FROM_VX 1 |
|
+# define HAVE_TO_VX 1 |
|
+#else |
|
+# define HAVE_FROM_VX 0 |
|
+# define HAVE_TO_VX 0 |
|
+#endif |
|
|
|
#if defined HAVE_S390_VX_GCC_SUPPORT |
|
# define ASM_CLOBBER_VR(NR) , NR |
|
@@ -53,8 +68,8 @@ |
|
#define MIN_NEEDED_FROM 2 |
|
#define MAX_NEEDED_FROM 4 |
|
#define MIN_NEEDED_TO 4 |
|
-#define FROM_LOOP __from_utf16_loop |
|
-#define TO_LOOP __to_utf16_loop |
|
+#define FROM_LOOP FROM_LOOP_DEFAULT |
|
+#define TO_LOOP TO_LOOP_DEFAULT |
|
#define FROM_DIRECTION (dir == from_utf16) |
|
#define ONE_DIRECTION 0 |
|
|
|
@@ -174,9 +189,10 @@ gconv_end (struct __gconv_step *data) |
|
|
|
/* Conversion function from UTF-16 to UTF-32 internal/BE. */ |
|
|
|
+#if HAVE_FROM_C == 1 |
|
/* The software routine is copied from utf-16.c (minus bytes |
|
swapping). */ |
|
-#define BODY_FROM_C \ |
|
+# define BODY_FROM_C \ |
|
{ \ |
|
uint16_t u1 = get16 (inptr); \ |
|
\ |
|
@@ -220,7 +236,22 @@ gconv_end (struct __gconv_step *data) |
|
outptr += 4; \ |
|
} |
|
|
|
-#define BODY_FROM_VX \ |
|
+ |
|
+/* Generate loop-function with software routing. */ |
|
+# define MIN_NEEDED_INPUT MIN_NEEDED_FROM |
|
+# define MAX_NEEDED_INPUT MAX_NEEDED_FROM |
|
+# define MIN_NEEDED_OUTPUT MIN_NEEDED_TO |
|
+# define FROM_LOOP_C __from_utf16_loop_c |
|
+# define LOOPFCT FROM_LOOP_C |
|
+# define LOOP_NEED_FLAGS |
|
+# define BODY BODY_FROM_C |
|
+# include <iconv/loop.c> |
|
+#else |
|
+# define FROM_LOOP_C NULL |
|
+#endif /* HAVE_FROM_C != 1 */ |
|
+ |
|
+#if HAVE_FROM_VX == 1 |
|
+# define BODY_FROM_VX \ |
|
{ \ |
|
size_t inlen = inend - inptr; \ |
|
size_t outlen = outend - outptr; \ |
|
@@ -255,7 +286,7 @@ gconv_end (struct __gconv_step *data) |
|
/* Setup to check for ch >= 0xd800 && ch <= 0xdfff. (v30, v31) */ \ |
|
"9: .short 0xd800,0xdfff,0x0,0x0,0x0,0x0,0x0,0x0\n\t" \ |
|
" .short 0xa000,0xc000,0x0,0x0,0x0,0x0,0x0,0x0\n\t" \ |
|
- /* At least on uint16_t is in range of surrogates. \ |
|
+ /* At least one uint16_t is in range of surrogates. \ |
|
Store the preceding chars. */ \ |
|
"10: vlgvb %[R_TMP],%%v19,7\n\t" \ |
|
" vuplhh %%v17,%%v16\n\t" \ |
|
@@ -351,52 +382,26 @@ gconv_end (struct __gconv_step *data) |
|
} |
|
|
|
|
|
-/* Generate loop-function with software routing. */ |
|
-#define MIN_NEEDED_INPUT MIN_NEEDED_FROM |
|
-#define MAX_NEEDED_INPUT MAX_NEEDED_FROM |
|
-#define MIN_NEEDED_OUTPUT MIN_NEEDED_TO |
|
-#if defined HAVE_S390_VX_ASM_SUPPORT |
|
-# define LOOPFCT __from_utf16_loop_c |
|
-# define LOOP_NEED_FLAGS |
|
-# define BODY BODY_FROM_C |
|
-# include <iconv/loop.c> |
|
- |
|
/* Generate loop-function with hardware vector instructions. */ |
|
# define MIN_NEEDED_INPUT MIN_NEEDED_FROM |
|
# define MAX_NEEDED_INPUT MAX_NEEDED_FROM |
|
# define MIN_NEEDED_OUTPUT MIN_NEEDED_TO |
|
-# define LOOPFCT __from_utf16_loop_vx |
|
+# define FROM_LOOP_VX __from_utf16_loop_vx |
|
+# define LOOPFCT FROM_LOOP_VX |
|
# define LOOP_NEED_FLAGS |
|
# define BODY BODY_FROM_VX |
|
# include <iconv/loop.c> |
|
- |
|
-/* Generate ifunc'ed loop function. */ |
|
-__typeof(__from_utf16_loop_c) |
|
-__attribute__ ((ifunc ("__from_utf16_loop_resolver"))) |
|
-__from_utf16_loop; |
|
- |
|
-static void * |
|
-__from_utf16_loop_resolver (unsigned long int dl_hwcap) |
|
-{ |
|
- if (dl_hwcap & HWCAP_S390_VX) |
|
- return __from_utf16_loop_vx; |
|
- else |
|
- return __from_utf16_loop_c; |
|
-} |
|
- |
|
-strong_alias (__from_utf16_loop_c_single, __from_utf16_loop_single) |
|
#else |
|
-# define LOOPFCT FROM_LOOP |
|
-# define LOOP_NEED_FLAGS |
|
-# define BODY BODY_FROM_C |
|
-# include <iconv/loop.c> |
|
-#endif |
|
+# define FROM_LOOP_VX NULL |
|
+#endif /* HAVE_FROM_VX != 1 */ |
|
+ |
|
|
|
/* Conversion from UTF-32 internal/BE to UTF-16. */ |
|
|
|
+#if HAVE_TO_C == 1 |
|
/* The software routine is copied from utf-16.c (minus bytes |
|
swapping). */ |
|
-#define BODY_TO_C \ |
|
+# define BODY_TO_C \ |
|
{ \ |
|
uint32_t c = get32 (inptr); \ |
|
\ |
|
@@ -439,7 +444,21 @@ strong_alias (__from_utf16_loop_c_single, __from_utf16_loop_single) |
|
inptr += 4; \ |
|
} |
|
|
|
-#define BODY_TO_VX \ |
|
+/* Generate loop-function with software routing. */ |
|
+# define MIN_NEEDED_INPUT MIN_NEEDED_TO |
|
+# define MIN_NEEDED_OUTPUT MIN_NEEDED_FROM |
|
+# define MAX_NEEDED_OUTPUT MAX_NEEDED_FROM |
|
+# define TO_LOOP_C __to_utf16_loop_c |
|
+# define LOOPFCT TO_LOOP_C |
|
+# define LOOP_NEED_FLAGS |
|
+# define BODY BODY_TO_C |
|
+# include <iconv/loop.c> |
|
+#else |
|
+# define TO_LOOP_C NULL |
|
+#endif /* HAVE_TO_C != 1 */ |
|
+ |
|
+#if HAVE_TO_VX == 1 |
|
+# define BODY_TO_VX \ |
|
{ \ |
|
size_t inlen = inend - inptr; \ |
|
size_t outlen = outend - outptr; \ |
|
@@ -563,43 +582,22 @@ strong_alias (__from_utf16_loop_c_single, __from_utf16_loop_single) |
|
STANDARD_TO_LOOP_ERR_HANDLER (4); \ |
|
} |
|
|
|
-/* Generate loop-function with software routing. */ |
|
-#define MIN_NEEDED_INPUT MIN_NEEDED_TO |
|
-#define MIN_NEEDED_OUTPUT MIN_NEEDED_FROM |
|
-#define MAX_NEEDED_OUTPUT MAX_NEEDED_FROM |
|
-#define LOOPFCT __to_utf16_loop_c |
|
-#define LOOP_NEED_FLAGS |
|
-#define BODY BODY_TO_C |
|
-#include <iconv/loop.c> |
|
- |
|
-#if defined HAVE_S390_VX_ASM_SUPPORT |
|
/* Generate loop-function with hardware vector instructions. */ |
|
# define MIN_NEEDED_INPUT MIN_NEEDED_TO |
|
# define MIN_NEEDED_OUTPUT MIN_NEEDED_FROM |
|
# define MAX_NEEDED_OUTPUT MAX_NEEDED_FROM |
|
-# define LOOPFCT __to_utf16_loop_vx |
|
+# define TO_LOOP_VX __to_utf16_loop_vx |
|
+# define LOOPFCT TO_LOOP_VX |
|
# define LOOP_NEED_FLAGS |
|
# define BODY BODY_TO_VX |
|
# include <iconv/loop.c> |
|
+#else |
|
+# define TO_LOOP_VX NULL |
|
+#endif /* HAVE_TO_VX != 1 */ |
|
+ |
|
+/* This file also exists in sysdeps/s390/multiarch/ which |
|
+ generates ifunc resolvers for FROM/TO_LOOP functions |
|
+ and includes iconv/skeleton.c afterwards. */ |
|
+#if ! defined USE_MULTIARCH |
|
+# include <iconv/skeleton.c> |
|
#endif |
|
- |
|
-/* Generate ifunc'ed loop function. */ |
|
-__typeof(__to_utf16_loop_c) |
|
-__attribute__ ((ifunc ("__to_utf16_loop_resolver"))) |
|
-__to_utf16_loop; |
|
- |
|
-static void * |
|
-__to_utf16_loop_resolver (unsigned long int dl_hwcap) |
|
-{ |
|
-#if defined HAVE_S390_VX_ASM_SUPPORT |
|
- if (dl_hwcap & HWCAP_S390_VX) |
|
- return __to_utf16_loop_vx; |
|
- else |
|
-#endif |
|
- return __to_utf16_loop_c; |
|
-} |
|
- |
|
-strong_alias (__to_utf16_loop_c_single, __to_utf16_loop_single) |
|
- |
|
- |
|
-#include <iconv/skeleton.c> |
|
-- |
|
1.8.3.1 |
|
|
|
|