1 /*
2 * Copyright (c) 1999
3 * Silicon Graphics Computer Systems, Inc.
4 *
5 * Copyright (c) 1999
6 * Boris Fomitchev
7 *
8 * This material is provided "as is", with absolutely no warranty expressed
9 * or implied. Any use is at your own risk.
10 *
11 * Permission to use or copy this software for any purpose is hereby granted
12 * without fee, provided the above notices are retained on all copies.
13 * Permission to modify the code and to distribute modified code is granted,
14 * provided the above notices are retained, and a notice that the code was
15 * modified is included with the above copyright notice.
16 *
17 */
18
19 #include "stlport_prefix.h"
20
21 #include <algorithm>
22 #include <locale>
23 #include <functional>
24
25 #include "c_locale.h"
26
27 _STLP_BEGIN_NAMESPACE
28
29 //----------------------------------------------------------------------
30 // ctype<char>
31
32 // The classic table: static data members.
33
34 #if !defined (_STLP_STATIC_CONST_INIT_BUG) && !defined (_STLP_NO_STATIC_CONST_DEFINITION)
35 //*TY 02/25/2000 - added workaround for MPW compilers; they confuse on in-class static const
36 const size_t ctype<char>::table_size;
37 #endif
38
39 // This macro is specifically for platforms where isprint() relies
40 // on separate flag
41
42 const ctype_base::mask*
classic_table()43 ctype<char>::classic_table() _STLP_NOTHROW {
44 /* Ctype table for the ASCII character set. */
45 static const ctype_base::mask _S_classic_table[table_size] = {
46 cntrl /* null */,
47 cntrl /* ^A */,
48 cntrl /* ^B */,
49 cntrl /* ^C */,
50 cntrl /* ^D */,
51 cntrl /* ^E */,
52 cntrl /* ^F */,
53 cntrl /* ^G */,
54 cntrl /* ^H */,
55 ctype_base::mask(space | cntrl) /* tab */,
56 ctype_base::mask(space | cntrl) /* LF */,
57 ctype_base::mask(space | cntrl) /* ^K */,
58 ctype_base::mask(space | cntrl) /* FF */,
59 ctype_base::mask(space | cntrl) /* ^M */,
60 cntrl /* ^N */,
61 cntrl /* ^O */,
62 cntrl /* ^P */,
63 cntrl /* ^Q */,
64 cntrl /* ^R */,
65 cntrl /* ^S */,
66 cntrl /* ^T */,
67 cntrl /* ^U */,
68 cntrl /* ^V */,
69 cntrl /* ^W */,
70 cntrl /* ^X */,
71 cntrl /* ^Y */,
72 cntrl /* ^Z */,
73 cntrl /* esc */,
74 cntrl /* ^\ */,
75 cntrl /* ^] */,
76 cntrl /* ^^ */,
77 cntrl /* ^_ */,
78 ctype_base::mask(space | print) /* */,
79 ctype_base::mask(punct | print) /* ! */,
80 ctype_base::mask(punct | print) /* " */,
81 ctype_base::mask(punct | print) /* # */,
82 ctype_base::mask(punct | print) /* $ */,
83 ctype_base::mask(punct | print) /* % */,
84 ctype_base::mask(punct | print) /* & */,
85 ctype_base::mask(punct | print) /* ' */,
86 ctype_base::mask(punct | print) /* ( */,
87 ctype_base::mask(punct | print) /* ) */,
88 ctype_base::mask(punct | print) /* * */,
89 ctype_base::mask(punct | print) /* + */,
90 ctype_base::mask(punct | print) /* , */,
91 ctype_base::mask(punct | print) /* - */,
92 ctype_base::mask(punct | print) /* . */,
93 ctype_base::mask(punct | print) /* / */,
94 ctype_base::mask(digit | print | xdigit) /* 0 */,
95 ctype_base::mask(digit | print | xdigit) /* 1 */,
96 ctype_base::mask(digit | print | xdigit) /* 2 */,
97 ctype_base::mask(digit | print | xdigit) /* 3 */,
98 ctype_base::mask(digit | print | xdigit) /* 4 */,
99 ctype_base::mask(digit | print | xdigit) /* 5 */,
100 ctype_base::mask(digit | print | xdigit) /* 6 */,
101 ctype_base::mask(digit | print | xdigit) /* 7 */,
102 ctype_base::mask(digit | print | xdigit) /* 8 */,
103 ctype_base::mask(digit | print | xdigit) /* 9 */,
104 ctype_base::mask(punct | print) /* : */,
105 ctype_base::mask(punct | print) /* ; */,
106 ctype_base::mask(punct | print) /* < */,
107 ctype_base::mask(punct | print) /* = */,
108 ctype_base::mask(punct | print) /* > */,
109 ctype_base::mask(punct | print) /* ? */,
110 ctype_base::mask(punct | print) /* ! */,
111 ctype_base::mask(alpha | print | upper | xdigit) /* A */,
112 ctype_base::mask(alpha | print | upper | xdigit) /* B */,
113 ctype_base::mask(alpha | print | upper | xdigit) /* C */,
114 ctype_base::mask(alpha | print | upper | xdigit) /* D */,
115 ctype_base::mask(alpha | print | upper | xdigit) /* E */,
116 ctype_base::mask(alpha | print | upper | xdigit) /* F */,
117 ctype_base::mask(alpha | print | upper) /* G */,
118 ctype_base::mask(alpha | print | upper) /* H */,
119 ctype_base::mask(alpha | print | upper) /* I */,
120 ctype_base::mask(alpha | print | upper) /* J */,
121 ctype_base::mask(alpha | print | upper) /* K */,
122 ctype_base::mask(alpha | print | upper) /* L */,
123 ctype_base::mask(alpha | print | upper) /* M */,
124 ctype_base::mask(alpha | print | upper) /* N */,
125 ctype_base::mask(alpha | print | upper) /* O */,
126 ctype_base::mask(alpha | print | upper) /* P */,
127 ctype_base::mask(alpha | print | upper) /* Q */,
128 ctype_base::mask(alpha | print | upper) /* R */,
129 ctype_base::mask(alpha | print | upper) /* S */,
130 ctype_base::mask(alpha | print | upper) /* T */,
131 ctype_base::mask(alpha | print | upper) /* U */,
132 ctype_base::mask(alpha | print | upper) /* V */,
133 ctype_base::mask(alpha | print | upper) /* W */,
134 ctype_base::mask(alpha | print | upper) /* X */,
135 ctype_base::mask(alpha | print | upper) /* Y */,
136 ctype_base::mask(alpha | print | upper) /* Z */,
137 ctype_base::mask(punct | print) /* [ */,
138 ctype_base::mask(punct | print) /* \ */,
139 ctype_base::mask(punct | print) /* ] */,
140 ctype_base::mask(punct | print) /* ^ */,
141 ctype_base::mask(punct | print) /* _ */,
142 ctype_base::mask(punct | print) /* ` */,
143 ctype_base::mask(alpha | print | lower | xdigit) /* a */,
144 ctype_base::mask(alpha | print | lower | xdigit) /* b */,
145 ctype_base::mask(alpha | print | lower | xdigit) /* c */,
146 ctype_base::mask(alpha | print | lower | xdigit) /* d */,
147 ctype_base::mask(alpha | print | lower | xdigit) /* e */,
148 ctype_base::mask(alpha | print | lower | xdigit) /* f */,
149 ctype_base::mask(alpha | print | lower) /* g */,
150 ctype_base::mask(alpha | print | lower) /* h */,
151 ctype_base::mask(alpha | print | lower) /* i */,
152 ctype_base::mask(alpha | print | lower) /* j */,
153 ctype_base::mask(alpha | print | lower) /* k */,
154 ctype_base::mask(alpha | print | lower) /* l */,
155 ctype_base::mask(alpha | print | lower) /* m */,
156 ctype_base::mask(alpha | print | lower) /* n */,
157 ctype_base::mask(alpha | print | lower) /* o */,
158 ctype_base::mask(alpha | print | lower) /* p */,
159 ctype_base::mask(alpha | print | lower) /* q */,
160 ctype_base::mask(alpha | print | lower) /* r */,
161 ctype_base::mask(alpha | print | lower) /* s */,
162 ctype_base::mask(alpha | print | lower) /* t */,
163 ctype_base::mask(alpha | print | lower) /* u */,
164 ctype_base::mask(alpha | print | lower) /* v */,
165 ctype_base::mask(alpha | print | lower) /* w */,
166 ctype_base::mask(alpha | print | lower) /* x */,
167 ctype_base::mask(alpha | print | lower) /* y */,
168 ctype_base::mask(alpha | print | lower) /* z */,
169 ctype_base::mask(punct | print) /* { */,
170 ctype_base::mask(punct | print) /* | */,
171 ctype_base::mask(punct | print) /* } */,
172 ctype_base::mask(punct | print) /* ~ */,
173 cntrl /* del (0x7f)*/,
174 /* ASCII is a 7-bit code, so everything else is non-ASCII */
175 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
176 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
177 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
178 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
179 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
180 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
181 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
182 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
183 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
184 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
185 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
186 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
187 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
188 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
189 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0),
190 ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0), ctype_base::mask(0)
191 };
192 return _S_classic_table;
193 }
194
195 // For every c in the range 0 <= c < 256, _S_upper[c] is the
196 // uppercased version of c and _S_lower[c] is the lowercased
197 // version. As before, these two tables assume the ASCII character
198 // set.
199
200 const unsigned char _S_upper[ctype<char>::table_size] =
201 {
202 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
203 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
204 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
205 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
206 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
207 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f,
208 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
209 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f,
210 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,
211 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f,
212 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57,
213 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f,
214 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47,
215 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f,
216 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57,
217 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f,
218 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
219 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f,
220 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
221 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f,
222 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7,
223 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf,
224 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7,
225 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf,
226 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7,
227 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf,
228 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7,
229 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf,
230 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7,
231 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef,
232 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,
233 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
234 };
235
236 const unsigned char _S_lower[ctype<char>::table_size] =
237 {
238 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
239 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f,
240 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
241 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f,
242 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27,
243 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f,
244 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37,
245 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f,
246 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
247 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f,
248 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,
249 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f,
250 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67,
251 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f,
252 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77,
253 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f,
254 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
255 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f,
256 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97,
257 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f,
258 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7,
259 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf,
260 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7,
261 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf,
262 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7,
263 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf,
264 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7,
265 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf,
266 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7,
267 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef,
268 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7,
269 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff
270 };
271
272 //An helper struct to check wchar_t index without generating warnings
273 //under some compilers (gcc) because of a limited range of value
274 //(when wchar_t is unsigned)
275 template <bool _IsSigned>
276 struct _WCharIndexT;
277
278 #if !(defined (__BORLANDC__) && !defined(__linux__)) && \
279 !(defined (__GNUC__) && (defined (__MINGW32__) || defined (__CYGWIN__))) && \
280 !defined (__ICL)
281 _STLP_TEMPLATE_NULL
282 struct _WCharIndexT<true> {
in_range_WCharIndexT283 static bool in_range(wchar_t c, size_t upperBound) {
284 return c >= 0 && size_t(c) < upperBound;
285 }
286 };
287 #endif
288
289 _STLP_TEMPLATE_NULL
290 struct _WCharIndexT<false> {
in_range_WCharIndexT291 static bool in_range(wchar_t c, size_t upperBound) {
292 return size_t(c) < upperBound;
293 }
294 };
295
296 typedef _WCharIndexT<wchar_t(-1) < 0> _WCharIndex;
297
298 // Some helper functions used in ctype<>::scan_is and scan_is_not.
299
300 struct _Ctype_is_mask : public unary_function<char, bool> {
301 ctype_base::mask _Mask;
302 const ctype_base::mask* _M_table;
303
_Ctype_is_mask_Ctype_is_mask304 _Ctype_is_mask(ctype_base::mask __m, const ctype_base::mask* __t) : _Mask(__m), _M_table(__t) {}
operator ()_Ctype_is_mask305 bool operator()(char __c) const { return (_M_table[(unsigned char) __c] & _Mask) != 0; }
306 };
307
308 struct _Ctype_not_mask : public unary_function<char, bool> {
309 ctype_base::mask _Mask;
310 const ctype_base::mask* _M_table;
311
_Ctype_not_mask_Ctype_not_mask312 _Ctype_not_mask(ctype_base::mask __m, const ctype_base::mask* __t) : _Mask(__m), _M_table(__t) {}
operator ()_Ctype_not_mask313 bool operator()(char __c) const { return (_M_table[(unsigned char) __c] & _Mask) == 0; }
314 };
315
ctype(const ctype_base::mask * __tab,bool __del,size_t __refs)316 ctype<char>::ctype(const ctype_base::mask * __tab, bool __del, size_t __refs) :
317 locale::facet(__refs),
318 _M_ctype_table(__tab ? __tab : classic_table()),
319 _M_delete(__tab && __del)
320 {}
321
~ctype()322 ctype<char>::~ctype() {
323 if (_M_delete)
324 delete[] __CONST_CAST(ctype_base::mask *, _M_ctype_table);
325 }
326
327 const char*
328 #if defined (__DMC__)
329 _STLP_DECLSPEC
330 #endif
scan_is(ctype_base::mask __m,const char * __low,const char * __high) const331 ctype<char>::scan_is(ctype_base::mask __m, const char* __low, const char* __high) const
332 { return _STLP_STD::find_if(__low, __high, _Ctype_is_mask(__m, _M_ctype_table)); }
333
334 const char*
335 #if defined (__DMC__)
336 _STLP_DECLSPEC
337 #endif
scan_not(ctype_base::mask __m,const char * __low,const char * __high) const338 ctype<char>::scan_not(ctype_base::mask __m, const char* __low, const char* __high) const
339 { return _STLP_STD::find_if(__low, __high, _Ctype_not_mask(__m, _M_ctype_table)); }
340
do_toupper(char __c) const341 char ctype<char>::do_toupper(char __c) const
342 { return (char) _S_upper[(unsigned char) __c]; }
do_tolower(char __c) const343 char ctype<char>::do_tolower(char __c) const
344 { return (char) _S_lower[(unsigned char) __c]; }
345
do_toupper(char * __low,const char * __high) const346 const char* ctype<char>::do_toupper(char* __low, const char* __high) const {
347 for ( ; __low < __high; ++__low)
348 *__low = (char) _S_upper[(unsigned char) *__low];
349 return __high;
350 }
do_tolower(char * __low,const char * __high) const351 const char* ctype<char>::do_tolower(char* __low, const char* __high) const {
352 for ( ; __low < __high; ++__low)
353 *__low = (char) _S_lower[(unsigned char) *__low];
354 return __high;
355 }
356
357 char
do_widen(char __c) const358 ctype<char>::do_widen(char __c) const { return __c; }
359
360 const char*
do_widen(const char * __low,const char * __high,char * __to) const361 ctype<char>::do_widen(const char* __low, const char* __high,
362 char* __to) const {
363 _STLP_PRIV __copy_trivial(__low, __high, __to);
364 return __high;
365 }
366 char
do_narrow(char __c,char) const367 ctype<char>::do_narrow(char __c, char /* dfault */ ) const { return __c; }
368 const char*
do_narrow(const char * __low,const char * __high,char,char * __to) const369 ctype<char>::do_narrow(const char* __low, const char* __high,
370 char /* dfault */, char* __to) const {
371 _STLP_PRIV __copy_trivial(__low, __high, __to);
372 return __high;
373 }
374
375
376 #if !defined (_STLP_NO_WCHAR_T)
377
378 struct _Ctype_w_is_mask : public unary_function<wchar_t, bool> {
379 ctype_base::mask M;
380 const ctype_base::mask* table;
381
_Ctype_w_is_mask_Ctype_w_is_mask382 _Ctype_w_is_mask(ctype_base::mask m, const ctype_base::mask* t)
383 : M(m), table(t) {}
operator ()_Ctype_w_is_mask384 bool operator()(wchar_t c) const
385 { return _WCharIndex::in_range(c, ctype<char>::table_size) && (table[c] & M); }
386 };
387
388 //----------------------------------------------------------------------
389 // ctype<wchar_t>
390
~ctype()391 ctype<wchar_t>::~ctype() {}
392
393
do_is(ctype_base::mask m,wchar_t c) const394 bool ctype<wchar_t>::do_is(ctype_base::mask m, wchar_t c) const {
395 const ctype_base::mask * table = ctype<char>::classic_table();
396 return _WCharIndex::in_range(c, ctype<char>::table_size) && (m & table[c]);
397 }
398
do_is(const wchar_t * low,const wchar_t * high,ctype_base::mask * vec) const399 const wchar_t* ctype<wchar_t>::do_is(const wchar_t* low, const wchar_t* high,
400 ctype_base::mask * vec) const {
401 // boris : not clear if this is the right thing to do...
402 const ctype_base::mask * table = ctype<char>::classic_table();
403 wchar_t c;
404 for ( ; low < high; ++low, ++vec) {
405 c = *low;
406 *vec = _WCharIndex::in_range(c, ctype<char>::table_size) ? table[c] : ctype_base::mask(0);
407 }
408 return high;
409 }
410
411 const wchar_t*
do_scan_is(ctype_base::mask m,const wchar_t * low,const wchar_t * high) const412 ctype<wchar_t>::do_scan_is(ctype_base::mask m,
413 const wchar_t* low, const wchar_t* high) const {
414 return find_if(low, high, _Ctype_w_is_mask(m, ctype<char>::classic_table()));
415 }
416
417
418 const wchar_t*
do_scan_not(ctype_base::mask m,const wchar_t * low,const wchar_t * high) const419 ctype<wchar_t>::do_scan_not(ctype_base::mask m,
420 const wchar_t* low, const wchar_t* high) const {
421 return find_if(low, high, not1(_Ctype_w_is_mask(m, ctype<char>::classic_table())));
422 }
423
do_toupper(wchar_t c) const424 wchar_t ctype<wchar_t>::do_toupper(wchar_t c) const {
425 return _WCharIndex::in_range(c, ctype<char>::table_size) ? (wchar_t)_S_upper[c]
426 : c;
427 }
428
429 const wchar_t*
do_toupper(wchar_t * low,const wchar_t * high) const430 ctype<wchar_t>::do_toupper(wchar_t* low, const wchar_t* high) const {
431 for ( ; low < high; ++low) {
432 wchar_t c = *low;
433 *low = _WCharIndex::in_range(c, ctype<char>::table_size) ? (wchar_t)_S_upper[c]
434 : c;
435 }
436 return high;
437 }
438
do_tolower(wchar_t c) const439 wchar_t ctype<wchar_t>::do_tolower(wchar_t c) const {
440 return _WCharIndex::in_range(c, ctype<char>::table_size) ? (wchar_t)_S_lower[c]
441 : c;
442 }
443
444 const wchar_t*
do_tolower(wchar_t * low,const wchar_t * high) const445 ctype<wchar_t>::do_tolower(wchar_t* low, const wchar_t* high) const {
446 for ( ; low < high; ++low) {
447 wchar_t c = *low;
448 *low = _WCharIndex::in_range(c, ctype<char>::table_size) ? (wchar_t)_S_lower[c]
449 : c;
450 }
451 return high;
452 }
453
do_widen(char c) const454 wchar_t ctype<wchar_t>::do_widen(char c) const {
455 return (wchar_t)(unsigned char)c;
456 }
457
458 const char*
do_widen(const char * low,const char * high,wchar_t * dest) const459 ctype<wchar_t>::do_widen(const char* low, const char* high,
460 wchar_t* dest) const {
461 while (low != high)
462 *dest++ = (wchar_t)(unsigned char)*low++;
463 return high;
464 }
465
do_narrow(wchar_t c,char dfault) const466 char ctype<wchar_t>::do_narrow(wchar_t c, char dfault) const
467 { return (unsigned char)c == c ? (char)c : dfault; }
468
do_narrow(const wchar_t * low,const wchar_t * high,char dfault,char * dest) const469 const wchar_t* ctype<wchar_t>::do_narrow(const wchar_t* low,
470 const wchar_t* high,
471 char dfault, char* dest) const {
472 while (low != high) {
473 wchar_t c = *low++;
474 *dest++ = (unsigned char)c == c ? (char)c : dfault;
475 }
476
477 return high;
478 }
479
480 # endif
481 _STLP_END_NAMESPACE
482
483 // Local Variables:
484 // mode:C++
485 // End:
486
487