This is the mail archive of the libc-alpha@sourceware.org mailing list for the glibc project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: [PATCH] Fix missing declaration of LC_CTYPE nonascii-case element


Testing on i686 revealed a blatant bug in the SSE4.2 and SSSE3
implementations, whereby the fall-through to the generic implementation
didn't clean up the stack frame.

The testsuite is now clean on i686, x86_64 and power7.

Andreas.

	* sysdeps/i386/i686/multiarch/strcmp-sse4.S (__strcasecmp_sse4_2)
	(__strncasecmp_sse4_2) [PIC]: Restore %ebx before falling through
	to __strcasecmp_nonascii and __strncasecmp_nonascii.
	* sysdeps/i386/i686/multiarch/strcmp-ssse3.S (__strcasecmp_ssse3)
	(__strncasecmp_ssse3) [PIC]: Likewise.
---
 sysdeps/i386/i686/multiarch/strcmp-sse4.S  | 12 ++++++++++++
 sysdeps/i386/i686/multiarch/strcmp-ssse3.S | 12 ++++++++++++
 2 files changed, 24 insertions(+)

diff --git a/sysdeps/i386/i686/multiarch/strcmp-sse4.S b/sysdeps/i386/i686/multiarch/strcmp-sse4.S
index 7177205..41a59a9 100644
--- a/sysdeps/i386/i686/multiarch/strcmp-sse4.S
+++ b/sysdeps/i386/i686/multiarch/strcmp-sse4.S
@@ -121,8 +121,14 @@ ENTRY (__strcasecmp_sse4_2)
 	movl	(%eax), %eax
 # endif
 	testl	$1, LOCALE_DATA_VALUES+_NL_CTYPE_NONASCII_CASE*SIZEOF_VALUES(%eax)
+# ifdef PIC
+	je	L(ascii)
+	POP	(%ebx)
+	jmp	__strcasecmp_nonascii
+# else
 	jne	__strcasecmp_nonascii
 	jmp	L(ascii)
+# endif
 END (__strcasecmp_sse4_2)
 #endif
 
@@ -152,8 +158,14 @@ ENTRY (__strncasecmp_sse4_2)
 	movl	(%eax), %eax
 # endif
 	testl	$1, LOCALE_DATA_VALUES+_NL_CTYPE_NONASCII_CASE*SIZEOF_VALUES(%eax)
+# ifdef PIC
+	je	L(ascii)
+	POP	(%ebx)
+	jmp	__strncasecmp_nonascii
+# else
 	jne	__strncasecmp_nonascii
 	jmp	L(ascii)
+# endif
 END (__strncasecmp_sse4_2)
 #endif
 
diff --git a/sysdeps/i386/i686/multiarch/strcmp-ssse3.S b/sysdeps/i386/i686/multiarch/strcmp-ssse3.S
index f2bc204..2fe3cdc 100644
--- a/sysdeps/i386/i686/multiarch/strcmp-ssse3.S
+++ b/sysdeps/i386/i686/multiarch/strcmp-ssse3.S
@@ -138,8 +138,14 @@ ENTRY (__strcasecmp_ssse3)
 	movl	(%eax), %eax
 # endif
 	testl	$1, LOCALE_DATA_VALUES+_NL_CTYPE_NONASCII_CASE*SIZEOF_VALUES(%eax)
+# ifdef PIC
+	je	L(ascii)
+	POP	(%ebx)
+	jmp	__strcasecmp_nonascii
+# else
 	jne	__strcasecmp_nonascii
 	jmp	L(ascii)
+# endif
 END (__strcasecmp_ssse3)
 #endif
 
@@ -169,8 +175,14 @@ ENTRY (__strncasecmp_ssse3)
 	movl	(%eax), %eax
 # endif
 	testl	$1, LOCALE_DATA_VALUES+_NL_CTYPE_NONASCII_CASE*SIZEOF_VALUES(%eax)
+# ifdef PIC
+	je	L(ascii)
+	POP	(%ebx)
+	jmp	__strncasecmp_nonascii
+# else
 	jne	__strncasecmp_nonascii
 	jmp	L(ascii)
+# endif
 END (__strncasecmp_ssse3)
 #endif
 
-- 
1.8.3.4

	[BZ #15736]
	* locale/categories.def (LC_CTYPE): Add "nonascii-case" element.
	* string/Makefile (test-strcasecmp-ENV, test-strncasecmp-ENV)
	(test-strcasecmp-ifunc-ENV, test-strncasecmp-ifunc-ENV): Define.
	* string/test-strcasecmp.c (test_main): Run tests in several
	locales.
	* string/test-strncasecmp.c (test_main): Likewise.
---
 locale/categories.def     |  1 +
 string/Makefile           |  4 ++++
 string/test-strcasecmp.c  | 26 ++++++++++++++++++++++----
 string/test-strncasecmp.c | 26 ++++++++++++++++++++++----
 4 files changed, 49 insertions(+), 8 deletions(-)

diff --git a/locale/categories.def b/locale/categories.def
index 9a89d2d..8c25378 100644
--- a/locale/categories.def
+++ b/locale/categories.def
@@ -133,6 +133,7 @@ DEFINE_CATEGORY
   DEFINE_ELEMENT (_NL_CTYPE_TRANSLIT_IGNORE_LEN, "ctype-translit-ignore-len", std, word)
   DEFINE_ELEMENT (_NL_CTYPE_TRANSLIT_IGNORE, "ctype-translit-ignore", std, string)
   DEFINE_ELEMENT (_NL_CTYPE_MAP_TO_NONASCII, "map-to-nonascii", std, word)
+  DEFINE_ELEMENT (_NL_CTYPE_NONASCII_CASE, "nonascii-case", std, word)
   ), _nl_postload_ctype)
 
 
