r12522: Try and fix bug #2926 by removing setlocale(LC_ALL, "C")
authorJeremy Allison <jra@samba.org>
Tue, 27 Dec 2005 20:52:36 +0000 (20:52 +0000)
committerGerald (Jerry) Carter <jerry@samba.org>
Wed, 10 Oct 2007 16:05:58 +0000 (11:05 -0500)
and replace calls to isupper/islower/toupper/tolower with
ASCII equivalents (mapping into _w variants).
Jeremy.

13 files changed:
source/auth/pass_check.c
source/client/clitar.c
source/include/smb.h
source/lib/charcnv.c
source/lib/replace.c
source/lib/username.c
source/lib/util_str.c
source/lib/util_unistr.c
source/passdb/passdb.c
source/passdb/pdb_pgsql.c
source/smbd/mangle_hash.c
source/smbd/mangle_hash2.c
source/web/swat.c

index 0425e01cdcb6c8880fa62fba4c7f25ddd8ab42b1..507e8a3836e8fd44b631772e8b25d161c3de39d9 100644 (file)
@@ -452,9 +452,9 @@ static NTSTATUS string_combinations2(char *s, int offset, NTSTATUS (*fn) (const
 
        for (i = offset; i < (len - (N - 1)); i++) {
                char c = s[i];
-               if (!islower(c))
+               if (!islower_ascii(c))
                        continue;
-               s[i] = toupper(c);
+               s[i] = toupper_ascii(c);
                if (!NT_STATUS_EQUAL(nt_status = string_combinations2(s, i + 1, fn, N - 1),NT_STATUS_WRONG_PASSWORD)) {
                        return (nt_status);
                }
index 5afe154cbbe5aaec2854ad136738973f291e14ee..c15d24d619a752e8dace2602d00df76f5a2b6b61 100644 (file)
@@ -482,7 +482,7 @@ static int strslashcmp(char *s1, char *s2)
 {
        char *s1_0=s1;
 
-       while(*s1 && *s2 && (*s1 == *s2 || tolower(*s1) == tolower(*s2) ||
+       while(*s1 && *s2 && (*s1 == *s2 || tolower_ascii(*s1) == tolower_ascii(*s2) ||
                                (*s1 == '\\' && *s2=='/') || (*s1 == '/' && *s2=='\\'))) {
                s1++; s2++;
        }
index fc256c6f698d2c794d1d94c37376905f09c6fc51..4f378f822e24666302aa63f5f2a8b071066d615a 100644 (file)
@@ -172,6 +172,9 @@ typedef smb_ucs2_t wfstring[FSTRING_LEN];
 /* turn a 7 bit character into a ucs2 character */
 #define UCS2_CHAR(c) ((c) << UCS2_SHIFT)
 
+/* return an ascii version of a ucs2 character */
+#define UCS2_TO_CHAR(c) ((c) & 0xff)
+
 /* Copy into a smb_ucs2_t from a possibly unaligned buffer. Return the copied smb_ucs2_t */
 #define COPY_UCS2_CHAR(dest,src) (((unsigned char *)(dest))[0] = ((unsigned char *)(src))[0],\
                                ((unsigned char *)(dest))[1] = ((unsigned char *)(src))[1], (dest))
index 0c806167f4135fce63ab61350a26d6650247cbdc..c4eeab135e9a21a31533718365bca8d8d817406e 100644 (file)
@@ -84,15 +84,6 @@ static const char *charset_name(charset_t ch)
                }
                ret = ln;
        }
-#ifdef HAVE_SETLOCALE
-       /* We set back the locale to C to get ASCII-compatible toupper/lower functions.
-          For now we do not need any other POSIX localisations anyway. When we should
-          really need localized string functions one day we need to write our own
-          ascii_tolower etc.
-       */
-       setlocale(LC_ALL, "C");
- #endif
-
 #endif
 
        if (!ret || !*ret) ret = "ASCII";
@@ -747,7 +738,7 @@ char *strdup_upper(const char *s)
        while (1) {
                if (*p & 0x80)
                        break;
-               *q++ = toupper(*p);
+               *q++ = toupper_ascii(*p);
                if (!*p)
                        break;
                p++;
index 57ee6ea11e631099800f054c6b3ff7e0ab1bef47..120fd3a4688caf0120090183da60bcc583955ae2 100644 (file)
@@ -390,7 +390,7 @@ char *rep_inet_ntoa(struct in_addr ip)
                if (isdigit(c))
                        c -= '0';
                else if (isalpha(c))
-                       c -= isupper(c) ? 'A' - 10 : 'a' - 10;
+                       c -= isupper_ascii(c) ? 'A' - 10 : 'a' - 10;
                else
                        break;
                if (c >= base)
index ecfd5fef9ef0af4e520ef38fbbacbf18881d4c9f..7d66b320adf8d61abd2aefdddd2b056bc1ba8ffe 100644 (file)
@@ -716,9 +716,9 @@ static struct passwd *uname_string_combinations2(char *s,int offset,struct passw
 
        for (i=offset;i<(len-(N-1));i++) {
                char c = s[i];
-               if (!islower((int)c))
+               if (!islower_ascii((int)c))
                        continue;
-               s[i] = toupper(c);
+               s[i] = toupper_ascii(c);
                ret = uname_string_combinations2(s,i+1,fn,N-1);
                if(ret)
                        return(ret);
index 80bb2ff2ad7823a0ccc57a26a60ceb7c35dc9c07..0b02487f774cdb804ce9e90328cd26a14b72eed2 100644 (file)
@@ -201,8 +201,8 @@ int StrCaseCmp(const char *s, const char *t)
                        /* not ascii anymore, do it the hard way from here on in */
                        break;
 
-               us = toupper(*ps);
-               ut = toupper(*pt);
+               us = toupper_ascii(*ps);
+               ut = toupper_ascii(*pt);
                if (us == ut)
                        continue;
                else if (us < ut)
@@ -309,7 +309,7 @@ int strwicmp(const char *psz1, const char *psz2)
                        psz1++;
                while (isspace((int)*psz2))
                        psz2++;
-               if (toupper(*psz1) != toupper(*psz2) || *psz1 == '\0'
+               if (toupper_ascii(*psz1) != toupper_ascii(*psz2) || *psz1 == '\0'
                    || *psz2 == '\0')
                        break;
                psz1++;
@@ -680,7 +680,7 @@ char *alpha_strcpy_fn(const char *fn, int line, char *dest, const char *src, con
 
        for(i = 0; i < len; i++) {
                int val = (src[i] & 0xff);
-               if (isupper(val) || islower(val) || isdigit(val) || strchr_m(other_safe_chars, val))
+               if (isupper_ascii(val) || islower_ascii(val) || isdigit(val) || strchr_m(other_safe_chars, val))
                        dest[i] = src[i];
                else
                        dest[i] = '_';
@@ -774,12 +774,12 @@ size_t strhex_to_str(char *p, size_t len, const char *strhex)
                        continue;
                }
 
-               if (!(p1 = strchr_m(hexchars, toupper(strhex[i]))))
+               if (!(p1 = strchr_m(hexchars, toupper_ascii(strhex[i]))))
                        break;
 
                i++; /* next hex digit */
 
-               if (!(p2 = strchr_m(hexchars, toupper(strhex[i]))))
+               if (!(p2 = strchr_m(hexchars, toupper_ascii(strhex[i]))))
                        break;
 
                /* get the two nybbles */
@@ -1510,7 +1510,7 @@ void strlower_m(char *s)
           (ie. they match for the first 128 chars) */
 
        while (*s && !(((unsigned char)s[0]) & 0x80)) {
-               *s = tolower((unsigned char)*s);
+               *s = tolower_ascii((unsigned char)*s);
                s++;
        }
 
@@ -1544,7 +1544,7 @@ void strupper_m(char *s)
           (ie. they match for the first 128 chars) */
 
        while (*s && !(((unsigned char)s[0]) & 0x80)) {
-               *s = toupper((unsigned char)*s);
+               *s = toupper_ascii((unsigned char)*s);
                s++;
        }
 
index b979745d36640b2d0280df45fb353acbcbf96498..880416a5491c44b2b4b21bad9edf8e98c4f1a9df 100644 (file)
@@ -51,6 +51,7 @@ static uint8 doschar_table[8192]; /* 65536 characters / 8 bits/byte */
 void load_case_tables(void)
 {
        static int initialised;
+       char *old_locale = NULL, *saved_locale = NULL;
        int i;
 
        if (initialised) {
@@ -61,6 +62,17 @@ void load_case_tables(void)
        upcase_table = map_file(lib_path("upcase.dat"), 0x20000);
        lowcase_table = map_file(lib_path("lowcase.dat"), 0x20000);
 
+#ifdef HAVE_SETLOCALE
+       /* Get the name of the current locale.  */
+       old_locale = setlocale(LC_ALL, NULL);
+
+       /* Save it as it is in static storage. */
+       saved_locale = SMB_STRDUP(old_locale);
+
+       /* We set back the locale to C to get ASCII-compatible toupper/lower functions. */
+       setlocale(LC_ALL, "C");
+#endif
+
        /* we would like Samba to limp along even if these tables are
           not available */
        if (!upcase_table) {
@@ -92,6 +104,12 @@ void load_case_tables(void)
                        lowcase_table[v] = UCS2_CHAR(isupper(i)?tolower(i):i);
                }
        }
+
+#ifdef HAVE_SETLOCALE
+       /* Restore the old locale. */
+       setlocale (LC_ALL, saved_locale);
+       SAFE_FREE(saved_locale);
+#endif
 }
 
 /*
@@ -997,3 +1015,41 @@ UNISTR2* ucs2_to_unistr2(TALLOC_CTX *ctx, UNISTR2* dst, smb_ucs2_t* src)
        
        return dst;
 }
+
+/*************************************************************
+ ascii only toupper - saves the need for smbd to be in C locale.
+*************************************************************/
+
+int toupper_ascii(int c)
+{
+       smb_ucs2_t uc = toupper_w(UCS2_CHAR(c));
+       return UCS2_TO_CHAR(uc);
+}
+
+/*************************************************************
+ ascii only tolower - saves the need for smbd to be in C locale.
+*************************************************************/
+
+int tolower_ascii(int c)
+{
+       smb_ucs2_t uc = tolower_w(UCS2_CHAR(c));
+       return UCS2_TO_CHAR(uc);
+}
+
+/*************************************************************
+ ascii only isupper - saves the need for smbd to be in C locale.
+*************************************************************/
+
+int isupper_ascii(int c)
+{
+       return isupper_w(UCS2_CHAR(c));
+}
+
+/*************************************************************
+ ascii only islower - saves the need for smbd to be in C locale.
+*************************************************************/
+
+int islower_ascii(int c)
+{
+       return islower_w(UCS2_CHAR(c));
+}
index 006161b6639580ec78c5df64f51f2e49403d9e6c..ac4d2555978e5803411a8397c555964b8ffcdc52 100644 (file)
@@ -566,8 +566,8 @@ BOOL pdb_gethexpwd(const char *p, unsigned char *pwd)
                return (False);
        
        for (i = 0; i < 32; i += 2) {
-               hinybble = toupper(p[i]);
-               lonybble = toupper(p[i + 1]);
+               hinybble = toupper_ascii(p[i]);
+               lonybble = toupper_ascii(p[i + 1]);
 
                p1 = strchr(hexchars, hinybble);
                p2 = strchr(hexchars, lonybble);
@@ -616,8 +616,8 @@ BOOL pdb_gethexhours(const char *p, unsigned char *hours)
        }
 
        for (i = 0; i < 42; i += 2) {
-               hinybble = toupper(p[i]);
-               lonybble = toupper(p[i + 1]);
+               hinybble = toupper_ascii(p[i]);
+               lonybble = toupper_ascii(p[i + 1]);
 
                p1 = strchr(hexchars, hinybble);
                p2 = strchr(hexchars, lonybble);
index 632903c1ac38d33aa4bb862b8bb9974121277e21..196fe8f855dbf2dcb8465e4d3f2264726e13d1d5 100644 (file)
@@ -368,7 +368,7 @@ static NTSTATUS pgsqlsam_getsampwnam ( struct pdb_methods *methods, SAM_ACCOUNT
   lowercasename = smb_xstrdup(sname);
   l = strlen(lowercasename);
   for(i = 0; i < l; i++) {
-    lowercasename[i] = tolower(lowercasename[i]);
+    lowercasename[i] = tolower_ascii(lowercasename[i]);
   }
   
   result = pgsqlsam_select_by_field( methods, user, SQL_SEARCH_USER_NAME, lowercasename ) ;
index 30befd2c849e6f5aec2c14829f787c865d937f1f..2092f430c0772eff91ccc106b4a9f1158764cddc 100644 (file)
@@ -372,8 +372,8 @@ static BOOL is_mangled(const char *s, int snum)
        magic = strchr_m( s, magic_char );
        while( magic && magic[1] && magic[2] ) {         /* 3 chars, 1st is magic. */
                if( ('.' == magic[3] || '/' == magic[3] || !(magic[3]))          /* Ends with '.' or nul or '/' ?  */
-                               && isbasechar( toupper(magic[1]) )           /* is 2nd char basechar?  */
-                               && isbasechar( toupper(magic[2]) ) )         /* is 3rd char basechar?  */
+                               && isbasechar( toupper_ascii(magic[1]) )           /* is 2nd char basechar?  */
+                               && isbasechar( toupper_ascii(magic[2]) ) )         /* is 3rd char basechar?  */
                        return( True );                           /* If all above, then true, */
                magic = strchr_m( magic+1, magic_char );      /*    else seek next magic. */
        }
@@ -426,7 +426,7 @@ static void cache_mangled_name( const char mangled_name[13], char *raw_name )
        s1 = strrchr( mangled_name_key, '.' );
        if( s1 && (s2 = strrchr( raw_name, '.' )) ) {
                size_t i = 1;
-               while( s1[i] && (tolower( s1[i] ) == s2[i]) )
+               while( s1[i] && (tolower_ascii( s1[i] ) == s2[i]) )
                        i++;
                if( !s1[i] && !s2[i] ) {
                        /* Truncate at the '.' */
index 335ba8e2ef9315e21e1f4240c7a47d14c85b2e27..0a161c9e769f369e68d7065c3bc929195d7f2af0 100644 (file)
@@ -560,7 +560,7 @@ static void name_map(fstring name, BOOL need83, BOOL cache83, int default_case,
                if (! FLAG_CHECK(lead_chars[i], FLAG_ASCII)) {
                        lead_chars[i] = '_';
                }
-               lead_chars[i] = toupper(lead_chars[i]);
+               lead_chars[i] = toupper_ascii(lead_chars[i]);
        }
        for (;i<mangle_prefix;i++) {
                lead_chars[i] = '_';
@@ -580,7 +580,7 @@ static void name_map(fstring name, BOOL need83, BOOL cache83, int default_case,
                for (i=1; extension_length < 3 && dot_p[i]; i++) {
                        char c = dot_p[i];
                        if (FLAG_CHECK(c, FLAG_ASCII)) {
-                               extension[extension_length++] = toupper(c);
+                               extension[extension_length++] = toupper_ascii(c);
                        }
                }
        }
@@ -679,10 +679,10 @@ static void init_tables(void)
                char_flags[c2] |= FLAG_POSSIBLE2;
                char_flags[c3] |= FLAG_POSSIBLE3;
                char_flags[c4] |= FLAG_POSSIBLE4;
-               char_flags[tolower(c1)] |= FLAG_POSSIBLE1;
-               char_flags[tolower(c2)] |= FLAG_POSSIBLE2;
-               char_flags[tolower(c3)] |= FLAG_POSSIBLE3;
-               char_flags[tolower(c4)] |= FLAG_POSSIBLE4;
+               char_flags[tolower_ascii(c1)] |= FLAG_POSSIBLE1;
+               char_flags[tolower_ascii(c2)] |= FLAG_POSSIBLE2;
+               char_flags[tolower_ascii(c3)] |= FLAG_POSSIBLE3;
+               char_flags[tolower_ascii(c4)] |= FLAG_POSSIBLE4;
 
                char_flags[(unsigned char)'.'] |= FLAG_POSSIBLE4;
        }
index 15612484a354bccb35665c1f6888a5564ba6bb30..3806291a6ad4cdc01776fc34f3d75718be96c67f 100644 (file)
@@ -103,7 +103,7 @@ static char *stripspaceupper(const char *str)
        char *p = newstring;
 
        while (*str) {
-               if (*str != ' ') *p++ = toupper(*str);
+               if (*str != ' ') *p++ = toupper_ascii(*str);
                ++str;
        }
        *p = '\0';