]> git.ipfire.org Git - thirdparty/gcc.git/blob - libstdc++-v3/include/bits/locale_facets.h
char_traits.h: Remove generic definitions.
[thirdparty/gcc.git] / libstdc++-v3 / include / bits / locale_facets.h
1 // Locale support -*- C++ -*-
2
3 // Copyright (C) 1997, 1998, 1999, 2000, 2001, 2002
4 // Free Software Foundation, Inc.
5 //
6 // This file is part of the GNU ISO C++ Library. This library is free
7 // software; you can redistribute it and/or modify it under the
8 // terms of the GNU General Public License as published by the
9 // Free Software Foundation; either version 2, or (at your option)
10 // any later version.
11
12 // This library is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 // GNU General Public License for more details.
16
17 // You should have received a copy of the GNU General Public License along
18 // with this library; see the file COPYING. If not, write to the Free
19 // Software Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
20 // USA.
21
22 // As a special exception, you may use this file as part of a free software
23 // library without restriction. Specifically, if other files instantiate
24 // templates or use macros or inline functions from this file, or you compile
25 // this file and link it with other files to produce an executable, this
26 // file does not by itself cause the resulting executable to be covered by
27 // the GNU General Public License. This exception does not however
28 // invalidate any other reasons why the executable file might be covered by
29 // the GNU General Public License.
30
31 //
32 // ISO C++ 14882: 22.1 Locales
33 //
34
35 /** @file locale_facets.h
36 * This is an internal header file, included by other library headers.
37 * You should not attempt to use it directly.
38 */
39
40 #ifndef _CPP_BITS_LOCFACETS_H
41 #define _CPP_BITS_LOCFACETS_H 1
42
43 #pragma GCC system_header
44
45 #include <ctime> // For struct tm
46 #include <cwctype> // For wctype_t
47 #include <ios> // For ios_base
48
49 namespace std
50 {
51 // NB: Don't instantiate required wchar_t facets if no wchar_t support.
52 #ifdef _GLIBCPP_USE_WCHAR_T
53 # define _GLIBCPP_NUM_FACETS 28
54 #else
55 # define _GLIBCPP_NUM_FACETS 14
56 #endif
57
58 template<typename _CharT, typename _Traits>
59 struct __pad;
60
61 // 22.2.1.1 Template class ctype
62 // Include host and configuration specific ctype enums for ctype_base.
63 #include <bits/ctype_base.h>
64
65 // Common base for ctype<_CharT>.
66 template<typename _CharT>
67 class __ctype_abstract_base : public locale::facet, public ctype_base
68 {
69 public:
70 // Types:
71 typedef _CharT char_type;
72
73 bool
74 is(mask __m, char_type __c) const
75 { return this->do_is(__m, __c); }
76
77 const char_type*
78 is(const char_type *__lo, const char_type *__hi, mask *__vec) const
79 { return this->do_is(__lo, __hi, __vec); }
80
81 const char_type*
82 scan_is(mask __m, const char_type* __lo, const char_type* __hi) const
83 { return this->do_scan_is(__m, __lo, __hi); }
84
85 const char_type*
86 scan_not(mask __m, const char_type* __lo, const char_type* __hi) const
87 { return this->do_scan_not(__m, __lo, __hi); }
88
89 char_type
90 toupper(char_type __c) const
91 { return this->do_toupper(__c); }
92
93 const char_type*
94 toupper(char_type *__lo, const char_type* __hi) const
95 { return this->do_toupper(__lo, __hi); }
96
97 char_type
98 tolower(char_type __c) const
99 { return this->do_tolower(__c); }
100
101 const char_type*
102 tolower(char_type* __lo, const char_type* __hi) const
103 { return this->do_tolower(__lo, __hi); }
104
105 char_type
106 widen(char __c) const
107 { return this->do_widen(__c); }
108
109 const char*
110 widen(const char* __lo, const char* __hi, char_type* __to) const
111 { return this->do_widen(__lo, __hi, __to); }
112
113 char
114 narrow(char_type __c, char __dfault) const
115 { return this->do_narrow(__c, __dfault); }
116
117 const char_type*
118 narrow(const char_type* __lo, const char_type* __hi,
119 char __dfault, char *__to) const
120 { return this->do_narrow(__lo, __hi, __dfault, __to); }
121
122 protected:
123 explicit
124 __ctype_abstract_base(size_t __refs = 0): locale::facet(__refs) { }
125
126 virtual
127 ~__ctype_abstract_base() { }
128
129 virtual bool
130 do_is(mask __m, char_type __c) const = 0;
131
132 virtual const char_type*
133 do_is(const char_type* __lo, const char_type* __hi,
134 mask* __vec) const = 0;
135
136 virtual const char_type*
137 do_scan_is(mask __m, const char_type* __lo,
138 const char_type* __hi) const = 0;
139
140 virtual const char_type*
141 do_scan_not(mask __m, const char_type* __lo,
142 const char_type* __hi) const = 0;
143
144 virtual char_type
145 do_toupper(char_type) const = 0;
146
147 virtual const char_type*
148 do_toupper(char_type* __lo, const char_type* __hi) const = 0;
149
150 virtual char_type
151 do_tolower(char_type) const = 0;
152
153 virtual const char_type*
154 do_tolower(char_type* __lo, const char_type* __hi) const = 0;
155
156 virtual char_type
157 do_widen(char) const = 0;
158
159 virtual const char*
160 do_widen(const char* __lo, const char* __hi,
161 char_type* __dest) const = 0;
162
163 virtual char
164 do_narrow(char_type, char __dfault) const = 0;
165
166 virtual const char_type*
167 do_narrow(const char_type* __lo, const char_type* __hi,
168 char __dfault, char* __dest) const = 0;
169 };
170
171 // NB: Generic, mostly useless implementation.
172 template<typename _CharT>
173 class ctype : public __ctype_abstract_base<_CharT>
174 {
175 public:
176 // Types:
177 typedef _CharT char_type;
178 typedef typename ctype::mask mask;
179
180 static locale::id id;
181
182 explicit
183 ctype(size_t __refs = 0) : __ctype_abstract_base<_CharT>(__refs) { }
184
185 protected:
186 virtual
187 ~ctype();
188
189 virtual bool
190 do_is(mask __m, char_type __c) const;
191
192 virtual const char_type*
193 do_is(const char_type* __lo, const char_type* __hi, mask* __vec) const;
194
195 virtual const char_type*
196 do_scan_is(mask __m, const char_type* __lo, const char_type* __hi) const;
197
198 virtual const char_type*
199 do_scan_not(mask __m, const char_type* __lo,
200 const char_type* __hi) const;
201
202 virtual char_type
203 do_toupper(char_type __c) const;
204
205 virtual const char_type*
206 do_toupper(char_type* __lo, const char_type* __hi) const;
207
208 virtual char_type
209 do_tolower(char_type __c) const;
210
211 virtual const char_type*
212 do_tolower(char_type* __lo, const char_type* __hi) const;
213
214 virtual char_type
215 do_widen(char __c) const;
216
217 virtual const char*
218 do_widen(const char* __lo, const char* __hi, char_type* __dest) const;
219
220 virtual char
221 do_narrow(char_type, char __dfault) const;
222
223 virtual const char_type*
224 do_narrow(const char_type* __lo, const char_type* __hi,
225 char __dfault, char* __dest) const;
226 };
227
228 template<typename _CharT>
229 locale::id ctype<_CharT>::id;
230
231 // 22.2.1.3 ctype<char> specialization.
232 template<>
233 class ctype<char> : public __ctype_abstract_base<char>
234 {
235 public:
236 // Types:
237 typedef char char_type;
238
239 protected:
240 // Data Members:
241 __c_locale _M_c_locale_ctype;
242 bool _M_del;
243 __to_type _M_toupper;
244 __to_type _M_tolower;
245 const mask* _M_table;
246
247 public:
248 static locale::id id;
249 static const size_t table_size = 1 + static_cast<unsigned char>(-1);
250
251 explicit
252 ctype(const mask* __table = 0, bool __del = false, size_t __refs = 0);
253
254 explicit
255 ctype(__c_locale __cloc, const mask* __table = 0, bool __del = false,
256 size_t __refs = 0);
257
258 inline bool
259 is(mask __m, char __c) const;
260
261 inline const char*
262 is(const char* __lo, const char* __hi, mask* __vec) const;
263
264 inline const char*
265 scan_is(mask __m, const char* __lo, const char* __hi) const;
266
267 inline const char*
268 scan_not(mask __m, const char* __lo, const char* __hi) const;
269
270 protected:
271 const mask*
272 table() const throw()
273 { return _M_table; }
274
275 static const mask*
276 classic_table() throw();
277
278 virtual
279 ~ctype();
280
281 virtual bool
282 do_is(mask __m, char_type __c) const;
283
284 virtual const char_type*
285 do_is(const char_type* __lo, const char_type* __hi, mask* __vec) const;
286
287 virtual const char_type*
288 do_scan_is(mask __m, const char_type* __lo, const char_type* __hi) const;
289
290 virtual const char_type*
291 do_scan_not(mask __m, const char_type* __lo,
292 const char_type* __hi) const;
293
294 virtual char_type
295 do_toupper(char_type) const;
296
297 virtual const char_type*
298 do_toupper(char_type* __lo, const char_type* __hi) const;
299
300 virtual char_type
301 do_tolower(char_type) const;
302
303 virtual const char_type*
304 do_tolower(char_type* __lo, const char_type* __hi) const;
305
306 virtual char_type
307 do_widen(char) const;
308
309 virtual const char*
310 do_widen(const char* __lo, const char* __hi, char_type* __dest) const;
311
312 virtual char
313 do_narrow(char_type, char __dfault) const;
314
315 virtual const char_type*
316 do_narrow(const char_type* __lo, const char_type* __hi,
317 char __dfault, char* __dest) const;
318 };
319
320 template<>
321 const ctype<char>&
322 use_facet<ctype<char> >(const locale& __loc);
323
324 #ifdef _GLIBCPP_USE_WCHAR_T
325 // 22.2.1.3 ctype<wchar_t> specialization
326 template<>
327 class ctype<wchar_t> : public __ctype_abstract_base<wchar_t>
328 {
329 public:
330 // Types:
331 typedef wchar_t char_type;
332 typedef wctype_t __wmask_type;
333
334 protected:
335 __c_locale _M_c_locale_ctype;
336
337 public:
338 // Data Members:
339 static locale::id id;
340
341 explicit
342 ctype(size_t __refs = 0);
343
344 explicit
345 ctype(__c_locale __cloc, size_t __refs = 0);
346
347 protected:
348 __wmask_type
349 _M_convert_to_wmask(const mask __m) const;
350
351 virtual
352 ~ctype();
353
354 virtual bool
355 do_is(mask __m, char_type __c) const;
356
357 virtual const char_type*
358 do_is(const char_type* __lo, const char_type* __hi, mask* __vec) const;
359
360 virtual const char_type*
361 do_scan_is(mask __m, const char_type* __lo, const char_type* __hi) const;
362
363 virtual const char_type*
364 do_scan_not(mask __m, const char_type* __lo,
365 const char_type* __hi) const;
366
367 virtual char_type
368 do_toupper(char_type) const;
369
370 virtual const char_type*
371 do_toupper(char_type* __lo, const char_type* __hi) const;
372
373 virtual char_type
374 do_tolower(char_type) const;
375
376 virtual const char_type*
377 do_tolower(char_type* __lo, const char_type* __hi) const;
378
379 virtual char_type
380 do_widen(char) const;
381
382 virtual const char*
383 do_widen(const char* __lo, const char* __hi, char_type* __dest) const;
384
385 virtual char
386 do_narrow(char_type, char __dfault) const;
387
388 virtual const char_type*
389 do_narrow(const char_type* __lo, const char_type* __hi,
390 char __dfault, char* __dest) const;
391
392 };
393
394 template<>
395 const ctype<wchar_t>&
396 use_facet<ctype<wchar_t> >(const locale& __loc);
397 #endif //_GLIBCPP_USE_WCHAR_T
398
399 // Include host and configuration specific ctype inlines.
400 #include <bits/ctype_inline.h>
401
402 // 22.2.1.2 Template class ctype_byname
403 template<typename _CharT>
404 class ctype_byname : public ctype<_CharT>
405 {
406 public:
407 typedef _CharT char_type;
408
409 explicit
410 ctype_byname(const char* __s, size_t __refs = 0);
411
412 protected:
413 virtual
414 ~ctype_byname() { };
415 };
416
417 // 22.2.1.4 Class ctype_byname specializations.
418 template<>
419 ctype_byname<char>::ctype_byname(const char*, size_t refs);
420
421 template<>
422 ctype_byname<wchar_t>::ctype_byname(const char*, size_t refs);
423
424 // 22.2.1.5 Template class codecvt
425 #include <bits/codecvt.h>
426
427
428 // 22.2.2 The numeric category.
429 class __num_base
430 {
431 protected:
432 // String literal of acceptable (narrow) input, for num_get.
433 // "0123456789eEabcdfABCDF"
434 static const char _S_atoms[];
435
436 enum
437 {
438 _M_zero,
439 _M_e = _M_zero + 10,
440 _M_E = _M_zero + 11,
441 _M_size = 21 + 1
442 };
443
444 // num_put
445 // Construct and return valid scanf format for floating point types.
446 static bool
447 _S_format_float(const ios_base& __io, char* __fptr, char __mod,
448 streamsize __prec);
449
450 // Construct and return valid scanf format for integer types.
451 static void
452 _S_format_int(const ios_base& __io, char* __fptr, char __mod, char __modl);
453 };
454
455
456 template<typename _CharT>
457 class numpunct : public locale::facet
458 {
459 public:
460 // Types:
461 typedef _CharT char_type;
462 typedef basic_string<_CharT> string_type;
463
464 static locale::id id;
465
466 private:
467 char_type _M_decimal_point;
468 char_type _M_thousands_sep;
469 const char* _M_grouping;
470 const char_type* _M_truename;
471 const char_type* _M_falsename;
472
473 public:
474 explicit
475 numpunct(size_t __refs = 0) : locale::facet(__refs)
476 { _M_initialize_numpunct(); }
477
478 explicit
479 numpunct(__c_locale __cloc, size_t __refs = 0) : locale::facet(__refs)
480 { _M_initialize_numpunct(__cloc); }
481
482 char_type
483 decimal_point() const
484 { return this->do_decimal_point(); }
485
486 char_type
487 thousands_sep() const
488 { return this->do_thousands_sep(); }
489
490 string
491 grouping() const
492 { return this->do_grouping(); }
493
494 string_type
495 truename() const
496 { return this->do_truename(); }
497
498 string_type
499 falsename() const
500 { return this->do_falsename(); }
501
502 protected:
503 virtual
504 ~numpunct();
505
506 virtual char_type
507 do_decimal_point() const
508 { return _M_decimal_point; }
509
510 virtual char_type
511 do_thousands_sep() const
512 { return _M_thousands_sep; }
513
514 virtual string
515 do_grouping() const
516 { return _M_grouping; }
517
518 virtual string_type
519 do_truename() const
520 { return _M_truename; }
521
522 virtual string_type
523 do_falsename() const
524 { return _M_falsename; }
525
526 // For use at construction time only.
527 void
528 _M_initialize_numpunct(__c_locale __cloc = _S_c_locale);
529 };
530
531 template<typename _CharT>
532 locale::id numpunct<_CharT>::id;
533
534 template<>
535 numpunct<char>::~numpunct();
536
537 template<>
538 void
539 numpunct<char>::_M_initialize_numpunct(__c_locale __cloc);
540
541 #ifdef _GLIBCPP_USE_WCHAR_T
542 template<>
543 numpunct<wchar_t>::~numpunct();
544
545 template<>
546 void
547 numpunct<wchar_t>::_M_initialize_numpunct(__c_locale __cloc);
548 #endif
549
550 template<typename _CharT>
551 class numpunct_byname : public numpunct<_CharT>
552 {
553 // Data Member.
554 __c_locale _M_c_locale_numpunct;
555
556 public:
557 typedef _CharT char_type;
558 typedef basic_string<_CharT> string_type;
559
560 explicit
561 numpunct_byname(const char* __s, size_t __refs = 0)
562 : numpunct<_CharT>(__refs)
563 {
564 _S_create_c_locale(_M_c_locale_numpunct, __s);
565 _M_initialize_numpunct(_M_c_locale_numpunct);
566 }
567
568 protected:
569 virtual
570 ~numpunct_byname()
571 { _S_destroy_c_locale(_M_c_locale_numpunct); }
572 };
573
574 template<typename _CharT, typename _InIter>
575 class num_get : public locale::facet, public __num_base
576 {
577 public:
578 // Types:
579 typedef _CharT char_type;
580 typedef _InIter iter_type;
581
582 static locale::id id;
583
584 explicit
585 num_get(size_t __refs = 0) : locale::facet(__refs) { }
586
587 iter_type
588 get(iter_type __in, iter_type __end, ios_base& __io,
589 ios_base::iostate& __err, bool& __v) const
590 { return this->do_get(__in, __end, __io, __err, __v); }
591
592 iter_type
593 get(iter_type __in, iter_type __end, ios_base& __io,
594 ios_base::iostate& __err, long& __v) const
595 { return this->do_get(__in, __end, __io, __err, __v); }
596
597 iter_type
598 get(iter_type __in, iter_type __end, ios_base& __io,
599 ios_base::iostate& __err, unsigned short& __v) const
600 { return this->do_get(__in, __end, __io, __err, __v); }
601
602 iter_type
603 get(iter_type __in, iter_type __end, ios_base& __io,
604 ios_base::iostate& __err, unsigned int& __v) const
605 { return this->do_get(__in, __end, __io, __err, __v); }
606
607 iter_type
608 get(iter_type __in, iter_type __end, ios_base& __io,
609 ios_base::iostate& __err, unsigned long& __v) const
610 { return this->do_get(__in, __end, __io, __err, __v); }
611
612 #ifdef _GLIBCPP_USE_LONG_LONG
613 iter_type
614 get(iter_type __in, iter_type __end, ios_base& __io,
615 ios_base::iostate& __err, long long& __v) const
616 { return this->do_get(__in, __end, __io, __err, __v); }
617
618 iter_type
619 get(iter_type __in, iter_type __end, ios_base& __io,
620 ios_base::iostate& __err, unsigned long long& __v) const
621 { return this->do_get(__in, __end, __io, __err, __v); }
622 #endif
623
624 iter_type
625 get(iter_type __in, iter_type __end, ios_base& __io,
626 ios_base::iostate& __err, float& __v) const
627 { return this->do_get(__in, __end, __io, __err, __v); }
628
629 iter_type
630 get(iter_type __in, iter_type __end, ios_base& __io,
631 ios_base::iostate& __err, double& __v) const
632 { return this->do_get(__in, __end, __io, __err, __v); }
633
634 iter_type
635 get(iter_type __in, iter_type __end, ios_base& __io,
636 ios_base::iostate& __err, long double& __v) const
637 { return this->do_get(__in, __end, __io, __err, __v); }
638
639 iter_type
640 get(iter_type __in, iter_type __end, ios_base& __io,
641 ios_base::iostate& __err, void*& __v) const
642 { return this->do_get(__in, __end, __io, __err, __v); }
643
644 protected:
645 virtual ~num_get() { }
646
647 iter_type
648 _M_extract_float(iter_type, iter_type, ios_base&, ios_base::iostate&,
649 string& __xtrc) const;
650
651 iter_type
652 _M_extract_int(iter_type, iter_type, ios_base&, ios_base::iostate&,
653 string& __xtrc, int& __base) const;
654
655 virtual iter_type
656 do_get(iter_type, iter_type, ios_base&, ios_base::iostate&, bool&) const;
657
658
659 virtual iter_type
660 do_get(iter_type, iter_type, ios_base&, ios_base::iostate&, long&) const;
661
662 virtual iter_type
663 do_get(iter_type, iter_type, ios_base&, ios_base::iostate& __err,
664 unsigned short&) const;
665
666 virtual iter_type
667 do_get(iter_type, iter_type, ios_base&, ios_base::iostate& __err,
668 unsigned int&) const;
669
670 virtual iter_type
671 do_get(iter_type, iter_type, ios_base&, ios_base::iostate& __err,
672 unsigned long&) const;
673
674 #ifdef _GLIBCPP_USE_LONG_LONG
675 virtual iter_type
676 do_get(iter_type, iter_type, ios_base&, ios_base::iostate& __err,
677 long long&) const;
678
679 virtual iter_type
680 do_get(iter_type, iter_type, ios_base&, ios_base::iostate& __err,
681 unsigned long long&) const;
682 #endif
683
684 virtual iter_type
685 do_get(iter_type, iter_type, ios_base&, ios_base::iostate& __err,
686 float&) const;
687
688 virtual iter_type
689 do_get(iter_type, iter_type, ios_base&, ios_base::iostate& __err,
690 double&) const;
691
692 virtual iter_type
693 do_get(iter_type, iter_type, ios_base&, ios_base::iostate& __err,
694 long double&) const;
695
696 virtual iter_type
697 do_get(iter_type, iter_type, ios_base&, ios_base::iostate& __err,
698 void*&) const;
699 };
700
701 template<typename _CharT, typename _InIter>
702 locale::id num_get<_CharT, _InIter>::id;
703
704 #if 0
705 // Partial specialization for istreambuf_iterator, so can use traits_type.
706 template<typename _CharT>
707 class num_get<_CharT, istreambuf_iterator<_CharT> >;
708
709 iter_type
710 _M_extract_float(iter_type, iter_type, ios_base&, ios_base::iostate&,
711 string& __xtrc) const;
712
713 iter_type
714 _M_extract_int(iter_type, iter_type, ios_base&, ios_base::iostate&,
715 string& __xtrc, int& __base) const;
716
717 virtual iter_type
718 do_get(iter_type, iter_type, ios_base&, ios_base::iostate&, bool&) const;
719 #endif
720
721 template<typename _CharT, typename _OutIter>
722 class num_put : public locale::facet, public __num_base
723 {
724 public:
725 // Types:
726 typedef _CharT char_type;
727 typedef _OutIter iter_type;
728
729 static locale::id id;
730
731 explicit
732 num_put(size_t __refs = 0) : locale::facet(__refs) { }
733
734 iter_type
735 put(iter_type __s, ios_base& __f, char_type __fill, bool __v) const
736 { return this->do_put(__s, __f, __fill, __v); }
737
738 iter_type
739 put(iter_type __s, ios_base& __f, char_type __fill, long __v) const
740 { return this->do_put(__s, __f, __fill, __v); }
741
742 iter_type
743 put(iter_type __s, ios_base& __f, char_type __fill,
744 unsigned long __v) const
745 { return this->do_put(__s, __f, __fill, __v); }
746
747 #ifdef _GLIBCPP_USE_LONG_LONG
748 iter_type
749 put(iter_type __s, ios_base& __f, char_type __fill, long long __v) const
750 { return this->do_put(__s, __f, __fill, __v); }
751
752 iter_type
753 put(iter_type __s, ios_base& __f, char_type __fill,
754 unsigned long long __v) const
755 { return this->do_put(__s, __f, __fill, __v); }
756 #endif
757
758 iter_type
759 put(iter_type __s, ios_base& __f, char_type __fill, double __v) const
760 { return this->do_put(__s, __f, __fill, __v); }
761
762 iter_type
763 put(iter_type __s, ios_base& __f, char_type __fill,
764 long double __v) const
765 { return this->do_put(__s, __f, __fill, __v); }
766
767 iter_type
768 put(iter_type __s, ios_base& __f, char_type __fill,
769 const void* __v) const
770 { return this->do_put(__s, __f, __fill, __v); }
771
772 protected:
773 template<typename _ValueT>
774 iter_type
775 _M_convert_float(iter_type, ios_base& __io, char_type __fill,
776 char __mod, _ValueT __v) const;
777
778 template<typename _ValueT>
779 iter_type
780 _M_convert_int(iter_type, ios_base& __io, char_type __fill,
781 char __mod, char __modl, _ValueT __v) const;
782
783 iter_type
784 _M_widen_float(iter_type, ios_base& __io, char_type __fill, char* __cs,
785 int __len) const;
786
787 iter_type
788 _M_widen_int(iter_type, ios_base& __io, char_type __fill, char* __cs,
789 int __len) const;
790
791 iter_type
792 _M_insert(iter_type, ios_base& __io, char_type __fill,
793 const char_type* __ws, int __len) const;
794
795 virtual
796 ~num_put() { };
797
798 virtual iter_type
799 do_put(iter_type, ios_base&, char_type __fill, bool __v) const;
800
801 virtual iter_type
802 do_put(iter_type, ios_base&, char_type __fill, long __v) const;
803
804 virtual iter_type
805 do_put(iter_type, ios_base&, char_type __fill, unsigned long) const;
806
807 #ifdef _GLIBCPP_USE_LONG_LONG
808 virtual iter_type
809 do_put(iter_type, ios_base&, char_type __fill, long long __v) const;
810
811 virtual iter_type
812 do_put(iter_type, ios_base&, char_type __fill, unsigned long long) const;
813 #endif
814
815 virtual iter_type
816 do_put(iter_type, ios_base&, char_type __fill, double __v) const;
817
818 virtual iter_type
819 do_put(iter_type, ios_base&, char_type __fill, long double __v) const;
820
821 virtual iter_type
822 do_put(iter_type, ios_base&, char_type __fill, const void* __v) const;
823 };
824
825 template <typename _CharT, typename _OutIter>
826 locale::id num_put<_CharT, _OutIter>::id;
827
828
829 template<typename _CharT>
830 class collate : public locale::facet
831 {
832 public:
833 // Types:
834 typedef _CharT char_type;
835 typedef basic_string<_CharT> string_type;
836
837 protected:
838 // Underlying "C" library locale information saved from
839 // initialization, needed by collate_byname as well.
840 __c_locale _M_c_locale_collate;
841
842 public:
843 static locale::id id;
844
845 explicit
846 collate(size_t __refs = 0)
847 : locale::facet(__refs)
848 { _M_c_locale_collate = _S_c_locale; }
849
850 // Non-standard.
851 explicit
852 collate(__c_locale __cloc, size_t __refs = 0)
853 : locale::facet(__refs)
854 { _M_c_locale_collate = _S_clone_c_locale(__cloc); }
855
856 int
857 compare(const _CharT* __lo1, const _CharT* __hi1,
858 const _CharT* __lo2, const _CharT* __hi2) const
859 { return this->do_compare(__lo1, __hi1, __lo2, __hi2); }
860
861 string_type
862 transform(const _CharT* __lo, const _CharT* __hi) const
863 { return this->do_transform(__lo, __hi); }
864
865 long
866 hash(const _CharT* __lo, const _CharT* __hi) const
867 { return this->do_hash(__lo, __hi); }
868
869 // Used to abstract out _CharT bits in virtual member functions, below.
870 int
871 _M_compare(const _CharT*, const _CharT*) const;
872
873 size_t
874 _M_transform(_CharT*, const _CharT*, size_t) const;
875
876 protected:
877 virtual
878 ~collate()
879 {
880 if (_M_c_locale_collate != _S_c_locale)
881 _S_destroy_c_locale(_M_c_locale_collate);
882 }
883
884 virtual int
885 do_compare(const _CharT* __lo1, const _CharT* __hi1,
886 const _CharT* __lo2, const _CharT* __hi2) const;
887
888 virtual string_type
889 do_transform(const _CharT* __lo, const _CharT* __hi) const;
890
891 virtual long
892 do_hash(const _CharT* __lo, const _CharT* __hi) const;
893 };
894
895 template<typename _CharT>
896 locale::id collate<_CharT>::id;
897
898 // Specializations.
899 template<>
900 int
901 collate<char>::_M_compare(const char*, const char*) const;
902
903 template<>
904 size_t
905 collate<char>::_M_transform(char*, const char*, size_t) const;
906
907 #ifdef _GLIBCPP_USE_WCHAR_T
908 template<>
909 int
910 collate<wchar_t>::_M_compare(const wchar_t*, const wchar_t*) const;
911
912 template<>
913 size_t
914 collate<wchar_t>::_M_transform(wchar_t*, const wchar_t*, size_t) const;
915 #endif
916
917 template<typename _CharT>
918 class collate_byname : public collate<_CharT>
919 {
920 public:
921 typedef _CharT char_type;
922 typedef basic_string<_CharT> string_type;
923
924 explicit
925 collate_byname(const char* __s, size_t __refs = 0)
926 : collate<_CharT>(__refs)
927 {
928 if (_M_c_locale_collate != _S_c_locale)
929 _S_destroy_c_locale(_M_c_locale_collate);
930 _S_create_c_locale(_M_c_locale_collate, __s);
931 }
932
933 protected:
934 virtual
935 ~collate_byname() { }
936 };
937
938
939 class time_base
940 {
941 public:
942 enum dateorder { no_order, dmy, mdy, ymd, ydm };
943 };
944
945 template<typename _CharT>
946 class __timepunct : public locale::facet
947 {
948 public:
949 // Types:
950 typedef _CharT __char_type;
951 typedef basic_string<_CharT> __string_type;
952
953 static locale::id id;
954
955 // List of all known timezones, with GMT first.
956 static const _CharT* _S_timezones[14];
957
958 protected:
959 __c_locale _M_c_locale_timepunct;
960 const char* _M_name_timepunct;
961 const _CharT* _M_date_format;
962 const _CharT* _M_date_era_format;
963 const _CharT* _M_time_format;
964 const _CharT* _M_time_era_format;
965 const _CharT* _M_date_time_format;
966 const _CharT* _M_date_time_era_format;
967 const _CharT* _M_am;
968 const _CharT* _M_pm;
969 const _CharT* _M_am_pm_format;
970
971 // Day names, starting with "C"'s Sunday.
972 const _CharT* _M_day1;
973 const _CharT* _M_day2;
974 const _CharT* _M_day3;
975 const _CharT* _M_day4;
976 const _CharT* _M_day5;
977 const _CharT* _M_day6;
978 const _CharT* _M_day7;
979
980 // Abbreviated day names, starting with "C"'s Sun.
981 const _CharT* _M_day_a1;
982 const _CharT* _M_day_a2;
983 const _CharT* _M_day_a3;
984 const _CharT* _M_day_a4;
985 const _CharT* _M_day_a5;
986 const _CharT* _M_day_a6;
987 const _CharT* _M_day_a7;
988
989 // Month names, starting with "C"'s January.
990 const _CharT* _M_month01;
991 const _CharT* _M_month02;
992 const _CharT* _M_month03;
993 const _CharT* _M_month04;
994 const _CharT* _M_month05;
995 const _CharT* _M_month06;
996 const _CharT* _M_month07;
997 const _CharT* _M_month08;
998 const _CharT* _M_month09;
999 const _CharT* _M_month10;
1000 const _CharT* _M_month11;
1001 const _CharT* _M_month12;
1002
1003 // Abbreviated month names, starting with "C"'s Jan.
1004 const _CharT* _M_month_a01;
1005 const _CharT* _M_month_a02;
1006 const _CharT* _M_month_a03;
1007 const _CharT* _M_month_a04;
1008 const _CharT* _M_month_a05;
1009 const _CharT* _M_month_a06;
1010 const _CharT* _M_month_a07;
1011 const _CharT* _M_month_a08;
1012 const _CharT* _M_month_a09;
1013 const _CharT* _M_month_a10;
1014 const _CharT* _M_month_a11;
1015 const _CharT* _M_month_a12;
1016
1017 public:
1018 explicit
1019 __timepunct(size_t __refs = 0)
1020 : locale::facet(__refs), _M_name_timepunct("C")
1021 { _M_initialize_timepunct(); }
1022
1023 explicit
1024 __timepunct(__c_locale __cloc, const char* __s, size_t __refs = 0)
1025 : locale::facet(__refs), _M_name_timepunct(__s)
1026 { _M_initialize_timepunct(__cloc); }
1027
1028 void
1029 _M_put(_CharT* __s, size_t __maxlen, const _CharT* __format,
1030 const tm* __tm) const;
1031
1032 void
1033 _M_date_formats(const _CharT** __date) const
1034 {
1035 // Always have default first.
1036 __date[0] = _M_date_format;
1037 __date[1] = _M_date_era_format;
1038 }
1039
1040 void
1041 _M_time_formats(const _CharT** __time) const
1042 {
1043 // Always have default first.
1044 __time[0] = _M_time_format;
1045 __time[1] = _M_time_era_format;
1046 }
1047
1048 void
1049 _M_ampm(const _CharT** __ampm) const
1050 {
1051 __ampm[0] = _M_am;
1052 __ampm[1] = _M_pm;
1053 }
1054
1055 void
1056 _M_date_time_formats(const _CharT** __dt) const
1057 {
1058 // Always have default first.
1059 __dt[0] = _M_date_time_format;
1060 __dt[1] = _M_date_time_era_format;
1061 }
1062
1063 void
1064 _M_days(const _CharT** __days) const
1065 {
1066 __days[0] = _M_day1;
1067 __days[1] = _M_day2;
1068 __days[2] = _M_day3;
1069 __days[3] = _M_day4;
1070 __days[4] = _M_day5;
1071 __days[5] = _M_day6;
1072 __days[6] = _M_day7;
1073 }
1074
1075 void
1076 _M_days_abbreviated(const _CharT** __days) const
1077 {
1078 __days[0] = _M_day_a1;
1079 __days[1] = _M_day_a2;
1080 __days[2] = _M_day_a3;
1081 __days[3] = _M_day_a4;
1082 __days[4] = _M_day_a5;
1083 __days[5] = _M_day_a6;
1084 __days[6] = _M_day_a7;
1085 }
1086
1087 void
1088 _M_months(const _CharT** __months) const
1089 {
1090 __months[0] = _M_month01;
1091 __months[1] = _M_month02;
1092 __months[2] = _M_month03;
1093 __months[3] = _M_month04;
1094 __months[4] = _M_month05;
1095 __months[5] = _M_month06;
1096 __months[6] = _M_month07;
1097 __months[7] = _M_month08;
1098 __months[8] = _M_month09;
1099 __months[9] = _M_month10;
1100 __months[10] = _M_month11;
1101 __months[11] = _M_month12;
1102 }
1103
1104 void
1105 _M_months_abbreviated(const _CharT** __months) const
1106 {
1107 __months[0] = _M_month_a01;
1108 __months[1] = _M_month_a02;
1109 __months[2] = _M_month_a03;
1110 __months[3] = _M_month_a04;
1111 __months[4] = _M_month_a05;
1112 __months[5] = _M_month_a06;
1113 __months[6] = _M_month_a07;
1114 __months[7] = _M_month_a08;
1115 __months[8] = _M_month_a09;
1116 __months[9] = _M_month_a10;
1117 __months[10] = _M_month_a11;
1118 __months[11] = _M_month_a12;
1119 }
1120
1121 protected:
1122 virtual
1123 ~__timepunct();
1124
1125 // For use at construction time only.
1126 void
1127 _M_initialize_timepunct(__c_locale __cloc = _S_c_locale);
1128 };
1129
1130 template<typename _CharT>
1131 locale::id __timepunct<_CharT>::id;
1132
1133 // Specializations.
1134 template<>
1135 __timepunct<char>::~__timepunct();
1136
1137 template<>
1138 const char*
1139 __timepunct<char>::_S_timezones[14];
1140
1141 template<>
1142 void
1143 __timepunct<char>::_M_initialize_timepunct(__c_locale __cloc);
1144
1145 template<>
1146 void
1147 __timepunct<char>::_M_put(char*, size_t, const char*, const tm*) const;
1148
1149 #ifdef _GLIBCPP_USE_WCHAR_T
1150 template<>
1151 __timepunct<wchar_t>::~__timepunct();
1152
1153 template<>
1154 const wchar_t*
1155 __timepunct<wchar_t>::_S_timezones[14];
1156
1157 template<>
1158 void
1159 __timepunct<wchar_t>::_M_initialize_timepunct(__c_locale __cloc);
1160
1161 template<>
1162 void
1163 __timepunct<wchar_t>::_M_put(wchar_t*, size_t, const wchar_t*,
1164 const tm*) const;
1165 #endif
1166
1167 // Generic.
1168 template<typename _CharT>
1169 const _CharT* __timepunct<_CharT>::_S_timezones[14];
1170
1171
1172 template<typename _CharT, typename _InIter>
1173 class time_get : public locale::facet, public time_base
1174 {
1175 public:
1176 // Types:
1177 typedef _CharT char_type;
1178 typedef _InIter iter_type;
1179 typedef basic_string<_CharT> __string_type;
1180
1181 static locale::id id;
1182
1183 explicit
1184 time_get(size_t __refs = 0)
1185 : locale::facet (__refs) { }
1186
1187 dateorder
1188 date_order() const
1189 { return this->do_date_order(); }
1190
1191 iter_type
1192 get_time(iter_type __beg, iter_type __end, ios_base& __io,
1193 ios_base::iostate& __err, tm* __tm) const
1194 { return this->do_get_time(__beg, __end, __io, __err, __tm); }
1195
1196 iter_type
1197 get_date(iter_type __beg, iter_type __end, ios_base& __io,
1198 ios_base::iostate& __err, tm* __tm) const
1199 { return this->do_get_date(__beg, __end, __io, __err, __tm); }
1200
1201 iter_type
1202 get_weekday(iter_type __beg, iter_type __end, ios_base& __io,
1203 ios_base::iostate& __err, tm* __tm) const
1204 { return this->do_get_weekday(__beg, __end, __io, __err, __tm); }
1205
1206 iter_type
1207 get_monthname(iter_type __beg, iter_type __end, ios_base& __io,
1208 ios_base::iostate& __err, tm* __tm) const
1209 { return this->do_get_monthname(__beg, __end, __io, __err, __tm); }
1210
1211 iter_type
1212 get_year(iter_type __beg, iter_type __end, ios_base& __io,
1213 ios_base::iostate& __err, tm* __tm) const
1214 { return this->do_get_year(__beg, __end, __io, __err, __tm); }
1215
1216 protected:
1217 virtual
1218 ~time_get() { }
1219
1220 virtual dateorder
1221 do_date_order() const;
1222
1223 virtual iter_type
1224 do_get_time(iter_type __beg, iter_type __end, ios_base& __io,
1225 ios_base::iostate& __err, tm* __tm) const;
1226
1227 virtual iter_type
1228 do_get_date(iter_type __beg, iter_type __end, ios_base& __io,
1229 ios_base::iostate& __err, tm* __tm) const;
1230
1231 virtual iter_type
1232 do_get_weekday(iter_type __beg, iter_type __end, ios_base&,
1233 ios_base::iostate& __err, tm* __tm) const;
1234
1235 virtual iter_type
1236 do_get_monthname(iter_type __beg, iter_type __end, ios_base&,
1237 ios_base::iostate& __err, tm* __tm) const;
1238
1239 virtual iter_type
1240 do_get_year(iter_type __beg, iter_type __end, ios_base& __io,
1241 ios_base::iostate& __err, tm* __tm) const;
1242
1243 // Extract numeric component of length __len.
1244 void
1245 _M_extract_num(iter_type& __beg, iter_type& __end, int& __member,
1246 int __min, int __max, size_t __len,
1247 const ctype<_CharT>& __ctype,
1248 ios_base::iostate& __err) const;
1249
1250 // Extract day or month name, or any unique array of string
1251 // literals in a const _CharT* array.
1252 void
1253 _M_extract_name(iter_type& __beg, iter_type& __end, int& __member,
1254 const _CharT** __names, size_t __indexlen,
1255 ios_base::iostate& __err) const;
1256
1257 // Extract on a component-by-component basis, via __format argument.
1258 void
1259 _M_extract_via_format(iter_type& __beg, iter_type& __end, ios_base& __io,
1260 ios_base::iostate& __err, tm* __tm,
1261 const _CharT* __format) const;
1262 };
1263
1264 template<typename _CharT, typename _InIter>
1265 locale::id time_get<_CharT, _InIter>::id;
1266
1267 template<typename _CharT, typename _InIter>
1268 class time_get_byname : public time_get<_CharT, _InIter>
1269 {
1270 public:
1271 // Types:
1272 typedef _CharT char_type;
1273 typedef _InIter iter_type;
1274
1275 explicit
1276 time_get_byname(const char*, size_t __refs = 0)
1277 : time_get<_CharT, _InIter>(__refs) { }
1278
1279 protected:
1280 virtual
1281 ~time_get_byname() { }
1282 };
1283
1284 template<typename _CharT, typename _OutIter>
1285 class time_put : public locale::facet, public time_base
1286 {
1287 public:
1288 // Types:
1289 typedef _CharT char_type;
1290 typedef _OutIter iter_type;
1291
1292 static locale::id id;
1293
1294 explicit
1295 time_put(size_t __refs = 0)
1296 : locale::facet(__refs) { }
1297
1298 iter_type
1299 put(iter_type __s, ios_base& __io, char_type __fill, const tm* __tm,
1300 const _CharT* __beg, const _CharT* __end) const;
1301
1302 iter_type
1303 put(iter_type __s, ios_base& __io, char_type __fill,
1304 const tm* __tm, char __format, char __mod = 0) const
1305 { return this->do_put(__s, __io, __fill, __tm, __format, __mod); }
1306
1307 protected:
1308 virtual
1309 ~time_put()
1310 { }
1311
1312 virtual iter_type
1313 do_put(iter_type __s, ios_base& __io, char_type __fill, const tm* __tm,
1314 char __format, char __mod) const;
1315 };
1316
1317 template<typename _CharT, typename _OutIter>
1318 locale::id time_put<_CharT, _OutIter>::id;
1319
1320 template<typename _CharT, typename _OutIter>
1321 class time_put_byname : public time_put<_CharT, _OutIter>
1322 {
1323 public:
1324 // Types:
1325 typedef _CharT char_type;
1326 typedef _OutIter iter_type;
1327
1328 explicit
1329 time_put_byname(const char* /*__s*/, size_t __refs = 0)
1330 : time_put<_CharT, _OutIter>(__refs)
1331 { };
1332
1333 protected:
1334 virtual
1335 ~time_put_byname() { }
1336 };
1337
1338
1339 class money_base
1340 {
1341 public:
1342 enum part { none, space, symbol, sign, value };
1343 struct pattern { char field[4]; };
1344
1345 static const pattern _S_default_pattern;
1346
1347 // Construct and return valid pattern consisting of some combination of:
1348 // space none symbol sign value
1349 static pattern
1350 _S_construct_pattern(char __precedes, char __space, char __posn);
1351 };
1352
1353 template<typename _CharT, bool _Intl>
1354 class moneypunct : public locale::facet, public money_base
1355 {
1356 public:
1357 // Types:
1358 typedef _CharT char_type;
1359 typedef basic_string<_CharT> string_type;
1360
1361 static const bool intl = _Intl;
1362 static locale::id id;
1363
1364 private:
1365 const char* _M_grouping;
1366 char_type _M_decimal_point;
1367 char_type _M_thousands_sep;
1368 const char_type* _M_curr_symbol;
1369 const char_type* _M_positive_sign;
1370 const char_type* _M_negative_sign;
1371 int _M_frac_digits;
1372 pattern _M_pos_format;
1373 pattern _M_neg_format;
1374
1375 public:
1376 explicit
1377 moneypunct(size_t __refs = 0) : locale::facet(__refs)
1378 { _M_initialize_moneypunct(); }
1379
1380 explicit
1381 moneypunct(__c_locale __cloc, const char* __s, size_t __refs = 0)
1382 : locale::facet(__refs)
1383 { _M_initialize_moneypunct(__cloc, __s); }
1384
1385 char_type
1386 decimal_point() const
1387 { return this->do_decimal_point(); }
1388
1389 char_type
1390 thousands_sep() const
1391 { return this->do_thousands_sep(); }
1392
1393 string
1394 grouping() const
1395 { return this->do_grouping(); }
1396
1397 string_type
1398 curr_symbol() const
1399 { return this->do_curr_symbol(); }
1400
1401 string_type
1402 positive_sign() const
1403 { return this->do_positive_sign(); }
1404
1405 string_type
1406 negative_sign() const
1407 { return this->do_negative_sign(); }
1408
1409 int
1410 frac_digits() const
1411 { return this->do_frac_digits(); }
1412
1413 pattern
1414 pos_format() const
1415 { return this->do_pos_format(); }
1416
1417 pattern
1418 neg_format() const
1419 { return this->do_neg_format(); }
1420
1421 protected:
1422 virtual
1423 ~moneypunct();
1424
1425 virtual char_type
1426 do_decimal_point() const
1427 { return _M_decimal_point; }
1428
1429 virtual char_type
1430 do_thousands_sep() const
1431 { return _M_thousands_sep; }
1432
1433 virtual string
1434 do_grouping() const
1435 { return _M_grouping; }
1436
1437 virtual string_type
1438 do_curr_symbol() const
1439 { return _M_curr_symbol; }
1440
1441 virtual string_type
1442 do_positive_sign() const
1443 { return _M_positive_sign; }
1444
1445 virtual string_type
1446 do_negative_sign() const
1447 { return _M_negative_sign; }
1448
1449 virtual int
1450 do_frac_digits() const
1451 { return _M_frac_digits; }
1452
1453 virtual pattern
1454 do_pos_format() const
1455 { return _M_pos_format; }
1456
1457 virtual pattern
1458 do_neg_format() const
1459 { return _M_neg_format; }
1460
1461 // For use at construction time only.
1462 void
1463 _M_initialize_moneypunct(__c_locale __cloc = _S_c_locale,
1464 const char* __name = NULL);
1465 };
1466
1467 template<typename _CharT, bool _Intl>
1468 locale::id moneypunct<_CharT, _Intl>::id;
1469
1470 template<typename _CharT, bool _Intl>
1471 const bool moneypunct<_CharT, _Intl>::intl;
1472
1473 template<>
1474 moneypunct<char, true>::~moneypunct();
1475
1476 template<>
1477 moneypunct<char, false>::~moneypunct();
1478
1479 template<>
1480 void
1481 moneypunct<char, true>::_M_initialize_moneypunct(__c_locale, const char*);
1482
1483 template<>
1484 void
1485 moneypunct<char, false>::_M_initialize_moneypunct(__c_locale, const char*);
1486
1487 #ifdef _GLIBCPP_USE_WCHAR_T
1488 template<>
1489 moneypunct<wchar_t, true>::~moneypunct();
1490
1491 template<>
1492 moneypunct<wchar_t, false>::~moneypunct();
1493
1494 template<>
1495 void
1496 moneypunct<wchar_t, true>::_M_initialize_moneypunct(__c_locale,
1497 const char*);
1498
1499 template<>
1500 void
1501 moneypunct<wchar_t, false>::_M_initialize_moneypunct(__c_locale,
1502 const char*);
1503 #endif
1504
1505 template<typename _CharT, bool _Intl>
1506 class moneypunct_byname : public moneypunct<_CharT, _Intl>
1507 {
1508 __c_locale _M_c_locale_moneypunct;
1509
1510 public:
1511 typedef _CharT char_type;
1512 typedef basic_string<_CharT> string_type;
1513
1514 static const bool intl = _Intl;
1515
1516 explicit
1517 moneypunct_byname(const char* __s, size_t __refs = 0)
1518 : moneypunct<_CharT, _Intl>(__refs)
1519 {
1520 _S_create_c_locale(_M_c_locale_moneypunct, __s);
1521 _M_initialize_moneypunct(_M_c_locale_moneypunct);
1522 }
1523
1524 protected:
1525 virtual
1526 ~moneypunct_byname()
1527 { _S_destroy_c_locale(_M_c_locale_moneypunct); }
1528 };
1529
1530 template<typename _CharT, bool _Intl>
1531 const bool moneypunct_byname<_CharT, _Intl>::intl;
1532
1533 template<typename _CharT, typename _InIter>
1534 class money_get : public locale::facet
1535 {
1536 public:
1537 // Types:
1538 typedef _CharT char_type;
1539 typedef _InIter iter_type;
1540 typedef basic_string<_CharT> string_type;
1541
1542 static locale::id id;
1543
1544 explicit
1545 money_get(size_t __refs = 0) : locale::facet(__refs) { }
1546
1547 iter_type
1548 get(iter_type __s, iter_type __end, bool __intl, ios_base& __io,
1549 ios_base::iostate& __err, long double& __units) const
1550 { return this->do_get(__s, __end, __intl, __io, __err, __units); }
1551
1552 iter_type
1553 get(iter_type __s, iter_type __end, bool __intl, ios_base& __io,
1554 ios_base::iostate& __err, string_type& __digits) const
1555 { return this->do_get(__s, __end, __intl, __io, __err, __digits); }
1556
1557 protected:
1558 virtual
1559 ~money_get() { }
1560
1561 virtual iter_type
1562 do_get(iter_type __s, iter_type __end, bool __intl, ios_base& __io,
1563 ios_base::iostate& __err, long double& __units) const;
1564
1565 virtual iter_type
1566 do_get(iter_type __s, iter_type __end, bool __intl, ios_base& __io,
1567 ios_base::iostate& __err, string_type& __digits) const;
1568 };
1569
1570 template<typename _CharT, typename _InIter>
1571 locale::id money_get<_CharT, _InIter>::id;
1572
1573 template<typename _CharT, typename _OutIter>
1574 class money_put : public locale::facet
1575 {
1576 public:
1577 typedef _CharT char_type;
1578 typedef _OutIter iter_type;
1579 typedef basic_string<_CharT> string_type;
1580
1581 static locale::id id;
1582
1583 explicit
1584 money_put(size_t __refs = 0) : locale::facet(__refs) { }
1585
1586 iter_type
1587 put(iter_type __s, bool __intl, ios_base& __io,
1588 char_type __fill, long double __units) const
1589 { return this->do_put(__s, __intl, __io, __fill, __units); }
1590
1591 iter_type
1592 put(iter_type __s, bool __intl, ios_base& __io,
1593 char_type __fill, const string_type& __digits) const
1594 { return this->do_put(__s, __intl, __io, __fill, __digits); }
1595
1596 protected:
1597 virtual
1598 ~money_put() { }
1599
1600 virtual iter_type
1601 do_put(iter_type __s, bool __intl, ios_base& __io, char_type __fill,
1602 long double __units) const;
1603
1604 virtual iter_type
1605 do_put(iter_type __s, bool __intl, ios_base& __io, char_type __fill,
1606 const string_type& __digits) const;
1607 };
1608
1609 template<typename _CharT, typename _OutIter>
1610 locale::id money_put<_CharT, _OutIter>::id;
1611
1612
1613 struct messages_base
1614 {
1615 typedef int catalog;
1616 };
1617
1618 template<typename _CharT>
1619 class messages : public locale::facet, public messages_base
1620 {
1621 public:
1622 // Types:
1623 typedef _CharT char_type;
1624 typedef basic_string<_CharT> string_type;
1625
1626 protected:
1627 // Underlying "C" library locale information saved from
1628 // initialization, needed by messages_byname as well.
1629 __c_locale _M_c_locale_messages;
1630 #if 1
1631 // Only needed if glibc < 2.3
1632 const char* _M_name_messages;
1633 #endif
1634
1635 public:
1636 static locale::id id;
1637
1638 explicit
1639 messages(size_t __refs = 0)
1640 : locale::facet(__refs), _M_name_messages("C")
1641 { _M_c_locale_messages = _S_c_locale; }
1642
1643 // Non-standard.
1644 explicit
1645 messages(__c_locale __cloc, const char* __name, size_t __refs = 0)
1646 : locale::facet(__refs)
1647 {
1648 _M_name_messages = __name;
1649 _M_c_locale_messages = _S_clone_c_locale(__cloc);
1650 }
1651
1652 catalog
1653 open(const basic_string<char>& __s, const locale& __loc) const
1654 { return this->do_open(__s, __loc); }
1655
1656 // Non-standard and unorthodox, yet effective.
1657 catalog
1658 open(const basic_string<char>&, const locale&, const char*) const;
1659
1660 string_type
1661 get(catalog __c, int __set, int __msgid, const string_type& __s) const
1662 { return this->do_get(__c, __set, __msgid, __s); }
1663
1664 void
1665 close(catalog __c) const
1666 { return this->do_close(__c); }
1667
1668 protected:
1669 virtual
1670 ~messages()
1671 {
1672 if (_M_c_locale_messages != _S_c_locale)
1673 _S_destroy_c_locale(_M_c_locale_messages);
1674 }
1675
1676 virtual catalog
1677 do_open(const basic_string<char>&, const locale&) const;
1678
1679 virtual string_type
1680 do_get(catalog, int, int, const string_type& __dfault) const;
1681
1682 virtual void
1683 do_close(catalog) const;
1684
1685 // Returns a locale and codeset-converted string, given a char* message.
1686 char*
1687 _M_convert_to_char(const string_type& __msg) const
1688 {
1689 // XXX
1690 return reinterpret_cast<char*>(const_cast<_CharT*>(__msg.c_str()));
1691 }
1692
1693 // Returns a locale and codeset-converted string, given a char* message.
1694 string_type
1695 _M_convert_from_char(char* __msg) const
1696 {
1697 // Length of message string without terminating null.
1698 size_t __len = char_traits<char>::length(__msg) - 1;
1699
1700 // "everybody can easily convert the string using
1701 // mbsrtowcs/wcsrtombs or with iconv()"
1702 #if 0
1703 // Convert char* to _CharT in locale used to open catalog.
1704 // XXX need additional template parameter on messages class for this..
1705 // typedef typename codecvt<char, _CharT, _StateT> __codecvt_type;
1706 typedef typename codecvt<char, _CharT, mbstate_t> __codecvt_type;
1707
1708 __codecvt_type::state_type __state;
1709 // XXX may need to initialize state.
1710 //initialize_state(__state._M_init());
1711
1712 char* __from_next;
1713 // XXX what size for this string?
1714 _CharT* __to = static_cast<_CharT*>(__builtin_alloca(__len + 1));
1715 const __codecvt_type& __cvt = use_facet<__codecvt_type>(_M_locale_conv);
1716 __cvt.out(__state, __msg, __msg + __len, __from_next,
1717 __to, __to + __len + 1, __to_next);
1718 return string_type(__to);
1719 #endif
1720 #if 0
1721 typedef ctype<_CharT> __ctype_type;
1722 // const __ctype_type& __cvt = use_facet<__ctype_type>(_M_locale_msg);
1723 const __ctype_type& __cvt = use_facet<__ctype_type>(locale());
1724 // XXX Again, proper length of converted string an issue here.
1725 // For now, assume the converted length is not larger.
1726 _CharT* __dest = static_cast<_CharT*>(__builtin_alloca(__len + 1));
1727 __cvt.widen(__msg, __msg + __len, __dest);
1728 return basic_string<_CharT>(__dest);
1729 #endif
1730 return string_type();
1731 }
1732 };
1733
1734 template<typename _CharT>
1735 locale::id messages<_CharT>::id;
1736
1737 // Specializations for required instantiations.
1738 template<>
1739 string
1740 messages<char>::do_get(catalog, int, int, const string&) const;
1741
1742 // Include host and configuration specific messages virtual functions.
1743 #include <bits/messages_members.h>
1744
1745 template<typename _CharT>
1746 class messages_byname : public messages<_CharT>
1747 {
1748 public:
1749 typedef _CharT char_type;
1750 typedef basic_string<_CharT> string_type;
1751
1752 explicit
1753 messages_byname(const char* __s, size_t __refs = 0)
1754 : messages<_CharT>(__refs)
1755 {
1756 _M_name_messages = __s;
1757 if (_M_c_locale_messages != _S_c_locale)
1758 _S_destroy_c_locale(_M_c_locale_messages);
1759 _S_create_c_locale(_M_c_locale_messages, __s);
1760 }
1761
1762 protected:
1763 virtual
1764 ~messages_byname()
1765 { }
1766 };
1767
1768
1769 // Subclause convenience interfaces, inlines.
1770 // NB: These are inline because, when used in a loop, some compilers
1771 // can hoist the body out of the loop; then it's just as fast as the
1772 // C is*() function.
1773 template<typename _CharT>
1774 inline bool
1775 isspace(_CharT __c, const locale& __loc)
1776 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::space, __c); }
1777
1778 template<typename _CharT>
1779 inline bool
1780 isprint(_CharT __c, const locale& __loc)
1781 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::print, __c); }
1782
1783 template<typename _CharT>
1784 inline bool
1785 iscntrl(_CharT __c, const locale& __loc)
1786 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::cntrl, __c); }
1787
1788 template<typename _CharT>
1789 inline bool
1790 isupper(_CharT __c, const locale& __loc)
1791 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::upper, __c); }
1792
1793 template<typename _CharT>
1794 inline bool islower(_CharT __c, const locale& __loc)
1795 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::lower, __c); }
1796
1797 template<typename _CharT>
1798 inline bool
1799 isalpha(_CharT __c, const locale& __loc)
1800 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::alpha, __c); }
1801
1802 template<typename _CharT>
1803 inline bool
1804 isdigit(_CharT __c, const locale& __loc)
1805 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::digit, __c); }
1806
1807 template<typename _CharT>
1808 inline bool
1809 ispunct(_CharT __c, const locale& __loc)
1810 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::punct, __c); }
1811
1812 template<typename _CharT>
1813 inline bool
1814 isxdigit(_CharT __c, const locale& __loc)
1815 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::xdigit, __c); }
1816
1817 template<typename _CharT>
1818 inline bool
1819 isalnum(_CharT __c, const locale& __loc)
1820 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::alnum, __c); }
1821
1822 template<typename _CharT>
1823 inline bool
1824 isgraph(_CharT __c, const locale& __loc)
1825 { return use_facet<ctype<_CharT> >(__loc).is(ctype_base::graph, __c); }
1826
1827 template<typename _CharT>
1828 inline _CharT
1829 toupper(_CharT __c, const locale& __loc)
1830 { return use_facet<ctype<_CharT> >(__loc).toupper(__c); }
1831
1832 template<typename _CharT>
1833 inline _CharT
1834 tolower(_CharT __c, const locale& __loc)
1835 { return use_facet<ctype<_CharT> >(__loc).tolower(__c); }
1836 } // namespace std
1837
1838 #endif