OSDN Git Service

Fix a few bugs in the new extended locale functions.
[uclinux-h8/uClibc.git] / libc / string / wstring.c
index 9661893..250f987 100644 (file)
@@ -49,6 +49,7 @@
 #ifdef WANT_WIDE
 #include <wchar.h>
 #include <wctype.h>
+#include <bits/uClibc_uwchar.h>
 
 #define Wvoid                  wchar_t
 #define Wchar                  wchar_t
@@ -77,12 +78,22 @@ typedef unsigned char       __string_uchar_t;
 #define _SYS_NERR                      126
 #endif
 
+#ifdef __UCLIBC_HAS_ERRNO_MESSAGES__
 #define _SYS_ERRMSG_MAXLEN      50
+#else  /* __UCLIBC_HAS_ERRNO_MESSAGES__ */
+#define _SYS_ERRMSG_MAXLEN      0
+#endif /* __UCLIBC_HAS_ERRNO_MESSAGES__ */
+
 
 extern const char _string_syserrmsgs[];
 
 #define _SYS_NSIG                      32
+
+#ifdef __UCLIBC_HAS_SIGNUM_MESSAGES__
 #define _SYS_SIGMSG_MAXLEN     25
+#else  /* __UCLIBC_HAS_SIGNUM_MESSAGES__ */
+#define _SYS_SIGMSG_MAXLEN     0
+#endif /* __UCLIBC_HAS_SIGNUM_MESSAGES__ */
 
 extern const char _string_syssigmsgs[];
 
@@ -93,14 +104,14 @@ extern const char _string_syssigmsgs[];
 #define _STRERROR_BUFSIZE _SYS_ERRMSG_MAXLEN
 #endif
 
-#if _SYS_SIGMSG_MAXLEN < __UIM_BUFLEN_INT + 14
-#define _STRSIGNAL_BUFSIZE (__UIM_BUFLEN_INT + 14)
+#if _SYS_SIGMSG_MAXLEN < __UIM_BUFLEN_INT + 15
+#define _STRSIGNAL_BUFSIZE (__UIM_BUFLEN_INT + 15)
 #else
 #define _STRSIGNAL_BUFSIZE _SYS_SIGMSG_MAXLEN
 #endif
 
 /**********************************************************************/
