diff options
Diffstat (limited to 'lib/nl_langinfo.c')
-rw-r--r-- | lib/nl_langinfo.c | 255 |
1 files changed, 102 insertions, 153 deletions
diff --git a/lib/nl_langinfo.c b/lib/nl_langinfo.c index ff0adc4b9..83d2c77af 100644 --- a/lib/nl_langinfo.c +++ b/lib/nl_langinfo.c @@ -1,6 +1,6 @@ /* nl_langinfo() replacement: query locale dependent information. - Copyright (C) 2007-2015 Free Software Foundation, Inc. + Copyright (C) 2007-2014 Free Software Foundation, Inc. This program is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by @@ -20,72 +20,13 @@ /* Specification. */ #include <langinfo.h> -#include <locale.h> -#include <string.h> -#if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__ -# define WIN32_LEAN_AND_MEAN /* avoid including junk */ -# include <windows.h> -# include <stdio.h> -#endif - -/* Return the codeset of the current locale, if this is easily deducible. - Otherwise, return "". */ -static char * -ctype_codeset (void) -{ - static char buf[2 + 10 + 1]; - size_t buflen = 0; - char const *locale = setlocale (LC_CTYPE, NULL); - char *codeset = buf; - size_t codesetlen; - codeset[0] = '\0'; - - if (locale && locale[0]) - { - /* If the locale name contains an encoding after the dot, return it. */ - char *dot = strchr (locale, '.'); - - if (dot) - { - /* Look for the possible @... trailer and remove it, if any. */ - char *codeset_start = dot + 1; - char const *modifier = strchr (codeset_start, '@'); - - if (! modifier) - codeset = codeset_start; - else - { - codesetlen = modifier - codeset_start; - if (codesetlen < sizeof buf) - { - codeset = memcpy (buf, codeset_start, codesetlen); - codeset[codesetlen] = '\0'; - } - } - } - } - -#if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__ - /* If setlocale is successful, it returns the number of the - codepage, as a string. Otherwise, fall back on Windows API - GetACP, which returns the locale's codepage as a number (although - this doesn't change according to what the 'setlocale' call specified). - Either way, prepend "CP" to make it a valid codeset name. */ - codesetlen = strlen (codeset); - if (0 < codesetlen && codesetlen < sizeof buf - 2) - memmove (buf + 2, codeset, codesetlen + 1); - else - sprintf (buf + 2, "%u", GetACP ()); - codeset = memcpy (buf, "CP", 2); -#endif - return codeset; -} - - #if REPLACE_NL_LANGINFO /* Override nl_langinfo with support for added nl_item values. */ +# include <locale.h> +# include <string.h> + # undef nl_langinfo char * @@ -95,7 +36,36 @@ rpl_nl_langinfo (nl_item item) { # if GNULIB_defined_CODESET case CODESET: - return ctype_codeset (); + { + const char *locale; + static char buf[2 + 10 + 1]; + + locale = setlocale (LC_CTYPE, NULL); + if (locale != NULL && locale[0] != '\0') + { + /* If the locale name contains an encoding after the dot, return + it. */ + const char *dot = strchr (locale, '.'); + + if (dot != NULL) + { + const char *modifier; + + dot++; + /* Look for the possible @... trailer and remove it, if any. */ + modifier = strchr (dot, '@'); + if (modifier == NULL) + return dot; + if (modifier - dot < sizeof (buf)) + { + memcpy (buf, dot, modifier - dot); + buf [modifier - dot] = '\0'; + return buf; + } + } + } + return ""; + } # endif # if GNULIB_defined_T_FMT_AMPM case T_FMT_AMPM: @@ -141,28 +111,42 @@ rpl_nl_langinfo (nl_item item) #else -/* Provide nl_langinfo from scratch, either for native MS-Windows, or - for old Unix platforms without locales, such as Linux libc5 or - BeOS. */ +/* Provide nl_langinfo from scratch. */ + +# if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__ -# include <time.h> +/* Native Windows platforms. */ + +# define WIN32_LEAN_AND_MEAN /* avoid including junk */ +# include <windows.h> + +# include <stdio.h> + +# else + +/* An old Unix platform without locales, such as Linux libc5 or BeOS. */ + +# endif + +# include <locale.h> char * nl_langinfo (nl_item item) { - static char nlbuf[100]; - struct tm tmm = { 0 }; - switch (item) { /* nl_langinfo items of the LC_CTYPE category */ case CODESET: +# if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__ { - char *codeset = ctype_codeset (); - if (*codeset) - return codeset; + static char buf[2 + 10 + 1]; + + /* The Windows API has a function returning the locale's codepage as + a number. */ + sprintf (buf, "CP%u", GetACP ()); + return buf; } -# ifdef __BEOS__ +# elif defined __BEOS__ return "UTF-8"; # else return "ISO-8859-1"; @@ -172,8 +156,6 @@ nl_langinfo (nl_item item) return localeconv () ->decimal_point; case THOUSEP: return localeconv () ->thousands_sep; - case GROUPING: - return localeconv () ->grouping; /* nl_langinfo items of the LC_TIME category. TODO: Really use the locale. */ case D_T_FMT: @@ -188,126 +170,93 @@ nl_langinfo (nl_item item) case T_FMT_AMPM: return "%I:%M:%S %p"; case AM_STR: - if (!strftime (nlbuf, sizeof nlbuf, "%p", &tmm)) - return "AM"; - return nlbuf; + return "AM"; case PM_STR: - tmm.tm_hour = 12; - if (!strftime (nlbuf, sizeof nlbuf, "%p", &tmm)) - return "PM"; - return nlbuf; + return "PM"; case DAY_1: + return "Sunday"; case DAY_2: + return "Monday"; case DAY_3: + return "Tuesday"; case DAY_4: + return "Wednesday"; case DAY_5: + return "Thursday"; case DAY_6: + return "Friday"; case DAY_7: - { - static char const days[][sizeof "Wednesday"] = { - "Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", - "Friday", "Saturday" - }; - tmm.tm_wday = item - DAY_1; - if (!strftime (nlbuf, sizeof nlbuf, "%A", &tmm)) - return (char *) days[item - DAY_1]; - return nlbuf; - } + return "Saturday"; case ABDAY_1: + return "Sun"; case ABDAY_2: + return "Mon"; case ABDAY_3: + return "Tue"; case ABDAY_4: + return "Wed"; case ABDAY_5: + return "Thu"; case ABDAY_6: + return "Fri"; case ABDAY_7: - { - static char const abdays[][sizeof "Sun"] = { - "Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat" - }; - tmm.tm_wday = item - ABDAY_1; - if (!strftime (nlbuf, sizeof nlbuf, "%a", &tmm)) - return (char *) abdays[item - ABDAY_1]; - return nlbuf; - } + return "Sat"; case MON_1: + return "January"; case MON_2: + return "February"; case MON_3: + return "March"; case MON_4: + return "April"; case MON_5: + return "May"; case MON_6: + return "June"; case MON_7: + return "July"; case MON_8: + return "August"; case MON_9: + return "September"; case MON_10: + return "October"; case MON_11: + return "November"; case MON_12: - { - static char const months[][sizeof "September"] = { - "January", "February", "March", "April", "May", "June", "July", - "September", "October", "November", "December" - }; - tmm.tm_mon = item - MON_1; - if (!strftime (nlbuf, sizeof nlbuf, "%B", &tmm)) - return (char *) months[item - MON_1]; - return nlbuf; - } + return "December"; case ABMON_1: + return "Jan"; case ABMON_2: + return "Feb"; case ABMON_3: + return "Mar"; case ABMON_4: + return "Apr"; case ABMON_5: + return "May"; case ABMON_6: + return "Jun"; case ABMON_7: + return "Jul"; case ABMON_8: + return "Aug"; case ABMON_9: + return "Sep"; case ABMON_10: + return "Oct"; case ABMON_11: + return "Nov"; case ABMON_12: - { - static char const abmonths[][sizeof "Jan"] = { - "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", - "Sep", "Oct", "Nov", "Dec" - }; - tmm.tm_mon = item - ABMON_1; - if (!strftime (nlbuf, sizeof nlbuf, "%b", &tmm)) - return (char *) abmonths[item - ABMON_1]; - return nlbuf; - } + return "Dec"; case ERA: return ""; case ALT_DIGITS: return "\0\0\0\0\0\0\0\0\0\0"; - /* nl_langinfo items of the LC_MONETARY category. */ + /* nl_langinfo items of the LC_MONETARY category + TODO: Really use the locale. */ case CRNCYSTR: - return localeconv () ->currency_symbol; - case INT_CURR_SYMBOL: - return localeconv () ->int_curr_symbol; - case MON_DECIMAL_POINT: - return localeconv () ->mon_decimal_point; - case MON_THOUSANDS_SEP: - return localeconv () ->mon_thousands_sep; - case MON_GROUPING: - return localeconv () ->mon_grouping; - case POSITIVE_SIGN: - return localeconv () ->positive_sign; - case NEGATIVE_SIGN: - return localeconv () ->negative_sign; - case FRAC_DIGITS: - return & localeconv () ->frac_digits; - case INT_FRAC_DIGITS: - return & localeconv () ->int_frac_digits; - case P_CS_PRECEDES: - return & localeconv () ->p_cs_precedes; - case N_CS_PRECEDES: - return & localeconv () ->n_cs_precedes; - case P_SEP_BY_SPACE: - return & localeconv () ->p_sep_by_space; - case N_SEP_BY_SPACE: - return & localeconv () ->n_sep_by_space; - case P_SIGN_POSN: - return & localeconv () ->p_sign_posn; - case N_SIGN_POSN: - return & localeconv () ->n_sign_posn; + return "-"; /* nl_langinfo items of the LC_MESSAGES category TODO: Really use the locale. */ case YESEXPR: |