1 //===----------------------------------------------------------------------===//
2 //
3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4 // See https://llvm.org/LICENSE.txt for license information.
5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6 //
7 //===----------------------------------------------------------------------===//
8
9 // NetBSD does not support LC_MONETARY at the moment
10 // XFAIL: netbsd
11
12 // Failure related to GLIBC's use of U00A0 as mon_thousands_sep
13 // and U002E as mon_decimal_point.
14 // TODO: U00A0 should be investigated.
15 // Possibly related to https://gcc.gnu.org/bugzilla/show_bug.cgi?id=16006
16 // XFAIL: linux
17
18 // REQUIRES: locale.ru_RU.UTF-8
19
20 // <locale>
21
22 // class money_put<charT, OutputIterator>
23
24 // iter_type put(iter_type s, bool intl, ios_base& f, char_type fill,
25 // long double units) const;
26
27 #include <locale>
28 #include <ios>
29 #include <streambuf>
30 #include <cassert>
31 #include "test_macros.h"
32 #include "test_iterators.h"
33
34 #include "platform_support.h" // locale name macros
35
36 // TODO:
37 // Some of the assertions in this test are failing on Apple platforms.
38 // Until we figure out the problem and fix it, disable these tests on
39 // Apple platforms. Note that we're not using XFAIL or UNSUPPORTED markup
40 // here, because this test would otherwise be disabled on all platforms
41 // we test. To avoid this test becoming entirely stale, we just disable
42 // the parts that fail.
43 //
44 // See https://llvm.org/PR45739 for the bug tracking this.
45 #if defined(__APPLE__)
46 # define APPLE_FIXME
47 #endif
48
49 typedef std::money_put<char, output_iterator<char*> > Fn;
50
51 class my_facet
52 : public Fn
53 {
54 public:
my_facet(std::size_t refs=0)55 explicit my_facet(std::size_t refs = 0)
56 : Fn(refs) {}
57 };
58
59 typedef std::money_put<wchar_t, output_iterator<wchar_t*> > Fw;
60
61 class my_facetw
62 : public Fw
63 {
64 public:
my_facetw(std::size_t refs=0)65 explicit my_facetw(std::size_t refs = 0)
66 : Fw(refs) {}
67 };
68
main(int,char **)69 int main(int, char**)
70 {
71 std::ios ios(0);
72 std::string loc_name(LOCALE_ru_RU_UTF_8);
73 ios.imbue(std::locale(ios.getloc(),
74 new std::moneypunct_byname<char, false>(loc_name)));
75 ios.imbue(std::locale(ios.getloc(),
76 new std::moneypunct_byname<char, true>(loc_name)));
77 ios.imbue(std::locale(ios.getloc(),
78 new std::moneypunct_byname<wchar_t, false>(loc_name)));
79 ios.imbue(std::locale(ios.getloc(),
80 new std::moneypunct_byname<wchar_t, true>(loc_name)));
81 {
82 const my_facet f(1);
83 // char, national
84 #if !defined(APPLE_FIXME)
85 { // zero
86 long double v = 0;
87 char str[100];
88 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
89 false, ios, '*', v);
90 std::string ex(str, iter.base());
91 assert(ex == "0,00 ");
92 }
93 { // negative one
94 long double v = -1;
95 char str[100];
96 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
97 false, ios, '*', v);
98 std::string ex(str, iter.base());
99 assert(ex == "-0,01 ");
100 }
101 { // positive
102 long double v = 123456789;
103 char str[100];
104 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
105 false, ios, '*', v);
106 std::string ex(str, iter.base());
107 assert(ex == "1 234 567,89 ");
108 }
109 { // negative
110 long double v = -123456789;
111 char str[100];
112 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
113 false, ios, '*', v);
114 std::string ex(str, iter.base());
115 assert(ex == "-1 234 567,89 ");
116 }
117 #endif
118 { // zero, showbase
119 long double v = 0;
120 showbase(ios);
121 char str[100];
122 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
123 false, ios, '*', v);
124 std::string ex(str, iter.base());
125 assert(ex == "0,00 \xD1\x80\xD1\x83\xD0\xB1"".");
126 }
127 { // negative one, showbase
128 long double v = -1;
129 showbase(ios);
130 char str[100];
131 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
132 false, ios, '*', v);
133 std::string ex(str, iter.base());
134 assert(ex == "-0,01 \xD1\x80\xD1\x83\xD0\xB1"".");
135 }
136 { // positive, showbase
137 long double v = 123456789;
138 showbase(ios);
139 char str[100];
140 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
141 false, ios, '*', v);
142 std::string ex(str, iter.base());
143 assert(ex == "1 234 567,89 \xD1\x80\xD1\x83\xD0\xB1"".");
144 }
145 { // negative, showbase
146 long double v = -123456789;
147 showbase(ios);
148 char str[100];
149 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
150 false, ios, '*', v);
151 std::string ex(str, iter.base());
152 assert(ex == "-1 234 567,89 \xD1\x80\xD1\x83\xD0\xB1"".");
153 }
154 { // negative, showbase, left
155 long double v = -123456789;
156 showbase(ios);
157 ios.width(20);
158 left(ios);
159 char str[100];
160 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
161 false, ios, ' ', v);
162 std::string ex(str, iter.base());
163 assert(ex == "-1 234 567,89 \xD1\x80\xD1\x83\xD0\xB1"".");
164 assert(ios.width() == 0);
165 }
166 { // negative, showbase, internal
167 long double v = -123456789;
168 showbase(ios);
169 ios.width(20);
170 internal(ios);
171 char str[100];
172 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
173 false, ios, ' ', v);
174 std::string ex(str, iter.base());
175 assert(ex == "-1 234 567,89 \xD1\x80\xD1\x83\xD0\xB1"".");
176 assert(ios.width() == 0);
177 }
178 { // negative, showbase, right
179 long double v = -123456789;
180 showbase(ios);
181 ios.width(20);
182 right(ios);
183 char str[100];
184 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
185 false, ios, ' ', v);
186 std::string ex(str, iter.base());
187 assert(ex == "-1 234 567,89 \xD1\x80\xD1\x83\xD0\xB1"".");
188 assert(ios.width() == 0);
189 }
190
191 // char, international
192 noshowbase(ios);
193 ios.unsetf(std::ios_base::adjustfield);
194 #if !defined(APPLE_FIXME)
195 { // zero
196 long double v = 0;
197 char str[100];
198 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
199 true, ios, '*', v);
200 std::string ex(str, iter.base());
201 assert(ex == "0,00 ");
202 }
203 { // negative one
204 long double v = -1;
205 char str[100];
206 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
207 true, ios, '*', v);
208 std::string ex(str, iter.base());
209 assert(ex == "-0,01 ");
210 }
211 { // positive
212 long double v = 123456789;
213 char str[100];
214 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
215 true, ios, '*', v);
216 std::string ex(str, iter.base());
217 assert(ex == "1 234 567,89 ");
218 }
219 { // negative
220 long double v = -123456789;
221 char str[100];
222 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
223 true, ios, '*', v);
224 std::string ex(str, iter.base());
225 assert(ex == "-1 234 567,89 ");
226 }
227 { // zero, showbase
228 long double v = 0;
229 showbase(ios);
230 char str[100];
231 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
232 true, ios, '*', v);
233 std::string ex(str, iter.base());
234 assert(ex == "0,00 RUB ");
235 }
236 { // negative one, showbase
237 long double v = -1;
238 showbase(ios);
239 char str[100];
240 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
241 true, ios, '*', v);
242 std::string ex(str, iter.base());
243 assert(ex == "-0,01 RUB ");
244 }
245 { // positive, showbase
246 long double v = 123456789;
247 showbase(ios);
248 char str[100];
249 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
250 true, ios, '*', v);
251 std::string ex(str, iter.base());
252 assert(ex == "1 234 567,89 RUB ");
253 }
254 { // negative, showbase
255 long double v = -123456789;
256 showbase(ios);
257 char str[100];
258 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
259 true, ios, '*', v);
260 std::string ex(str, iter.base());
261 assert(ex == "-1 234 567,89 RUB ");
262 }
263 #endif
264 { // negative, showbase, left
265 long double v = -123456789;
266 showbase(ios);
267 ios.width(20);
268 left(ios);
269 char str[100];
270 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
271 true, ios, ' ', v);
272 std::string ex(str, iter.base());
273 assert(ex == "-1 234 567,89 RUB ");
274 assert(ios.width() == 0);
275 }
276 #if !defined(APPLE_FIXME)
277 { // negative, showbase, internal
278 long double v = -123456789;
279 showbase(ios);
280 ios.width(20);
281 internal(ios);
282 char str[100];
283 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
284 true, ios, ' ', v);
285 std::string ex(str, iter.base());
286 assert(ex == "-1 234 567,89 RUB ");
287 assert(ios.width() == 0);
288 }
289 { // negative, showbase, right
290 long double v = -123456789;
291 showbase(ios);
292 ios.width(20);
293 right(ios);
294 char str[100];
295 output_iterator<char*> iter = f.put(output_iterator<char*>(str),
296 true, ios, ' ', v);
297 std::string ex(str, iter.base());
298 assert(ex == " -1 234 567,89 RUB ");
299 assert(ios.width() == 0);
300 }
301 #endif
302 }
303 {
304 const my_facetw f(1);
305 // wchar_t, national
306 noshowbase(ios);
307 ios.unsetf(std::ios_base::adjustfield);
308 #if !defined(APPLE_FIXME)
309 { // zero
310 long double v = 0;
311 wchar_t str[100];
312 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
313 false, ios, '*', v);
314 std::wstring ex(str, iter.base());
315 assert(ex == L"0,00 ");
316 }
317 { // negative one
318 long double v = -1;
319 wchar_t str[100];
320 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
321 false, ios, '*', v);
322 std::wstring ex(str, iter.base());
323 assert(ex == L"-0,01 ");
324 }
325 { // positive
326 long double v = 123456789;
327 wchar_t str[100];
328 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
329 false, ios, '*', v);
330 std::wstring ex(str, iter.base());
331 assert(ex == L"1 234 567,89 ");
332 }
333 { // negative
334 long double v = -123456789;
335 wchar_t str[100];
336 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
337 false, ios, '*', v);
338 std::wstring ex(str, iter.base());
339 assert(ex == L"-1 234 567,89 ");
340 }
341 #endif
342 { // zero, showbase
343 long double v = 0;
344 showbase(ios);
345 wchar_t str[100];
346 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
347 false, ios, '*', v);
348 std::wstring ex(str, iter.base());
349 assert(ex == L"0,00 \x440\x443\x431"".");
350 }
351 { // negative one, showbase
352 long double v = -1;
353 showbase(ios);
354 wchar_t str[100];
355 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
356 false, ios, '*', v);
357 std::wstring ex(str, iter.base());
358 assert(ex == L"-0,01 \x440\x443\x431"".");
359 }
360 { // positive, showbase
361 long double v = 123456789;
362 showbase(ios);
363 wchar_t str[100];
364 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
365 false, ios, '*', v);
366 std::wstring ex(str, iter.base());
367 assert(ex == L"1 234 567,89 \x440\x443\x431"".");
368 }
369 { // negative, showbase
370 long double v = -123456789;
371 showbase(ios);
372 wchar_t str[100];
373 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
374 false, ios, '*', v);
375 std::wstring ex(str, iter.base());
376 assert(ex == L"-1 234 567,89 \x440\x443\x431"".");
377 }
378 { // negative, showbase, left
379 long double v = -123456789;
380 showbase(ios);
381 ios.width(20);
382 left(ios);
383 wchar_t str[100];
384 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
385 false, ios, ' ', v);
386 std::wstring ex(str, iter.base());
387 assert(ex == L"-1 234 567,89 \x440\x443\x431"". ");
388 assert(ios.width() == 0);
389 }
390 { // negative, showbase, internal
391 long double v = -123456789;
392 showbase(ios);
393 ios.width(20);
394 internal(ios);
395 wchar_t str[100];
396 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
397 false, ios, ' ', v);
398 std::wstring ex(str, iter.base());
399 assert(ex == L"-1 234 567,89 \x440\x443\x431"".");
400 assert(ios.width() == 0);
401 }
402 { // negative, showbase, right
403 long double v = -123456789;
404 showbase(ios);
405 ios.width(20);
406 right(ios);
407 wchar_t str[100];
408 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
409 false, ios, ' ', v);
410 std::wstring ex(str, iter.base());
411 assert(ex == L" -1 234 567,89 \x440\x443\x431"".");
412 assert(ios.width() == 0);
413 }
414
415 // wchar_t, international
416 noshowbase(ios);
417 ios.unsetf(std::ios_base::adjustfield);
418 #if !defined(APPLE_FIXME)
419 { // zero
420 long double v = 0;
421 wchar_t str[100];
422 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
423 true, ios, '*', v);
424 std::wstring ex(str, iter.base());
425 assert(ex == L"0,00 ");
426 }
427 { // negative one
428 long double v = -1;
429 wchar_t str[100];
430 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
431 true, ios, '*', v);
432 std::wstring ex(str, iter.base());
433 assert(ex == L"-0,01 ");
434 }
435 { // positive
436 long double v = 123456789;
437 wchar_t str[100];
438 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
439 true, ios, '*', v);
440 std::wstring ex(str, iter.base());
441 assert(ex == L"1 234 567,89 ");
442 }
443 { // negative
444 long double v = -123456789;
445 wchar_t str[100];
446 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
447 true, ios, '*', v);
448 std::wstring ex(str, iter.base());
449 assert(ex == L"-1 234 567,89 ");
450 }
451 { // zero, showbase
452 long double v = 0;
453 showbase(ios);
454 wchar_t str[100];
455 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
456 true, ios, '*', v);
457 std::wstring ex(str, iter.base());
458 assert(ex == L"0,00 RUB ");
459 }
460 { // negative one, showbase
461 long double v = -1;
462 showbase(ios);
463 wchar_t str[100];
464 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
465 true, ios, '*', v);
466 std::wstring ex(str, iter.base());
467 assert(ex == L"-0,01 RUB ");
468 }
469 { // positive, showbase
470 long double v = 123456789;
471 showbase(ios);
472 wchar_t str[100];
473 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
474 true, ios, '*', v);
475 std::wstring ex(str, iter.base());
476 assert(ex == L"1 234 567,89 RUB ");
477 }
478 { // negative, showbase
479 long double v = -123456789;
480 showbase(ios);
481 wchar_t str[100];
482 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
483 true, ios, '*', v);
484 std::wstring ex(str, iter.base());
485 assert(ex == L"-1 234 567,89 RUB ");
486 }
487 #endif
488 { // negative, showbase, left
489 long double v = -123456789;
490 showbase(ios);
491 ios.width(20);
492 left(ios);
493 wchar_t str[100];
494 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
495 true, ios, ' ', v);
496 std::wstring ex(str, iter.base());
497 assert(ex == L"-1 234 567,89 RUB ");
498 assert(ios.width() == 0);
499 }
500 #if !defined(APPLE_FIXME)
501 { // negative, showbase, internal
502 long double v = -123456789;
503 showbase(ios);
504 ios.width(20);
505 internal(ios);
506 wchar_t str[100];
507 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
508 true, ios, ' ', v);
509 std::wstring ex(str, iter.base());
510 assert(ex == L"-1 234 567,89 RUB ");
511 assert(ios.width() == 0);
512 }
513 { // negative, showbase, right
514 long double v = -123456789;
515 showbase(ios);
516 ios.width(20);
517 right(ios);
518 wchar_t str[100];
519 output_iterator<wchar_t*> iter = f.put(output_iterator<wchar_t*>(str),
520 true, ios, ' ', v);
521 std::wstring ex(str, iter.base());
522 assert(ex == L" -1 234 567,89 RUB ");
523 assert(ios.width() == 0);
524 }
525 #endif
526 }
527
528 return 0;
529 }
530