-#ifdef L__string_syserrmsgs
+#if defined(L__string_syserrmsgs) && defined(__UCLIBC_HAS_ERRNO_MESSAGES__)
 
 const char _string_syserrmsgs[] = {
        /*   0:    0,  8 */ "Success\0"
@@ -238,7 +249,7 @@ const char _string_syserrmsgs[] = {
 
 #endif
 /**********************************************************************/
-#ifdef L_sys_errlist
+#if defined(L_sys_errlist) && defined(__UCLIBC_HAS_SYS_ERRLIST__)
 
 link_warning(_sys_errlist, "sys_nerr and sys_errlist are obsolete and uClibc support for them (in at least some configurations) will probably be unavailable in the near future.")
 
@@ -1070,54 +1081,108 @@ int ffs(int i)
 
 #endif
 /**********************************************************************/
-#ifdef L_wcscasecmp
-#define L_strcasecmp
-#define Wstrcasecmp wcscasecmp
+#if defined(L_strcasecmp) || defined(L_strcasecmp_l) || defined(L_wcscasecmp) || defined(L_wcscasecmp_l)
+
+#if defined(L_wcscasecmp) || defined(L_wcscasecmp_l)
+
+#define strcasecmp wcscasecmp
+#define strcasecmp_l wcscasecmp_l
+#define __strcasecmp_l __wcscasecmp_l
+#ifdef __UCLIBC_DO_XLOCALE
+#define TOLOWER(C) __towlower_l((C), locale_arg)
+#else
+#define TOLOWER(C) towlower((C))
+#endif
+
+#else  /* defined(L_wcscasecmp) || defined(L_wcscasecmp_l) */
+
+#ifdef __UCLIBC_DO_XLOCALE
+#define TOLOWER(C) __tolower_l((C), locale_arg)
 #else
-#define Wstrcasecmp strcasecmp
+#define TOLOWER(C) tolower((C))
 #endif
 
-#ifdef L_strcasecmp
+#endif /* defined(L_wcscasecmp) || defined(L_wcscasecmp_l) */
 
-int Wstrcasecmp(register const Wchar *s1, register const Wchar *s2)
+
+#if defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE)
+
+int strcasecmp(register const Wchar *s1, register const Wchar *s2)
+{
+       return __strcasecmp_l(s1, s2, __UCLIBC_CURLOCALE);
+}
+
+#else  /* defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE) */
+
+int __XL(strcasecmp)(register const Wchar *s1, register const Wchar *s2
+                                         __LOCALE_PARAM )
 {
 #ifdef WANT_WIDE
-       while ((*s1 == *s2) || (towlower(*s1) == towlower(*s2))) {
+       while ((*s1 == *s2) || (TOLOWER(*s1) == TOLOWER(*s2))) {
                if (!*s1++) {
                        return 0;
                }
                ++s2;
        }
 
-       return (((Wuchar)towlower(*s1)) < ((Wuchar)towlower(*s2))) ? -1 : 1;
+       return (((Wuchar)TOLOWER(*s1)) < ((Wuchar)TOLOWER(*s2))) ? -1 : 1;
        /* TODO -- should wide cmp funcs do wchar or Wuchar compares? */
 #else
        int r = 0;
 
        while ( ((s1 == s2) ||
-                        !(r = ((int)( tolower(*((Wuchar *)s1))))
-                          - tolower(*((Wuchar *)s2))))
+                        !(r = ((int)( TOLOWER(*((Wuchar *)s1))))
+                          - TOLOWER(*((Wuchar *)s2))))
                        && (++s2, *s1++));
 
        return r;
 #endif
 }
 
+__XL_ALIAS(strcasecmp)
+
+#endif /* defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE) */
+
 #endif
 /**********************************************************************/
-#ifdef L_wcsncasecmp
-#define L_strncasecmp
-#define Wstrncasecmp wcsncasecmp
+#if defined(L_strncasecmp) || defined(L_strncasecmp_l) || defined(L_wcsncasecmp) || defined(L_wcsncasecmp_l)
+
+#if defined(L_wcsncasecmp) || defined(L_wcsncasecmp_l)
+
+#define strncasecmp wcsncasecmp
+#define strncasecmp_l wcsncasecmp_l
+#define __strncasecmp_l __wcsncasecmp_l
+#ifdef __UCLIBC_DO_XLOCALE
+#define TOLOWER(C) __towlower_l((C), locale_arg)
+#else
+#define TOLOWER(C) towlower((C))
+#endif
+
+#else  /* defined(L_wcsncasecmp) || defined(L_wcsncasecmp_l) */
+
+#ifdef __UCLIBC_DO_XLOCALE
+#define TOLOWER(C) __tolower_l((C), locale_arg)
 #else
-#define Wstrncasecmp strncasecmp
+#define TOLOWER(C) tolower((C))
 #endif
 
-#ifdef L_strncasecmp
+#endif /* defined(L_wcsncasecmp) || defined(L_wcsncasecmp_l) */
 
-int Wstrncasecmp(register const Wchar *s1, register const Wchar *s2, size_t n)
+
+#if defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE)
+
+int strncasecmp(register const Wchar *s1, register const Wchar *s2, size_t n)
+{
+       return __strncasecmp_l(s1, s2, n, __UCLIBC_CURLOCALE);
+}
+
+#else  /* defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE) */
+
+int __XL(strncasecmp)(register const Wchar *s1, register const Wchar *s2,
+                                         size_t n   __LOCALE_PARAM )
 {
 #ifdef WANT_WIDE
-       while (n && ((*s1 == *s2) || (towlower(*s1) == towlower(*s2)))) {
+       while (n && ((*s1 == *s2) || (TOLOWER(*s1) == TOLOWER(*s2)))) {
                if (!*s1++) {
                        return 0;
                }
@@ -1127,19 +1192,24 @@ int Wstrncasecmp(register const Wchar *s1, register const Wchar *s2, size_t n)
 
        return (n == 0)
                ? 0
-               : ((((Wuchar)towlower(*s1)) < ((Wuchar)towlower(*s2))) ? -1 : 1);
+               : ((((Wuchar)TOLOWER(*s1)) < ((Wuchar)TOLOWER(*s2))) ? -1 : 1);
        /* TODO -- should wide cmp funcs do wchar or Wuchar compares? */
 #else
        int r = 0;
 
        while ( n
                        && ((s1 == s2) ||
-                               !(r = ((int)( tolower(*((unsigned char *)s1))))
-                                 - tolower(*((unsigned char *)s2))))
+                               !(r = ((int)( TOLOWER(*((unsigned char *)s1))))
+                                 - TOLOWER(*((unsigned char *)s2))))
                        && (--n, ++s2, *s1++));
        return r;
 #endif
 }
+
+__XL_ALIAS(strncasecmp)
+
+#endif /* defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE) */
+
 #endif
 /**********************************************************************/
 #ifdef L_wcsnlen
@@ -1220,7 +1290,7 @@ Wchar *Wstrdup(register const Wchar *s1)
 
 char *strerror(int errnum)
 {
-    static char buf[_SYS_ERRMSG_MAXLEN];
+    static char buf[_STRERROR_BUFSIZE];
 
        _susv3_strerror_r(errnum, buf, sizeof(buf));
 
@@ -1233,6 +1303,7 @@ char *strerror(int errnum)
 /**********************************************************************/
 #ifdef L__susv3_strerror_r
 
+#ifdef __UCLIBC_HAS_ERRNO_MESSAGES__
 #if defined(__alpha__) || defined(__mips__) || defined(__sparc__)
 
 static const unsigned char estridx[] = {
@@ -1372,19 +1443,20 @@ static const unsigned char estridx[] = {
 
 #endif
 
-
 int _susv3_strerror_r(int errnum, char *strerrbuf, size_t buflen)
 {
     register char *s;
     int i, retval;
-    char buf[_SYS_ERRMSG_MAXLEN];
-    static const char unknown[14] = {
+    char buf[_STRERROR_BUFSIZE];
+    static const char unknown[] = {
                'U', 'n', 'k', 'n', 'o', 'w', 'n', ' ', 'e', 'r', 'r', 'o', 'r', ' '
     };
 
     retval = EINVAL;
 
 
+#ifdef __UCLIBC_HAS_ERRNO_MESSAGES__
+
 #if defined(__alpha__) || defined(__mips__) || defined(__sparc__)
        /* Need to translate errno to string index. */
        for (i = 0 ; i < sizeof(estridx)/sizeof(estridx[0]) ; i++) {
@@ -1420,6 +1492,8 @@ int _susv3_strerror_r(int errnum, char *strerrbuf, size_t buflen)
                }
     }
 
+#endif /* __UCLIBC_HAS_ERRNO_MESSAGES__ */
+
     s = _int10tostr(buf+sizeof(buf)-1, errnum) - sizeof(unknown);
     memcpy(s, unknown, sizeof(unknown));
 
@@ -1445,6 +1519,45 @@ int _susv3_strerror_r(int errnum, char *strerrbuf, size_t buflen)
     return retval;
 }
 
+#else  /* __UCLIBC_HAS_ERRNO_MESSAGES__ */
+
+int _susv3_strerror_r(int errnum, char *strerrbuf, size_t buflen)
+{
+    register char *s;
+    int i, retval;
+    char buf[_STRERROR_BUFSIZE];
+    static const char unknown[] = {
+               'U', 'n', 'k', 'n', 'o', 'w', 'n', ' ', 'e', 'r', 'r', 'o', 'r', ' '
+    };
+
+    s = _int10tostr(buf+sizeof(buf)-1, errnum) - sizeof(unknown);
+    memcpy(s, unknown, sizeof(unknown));
+
+    if (!strerrbuf) {          /* SUSv3  */
+               buflen = 0;
+    }
+
+    retval = EINVAL;
+
+       i = buf + sizeof(buf) - s;
+
+    if (i > buflen) {
+               i = buflen;
+               retval = ERANGE;
+    }
+
+    if (i) {
+               memcpy(strerrbuf, s, i);
+               strerrbuf[i-1] = 0;     /* In case buf was too small. */
+    }
+
+       __set_errno(retval);
+
+    return retval;
+}
+
+#endif /* __UCLIBC_HAS_ERRNO_MESSAGES__ */
+
 #endif
 /**********************************************************************/
 /* GNU extension functions. */
@@ -1462,6 +1575,40 @@ char *_glibc_strerror_r(int errnum, char *strerrbuf, size_t buflen)
 
 #endif
 /**********************************************************************/
+#ifdef L_memmem
+
+void *memmem(const void *haystack, size_t haystacklen,
+                    const void *needle, size_t needlelen)
+{
+       register const char *ph;
+       register const char *pn;
+       const char *plast;
+       size_t n;
+
+       if (needlelen == 0) {
+               return (void *) haystack;
+       }
+
+       if (haystacklen >= needlelen) {
+               ph = (const char *) haystack;
+               pn = (const char *) needle;
+               plast = ph + (haystacklen - needlelen);
+
+               do {
+                       n = 0;
+                       while (ph[n] == pn[n]) {
+                               if (++n == needlelen) {
+                                       return (void *) ph;
+                               }
+                       }
+               } while (++ph <= plast);
+       }
+
+       return NULL;
+}
+
+#endif
+/**********************************************************************/
 #ifdef L_wmempcpy
 #define L_mempcpy
 #define Wmempcpy wmempcpy
@@ -1959,7 +2106,7 @@ size_t Wstrlcpy(register Wchar *__restrict dst,
 
 #endif
 /**********************************************************************/
-#ifdef L__string_syssigmsgs
+#if defined(L__string_syssigmsgs) && defined(__UCLIBC_HAS_SIGNUM_MESSAGES__)
 
 const char _string_syssigmsgs[] = {
        /*   0:    0,  1 */ "\0"
@@ -1999,7 +2146,7 @@ const char _string_syssigmsgs[] = {
 #endif
 
 /**********************************************************************/
-#ifdef L_sys_siglist
+#if defined(L_sys_siglist) && defined(__UCLIBC_HAS_SYS_SIGLIST__)
 
 const char *const sys_siglist[_NSIG] = {
        NULL,
@@ -2074,12 +2221,14 @@ const char *const sys_siglist[_NSIG] = {
 
 /* TODO: make a threadsafe version? */
 
+#ifdef __UCLIBC_HAS_SIGNUM_MESSAGES__
+
 char *strsignal(int signum)
 {
     register char *s;
     int i;
     static char buf[_STRSIGNAL_BUFSIZE];
-    static const char unknown[15] = {
+    static const char unknown[] = {
                'U', 'n', 'k', 'n', 'o', 'w', 'n', ' ', 's', 'i', 'g', 'n', 'a', 'l', ' '
     };
 
@@ -2105,6 +2254,22 @@ char *strsignal(int signum)
        return s;
 }
 
+#else  /* __UCLIBC_HAS_SIGNUM_MESSAGES__ */
+
+char *strsignal(int signum)
+{
+    static char buf[_STRSIGNAL_BUFSIZE];
+    static const char unknown[] = {
+               'U', 'n', 'k', 'n', 'o', 'w', 'n', ' ', 's', 'i', 'g', 'n', 'a', 'l', ' '
+    };
+
+    return (char *) memcpy(_int10tostr(buf+sizeof(buf)-1, signum)
+                                                  - sizeof(unknown),
+                                                  unknown, sizeof(unknown));
+}
+
+#endif /* __UCLIBC_HAS_SIGNUM_MESSAGES__ */
+
 #endif
 /**********************************************************************/
 #ifdef L_psignal
@@ -2137,6 +2302,7 @@ void psignal(int signum, register const char *message)
 #endif
 /**********************************************************************/
 #ifndef __LOCALE_C_ONLY
+#if defined(L_strxfrm) || defined(L_strxfrm_l) || defined(L_wcsxfrm) || defined(L_wcsxfrm_l)
 
 #ifdef L_strxfrm
 #ifndef WANT_WIDE
@@ -2145,11 +2311,18 @@ void psignal(int signum, register const char *message)
 #ifdef L_wcsxfrm
 #error L_wcsxfrm already defined for L_strxfrm
 #endif
+#endif /* L_strxfrm */
 
-#define wcscoll strcoll
-#define L_wcsxfrm
-#undef WANT_WIDE
+#if defined(L_strxfrm) || defined(L_strxfrm_l)
 
+#define wcscoll   strcoll
+#define wcscoll_l strcoll_l
+#define __wcscoll_l __strcoll_l
+#define wcsxfrm   strxfrm
+#define wcsxfrm_l strxfrm_l
+#define __wcsxfrm_l __strxfrm_l
+
+#undef WANT_WIDE
 #undef Wvoid
 #undef Wchar
 #undef Wuchar
@@ -2157,13 +2330,28 @@ void psignal(int signum, register const char *message)
 
 #define Wchar char
 
-#endif /* L_strxfrm */
+#endif /* defined(L_strxfrm) || defined(L_strxfrm_l) */
+
+#if defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE)
+
+int wcscoll (const Wchar *s0, const Wchar *s1)
+{
+       return __wcscoll_l(s0, s1, __UCLIBC_CURLOCALE );
+}
 
+size_t wcsxfrm(Wchar *__restrict ws1, const Wchar *__restrict ws2, size_t n)
+{
+       return __wcsxfrm_l(ws1, ws2, n, __UCLIBC_CURLOCALE );
+}
 
+#else  /* defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE) */
 
-#ifdef L_wcsxfrm
 
-#define CUR_COLLATE (&__global_locale.collate)
+#if 0
+#define CUR_COLLATE (&__UCLIBC_CURLOCALE_DATA.collate)
+#else
+#define CUR_COLLATE (& __LOCALE_PTR->collate)
+#endif
 
 #define MAX_PENDING 8
 
@@ -2207,12 +2395,12 @@ typedef struct {
 
 #undef TRACE
 #if 0
-#define TRACE(X)       printf##X
+#define TRACE(X)       printf X
 #else
 #define TRACE(X)       ((void)0)
 #endif
 
-static int lookup(wchar_t wc)
+static int lookup(wchar_t wc   __LOCALE_PARAM )
 {
        unsigned int sc, n, i0, i1;
 
@@ -2242,7 +2430,7 @@ static void init_col_state(col_state_t *cs, const Wchar *wcs)
        cs->bbe = cs->back_buf + (cs->bb_size -1);
 }
 
-static void next_weight(col_state_t *cs, int pass)
+static void next_weight(col_state_t *cs, int pass   __LOCALE_PARAM )
 {
        int r, w, ru, ri, popping_backup_stack;
        ssize_t n;
@@ -2251,12 +2439,10 @@ static void next_weight(col_state_t *cs, int pass)
 #define WC (*cs->s)
 #define N (1)
 #else  /* WANT_WIDE */
-       mbstate_t mbstate;
        wchar_t WC;
        size_t n0, nx;
 #define N n0
 
-       mbstate.mask = 0;
 #endif /* WANT_WIDE */
 
        do {
@@ -2309,15 +2495,15 @@ static void next_weight(col_state_t *cs, int pass)
                BACK_LOOP:
 #ifdef WANT_WIDE
                        n = 1;
-                       cs->colitem = r = lookup(*cs->s);
+                       cs->colitem = r = lookup(*cs->s   __LOCALE_ARG );
 #else  /* WANT_WIDE */
-                       n = n0 = mbrtowc(&WC, cs->s, SIZE_MAX, &mbstate);
+                       n = n0 = __locale_mbrtowc_l(&WC, cs->s, __LOCALE_PTR);
                        if (n < 0) {
                                __set_errno(EILSEQ);
                                cs->weight = 0;
                                return;
                        }
-                       cs->colitem = r = lookup(WC);
+                       cs->colitem = r = lookup(WC   __LOCALE_ARG );
 #endif /* WANT_WIDE */
 
                        TRACE((" r=%d WC=%#lx\n", r, (unsigned long)(WC)));
@@ -2336,7 +2522,7 @@ static void next_weight(col_state_t *cs, int pass)
                                                }
 #ifdef WANT_WIDE
                                                /* the lookup check here is safe since we're assured that *p is a valid colidx */
-                                               if (!cs->s[n] || (lookup(cs->s[n]) != *p)) {
+                                               if (!cs->s[n] || (lookup(cs->s[n]   __LOCALE_ARG ) != *p)) {
                                                        do {} while (*p++);
                                                        break;
                                                }
@@ -2344,19 +2530,19 @@ static void next_weight(col_state_t *cs, int pass)
                                                ++n;
 #else  /* WANT_WIDE */
                                                if (cs->s[n]) {
-                                                       nx = mbrtowc(&WC, cs->s + n, SIZE_MAX, &mbstate);
+                                                       nx = __locale_mbrtowc_l(&WC, cs->s + n, __LOCALE_PTR);
                                                        if (nx < 0) {
                                                                __set_errno(EILSEQ);
                                                                cs->weight = 0;
                                                                return;
                                                        }
                                                }
-                                               if (!cs->s[n] || (lookup(WC) != *p)) {
+                                               if (!cs->s[n] || (lookup(WC   __LOCALE_ARG ) != *p)) {
                                                        do {} while (*p++);
                                                        break;
                                                }
                                                ++p;
-                                               n += nx;
+                                               n += nx; /* Only gets here if cs->s[n] != 0, so nx is set. */
 #endif /* WANT_WIDE */
                                        } while (1);
                                } while (1);
@@ -2594,7 +2780,7 @@ static void next_weight(col_state_t *cs, int pass)
        } while (1);
 }
 
-int wcscoll (const Wchar *s0, const Wchar *s1)
+int __XL(wcscoll) (const Wchar *s0, const Wchar *s1   __LOCALE_PARAM )
 {
        col_state_t ws[2];
        int pass;
@@ -2613,8 +2799,8 @@ int wcscoll (const Wchar *s0, const Wchar *s1)
                init_col_state(ws+1, s1);
                do {                                    /* loop through the strings */
                        /* for each string, get the next weight */
-                       next_weight(ws, pass);
-                       next_weight(ws+1, pass);
+                       next_weight(ws, pass   __LOCALE_ARG );
+                       next_weight(ws+1, pass   __LOCALE_ARG );
                        TRACE(("w0=%lu  w1=%lu\n",
                                   (unsigned long) ws[0].weight,
                                   (unsigned long) ws[1].weight));
@@ -2628,9 +2814,12 @@ int wcscoll (const Wchar *s0, const Wchar *s1)
        return 0;
 }
 
+__XL_ALIAS(wcscoll)
+
 #ifdef WANT_WIDE
 
-size_t wcsxfrm(wchar_t *__restrict ws1, const wchar_t *__restrict ws2, size_t n)
+size_t __XL(wcsxfrm)(wchar_t *__restrict ws1, const wchar_t *__restrict ws2,
+                                        size_t n   __LOCALE_PARAM )
 {
        col_state_t cs;
        size_t count;
@@ -2648,7 +2837,7 @@ size_t wcsxfrm(wchar_t *__restrict ws1, const wchar_t *__restrict ws2, size_t n)
        do {                                            /* loop through the weights levels */
                init_col_state(&cs, ws2);
                do {                                    /* loop through the string */
-                       next_weight(&cs, pass);
+                       next_weight(&cs, pass   __LOCALE_ARG );
                        TRACE(("weight=%lu (%#lx)\n", (unsigned long) cs.weight, (unsigned long) cs.weight));
                        if (count < n) {
                                ws1[count] = cs.weight +1;
@@ -2667,6 +2856,8 @@ size_t wcsxfrm(wchar_t *__restrict ws1, const wchar_t *__restrict ws2, size_t n)
        return count-1;
 }
 
+__XL_ALIAS(wcsxfrm)
+
 #else  /* WANT_WIDE */
 
 static const unsigned long bound[] = {
@@ -2709,7 +2900,8 @@ static size_t store(unsigned char *s, size_t count, size_t n, __uwchar_t weight)
        return r;
 }
 
-size_t strxfrm(char *__restrict ws1, const char *__restrict ws2, size_t n)
+size_t __XL(strxfrm)(char *__restrict ws1, const char *__restrict ws2, size_t n
+                                        __LOCALE_PARAM )
 {
        col_state_t cs;
        size_t count, inc;
@@ -2727,7 +2919,7 @@ size_t strxfrm(char *__restrict ws1, const char *__restrict ws2, size_t n)
        do {                                            /* loop through the weights levels */
                init_col_state(&cs, ws2);
                do {                                    /* loop through the string */
-                       next_weight(&cs, pass);
+                       next_weight(&cs, pass   __LOCALE_ARG );
                        TRACE(("weight=%lu (%#lx)\n", (unsigned long) cs.weight, (unsigned long) cs.weight));
                        inc = store((unsigned char *)ws1, count, n, cs.weight + 1);
                        count += inc;
@@ -2746,11 +2938,13 @@ size_t strxfrm(char *__restrict ws1, const char *__restrict ws2, size_t n)
        return count-1;
 }
 
+__XL_ALIAS(strxfrm)
 
 #endif /* WANT_WIDE */
 
-#endif /* wcscoll */
+#endif /* defined(__UCLIBC_HAS_XLOCALE__) && !defined(__UCLIBC_DO_XLOCALE) */
+
+#endif /* defined(L_strxfrm) || defined(L_strxfrm_l) || defined(L_wcsxfrm) || defined(L_wcsxfrm_l) */
 
 #endif /* __LOCALE_C_ONLY */
 /**********************************************************************/
-