summary refs log tree commit diff
path: root/wctype
diff options
context:
space:
mode:
Diffstat (limited to 'wctype')
-rw-r--r--wctype/wcfuncs.c6
-rw-r--r--wctype/wctype.h16
2 files changed, 20 insertions, 2 deletions
diff --git a/wctype/wcfuncs.c b/wctype/wcfuncs.c
index 30836edb9b..2f60c4a650 100644
--- a/wctype/wcfuncs.c
+++ b/wctype/wcfuncs.c
@@ -25,6 +25,8 @@
 /* If the program is compiled without optimization the following declaration
    is not visible in the header.   */
 extern unsigned int *__ctype32_b;
+extern const uint32_t *__ctype32_toupper;
+extern const uint32_t *__ctype32_tolower;
 
 /* Provide real-function versions of all the wctype macros.  */
 
@@ -76,7 +78,7 @@ wint_t
     /* Character is not known.  Default action is to simply return it.  */
     return wc;
 
-  return (wint_t) __ctype_tolower[idx];
+  return (wint_t) __ctype32_tolower[idx];
 }
 
 wint_t
@@ -90,5 +92,5 @@ wint_t
     /* Character is not known.  Default action is to simply return it.  */
     return wc;
 
-  return (wint_t) __ctype_toupper[idx];
+  return (wint_t) __ctype32_toupper[idx];
 }
diff --git a/wctype/wctype.h b/wctype/wctype.h
index 378095bcb4..2a4caddd90 100644
--- a/wctype/wctype.h
+++ b/wctype/wctype.h
@@ -238,6 +238,22 @@ extern wint_t towupper (wint_t __wc) __THROW;
 /* Map the wide character WC using the mapping described by DESC.  */
 extern wint_t __towctrans (wint_t __wc, wctrans_t __desc) __THROW;
 
+#if __GNUC__ >= 2 && defined __OPTIMIZE__
+/* The tables are always organized in a way which allows direct access
+   for single byte characters.  */
+extern const wint_t *__ctype32_tolower;
+extern const wint_t *__ctype32_toupper;
+
+# define towlower(wc) \
+  (__builtin_constant_p (wc) && (wc) >= L'\0' && (wc) <= L'\xff'	      \
+   ? (wint_t) __ctype32_tolower[wc] : towlower (wc))
+
+# define towupper(wc) \
+  (__builtin_constant_p (wc) && (wc) >= L'\0' && (wc) <= L'\xff'	      \
+   ? (wint_t) __ctype32_toupper[wc] : towupper (wc))
+
+#endif	/* gcc && optimizing */
+
 __END_DECLS
 
 #endif	/* need iswxxx.  */