diff --git a/string/Makefile b/string/Makefile
index 0237edd..aaad743 100644
--- a/string/Makefile
+++ b/string/Makefile
@@ -65,6 +65,10 @@ noinl-tester-ENV = LANGUAGE=C
 tst-strxfrm-ENV = LOCPATH=$(common-objpfx)localedata
 tst-strxfrm2-ENV = LOCPATH=$(common-objpfx)localedata
 bug-strcoll1-ENV = LOCPATH=$(common-objpfx)localedata
+test-strcasecmp-ENV = LOCPATH=$(common-objpfx)localedata
+test-strncasecmp-ENV = LOCPATH=$(common-objpfx)localedata
+test-strcasecmp-ifunc-ENV = LOCPATH=$(common-objpfx)localedata
+test-strncasecmp-ifunc-ENV = LOCPATH=$(common-objpfx)localedata
 CFLAGS-inl-tester.c = -fno-builtin
 CFLAGS-noinl-tester.c = -fno-builtin
 CFLAGS-tst-strlen.c = -fno-builtin
diff --git a/string/test-strcasecmp.c b/string/test-strcasecmp.c
index f321501..bdfccca 100644
--- a/string/test-strcasecmp.c
+++ b/string/test-strcasecmp.c
@@ -17,6 +17,7 @@
    License along with the GNU C Library; if not, see
    <http://www.gnu.org/licenses/>.  */
 
+#include <locale.h>
 #include <ctype.h>
 #define TEST_MAIN
 #define TEST_NAME "strcasecmp"
@@ -206,14 +207,18 @@ do_random_tests (void)
     }
 }
 
-int
-test_main (void)
+static void
+test_locale (const char *locale)
 {
   size_t i;
 
-  test_init ();
+  if (setlocale (LC_CTYPE, locale) == NULL)
+    {
+      error (0, 0, "cannot set locale \"%s\"", locale);
+      ret = 1;
+    }
 
-  printf ("%23s", "");
+  printf ("%-23s", locale);
   FOR_EACH_IMPL (impl, 0)
     printf ("\t%s", impl->name);
   putchar ('\n');
@@ -246,6 +251,19 @@ test_main (void)
     }
 
   do_random_tests ();
+}
+
+int
+test_main (void)
+{
+  test_init ();
+
+  test_locale ("C");
+  test_locale ("en_US.ISO-8859-1");
+  test_locale ("en_US.UTF-8");
+  test_locale ("tr_TR.ISO-8859-9");
+  test_locale ("tr_TR.UTF-8");
+
   return ret;
 }
 
diff --git a/string/test-strncasecmp.c b/string/test-strncasecmp.c
index 4eedd3d..00eca4a 100644
--- a/string/test-strncasecmp.c
+++ b/string/test-strncasecmp.c
@@ -17,6 +17,7 @@
    License along with the GNU C Library; if not, see
    <http://www.gnu.org/licenses/>.  */
 
+#include <locale.h>
 #include <ctype.h>
 #define TEST_MAIN
 #define TEST_NAME "strncasecmp"
@@ -256,17 +257,21 @@ bz14195 (void)
     check_result (impl, empty_string, "", 5, 0);
 }
 
-int
-test_main (void)
+static void
+test_locale (const char *locale)
 {
   size_t i;
 
-  test_init ();
+  if (setlocale (LC_CTYPE, locale) == NULL)
+    {
+      error (0, 0, "cannot set locale \"%s\"", locale);
+      ret = 1;
+    }
 
   bz12205 ();
   bz14195 ();
 
-  printf ("%23s", "");
+  printf ("%23s", locale);
   FOR_EACH_IMPL (impl, 0)
     printf ("\t%s", impl->name);
   putchar ('\n');
@@ -329,6 +334,19 @@ test_main (void)
     }
 
   do_random_tests ();
+}
+
+int
+test_main (void)
+{
+  test_init ();
+
+  test_locale ("C");
+  test_locale ("en_US.ISO-8859-1");
+  test_locale ("en_US.UTF-8");
+  test_locale ("tr_TR.ISO-8859-9");
+  test_locale ("tr_TR.UTF-8");
+
   return ret;
 }
 
-- 
1.8.3.4


-- 
Andreas Schwab, SUSE Labs, schwab@suse.de
GPG Key fingerprint = 0196 BAD8 1CE9 1970 F4BE  1748 E4D4 88E3 0EEA B9D7
"And now for something completely different."


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