Back to index

glibc  2.9
localeinfo.h
Go to the documentation of this file.
00001 /* Declarations for internal libc locale interfaces
00002    Copyright (C) 1995-2003, 2005, 2006, 2007, 2008
00003    Free Software Foundation, Inc.
00004    This file is part of the GNU C Library.
00005 
00006    The GNU C Library is free software; you can redistribute it and/or
00007    modify it under the terms of the GNU Lesser General Public
00008    License as published by the Free Software Foundation; either
00009    version 2.1 of the License, or (at your option) any later version.
00010 
00011    The GNU C Library is distributed in the hope that it will be useful,
00012    but WITHOUT ANY WARRANTY; without even the implied warranty of
00013    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014    Lesser General Public License for more details.
00015 
00016    You should have received a copy of the GNU Lesser General Public
00017    License along with the GNU C Library; if not, write to the Free
00018    Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
00019    02111-1307 USA.  */
00020 
00021 #ifndef _LOCALEINFO_H
00022 #define _LOCALEINFO_H 1
00023 
00024 #include <stddef.h>
00025 #include <langinfo.h>
00026 #include <limits.h>
00027 #include <locale.h>
00028 #include <time.h>
00029 #include <stdint.h>
00030 #include <sys/types.h>
00031 
00032 #include <intl/loadinfo.h>  /* For loaded_l10nfile definition.  */
00033 
00034 /* Magic number at the beginning of a locale data file for CATEGORY.  */
00035 #define       LIMAGIC(category) \
00036   (category == LC_COLLATE                                      \
00037    ? ((unsigned int) (0x20051014 ^ (category)))                       \
00038    : ((unsigned int) (0x20031115 ^ (category))))
00039 
00040 /* Two special weight constants for the collation data.  */
00041 #define IGNORE_CHAR  2
00042 
00043 /* We use a special value for the usage counter in `locale_data' to
00044    signal that this data must never be removed anymore.  */
00045 #define MAX_USAGE_COUNT (UINT_MAX - 1)
00046 #define UNDELETABLE  UINT_MAX
00047 
00048 /* Structure describing locale data in core for a category.  */
00049 struct locale_data
00050 {
00051   const char *name;
00052   const char *filedata;            /* Region mapping the file data.  */
00053   off_t filesize;           /* Size of the file (and the region).  */
00054   enum                      /* Flavor of storage used for those.  */
00055   {
00056     ld_malloced,            /* Both are malloc'd.  */
00057     ld_mapped,                     /* name is malloc'd, filedata mmap'd */
00058     ld_archive                     /* Both point into mmap'd archive regions.  */
00059   } alloc;
00060 
00061   /* This provides a slot for category-specific code to cache data computed
00062      about this locale.  That code can set a cleanup function to deallocate
00063      the data.  */
00064   struct
00065   {
00066     void (*cleanup) (struct locale_data *) internal_function;
00067     union
00068     {
00069       void *data;
00070       struct lc_time_data *time;
00071       const struct gconv_fcts *ctype;
00072     };
00073   } private;
00074 
00075   unsigned int usage_count; /* Counter for users.  */
00076 
00077   int use_translit;         /* Nonzero if the mb*towv*() and wc*tomb()
00078                                functions should use transliteration.  */
00079 
00080   unsigned int nstrings;    /* Number of strings below.  */
00081   union locale_data_value
00082   {
00083     const uint32_t *wstr;
00084     const char *string;
00085     unsigned int word;             /* Note endian issues vs 64-bit pointers.  */
00086   }
00087   values __flexarr;  /* Items, usually pointers into `filedata'.  */
00088 };
00089 
00090 /* We know three kinds of collation sorting rules.  */
00091 enum coll_sort_rule
00092 {
00093   illegal_0__,
00094   sort_forward,
00095   sort_backward,
00096   illegal_3__,
00097   sort_position,
00098   sort_forward_position,
00099   sort_backward_position,
00100   sort_mask
00101 };
00102 
00103 /* We can map the types of the entries into a few categories.  */
00104 enum value_type
00105 {
00106   none,
00107   string,
00108   stringarray,
00109   byte,
00110   bytearray,
00111   word,
00112   stringlist,
00113   wordarray,
00114   wstring,
00115   wstringarray,
00116   wstringlist
00117 };
00118 
00119 
00120 /* Definitions for `era' information from LC_TIME.  */
00121 #define ERA_NAME_FORMAT_MEMBERS 4
00122 #define ERA_M_NAME   0
00123 #define ERA_M_FORMAT 1
00124 #define ERA_W_NAME   2
00125 #define ERA_W_FORMAT 3
00126 
00127 
00128 /* Structure to access `era' information from LC_TIME.  */
00129 struct era_entry
00130 {
00131   uint32_t direction;              /* Contains '+' or '-'.  */
00132   int32_t offset;
00133   int32_t start_date[3];
00134   int32_t stop_date[3];
00135   const char *era_name;
00136   const char *era_format;
00137   const wchar_t *era_wname;
00138   const wchar_t *era_wformat;
00139   int absolute_direction;
00140   /* absolute direction:
00141      +1 indicates that year number is higher in the future. (like A.D.)
00142      -1 indicates that year number is higher in the past. (like B.C.)  */
00143 };
00144 
00145 /* Structure caching computed data about information from LC_TIME.
00146    The `private.time' member of `struct locale_data' points to this.  */
00147 struct lc_time_data
00148 {
00149   struct era_entry *eras;
00150   size_t num_eras;
00151   int era_initialized;
00152 
00153   const char **alt_digits;
00154   const wchar_t **walt_digits;
00155   int alt_digits_initialized;
00156   int walt_digits_initialized;
00157 };
00158 
00159 
00160 /* LC_CTYPE specific:
00161    Hardwired indices for standard wide character translation mappings.  */
00162 enum
00163 {
00164   __TOW_toupper = 0,
00165   __TOW_tolower = 1
00166 };
00167 
00168 
00169 /* LC_CTYPE specific:
00170    Access a wide character class with a single character index.
00171    _ISCTYPE (c, desc) = iswctype (btowc (c), desc).
00172    c must be an `unsigned char'.  desc must be a nonzero wctype_t.  */
00173 #define _ISCTYPE(c, desc) \
00174   (((((const uint32_t *) (desc)) - 8)[(c) >> 5] >> ((c) & 0x1f)) & 1)
00175 
00176 /* Category name handling variables.  */
00177 #define CATNAMEMF(line) CATNAMEMF1 (line)
00178 #define CATNAMEMF1(line) str##line
00179 extern const union catnamestr_t
00180 {
00181   struct
00182   {
00183 #define DEFINE_CATEGORY(category, category_name, items, a) \
00184     char CATNAMEMF (__LINE__)[sizeof (category_name)];
00185 #include "categories.def"
00186 #undef DEFINE_CATEGORY
00187   };
00188   char str[0];
00189 } _nl_category_names attribute_hidden;
00190 extern const uint8_t _nl_category_name_idxs[__LC_LAST] attribute_hidden;
00191 extern const uint8_t _nl_category_name_sizes[__LC_LAST] attribute_hidden;
00192 
00193 /* Name of the standard locales.  */
00194 extern const char _nl_C_name[] attribute_hidden;
00195 extern const char _nl_POSIX_name[] attribute_hidden;
00196 
00197 /* The standard codeset.  */
00198 extern const char _nl_C_codeset[] attribute_hidden;
00199 
00200 /* This is the internal locale_t object that holds the global locale
00201    controlled by calls to setlocale.  A thread's TSD locale pointer
00202    points to this when `uselocale (LC_GLOBAL_LOCALE)' is in effect.  */
00203 extern struct __locale_struct _nl_global_locale attribute_hidden;
00204 
00205 /* This fetches the thread-local locale_t pointer, either one set with
00206    uselocale or &_nl_global_locale.  */
00207 #define _NL_CURRENT_LOCALE  (__libc_tsd_get (__locale_t, LOCALE))
00208 #include <bits/libc-tsd.h>
00209 __libc_tsd_define (extern, __locale_t, LOCALE)
00210 
00211 
00212 /* For static linking it is desireable to avoid always linking in the code
00213    and data for every category when we can tell at link time that they are
00214    unused.  We can manage this playing some tricks with weak references.
00215    But with thread-local locale settings, it becomes quite ungainly unless
00216    we can use __thread variables.  So only in that case do we attempt this.  */
00217 #if !defined SHARED && defined HAVE___THREAD && defined HAVE_WEAK_SYMBOLS
00218 # include <tls.h>
00219 # define NL_CURRENT_INDIRECT       1
00220 #endif
00221 
00222 #ifdef NL_CURRENT_INDIRECT
00223 
00224 /* For each category declare the thread-local variable for the current
00225    locale data.  This has an extra indirection so it points at the
00226    __locales[CATEGORY] element in either _nl_global_locale or the current
00227    locale object set by uselocale, which points at the actual data.  The
00228    reason for having these variables is so that references to particular
00229    categories will link in the lc-CATEGORY.c module to define this symbol,
00230    and we arrange that linking that module is what brings in all the code
00231    associated with this category.  */
00232 #define DEFINE_CATEGORY(category, category_name, items, a) \
00233 extern __thread struct locale_data *const *_nl_current_##category \
00234   attribute_hidden attribute_tls_model_ie;
00235 #include "categories.def"
00236 #undef DEFINE_CATEGORY
00237 
00238 /* Return a pointer to the current `struct locale_data' for CATEGORY.  */
00239 #define _NL_CURRENT_DATA(category) (*_nl_current_##category)
00240 
00241 /* Extract the current CATEGORY locale's string for ITEM.  */
00242 #define _NL_CURRENT(category, item) \
00243   ((*_nl_current_##category)->values[_NL_ITEM_INDEX (item)].string)
00244 
00245 /* Extract the current CATEGORY locale's string for ITEM.  */
00246 #define _NL_CURRENT_WSTR(category, item) \
00247   ((wchar_t *) (*_nl_current_##category)->values[_NL_ITEM_INDEX (item)].wstr)
00248 
00249 /* Extract the current CATEGORY locale's word for ITEM.  */
00250 #define _NL_CURRENT_WORD(category, item) \
00251   ((uint32_t) (*_nl_current_##category)->values[_NL_ITEM_INDEX (item)].word)
00252 
00253 /* This is used in lc-CATEGORY.c to define _nl_current_CATEGORY.  */
00254 #define _NL_CURRENT_DEFINE(category) \
00255   __thread struct locale_data *const *_nl_current_##category \
00256     attribute_hidden = &_nl_global_locale.__locales[category]; \
00257   asm (_NL_CURRENT_DEFINE_STRINGIFY (ASM_GLOBAL_DIRECTIVE) \
00258        " " __SYMBOL_PREFIX "_nl_current_" #category "_used\n" \
00259        _NL_CURRENT_DEFINE_ABS (_nl_current_##category##_used, 1));
00260 #define _NL_CURRENT_DEFINE_STRINGIFY(x) _NL_CURRENT_DEFINE_STRINGIFY_1 (x)
00261 #define _NL_CURRENT_DEFINE_STRINGIFY_1(x) #x
00262 #ifdef HAVE_ASM_SET_DIRECTIVE
00263 # define _NL_CURRENT_DEFINE_ABS(sym, val) ".set " #sym ", " #val
00264 #else
00265 # define _NL_CURRENT_DEFINE_ABS(sym, val) #sym " = " #val
00266 #endif
00267 
00268 #else
00269 
00270 /* All categories are always loaded in the shared library, so there is no
00271    point in having lots of separate symbols for linking.  */
00272 
00273 /* Return a pointer to the current `struct locale_data' for CATEGORY.  */
00274 # define _NL_CURRENT_DATA(category) \
00275   (_NL_CURRENT_LOCALE->__locales[category])
00276 
00277 /* Extract the current CATEGORY locale's string for ITEM.  */
00278 # define _NL_CURRENT(category, item) \
00279   (_NL_CURRENT_DATA (category)->values[_NL_ITEM_INDEX (item)].string)
00280 
00281 /* Extract the current CATEGORY locale's string for ITEM.  */
00282 # define _NL_CURRENT_WSTR(category, item) \
00283   ((wchar_t *) _NL_CURRENT_DATA (category)->values[_NL_ITEM_INDEX (item)].wstr)
00284 
00285 /* Extract the current CATEGORY locale's word for ITEM.  */
00286 # define _NL_CURRENT_WORD(category, item) \
00287   ((uint32_t) _NL_CURRENT_DATA (category)->values[_NL_ITEM_INDEX (item)].word)
00288 
00289 /* This is used in lc-CATEGORY.c to define _nl_current_CATEGORY.  */
00290 # define _NL_CURRENT_DEFINE(category) \
00291   /* No per-category variable here. */
00292 
00293 #endif
00294 
00295 
00296 /* Default search path if no LOCPATH environment variable.  */
00297 extern const char _nl_default_locale_path[] attribute_hidden;
00298 
00299 /* Load the locale data for CATEGORY from the file specified by *NAME.
00300    If *NAME is "", use environment variables as specified by POSIX, and
00301    fill in *NAME with the actual name used.  If LOCALE_PATH is not null,
00302    those directories are searched for the locale files.  If it's null,
00303    the locale archive is checked first and then _nl_default_locale_path
00304    is searched for locale files.  */
00305 extern struct locale_data *_nl_find_locale (const char *locale_path,
00306                                        size_t locale_path_len,
00307                                        int category, const char **name)
00308      internal_function attribute_hidden;
00309 
00310 /* Try to load the file described by FILE.  */
00311 extern void _nl_load_locale (struct loaded_l10nfile *file, int category)
00312      internal_function attribute_hidden;
00313 
00314 /* Free all resource.  */
00315 extern void _nl_unload_locale (struct locale_data *locale)
00316      internal_function attribute_hidden;
00317 
00318 /* Free the locale and give back all memory if the usage count is one.  */
00319 extern void _nl_remove_locale (int locale, struct locale_data *data)
00320      internal_function attribute_hidden;
00321 
00322 /* Find the locale *NAMEP in the locale archive, and return the
00323    internalized data structure for its CATEGORY data.  If this locale has
00324    already been loaded from the archive, just returns the existing data
00325    structure.  If successful, sets *NAMEP to point directly into the mapped
00326    archive string table; that way, the next call can short-circuit strcmp.  */
00327 extern struct locale_data *_nl_load_locale_from_archive (int category,
00328                                                   const char **namep)
00329      internal_function attribute_hidden;
00330 
00331 /* Subroutine of setlocale's __libc_subfreeres hook.  */
00332 extern void _nl_archive_subfreeres (void) attribute_hidden;
00333 
00334 /* Subroutine of gconv-db's __libc_subfreeres hook.  */
00335 extern void _nl_locale_subfreeres (void) attribute_hidden;
00336 
00337 /* Validate the contents of a locale file and set up the in-core
00338    data structure to point into the data.  This leaves the `alloc'
00339    and `name' fields uninitialized, for the caller to fill in.
00340    If any bogons are detected in the data, this will refuse to
00341    intern it, and return a null pointer instead.  */
00342 extern struct locale_data *_nl_intern_locale_data (int category,
00343                                              const void *data,
00344                                              size_t datasize)
00345      internal_function attribute_hidden;
00346 
00347 
00348 /* Return `era' entry which corresponds to TP.  Used in strftime.  */
00349 extern struct era_entry *_nl_get_era_entry (const struct tm *tp,
00350                                        struct locale_data *lc_time)
00351      internal_function attribute_hidden;
00352 
00353 /* Return `era' cnt'th entry .  Used in strptime.  */
00354 extern struct era_entry *_nl_select_era_entry (int cnt,
00355                                           struct locale_data *lc_time)
00356           internal_function attribute_hidden;
00357 
00358 /* Return `alt_digit' which corresponds to NUMBER.  Used in strftime.  */
00359 extern const char *_nl_get_alt_digit (unsigned int number,
00360                                   struct locale_data *lc_time)
00361           internal_function attribute_hidden;
00362 
00363 /* Similar, but now for wide characters.  */
00364 extern const wchar_t *_nl_get_walt_digit (unsigned int number,
00365                                      struct locale_data *lc_time)
00366      internal_function attribute_hidden;
00367 
00368 /* Parse string as alternative digit and return numeric value.  */
00369 extern int _nl_parse_alt_digit (const char **strp,
00370                             struct locale_data *lc_time)
00371      internal_function attribute_hidden;
00372 
00373 /* Postload processing.  */
00374 extern void _nl_postload_ctype (void);
00375 
00376 /* Functions used for the `private.cleanup' hook.  */
00377 extern void _nl_cleanup_time (struct locale_data *)
00378      internal_function attribute_hidden;
00379 
00380 
00381 #endif /* localeinfo.h */