1 | |
2 | |
3 | |
4 | |
5 | |
6 | |
7 | |
8 | |
9 | |
10 | |
11 | |
12 | |
13 | |
14 | |
15 | |
16 | |
17 | |
18 | # include "stlport_prefix.h" |
19 | |
20 | #include "locale_impl.h" |
21 | #include <locale> |
22 | #include <typeinfo> |
23 | #include <stdexcept> |
24 | #include "c_locale.h" |
25 | #include "aligned_buffer.h" |
26 | |
27 | |
28 | #include "locale_impl.h" |
29 | #include <stl/_codecvt.h> |
30 | #include <stl/_collate.h> |
31 | #include <stl/_ctype.h> |
32 | #include <stl/_monetary.h> |
33 | #include "message_facets.h" |
34 | |
35 | _STLP_BEGIN_NAMESPACEnamespace _STL { |
36 | |
37 | _Locale_impl::_Locale_impl(const char* s) : name(s) {} |
38 | _Locale_impl::~_Locale_impl() {} |
39 | void _Locale_impl::incr() {} |
40 | void _Locale_impl::decr() {} |
41 | |
42 | |
43 | void _STLP_CALL |
44 | _Locale_impl::_M_throw_bad_cast() |
45 | { |
46 | _STLP_THROW(bad_cast())throw bad_cast(); |
47 | } |
48 | |
49 | static void |
50 | _Stl_loc_assign_ids() { |
51 | |
52 | |
53 | |
54 | |
55 | |
56 | money_get<char, istreambuf_iterator<char, char_traits<char> > >::id._M_index = 8; |
57 | money_get<char, const char*>::id._M_index = 9; |
58 | money_put<char, ostreambuf_iterator<char, char_traits<char> > >::id._M_index = 10; |
59 | money_put<char, char*>::id._M_index = 11; |
60 | |
61 | num_get<char, istreambuf_iterator<char, char_traits<char> > >::id._M_index = 12; |
62 | num_get<char, const char*>::id._M_index = 13; |
63 | num_put<char, ostreambuf_iterator<char, char_traits<char> > >::id._M_index = 14; |
64 | num_put<char, char*>::id._M_index = 15; |
65 | time_get<char, istreambuf_iterator<char, char_traits<char> > >::id._M_index = 16; |
66 | time_get<char, const char*>::id._M_index = 17; |
67 | time_put<char, ostreambuf_iterator<char, char_traits<char> > >::id._M_index = 18; |
68 | time_put<char, char*>::id._M_index = 19; |
69 | |
70 | # ifndef _STLP_NO_WCHAR_T |
71 | |
72 | money_get<wchar_t, istreambuf_iterator<wchar_t, char_traits<wchar_t> > >::id._M_index = 27; |
73 | money_get<wchar_t, const wchar_t*>::id._M_index = 28; |
74 | money_put<wchar_t, ostreambuf_iterator<wchar_t, char_traits<wchar_t> > >::id._M_index = 29; |
75 | money_put<wchar_t, wchar_t*>::id._M_index = 30; |
76 | |
77 | num_get<wchar_t, istreambuf_iterator<wchar_t, char_traits<wchar_t> > >::id._M_index = 31; |
78 | num_get<wchar_t, const wchar_t*>::id._M_index = 32; |
79 | num_put<wchar_t, ostreambuf_iterator<wchar_t, char_traits<wchar_t> > > ::id._M_index = 33; |
80 | num_put<wchar_t, wchar_t*>::id._M_index = 34; |
81 | time_get<wchar_t, istreambuf_iterator<wchar_t, char_traits<wchar_t> > >::id._M_index = 35; |
82 | time_get<wchar_t, const wchar_t*>::id._M_index = 36; |
83 | time_put<wchar_t, ostreambuf_iterator<wchar_t, char_traits<wchar_t> > >::id._M_index = 37; |
84 | time_put<wchar_t, wchar_t*>::id._M_index = 38; |
85 | |
86 | # endif |
87 | |
88 | |
89 | } |
90 | |
91 | static _Stl_aligned_buffer<_Locale_impl> _S_classic_locale; |
92 | |
93 | static _Stl_aligned_buffer<collate<char> > _S_collate_char; |
94 | static _Stl_aligned_buffer<ctype<char> > _S_ctype_char; |
95 | static _Stl_aligned_buffer<codecvt<char, char, mbstate_t> > _S_codecvt_char; |
96 | static _Stl_aligned_buffer<moneypunct<char, true> > _S_moneypunct_true_char; |
97 | static _Stl_aligned_buffer<moneypunct<char, false> > _S_moneypunct_false_char; |
98 | static _Stl_aligned_buffer<numpunct<char> > _S_numpunct_char; |
99 | static _Stl_aligned_buffer<messages<char> > _S_messages_char; |
100 | |
101 | static _Stl_aligned_buffer<money_get<char, istreambuf_iterator<char, char_traits<char> > > > _S_money_get_char; |
102 | static _Stl_aligned_buffer<money_put<char, ostreambuf_iterator<char, char_traits<char> > > > _S_money_put_char; |
103 | static _Stl_aligned_buffer<num_get<char, istreambuf_iterator<char, char_traits<char> > > > _S_num_get_char; |
104 | static _Stl_aligned_buffer<num_put<char, ostreambuf_iterator<char, char_traits<char> > > > _S_num_put_char; |
105 | static _Stl_aligned_buffer<time_get<char, istreambuf_iterator<char, char_traits<char> > > > _S_time_get_char; |
106 | static _Stl_aligned_buffer<time_put<char, ostreambuf_iterator<char, char_traits<char> > > > _S_time_put_char; |
107 | |
108 | # ifndef _STLP_NO_WCHAR_T |
109 | static _Stl_aligned_buffer<collate<wchar_t> > _S_collate_wchar; |
110 | static _Stl_aligned_buffer<ctype<wchar_t> > _S_ctype_wchar; |
111 | static _Stl_aligned_buffer<codecvt<wchar_t, char, mbstate_t> > _S_codecvt_wchar; |
112 | static _Stl_aligned_buffer<moneypunct<wchar_t, true> > _S_moneypunct_true_wchar; |
113 | static _Stl_aligned_buffer<moneypunct<wchar_t, false> > _S_moneypunct_false_wchar; |
114 | static _Stl_aligned_buffer<numpunct<wchar_t> > _S_numpunct_wchar; |
115 | static _Stl_aligned_buffer<messages<wchar_t> > _S_messages_wchar; |
116 | |
117 | static _Stl_aligned_buffer<money_get<wchar_t, istreambuf_iterator<wchar_t, char_traits<wchar_t> > > > _S_money_get_wchar; |
118 | static _Stl_aligned_buffer<money_put<wchar_t, ostreambuf_iterator<wchar_t, char_traits<wchar_t> > > > _S_money_put_wchar; |
119 | static _Stl_aligned_buffer<num_get<wchar_t, istreambuf_iterator<wchar_t, char_traits<wchar_t> > > > _S_num_get_wchar; |
120 | static _Stl_aligned_buffer<num_put<wchar_t, ostreambuf_iterator<wchar_t, char_traits<wchar_t> > > > _S_num_put_wchar; |
121 | static _Stl_aligned_buffer<time_get<wchar_t, istreambuf_iterator<wchar_t, char_traits<wchar_t> > > > _S_time_get_wchar; |
122 | static _Stl_aligned_buffer<time_put<wchar_t, ostreambuf_iterator<wchar_t, char_traits<wchar_t> > > > _S_time_put_wchar; |
123 | |
124 | # endif |
125 | |
126 | |
127 | |
128 | static locale::facet* _S_classic_facets[] = { |
129 | (locale::facet*)0, |
130 | (locale::facet*)&_S_collate_char, |
131 | (locale::facet*)&_S_ctype_char, |
132 | (locale::facet*)&_S_codecvt_char, |
133 | (locale::facet*)&_S_moneypunct_true_char, |
134 | (locale::facet*)&_S_moneypunct_false_char, |
135 | (locale::facet*)&_S_numpunct_char, |
136 | (locale::facet*)&_S_messages_char, |
137 | |
138 | (locale::facet*)&_S_money_get_char, |
139 | (locale::facet*)0, |
140 | (locale::facet*)&_S_money_put_char, |
141 | (locale::facet*)0, |
142 | |
143 | (locale::facet*)&_S_num_get_char, |
144 | (locale::facet*)0, |
145 | (locale::facet*)&_S_num_put_char, |
146 | (locale::facet*)0, |
147 | (locale::facet*)&_S_time_get_char, |
148 | (locale::facet*)0, |
149 | (locale::facet*)&_S_time_put_char, |
150 | (locale::facet*)0, |
151 | # ifndef _STLP_NO_WCHAR_T |
152 | (locale::facet*)&_S_collate_wchar, |
153 | (locale::facet*)&_S_ctype_wchar, |
154 | (locale::facet*)&_S_codecvt_wchar, |
155 | (locale::facet*)&_S_moneypunct_true_wchar, |
156 | (locale::facet*)&_S_moneypunct_false_wchar, |
157 | (locale::facet*)&_S_numpunct_wchar, |
158 | (locale::facet*)&_S_messages_wchar, |
159 | |
160 | (locale::facet*)&_S_money_get_wchar, |
161 | (locale::facet*)0, |
162 | (locale::facet*)&_S_money_put_wchar, |
163 | (locale::facet*)0, |
164 | |
165 | (locale::facet*)&_S_num_get_wchar, |
166 | (locale::facet*)0, |
167 | (locale::facet*)&_S_num_put_wchar, |
168 | (locale::facet*)0, |
169 | (locale::facet*)&_S_time_get_wchar, |
170 | (locale::facet*)0, |
171 | (locale::facet*)&_S_time_put_wchar, |
172 | (locale::facet*)0, |
173 | # endif |
174 | 0 |
175 | }; |
176 | |
177 | _Locale_impl* |
178 | _Locale_impl::make_classic_locale() { |
179 | |
180 | _Locale_impl* classic = (_Locale_impl*) &_S_classic_locale; |
181 | |
182 | new (classic) _Locale_impl("C"); |
183 | |
184 | |
185 | new(&_S_ctype_char) ctype<char>(0, false, 1); |
186 | |
187 | new(&_S_collate_char) collate<char>(1); |
188 | new(&_S_codecvt_char) codecvt<char, char, mbstate_t>(1); |
189 | |
190 | new (&_S_moneypunct_true_char) moneypunct<char, true>(1); |
191 | new (&_S_moneypunct_false_char) moneypunct<char, false>(1); |
192 | new (&_S_money_get_char) money_get<char, istreambuf_iterator<char, char_traits<char> > >(1); |
193 | new (&_S_money_put_char) money_put<char, ostreambuf_iterator<char, char_traits<char> > >(1); |
194 | |
195 | new(&_S_numpunct_char) numpunct<char>(1); |
196 | new (&_S_num_get_char) num_get<char, istreambuf_iterator<char, char_traits<char> > >(1); |
197 | new (&_S_num_put_char) num_put<char, ostreambuf_iterator<char, char_traits<char> > >(1); |
198 | new (&_S_time_get_char) time_get<char, istreambuf_iterator<char, char_traits<char> > >(1); |
199 | new (&_S_time_put_char) time_put<char, ostreambuf_iterator<char, char_traits<char> > >(1); |
200 | |
201 | |
202 | |
203 | # ifndef _STLP_NO_WCHAR_T |
204 | |
205 | new(&_S_ctype_wchar) ctype<wchar_t>(1); |
206 | |
207 | new(&_S_collate_wchar) collate<wchar_t>(1); |
208 | new(&_S_codecvt_wchar) codecvt<wchar_t, char, mbstate_t>(1); |
209 | |
210 | new (&_S_moneypunct_true_wchar) moneypunct<wchar_t, true>(1); |
211 | new (&_S_moneypunct_false_wchar) moneypunct<wchar_t, false>(1); |
212 | new (&_S_money_get_wchar) money_get<wchar_t, istreambuf_iterator<wchar_t, char_traits<wchar_t> > >(1); |
213 | new (&_S_money_put_wchar) money_put<wchar_t, ostreambuf_iterator<wchar_t, char_traits<wchar_t> > >(1); |
214 | |
215 | new(&_S_numpunct_wchar) numpunct<wchar_t>(1); |
216 | new (&_S_num_get_wchar) num_get<wchar_t, istreambuf_iterator<wchar_t, char_traits<wchar_t> > >(1); |
217 | new (&_S_num_put_wchar) num_put<wchar_t, ostreambuf_iterator<wchar_t, char_traits<wchar_t> > >(1); |
218 | new (&_S_time_get_wchar) time_get<wchar_t, istreambuf_iterator<wchar_t, char_traits<wchar_t> > >(1); |
219 | new (&_S_time_put_wchar) time_put<wchar_t, ostreambuf_iterator<wchar_t, char_traits<wchar_t> > >(1); |
220 | |
221 | # endif |
222 | |
223 | classic->facets = _S_classic_facets; |
224 | classic->_M_size = locale::id::_S_max; |
225 | return classic; |
226 | } |
227 | |
228 | |
229 | |
230 | |
231 | |
232 | size_t locale::id::_S_max = 39; |
233 | |
234 | _STLP_STATIC_MEMBER_DECLSPEC locale::id collate<char>::id = { 1 }; |
235 | _STLP_STATIC_MEMBER_DECLSPEC locale::id ctype<char>::id = { 2 }; |
236 | |
237 | # ifndef _STLP_NO_MBSTATE_T |
238 | _STLP_STATIC_MEMBER_DECLSPEC locale::id codecvt<char, char, mbstate_t>::id = { 3 }; |
239 | # ifndef _STLP_NO_WCHAR_T |
240 | _STLP_STATIC_MEMBER_DECLSPEC locale::id codecvt<wchar_t, char, mbstate_t>::id = { 22 }; |
241 | # endif |
242 | # endif |
243 | |
244 | _STLP_STATIC_MEMBER_DECLSPEC locale::id moneypunct<char, true>::id = { 4 }; |
245 | _STLP_STATIC_MEMBER_DECLSPEC locale::id moneypunct<char, false>::id = { 5 }; |
246 | _STLP_STATIC_MEMBER_DECLSPEC locale::id numpunct<char>::id = { 6 } ; |
247 | _STLP_STATIC_MEMBER_DECLSPEC locale::id messages<char>::id = { 7 }; |
248 | |
249 | # ifndef _STLP_NO_WCHAR_T |
250 | _STLP_STATIC_MEMBER_DECLSPEC locale::id collate<wchar_t>::id = { 20 }; |
251 | _STLP_STATIC_MEMBER_DECLSPEC locale::id ctype<wchar_t>::id = { 21 }; |
252 | |
253 | _STLP_STATIC_MEMBER_DECLSPEC locale::id moneypunct<wchar_t, true>::id = { 23 } ; |
254 | _STLP_STATIC_MEMBER_DECLSPEC locale::id moneypunct<wchar_t, false>::id = { 24 } ; |
255 | |
256 | _STLP_STATIC_MEMBER_DECLSPEC locale::id numpunct<wchar_t>::id = { 25 }; |
257 | _STLP_STATIC_MEMBER_DECLSPEC locale::id messages<wchar_t>::id = { 26 }; |
258 | # endif |
259 | |
260 | |
261 | |
262 | |
263 | |
264 | locale::facet::~facet() {} |
265 | |
266 | # if ! defined ( _STLP_MEMBER_TEMPLATES1 ) || defined (_STLP_INLINE_MEMBER_TEMPLATES) |
267 | |
268 | bool locale::operator()(const string& __x, |
269 | const string& __y) const { |
270 | return __locale_do_operator_call(this, __x, __y); |
271 | } |
272 | |
273 | # ifndef _STLP_NO_WCHAR_T |
274 | bool locale::operator()(const wstring& __x, |
275 | const wstring& __y) const { |
276 | return __locale_do_operator_call(this, __x, __y); |
277 | } |
278 | # endif |
279 | # endif |
280 | |
281 | |
282 | _Locale_impl* _Stl_loc_global_impl = 0; |
283 | locale _Stl_loc_classic_locale((_Locale_impl*) &_S_classic_locale); |
284 | _STLP_STATIC_MUTEX_STLP_mutex_base _Stl_loc_global_locale_lock _STLP_MUTEX_INITIALIZER= { { { 0, 0, 0, 0, 0, { 0 } } } }; |
285 | |
286 | |
287 | |
288 | |
289 | |
290 | void _STLP_CALL |
291 | locale::_M_throw_runtime_error(const char* name) |
292 | { |
293 | char buf[256]; |
294 | |
295 | if (name) { |
| 1 | Assuming 'name' is non-null | |
|
| |
296 | const char* prefix = "bad locale name: "; |
297 | strcpy(buf, prefix); |
298 | strncat(buf, name, 256 - strlen(prefix)); |
| 3 | | Size argument is greater than the free space in the destination buffer |
|
299 | buf[255] = '\0'; |
300 | } |
301 | else { |
302 | strcpy(buf, "locale error"); |
303 | } |
304 | _STLP_THROW(runtime_error(buf))throw runtime_error(buf); |
305 | } |
306 | |
307 | #if !( defined (__BORLANDC__) && defined(_RTLDLL)) |
308 | |
309 | long ios_base::_Loc_init::_S_count = 0; |
310 | |
311 | ios_base::_Loc_init::_Loc_init() { |
312 | if (_S_count++ == 0) |
313 | locale::_S_initialize(); |
314 | } |
315 | |
316 | ios_base::_Loc_init::~_Loc_init() { |
317 | if (--_S_count == 0) |
318 | locale::_S_uninitialize(); |
319 | } |
320 | |
321 | #endif /* _RTLDLL */ |
322 | |
323 | |
324 | |
325 | |
326 | void _STLP_CALL |
327 | locale::_S_initialize() |
328 | { |
329 | _Stl_loc_assign_ids(); |
330 | _Stl_loc_global_impl = _Locale_impl::make_classic_locale(); |
331 | } |
332 | |
333 | |
334 | |
335 | void _STLP_CALL |
336 | locale::_S_uninitialize() |
337 | { |
338 | _Stl_loc_global_impl->decr(); |
339 | } |
340 | |
341 | |
342 | |
343 | locale::locale() : _M_impl(0) { |
344 | _M_impl = _S_copy_impl(_Stl_loc_global_impl); |
345 | } |
346 | |
347 | locale::locale(_Locale_impl* impl) : _M_impl(impl) |
348 | {} |
349 | |
350 | |
351 | locale::locale(const locale& L) _STLP_NOTHROW |
352 | : _M_impl(0) |
353 | { |
354 | _M_impl = _S_copy_impl(L._M_impl); |
355 | } |
356 | |
357 | |
358 | locale::~locale() _STLP_NOTHROW |
359 | { |
360 | _M_impl->decr(); |
361 | } |
362 | |
363 | |
364 | |
365 | const locale& locale::operator=(const locale& L) _STLP_NOTHROW |
366 | { |
367 | if (this->_M_impl != L._M_impl) { |
368 | this->_M_impl->decr(); |
369 | this->_M_impl = _S_copy_impl(L._M_impl); |
370 | } |
371 | return *this; |
372 | } |
373 | |
374 | locale::facet* locale::_M_get_facet(const locale::id& n) const |
375 | { |
376 | return n._M_index < _M_impl->size() |
377 | ? (locale::facet*)_M_impl->facets[n._M_index] |
378 | : (locale::facet*) 0; |
379 | } |
380 | |
381 | locale::facet* locale::_M_use_facet(const locale::id& n) const |
382 | { |
383 | locale::facet* f = (n._M_index < _M_impl->size() |
384 | ? (locale::facet*)_M_impl->facets[n._M_index] |
385 | : (locale::facet*) 0); |
386 | if (!f) |
387 | _M_impl->_M_throw_bad_cast(); |
388 | return f; |
389 | } |
390 | |
391 | string locale::name() const { |
392 | return _M_impl->name; |
393 | } |
394 | |
395 | static string _Nameless("*"); |
396 | |
397 | |
398 | bool locale::operator==(const locale& L) const { |
399 | |
400 | return this->_M_impl == L._M_impl || |
401 | (this->name() == L.name() && this->name() != _Nameless); |
402 | } |
403 | |
404 | bool locale::operator!=(const locale& L) const { |
405 | return !(*this == L); |
406 | } |
407 | |
408 | |
409 | const locale& _STLP_CALL |
410 | locale::classic() { |
411 | return _Stl_loc_classic_locale; |
412 | } |
413 | |
414 | locale _STLP_CALL |
415 | locale::global(const locale& L) |
416 | { |
417 | locale old; |
418 | |
419 | L._M_impl->incr(); |
420 | { |
421 | _STLP_auto_lock lock(_Stl_loc_global_locale_lock); |
422 | _Stl_loc_global_impl->decr(); |
423 | _Stl_loc_global_impl = L._M_impl; |
424 | } |
425 | |
426 | |
427 | if (L.name() != _Nameless) |
428 | setlocale(LC_ALL__LC_ALL, L.name().c_str()); |
429 | |
430 | return old; |
431 | } |
432 | |
433 | |
434 | |
435 | |
436 | # if !defined (_STLP_STATIC_CONST_INIT_BUG) && ! defined (_STLP_USE_DECLSPEC) |
437 | |
438 | const locale::category locale::none; |
439 | const locale::category locale::collate; |
440 | const locale::category locale::ctype; |
441 | const locale::category locale::monetary; |
442 | const locale::category locale::numeric; |
443 | const locale::category locale::time; |
444 | const locale::category locale::messages; |
445 | const locale::category locale::all; |
446 | |
447 | # endif |
448 | |
449 | _STLP_END_NAMESPACE} |
450 | |
451 | |
452 | |
453 | |
454 | |
455 | |
456 | # if 0 |
457 | # include "ctype.cpp" |
458 | # include "collate.cpp" |
459 | # include "codecvt.cpp" |
460 | |
461 | # include "num_put_float.cpp" |
462 | # include "num_put.cpp" |
463 | # include "numpunct.cpp" |
464 | # include "num_get.cpp" |
465 | # include "num_get_float.cpp" |
466 | |
467 | # include "monetary.cpp" |
468 | # include "time_facets.cpp" |
469 | # include "messages.cpp" |
470 | # endif |
471 | |