1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/os/ossrv/genericopenlibs/cppstdlib/stl/src/locale_catalog.cpp Fri Jun 15 03:10:57 2012 +0200
1.3 @@ -0,0 +1,308 @@
1.4 +/*
1.5 + * Portions Copyright (c) 2008 Nokia Corporation and/or its subsidiary(-ies). All rights reserved.
1.6 + *
1.7 + * Copyright (c) 1999
1.8 + * Silicon Graphics Computer Systems, Inc.
1.9 + *
1.10 + * Copyright (c) 1999
1.11 + * Boris Fomitchev
1.12 + *
1.13 + * This material is provided "as is", with absolutely no warranty expressed
1.14 + * or implied. Any use is at your own risk.
1.15 + *
1.16 + * Permission to use or copy this software for any purpose is hereby granted
1.17 + * without fee, provided the above notices are retained on all copies.
1.18 + * Permission to modify the code and to distribute modified code is granted,
1.19 + * provided the above notices are retained, and a notice that the code was
1.20 + * modified is included with the above copyright notice.
1.21 + *
1.22 + */
1.23 +#include "stlport_prefix.h"
1.24 +
1.25 +#include <hash_map>
1.26 +#include <string>
1.27 +
1.28 +#include <locale>
1.29 +#include <istream>
1.30 +
1.31 +#include "c_locale.h"
1.32 +#include "locale_impl.h"
1.33 +#include "acquire_release.h"
1.34 +
1.35 +#if defined(__SYMBIAN32__WSD__)
1.36 +#include "libstdcppwsd.h"
1.37 +#endif
1.38 +
1.39 +_STLP_BEGIN_NAMESPACE
1.40 +_STLP_MOVE_TO_PRIV_NAMESPACE
1.41 +
1.42 +// those wrappers are needed to avoid extern "C"
1.43 +
1.44 +static void* _Loc_ctype_create(const char * s, _Locale_name_hint* hint)
1.45 +{ return _Locale_ctype_create(s, hint); }
1.46 +static void* _Loc_numeric_create(const char * s, _Locale_name_hint* hint)
1.47 +{ return _Locale_numeric_create(s, hint); }
1.48 +static void* _Loc_time_create(const char * s, _Locale_name_hint* hint)
1.49 +{ return _Locale_time_create(s, hint); }
1.50 +static void* _Loc_collate_create(const char * s, _Locale_name_hint* hint)
1.51 +{ return _Locale_collate_create(s, hint); }
1.52 +static void* _Loc_monetary_create(const char * s, _Locale_name_hint* hint)
1.53 +{ return _Locale_monetary_create(s, hint); }
1.54 +static void* _Loc_messages_create(const char * s, _Locale_name_hint* hint)
1.55 +{ return _Locale_messages_create(s, hint); }
1.56 +
1.57 +static char const* _Loc_ctype_name(const void* l, char* s)
1.58 +{ return _Locale_ctype_name(l, s); }
1.59 +static char const* _Loc_numeric_name(const void* l, char* s)
1.60 +{ return _Locale_numeric_name(l, s); }
1.61 +static char const* _Loc_time_name(const void* l, char* s)
1.62 +{ return _Locale_time_name(l,s); }
1.63 +static char const* _Loc_collate_name( const void* l, char* s)
1.64 +{ return _Locale_collate_name(l,s); }
1.65 +static char const* _Loc_monetary_name(const void* l, char* s)
1.66 +{ return _Locale_monetary_name(l,s); }
1.67 +static char const* _Loc_messages_name(const void* l, char* s)
1.68 +{ return _Locale_messages_name(l,s); }
1.69 +
1.70 +static const char* _Loc_ctype_default(char* p)
1.71 +{ return _Locale_ctype_default(p); }
1.72 +static const char* _Loc_numeric_default(char * p)
1.73 +{ return _Locale_numeric_default(p); }
1.74 +static const char* _Loc_time_default(char* p)
1.75 +{ return _Locale_time_default(p); }
1.76 +static const char* _Loc_collate_default(char* p)
1.77 +{ return _Locale_collate_default(p); }
1.78 +static const char* _Loc_monetary_default(char* p)
1.79 +{ return _Locale_monetary_default(p); }
1.80 +static const char* _Loc_messages_default(char* p)
1.81 +{ return _Locale_messages_default(p); }
1.82 +
1.83 +static void _Loc_ctype_destroy(void* p) {_Locale_ctype_destroy(p); }
1.84 +static void _Loc_numeric_destroy(void* p) {_Locale_numeric_destroy(p); }
1.85 +static void _Loc_time_destroy(void* p) {_Locale_time_destroy(p);}
1.86 +static void _Loc_collate_destroy(void* p) {_Locale_collate_destroy(p);}
1.87 +static void _Loc_monetary_destroy(void* p) {_Locale_monetary_destroy(p);}
1.88 +static void _Loc_messages_destroy(void* p) {_Locale_messages_destroy(p);}
1.89 +
1.90 +typedef void* (*loc_create_func_t)(const char *, _Locale_name_hint*);
1.91 +typedef char const* (*loc_name_func_t)(const void* l, char* s);
1.92 +typedef void (*loc_destroy_func_t)(void* l);
1.93 +typedef const char* (*loc_default_name_func_t)(char* s);
1.94 +typedef char const* (*loc_extract_name_func_t)(const char*, char*, _Locale_name_hint*);
1.95 +
1.96 +//----------------------------------------------------------------------
1.97 +// Acquire and release low-level category objects. The whole point of
1.98 +// this is so that we don't allocate (say) four different _Locale_ctype
1.99 +// objects for a single locale.
1.100 +
1.101 +// Global hash tables for category objects.
1.102 +typedef hash_map<string, pair<void*, size_t>, hash<string>, equal_to<string> > Category_Map;
1.103 +
1.104 +# if !defined(__SYMBIAN32__WSD__)
1.105 +// Look up a category by name
1.106 +static Category_Map** ctype_hash() {
1.107 + static Category_Map *_S_ctype_hash = 0;
1.108 + return &_S_ctype_hash;
1.109 +}
1.110 +static Category_Map** numeric_hash() {
1.111 + static Category_Map *_S_numeric_hash = 0;
1.112 + return &_S_numeric_hash;
1.113 +}
1.114 +static Category_Map** time_hash() {
1.115 + static Category_Map *_S_time_hash = 0;
1.116 + return &_S_time_hash;
1.117 +}
1.118 +static Category_Map** collate_hash() {
1.119 + static Category_Map *_S_collate_hash = 0;
1.120 + return &_S_collate_hash;
1.121 +}
1.122 +static Category_Map** monetary_hash() {
1.123 + static Category_Map *_S_monetary_hash = 0;
1.124 + return &_S_monetary_hash;
1.125 +}
1.126 +static Category_Map** messages_hash() {
1.127 + static Category_Map *_S_messages_hash;
1.128 + return &_S_messages_hash;
1.129 +}
1.130 +#else
1.131 +// Look up a category by name
1.132 +static Category_Map** ctype_hash() {
1.133 + return &get_libcpp_wsd()._S_ctype_hash;
1.134 +}
1.135 +static Category_Map** numeric_hash() {
1.136 + return &get_libcpp_wsd()._S_numeric_hash;
1.137 +}
1.138 +static Category_Map** time_hash() {
1.139 + return &get_libcpp_wsd()._S_time_hash;
1.140 +}
1.141 +static Category_Map** collate_hash() {
1.142 + return &get_libcpp_wsd()._S_collate_hash;
1.143 +}
1.144 +static Category_Map** monetary_hash() {
1.145 + return &get_libcpp_wsd()._S_monetary_hash;
1.146 +}
1.147 +static Category_Map** messages_hash() {
1.148 + return &get_libcpp_wsd()._S_messages_hash;
1.149 +}
1.150 +
1.151 +void Category_Map_Init()
1.152 +{
1.153 + get_libcpp_wsd()._S_ctype_hash = 0;
1.154 + get_libcpp_wsd()._S_numeric_hash = 0;
1.155 + get_libcpp_wsd()._S_time_hash = 0;
1.156 + get_libcpp_wsd()._S_collate_hash = 0;
1.157 + get_libcpp_wsd()._S_monetary_hash = 0;
1.158 + get_libcpp_wsd()._S_messages_hash = 0;
1.159 +}
1.160 +# endif
1.161 +
1.162 +
1.163 +// We have a single lock for all of the hash tables. We may wish to
1.164 +// replace it with six different locks.
1.165 +/* REFERENCED */
1.166 +# if !defined(__SYMBIAN32__WSD__)
1.167 +static _STLP_STATIC_MUTEX __category_hash_lock _STLP_MUTEX_INITIALIZER;
1.168 +#else
1.169 +
1.170 +#define __category_hash_lock get_locale_catalog_category_hash_lock()
1.171 +
1.172 +void locale_catalog_category_hash_lock_init()
1.173 +{
1.174 + __category_hash_lock._M_lock.iState = _ENeedsNormalInit;
1.175 + __category_hash_lock._M_lock.iPtr = 0;
1.176 + __category_hash_lock._M_lock.iReentry = 0;
1.177 +}
1.178 +# endif
1.179 +
1.180 +
1.181 +static void*
1.182 +__acquire_category(const char* name, _Locale_name_hint* hint,
1.183 + loc_extract_name_func_t extract_name,
1.184 + loc_create_func_t create_obj, loc_default_name_func_t default_obj,
1.185 + Category_Map ** M) {
1.186 +#if !defined (__BORLANDC__) || (__BORLANDC__ >= 0x564)
1.187 + typedef Category_Map::iterator Category_iterator;
1.188 + pair<Category_iterator, bool> result;
1.189 +#else
1.190 + pair<Category_Map::iterator, bool> result;
1.191 +#endif
1.192 +
1.193 + // Find what name to look for. Be careful if user requests the default.
1.194 + const char *cname;
1.195 + char buf[_Locale_MAX_SIMPLE_NAME];
1.196 + if (name == 0 || name[0] == 0) {
1.197 + cname = default_obj(buf);
1.198 + if (cname == 0 || cname[0] == 0)
1.199 + cname = "C";
1.200 + }
1.201 + else {
1.202 + cname = extract_name(name, buf, hint);
1.203 + if (cname == 0) {
1.204 + return 0;
1.205 + }
1.206 + }
1.207 +
1.208 + Category_Map::value_type __e(cname, pair<void*,size_t>((void*)0,size_t(0)));
1.209 +
1.210 + _STLP_auto_lock sentry(__category_hash_lock);
1.211 +
1.212 + if (!*M)
1.213 + *M = new Category_Map();
1.214 +
1.215 +#if defined(__SC__) //*TY 06/01/2000 - added workaround for SCpp
1.216 + if(!*M) delete *M; //*TY 06/01/2000 - it forgets to generate dtor for Category_Map class. This fake code forces to generate one.
1.217 +#endif //*TY 06/01/2000 -
1.218 +
1.219 + // Look for an existing entry with that name.
1.220 + result = (*M)->insert_noresize(__e);
1.221 +
1.222 + // There was no entry in the map already. Create the category.
1.223 + if (result.second)
1.224 + (*result.first).second.first = create_obj(cname, hint);
1.225 +
1.226 + // Increment the reference count.
1.227 + ++((*result.first).second.second);
1.228 +
1.229 + return (*result.first).second.first;
1.230 +}
1.231 +
1.232 +static void
1.233 +__release_category(void* cat,
1.234 + loc_destroy_func_t destroy_fun,
1.235 + loc_name_func_t get_name,
1.236 + Category_Map** M) {
1.237 + Category_Map *pM = *M;
1.238 +
1.239 + if (cat && pM) {
1.240 + // Find the name of the category object.
1.241 + char buf[_Locale_MAX_SIMPLE_NAME + 1];
1.242 + char const* name = get_name(cat, buf);
1.243 +
1.244 + if (name != 0) {
1.245 + _STLP_auto_lock sentry(__category_hash_lock);
1.246 + Category_Map::iterator it = pM->find(name);
1.247 + if (it != pM->end()) {
1.248 + // Decrement the ref count. If it goes to zero, delete this category
1.249 + // from the map.
1.250 + if (--((*it).second.second) == 0) {
1.251 + void* cat1 = (*it).second.first;
1.252 + destroy_fun(cat1);
1.253 + pM->erase(it);
1.254 +#if defined (_STLP_LEAKS_PEDANTIC)
1.255 + if (pM->empty()) {
1.256 + delete pM;
1.257 + *M = 0;
1.258 + }
1.259 +#endif /* _STLP_LEAKS_PEDANTIC */
1.260 + }
1.261 + }
1.262 + }
1.263 + }
1.264 +}
1.265 +
1.266 +_Locale_ctype* _STLP_CALL __acquire_ctype(const char* name, _Locale_name_hint* hint) {
1.267 + return __REINTERPRET_CAST(_Locale_ctype*, __acquire_category(name, hint,
1.268 + _Locale_extract_ctype_name, _Loc_ctype_create, _Loc_ctype_default,
1.269 + ctype_hash()));
1.270 +}
1.271 +_Locale_numeric* _STLP_CALL __acquire_numeric(const char* name, _Locale_name_hint* hint) {
1.272 + return __REINTERPRET_CAST(_Locale_numeric*, __acquire_category(name, hint,
1.273 + _Locale_extract_numeric_name, _Loc_numeric_create, _Loc_numeric_default,
1.274 + numeric_hash()));
1.275 +}
1.276 +_STLP_DECLSPEC _Locale_time* _STLP_CALL __acquire_time(const char* name, _Locale_name_hint* hint) {
1.277 + return __REINTERPRET_CAST(_Locale_time*, __acquire_category(name, hint,
1.278 + _Locale_extract_time_name, _Loc_time_create, _Loc_time_default,
1.279 + time_hash()));
1.280 +}
1.281 +_Locale_collate* _STLP_CALL __acquire_collate(const char* name, _Locale_name_hint* hint) {
1.282 + return __REINTERPRET_CAST(_Locale_collate*, __acquire_category(name, hint,
1.283 + _Locale_extract_collate_name, _Loc_collate_create, _Loc_collate_default,
1.284 + collate_hash()));
1.285 +}
1.286 +_Locale_monetary* _STLP_CALL __acquire_monetary(const char* name, _Locale_name_hint* hint) {
1.287 + return __REINTERPRET_CAST(_Locale_monetary*, __acquire_category(name, hint,
1.288 + _Locale_extract_monetary_name, _Loc_monetary_create, _Loc_monetary_default,
1.289 + monetary_hash()));
1.290 +}
1.291 +_Locale_messages* _STLP_CALL __acquire_messages(const char* name, _Locale_name_hint* hint) {
1.292 + return __REINTERPRET_CAST(_Locale_messages*, __acquire_category(name, hint,
1.293 + _Locale_extract_messages_name, _Loc_messages_create, _Loc_messages_default,
1.294 + messages_hash()));
1.295 +}
1.296 +
1.297 +void _STLP_CALL __release_ctype(_Locale_ctype* cat)
1.298 +{ __release_category(cat, _Loc_ctype_destroy, _Loc_ctype_name, ctype_hash()); }
1.299 +void _STLP_CALL __release_numeric(_Locale_numeric* cat)
1.300 +{ __release_category(cat, _Loc_numeric_destroy, _Loc_numeric_name, numeric_hash()); }
1.301 +_STLP_DECLSPEC void _STLP_CALL __release_time(_Locale_time* cat)
1.302 +{ __release_category(cat, _Loc_time_destroy, _Loc_time_name, time_hash()); }
1.303 +void _STLP_CALL __release_collate(_Locale_collate* cat)
1.304 +{ __release_category(cat, _Loc_collate_destroy, _Loc_collate_name, collate_hash()); }
1.305 +void _STLP_CALL __release_monetary(_Locale_monetary* cat)
1.306 +{ __release_category(cat, _Loc_monetary_destroy, _Loc_monetary_name, monetary_hash()); }
1.307 +void _STLP_CALL __release_messages(_Locale_messages* cat)
1.308 +{ __release_category(cat, _Loc_messages_destroy, _Loc_messages_name, messages_hash()); }
1.309 +
1.310 +_STLP_MOVE_TO_STD_NAMESPACE
1.311 +_STLP_END_NAMESPACE