Support one-parameter unpack(), which unpacks $_.
[perl.git] / locale.c
1 /*    locale.c
2  *
3  *    Copyright (c) 2001-2002, Larry Wall
4  *
5  *    You may distribute under the terms of either the GNU General Public
6  *    License or the Artistic License, as specified in the README file.
7  *
8  */
9
10 /*
11  * A Elbereth Gilthoniel,
12  * silivren penna m�riel
13  * o menel aglar elenath!
14  * Na-chaered palan-d�riel
15  * o galadhremmin ennorath,
16  * Fanuilos, le linnathon
17  * nef aear, si nef aearon!
18  */
19
20 #include "EXTERN.h"
21 #define PERL_IN_LOCALE_C
22 #include "perl.h"
23
24 #ifdef I_LOCALE
25 #  include <locale.h>
26 #endif
27
28 #ifdef I_LANGINFO
29 #   include <langinfo.h>
30 #endif
31
32 #include "reentr.h"
33
34 /*
35  * Standardize the locale name from a string returned by 'setlocale'.
36  *
37  * The standard return value of setlocale() is either
38  * (1) "xx_YY" if the first argument of setlocale() is not LC_ALL
39  * (2) "xa_YY xb_YY ..." if the first argument of setlocale() is LC_ALL
40  *     (the space-separated values represent the various sublocales,
41  *      in some unspecificed order)
42  *
43  * In some platforms it has a form like "LC_SOMETHING=Lang_Country.866\n",
44  * which is harmful for further use of the string in setlocale().
45  *
46  */
47 STATIC char *
48 S_stdize_locale(pTHX_ char *locs)
49 {
50     char *s;
51     bool okay = TRUE;
52
53     if ((s = strchr(locs, '='))) {
54         char *t;
55
56         okay = FALSE;
57         if ((t = strchr(s, '.'))) {
58             char *u;
59
60             if ((u = strchr(t, '\n'))) {
61
62                 if (u[1] == 0) {
63                     STRLEN len = u - s;
64                     Move(s + 1, locs, len, char);
65                     locs[len] = 0;
66                     okay = TRUE;
67                 }
68             }
69         }
70     }
71
72     if (!okay)
73         Perl_croak(aTHX_ "Can't fix broken locale name \"%s\"", locs);
74
75     return locs;
76 }
77
78 void
79 Perl_set_numeric_radix(pTHX)
80 {
81 #ifdef USE_LOCALE_NUMERIC
82 # ifdef HAS_LOCALECONV
83     struct lconv* lc;
84
85     lc = localeconv();
86     if (lc && lc->decimal_point) {
87         if (lc->decimal_point[0] == '.' && lc->decimal_point[1] == 0) {
88             SvREFCNT_dec(PL_numeric_radix_sv);
89             PL_numeric_radix_sv = Nullsv;
90         }
91         else {
92             if (PL_numeric_radix_sv)
93                 sv_setpv(PL_numeric_radix_sv, lc->decimal_point);
94             else
95                 PL_numeric_radix_sv = newSVpv(lc->decimal_point, 0);
96         }
97     }
98     else
99         PL_numeric_radix_sv = Nullsv;
100 # endif /* HAS_LOCALECONV */
101 #endif /* USE_LOCALE_NUMERIC */
102 }
103
104 /*
105  * Set up for a new numeric locale.
106  */
107 void
108 Perl_new_numeric(pTHX_ char *newnum)
109 {
110 #ifdef USE_LOCALE_NUMERIC
111
112     if (! newnum) {
113         if (PL_numeric_name) {
114             Safefree(PL_numeric_name);
115             PL_numeric_name = NULL;
116         }
117         PL_numeric_standard = TRUE;
118         PL_numeric_local = TRUE;
119         return;
120     }
121
122     if (! PL_numeric_name || strNE(PL_numeric_name, newnum)) {
123         Safefree(PL_numeric_name);
124         PL_numeric_name = stdize_locale(savepv(newnum));
125         PL_numeric_standard = (strEQ(newnum, "C") || strEQ(newnum, "POSIX"));
126         PL_numeric_local = TRUE;
127         set_numeric_radix();
128     }
129
130 #endif /* USE_LOCALE_NUMERIC */
131 }
132
133 void
134 Perl_set_numeric_standard(pTHX)
135 {
136 #ifdef USE_LOCALE_NUMERIC
137
138     if (! PL_numeric_standard) {
139         setlocale(LC_NUMERIC, "C");
140         PL_numeric_standard = TRUE;
141         PL_numeric_local = FALSE;
142         set_numeric_radix();
143     }
144
145 #endif /* USE_LOCALE_NUMERIC */
146 }
147
148 void
149 Perl_set_numeric_local(pTHX)
150 {
151 #ifdef USE_LOCALE_NUMERIC
152
153     if (! PL_numeric_local) {
154         setlocale(LC_NUMERIC, PL_numeric_name);
155         PL_numeric_standard = FALSE;
156         PL_numeric_local = TRUE;
157         set_numeric_radix();
158     }
159
160 #endif /* USE_LOCALE_NUMERIC */
161 }
162
163 /*
164  * Set up for a new ctype locale.
165  */
166 void
167 Perl_new_ctype(pTHX_ char *newctype)
168 {
169 #ifdef USE_LOCALE_CTYPE
170
171     int i;
172
173     for (i = 0; i < 256; i++) {
174         if (isUPPER_LC(i))
175             PL_fold_locale[i] = toLOWER_LC(i);
176         else if (isLOWER_LC(i))
177             PL_fold_locale[i] = toUPPER_LC(i);
178         else
179             PL_fold_locale[i] = i;
180     }
181
182 #endif /* USE_LOCALE_CTYPE */
183 }
184
185 /*
186  * Set up for a new collation locale.
187  */
188 void
189 Perl_new_collate(pTHX_ char *newcoll)
190 {
191 #ifdef USE_LOCALE_COLLATE
192
193     if (! newcoll) {
194         if (PL_collation_name) {
195             ++PL_collation_ix;
196             Safefree(PL_collation_name);
197             PL_collation_name = NULL;
198         }
199         PL_collation_standard = TRUE;
200         PL_collxfrm_base = 0;
201         PL_collxfrm_mult = 2;
202         return;
203     }
204
205     if (! PL_collation_name || strNE(PL_collation_name, newcoll)) {
206         ++PL_collation_ix;
207         Safefree(PL_collation_name);
208         PL_collation_name = stdize_locale(savepv(newcoll));
209         PL_collation_standard = (strEQ(newcoll, "C") || strEQ(newcoll, "POSIX"));
210
211         {
212           /*  2: at most so many chars ('a', 'b'). */
213           /* 50: surely no system expands a char more. */
214 #define XFRMBUFSIZE  (2 * 50)
215           char xbuf[XFRMBUFSIZE];
216           Size_t fa = strxfrm(xbuf, "a",  XFRMBUFSIZE);
217           Size_t fb = strxfrm(xbuf, "ab", XFRMBUFSIZE);
218           SSize_t mult = fb - fa;
219           if (mult < 1)
220               Perl_croak(aTHX_ "strxfrm() gets absurd");
221           PL_collxfrm_base = (fa > (Size_t)mult) ? (fa - mult) : 0;
222           PL_collxfrm_mult = mult;
223         }
224     }
225
226 #endif /* USE_LOCALE_COLLATE */
227 }
228
229 /*
230  * Initialize locale awareness.
231  */
232 int
233 Perl_init_i18nl10n(pTHX_ int printwarn)
234 {
235     int ok = 1;
236     /* returns
237      *    1 = set ok or not applicable,
238      *    0 = fallback to C locale,
239      *   -1 = fallback to C locale failed
240      */
241
242 #if defined(USE_LOCALE)
243
244 #ifdef USE_LOCALE_CTYPE
245     char *curctype   = NULL;
246 #endif /* USE_LOCALE_CTYPE */
247 #ifdef USE_LOCALE_COLLATE
248     char *curcoll    = NULL;
249 #endif /* USE_LOCALE_COLLATE */
250 #ifdef USE_LOCALE_NUMERIC
251     char *curnum     = NULL;
252 #endif /* USE_LOCALE_NUMERIC */
253 #ifdef __GLIBC__
254     char *language   = PerlEnv_getenv("LANGUAGE");
255 #endif
256     char *lc_all     = PerlEnv_getenv("LC_ALL");
257     char *lang       = PerlEnv_getenv("LANG");
258     bool setlocale_failure = FALSE;
259
260 #ifdef LOCALE_ENVIRON_REQUIRED
261
262     /*
263      * Ultrix setlocale(..., "") fails if there are no environment
264      * variables from which to get a locale name.
265      */
266
267     bool done = FALSE;
268
269 #ifdef LC_ALL
270     if (lang) {
271         if (setlocale(LC_ALL, ""))
272             done = TRUE;
273         else
274             setlocale_failure = TRUE;
275     }
276     if (!setlocale_failure) {
277 #ifdef USE_LOCALE_CTYPE
278         if (! (curctype =
279                setlocale(LC_CTYPE,
280                          (!done && (lang || PerlEnv_getenv("LC_CTYPE")))
281                                     ? "" : Nullch)))
282             setlocale_failure = TRUE;
283         else
284             curctype = savepv(curctype);
285 #endif /* USE_LOCALE_CTYPE */
286 #ifdef USE_LOCALE_COLLATE
287         if (! (curcoll =
288                setlocale(LC_COLLATE,
289                          (!done && (lang || PerlEnv_getenv("LC_COLLATE")))
290                                    ? "" : Nullch)))
291             setlocale_failure = TRUE;
292         else
293             curcoll = savepv(curcoll);
294 #endif /* USE_LOCALE_COLLATE */
295 #ifdef USE_LOCALE_NUMERIC
296         if (! (curnum =
297                setlocale(LC_NUMERIC,
298                          (!done && (lang || PerlEnv_getenv("LC_NUMERIC")))
299                                   ? "" : Nullch)))
300             setlocale_failure = TRUE;
301         else
302             curnum = savepv(curnum);
303 #endif /* USE_LOCALE_NUMERIC */
304     }
305
306 #endif /* LC_ALL */
307
308 #endif /* !LOCALE_ENVIRON_REQUIRED */
309
310 #ifdef LC_ALL
311     if (! setlocale(LC_ALL, ""))
312         setlocale_failure = TRUE;
313 #endif /* LC_ALL */
314
315     if (!setlocale_failure) {
316 #ifdef USE_LOCALE_CTYPE
317         if (! (curctype = setlocale(LC_CTYPE, "")))
318             setlocale_failure = TRUE;
319         else
320             curctype = savepv(curctype);
321 #endif /* USE_LOCALE_CTYPE */
322 #ifdef USE_LOCALE_COLLATE
323         if (! (curcoll = setlocale(LC_COLLATE, "")))
324             setlocale_failure = TRUE;
325         else
326             curcoll = savepv(curcoll);
327 #endif /* USE_LOCALE_COLLATE */
328 #ifdef USE_LOCALE_NUMERIC
329         if (! (curnum = setlocale(LC_NUMERIC, "")))
330             setlocale_failure = TRUE;
331         else
332             curnum = savepv(curnum);
333 #endif /* USE_LOCALE_NUMERIC */
334     }
335
336     if (setlocale_failure) {
337         char *p;
338         bool locwarn = (printwarn > 1 ||
339                         (printwarn &&
340                          (!(p = PerlEnv_getenv("PERL_BADLANG")) || atoi(p))));
341
342         if (locwarn) {
343 #ifdef LC_ALL
344
345             PerlIO_printf(Perl_error_log,
346                "perl: warning: Setting locale failed.\n");
347
348 #else /* !LC_ALL */
349
350             PerlIO_printf(Perl_error_log,
351                "perl: warning: Setting locale failed for the categories:\n\t");
352 #ifdef USE_LOCALE_CTYPE
353             if (! curctype)
354                 PerlIO_printf(Perl_error_log, "LC_CTYPE ");
355 #endif /* USE_LOCALE_CTYPE */
356 #ifdef USE_LOCALE_COLLATE
357             if (! curcoll)
358                 PerlIO_printf(Perl_error_log, "LC_COLLATE ");
359 #endif /* USE_LOCALE_COLLATE */
360 #ifdef USE_LOCALE_NUMERIC
361             if (! curnum)
362                 PerlIO_printf(Perl_error_log, "LC_NUMERIC ");
363 #endif /* USE_LOCALE_NUMERIC */
364             PerlIO_printf(Perl_error_log, "\n");
365
366 #endif /* LC_ALL */
367
368             PerlIO_printf(Perl_error_log,
369                 "perl: warning: Please check that your locale settings:\n");
370
371 #ifdef __GLIBC__
372             PerlIO_printf(Perl_error_log,
373                           "\tLANGUAGE = %c%s%c,\n",
374                           language ? '"' : '(',
375                           language ? language : "unset",
376                           language ? '"' : ')');
377 #endif
378
379             PerlIO_printf(Perl_error_log,
380                           "\tLC_ALL = %c%s%c,\n",
381                           lc_all ? '"' : '(',
382                           lc_all ? lc_all : "unset",
383                           lc_all ? '"' : ')');
384
385 #if defined(USE_ENVIRON_ARRAY)
386             {
387               char **e;
388               for (e = environ; *e; e++) {
389                   if (strnEQ(*e, "LC_", 3)
390                         && strnNE(*e, "LC_ALL=", 7)
391                         && (p = strchr(*e, '=')))
392                       PerlIO_printf(Perl_error_log, "\t%.*s = \"%s\",\n",
393                                     (int)(p - *e), *e, p + 1);
394               }
395             }
396 #else
397             PerlIO_printf(Perl_error_log,
398                           "\t(possibly more locale environment variables)\n");
399 #endif
400
401             PerlIO_printf(Perl_error_log,
402                           "\tLANG = %c%s%c\n",
403                           lang ? '"' : '(',
404                           lang ? lang : "unset",
405                           lang ? '"' : ')');
406
407             PerlIO_printf(Perl_error_log,
408                           "    are supported and installed on your system.\n");
409         }
410
411 #ifdef LC_ALL
412
413         if (setlocale(LC_ALL, "C")) {
414             if (locwarn)
415                 PerlIO_printf(Perl_error_log,
416       "perl: warning: Falling back to the standard locale (\"C\").\n");
417             ok = 0;
418         }
419         else {
420             if (locwarn)
421                 PerlIO_printf(Perl_error_log,
422       "perl: warning: Failed to fall back to the standard locale (\"C\").\n");
423             ok = -1;
424         }
425
426 #else /* ! LC_ALL */
427
428         if (0
429 #ifdef USE_LOCALE_CTYPE
430             || !(curctype || setlocale(LC_CTYPE, "C"))
431 #endif /* USE_LOCALE_CTYPE */
432 #ifdef USE_LOCALE_COLLATE
433             || !(curcoll || setlocale(LC_COLLATE, "C"))
434 #endif /* USE_LOCALE_COLLATE */
435 #ifdef USE_LOCALE_NUMERIC
436             || !(curnum || setlocale(LC_NUMERIC, "C"))
437 #endif /* USE_LOCALE_NUMERIC */
438             )
439         {
440             if (locwarn)
441                 PerlIO_printf(Perl_error_log,
442       "perl: warning: Cannot fall back to the standard locale (\"C\").\n");
443             ok = -1;
444         }
445
446 #endif /* ! LC_ALL */
447
448 #ifdef USE_LOCALE_CTYPE
449         curctype = savepv(setlocale(LC_CTYPE, Nullch));
450 #endif /* USE_LOCALE_CTYPE */
451 #ifdef USE_LOCALE_COLLATE
452         curcoll = savepv(setlocale(LC_COLLATE, Nullch));
453 #endif /* USE_LOCALE_COLLATE */
454 #ifdef USE_LOCALE_NUMERIC
455         curnum = savepv(setlocale(LC_NUMERIC, Nullch));
456 #endif /* USE_LOCALE_NUMERIC */
457     }
458     else {
459
460 #ifdef USE_LOCALE_CTYPE
461     new_ctype(curctype);
462 #endif /* USE_LOCALE_CTYPE */
463
464 #ifdef USE_LOCALE_COLLATE
465     new_collate(curcoll);
466 #endif /* USE_LOCALE_COLLATE */
467
468 #ifdef USE_LOCALE_NUMERIC
469     new_numeric(curnum);
470 #endif /* USE_LOCALE_NUMERIC */
471
472     }
473
474 #endif /* USE_LOCALE */
475
476 #ifdef USE_PERLIO
477     {
478       /* Set PL_utf8locale to TRUE if using PerlIO _and_
479          any of the following are true:
480          - nl_langinfo(CODESET) contains /^utf-?8/i
481          - $ENV{LC_ALL}   contains /^utf-?8/i
482          - $ENV{LC_CTYPE} contains /^utf-?8/i
483          - $ENV{LANG}     contains /^utf-?8/i
484          The LC_ALL, LC_CTYPE, LANG obey the usual override
485          hierarchy of locale environment variables.  (LANGUAGE
486          affects only LC_MESSAGES only under glibc.) (If present,
487          it overrides LC_MESSAGES for GNU gettext, and it also
488          can have more than one locale, separated by spaces,
489          in case you need to know.)
490          If PL_utf8locale and PL_unicode (set by -C or by $ENV{PERL_UNICODE})
491          are true, perl.c:S_parse_body() will turn on the PerlIO :utf8 layer
492          on STDIN, STDOUT, STDERR, _and_ the default open discipline.
493       */
494          bool utf8locale = FALSE;
495          char *codeset = NULL;
496 #if defined(HAS_NL_LANGINFO) && defined(CODESET)
497          codeset = nl_langinfo(CODESET);
498 #endif
499          if (codeset)
500               utf8locale = (ibcmp(codeset,  "UTF-8", 5) == 0 ||
501                             ibcmp(codeset,  "UTF8",  4) == 0);
502 #if defined(USE_LOCALE)
503          else { /* nl_langinfo(CODESET) is supposed to correctly
504                  * interpret the locale environment variables,
505                  * but just in case it fails, let's do this manually. */ 
506               if (lang)
507                    utf8locale = (ibcmp(lang,     "UTF-8", 5) == 0 ||
508                                  ibcmp(lang,     "UTF8",  4) == 0);
509 #ifdef USE_LOCALE_CTYPE
510               if (curctype)
511                    utf8locale = (ibcmp(curctype,     "UTF-8", 5) == 0 ||
512                                  ibcmp(curctype,     "UTF8",  4) == 0);
513 #endif
514               if (lc_all)
515                    utf8locale = (ibcmp(lc_all,   "UTF-8", 5) == 0 ||
516                                  ibcmp(lc_all,   "UTF8",  4) == 0);
517          }
518 #endif /* USE_LOCALE */
519          if (utf8locale)
520               PL_utf8locale = TRUE;
521     }
522     /* Set PL_unicode to $ENV{PERL_UNICODE} if using PerlIO.
523        This is an alternative to using the -C command line switch
524        (the -C if present will override this). */
525     {
526          char *p = PerlEnv_getenv("PERL_UNICODE");
527          PL_unicode = p ? parse_unicode_opts(&p) : 0;
528     }
529 #endif
530
531 #ifdef USE_LOCALE_CTYPE
532     if (curctype != NULL)
533         Safefree(curctype);
534 #endif /* USE_LOCALE_CTYPE */
535 #ifdef USE_LOCALE_COLLATE
536     if (curcoll != NULL)
537         Safefree(curcoll);
538 #endif /* USE_LOCALE_COLLATE */
539 #ifdef USE_LOCALE_NUMERIC
540     if (curnum != NULL)
541         Safefree(curnum);
542 #endif /* USE_LOCALE_NUMERIC */
543     return ok;
544 }
545
546 /* Backwards compatibility. */
547 int
548 Perl_init_i18nl14n(pTHX_ int printwarn)
549 {
550     return init_i18nl10n(printwarn);
551 }
552
553 #ifdef USE_LOCALE_COLLATE
554
555 /*
556  * mem_collxfrm() is a bit like strxfrm() but with two important
557  * differences. First, it handles embedded NULs. Second, it allocates
558  * a bit more memory than needed for the transformed data itself.
559  * The real transformed data begins at offset sizeof(collationix).
560  * Please see sv_collxfrm() to see how this is used.
561  */
562 char *
563 Perl_mem_collxfrm(pTHX_ const char *s, STRLEN len, STRLEN *xlen)
564 {
565     char *xbuf;
566     STRLEN xAlloc, xin, xout; /* xalloc is a reserved word in VC */
567
568     /* the first sizeof(collationix) bytes are used by sv_collxfrm(). */
569     /* the +1 is for the terminating NUL. */
570
571     xAlloc = sizeof(PL_collation_ix) + PL_collxfrm_base + (PL_collxfrm_mult * len) + 1;
572     New(171, xbuf, xAlloc, char);
573     if (! xbuf)
574         goto bad;
575
576     *(U32*)xbuf = PL_collation_ix;
577     xout = sizeof(PL_collation_ix);
578     for (xin = 0; xin < len; ) {
579         SSize_t xused;
580
581         for (;;) {
582             xused = strxfrm(xbuf + xout, s + xin, xAlloc - xout);
583             if (xused == -1)
584                 goto bad;
585             if ((STRLEN)xused < xAlloc - xout)
586                 break;
587             xAlloc = (2 * xAlloc) + 1;
588             Renew(xbuf, xAlloc, char);
589             if (! xbuf)
590                 goto bad;
591         }
592
593         xin += strlen(s + xin) + 1;
594         xout += xused;
595
596         /* Embedded NULs are understood but silently skipped
597          * because they make no sense in locale collation. */
598     }
599
600     xbuf[xout] = '\0';
601     *xlen = xout - sizeof(PL_collation_ix);
602     return xbuf;
603
604   bad:
605     Safefree(xbuf);
606     *xlen = 0;
607     return NULL;
608 }
609
610 #endif /* USE_LOCALE_COLLATE */
611