]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - contrib/libc++/src/locale.cpp
Merge llvm, clang, lld, lldb, compiler-rt and libc++ r302418, and update
[FreeBSD/FreeBSD.git] / contrib / libc++ / src / locale.cpp
1 //===------------------------- locale.cpp ---------------------------------===//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is dual licensed under the MIT and the University of Illinois Open
6 // Source Licenses. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9
10 // On Solaris, we need to define something to make the C99 parts of localeconv
11 // visible.
12 #ifdef __sun__
13 #define _LCONV_C99
14 #endif
15
16 #include "string"
17 #include "locale"
18 #include "codecvt"
19 #include "vector"
20 #include "algorithm"
21 #include "typeinfo"
22 #ifndef _LIBCPP_NO_EXCEPTIONS
23 #  include "type_traits"
24 #endif
25 #include "clocale"
26 #include "cstring"
27 #if defined(_LIBCPP_MSVCRT)
28 #define _CTYPE_DISABLE_MACROS
29 #endif
30 #include "cwctype"
31 #include "__sso_allocator"
32 #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
33 #include "support/win32/locale_win32.h"
34 #elif !defined(__BIONIC__)
35 #include <langinfo.h>
36 #endif
37 #include <stdlib.h>
38 #include <stdio.h>
39
40 // On Linux, wint_t and wchar_t have different signed-ness, and this causes
41 // lots of noise in the build log, but no bugs that I know of. 
42 #if defined(__clang__)
43 #pragma clang diagnostic ignored "-Wsign-conversion"
44 #endif
45
46 _LIBCPP_BEGIN_NAMESPACE_STD
47
48 #ifdef __cloc_defined
49 locale_t __cloc() {
50   // In theory this could create a race condition. In practice
51   // the race condition is non-fatal since it will just create
52   // a little resource leak. Better approach would be appreciated.
53   static locale_t result = newlocale(LC_ALL_MASK, "C", 0);
54   return result;
55 }
56 #endif // __cloc_defined
57
58 namespace {
59
60 struct release
61 {
62     void operator()(locale::facet* p) {p->__release_shared();}
63 };
64
65 template <class T, class A0>
66 inline
67 T&
68 make(A0 a0)
69 {
70     static typename aligned_storage<sizeof(T)>::type buf;
71     auto *obj = ::new (&buf) T(a0);
72     return *obj;
73 }
74
75 template <class T, class A0, class A1>
76 inline
77 T&
78 make(A0 a0, A1 a1)
79 {
80     static typename aligned_storage<sizeof(T)>::type buf;
81     ::new (&buf) T(a0, a1);
82     return *reinterpret_cast<T*>(&buf);
83 }
84
85 template <class T, class A0, class A1, class A2>
86 inline
87 T&
88 make(A0 a0, A1 a1, A2 a2)
89 {
90     static typename aligned_storage<sizeof(T)>::type buf;
91     auto *obj = ::new (&buf) T(a0, a1, a2);
92     return *obj;
93 }
94
95 template <typename T, size_t N>
96 inline
97 _LIBCPP_CONSTEXPR
98 size_t
99 countof(const T (&)[N])
100 {
101     return N;
102 }
103
104 template <typename T>
105 inline
106 _LIBCPP_CONSTEXPR
107 size_t
108 countof(const T * const begin, const T * const end)
109 {
110     return static_cast<size_t>(end - begin);
111 }
112
113 _LIBCPP_NORETURN static void __throw_runtime_error(const string &msg)
114 {
115 #ifndef _LIBCPP_NO_EXCEPTIONS
116     throw runtime_error(msg);
117 #else
118     (void)msg;
119     _VSTD::abort();
120 #endif
121 }
122
123 }
124
125 #if defined(_AIX)
126 // Set priority to INT_MIN + 256 + 150
127 # pragma priority ( -2147483242 )
128 #endif
129
130 const locale::category locale::none;
131 const locale::category locale::collate;
132 const locale::category locale::ctype;
133 const locale::category locale::monetary;
134 const locale::category locale::numeric;
135 const locale::category locale::time;
136 const locale::category locale::messages;
137 const locale::category locale::all;
138
139 class _LIBCPP_HIDDEN locale::__imp
140     : public facet
141 {
142     enum {N = 28};
143 #if defined(_LIBCPP_COMPILER_MSVC)
144 // FIXME: MSVC doesn't support aligned parameters by value.
145 // I can't get the __sso_allocator to work here
146 // for MSVC I think for this reason.
147     vector<facet*> facets_;
148 #else
149     vector<facet*, __sso_allocator<facet*, N> > facets_;
150 #endif
151     string         name_;
152 public:
153     explicit __imp(size_t refs = 0);
154     explicit __imp(const string& name, size_t refs = 0);
155     __imp(const __imp&);
156     __imp(const __imp&, const string&, locale::category c);
157     __imp(const __imp& other, const __imp& one, locale::category c);
158     __imp(const __imp&, facet* f, long id);
159     ~__imp();
160
161     const string& name() const {return name_;}
162     bool has_facet(long id) const
163         {return static_cast<size_t>(id) < facets_.size() && facets_[static_cast<size_t>(id)];}
164     const locale::facet* use_facet(long id) const;
165
166     static const locale& make_classic();
167     static       locale& make_global();
168 private:
169     void install(facet* f, long id);
170     template <class F> void install(F* f) {install(f, f->id.__get());}
171     template <class F> void install_from(const __imp& other);
172 };
173
174 locale::__imp::__imp(size_t refs)
175     : facet(refs),
176       facets_(N),
177       name_("C")
178 {
179     facets_.clear();
180     install(&make<_VSTD::collate<char> >(1u));
181     install(&make<_VSTD::collate<wchar_t> >(1u));
182     install(&make<_VSTD::ctype<char> >(nullptr, false, 1u));
183     install(&make<_VSTD::ctype<wchar_t> >(1u));
184     install(&make<codecvt<char, char, mbstate_t> >(1u));
185     install(&make<codecvt<wchar_t, char, mbstate_t> >(1u));
186     install(&make<codecvt<char16_t, char, mbstate_t> >(1u));
187     install(&make<codecvt<char32_t, char, mbstate_t> >(1u));
188     install(&make<numpunct<char> >(1u));
189     install(&make<numpunct<wchar_t> >(1u));
190     install(&make<num_get<char> >(1u));
191     install(&make<num_get<wchar_t> >(1u));
192     install(&make<num_put<char> >(1u));
193     install(&make<num_put<wchar_t> >(1u));
194     install(&make<moneypunct<char, false> >(1u));
195     install(&make<moneypunct<char, true> >(1u));
196     install(&make<moneypunct<wchar_t, false> >(1u));
197     install(&make<moneypunct<wchar_t, true> >(1u));
198     install(&make<money_get<char> >(1u));
199     install(&make<money_get<wchar_t> >(1u));
200     install(&make<money_put<char> >(1u));
201     install(&make<money_put<wchar_t> >(1u));
202     install(&make<time_get<char> >(1u));
203     install(&make<time_get<wchar_t> >(1u));
204     install(&make<time_put<char> >(1u));
205     install(&make<time_put<wchar_t> >(1u));
206     install(&make<_VSTD::messages<char> >(1u));
207     install(&make<_VSTD::messages<wchar_t> >(1u));
208 }
209
210 locale::__imp::__imp(const string& name, size_t refs)
211     : facet(refs),
212       facets_(N),
213       name_(name)
214 {
215 #ifndef _LIBCPP_NO_EXCEPTIONS
216     try
217     {
218 #endif  // _LIBCPP_NO_EXCEPTIONS
219         facets_ = locale::classic().__locale_->facets_;
220         for (unsigned i = 0; i < facets_.size(); ++i)
221             if (facets_[i])
222                 facets_[i]->__add_shared();
223         install(new collate_byname<char>(name_));
224         install(new collate_byname<wchar_t>(name_));
225         install(new ctype_byname<char>(name_));
226         install(new ctype_byname<wchar_t>(name_));
227         install(new codecvt_byname<char, char, mbstate_t>(name_));
228         install(new codecvt_byname<wchar_t, char, mbstate_t>(name_));
229         install(new codecvt_byname<char16_t, char, mbstate_t>(name_));
230         install(new codecvt_byname<char32_t, char, mbstate_t>(name_));
231         install(new numpunct_byname<char>(name_));
232         install(new numpunct_byname<wchar_t>(name_));
233         install(new moneypunct_byname<char, false>(name_));
234         install(new moneypunct_byname<char, true>(name_));
235         install(new moneypunct_byname<wchar_t, false>(name_));
236         install(new moneypunct_byname<wchar_t, true>(name_));
237         install(new time_get_byname<char>(name_));
238         install(new time_get_byname<wchar_t>(name_));
239         install(new time_put_byname<char>(name_));
240         install(new time_put_byname<wchar_t>(name_));
241         install(new messages_byname<char>(name_));
242         install(new messages_byname<wchar_t>(name_));
243 #ifndef _LIBCPP_NO_EXCEPTIONS
244     }
245     catch (...)
246     {
247         for (unsigned i = 0; i < facets_.size(); ++i)
248             if (facets_[i])
249                 facets_[i]->__release_shared();
250         throw;
251     }
252 #endif  // _LIBCPP_NO_EXCEPTIONS
253 }
254
255 // NOTE avoid the `base class should be explicitly initialized in the
256 // copy constructor` warning emitted by GCC
257 #if defined(__clang__) || _GNUC_VER >= 406
258 #pragma GCC diagnostic push
259 #pragma GCC diagnostic ignored "-Wextra"
260 #endif
261
262 locale::__imp::__imp(const __imp& other)
263     : facets_(max<size_t>(N, other.facets_.size())),
264       name_(other.name_)
265 {
266     facets_ = other.facets_;
267     for (unsigned i = 0; i < facets_.size(); ++i)
268         if (facets_[i])
269             facets_[i]->__add_shared();
270 }
271
272 #if defined(__clang__) || _GNUC_VER >= 406
273 #pragma GCC diagnostic pop
274 #endif
275
276 locale::__imp::__imp(const __imp& other, const string& name, locale::category c)
277     : facets_(N),
278       name_("*")
279 {
280     facets_ = other.facets_;
281     for (unsigned i = 0; i < facets_.size(); ++i)
282         if (facets_[i])
283             facets_[i]->__add_shared();
284 #ifndef _LIBCPP_NO_EXCEPTIONS
285     try
286     {
287 #endif  // _LIBCPP_NO_EXCEPTIONS
288         if (c & locale::collate)
289         {
290             install(new collate_byname<char>(name));
291             install(new collate_byname<wchar_t>(name));
292         }
293         if (c & locale::ctype)
294         {
295             install(new ctype_byname<char>(name));
296             install(new ctype_byname<wchar_t>(name));
297             install(new codecvt_byname<char, char, mbstate_t>(name));
298             install(new codecvt_byname<wchar_t, char, mbstate_t>(name));
299             install(new codecvt_byname<char16_t, char, mbstate_t>(name));
300             install(new codecvt_byname<char32_t, char, mbstate_t>(name));
301         }
302         if (c & locale::monetary)
303         {
304             install(new moneypunct_byname<char, false>(name));
305             install(new moneypunct_byname<char, true>(name));
306             install(new moneypunct_byname<wchar_t, false>(name));
307             install(new moneypunct_byname<wchar_t, true>(name));
308         }
309         if (c & locale::numeric)
310         {
311             install(new numpunct_byname<char>(name));
312             install(new numpunct_byname<wchar_t>(name));
313         }
314         if (c & locale::time)
315         {
316             install(new time_get_byname<char>(name));
317             install(new time_get_byname<wchar_t>(name));
318             install(new time_put_byname<char>(name));
319             install(new time_put_byname<wchar_t>(name));
320         }
321         if (c & locale::messages)
322         {
323             install(new messages_byname<char>(name));
324             install(new messages_byname<wchar_t>(name));
325         }
326 #ifndef _LIBCPP_NO_EXCEPTIONS
327     }
328     catch (...)
329     {
330         for (unsigned i = 0; i < facets_.size(); ++i)
331             if (facets_[i])
332                 facets_[i]->__release_shared();
333         throw;
334     }
335 #endif  // _LIBCPP_NO_EXCEPTIONS
336 }
337
338 template<class F>
339 inline
340 void
341 locale::__imp::install_from(const locale::__imp& one)
342 {
343     long id = F::id.__get();
344     install(const_cast<F*>(static_cast<const F*>(one.use_facet(id))), id);
345 }
346
347 locale::__imp::__imp(const __imp& other, const __imp& one, locale::category c)
348     : facets_(N),
349       name_("*")
350 {
351     facets_ = other.facets_;
352     for (unsigned i = 0; i < facets_.size(); ++i)
353         if (facets_[i])
354             facets_[i]->__add_shared();
355 #ifndef _LIBCPP_NO_EXCEPTIONS
356     try
357     {
358 #endif  // _LIBCPP_NO_EXCEPTIONS
359         if (c & locale::collate)
360         {
361             install_from<_VSTD::collate<char> >(one);
362             install_from<_VSTD::collate<wchar_t> >(one);
363         }
364         if (c & locale::ctype)
365         {
366             install_from<_VSTD::ctype<char> >(one);
367             install_from<_VSTD::ctype<wchar_t> >(one);
368             install_from<_VSTD::codecvt<char, char, mbstate_t> >(one);
369             install_from<_VSTD::codecvt<char16_t, char, mbstate_t> >(one);
370             install_from<_VSTD::codecvt<char32_t, char, mbstate_t> >(one);
371             install_from<_VSTD::codecvt<wchar_t, char, mbstate_t> >(one);
372         }
373         if (c & locale::monetary)
374         {
375             install_from<moneypunct<char, false> >(one);
376             install_from<moneypunct<char, true> >(one);
377             install_from<moneypunct<wchar_t, false> >(one);
378             install_from<moneypunct<wchar_t, true> >(one);
379             install_from<money_get<char> >(one);
380             install_from<money_get<wchar_t> >(one);
381             install_from<money_put<char> >(one);
382             install_from<money_put<wchar_t> >(one);
383         }
384         if (c & locale::numeric)
385         {
386             install_from<numpunct<char> >(one);
387             install_from<numpunct<wchar_t> >(one);
388             install_from<num_get<char> >(one);
389             install_from<num_get<wchar_t> >(one);
390             install_from<num_put<char> >(one);
391             install_from<num_put<wchar_t> >(one);
392         }
393         if (c & locale::time)
394         {
395             install_from<time_get<char> >(one);
396             install_from<time_get<wchar_t> >(one);
397             install_from<time_put<char> >(one);
398             install_from<time_put<wchar_t> >(one);
399         }
400         if (c & locale::messages)
401         {
402             install_from<_VSTD::messages<char> >(one);
403             install_from<_VSTD::messages<wchar_t> >(one);
404         }
405 #ifndef _LIBCPP_NO_EXCEPTIONS
406     }
407     catch (...)
408     {
409         for (unsigned i = 0; i < facets_.size(); ++i)
410             if (facets_[i])
411                 facets_[i]->__release_shared();
412         throw;
413     }
414 #endif  // _LIBCPP_NO_EXCEPTIONS
415 }
416
417 locale::__imp::__imp(const __imp& other, facet* f, long id)
418     : facets_(max<size_t>(N, other.facets_.size()+1)),
419       name_("*")
420 {
421     f->__add_shared();
422     unique_ptr<facet, release> hold(f);
423     facets_ = other.facets_;
424     for (unsigned i = 0; i < other.facets_.size(); ++i)
425         if (facets_[i])
426             facets_[i]->__add_shared();
427     install(hold.get(), id);
428 }
429
430 locale::__imp::~__imp()
431 {
432     for (unsigned i = 0; i < facets_.size(); ++i)
433         if (facets_[i])
434             facets_[i]->__release_shared();
435 }
436
437 void
438 locale::__imp::install(facet* f, long id)
439 {
440     f->__add_shared();
441     unique_ptr<facet, release> hold(f);
442     if (static_cast<size_t>(id) >= facets_.size())
443         facets_.resize(static_cast<size_t>(id+1));
444     if (facets_[static_cast<size_t>(id)])
445         facets_[static_cast<size_t>(id)]->__release_shared();
446     facets_[static_cast<size_t>(id)] = hold.release();
447 }
448
449 const locale::facet*
450 locale::__imp::use_facet(long id) const
451 {
452 #ifndef _LIBCPP_NO_EXCEPTIONS
453     if (!has_facet(id))
454         throw bad_cast();
455 #endif  // _LIBCPP_NO_EXCEPTIONS
456     return facets_[static_cast<size_t>(id)];
457 }
458
459 // locale
460
461 const locale&
462 locale::__imp::make_classic()
463 {
464     // only one thread can get in here and it only gets in once
465     static aligned_storage<sizeof(locale)>::type buf;
466     locale* c = reinterpret_cast<locale*>(&buf);
467     c->__locale_ = &make<__imp>(1u);
468     return *c;
469 }
470
471 const locale&
472 locale::classic()
473 {
474     static const locale& c = __imp::make_classic();
475     return c;
476 }
477
478 locale&
479 locale::__imp::make_global()
480 {
481     // only one thread can get in here and it only gets in once
482     static aligned_storage<sizeof(locale)>::type buf;
483     auto *obj = ::new (&buf) locale(locale::classic());
484     return *obj;
485 }
486
487 locale&
488 locale::__global()
489 {
490     static locale& g = __imp::make_global();
491     return g;
492 }
493
494 locale::locale()  _NOEXCEPT
495     : __locale_(__global().__locale_)
496 {
497     __locale_->__add_shared();
498 }
499
500 locale::locale(const locale& l)  _NOEXCEPT
501     : __locale_(l.__locale_)
502 {
503     __locale_->__add_shared();
504 }
505
506 locale::~locale()
507 {
508     __locale_->__release_shared();
509 }
510
511 const locale&
512 locale::operator=(const locale& other)  _NOEXCEPT
513 {
514     other.__locale_->__add_shared();
515     __locale_->__release_shared();
516     __locale_ = other.__locale_;
517     return *this;
518 }
519
520 locale::locale(const char* name)
521 #ifndef _LIBCPP_NO_EXCEPTIONS
522     : __locale_(name ? new __imp(name)
523                      : throw runtime_error("locale constructed with null"))
524 #else  // _LIBCPP_NO_EXCEPTIONS
525     : __locale_(new __imp(name))
526 #endif
527 {
528     __locale_->__add_shared();
529 }
530
531 locale::locale(const string& name)
532     : __locale_(new __imp(name))
533 {
534     __locale_->__add_shared();
535 }
536
537 locale::locale(const locale& other, const char* name, category c)
538 #ifndef _LIBCPP_NO_EXCEPTIONS
539     : __locale_(name ? new __imp(*other.__locale_, name, c)
540                      : throw runtime_error("locale constructed with null"))
541 #else  // _LIBCPP_NO_EXCEPTIONS
542     : __locale_(new __imp(*other.__locale_, name, c))
543 #endif
544 {
545     __locale_->__add_shared();
546 }
547
548 locale::locale(const locale& other, const string& name, category c)
549     : __locale_(new __imp(*other.__locale_, name, c))
550 {
551     __locale_->__add_shared();
552 }
553
554 locale::locale(const locale& other, const locale& one, category c)
555     : __locale_(new __imp(*other.__locale_, *one.__locale_, c))
556 {
557     __locale_->__add_shared();
558 }
559
560 string
561 locale::name() const
562 {
563     return __locale_->name();
564 }
565
566 void
567 locale::__install_ctor(const locale& other, facet* f, long id)
568 {
569     if (f)
570         __locale_ = new __imp(*other.__locale_, f, id);
571     else
572         __locale_ = other.__locale_;
573     __locale_->__add_shared();
574 }
575
576 locale
577 locale::global(const locale& loc)
578 {
579     locale& g = __global();
580     locale r = g;
581     g = loc;
582     if (g.name() != "*")
583         setlocale(LC_ALL, g.name().c_str());
584     return r;
585 }
586
587 bool
588 locale::has_facet(id& x) const
589 {
590     return __locale_->has_facet(x.__get());
591 }
592
593 const locale::facet*
594 locale::use_facet(id& x) const
595 {
596     return __locale_->use_facet(x.__get());
597 }
598
599 bool
600 locale::operator==(const locale& y) const
601 {
602     return (__locale_ == y.__locale_)
603         || (__locale_->name() != "*" && __locale_->name() == y.__locale_->name());
604 }
605
606 // locale::facet
607
608 locale::facet::~facet()
609 {
610 }
611
612 void
613 locale::facet::__on_zero_shared() _NOEXCEPT
614 {
615     delete this;
616 }
617
618 // locale::id
619
620 int32_t locale::id::__next_id = 0;
621
622 namespace
623 {
624
625 class __fake_bind
626 {
627     locale::id* id_;
628     void (locale::id::* pmf_)();
629 public:
630     __fake_bind(void (locale::id::* pmf)(), locale::id* id)
631         : id_(id), pmf_(pmf) {}
632
633     void operator()() const
634     {
635         (id_->*pmf_)();
636     }
637 };
638
639 }
640
641 long
642 locale::id::__get()
643 {
644     call_once(__flag_, __fake_bind(&locale::id::__init, this));
645     return __id_ - 1;
646 }
647
648 void
649 locale::id::__init()
650 {
651     __id_ = __sync_add_and_fetch(&__next_id, 1);
652 }
653
654 // template <> class collate_byname<char>
655
656 collate_byname<char>::collate_byname(const char* n, size_t refs)
657     : collate<char>(refs),
658       __l(newlocale(LC_ALL_MASK, n, 0))
659 {
660     if (__l == 0)
661         __throw_runtime_error("collate_byname<char>::collate_byname"
662                             " failed to construct for " + string(n));
663 }
664
665 collate_byname<char>::collate_byname(const string& name, size_t refs)
666     : collate<char>(refs),
667       __l(newlocale(LC_ALL_MASK, name.c_str(), 0))
668 {
669     if (__l == 0)
670         __throw_runtime_error("collate_byname<char>::collate_byname"
671                             " failed to construct for " + name);
672 }
673
674 collate_byname<char>::~collate_byname()
675 {
676     freelocale(__l);
677 }
678
679 int
680 collate_byname<char>::do_compare(const char_type* __lo1, const char_type* __hi1,
681                                  const char_type* __lo2, const char_type* __hi2) const
682 {
683     string_type lhs(__lo1, __hi1);
684     string_type rhs(__lo2, __hi2);
685     int r = strcoll_l(lhs.c_str(), rhs.c_str(), __l);
686     if (r < 0)
687         return -1;
688     if (r > 0)
689         return 1;
690     return r;
691 }
692
693 collate_byname<char>::string_type
694 collate_byname<char>::do_transform(const char_type* lo, const char_type* hi) const
695 {
696     const string_type in(lo, hi);
697     string_type out(strxfrm_l(0, in.c_str(), 0, __l), char());
698     strxfrm_l(const_cast<char*>(out.c_str()), in.c_str(), out.size()+1, __l);
699     return out;
700 }
701
702 // template <> class collate_byname<wchar_t>
703
704 collate_byname<wchar_t>::collate_byname(const char* n, size_t refs)
705     : collate<wchar_t>(refs),
706       __l(newlocale(LC_ALL_MASK, n, 0))
707 {
708     if (__l == 0)
709         __throw_runtime_error("collate_byname<wchar_t>::collate_byname(size_t refs)"
710                             " failed to construct for " + string(n));
711 }
712
713 collate_byname<wchar_t>::collate_byname(const string& name, size_t refs)
714     : collate<wchar_t>(refs),
715       __l(newlocale(LC_ALL_MASK, name.c_str(), 0))
716 {
717     if (__l == 0)
718         __throw_runtime_error("collate_byname<wchar_t>::collate_byname(size_t refs)"
719                             " failed to construct for " + name);
720 }
721
722 collate_byname<wchar_t>::~collate_byname()
723 {
724     freelocale(__l);
725 }
726
727 int
728 collate_byname<wchar_t>::do_compare(const char_type* __lo1, const char_type* __hi1,
729                                  const char_type* __lo2, const char_type* __hi2) const
730 {
731     string_type lhs(__lo1, __hi1);
732     string_type rhs(__lo2, __hi2);
733     int r = wcscoll_l(lhs.c_str(), rhs.c_str(), __l);
734     if (r < 0)
735         return -1;
736     if (r > 0)
737         return 1;
738     return r;
739 }
740
741 collate_byname<wchar_t>::string_type
742 collate_byname<wchar_t>::do_transform(const char_type* lo, const char_type* hi) const
743 {
744     const string_type in(lo, hi);
745     string_type out(wcsxfrm_l(0, in.c_str(), 0, __l), wchar_t());
746     wcsxfrm_l(const_cast<wchar_t*>(out.c_str()), in.c_str(), out.size()+1, __l);
747     return out;
748 }
749
750 // template <> class ctype<wchar_t>;
751
752 const ctype_base::mask ctype_base::space;
753 const ctype_base::mask ctype_base::print;
754 const ctype_base::mask ctype_base::cntrl;
755 const ctype_base::mask ctype_base::upper;
756 const ctype_base::mask ctype_base::lower;
757 const ctype_base::mask ctype_base::alpha;
758 const ctype_base::mask ctype_base::digit;
759 const ctype_base::mask ctype_base::punct;
760 const ctype_base::mask ctype_base::xdigit;
761 const ctype_base::mask ctype_base::blank;
762 const ctype_base::mask ctype_base::alnum;
763 const ctype_base::mask ctype_base::graph;
764     
765 locale::id ctype<wchar_t>::id;
766
767 ctype<wchar_t>::~ctype()
768 {
769 }
770
771 bool
772 ctype<wchar_t>::do_is(mask m, char_type c) const
773 {
774     return isascii(c) ? (ctype<char>::classic_table()[c] & m) != 0 : false;
775 }
776
777 const wchar_t*
778 ctype<wchar_t>::do_is(const char_type* low, const char_type* high, mask* vec) const
779 {
780     for (; low != high; ++low, ++vec)
781         *vec = static_cast<mask>(isascii(*low) ?
782                                    ctype<char>::classic_table()[*low] : 0);
783     return low;
784 }
785
786 const wchar_t*
787 ctype<wchar_t>::do_scan_is(mask m, const char_type* low, const char_type* high) const
788 {
789     for (; low != high; ++low)
790         if (isascii(*low) && (ctype<char>::classic_table()[*low] & m))
791             break;
792     return low;
793 }
794
795 const wchar_t*
796 ctype<wchar_t>::do_scan_not(mask m, const char_type* low, const char_type* high) const
797 {
798     for (; low != high; ++low)
799         if (!(isascii(*low) && (ctype<char>::classic_table()[*low] & m)))
800             break;
801     return low;
802 }
803
804 wchar_t
805 ctype<wchar_t>::do_toupper(char_type c) const
806 {
807 #ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE
808     return isascii(c) ? _DefaultRuneLocale.__mapupper[c] : c;
809 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || \
810       defined(__NetBSD__)
811     return isascii(c) ? ctype<char>::__classic_upper_table()[c] : c;
812 #else
813     return (isascii(c) && iswlower_l(c, _LIBCPP_GET_C_LOCALE)) ? c-L'a'+L'A' : c;
814 #endif
815 }
816
817 const wchar_t*
818 ctype<wchar_t>::do_toupper(char_type* low, const char_type* high) const
819 {
820     for (; low != high; ++low)
821 #ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE
822         *low = isascii(*low) ? _DefaultRuneLocale.__mapupper[*low] : *low;
823 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || \
824       defined(__NetBSD__)
825         *low = isascii(*low) ? ctype<char>::__classic_upper_table()[*low]
826                              : *low;
827 #else
828         *low = (isascii(*low) && islower_l(*low, _LIBCPP_GET_C_LOCALE)) ? (*low-L'a'+L'A') : *low;
829 #endif
830     return low;
831 }
832
833 wchar_t
834 ctype<wchar_t>::do_tolower(char_type c) const
835 {
836 #ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE
837     return isascii(c) ? _DefaultRuneLocale.__maplower[c] : c;
838 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || \
839       defined(__NetBSD__)
840     return isascii(c) ? ctype<char>::__classic_lower_table()[c] : c;
841 #else
842     return (isascii(c) && isupper_l(c, _LIBCPP_GET_C_LOCALE)) ? c-L'A'+'a' : c;
843 #endif
844 }
845
846 const wchar_t*
847 ctype<wchar_t>::do_tolower(char_type* low, const char_type* high) const
848 {
849     for (; low != high; ++low)
850 #ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE
851         *low = isascii(*low) ? _DefaultRuneLocale.__maplower[*low] : *low;
852 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__) || \
853       defined(__NetBSD__)
854         *low = isascii(*low) ? ctype<char>::__classic_lower_table()[*low]
855                              : *low;
856 #else
857         *low = (isascii(*low) && isupper_l(*low, _LIBCPP_GET_C_LOCALE)) ? *low-L'A'+L'a' : *low;
858 #endif
859     return low;
860 }
861
862 wchar_t
863 ctype<wchar_t>::do_widen(char c) const
864 {
865     return c;
866 }
867
868 const char*
869 ctype<wchar_t>::do_widen(const char* low, const char* high, char_type* dest) const
870 {
871     for (; low != high; ++low, ++dest)
872         *dest = *low;
873     return low;
874 }
875
876 char
877 ctype<wchar_t>::do_narrow(char_type c, char dfault) const
878 {
879     if (isascii(c))
880         return static_cast<char>(c);
881     return dfault;
882 }
883
884 const wchar_t*
885 ctype<wchar_t>::do_narrow(const char_type* low, const char_type* high, char dfault, char* dest) const
886 {
887     for (; low != high; ++low, ++dest)
888         if (isascii(*low))
889             *dest = static_cast<char>(*low);
890         else
891             *dest = dfault;
892     return low;
893 }
894
895 // template <> class ctype<char>;
896
897 locale::id ctype<char>::id;
898
899 ctype<char>::ctype(const mask* tab, bool del, size_t refs)
900     : locale::facet(refs),
901       __tab_(tab),
902       __del_(del)
903 {
904   if (__tab_ == 0)
905       __tab_ = classic_table();
906 }
907
908 ctype<char>::~ctype()
909 {
910     if (__tab_ && __del_)
911         delete [] __tab_;
912 }
913
914 char
915 ctype<char>::do_toupper(char_type c) const
916 {
917 #ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE
918     return isascii(c) ?
919       static_cast<char>(_DefaultRuneLocale.__mapupper[static_cast<ptrdiff_t>(c)]) : c;
920 #elif defined(__NetBSD__)
921     return static_cast<char>(__classic_upper_table()[static_cast<unsigned char>(c)]);
922 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__)
923     return isascii(c) ?
924       static_cast<char>(__classic_upper_table()[static_cast<unsigned char>(c)]) : c;
925 #else
926     return (isascii(c) && islower_l(c, _LIBCPP_GET_C_LOCALE)) ? c-'a'+'A' : c;
927 #endif
928 }
929
930 const char*
931 ctype<char>::do_toupper(char_type* low, const char_type* high) const
932 {
933     for (; low != high; ++low)
934 #ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE
935         *low = isascii(*low) ?
936           static_cast<char>(_DefaultRuneLocale.__mapupper[static_cast<ptrdiff_t>(*low)]) : *low;
937 #elif defined(__NetBSD__)
938         *low = static_cast<char>(__classic_upper_table()[static_cast<unsigned char>(*low)]);
939 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__)
940         *low = isascii(*low) ?
941           static_cast<char>(__classic_upper_table()[static_cast<size_t>(*low)]) : *low;
942 #else
943         *low = (isascii(*low) && islower_l(*low, _LIBCPP_GET_C_LOCALE)) ? *low-'a'+'A' : *low;
944 #endif
945     return low;
946 }
947
948 char
949 ctype<char>::do_tolower(char_type c) const
950 {
951 #ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE
952     return isascii(c) ?
953       static_cast<char>(_DefaultRuneLocale.__maplower[static_cast<ptrdiff_t>(c)]) : c;
954 #elif defined(__NetBSD__)
955     return static_cast<char>(__classic_lower_table()[static_cast<unsigned char>(c)]);
956 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__)
957     return isascii(c) ?
958       static_cast<char>(__classic_lower_table()[static_cast<size_t>(c)]) : c;
959 #else
960     return (isascii(c) && isupper_l(c, _LIBCPP_GET_C_LOCALE)) ? c-'A'+'a' : c;
961 #endif
962 }
963
964 const char*
965 ctype<char>::do_tolower(char_type* low, const char_type* high) const
966 {
967     for (; low != high; ++low)
968 #ifdef _LIBCPP_HAS_DEFAULTRUNELOCALE
969         *low = isascii(*low) ? static_cast<char>(_DefaultRuneLocale.__maplower[static_cast<ptrdiff_t>(*low)]) : *low;
970 #elif defined(__NetBSD__)
971         *low = static_cast<char>(__classic_lower_table()[static_cast<unsigned char>(*low)]);
972 #elif defined(__GLIBC__) || defined(__EMSCRIPTEN__)
973         *low = isascii(*low) ? static_cast<char>(__classic_lower_table()[static_cast<size_t>(*low)]) : *low;
974 #else
975         *low = (isascii(*low) && isupper_l(*low, _LIBCPP_GET_C_LOCALE)) ? *low-'A'+'a' : *low;
976 #endif
977     return low;
978 }
979
980 char
981 ctype<char>::do_widen(char c) const
982 {
983     return c;
984 }
985
986 const char*
987 ctype<char>::do_widen(const char* low, const char* high, char_type* dest) const
988 {
989     for (; low != high; ++low, ++dest)
990         *dest = *low;
991     return low;
992 }
993
994 char
995 ctype<char>::do_narrow(char_type c, char dfault) const
996 {
997     if (isascii(c))
998         return static_cast<char>(c);
999     return dfault;
1000 }
1001
1002 const char*
1003 ctype<char>::do_narrow(const char_type* low, const char_type* high, char dfault, char* dest) const
1004 {
1005     for (; low != high; ++low, ++dest)
1006         if (isascii(*low))
1007             *dest = *low;
1008         else
1009             *dest = dfault;
1010     return low;
1011 }
1012
1013 #if defined(__EMSCRIPTEN__)
1014 extern "C" const unsigned short ** __ctype_b_loc();
1015 extern "C" const int ** __ctype_tolower_loc();
1016 extern "C" const int ** __ctype_toupper_loc();
1017 #endif
1018
1019 #ifdef _LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE
1020 const ctype<char>::mask*
1021 ctype<char>::classic_table()  _NOEXCEPT
1022 {
1023     static _LIBCPP_CONSTEXPR const ctype<char>::mask builtin_table[table_size] = {
1024         cntrl,                          cntrl,
1025         cntrl,                          cntrl,
1026         cntrl,                          cntrl,
1027         cntrl,                          cntrl,
1028         cntrl,                          cntrl | space | blank,
1029         cntrl | space,                  cntrl | space,
1030         cntrl | space,                  cntrl | space,
1031         cntrl,                          cntrl,
1032         cntrl,                          cntrl,
1033         cntrl,                          cntrl,
1034         cntrl,                          cntrl,
1035         cntrl,                          cntrl,
1036         cntrl,                          cntrl,
1037         cntrl,                          cntrl,
1038         cntrl,                          cntrl,
1039         cntrl,                          cntrl,
1040         space | blank | print,          punct | print,
1041         punct | print,                  punct | print,
1042         punct | print,                  punct | print,
1043         punct | print,                  punct | print,
1044         punct | print,                  punct | print,
1045         punct | print,                  punct | print,
1046         punct | print,                  punct | print,
1047         punct | print,                  punct | print,
1048         digit | print | xdigit,         digit | print | xdigit,
1049         digit | print | xdigit,         digit | print | xdigit,
1050         digit | print | xdigit,         digit | print | xdigit,
1051         digit | print | xdigit,         digit | print | xdigit,
1052         digit | print | xdigit,         digit | print | xdigit,
1053         punct | print,                  punct | print,
1054         punct | print,                  punct | print,
1055         punct | print,                  punct | print,
1056         punct | print,                  upper | xdigit | print | alpha,
1057         upper | xdigit | print | alpha, upper | xdigit | print | alpha,
1058         upper | xdigit | print | alpha, upper | xdigit | print | alpha,
1059         upper | xdigit | print | alpha, upper | print | alpha,
1060         upper | print | alpha,          upper | print | alpha,
1061         upper | print | alpha,          upper | print | alpha,
1062         upper | print | alpha,          upper | print | alpha,
1063         upper | print | alpha,          upper | print | alpha,
1064         upper | print | alpha,          upper | print | alpha,
1065         upper | print | alpha,          upper | print | alpha,
1066         upper | print | alpha,          upper | print | alpha,
1067         upper | print | alpha,          upper | print | alpha,
1068         upper | print | alpha,          upper | print | alpha,
1069         upper | print | alpha,          punct | print,
1070         punct | print,                  punct | print,
1071         punct | print,                  punct | print,
1072         punct | print,                  lower | xdigit | print | alpha,
1073         lower | xdigit | print | alpha, lower | xdigit | print | alpha,
1074         lower | xdigit | print | alpha, lower | xdigit | print | alpha,
1075         lower | xdigit | print | alpha, lower | print | alpha,
1076         lower | print | alpha,          lower | print | alpha,
1077         lower | print | alpha,          lower | print | alpha,
1078         lower | print | alpha,          lower | print | alpha,
1079         lower | print | alpha,          lower | print | alpha,
1080         lower | print | alpha,          lower | print | alpha,
1081         lower | print | alpha,          lower | print | alpha,
1082         lower | print | alpha,          lower | print | alpha,
1083         lower | print | alpha,          lower | print | alpha,
1084         lower | print | alpha,          lower | print | alpha,
1085         lower | print | alpha,          punct | print,
1086         punct | print,                  punct | print,
1087         punct | print,                  cntrl,
1088         0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1089         0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1090         0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1091         0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1092         0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1093         0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1094         0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1095         0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
1096     };
1097     return builtin_table;
1098 }
1099 #else
1100 const ctype<char>::mask*
1101 ctype<char>::classic_table()  _NOEXCEPT
1102 {
1103 #if defined(__APPLE__) || defined(__FreeBSD__)
1104     return _DefaultRuneLocale.__runetype;
1105 #elif defined(__NetBSD__)
1106     return _C_ctype_tab_ + 1;
1107 #elif defined(__GLIBC__)
1108     return _LIBCPP_GET_C_LOCALE->__ctype_b;
1109 #elif __sun__
1110     return __ctype_mask;
1111 #elif defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
1112     return __pctype_func();
1113 #elif defined(__EMSCRIPTEN__)
1114     return *__ctype_b_loc();
1115 #elif defined(_NEWLIB_VERSION)
1116     // Newlib has a 257-entry table in ctype_.c, where (char)0 starts at [1].
1117     return _ctype_ + 1;
1118 #elif defined(_AIX)
1119     return (const unsigned int *)__lc_ctype_ptr->obj->mask;
1120 #else
1121     // Platform not supported: abort so the person doing the port knows what to
1122     // fix
1123 # warning  ctype<char>::classic_table() is not implemented
1124     printf("ctype<char>::classic_table() is not implemented\n");
1125     abort();
1126     return NULL;
1127 #endif
1128 }
1129 #endif
1130
1131 #if defined(__GLIBC__)
1132 const int*
1133 ctype<char>::__classic_lower_table() _NOEXCEPT
1134 {
1135     return _LIBCPP_GET_C_LOCALE->__ctype_tolower;
1136 }
1137
1138 const int*
1139 ctype<char>::__classic_upper_table() _NOEXCEPT
1140 {
1141     return _LIBCPP_GET_C_LOCALE->__ctype_toupper;
1142 }
1143 #elif __NetBSD__
1144 const short*
1145 ctype<char>::__classic_lower_table() _NOEXCEPT
1146 {
1147     return _C_tolower_tab_ + 1;
1148 }
1149
1150 const short*
1151 ctype<char>::__classic_upper_table() _NOEXCEPT
1152 {
1153     return _C_toupper_tab_ + 1;
1154 }
1155
1156 #elif defined(__EMSCRIPTEN__)
1157 const int*
1158 ctype<char>::__classic_lower_table() _NOEXCEPT
1159 {
1160     return *__ctype_tolower_loc();
1161 }
1162
1163 const int*
1164 ctype<char>::__classic_upper_table() _NOEXCEPT
1165 {
1166     return *__ctype_toupper_loc();
1167 }
1168 #endif // __GLIBC__ || __NETBSD__ || __EMSCRIPTEN__
1169
1170 // template <> class ctype_byname<char>
1171
1172 ctype_byname<char>::ctype_byname(const char* name, size_t refs)
1173     : ctype<char>(0, false, refs),
1174       __l(newlocale(LC_ALL_MASK, name, 0))
1175 {
1176     if (__l == 0)
1177         __throw_runtime_error("ctype_byname<char>::ctype_byname"
1178                             " failed to construct for " + string(name));
1179 }
1180
1181 ctype_byname<char>::ctype_byname(const string& name, size_t refs)
1182     : ctype<char>(0, false, refs),
1183       __l(newlocale(LC_ALL_MASK, name.c_str(), 0))
1184 {
1185     if (__l == 0)
1186         __throw_runtime_error("ctype_byname<char>::ctype_byname"
1187                             " failed to construct for " + name);
1188 }
1189
1190 ctype_byname<char>::~ctype_byname()
1191 {
1192     freelocale(__l);
1193 }
1194
1195 char
1196 ctype_byname<char>::do_toupper(char_type c) const
1197 {
1198     return static_cast<char>(toupper_l(static_cast<unsigned char>(c), __l));
1199 }
1200
1201 const char*
1202 ctype_byname<char>::do_toupper(char_type* low, const char_type* high) const
1203 {
1204     for (; low != high; ++low)
1205         *low = static_cast<char>(toupper_l(static_cast<unsigned char>(*low), __l));
1206     return low;
1207 }
1208
1209 char
1210 ctype_byname<char>::do_tolower(char_type c) const
1211 {
1212     return static_cast<char>(tolower_l(static_cast<unsigned char>(c), __l));
1213 }
1214
1215 const char*
1216 ctype_byname<char>::do_tolower(char_type* low, const char_type* high) const
1217 {
1218     for (; low != high; ++low)
1219         *low = static_cast<char>(tolower_l(static_cast<unsigned char>(*low), __l));
1220     return low;
1221 }
1222
1223 // template <> class ctype_byname<wchar_t>
1224
1225 ctype_byname<wchar_t>::ctype_byname(const char* name, size_t refs)
1226     : ctype<wchar_t>(refs),
1227       __l(newlocale(LC_ALL_MASK, name, 0))
1228 {
1229     if (__l == 0)
1230         __throw_runtime_error("ctype_byname<wchar_t>::ctype_byname"
1231                             " failed to construct for " + string(name));
1232 }
1233
1234 ctype_byname<wchar_t>::ctype_byname(const string& name, size_t refs)
1235     : ctype<wchar_t>(refs),
1236       __l(newlocale(LC_ALL_MASK, name.c_str(), 0))
1237 {
1238     if (__l == 0)
1239         __throw_runtime_error("ctype_byname<wchar_t>::ctype_byname"
1240                             " failed to construct for " + name);
1241 }
1242
1243 ctype_byname<wchar_t>::~ctype_byname()
1244 {
1245     freelocale(__l);
1246 }
1247
1248 bool
1249 ctype_byname<wchar_t>::do_is(mask m, char_type c) const
1250 {
1251 #ifdef _LIBCPP_WCTYPE_IS_MASK
1252     return static_cast<bool>(iswctype_l(c, m, __l));
1253 #else
1254     bool result = false;
1255     wint_t ch = static_cast<wint_t>(c);
1256     if ((m & space) == space) result |= (iswspace_l(ch, __l) != 0);
1257     if ((m & print) == print) result |= (iswprint_l(ch, __l) != 0);
1258     if ((m & cntrl) == cntrl) result |= (iswcntrl_l(ch, __l) != 0);
1259     if ((m & upper) == upper) result |= (iswupper_l(ch, __l) != 0);
1260     if ((m & lower) == lower) result |= (iswlower_l(ch, __l) != 0);
1261     if ((m & alpha) == alpha) result |= (iswalpha_l(ch, __l) != 0);
1262     if ((m & digit) == digit) result |= (iswdigit_l(ch, __l) != 0);
1263     if ((m & punct) == punct) result |= (iswpunct_l(ch, __l) != 0);
1264     if ((m & xdigit) == xdigit) result |= (iswxdigit_l(ch, __l) != 0);
1265     if ((m & blank) == blank) result |= (iswblank_l(ch, __l) != 0);
1266     return result;
1267 #endif
1268 }
1269
1270 const wchar_t*
1271 ctype_byname<wchar_t>::do_is(const char_type* low, const char_type* high, mask* vec) const
1272 {
1273     for (; low != high; ++low, ++vec)
1274     {
1275         if (isascii(*low))
1276             *vec = static_cast<mask>(ctype<char>::classic_table()[*low]);
1277         else
1278         {
1279             *vec = 0;
1280             wint_t ch = static_cast<wint_t>(*low);
1281             if (iswspace_l(ch, __l))
1282                 *vec |= space;
1283 #ifndef _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT
1284             if (iswprint_l(ch, __l))
1285                 *vec |= print;
1286 #endif
1287             if (iswcntrl_l(ch, __l))
1288                 *vec |= cntrl;
1289             if (iswupper_l(ch, __l))
1290                 *vec |= upper;
1291             if (iswlower_l(ch, __l))
1292                 *vec |= lower;
1293 #ifndef _LIBCPP_CTYPE_MASK_IS_COMPOSITE_ALPHA
1294             if (iswalpha_l(ch, __l))
1295                 *vec |= alpha;
1296 #endif
1297             if (iswdigit_l(ch, __l))
1298                 *vec |= digit;
1299             if (iswpunct_l(ch, __l))
1300                 *vec |= punct;
1301 #ifndef _LIBCPP_CTYPE_MASK_IS_COMPOSITE_XDIGIT
1302             if (iswxdigit_l(ch, __l))
1303                 *vec |= xdigit;
1304 #endif
1305 #if !defined(__sun__)
1306             if (iswblank_l(ch, __l))
1307                 *vec |= blank;
1308 #endif
1309         }
1310     }
1311     return low;
1312 }
1313
1314 const wchar_t*
1315 ctype_byname<wchar_t>::do_scan_is(mask m, const char_type* low, const char_type* high) const
1316 {
1317     for (; low != high; ++low)
1318     {
1319 #ifdef _LIBCPP_WCTYPE_IS_MASK
1320         if (iswctype_l(*low, m, __l))
1321             break;
1322 #else
1323         wint_t ch = static_cast<wint_t>(*low);
1324         if ((m & space) == space && iswspace_l(ch, __l)) break;
1325         if ((m & print) == print && iswprint_l(ch, __l)) break;
1326         if ((m & cntrl) == cntrl && iswcntrl_l(ch, __l)) break;
1327         if ((m & upper) == upper && iswupper_l(ch, __l)) break;
1328         if ((m & lower) == lower && iswlower_l(ch, __l)) break;
1329         if ((m & alpha) == alpha && iswalpha_l(ch, __l)) break;
1330         if ((m & digit) == digit && iswdigit_l(ch, __l)) break;
1331         if ((m & punct) == punct && iswpunct_l(ch, __l)) break;
1332         if ((m & xdigit) == xdigit && iswxdigit_l(ch, __l)) break;
1333         if ((m & blank) == blank && iswblank_l(ch, __l)) break;
1334 #endif
1335     }
1336     return low;
1337 }
1338
1339 const wchar_t*
1340 ctype_byname<wchar_t>::do_scan_not(mask m, const char_type* low, const char_type* high) const
1341 {
1342     for (; low != high; ++low)
1343     {
1344 #ifdef _LIBCPP_WCTYPE_IS_MASK
1345         if (!iswctype_l(*low, m, __l))
1346             break;
1347 #else
1348         wint_t ch = static_cast<wint_t>(*low);
1349         if ((m & space) == space && iswspace_l(ch, __l)) continue;
1350         if ((m & print) == print && iswprint_l(ch, __l)) continue;
1351         if ((m & cntrl) == cntrl && iswcntrl_l(ch, __l)) continue;
1352         if ((m & upper) == upper && iswupper_l(ch, __l)) continue;
1353         if ((m & lower) == lower && iswlower_l(ch, __l)) continue;
1354         if ((m & alpha) == alpha && iswalpha_l(ch, __l)) continue;
1355         if ((m & digit) == digit && iswdigit_l(ch, __l)) continue;
1356         if ((m & punct) == punct && iswpunct_l(ch, __l)) continue;
1357         if ((m & xdigit) == xdigit && iswxdigit_l(ch, __l)) continue;
1358         if ((m & blank) == blank && iswblank_l(ch, __l)) continue;
1359         break;
1360 #endif
1361     }
1362     return low;
1363 }
1364
1365 wchar_t
1366 ctype_byname<wchar_t>::do_toupper(char_type c) const
1367 {
1368     return towupper_l(c, __l);
1369 }
1370
1371 const wchar_t*
1372 ctype_byname<wchar_t>::do_toupper(char_type* low, const char_type* high) const
1373 {
1374     for (; low != high; ++low)
1375         *low = towupper_l(*low, __l);
1376     return low;
1377 }
1378
1379 wchar_t
1380 ctype_byname<wchar_t>::do_tolower(char_type c) const
1381 {
1382     return towlower_l(c, __l);
1383 }
1384
1385 const wchar_t*
1386 ctype_byname<wchar_t>::do_tolower(char_type* low, const char_type* high) const
1387 {
1388     for (; low != high; ++low)
1389         *low = towlower_l(*low, __l);
1390     return low;
1391 }
1392
1393 wchar_t
1394 ctype_byname<wchar_t>::do_widen(char c) const
1395 {
1396     return __libcpp_btowc_l(c, __l);
1397 }
1398
1399 const char*
1400 ctype_byname<wchar_t>::do_widen(const char* low, const char* high, char_type* dest) const
1401 {
1402     for (; low != high; ++low, ++dest)
1403         *dest = __libcpp_btowc_l(*low, __l);
1404     return low;
1405 }
1406
1407 char
1408 ctype_byname<wchar_t>::do_narrow(char_type c, char dfault) const
1409 {
1410     int r = __libcpp_wctob_l(c, __l);
1411     return r != static_cast<int>(WEOF) ? static_cast<char>(r) : dfault;
1412 }
1413
1414 const wchar_t*
1415 ctype_byname<wchar_t>::do_narrow(const char_type* low, const char_type* high, char dfault, char* dest) const
1416 {
1417     for (; low != high; ++low, ++dest)
1418     {
1419         int r = __libcpp_wctob_l(*low, __l);
1420         *dest = r != static_cast<int>(WEOF) ? static_cast<char>(r) : dfault;
1421     }
1422     return low;
1423 }
1424
1425 // template <> class codecvt<char, char, mbstate_t>
1426
1427 locale::id codecvt<char, char, mbstate_t>::id;
1428
1429 codecvt<char, char, mbstate_t>::~codecvt()
1430 {
1431 }
1432
1433 codecvt<char, char, mbstate_t>::result
1434 codecvt<char, char, mbstate_t>::do_out(state_type&,
1435     const intern_type* frm, const intern_type*, const intern_type*& frm_nxt,
1436     extern_type* to, extern_type*, extern_type*& to_nxt) const
1437 {
1438     frm_nxt = frm;
1439     to_nxt = to;
1440     return noconv;
1441 }
1442
1443 codecvt<char, char, mbstate_t>::result
1444 codecvt<char, char, mbstate_t>::do_in(state_type&,
1445     const extern_type* frm, const extern_type*, const extern_type*& frm_nxt,
1446     intern_type* to, intern_type*, intern_type*& to_nxt) const
1447 {
1448     frm_nxt = frm;
1449     to_nxt = to;
1450     return noconv;
1451 }
1452
1453 codecvt<char, char, mbstate_t>::result
1454 codecvt<char, char, mbstate_t>::do_unshift(state_type&,
1455     extern_type* to, extern_type*, extern_type*& to_nxt) const
1456 {
1457     to_nxt = to;
1458     return noconv;
1459 }
1460
1461 int
1462 codecvt<char, char, mbstate_t>::do_encoding() const  _NOEXCEPT
1463 {
1464     return 1;
1465 }
1466
1467 bool
1468 codecvt<char, char, mbstate_t>::do_always_noconv() const  _NOEXCEPT
1469 {
1470     return true;
1471 }
1472
1473 int
1474 codecvt<char, char, mbstate_t>::do_length(state_type&,
1475     const extern_type* frm, const extern_type* end, size_t mx) const
1476 {
1477     return static_cast<int>(min<size_t>(mx, static_cast<size_t>(end-frm)));
1478 }
1479
1480 int
1481 codecvt<char, char, mbstate_t>::do_max_length() const  _NOEXCEPT
1482 {
1483     return 1;
1484 }
1485
1486 // template <> class codecvt<wchar_t, char, mbstate_t>
1487
1488 locale::id codecvt<wchar_t, char, mbstate_t>::id;
1489
1490 codecvt<wchar_t, char, mbstate_t>::codecvt(size_t refs)
1491     : locale::facet(refs),
1492       __l(_LIBCPP_GET_C_LOCALE)
1493 {
1494 }
1495
1496 codecvt<wchar_t, char, mbstate_t>::codecvt(const char* nm, size_t refs)
1497     : locale::facet(refs),
1498       __l(newlocale(LC_ALL_MASK, nm, 0))
1499 {
1500     if (__l == 0)
1501         __throw_runtime_error("codecvt_byname<wchar_t, char, mbstate_t>::codecvt_byname"
1502                             " failed to construct for " + string(nm));
1503 }
1504
1505 codecvt<wchar_t, char, mbstate_t>::~codecvt()
1506 {
1507     if (__l != _LIBCPP_GET_C_LOCALE)
1508         freelocale(__l);
1509 }
1510
1511 codecvt<wchar_t, char, mbstate_t>::result
1512 codecvt<wchar_t, char, mbstate_t>::do_out(state_type& st,
1513     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
1514     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
1515 {
1516     // look for first internal null in frm
1517     const intern_type* fend = frm;
1518     for (; fend != frm_end; ++fend)
1519         if (*fend == 0)
1520             break;
1521     // loop over all null-terminated sequences in frm
1522     to_nxt = to;
1523     for (frm_nxt = frm; frm != frm_end && to != to_end; frm = frm_nxt, to = to_nxt)
1524     {
1525         // save state in case it is needed to recover to_nxt on error
1526         mbstate_t save_state = st;
1527         size_t n = __libcpp_wcsnrtombs_l(to, &frm_nxt, static_cast<size_t>(fend-frm),
1528                                      static_cast<size_t>(to_end-to), &st, __l);
1529         if (n == size_t(-1))
1530         {
1531             // need to recover to_nxt
1532             for (to_nxt = to; frm != frm_nxt; ++frm)
1533             {
1534                 n = __libcpp_wcrtomb_l(to_nxt, *frm, &save_state, __l);
1535                 if (n == size_t(-1))
1536                     break;
1537                 to_nxt += n;
1538             }
1539             frm_nxt = frm;
1540             return error;
1541         }
1542         if (n == 0)
1543             return partial;
1544         to_nxt += n;
1545         if (to_nxt == to_end)
1546             break;
1547         if (fend != frm_end)  // set up next null terminated sequence
1548         {
1549             // Try to write the terminating null
1550             extern_type tmp[MB_LEN_MAX];
1551             n = __libcpp_wcrtomb_l(tmp, intern_type(), &st, __l);
1552             if (n == size_t(-1))  // on error
1553                 return error;
1554             if (n > static_cast<size_t>(to_end-to_nxt))  // is there room?
1555                 return partial;
1556             for (extern_type* p = tmp; n; --n)  // write it
1557                 *to_nxt++ = *p++;
1558             ++frm_nxt;
1559             // look for next null in frm
1560             for (fend = frm_nxt; fend != frm_end; ++fend)
1561                 if (*fend == 0)
1562                     break;
1563         }
1564     }
1565     return frm_nxt == frm_end ? ok : partial;
1566 }
1567
1568 codecvt<wchar_t, char, mbstate_t>::result
1569 codecvt<wchar_t, char, mbstate_t>::do_in(state_type& st,
1570     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
1571     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
1572 {
1573     // look for first internal null in frm
1574     const extern_type* fend = frm;
1575     for (; fend != frm_end; ++fend)
1576         if (*fend == 0)
1577             break;
1578     // loop over all null-terminated sequences in frm
1579     to_nxt = to;
1580     for (frm_nxt = frm; frm != frm_end && to != to_end; frm = frm_nxt, to = to_nxt)
1581     {
1582         // save state in case it is needed to recover to_nxt on error
1583         mbstate_t save_state = st;
1584         size_t n = __libcpp_mbsnrtowcs_l(to, &frm_nxt, static_cast<size_t>(fend-frm),
1585                                      static_cast<size_t>(to_end-to), &st, __l);
1586         if (n == size_t(-1))
1587         {
1588             // need to recover to_nxt
1589             for (to_nxt = to; frm != frm_nxt; ++to_nxt)
1590             {
1591                 n = __libcpp_mbrtowc_l(to_nxt, frm, static_cast<size_t>(fend-frm),
1592                                    &save_state, __l);
1593                 switch (n)
1594                 {
1595                 case 0:
1596                     ++frm;
1597                     break;
1598                 case size_t(-1):
1599                     frm_nxt = frm;
1600                     return error;
1601                 case size_t(-2):
1602                     frm_nxt = frm;
1603                     return partial;
1604                 default:
1605                     frm += n;
1606                     break;
1607                 }
1608             }
1609             frm_nxt = frm;
1610             return frm_nxt == frm_end ? ok : partial;
1611         }
1612         if (n == size_t(-1))
1613             return error;
1614         to_nxt += n;
1615         if (to_nxt == to_end)
1616             break;
1617         if (fend != frm_end)  // set up next null terminated sequence
1618         {
1619             // Try to write the terminating null
1620             n = __libcpp_mbrtowc_l(to_nxt, frm_nxt, 1, &st, __l);
1621             if (n != 0)  // on error
1622                 return error;
1623             ++to_nxt;
1624             ++frm_nxt;
1625             // look for next null in frm
1626             for (fend = frm_nxt; fend != frm_end; ++fend)
1627                 if (*fend == 0)
1628                     break;
1629         }
1630     }
1631     return frm_nxt == frm_end ? ok : partial;
1632 }
1633
1634 codecvt<wchar_t, char, mbstate_t>::result
1635 codecvt<wchar_t, char, mbstate_t>::do_unshift(state_type& st,
1636     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
1637 {
1638     to_nxt = to;
1639     extern_type tmp[MB_LEN_MAX];
1640     size_t n = __libcpp_wcrtomb_l(tmp, intern_type(), &st, __l);
1641     if (n == size_t(-1) || n == 0)  // on error
1642         return error;
1643     --n;
1644     if (n > static_cast<size_t>(to_end-to_nxt))  // is there room?
1645         return partial;
1646     for (extern_type* p = tmp; n; --n)  // write it
1647         *to_nxt++ = *p++;
1648     return ok;
1649 }
1650
1651 int
1652 codecvt<wchar_t, char, mbstate_t>::do_encoding() const  _NOEXCEPT
1653 {
1654     if (__libcpp_mbtowc_l(nullptr, nullptr, MB_LEN_MAX, __l) != 0)
1655         return -1;
1656
1657     // stateless encoding
1658     if (__l == 0 || __libcpp_mb_cur_max_l(__l) == 1)  // there are no known constant length encodings
1659         return 1;                // which take more than 1 char to form a wchar_t
1660     return 0;
1661 }
1662
1663 bool
1664 codecvt<wchar_t, char, mbstate_t>::do_always_noconv() const  _NOEXCEPT
1665 {
1666     return false;
1667 }
1668
1669 int
1670 codecvt<wchar_t, char, mbstate_t>::do_length(state_type& st,
1671     const extern_type* frm, const extern_type* frm_end, size_t mx) const
1672 {
1673     int nbytes = 0;
1674     for (size_t nwchar_t = 0; nwchar_t < mx && frm != frm_end; ++nwchar_t)
1675     {
1676         size_t n = __libcpp_mbrlen_l(frm, static_cast<size_t>(frm_end-frm), &st, __l);
1677         switch (n)
1678         {
1679         case 0:
1680             ++nbytes;
1681             ++frm;
1682             break;
1683         case size_t(-1):
1684         case size_t(-2):
1685             return nbytes;
1686         default:
1687             nbytes += n;
1688             frm += n;
1689             break;
1690         }
1691     }
1692     return nbytes;
1693 }
1694
1695 int
1696 codecvt<wchar_t, char, mbstate_t>::do_max_length() const  _NOEXCEPT
1697 {
1698     return __l == 0 ? 1 : static_cast<int>(__libcpp_mb_cur_max_l(__l));
1699 }
1700
1701 //                                     Valid UTF ranges
1702 //     UTF-32               UTF-16                          UTF-8               # of code points
1703 //                     first      second       first   second    third   fourth
1704 // 000000 - 00007F  0000 - 007F               00 - 7F                                 127
1705 // 000080 - 0007FF  0080 - 07FF               C2 - DF, 80 - BF                       1920
1706 // 000800 - 000FFF  0800 - 0FFF               E0 - E0, A0 - BF, 80 - BF              2048
1707 // 001000 - 00CFFF  1000 - CFFF               E1 - EC, 80 - BF, 80 - BF             49152
1708 // 00D000 - 00D7FF  D000 - D7FF               ED - ED, 80 - 9F, 80 - BF              2048
1709 // 00D800 - 00DFFF                invalid
1710 // 00E000 - 00FFFF  E000 - FFFF               EE - EF, 80 - BF, 80 - BF              8192
1711 // 010000 - 03FFFF  D800 - D8BF, DC00 - DFFF  F0 - F0, 90 - BF, 80 - BF, 80 - BF   196608
1712 // 040000 - 0FFFFF  D8C0 - DBBF, DC00 - DFFF  F1 - F3, 80 - BF, 80 - BF, 80 - BF   786432
1713 // 100000 - 10FFFF  DBC0 - DBFF, DC00 - DFFF  F4 - F4, 80 - 8F, 80 - BF, 80 - BF    65536
1714
1715 static
1716 codecvt_base::result
1717 utf16_to_utf8(const uint16_t* frm, const uint16_t* frm_end, const uint16_t*& frm_nxt,
1718               uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt,
1719               unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
1720 {
1721     frm_nxt = frm;
1722     to_nxt = to;
1723     if (mode & generate_header)
1724     {
1725         if (to_end-to_nxt < 3)
1726             return codecvt_base::partial;
1727         *to_nxt++ = static_cast<uint8_t>(0xEF);
1728         *to_nxt++ = static_cast<uint8_t>(0xBB);
1729         *to_nxt++ = static_cast<uint8_t>(0xBF);
1730     }
1731     for (; frm_nxt < frm_end; ++frm_nxt)
1732     {
1733         uint16_t wc1 = *frm_nxt;
1734         if (wc1 > Maxcode)
1735             return codecvt_base::error;
1736         if (wc1 < 0x0080)
1737         {
1738             if (to_end-to_nxt < 1)
1739                 return codecvt_base::partial;
1740             *to_nxt++ = static_cast<uint8_t>(wc1);
1741         }
1742         else if (wc1 < 0x0800)
1743         {
1744             if (to_end-to_nxt < 2)
1745                 return codecvt_base::partial;
1746             *to_nxt++ = static_cast<uint8_t>(0xC0 | (wc1 >> 6));
1747             *to_nxt++ = static_cast<uint8_t>(0x80 | (wc1 & 0x03F));
1748         }
1749         else if (wc1 < 0xD800)
1750         {
1751             if (to_end-to_nxt < 3)
1752                 return codecvt_base::partial;
1753             *to_nxt++ = static_cast<uint8_t>(0xE0 |  (wc1 >> 12));
1754             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0FC0) >> 6));
1755             *to_nxt++ = static_cast<uint8_t>(0x80 |  (wc1 & 0x003F));
1756         }
1757         else if (wc1 < 0xDC00)
1758         {
1759             if (frm_end-frm_nxt < 2)
1760                 return codecvt_base::partial;
1761             uint16_t wc2 = frm_nxt[1];
1762             if ((wc2 & 0xFC00) != 0xDC00)
1763                 return codecvt_base::error;
1764             if (to_end-to_nxt < 4)
1765                 return codecvt_base::partial;
1766             if (((((wc1 & 0x03C0UL) >> 6) + 1) << 16) +
1767                 ((wc1 & 0x003FUL) << 10) + (wc2 & 0x03FF) > Maxcode)
1768                 return codecvt_base::error;
1769             ++frm_nxt;
1770             uint8_t z = ((wc1 & 0x03C0) >> 6) + 1;
1771             *to_nxt++ = static_cast<uint8_t>(0xF0 | (z >> 2));
1772             *to_nxt++ = static_cast<uint8_t>(0x80 | ((z & 0x03) << 4)     | ((wc1 & 0x003C) >> 2));
1773             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0003) << 4) | ((wc2 & 0x03C0) >> 6));
1774             *to_nxt++ = static_cast<uint8_t>(0x80 |  (wc2 & 0x003F));
1775         }
1776         else if (wc1 < 0xE000)
1777         {
1778             return codecvt_base::error;
1779         }
1780         else
1781         {
1782             if (to_end-to_nxt < 3)
1783                 return codecvt_base::partial;
1784             *to_nxt++ = static_cast<uint8_t>(0xE0 |  (wc1 >> 12));
1785             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0FC0) >> 6));
1786             *to_nxt++ = static_cast<uint8_t>(0x80 |  (wc1 & 0x003F));
1787         }
1788     }
1789     return codecvt_base::ok;
1790 }
1791
1792 static
1793 codecvt_base::result
1794 utf16_to_utf8(const uint32_t* frm, const uint32_t* frm_end, const uint32_t*& frm_nxt,
1795               uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt,
1796               unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
1797 {
1798     frm_nxt = frm;
1799     to_nxt = to;
1800     if (mode & generate_header)
1801     {
1802         if (to_end-to_nxt < 3)
1803             return codecvt_base::partial;
1804         *to_nxt++ = static_cast<uint8_t>(0xEF);
1805         *to_nxt++ = static_cast<uint8_t>(0xBB);
1806         *to_nxt++ = static_cast<uint8_t>(0xBF);
1807     }
1808     for (; frm_nxt < frm_end; ++frm_nxt)
1809     {
1810         uint16_t wc1 = static_cast<uint16_t>(*frm_nxt);
1811         if (wc1 > Maxcode)
1812             return codecvt_base::error;
1813         if (wc1 < 0x0080)
1814         {
1815             if (to_end-to_nxt < 1)
1816                 return codecvt_base::partial;
1817             *to_nxt++ = static_cast<uint8_t>(wc1);
1818         }
1819         else if (wc1 < 0x0800)
1820         {
1821             if (to_end-to_nxt < 2)
1822                 return codecvt_base::partial;
1823             *to_nxt++ = static_cast<uint8_t>(0xC0 | (wc1 >> 6));
1824             *to_nxt++ = static_cast<uint8_t>(0x80 | (wc1 & 0x03F));
1825         }
1826         else if (wc1 < 0xD800)
1827         {
1828             if (to_end-to_nxt < 3)
1829                 return codecvt_base::partial;
1830             *to_nxt++ = static_cast<uint8_t>(0xE0 |  (wc1 >> 12));
1831             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0FC0) >> 6));
1832             *to_nxt++ = static_cast<uint8_t>(0x80 |  (wc1 & 0x003F));
1833         }
1834         else if (wc1 < 0xDC00)
1835         {
1836             if (frm_end-frm_nxt < 2)
1837                 return codecvt_base::partial;
1838             uint16_t wc2 = static_cast<uint16_t>(frm_nxt[1]);
1839             if ((wc2 & 0xFC00) != 0xDC00)
1840                 return codecvt_base::error;
1841             if (to_end-to_nxt < 4)
1842                 return codecvt_base::partial;
1843             if (((((wc1 & 0x03C0UL) >> 6) + 1) << 16) +
1844                 ((wc1 & 0x003FUL) << 10) + (wc2 & 0x03FF) > Maxcode)
1845                 return codecvt_base::error;
1846             ++frm_nxt;
1847             uint8_t z = ((wc1 & 0x03C0) >> 6) + 1;
1848             *to_nxt++ = static_cast<uint8_t>(0xF0 | (z >> 2));
1849             *to_nxt++ = static_cast<uint8_t>(0x80 | ((z & 0x03) << 4)     | ((wc1 & 0x003C) >> 2));
1850             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0003) << 4) | ((wc2 & 0x03C0) >> 6));
1851             *to_nxt++ = static_cast<uint8_t>(0x80 |  (wc2 & 0x003F));
1852         }
1853         else if (wc1 < 0xE000)
1854         {
1855             return codecvt_base::error;
1856         }
1857         else
1858         {
1859             if (to_end-to_nxt < 3)
1860                 return codecvt_base::partial;
1861             *to_nxt++ = static_cast<uint8_t>(0xE0 |  (wc1 >> 12));
1862             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc1 & 0x0FC0) >> 6));
1863             *to_nxt++ = static_cast<uint8_t>(0x80 |  (wc1 & 0x003F));
1864         }
1865     }
1866     return codecvt_base::ok;
1867 }
1868
1869 static
1870 codecvt_base::result
1871 utf8_to_utf16(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt,
1872               uint16_t* to, uint16_t* to_end, uint16_t*& to_nxt,
1873               unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
1874 {
1875     frm_nxt = frm;
1876     to_nxt = to;
1877     if (mode & consume_header)
1878     {
1879         if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB &&
1880                                                           frm_nxt[2] == 0xBF)
1881             frm_nxt += 3;
1882     }
1883     for (; frm_nxt < frm_end && to_nxt < to_end; ++to_nxt)
1884     {
1885         uint8_t c1 = *frm_nxt;
1886         if (c1 > Maxcode)
1887             return codecvt_base::error;
1888         if (c1 < 0x80)
1889         {
1890             *to_nxt = static_cast<uint16_t>(c1);
1891             ++frm_nxt;
1892         }
1893         else if (c1 < 0xC2)
1894         {
1895             return codecvt_base::error;
1896         }
1897         else if (c1 < 0xE0)
1898         {
1899             if (frm_end-frm_nxt < 2)
1900                 return codecvt_base::partial;
1901             uint8_t c2 = frm_nxt[1];
1902             if ((c2 & 0xC0) != 0x80)
1903                 return codecvt_base::error;
1904             uint16_t t = static_cast<uint16_t>(((c1 & 0x1F) << 6) | (c2 & 0x3F));
1905             if (t > Maxcode)
1906                 return codecvt_base::error;
1907             *to_nxt = t;
1908             frm_nxt += 2;
1909         }
1910         else if (c1 < 0xF0)
1911         {
1912             if (frm_end-frm_nxt < 3)
1913                 return codecvt_base::partial;
1914             uint8_t c2 = frm_nxt[1];
1915             uint8_t c3 = frm_nxt[2];
1916             switch (c1)
1917             {
1918             case 0xE0:
1919                 if ((c2 & 0xE0) != 0xA0)
1920                     return codecvt_base::error;
1921                  break;
1922             case 0xED:
1923                 if ((c2 & 0xE0) != 0x80)
1924                     return codecvt_base::error;
1925                  break;
1926             default:
1927                 if ((c2 & 0xC0) != 0x80)
1928                     return codecvt_base::error;
1929                  break;
1930             }
1931             if ((c3 & 0xC0) != 0x80)
1932                 return codecvt_base::error;
1933             uint16_t t = static_cast<uint16_t>(((c1 & 0x0F) << 12)
1934                                              | ((c2 & 0x3F) << 6)
1935                                              |  (c3 & 0x3F));
1936             if (t > Maxcode)
1937                 return codecvt_base::error;
1938             *to_nxt = t;
1939             frm_nxt += 3;
1940         }
1941         else if (c1 < 0xF5)
1942         {
1943             if (frm_end-frm_nxt < 4)
1944                 return codecvt_base::partial;
1945             uint8_t c2 = frm_nxt[1];
1946             uint8_t c3 = frm_nxt[2];
1947             uint8_t c4 = frm_nxt[3];
1948             switch (c1)
1949             {
1950             case 0xF0:
1951                 if (!(0x90 <= c2 && c2 <= 0xBF))
1952                     return codecvt_base::error;
1953                  break;
1954             case 0xF4:
1955                 if ((c2 & 0xF0) != 0x80)
1956                     return codecvt_base::error;
1957                  break;
1958             default:
1959                 if ((c2 & 0xC0) != 0x80)
1960                     return codecvt_base::error;
1961                  break;
1962             }
1963             if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80)
1964                 return codecvt_base::error;
1965             if (to_end-to_nxt < 2)
1966                 return codecvt_base::partial;
1967             if ((((c1 & 7UL) << 18) +
1968                 ((c2 & 0x3FUL) << 12) +
1969                 ((c3 & 0x3FUL) << 6) + (c4 & 0x3F)) > Maxcode)
1970                 return codecvt_base::error;
1971             *to_nxt = static_cast<uint16_t>(
1972                     0xD800
1973                   | (((((c1 & 0x07) << 2) | ((c2 & 0x30) >> 4)) - 1) << 6)
1974                   | ((c2 & 0x0F) << 2)
1975                   | ((c3 & 0x30) >> 4));
1976             *++to_nxt = static_cast<uint16_t>(
1977                     0xDC00
1978                   | ((c3 & 0x0F) << 6)
1979                   |  (c4 & 0x3F));
1980             frm_nxt += 4;
1981         }
1982         else
1983         {
1984             return codecvt_base::error;
1985         }
1986     }
1987     return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok;
1988 }
1989
1990 static
1991 codecvt_base::result
1992 utf8_to_utf16(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt,
1993               uint32_t* to, uint32_t* to_end, uint32_t*& to_nxt,
1994               unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
1995 {
1996     frm_nxt = frm;
1997     to_nxt = to;
1998     if (mode & consume_header)
1999     {
2000         if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB &&
2001                                                           frm_nxt[2] == 0xBF)
2002             frm_nxt += 3;
2003     }
2004     for (; frm_nxt < frm_end && to_nxt < to_end; ++to_nxt)
2005     {
2006         uint8_t c1 = *frm_nxt;
2007         if (c1 > Maxcode)
2008             return codecvt_base::error;
2009         if (c1 < 0x80)
2010         {
2011             *to_nxt = static_cast<uint32_t>(c1);
2012             ++frm_nxt;
2013         }
2014         else if (c1 < 0xC2)
2015         {
2016             return codecvt_base::error;
2017         }
2018         else if (c1 < 0xE0)
2019         {
2020             if (frm_end-frm_nxt < 2)
2021                 return codecvt_base::partial;
2022             uint8_t c2 = frm_nxt[1];
2023             if ((c2 & 0xC0) != 0x80)
2024                 return codecvt_base::error;
2025             uint16_t t = static_cast<uint16_t>(((c1 & 0x1F) << 6) | (c2 & 0x3F));
2026             if (t > Maxcode)
2027                 return codecvt_base::error;
2028             *to_nxt = static_cast<uint32_t>(t);
2029             frm_nxt += 2;
2030         }
2031         else if (c1 < 0xF0)
2032         {
2033             if (frm_end-frm_nxt < 3)
2034                 return codecvt_base::partial;
2035             uint8_t c2 = frm_nxt[1];
2036             uint8_t c3 = frm_nxt[2];
2037             switch (c1)
2038             {
2039             case 0xE0:
2040                 if ((c2 & 0xE0) != 0xA0)
2041                     return codecvt_base::error;
2042                  break;
2043             case 0xED:
2044                 if ((c2 & 0xE0) != 0x80)
2045                     return codecvt_base::error;
2046                  break;
2047             default:
2048                 if ((c2 & 0xC0) != 0x80)
2049                     return codecvt_base::error;
2050                  break;
2051             }
2052             if ((c3 & 0xC0) != 0x80)
2053                 return codecvt_base::error;
2054             uint16_t t = static_cast<uint16_t>(((c1 & 0x0F) << 12)
2055                                              | ((c2 & 0x3F) << 6)
2056                                              |  (c3 & 0x3F));
2057             if (t > Maxcode)
2058                 return codecvt_base::error;
2059             *to_nxt = static_cast<uint32_t>(t);
2060             frm_nxt += 3;
2061         }
2062         else if (c1 < 0xF5)
2063         {
2064             if (frm_end-frm_nxt < 4)
2065                 return codecvt_base::partial;
2066             uint8_t c2 = frm_nxt[1];
2067             uint8_t c3 = frm_nxt[2];
2068             uint8_t c4 = frm_nxt[3];
2069             switch (c1)
2070             {
2071             case 0xF0:
2072                 if (!(0x90 <= c2 && c2 <= 0xBF))
2073                     return codecvt_base::error;
2074                  break;
2075             case 0xF4:
2076                 if ((c2 & 0xF0) != 0x80)
2077                     return codecvt_base::error;
2078                  break;
2079             default:
2080                 if ((c2 & 0xC0) != 0x80)
2081                     return codecvt_base::error;
2082                  break;
2083             }
2084             if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80)
2085                 return codecvt_base::error;
2086             if (to_end-to_nxt < 2)
2087                 return codecvt_base::partial;
2088             if ((((c1 & 7UL) << 18) +
2089                 ((c2 & 0x3FUL) << 12) +
2090                 ((c3 & 0x3FUL) << 6) + (c4 & 0x3F)) > Maxcode)
2091                 return codecvt_base::error;
2092             *to_nxt = static_cast<uint32_t>(
2093                     0xD800
2094                   | (((((c1 & 0x07) << 2) | ((c2 & 0x30) >> 4)) - 1) << 6)
2095                   | ((c2 & 0x0F) << 2)
2096                   | ((c3 & 0x30) >> 4));
2097             *++to_nxt = static_cast<uint32_t>(
2098                     0xDC00
2099                   | ((c3 & 0x0F) << 6)
2100                   |  (c4 & 0x3F));
2101             frm_nxt += 4;
2102         }
2103         else
2104         {
2105             return codecvt_base::error;
2106         }
2107     }
2108     return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok;
2109 }
2110
2111 static
2112 int
2113 utf8_to_utf16_length(const uint8_t* frm, const uint8_t* frm_end,
2114                      size_t mx, unsigned long Maxcode = 0x10FFFF,
2115                      codecvt_mode mode = codecvt_mode(0))
2116 {
2117     const uint8_t* frm_nxt = frm;
2118     if (mode & consume_header)
2119     {
2120         if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB &&
2121                                                           frm_nxt[2] == 0xBF)
2122             frm_nxt += 3;
2123     }
2124     for (size_t nchar16_t = 0; frm_nxt < frm_end && nchar16_t < mx; ++nchar16_t)
2125     {
2126         uint8_t c1 = *frm_nxt;
2127         if (c1 > Maxcode)
2128             break;
2129         if (c1 < 0x80)
2130         {
2131             ++frm_nxt;
2132         }
2133         else if (c1 < 0xC2)
2134         {
2135             break;
2136         }
2137         else if (c1 < 0xE0)
2138         {
2139             if ((frm_end-frm_nxt < 2) || (frm_nxt[1] & 0xC0) != 0x80)
2140                 break;
2141             uint16_t t = static_cast<uint16_t>(((c1 & 0x1F) << 6) | (frm_nxt[1] & 0x3F));
2142             if (t > Maxcode)
2143                 break;
2144             frm_nxt += 2;
2145         }
2146         else if (c1 < 0xF0)
2147         {
2148             if (frm_end-frm_nxt < 3)
2149                 break;
2150             uint8_t c2 = frm_nxt[1];
2151             uint8_t c3 = frm_nxt[2];
2152             switch (c1)
2153             {
2154             case 0xE0:
2155                 if ((c2 & 0xE0) != 0xA0)
2156                     return static_cast<int>(frm_nxt - frm);
2157                 break;
2158             case 0xED:
2159                 if ((c2 & 0xE0) != 0x80)
2160                     return static_cast<int>(frm_nxt - frm);
2161                  break;
2162             default:
2163                 if ((c2 & 0xC0) != 0x80)
2164                     return static_cast<int>(frm_nxt - frm);
2165                  break;
2166             }
2167             if ((c3 & 0xC0) != 0x80)
2168                 break;
2169             if ((((c1 & 0x0Fu) << 12) | ((c2 & 0x3Fu) << 6) | (c3 & 0x3Fu)) > Maxcode)
2170                 break;
2171             frm_nxt += 3;
2172         }
2173         else if (c1 < 0xF5)
2174         {
2175             if (frm_end-frm_nxt < 4 || mx-nchar16_t < 2)
2176                 break;
2177             uint8_t c2 = frm_nxt[1];
2178             uint8_t c3 = frm_nxt[2];
2179             uint8_t c4 = frm_nxt[3];
2180             switch (c1)
2181             {
2182             case 0xF0:
2183                 if (!(0x90 <= c2 && c2 <= 0xBF))
2184                     return static_cast<int>(frm_nxt - frm);
2185                  break;
2186             case 0xF4:
2187                 if ((c2 & 0xF0) != 0x80)
2188                     return static_cast<int>(frm_nxt - frm);
2189                  break;
2190             default:
2191                 if ((c2 & 0xC0) != 0x80)
2192                     return static_cast<int>(frm_nxt - frm);
2193                  break;
2194             }
2195             if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80)
2196                 break;
2197             if ((((c1 & 7UL) << 18) +
2198                 ((c2 & 0x3FUL) << 12) +
2199                 ((c3 & 0x3FUL) << 6) + (c4 & 0x3F)) > Maxcode)
2200                 break;
2201             ++nchar16_t;
2202             frm_nxt += 4;
2203         }
2204         else
2205         {
2206             break;
2207         }
2208     }
2209     return static_cast<int>(frm_nxt - frm);
2210 }
2211
2212 static
2213 codecvt_base::result
2214 ucs4_to_utf8(const uint32_t* frm, const uint32_t* frm_end, const uint32_t*& frm_nxt,
2215              uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt,
2216              unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2217 {
2218     frm_nxt = frm;
2219     to_nxt = to;
2220     if (mode & generate_header)
2221     {
2222         if (to_end-to_nxt < 3)
2223             return codecvt_base::partial;
2224         *to_nxt++ = static_cast<uint8_t>(0xEF);
2225         *to_nxt++ = static_cast<uint8_t>(0xBB);
2226         *to_nxt++ = static_cast<uint8_t>(0xBF);
2227     }
2228     for (; frm_nxt < frm_end; ++frm_nxt)
2229     {
2230         uint32_t wc = *frm_nxt;
2231         if ((wc & 0xFFFFF800) == 0x00D800 || wc > Maxcode)
2232             return codecvt_base::error;
2233         if (wc < 0x000080)
2234         {
2235             if (to_end-to_nxt < 1)
2236                 return codecvt_base::partial;
2237             *to_nxt++ = static_cast<uint8_t>(wc);
2238         }
2239         else if (wc < 0x000800)
2240         {
2241             if (to_end-to_nxt < 2)
2242                 return codecvt_base::partial;
2243             *to_nxt++ = static_cast<uint8_t>(0xC0 | (wc >> 6));
2244             *to_nxt++ = static_cast<uint8_t>(0x80 | (wc & 0x03F));
2245         }
2246         else if (wc < 0x010000)
2247         {
2248             if (to_end-to_nxt < 3)
2249                 return codecvt_base::partial;
2250             *to_nxt++ = static_cast<uint8_t>(0xE0 |  (wc >> 12));
2251             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc & 0x0FC0) >> 6));
2252             *to_nxt++ = static_cast<uint8_t>(0x80 |  (wc & 0x003F));
2253         }
2254         else // if (wc < 0x110000)
2255         {
2256             if (to_end-to_nxt < 4)
2257                 return codecvt_base::partial;
2258             *to_nxt++ = static_cast<uint8_t>(0xF0 |  (wc >> 18));
2259             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc & 0x03F000) >> 12));
2260             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc & 0x000FC0) >> 6));
2261             *to_nxt++ = static_cast<uint8_t>(0x80 |  (wc & 0x00003F));
2262         }
2263     }
2264     return codecvt_base::ok;
2265 }
2266
2267 static
2268 codecvt_base::result
2269 utf8_to_ucs4(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt,
2270              uint32_t* to, uint32_t* to_end, uint32_t*& to_nxt,
2271              unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2272 {
2273     frm_nxt = frm;
2274     to_nxt = to;
2275     if (mode & consume_header)
2276     {
2277         if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB &&
2278                                                           frm_nxt[2] == 0xBF)
2279             frm_nxt += 3;
2280     }
2281     for (; frm_nxt < frm_end && to_nxt < to_end; ++to_nxt)
2282     {
2283         uint8_t c1 = static_cast<uint8_t>(*frm_nxt);
2284         if (c1 < 0x80)
2285         {
2286             if (c1 > Maxcode)
2287                 return codecvt_base::error;
2288             *to_nxt = static_cast<uint32_t>(c1);
2289             ++frm_nxt;
2290         }
2291         else if (c1 < 0xC2)
2292         {
2293             return codecvt_base::error;
2294         }
2295         else if (c1 < 0xE0)
2296         {
2297             if (frm_end-frm_nxt < 2)
2298                 return codecvt_base::partial;
2299             uint8_t c2 = frm_nxt[1];
2300             if ((c2 & 0xC0) != 0x80)
2301                 return codecvt_base::error;
2302             uint32_t t = static_cast<uint32_t>(((c1 & 0x1F) << 6)
2303                                               | (c2 & 0x3F));
2304             if (t > Maxcode)
2305                 return codecvt_base::error;
2306             *to_nxt = t;
2307             frm_nxt += 2;
2308         }
2309         else if (c1 < 0xF0)
2310         {
2311             if (frm_end-frm_nxt < 3)
2312                 return codecvt_base::partial;
2313             uint8_t c2 = frm_nxt[1];
2314             uint8_t c3 = frm_nxt[2];
2315             switch (c1)
2316             {
2317             case 0xE0:
2318                 if ((c2 & 0xE0) != 0xA0)
2319                     return codecvt_base::error;
2320                  break;
2321             case 0xED:
2322                 if ((c2 & 0xE0) != 0x80)
2323                     return codecvt_base::error;
2324                  break;
2325             default:
2326                 if ((c2 & 0xC0) != 0x80)
2327                     return codecvt_base::error;
2328                  break;
2329             }
2330             if ((c3 & 0xC0) != 0x80)
2331                 return codecvt_base::error;
2332             uint32_t t = static_cast<uint32_t>(((c1 & 0x0F) << 12)
2333                                              | ((c2 & 0x3F) << 6)
2334                                              |  (c3 & 0x3F));
2335             if (t > Maxcode)
2336                 return codecvt_base::error;
2337             *to_nxt = t;
2338             frm_nxt += 3;
2339         }
2340         else if (c1 < 0xF5)
2341         {
2342             if (frm_end-frm_nxt < 4)
2343                 return codecvt_base::partial;
2344             uint8_t c2 = frm_nxt[1];
2345             uint8_t c3 = frm_nxt[2];
2346             uint8_t c4 = frm_nxt[3];
2347             switch (c1)
2348             {
2349             case 0xF0:
2350                 if (!(0x90 <= c2 && c2 <= 0xBF))
2351                     return codecvt_base::error;
2352                  break;
2353             case 0xF4:
2354                 if ((c2 & 0xF0) != 0x80)
2355                     return codecvt_base::error;
2356                  break;
2357             default:
2358                 if ((c2 & 0xC0) != 0x80)
2359                     return codecvt_base::error;
2360                  break;
2361             }
2362             if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80)
2363                 return codecvt_base::error;
2364             uint32_t t = static_cast<uint32_t>(((c1 & 0x07) << 18)
2365                                              | ((c2 & 0x3F) << 12)
2366                                              | ((c3 & 0x3F) << 6)
2367                                              |  (c4 & 0x3F));
2368             if (t > Maxcode)
2369                 return codecvt_base::error;
2370             *to_nxt = t;
2371             frm_nxt += 4;
2372         }
2373         else
2374         {
2375             return codecvt_base::error;
2376         }
2377     }
2378     return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok;
2379 }
2380
2381 static
2382 int
2383 utf8_to_ucs4_length(const uint8_t* frm, const uint8_t* frm_end,
2384                     size_t mx, unsigned long Maxcode = 0x10FFFF,
2385                     codecvt_mode mode = codecvt_mode(0))
2386 {
2387     const uint8_t* frm_nxt = frm;
2388     if (mode & consume_header)
2389     {
2390         if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB &&
2391                                                           frm_nxt[2] == 0xBF)
2392             frm_nxt += 3;
2393     }
2394     for (size_t nchar32_t = 0; frm_nxt < frm_end && nchar32_t < mx; ++nchar32_t)
2395     {
2396         uint8_t c1 = static_cast<uint8_t>(*frm_nxt);
2397         if (c1 < 0x80)
2398         {
2399             if (c1 > Maxcode)
2400                 break;
2401             ++frm_nxt;
2402         }
2403         else if (c1 < 0xC2)
2404         {
2405             break;
2406         }
2407         else if (c1 < 0xE0)
2408         {
2409             if ((frm_end-frm_nxt < 2) || ((frm_nxt[1] & 0xC0) != 0x80))
2410                 break;
2411             if ((((c1 & 0x1Fu) << 6) | (frm_nxt[1] & 0x3Fu)) > Maxcode)
2412                 break;
2413             frm_nxt += 2;
2414         }
2415         else if (c1 < 0xF0)
2416         {
2417             if (frm_end-frm_nxt < 3)
2418                 break;
2419             uint8_t c2 = frm_nxt[1];
2420             uint8_t c3 = frm_nxt[2];
2421             switch (c1)
2422             {
2423             case 0xE0:
2424                 if ((c2 & 0xE0) != 0xA0)
2425                     return static_cast<int>(frm_nxt - frm);
2426                 break;
2427             case 0xED:
2428                 if ((c2 & 0xE0) != 0x80)
2429                     return static_cast<int>(frm_nxt - frm);
2430                  break;
2431             default:
2432                 if ((c2 & 0xC0) != 0x80)
2433                     return static_cast<int>(frm_nxt - frm);
2434                  break;
2435             }
2436             if ((c3 & 0xC0) != 0x80)
2437                 break;
2438             if ((((c1 & 0x0Fu) << 12) | ((c2 & 0x3Fu) << 6) | (c3 & 0x3Fu)) > Maxcode)
2439                 break;
2440             frm_nxt += 3;
2441         }
2442         else if (c1 < 0xF5)
2443         {
2444             if (frm_end-frm_nxt < 4)
2445                 break;
2446             uint8_t c2 = frm_nxt[1];
2447             uint8_t c3 = frm_nxt[2];
2448             uint8_t c4 = frm_nxt[3];
2449             switch (c1)
2450             {
2451             case 0xF0:
2452                 if (!(0x90 <= c2 && c2 <= 0xBF))
2453                     return static_cast<int>(frm_nxt - frm);
2454                  break;
2455             case 0xF4:
2456                 if ((c2 & 0xF0) != 0x80)
2457                     return static_cast<int>(frm_nxt - frm);
2458                  break;
2459             default:
2460                 if ((c2 & 0xC0) != 0x80)
2461                     return static_cast<int>(frm_nxt - frm);
2462                  break;
2463             }
2464             if ((c3 & 0xC0) != 0x80 || (c4 & 0xC0) != 0x80)
2465                 break;
2466             if ((((c1 & 0x07u) << 18) | ((c2 & 0x3Fu) << 12) |
2467                  ((c3 & 0x3Fu) << 6)  |  (c4 & 0x3Fu)) > Maxcode)
2468                 break;
2469             frm_nxt += 4;
2470         }
2471         else
2472         {
2473             break;
2474         }
2475     }
2476     return static_cast<int>(frm_nxt - frm);
2477 }
2478
2479 static
2480 codecvt_base::result
2481 ucs2_to_utf8(const uint16_t* frm, const uint16_t* frm_end, const uint16_t*& frm_nxt,
2482              uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt,
2483              unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2484 {
2485     frm_nxt = frm;
2486     to_nxt = to;
2487     if (mode & generate_header)
2488     {
2489         if (to_end-to_nxt < 3)
2490             return codecvt_base::partial;
2491         *to_nxt++ = static_cast<uint8_t>(0xEF);
2492         *to_nxt++ = static_cast<uint8_t>(0xBB);
2493         *to_nxt++ = static_cast<uint8_t>(0xBF);
2494     }
2495     for (; frm_nxt < frm_end; ++frm_nxt)
2496     {
2497         uint16_t wc = *frm_nxt;
2498         if ((wc & 0xF800) == 0xD800 || wc > Maxcode)
2499             return codecvt_base::error;
2500         if (wc < 0x0080)
2501         {
2502             if (to_end-to_nxt < 1)
2503                 return codecvt_base::partial;
2504             *to_nxt++ = static_cast<uint8_t>(wc);
2505         }
2506         else if (wc < 0x0800)
2507         {
2508             if (to_end-to_nxt < 2)
2509                 return codecvt_base::partial;
2510             *to_nxt++ = static_cast<uint8_t>(0xC0 | (wc >> 6));
2511             *to_nxt++ = static_cast<uint8_t>(0x80 | (wc & 0x03F));
2512         }
2513         else // if (wc <= 0xFFFF)
2514         {
2515             if (to_end-to_nxt < 3)
2516                 return codecvt_base::partial;
2517             *to_nxt++ = static_cast<uint8_t>(0xE0 |  (wc >> 12));
2518             *to_nxt++ = static_cast<uint8_t>(0x80 | ((wc & 0x0FC0) >> 6));
2519             *to_nxt++ = static_cast<uint8_t>(0x80 |  (wc & 0x003F));
2520         }
2521     }
2522     return codecvt_base::ok;
2523 }
2524
2525 static
2526 codecvt_base::result
2527 utf8_to_ucs2(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt,
2528              uint16_t* to, uint16_t* to_end, uint16_t*& to_nxt,
2529              unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2530 {
2531     frm_nxt = frm;
2532     to_nxt = to;
2533     if (mode & consume_header)
2534     {
2535         if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB &&
2536                                                           frm_nxt[2] == 0xBF)
2537             frm_nxt += 3;
2538     }
2539     for (; frm_nxt < frm_end && to_nxt < to_end; ++to_nxt)
2540     {
2541         uint8_t c1 = static_cast<uint8_t>(*frm_nxt);
2542         if (c1 < 0x80)
2543         {
2544             if (c1 > Maxcode)
2545                 return codecvt_base::error;
2546             *to_nxt = static_cast<uint16_t>(c1);
2547             ++frm_nxt;
2548         }
2549         else if (c1 < 0xC2)
2550         {
2551             return codecvt_base::error;
2552         }
2553         else if (c1 < 0xE0)
2554         {
2555             if (frm_end-frm_nxt < 2)
2556                 return codecvt_base::partial;
2557             uint8_t c2 = frm_nxt[1];
2558             if ((c2 & 0xC0) != 0x80)
2559                 return codecvt_base::error;
2560             uint16_t t = static_cast<uint16_t>(((c1 & 0x1F) << 6)
2561                                               | (c2 & 0x3F));
2562             if (t > Maxcode)
2563                 return codecvt_base::error;
2564             *to_nxt = t;
2565             frm_nxt += 2;
2566         }
2567         else if (c1 < 0xF0)
2568         {
2569             if (frm_end-frm_nxt < 3)
2570                 return codecvt_base::partial;
2571             uint8_t c2 = frm_nxt[1];
2572             uint8_t c3 = frm_nxt[2];
2573             switch (c1)
2574             {
2575             case 0xE0:
2576                 if ((c2 & 0xE0) != 0xA0)
2577                     return codecvt_base::error;
2578                  break;
2579             case 0xED:
2580                 if ((c2 & 0xE0) != 0x80)
2581                     return codecvt_base::error;
2582                  break;
2583             default:
2584                 if ((c2 & 0xC0) != 0x80)
2585                     return codecvt_base::error;
2586                  break;
2587             }
2588             if ((c3 & 0xC0) != 0x80)
2589                 return codecvt_base::error;
2590             uint16_t t = static_cast<uint16_t>(((c1 & 0x0F) << 12)
2591                                              | ((c2 & 0x3F) << 6)
2592                                              |  (c3 & 0x3F));
2593             if (t > Maxcode)
2594                 return codecvt_base::error;
2595             *to_nxt = t;
2596             frm_nxt += 3;
2597         }
2598         else
2599         {
2600             return codecvt_base::error;
2601         }
2602     }
2603     return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok;
2604 }
2605
2606 static
2607 int
2608 utf8_to_ucs2_length(const uint8_t* frm, const uint8_t* frm_end,
2609                     size_t mx, unsigned long Maxcode = 0x10FFFF,
2610                     codecvt_mode mode = codecvt_mode(0))
2611 {
2612     const uint8_t* frm_nxt = frm;
2613     if (mode & consume_header)
2614     {
2615         if (frm_end-frm_nxt >= 3 && frm_nxt[0] == 0xEF && frm_nxt[1] == 0xBB &&
2616                                                           frm_nxt[2] == 0xBF)
2617             frm_nxt += 3;
2618     }
2619     for (size_t nchar32_t = 0; frm_nxt < frm_end && nchar32_t < mx; ++nchar32_t)
2620     {
2621         uint8_t c1 = static_cast<uint8_t>(*frm_nxt);
2622         if (c1 < 0x80)
2623         {
2624             if (c1 > Maxcode)
2625                 break;
2626             ++frm_nxt;
2627         }
2628         else if (c1 < 0xC2)
2629         {
2630             break;
2631         }
2632         else if (c1 < 0xE0)
2633         {
2634             if ((frm_end-frm_nxt < 2) || ((frm_nxt[1] & 0xC0) != 0x80))
2635                 break;
2636             if ((((c1 & 0x1Fu) << 6) | (frm_nxt[1] & 0x3Fu)) > Maxcode)
2637                 break;
2638             frm_nxt += 2;
2639         }
2640         else if (c1 < 0xF0)
2641         {
2642             if (frm_end-frm_nxt < 3)
2643                 break;
2644             uint8_t c2 = frm_nxt[1];
2645             uint8_t c3 = frm_nxt[2];
2646             switch (c1)
2647             {
2648             case 0xE0:
2649                 if ((c2 & 0xE0) != 0xA0)
2650                     return static_cast<int>(frm_nxt - frm);
2651                 break;
2652             case 0xED:
2653                 if ((c2 & 0xE0) != 0x80)
2654                     return static_cast<int>(frm_nxt - frm);
2655                  break;
2656             default:
2657                 if ((c2 & 0xC0) != 0x80)
2658                     return static_cast<int>(frm_nxt - frm);
2659                  break;
2660             }
2661             if ((c3 & 0xC0) != 0x80)
2662                 break;
2663             if ((((c1 & 0x0Fu) << 12) | ((c2 & 0x3Fu) << 6) | (c3 & 0x3Fu)) > Maxcode)
2664                 break;
2665             frm_nxt += 3;
2666         }
2667         else
2668         {
2669             break;
2670         }
2671     }
2672     return static_cast<int>(frm_nxt - frm);
2673 }
2674
2675 static
2676 codecvt_base::result
2677 ucs4_to_utf16be(const uint32_t* frm, const uint32_t* frm_end, const uint32_t*& frm_nxt,
2678                 uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt,
2679                 unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2680 {
2681     frm_nxt = frm;
2682     to_nxt = to;
2683     if (mode & generate_header)
2684     {
2685         if (to_end-to_nxt < 2)
2686             return codecvt_base::partial;
2687         *to_nxt++ = static_cast<uint8_t>(0xFE);
2688         *to_nxt++ = static_cast<uint8_t>(0xFF);
2689     }
2690     for (; frm_nxt < frm_end; ++frm_nxt)
2691     {
2692         uint32_t wc = *frm_nxt;
2693         if ((wc & 0xFFFFF800) == 0x00D800 || wc > Maxcode)
2694             return codecvt_base::error;
2695         if (wc < 0x010000)
2696         {
2697             if (to_end-to_nxt < 2)
2698                 return codecvt_base::partial;
2699             *to_nxt++ = static_cast<uint8_t>(wc >> 8);
2700             *to_nxt++ = static_cast<uint8_t>(wc);
2701         }
2702         else
2703         {
2704             if (to_end-to_nxt < 4)
2705                 return codecvt_base::partial;
2706             uint16_t t = static_cast<uint16_t>(
2707                     0xD800
2708                   | ((((wc & 0x1F0000) >> 16) - 1) << 6)
2709                   |   ((wc & 0x00FC00) >> 10));
2710             *to_nxt++ = static_cast<uint8_t>(t >> 8);
2711             *to_nxt++ = static_cast<uint8_t>(t);
2712             t = static_cast<uint16_t>(0xDC00 | (wc & 0x03FF));
2713             *to_nxt++ = static_cast<uint8_t>(t >> 8);
2714             *to_nxt++ = static_cast<uint8_t>(t);
2715         }
2716     }
2717     return codecvt_base::ok;
2718 }
2719
2720 static
2721 codecvt_base::result
2722 utf16be_to_ucs4(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt,
2723                 uint32_t* to, uint32_t* to_end, uint32_t*& to_nxt,
2724                 unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2725 {
2726     frm_nxt = frm;
2727     to_nxt = to;
2728     if (mode & consume_header)
2729     {
2730         if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFE && frm_nxt[1] == 0xFF)
2731             frm_nxt += 2;
2732     }
2733     for (; frm_nxt < frm_end - 1 && to_nxt < to_end; ++to_nxt)
2734     {
2735         uint16_t c1 = static_cast<uint16_t>(frm_nxt[0] << 8 | frm_nxt[1]);
2736         if ((c1 & 0xFC00) == 0xDC00)
2737             return codecvt_base::error;
2738         if ((c1 & 0xFC00) != 0xD800)
2739         {
2740             if (c1 > Maxcode)
2741                 return codecvt_base::error;
2742             *to_nxt = static_cast<uint32_t>(c1);
2743             frm_nxt += 2;
2744         }
2745         else
2746         {
2747             if (frm_end-frm_nxt < 4)
2748                 return codecvt_base::partial;
2749             uint16_t c2 = static_cast<uint16_t>(frm_nxt[2] << 8 | frm_nxt[3]);
2750             if ((c2 & 0xFC00) != 0xDC00)
2751                 return codecvt_base::error;
2752             uint32_t t = static_cast<uint32_t>(
2753                     ((((c1 & 0x03C0) >> 6) + 1) << 16)
2754                   |   ((c1 & 0x003F) << 10)
2755                   |    (c2 & 0x03FF));
2756             if (t > Maxcode)
2757                 return codecvt_base::error;
2758             *to_nxt = t;
2759             frm_nxt += 4;
2760         }
2761     }
2762     return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok;
2763 }
2764
2765 static
2766 int
2767 utf16be_to_ucs4_length(const uint8_t* frm, const uint8_t* frm_end,
2768                        size_t mx, unsigned long Maxcode = 0x10FFFF,
2769                        codecvt_mode mode = codecvt_mode(0))
2770 {
2771     const uint8_t* frm_nxt = frm;
2772     if (mode & consume_header)
2773     {
2774         if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFE && frm_nxt[1] == 0xFF)
2775             frm_nxt += 2;
2776     }
2777     for (size_t nchar32_t = 0; frm_nxt < frm_end - 1 && nchar32_t < mx; ++nchar32_t)
2778     {
2779         uint16_t c1 = static_cast<uint16_t>(frm_nxt[0] << 8 | frm_nxt[1]);
2780         if ((c1 & 0xFC00) == 0xDC00)
2781             break;
2782         if ((c1 & 0xFC00) != 0xD800)
2783         {
2784             if (c1 > Maxcode)
2785                 break;
2786             frm_nxt += 2;
2787         }
2788         else
2789         {
2790             if (frm_end-frm_nxt < 4)
2791                 break;
2792             uint16_t c2 = static_cast<uint16_t>(frm_nxt[2] << 8 | frm_nxt[3]);
2793             if ((c2 & 0xFC00) != 0xDC00)
2794                 break;
2795             uint32_t t = static_cast<uint32_t>(
2796                     ((((c1 & 0x03C0) >> 6) + 1) << 16)
2797                   |   ((c1 & 0x003F) << 10)
2798                   |    (c2 & 0x03FF));
2799             if (t > Maxcode)
2800                 break;
2801             frm_nxt += 4;
2802         }
2803     }
2804     return static_cast<int>(frm_nxt - frm);
2805 }
2806
2807 static
2808 codecvt_base::result
2809 ucs4_to_utf16le(const uint32_t* frm, const uint32_t* frm_end, const uint32_t*& frm_nxt,
2810                 uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt,
2811                 unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2812 {
2813     frm_nxt = frm;
2814     to_nxt = to;
2815     if (mode & generate_header)
2816     {
2817         if (to_end - to_nxt < 2)
2818             return codecvt_base::partial;
2819         *to_nxt++ = static_cast<uint8_t>(0xFF);
2820         *to_nxt++ = static_cast<uint8_t>(0xFE);
2821     }
2822     for (; frm_nxt < frm_end; ++frm_nxt)
2823     {
2824         uint32_t wc = *frm_nxt;
2825         if ((wc & 0xFFFFF800) == 0x00D800 || wc > Maxcode)
2826             return codecvt_base::error;
2827         if (wc < 0x010000)
2828         {
2829             if (to_end-to_nxt < 2)
2830                 return codecvt_base::partial;
2831             *to_nxt++ = static_cast<uint8_t>(wc);
2832             *to_nxt++ = static_cast<uint8_t>(wc >> 8);
2833         }
2834         else
2835         {
2836             if (to_end-to_nxt < 4)
2837                 return codecvt_base::partial;
2838             uint16_t t = static_cast<uint16_t>(
2839                     0xD800
2840                   | ((((wc & 0x1F0000) >> 16) - 1) << 6)
2841                   |   ((wc & 0x00FC00) >> 10));
2842             *to_nxt++ = static_cast<uint8_t>(t);
2843             *to_nxt++ = static_cast<uint8_t>(t >> 8);
2844             t = static_cast<uint16_t>(0xDC00 | (wc & 0x03FF));
2845             *to_nxt++ = static_cast<uint8_t>(t);
2846             *to_nxt++ = static_cast<uint8_t>(t >> 8);
2847         }
2848     }
2849     return codecvt_base::ok;
2850 }
2851
2852 static
2853 codecvt_base::result
2854 utf16le_to_ucs4(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt,
2855                 uint32_t* to, uint32_t* to_end, uint32_t*& to_nxt,
2856                 unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2857 {
2858     frm_nxt = frm;
2859     to_nxt = to;
2860     if (mode & consume_header)
2861     {
2862         if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFF && frm_nxt[1] == 0xFE)
2863             frm_nxt += 2;
2864     }
2865     for (; frm_nxt < frm_end - 1 && to_nxt < to_end; ++to_nxt)
2866     {
2867         uint16_t c1 = static_cast<uint16_t>(frm_nxt[1] << 8 | frm_nxt[0]);
2868         if ((c1 & 0xFC00) == 0xDC00)
2869             return codecvt_base::error;
2870         if ((c1 & 0xFC00) != 0xD800)
2871         {
2872             if (c1 > Maxcode)
2873                 return codecvt_base::error;
2874             *to_nxt = static_cast<uint32_t>(c1);
2875             frm_nxt += 2;
2876         }
2877         else
2878         {
2879             if (frm_end-frm_nxt < 4)
2880                 return codecvt_base::partial;
2881             uint16_t c2 = static_cast<uint16_t>(frm_nxt[3] << 8 | frm_nxt[2]);
2882             if ((c2 & 0xFC00) != 0xDC00)
2883                 return codecvt_base::error;
2884             uint32_t t = static_cast<uint32_t>(
2885                     ((((c1 & 0x03C0) >> 6) + 1) << 16)
2886                   |   ((c1 & 0x003F) << 10)
2887                   |    (c2 & 0x03FF));
2888             if (t > Maxcode)
2889                 return codecvt_base::error;
2890             *to_nxt = t;
2891             frm_nxt += 4;
2892         }
2893     }
2894     return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok;
2895 }
2896
2897 static
2898 int
2899 utf16le_to_ucs4_length(const uint8_t* frm, const uint8_t* frm_end,
2900                        size_t mx, unsigned long Maxcode = 0x10FFFF,
2901                        codecvt_mode mode = codecvt_mode(0))
2902 {
2903     const uint8_t* frm_nxt = frm;
2904     if (mode & consume_header)
2905     {
2906         if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFF && frm_nxt[1] == 0xFE)
2907             frm_nxt += 2;
2908     }
2909     for (size_t nchar32_t = 0; frm_nxt < frm_end - 1 && nchar32_t < mx; ++nchar32_t)
2910     {
2911         uint16_t c1 = static_cast<uint16_t>(frm_nxt[1] << 8 | frm_nxt[0]);
2912         if ((c1 & 0xFC00) == 0xDC00)
2913             break;
2914         if ((c1 & 0xFC00) != 0xD800)
2915         {
2916             if (c1 > Maxcode)
2917                 break;
2918             frm_nxt += 2;
2919         }
2920         else
2921         {
2922             if (frm_end-frm_nxt < 4)
2923                 break;
2924             uint16_t c2 = static_cast<uint16_t>(frm_nxt[3] << 8 | frm_nxt[2]);
2925             if ((c2 & 0xFC00) != 0xDC00)
2926                 break;
2927             uint32_t t = static_cast<uint32_t>(
2928                     ((((c1 & 0x03C0) >> 6) + 1) << 16)
2929                   |   ((c1 & 0x003F) << 10)
2930                   |    (c2 & 0x03FF));
2931             if (t > Maxcode)
2932                 break;
2933             frm_nxt += 4;
2934         }
2935     }
2936     return static_cast<int>(frm_nxt - frm);
2937 }
2938
2939 static
2940 codecvt_base::result
2941 ucs2_to_utf16be(const uint16_t* frm, const uint16_t* frm_end, const uint16_t*& frm_nxt,
2942                 uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt,
2943                 unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2944 {
2945     frm_nxt = frm;
2946     to_nxt = to;
2947     if (mode & generate_header)
2948     {
2949         if (to_end-to_nxt < 2)
2950             return codecvt_base::partial;
2951         *to_nxt++ = static_cast<uint8_t>(0xFE);
2952         *to_nxt++ = static_cast<uint8_t>(0xFF);
2953     }
2954     for (; frm_nxt < frm_end; ++frm_nxt)
2955     {
2956         uint16_t wc = *frm_nxt;
2957         if ((wc & 0xF800) == 0xD800 || wc > Maxcode)
2958             return codecvt_base::error;
2959         if (to_end-to_nxt < 2)
2960             return codecvt_base::partial;
2961         *to_nxt++ = static_cast<uint8_t>(wc >> 8);
2962         *to_nxt++ = static_cast<uint8_t>(wc);
2963     }
2964     return codecvt_base::ok;
2965 }
2966
2967 static
2968 codecvt_base::result
2969 utf16be_to_ucs2(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt,
2970                 uint16_t* to, uint16_t* to_end, uint16_t*& to_nxt,
2971                 unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
2972 {
2973     frm_nxt = frm;
2974     to_nxt = to;
2975     if (mode & consume_header)
2976     {
2977         if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFE && frm_nxt[1] == 0xFF)
2978             frm_nxt += 2;
2979     }
2980     for (; frm_nxt < frm_end - 1 && to_nxt < to_end; ++to_nxt)
2981     {
2982         uint16_t c1 = static_cast<uint16_t>(frm_nxt[0] << 8 | frm_nxt[1]);
2983         if ((c1 & 0xF800) == 0xD800 || c1 > Maxcode)
2984             return codecvt_base::error;
2985         *to_nxt = c1;
2986         frm_nxt += 2;
2987     }
2988     return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok;
2989 }
2990
2991 static
2992 int
2993 utf16be_to_ucs2_length(const uint8_t* frm, const uint8_t* frm_end,
2994                        size_t mx, unsigned long Maxcode = 0x10FFFF,
2995                        codecvt_mode mode = codecvt_mode(0))
2996 {
2997     const uint8_t* frm_nxt = frm;
2998     if (mode & consume_header)
2999     {
3000         if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFE && frm_nxt[1] == 0xFF)
3001             frm_nxt += 2;
3002     }
3003     for (size_t nchar16_t = 0; frm_nxt < frm_end - 1 && nchar16_t < mx; ++nchar16_t)
3004     {
3005         uint16_t c1 = static_cast<uint16_t>(frm_nxt[0] << 8 | frm_nxt[1]);
3006         if ((c1 & 0xF800) == 0xD800 || c1 > Maxcode)
3007             break;
3008         frm_nxt += 2;
3009     }
3010     return static_cast<int>(frm_nxt - frm);
3011 }
3012
3013 static
3014 codecvt_base::result
3015 ucs2_to_utf16le(const uint16_t* frm, const uint16_t* frm_end, const uint16_t*& frm_nxt,
3016                 uint8_t* to, uint8_t* to_end, uint8_t*& to_nxt,
3017                 unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
3018 {
3019     frm_nxt = frm;
3020     to_nxt = to;
3021     if (mode & generate_header)
3022     {
3023         if (to_end-to_nxt < 2)
3024             return codecvt_base::partial;
3025         *to_nxt++ = static_cast<uint8_t>(0xFF);
3026         *to_nxt++ = static_cast<uint8_t>(0xFE);
3027     }
3028     for (; frm_nxt < frm_end; ++frm_nxt)
3029     {
3030         uint16_t wc = *frm_nxt;
3031         if ((wc & 0xF800) == 0xD800 || wc > Maxcode)
3032             return codecvt_base::error;
3033         if (to_end-to_nxt < 2)
3034             return codecvt_base::partial;
3035         *to_nxt++ = static_cast<uint8_t>(wc);
3036         *to_nxt++ = static_cast<uint8_t>(wc >> 8);
3037     }
3038     return codecvt_base::ok;
3039 }
3040
3041 static
3042 codecvt_base::result
3043 utf16le_to_ucs2(const uint8_t* frm, const uint8_t* frm_end, const uint8_t*& frm_nxt,
3044                 uint16_t* to, uint16_t* to_end, uint16_t*& to_nxt,
3045                 unsigned long Maxcode = 0x10FFFF, codecvt_mode mode = codecvt_mode(0))
3046 {
3047     frm_nxt = frm;
3048     to_nxt = to;
3049     if (mode & consume_header)
3050     {
3051         if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFF && frm_nxt[1] == 0xFE)
3052             frm_nxt += 2;
3053     }
3054     for (; frm_nxt < frm_end - 1 && to_nxt < to_end; ++to_nxt)
3055     {
3056         uint16_t c1 = static_cast<uint16_t>(frm_nxt[1] << 8 | frm_nxt[0]);
3057         if ((c1 & 0xF800) == 0xD800 || c1 > Maxcode)
3058             return codecvt_base::error;
3059         *to_nxt = c1;
3060         frm_nxt += 2;
3061     }
3062     return frm_nxt < frm_end ? codecvt_base::partial : codecvt_base::ok;
3063 }
3064
3065 static
3066 int
3067 utf16le_to_ucs2_length(const uint8_t* frm, const uint8_t* frm_end,
3068                        size_t mx, unsigned long Maxcode = 0x10FFFF,
3069                        codecvt_mode mode = codecvt_mode(0))
3070 {
3071     const uint8_t* frm_nxt = frm;
3072     frm_nxt = frm;
3073     if (mode & consume_header)
3074     {
3075         if (frm_end-frm_nxt >= 2 && frm_nxt[0] == 0xFF && frm_nxt[1] == 0xFE)
3076             frm_nxt += 2;
3077     }
3078     for (size_t nchar16_t = 0; frm_nxt < frm_end - 1 && nchar16_t < mx; ++nchar16_t)
3079     {
3080         uint16_t c1 = static_cast<uint16_t>(frm_nxt[1] << 8 | frm_nxt[0]);
3081         if ((c1 & 0xF800) == 0xD800 || c1 > Maxcode)
3082             break;
3083         frm_nxt += 2;
3084     }
3085     return static_cast<int>(frm_nxt - frm);
3086 }
3087
3088 // template <> class codecvt<char16_t, char, mbstate_t>
3089
3090 locale::id codecvt<char16_t, char, mbstate_t>::id;
3091
3092 codecvt<char16_t, char, mbstate_t>::~codecvt()
3093 {
3094 }
3095
3096 codecvt<char16_t, char, mbstate_t>::result
3097 codecvt<char16_t, char, mbstate_t>::do_out(state_type&,
3098     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3099     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3100 {
3101     const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm);
3102     const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end);
3103     const uint16_t* _frm_nxt = _frm;
3104     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3105     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3106     uint8_t* _to_nxt = _to;
3107     result r = utf16_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt);
3108     frm_nxt = frm + (_frm_nxt - _frm);
3109     to_nxt = to + (_to_nxt - _to);
3110     return r;
3111 }
3112
3113 codecvt<char16_t, char, mbstate_t>::result
3114 codecvt<char16_t, char, mbstate_t>::do_in(state_type&,
3115     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3116     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3117 {
3118     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3119     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3120     const uint8_t* _frm_nxt = _frm;
3121     uint16_t* _to = reinterpret_cast<uint16_t*>(to);
3122     uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end);
3123     uint16_t* _to_nxt = _to;
3124     result r = utf8_to_utf16(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt);
3125     frm_nxt = frm + (_frm_nxt - _frm);
3126     to_nxt = to + (_to_nxt - _to);
3127     return r;
3128 }
3129
3130 codecvt<char16_t, char, mbstate_t>::result
3131 codecvt<char16_t, char, mbstate_t>::do_unshift(state_type&,
3132     extern_type* to, extern_type*, extern_type*& to_nxt) const
3133 {
3134     to_nxt = to;
3135     return noconv;
3136 }
3137
3138 int
3139 codecvt<char16_t, char, mbstate_t>::do_encoding() const  _NOEXCEPT
3140 {
3141     return 0;
3142 }
3143
3144 bool
3145 codecvt<char16_t, char, mbstate_t>::do_always_noconv() const  _NOEXCEPT
3146 {
3147     return false;
3148 }
3149
3150 int
3151 codecvt<char16_t, char, mbstate_t>::do_length(state_type&,
3152     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3153 {
3154     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3155     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3156     return utf8_to_utf16_length(_frm, _frm_end, mx);
3157 }
3158
3159 int
3160 codecvt<char16_t, char, mbstate_t>::do_max_length() const  _NOEXCEPT
3161 {
3162     return 4;
3163 }
3164
3165 // template <> class codecvt<char32_t, char, mbstate_t>
3166
3167 locale::id codecvt<char32_t, char, mbstate_t>::id;
3168
3169 codecvt<char32_t, char, mbstate_t>::~codecvt()
3170 {
3171 }
3172
3173 codecvt<char32_t, char, mbstate_t>::result
3174 codecvt<char32_t, char, mbstate_t>::do_out(state_type&,
3175     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3176     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3177 {
3178     const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm);
3179     const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end);
3180     const uint32_t* _frm_nxt = _frm;
3181     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3182     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3183     uint8_t* _to_nxt = _to;
3184     result r = ucs4_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt);
3185     frm_nxt = frm + (_frm_nxt - _frm);
3186     to_nxt = to + (_to_nxt - _to);
3187     return r;
3188 }
3189
3190 codecvt<char32_t, char, mbstate_t>::result
3191 codecvt<char32_t, char, mbstate_t>::do_in(state_type&,
3192     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3193     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3194 {
3195     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3196     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3197     const uint8_t* _frm_nxt = _frm;
3198     uint32_t* _to = reinterpret_cast<uint32_t*>(to);
3199     uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end);
3200     uint32_t* _to_nxt = _to;
3201     result r = utf8_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt);
3202     frm_nxt = frm + (_frm_nxt - _frm);
3203     to_nxt = to + (_to_nxt - _to);
3204     return r;
3205 }
3206
3207 codecvt<char32_t, char, mbstate_t>::result
3208 codecvt<char32_t, char, mbstate_t>::do_unshift(state_type&,
3209     extern_type* to, extern_type*, extern_type*& to_nxt) const
3210 {
3211     to_nxt = to;
3212     return noconv;
3213 }
3214
3215 int
3216 codecvt<char32_t, char, mbstate_t>::do_encoding() const  _NOEXCEPT
3217 {
3218     return 0;
3219 }
3220
3221 bool
3222 codecvt<char32_t, char, mbstate_t>::do_always_noconv() const  _NOEXCEPT
3223 {
3224     return false;
3225 }
3226
3227 int
3228 codecvt<char32_t, char, mbstate_t>::do_length(state_type&,
3229     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3230 {
3231     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3232     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3233     return utf8_to_ucs4_length(_frm, _frm_end, mx);
3234 }
3235
3236 int
3237 codecvt<char32_t, char, mbstate_t>::do_max_length() const  _NOEXCEPT
3238 {
3239     return 4;
3240 }
3241
3242 // __codecvt_utf8<wchar_t>
3243
3244 __codecvt_utf8<wchar_t>::result
3245 __codecvt_utf8<wchar_t>::do_out(state_type&,
3246     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3247     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3248 {
3249 #if defined(_LIBCPP_SHORT_WCHAR)
3250     const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm);
3251     const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end);
3252     const uint16_t* _frm_nxt = _frm;
3253 #else
3254     const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm);
3255     const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end);
3256     const uint32_t* _frm_nxt = _frm;
3257 #endif
3258     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3259     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3260     uint8_t* _to_nxt = _to;
3261 #if defined(_LIBCPP_SHORT_WCHAR)
3262     result r = ucs2_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3263                             _Maxcode_, _Mode_);
3264 #else
3265     result r = ucs4_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3266                             _Maxcode_, _Mode_);
3267 #endif
3268     frm_nxt = frm + (_frm_nxt - _frm);
3269     to_nxt = to + (_to_nxt - _to);
3270     return r;
3271 }
3272
3273 __codecvt_utf8<wchar_t>::result
3274 __codecvt_utf8<wchar_t>::do_in(state_type&,
3275     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3276     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3277 {
3278     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3279     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3280     const uint8_t* _frm_nxt = _frm;
3281 #if defined(_LIBCPP_SHORT_WCHAR)
3282     uint16_t* _to = reinterpret_cast<uint16_t*>(to);
3283     uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end);
3284     uint16_t* _to_nxt = _to;
3285     result r = utf8_to_ucs2(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3286                             _Maxcode_, _Mode_);
3287 #else
3288     uint32_t* _to = reinterpret_cast<uint32_t*>(to);
3289     uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end);
3290     uint32_t* _to_nxt = _to;
3291     result r = utf8_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3292                             _Maxcode_, _Mode_);
3293 #endif
3294     frm_nxt = frm + (_frm_nxt - _frm);
3295     to_nxt = to + (_to_nxt - _to);
3296     return r;
3297 }
3298
3299 __codecvt_utf8<wchar_t>::result
3300 __codecvt_utf8<wchar_t>::do_unshift(state_type&,
3301     extern_type* to, extern_type*, extern_type*& to_nxt) const
3302 {
3303     to_nxt = to;
3304     return noconv;
3305 }
3306
3307 int
3308 __codecvt_utf8<wchar_t>::do_encoding() const  _NOEXCEPT
3309 {
3310     return 0;
3311 }
3312
3313 bool
3314 __codecvt_utf8<wchar_t>::do_always_noconv() const  _NOEXCEPT
3315 {
3316     return false;
3317 }
3318
3319 int
3320 __codecvt_utf8<wchar_t>::do_length(state_type&,
3321     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3322 {
3323     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3324     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3325     return utf8_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
3326 }
3327
3328 int
3329 __codecvt_utf8<wchar_t>::do_max_length() const  _NOEXCEPT
3330 {
3331     if (_Mode_ & consume_header)
3332         return 7;
3333     return 4;
3334 }
3335
3336 // __codecvt_utf8<char16_t>
3337
3338 __codecvt_utf8<char16_t>::result
3339 __codecvt_utf8<char16_t>::do_out(state_type&,
3340     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3341     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3342 {
3343     const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm);
3344     const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end);
3345     const uint16_t* _frm_nxt = _frm;
3346     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3347     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3348     uint8_t* _to_nxt = _to;
3349     result r = ucs2_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3350                             _Maxcode_, _Mode_);
3351     frm_nxt = frm + (_frm_nxt - _frm);
3352     to_nxt = to + (_to_nxt - _to);
3353     return r;
3354 }
3355
3356 __codecvt_utf8<char16_t>::result
3357 __codecvt_utf8<char16_t>::do_in(state_type&,
3358     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3359     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3360 {
3361     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3362     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3363     const uint8_t* _frm_nxt = _frm;
3364     uint16_t* _to = reinterpret_cast<uint16_t*>(to);
3365     uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end);
3366     uint16_t* _to_nxt = _to;
3367     result r = utf8_to_ucs2(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3368                             _Maxcode_, _Mode_);
3369     frm_nxt = frm + (_frm_nxt - _frm);
3370     to_nxt = to + (_to_nxt - _to);
3371     return r;
3372 }
3373
3374 __codecvt_utf8<char16_t>::result
3375 __codecvt_utf8<char16_t>::do_unshift(state_type&,
3376     extern_type* to, extern_type*, extern_type*& to_nxt) const
3377 {
3378     to_nxt = to;
3379     return noconv;
3380 }
3381
3382 int
3383 __codecvt_utf8<char16_t>::do_encoding() const  _NOEXCEPT
3384 {
3385     return 0;
3386 }
3387
3388 bool
3389 __codecvt_utf8<char16_t>::do_always_noconv() const  _NOEXCEPT
3390 {
3391     return false;
3392 }
3393
3394 int
3395 __codecvt_utf8<char16_t>::do_length(state_type&,
3396     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3397 {
3398     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3399     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3400     return utf8_to_ucs2_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
3401 }
3402
3403 int
3404 __codecvt_utf8<char16_t>::do_max_length() const  _NOEXCEPT
3405 {
3406     if (_Mode_ & consume_header)
3407         return 6;
3408     return 3;
3409 }
3410
3411 // __codecvt_utf8<char32_t>
3412
3413 __codecvt_utf8<char32_t>::result
3414 __codecvt_utf8<char32_t>::do_out(state_type&,
3415     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3416     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3417 {
3418     const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm);
3419     const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end);
3420     const uint32_t* _frm_nxt = _frm;
3421     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3422     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3423     uint8_t* _to_nxt = _to;
3424     result r = ucs4_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3425                             _Maxcode_, _Mode_);
3426     frm_nxt = frm + (_frm_nxt - _frm);
3427     to_nxt = to + (_to_nxt - _to);
3428     return r;
3429 }
3430
3431 __codecvt_utf8<char32_t>::result
3432 __codecvt_utf8<char32_t>::do_in(state_type&,
3433     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3434     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3435 {
3436     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3437     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3438     const uint8_t* _frm_nxt = _frm;
3439     uint32_t* _to = reinterpret_cast<uint32_t*>(to);
3440     uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end);
3441     uint32_t* _to_nxt = _to;
3442     result r = utf8_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3443                             _Maxcode_, _Mode_);
3444     frm_nxt = frm + (_frm_nxt - _frm);
3445     to_nxt = to + (_to_nxt - _to);
3446     return r;
3447 }
3448
3449 __codecvt_utf8<char32_t>::result
3450 __codecvt_utf8<char32_t>::do_unshift(state_type&,
3451     extern_type* to, extern_type*, extern_type*& to_nxt) const
3452 {
3453     to_nxt = to;
3454     return noconv;
3455 }
3456
3457 int
3458 __codecvt_utf8<char32_t>::do_encoding() const  _NOEXCEPT
3459 {
3460     return 0;
3461 }
3462
3463 bool
3464 __codecvt_utf8<char32_t>::do_always_noconv() const  _NOEXCEPT
3465 {
3466     return false;
3467 }
3468
3469 int
3470 __codecvt_utf8<char32_t>::do_length(state_type&,
3471     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3472 {
3473     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3474     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3475     return utf8_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
3476 }
3477
3478 int
3479 __codecvt_utf8<char32_t>::do_max_length() const  _NOEXCEPT
3480 {
3481     if (_Mode_ & consume_header)
3482         return 7;
3483     return 4;
3484 }
3485
3486 // __codecvt_utf16<wchar_t, false>
3487
3488 __codecvt_utf16<wchar_t, false>::result
3489 __codecvt_utf16<wchar_t, false>::do_out(state_type&,
3490     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3491     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3492 {
3493     const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm);
3494     const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end);
3495     const uint32_t* _frm_nxt = _frm;
3496     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3497     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3498     uint8_t* _to_nxt = _to;
3499     result r = ucs4_to_utf16be(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3500                                _Maxcode_, _Mode_);
3501     frm_nxt = frm + (_frm_nxt - _frm);
3502     to_nxt = to + (_to_nxt - _to);
3503     return r;
3504 }
3505
3506 __codecvt_utf16<wchar_t, false>::result
3507 __codecvt_utf16<wchar_t, false>::do_in(state_type&,
3508     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3509     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3510 {
3511     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3512     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3513     const uint8_t* _frm_nxt = _frm;
3514     uint32_t* _to = reinterpret_cast<uint32_t*>(to);
3515     uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end);
3516     uint32_t* _to_nxt = _to;
3517     result r = utf16be_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3518                                _Maxcode_, _Mode_);
3519     frm_nxt = frm + (_frm_nxt - _frm);
3520     to_nxt = to + (_to_nxt - _to);
3521     return r;
3522 }
3523
3524 __codecvt_utf16<wchar_t, false>::result
3525 __codecvt_utf16<wchar_t, false>::do_unshift(state_type&,
3526     extern_type* to, extern_type*, extern_type*& to_nxt) const
3527 {
3528     to_nxt = to;
3529     return noconv;
3530 }
3531
3532 int
3533 __codecvt_utf16<wchar_t, false>::do_encoding() const  _NOEXCEPT
3534 {
3535     return 0;
3536 }
3537
3538 bool
3539 __codecvt_utf16<wchar_t, false>::do_always_noconv() const  _NOEXCEPT
3540 {
3541     return false;
3542 }
3543
3544 int
3545 __codecvt_utf16<wchar_t, false>::do_length(state_type&,
3546     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3547 {
3548     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3549     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3550     return utf16be_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
3551 }
3552
3553 int
3554 __codecvt_utf16<wchar_t, false>::do_max_length() const  _NOEXCEPT
3555 {
3556     if (_Mode_ & consume_header)
3557         return 6;
3558     return 4;
3559 }
3560
3561 // __codecvt_utf16<wchar_t, true>
3562
3563 __codecvt_utf16<wchar_t, true>::result
3564 __codecvt_utf16<wchar_t, true>::do_out(state_type&,
3565     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3566     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3567 {
3568     const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm);
3569     const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end);
3570     const uint32_t* _frm_nxt = _frm;
3571     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3572     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3573     uint8_t* _to_nxt = _to;
3574     result r = ucs4_to_utf16le(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3575                                _Maxcode_, _Mode_);
3576     frm_nxt = frm + (_frm_nxt - _frm);
3577     to_nxt = to + (_to_nxt - _to);
3578     return r;
3579 }
3580
3581 __codecvt_utf16<wchar_t, true>::result
3582 __codecvt_utf16<wchar_t, true>::do_in(state_type&,
3583     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3584     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3585 {
3586     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3587     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3588     const uint8_t* _frm_nxt = _frm;
3589     uint32_t* _to = reinterpret_cast<uint32_t*>(to);
3590     uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end);
3591     uint32_t* _to_nxt = _to;
3592     result r = utf16le_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3593                                _Maxcode_, _Mode_);
3594     frm_nxt = frm + (_frm_nxt - _frm);
3595     to_nxt = to + (_to_nxt - _to);
3596     return r;
3597 }
3598
3599 __codecvt_utf16<wchar_t, true>::result
3600 __codecvt_utf16<wchar_t, true>::do_unshift(state_type&,
3601     extern_type* to, extern_type*, extern_type*& to_nxt) const
3602 {
3603     to_nxt = to;
3604     return noconv;
3605 }
3606
3607 int
3608 __codecvt_utf16<wchar_t, true>::do_encoding() const  _NOEXCEPT
3609 {
3610     return 0;
3611 }
3612
3613 bool
3614 __codecvt_utf16<wchar_t, true>::do_always_noconv() const  _NOEXCEPT
3615 {
3616     return false;
3617 }
3618
3619 int
3620 __codecvt_utf16<wchar_t, true>::do_length(state_type&,
3621     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3622 {
3623     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3624     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3625     return utf16le_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
3626 }
3627
3628 int
3629 __codecvt_utf16<wchar_t, true>::do_max_length() const  _NOEXCEPT
3630 {
3631     if (_Mode_ & consume_header)
3632         return 6;
3633     return 4;
3634 }
3635
3636 // __codecvt_utf16<char16_t, false>
3637
3638 __codecvt_utf16<char16_t, false>::result
3639 __codecvt_utf16<char16_t, false>::do_out(state_type&,
3640     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3641     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3642 {
3643     const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm);
3644     const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end);
3645     const uint16_t* _frm_nxt = _frm;
3646     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3647     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3648     uint8_t* _to_nxt = _to;
3649     result r = ucs2_to_utf16be(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3650                                _Maxcode_, _Mode_);
3651     frm_nxt = frm + (_frm_nxt - _frm);
3652     to_nxt = to + (_to_nxt - _to);
3653     return r;
3654 }
3655
3656 __codecvt_utf16<char16_t, false>::result
3657 __codecvt_utf16<char16_t, false>::do_in(state_type&,
3658     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3659     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3660 {
3661     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3662     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3663     const uint8_t* _frm_nxt = _frm;
3664     uint16_t* _to = reinterpret_cast<uint16_t*>(to);
3665     uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end);
3666     uint16_t* _to_nxt = _to;
3667     result r = utf16be_to_ucs2(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3668                                _Maxcode_, _Mode_);
3669     frm_nxt = frm + (_frm_nxt - _frm);
3670     to_nxt = to + (_to_nxt - _to);
3671     return r;
3672 }
3673
3674 __codecvt_utf16<char16_t, false>::result
3675 __codecvt_utf16<char16_t, false>::do_unshift(state_type&,
3676     extern_type* to, extern_type*, extern_type*& to_nxt) const
3677 {
3678     to_nxt = to;
3679     return noconv;
3680 }
3681
3682 int
3683 __codecvt_utf16<char16_t, false>::do_encoding() const  _NOEXCEPT
3684 {
3685     return 0;
3686 }
3687
3688 bool
3689 __codecvt_utf16<char16_t, false>::do_always_noconv() const  _NOEXCEPT
3690 {
3691     return false;
3692 }
3693
3694 int
3695 __codecvt_utf16<char16_t, false>::do_length(state_type&,
3696     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3697 {
3698     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3699     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3700     return utf16be_to_ucs2_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
3701 }
3702
3703 int
3704 __codecvt_utf16<char16_t, false>::do_max_length() const  _NOEXCEPT
3705 {
3706     if (_Mode_ & consume_header)
3707         return 4;
3708     return 2;
3709 }
3710
3711 // __codecvt_utf16<char16_t, true>
3712
3713 __codecvt_utf16<char16_t, true>::result
3714 __codecvt_utf16<char16_t, true>::do_out(state_type&,
3715     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3716     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3717 {
3718     const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm);
3719     const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end);
3720     const uint16_t* _frm_nxt = _frm;
3721     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3722     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3723     uint8_t* _to_nxt = _to;
3724     result r = ucs2_to_utf16le(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3725                                _Maxcode_, _Mode_);
3726     frm_nxt = frm + (_frm_nxt - _frm);
3727     to_nxt = to + (_to_nxt - _to);
3728     return r;
3729 }
3730
3731 __codecvt_utf16<char16_t, true>::result
3732 __codecvt_utf16<char16_t, true>::do_in(state_type&,
3733     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3734     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3735 {
3736     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3737     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3738     const uint8_t* _frm_nxt = _frm;
3739     uint16_t* _to = reinterpret_cast<uint16_t*>(to);
3740     uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end);
3741     uint16_t* _to_nxt = _to;
3742     result r = utf16le_to_ucs2(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3743                                _Maxcode_, _Mode_);
3744     frm_nxt = frm + (_frm_nxt - _frm);
3745     to_nxt = to + (_to_nxt - _to);
3746     return r;
3747 }
3748
3749 __codecvt_utf16<char16_t, true>::result
3750 __codecvt_utf16<char16_t, true>::do_unshift(state_type&,
3751     extern_type* to, extern_type*, extern_type*& to_nxt) const
3752 {
3753     to_nxt = to;
3754     return noconv;
3755 }
3756
3757 int
3758 __codecvt_utf16<char16_t, true>::do_encoding() const  _NOEXCEPT
3759 {
3760     return 0;
3761 }
3762
3763 bool
3764 __codecvt_utf16<char16_t, true>::do_always_noconv() const  _NOEXCEPT
3765 {
3766     return false;
3767 }
3768
3769 int
3770 __codecvt_utf16<char16_t, true>::do_length(state_type&,
3771     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3772 {
3773     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3774     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3775     return utf16le_to_ucs2_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
3776 }
3777
3778 int
3779 __codecvt_utf16<char16_t, true>::do_max_length() const  _NOEXCEPT
3780 {
3781     if (_Mode_ & consume_header)
3782         return 4;
3783     return 2;
3784 }
3785
3786 // __codecvt_utf16<char32_t, false>
3787
3788 __codecvt_utf16<char32_t, false>::result
3789 __codecvt_utf16<char32_t, false>::do_out(state_type&,
3790     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3791     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3792 {
3793     const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm);
3794     const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end);
3795     const uint32_t* _frm_nxt = _frm;
3796     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3797     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3798     uint8_t* _to_nxt = _to;
3799     result r = ucs4_to_utf16be(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3800                                _Maxcode_, _Mode_);
3801     frm_nxt = frm + (_frm_nxt - _frm);
3802     to_nxt = to + (_to_nxt - _to);
3803     return r;
3804 }
3805
3806 __codecvt_utf16<char32_t, false>::result
3807 __codecvt_utf16<char32_t, false>::do_in(state_type&,
3808     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3809     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3810 {
3811     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3812     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3813     const uint8_t* _frm_nxt = _frm;
3814     uint32_t* _to = reinterpret_cast<uint32_t*>(to);
3815     uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end);
3816     uint32_t* _to_nxt = _to;
3817     result r = utf16be_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3818                                _Maxcode_, _Mode_);
3819     frm_nxt = frm + (_frm_nxt - _frm);
3820     to_nxt = to + (_to_nxt - _to);
3821     return r;
3822 }
3823
3824 __codecvt_utf16<char32_t, false>::result
3825 __codecvt_utf16<char32_t, false>::do_unshift(state_type&,
3826     extern_type* to, extern_type*, extern_type*& to_nxt) const
3827 {
3828     to_nxt = to;
3829     return noconv;
3830 }
3831
3832 int
3833 __codecvt_utf16<char32_t, false>::do_encoding() const  _NOEXCEPT
3834 {
3835     return 0;
3836 }
3837
3838 bool
3839 __codecvt_utf16<char32_t, false>::do_always_noconv() const  _NOEXCEPT
3840 {
3841     return false;
3842 }
3843
3844 int
3845 __codecvt_utf16<char32_t, false>::do_length(state_type&,
3846     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3847 {
3848     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3849     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3850     return utf16be_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
3851 }
3852
3853 int
3854 __codecvt_utf16<char32_t, false>::do_max_length() const  _NOEXCEPT
3855 {
3856     if (_Mode_ & consume_header)
3857         return 6;
3858     return 4;
3859 }
3860
3861 // __codecvt_utf16<char32_t, true>
3862
3863 __codecvt_utf16<char32_t, true>::result
3864 __codecvt_utf16<char32_t, true>::do_out(state_type&,
3865     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3866     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3867 {
3868     const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm);
3869     const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end);
3870     const uint32_t* _frm_nxt = _frm;
3871     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3872     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3873     uint8_t* _to_nxt = _to;
3874     result r = ucs4_to_utf16le(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3875                                _Maxcode_, _Mode_);
3876     frm_nxt = frm + (_frm_nxt - _frm);
3877     to_nxt = to + (_to_nxt - _to);
3878     return r;
3879 }
3880
3881 __codecvt_utf16<char32_t, true>::result
3882 __codecvt_utf16<char32_t, true>::do_in(state_type&,
3883     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3884     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3885 {
3886     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3887     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3888     const uint8_t* _frm_nxt = _frm;
3889     uint32_t* _to = reinterpret_cast<uint32_t*>(to);
3890     uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end);
3891     uint32_t* _to_nxt = _to;
3892     result r = utf16le_to_ucs4(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3893                                _Maxcode_, _Mode_);
3894     frm_nxt = frm + (_frm_nxt - _frm);
3895     to_nxt = to + (_to_nxt - _to);
3896     return r;
3897 }
3898
3899 __codecvt_utf16<char32_t, true>::result
3900 __codecvt_utf16<char32_t, true>::do_unshift(state_type&,
3901     extern_type* to, extern_type*, extern_type*& to_nxt) const
3902 {
3903     to_nxt = to;
3904     return noconv;
3905 }
3906
3907 int
3908 __codecvt_utf16<char32_t, true>::do_encoding() const  _NOEXCEPT
3909 {
3910     return 0;
3911 }
3912
3913 bool
3914 __codecvt_utf16<char32_t, true>::do_always_noconv() const  _NOEXCEPT
3915 {
3916     return false;
3917 }
3918
3919 int
3920 __codecvt_utf16<char32_t, true>::do_length(state_type&,
3921     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3922 {
3923     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3924     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3925     return utf16le_to_ucs4_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
3926 }
3927
3928 int
3929 __codecvt_utf16<char32_t, true>::do_max_length() const  _NOEXCEPT
3930 {
3931     if (_Mode_ & consume_header)
3932         return 6;
3933     return 4;
3934 }
3935
3936 // __codecvt_utf8_utf16<wchar_t>
3937
3938 __codecvt_utf8_utf16<wchar_t>::result
3939 __codecvt_utf8_utf16<wchar_t>::do_out(state_type&,
3940     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
3941     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
3942 {
3943     const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm);
3944     const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end);
3945     const uint32_t* _frm_nxt = _frm;
3946     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
3947     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
3948     uint8_t* _to_nxt = _to;
3949     result r = utf16_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3950                              _Maxcode_, _Mode_);
3951     frm_nxt = frm + (_frm_nxt - _frm);
3952     to_nxt = to + (_to_nxt - _to);
3953     return r;
3954 }
3955
3956 __codecvt_utf8_utf16<wchar_t>::result
3957 __codecvt_utf8_utf16<wchar_t>::do_in(state_type&,
3958     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
3959     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
3960 {
3961     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3962     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
3963     const uint8_t* _frm_nxt = _frm;
3964     uint32_t* _to = reinterpret_cast<uint32_t*>(to);
3965     uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end);
3966     uint32_t* _to_nxt = _to;
3967     result r = utf8_to_utf16(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
3968                              _Maxcode_, _Mode_);
3969     frm_nxt = frm + (_frm_nxt - _frm);
3970     to_nxt = to + (_to_nxt - _to);
3971     return r;
3972 }
3973
3974 __codecvt_utf8_utf16<wchar_t>::result
3975 __codecvt_utf8_utf16<wchar_t>::do_unshift(state_type&,
3976     extern_type* to, extern_type*, extern_type*& to_nxt) const
3977 {
3978     to_nxt = to;
3979     return noconv;
3980 }
3981
3982 int
3983 __codecvt_utf8_utf16<wchar_t>::do_encoding() const  _NOEXCEPT
3984 {
3985     return 0;
3986 }
3987
3988 bool
3989 __codecvt_utf8_utf16<wchar_t>::do_always_noconv() const  _NOEXCEPT
3990 {
3991     return false;
3992 }
3993
3994 int
3995 __codecvt_utf8_utf16<wchar_t>::do_length(state_type&,
3996     const extern_type* frm, const extern_type* frm_end, size_t mx) const
3997 {
3998     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
3999     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
4000     return utf8_to_utf16_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
4001 }
4002
4003 int
4004 __codecvt_utf8_utf16<wchar_t>::do_max_length() const  _NOEXCEPT
4005 {
4006     if (_Mode_ & consume_header)
4007         return 7;
4008     return 4;
4009 }
4010
4011 // __codecvt_utf8_utf16<char16_t>
4012
4013 __codecvt_utf8_utf16<char16_t>::result
4014 __codecvt_utf8_utf16<char16_t>::do_out(state_type&,
4015     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
4016     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
4017 {
4018     const uint16_t* _frm = reinterpret_cast<const uint16_t*>(frm);
4019     const uint16_t* _frm_end = reinterpret_cast<const uint16_t*>(frm_end);
4020     const uint16_t* _frm_nxt = _frm;
4021     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
4022     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
4023     uint8_t* _to_nxt = _to;
4024     result r = utf16_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
4025                              _Maxcode_, _Mode_);
4026     frm_nxt = frm + (_frm_nxt - _frm);
4027     to_nxt = to + (_to_nxt - _to);
4028     return r;
4029 }
4030
4031 __codecvt_utf8_utf16<char16_t>::result
4032 __codecvt_utf8_utf16<char16_t>::do_in(state_type&,
4033     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
4034     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
4035 {
4036     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
4037     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
4038     const uint8_t* _frm_nxt = _frm;
4039     uint16_t* _to = reinterpret_cast<uint16_t*>(to);
4040     uint16_t* _to_end = reinterpret_cast<uint16_t*>(to_end);
4041     uint16_t* _to_nxt = _to;
4042     result r = utf8_to_utf16(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
4043                              _Maxcode_, _Mode_);
4044     frm_nxt = frm + (_frm_nxt - _frm);
4045     to_nxt = to + (_to_nxt - _to);
4046     return r;
4047 }
4048
4049 __codecvt_utf8_utf16<char16_t>::result
4050 __codecvt_utf8_utf16<char16_t>::do_unshift(state_type&,
4051     extern_type* to, extern_type*, extern_type*& to_nxt) const
4052 {
4053     to_nxt = to;
4054     return noconv;
4055 }
4056
4057 int
4058 __codecvt_utf8_utf16<char16_t>::do_encoding() const  _NOEXCEPT
4059 {
4060     return 0;
4061 }
4062
4063 bool
4064 __codecvt_utf8_utf16<char16_t>::do_always_noconv() const  _NOEXCEPT
4065 {
4066     return false;
4067 }
4068
4069 int
4070 __codecvt_utf8_utf16<char16_t>::do_length(state_type&,
4071     const extern_type* frm, const extern_type* frm_end, size_t mx) const
4072 {
4073     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
4074     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
4075     return utf8_to_utf16_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
4076 }
4077
4078 int
4079 __codecvt_utf8_utf16<char16_t>::do_max_length() const  _NOEXCEPT
4080 {
4081     if (_Mode_ & consume_header)
4082         return 7;
4083     return 4;
4084 }
4085
4086 // __codecvt_utf8_utf16<char32_t>
4087
4088 __codecvt_utf8_utf16<char32_t>::result
4089 __codecvt_utf8_utf16<char32_t>::do_out(state_type&,
4090     const intern_type* frm, const intern_type* frm_end, const intern_type*& frm_nxt,
4091     extern_type* to, extern_type* to_end, extern_type*& to_nxt) const
4092 {
4093     const uint32_t* _frm = reinterpret_cast<const uint32_t*>(frm);
4094     const uint32_t* _frm_end = reinterpret_cast<const uint32_t*>(frm_end);
4095     const uint32_t* _frm_nxt = _frm;
4096     uint8_t* _to = reinterpret_cast<uint8_t*>(to);
4097     uint8_t* _to_end = reinterpret_cast<uint8_t*>(to_end);
4098     uint8_t* _to_nxt = _to;
4099     result r = utf16_to_utf8(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
4100                              _Maxcode_, _Mode_);
4101     frm_nxt = frm + (_frm_nxt - _frm);
4102     to_nxt = to + (_to_nxt - _to);
4103     return r;
4104 }
4105
4106 __codecvt_utf8_utf16<char32_t>::result
4107 __codecvt_utf8_utf16<char32_t>::do_in(state_type&,
4108     const extern_type* frm, const extern_type* frm_end, const extern_type*& frm_nxt,
4109     intern_type* to, intern_type* to_end, intern_type*& to_nxt) const
4110 {
4111     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
4112     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
4113     const uint8_t* _frm_nxt = _frm;
4114     uint32_t* _to = reinterpret_cast<uint32_t*>(to);
4115     uint32_t* _to_end = reinterpret_cast<uint32_t*>(to_end);
4116     uint32_t* _to_nxt = _to;
4117     result r = utf8_to_utf16(_frm, _frm_end, _frm_nxt, _to, _to_end, _to_nxt,
4118                              _Maxcode_, _Mode_);
4119     frm_nxt = frm + (_frm_nxt - _frm);
4120     to_nxt = to + (_to_nxt - _to);
4121     return r;
4122 }
4123
4124 __codecvt_utf8_utf16<char32_t>::result
4125 __codecvt_utf8_utf16<char32_t>::do_unshift(state_type&,
4126     extern_type* to, extern_type*, extern_type*& to_nxt) const
4127 {
4128     to_nxt = to;
4129     return noconv;
4130 }
4131
4132 int
4133 __codecvt_utf8_utf16<char32_t>::do_encoding() const  _NOEXCEPT
4134 {
4135     return 0;
4136 }
4137
4138 bool
4139 __codecvt_utf8_utf16<char32_t>::do_always_noconv() const  _NOEXCEPT
4140 {
4141     return false;
4142 }
4143
4144 int
4145 __codecvt_utf8_utf16<char32_t>::do_length(state_type&,
4146     const extern_type* frm, const extern_type* frm_end, size_t mx) const
4147 {
4148     const uint8_t* _frm = reinterpret_cast<const uint8_t*>(frm);
4149     const uint8_t* _frm_end = reinterpret_cast<const uint8_t*>(frm_end);
4150     return utf8_to_utf16_length(_frm, _frm_end, mx, _Maxcode_, _Mode_);
4151 }
4152
4153 int
4154 __codecvt_utf8_utf16<char32_t>::do_max_length() const  _NOEXCEPT
4155 {
4156     if (_Mode_ & consume_header)
4157         return 7;
4158     return 4;
4159 }
4160
4161 // __narrow_to_utf8<16>
4162
4163 __narrow_to_utf8<16>::~__narrow_to_utf8()
4164 {
4165 }
4166
4167 // __narrow_to_utf8<32>
4168
4169 __narrow_to_utf8<32>::~__narrow_to_utf8()
4170 {
4171 }
4172
4173 // __widen_from_utf8<16>
4174
4175 __widen_from_utf8<16>::~__widen_from_utf8()
4176 {
4177 }
4178
4179 // __widen_from_utf8<32>
4180
4181 __widen_from_utf8<32>::~__widen_from_utf8()
4182 {
4183 }
4184
4185
4186 static bool checked_string_to_wchar_convert(wchar_t& dest,
4187                                             const char* ptr,
4188                                             __locale_struct* loc) {
4189   if (*ptr == '\0')
4190     return false;
4191   mbstate_t mb = {};
4192   wchar_t out;
4193   size_t ret = __libcpp_mbrtowc_l(&out, ptr, strlen(ptr), &mb, loc);
4194   if (ret == static_cast<size_t>(-1) || ret == static_cast<size_t>(-2)) {
4195     return false;
4196   }
4197   dest = out;
4198   return true;
4199 }
4200
4201 static bool checked_string_to_char_convert(char& dest,
4202                                            const char* ptr,
4203                                            __locale_struct* __loc) {
4204   if (*ptr == '\0')
4205     return false;
4206   if (!ptr[1]) {
4207     dest = *ptr;
4208     return true;
4209   }
4210   // First convert the MBS into a wide char then attempt to narrow it using
4211   // wctob_l.
4212   wchar_t wout;
4213   if (!checked_string_to_wchar_convert(wout, ptr, __loc))
4214     return false;
4215   int res;
4216   if ((res = __libcpp_wctob_l(wout, __loc)) != char_traits<char>::eof()) {
4217     dest = res;
4218     return true;
4219   }
4220   // FIXME: Work around specific multibyte sequences that we can reasonable
4221   // translate into a different single byte.
4222   switch (wout) {
4223   case L'\u00A0': // non-breaking space
4224     dest = ' ';
4225     return true;
4226   default:
4227     return false;
4228   }
4229   _LIBCPP_UNREACHABLE();
4230 }
4231
4232
4233 // numpunct<char> && numpunct<wchar_t>
4234
4235 locale::id numpunct< char  >::id;
4236 locale::id numpunct<wchar_t>::id;
4237
4238 numpunct<char>::numpunct(size_t refs)
4239     : locale::facet(refs),
4240       __decimal_point_('.'),
4241       __thousands_sep_(',')
4242 {
4243 }
4244
4245 numpunct<wchar_t>::numpunct(size_t refs)
4246     : locale::facet(refs),
4247       __decimal_point_(L'.'),
4248       __thousands_sep_(L',')
4249 {
4250 }
4251
4252 numpunct<char>::~numpunct()
4253 {
4254 }
4255
4256 numpunct<wchar_t>::~numpunct()
4257 {
4258 }
4259
4260  char   numpunct< char  >::do_decimal_point() const {return __decimal_point_;}
4261 wchar_t numpunct<wchar_t>::do_decimal_point() const {return __decimal_point_;}
4262
4263  char   numpunct< char  >::do_thousands_sep() const {return __thousands_sep_;}
4264 wchar_t numpunct<wchar_t>::do_thousands_sep() const {return __thousands_sep_;}
4265
4266 string numpunct< char  >::do_grouping() const {return __grouping_;}
4267 string numpunct<wchar_t>::do_grouping() const {return __grouping_;}
4268
4269  string numpunct< char  >::do_truename() const {return "true";}
4270 wstring numpunct<wchar_t>::do_truename() const {return L"true";}
4271
4272  string numpunct< char  >::do_falsename() const {return "false";}
4273 wstring numpunct<wchar_t>::do_falsename() const {return L"false";}
4274
4275 // numpunct_byname<char>
4276
4277 numpunct_byname<char>::numpunct_byname(const char* nm, size_t refs)
4278     : numpunct<char>(refs)
4279 {
4280     __init(nm);
4281 }
4282
4283 numpunct_byname<char>::numpunct_byname(const string& nm, size_t refs)
4284     : numpunct<char>(refs)
4285 {
4286     __init(nm.c_str());
4287 }
4288
4289 numpunct_byname<char>::~numpunct_byname()
4290 {
4291 }
4292
4293 void
4294 numpunct_byname<char>::__init(const char* nm)
4295 {
4296     if (strcmp(nm, "C") != 0)
4297     {
4298         __locale_unique_ptr loc(newlocale(LC_ALL_MASK, nm, 0), freelocale);
4299         if (loc == nullptr)
4300             __throw_runtime_error("numpunct_byname<char>::numpunct_byname"
4301                                 " failed to construct for " + string(nm));
4302
4303         lconv* lc = __libcpp_localeconv_l(loc.get());
4304         checked_string_to_char_convert(__decimal_point_, lc->decimal_point,
4305                                        loc.get());
4306         checked_string_to_char_convert(__thousands_sep_, lc->thousands_sep,
4307                                        loc.get());
4308         __grouping_ = lc->grouping;
4309         // localization for truename and falsename is not available
4310     }
4311 }
4312
4313 // numpunct_byname<wchar_t>
4314
4315 numpunct_byname<wchar_t>::numpunct_byname(const char* nm, size_t refs)
4316     : numpunct<wchar_t>(refs)
4317 {
4318     __init(nm);
4319 }
4320
4321 numpunct_byname<wchar_t>::numpunct_byname(const string& nm, size_t refs)
4322     : numpunct<wchar_t>(refs)
4323 {
4324     __init(nm.c_str());
4325 }
4326
4327 numpunct_byname<wchar_t>::~numpunct_byname()
4328 {
4329 }
4330
4331 void
4332 numpunct_byname<wchar_t>::__init(const char* nm)
4333 {
4334     if (strcmp(nm, "C") != 0)
4335     {
4336         __locale_unique_ptr loc(newlocale(LC_ALL_MASK, nm, 0), freelocale);
4337         if (loc == nullptr)
4338             __throw_runtime_error("numpunct_byname<wchar_t>::numpunct_byname"
4339                                 " failed to construct for " + string(nm));
4340
4341         lconv* lc = __libcpp_localeconv_l(loc.get());
4342         checked_string_to_wchar_convert(__decimal_point_, lc->decimal_point,
4343                                         loc.get());
4344         checked_string_to_wchar_convert(__thousands_sep_, lc->thousands_sep,
4345                                         loc.get());
4346         __grouping_ = lc->grouping;
4347         // localization for truename and falsename is not available
4348     }
4349 }
4350
4351 // num_get helpers
4352
4353 int
4354 __num_get_base::__get_base(ios_base& iob)
4355 {
4356     ios_base::fmtflags __basefield = iob.flags() & ios_base::basefield;
4357     if (__basefield == ios_base::oct)
4358         return 8;
4359     else if (__basefield == ios_base::hex)
4360         return 16;
4361     else if (__basefield == 0)
4362         return 0;
4363     return 10;
4364 }
4365
4366 const char __num_get_base::__src[33] = "0123456789abcdefABCDEFxX+-pPiInN";
4367
4368 void
4369 __check_grouping(const string& __grouping, unsigned* __g, unsigned* __g_end,
4370                  ios_base::iostate& __err)
4371 {
4372     if (__grouping.size() != 0)
4373     {
4374         reverse(__g, __g_end);
4375         const char* __ig = __grouping.data();
4376         const char* __eg = __ig + __grouping.size();
4377         for (unsigned* __r = __g; __r < __g_end-1; ++__r)
4378         {
4379             if (0 < *__ig && *__ig < numeric_limits<char>::max())
4380             {
4381                 if (static_cast<unsigned>(*__ig) != *__r)
4382                 {
4383                     __err = ios_base::failbit;
4384                     return;
4385                 }
4386             }
4387             if (__eg - __ig > 1)
4388                 ++__ig;
4389         }
4390         if (0 < *__ig && *__ig < numeric_limits<char>::max())
4391         {
4392             if (static_cast<unsigned>(*__ig) < __g_end[-1] || __g_end[-1] == 0)
4393                 __err = ios_base::failbit;
4394         }
4395     }
4396 }
4397
4398 void
4399 __num_put_base::__format_int(char* __fmtp, const char* __len, bool __signd,
4400                              ios_base::fmtflags __flags)
4401 {
4402     if (__flags & ios_base::showpos)
4403         *__fmtp++ = '+';
4404     if (__flags & ios_base::showbase)
4405         *__fmtp++ = '#';
4406     while(*__len)
4407         *__fmtp++ = *__len++;
4408     if ((__flags & ios_base::basefield) == ios_base::oct)
4409         *__fmtp = 'o';
4410     else if ((__flags & ios_base::basefield) == ios_base::hex)
4411     {
4412         if (__flags & ios_base::uppercase)
4413             *__fmtp = 'X';
4414         else
4415             *__fmtp = 'x';
4416     }
4417     else if (__signd)
4418         *__fmtp = 'd';
4419     else
4420         *__fmtp = 'u';
4421 }
4422
4423 bool
4424 __num_put_base::__format_float(char* __fmtp, const char* __len,
4425                                ios_base::fmtflags __flags)
4426 {
4427     bool specify_precision = true;
4428     if (__flags & ios_base::showpos)
4429         *__fmtp++ = '+';
4430     if (__flags & ios_base::showpoint)
4431         *__fmtp++ = '#';
4432     ios_base::fmtflags floatfield = __flags & ios_base::floatfield;
4433     bool uppercase = (__flags & ios_base::uppercase) != 0;
4434     if (floatfield == (ios_base::fixed | ios_base::scientific))
4435         specify_precision = false;
4436     else
4437     {
4438         *__fmtp++ = '.';
4439         *__fmtp++ = '*';
4440     }
4441     while(*__len)
4442         *__fmtp++ = *__len++;
4443     if (floatfield == ios_base::fixed)
4444     {
4445         if (uppercase)
4446             *__fmtp = 'F';
4447         else
4448             *__fmtp = 'f';
4449     }
4450     else if (floatfield == ios_base::scientific)
4451     {
4452         if (uppercase)
4453             *__fmtp = 'E';
4454         else
4455             *__fmtp = 'e';
4456     }
4457     else if (floatfield == (ios_base::fixed | ios_base::scientific))
4458     {
4459         if (uppercase)
4460             *__fmtp = 'A';
4461         else
4462             *__fmtp = 'a';
4463     }
4464     else
4465     {
4466         if (uppercase)
4467             *__fmtp = 'G';
4468         else
4469             *__fmtp = 'g';
4470     }
4471     return specify_precision;
4472 }
4473
4474 char*
4475 __num_put_base::__identify_padding(char* __nb, char* __ne,
4476                                    const ios_base& __iob)
4477 {
4478     switch (__iob.flags() & ios_base::adjustfield)
4479     {
4480     case ios_base::internal:
4481         if (__nb[0] == '-' || __nb[0] == '+')
4482             return __nb+1;
4483         if (__ne - __nb >= 2 && __nb[0] == '0'
4484                             && (__nb[1] == 'x' || __nb[1] == 'X'))
4485             return __nb+2;
4486         break;
4487     case ios_base::left:
4488         return __ne;
4489     case ios_base::right:
4490     default:
4491         break;
4492     }
4493     return __nb;
4494 }
4495
4496 // time_get
4497
4498 static
4499 string*
4500 init_weeks()
4501 {
4502     static string weeks[14];
4503     weeks[0]  = "Sunday";
4504     weeks[1]  = "Monday";
4505     weeks[2]  = "Tuesday";
4506     weeks[3]  = "Wednesday";
4507     weeks[4]  = "Thursday";
4508     weeks[5]  = "Friday";
4509     weeks[6]  = "Saturday";
4510     weeks[7]  = "Sun";
4511     weeks[8]  = "Mon";
4512     weeks[9]  = "Tue";
4513     weeks[10] = "Wed";
4514     weeks[11] = "Thu";
4515     weeks[12] = "Fri";
4516     weeks[13] = "Sat";
4517     return weeks;
4518 }
4519
4520 static
4521 wstring*
4522 init_wweeks()
4523 {
4524     static wstring weeks[14];
4525     weeks[0]  = L"Sunday";
4526     weeks[1]  = L"Monday";
4527     weeks[2]  = L"Tuesday";
4528     weeks[3]  = L"Wednesday";
4529     weeks[4]  = L"Thursday";
4530     weeks[5]  = L"Friday";
4531     weeks[6]  = L"Saturday";
4532     weeks[7]  = L"Sun";
4533     weeks[8]  = L"Mon";
4534     weeks[9]  = L"Tue";
4535     weeks[10] = L"Wed";
4536     weeks[11] = L"Thu";
4537     weeks[12] = L"Fri";
4538     weeks[13] = L"Sat";
4539     return weeks;
4540 }
4541
4542 template <>
4543 const string*
4544 __time_get_c_storage<char>::__weeks() const
4545 {
4546     static const string* weeks = init_weeks();
4547     return weeks;
4548 }
4549
4550 template <>
4551 const wstring*
4552 __time_get_c_storage<wchar_t>::__weeks() const
4553 {
4554     static const wstring* weeks = init_wweeks();
4555     return weeks;
4556 }
4557
4558 static
4559 string*
4560 init_months()
4561 {
4562     static string months[24];
4563     months[0]  = "January";
4564     months[1]  = "February";
4565     months[2]  = "March";
4566     months[3]  = "April";
4567     months[4]  = "May";
4568     months[5]  = "June";
4569     months[6]  = "July";
4570     months[7]  = "August";
4571     months[8]  = "September";
4572     months[9]  = "October";
4573     months[10] = "November";
4574     months[11] = "December";
4575     months[12] = "Jan";
4576     months[13] = "Feb";
4577     months[14] = "Mar";
4578     months[15] = "Apr";
4579     months[16] = "May";
4580     months[17] = "Jun";
4581     months[18] = "Jul";
4582     months[19] = "Aug";
4583     months[20] = "Sep";
4584     months[21] = "Oct";
4585     months[22] = "Nov";
4586     months[23] = "Dec";
4587     return months;
4588 }
4589
4590 static
4591 wstring*
4592 init_wmonths()
4593 {
4594     static wstring months[24];
4595     months[0]  = L"January";
4596     months[1]  = L"February";
4597     months[2]  = L"March";
4598     months[3]  = L"April";
4599     months[4]  = L"May";
4600     months[5]  = L"June";
4601     months[6]  = L"July";
4602     months[7]  = L"August";
4603     months[8]  = L"September";
4604     months[9]  = L"October";
4605     months[10] = L"November";
4606     months[11] = L"December";
4607     months[12] = L"Jan";
4608     months[13] = L"Feb";
4609     months[14] = L"Mar";
4610     months[15] = L"Apr";
4611     months[16] = L"May";
4612     months[17] = L"Jun";
4613     months[18] = L"Jul";
4614     months[19] = L"Aug";
4615     months[20] = L"Sep";
4616     months[21] = L"Oct";
4617     months[22] = L"Nov";
4618     months[23] = L"Dec";
4619     return months;
4620 }
4621
4622 template <>
4623 const string*
4624 __time_get_c_storage<char>::__months() const
4625 {
4626     static const string* months = init_months();
4627     return months;
4628 }
4629
4630 template <>
4631 const wstring*
4632 __time_get_c_storage<wchar_t>::__months() const
4633 {
4634     static const wstring* months = init_wmonths();
4635     return months;
4636 }
4637
4638 static
4639 string*
4640 init_am_pm()
4641 {
4642     static string am_pm[24];
4643     am_pm[0]  = "AM";
4644     am_pm[1]  = "PM";
4645     return am_pm;
4646 }
4647
4648 static
4649 wstring*
4650 init_wam_pm()
4651 {
4652     static wstring am_pm[24];
4653     am_pm[0]  = L"AM";
4654     am_pm[1]  = L"PM";
4655     return am_pm;
4656 }
4657
4658 template <>
4659 const string*
4660 __time_get_c_storage<char>::__am_pm() const
4661 {
4662     static const string* am_pm = init_am_pm();
4663     return am_pm;
4664 }
4665
4666 template <>
4667 const wstring*
4668 __time_get_c_storage<wchar_t>::__am_pm() const
4669 {
4670     static const wstring* am_pm = init_wam_pm();
4671     return am_pm;
4672 }
4673
4674 template <>
4675 const string&
4676 __time_get_c_storage<char>::__x() const
4677 {
4678     static string s("%m/%d/%y");
4679     return s;
4680 }
4681
4682 template <>
4683 const wstring&
4684 __time_get_c_storage<wchar_t>::__x() const
4685 {
4686     static wstring s(L"%m/%d/%y");
4687     return s;
4688 }
4689
4690 template <>
4691 const string&
4692 __time_get_c_storage<char>::__X() const
4693 {
4694     static string s("%H:%M:%S");
4695     return s;
4696 }
4697
4698 template <>
4699 const wstring&
4700 __time_get_c_storage<wchar_t>::__X() const
4701 {
4702     static wstring s(L"%H:%M:%S");
4703     return s;
4704 }
4705
4706 template <>
4707 const string&
4708 __time_get_c_storage<char>::__c() const
4709 {
4710     static string s("%a %b %d %H:%M:%S %Y");
4711     return s;
4712 }
4713
4714 template <>
4715 const wstring&
4716 __time_get_c_storage<wchar_t>::__c() const
4717 {
4718     static wstring s(L"%a %b %d %H:%M:%S %Y");
4719     return s;
4720 }
4721
4722 template <>
4723 const string&
4724 __time_get_c_storage<char>::__r() const
4725 {
4726     static string s("%I:%M:%S %p");
4727     return s;
4728 }
4729
4730 template <>
4731 const wstring&
4732 __time_get_c_storage<wchar_t>::__r() const
4733 {
4734     static wstring s(L"%I:%M:%S %p");
4735     return s;
4736 }
4737
4738 // time_get_byname
4739
4740 __time_get::__time_get(const char* nm)
4741     : __loc_(newlocale(LC_ALL_MASK, nm, 0))
4742 {
4743     if (__loc_ == 0)
4744         __throw_runtime_error("time_get_byname"
4745                             " failed to construct for " + string(nm));
4746 }
4747
4748 __time_get::__time_get(const string& nm)
4749     : __loc_(newlocale(LC_ALL_MASK, nm.c_str(), 0))
4750 {
4751     if (__loc_ == 0)
4752         __throw_runtime_error("time_get_byname"
4753                             " failed to construct for " + nm);
4754 }
4755
4756 __time_get::~__time_get()
4757 {
4758     freelocale(__loc_);
4759 }
4760 #if defined(__clang__)
4761 #pragma clang diagnostic ignored "-Wmissing-field-initializers"
4762 #endif
4763 #if defined(__GNUG__)
4764 #pragma GCC   diagnostic ignored "-Wmissing-field-initializers"
4765 #endif
4766
4767 template <>
4768 string
4769 __time_get_storage<char>::__analyze(char fmt, const ctype<char>& ct)
4770 {
4771     tm t = {0};
4772     t.tm_sec = 59;
4773     t.tm_min = 55;
4774     t.tm_hour = 23;
4775     t.tm_mday = 31;
4776     t.tm_mon = 11;
4777     t.tm_year = 161;
4778     t.tm_wday = 6;
4779     t.tm_yday = 364;
4780     t.tm_isdst = -1;
4781     char buf[100];
4782     char f[3] = {0};
4783     f[0] = '%';
4784     f[1] = fmt;
4785     size_t n = strftime_l(buf, countof(buf), f, &t, __loc_);
4786     char* bb = buf;
4787     char* be = buf + n;
4788     string result;
4789     while (bb != be)
4790     {
4791         if (ct.is(ctype_base::space, *bb))
4792         {
4793             result.push_back(' ');
4794             for (++bb; bb != be && ct.is(ctype_base::space, *bb); ++bb)
4795                 ;
4796             continue;
4797         }
4798         char* w = bb;
4799         ios_base::iostate err = ios_base::goodbit;
4800         ptrdiff_t i = __scan_keyword(w, be, this->__weeks_, this->__weeks_+14,
4801                                ct, err, false)
4802                                - this->__weeks_;
4803         if (i < 14)
4804         {
4805             result.push_back('%');
4806             if (i < 7)
4807                 result.push_back('A');
4808             else
4809                 result.push_back('a');
4810             bb = w;
4811             continue;
4812         }
4813         w = bb;
4814         i = __scan_keyword(w, be, this->__months_, this->__months_+24,
4815                            ct, err, false)
4816                            - this->__months_;
4817         if (i < 24)
4818         {
4819             result.push_back('%');
4820             if (i < 12)
4821                 result.push_back('B');
4822             else
4823                 result.push_back('b');
4824             if (fmt == 'x' && ct.is(ctype_base::digit, this->__months_[i][0]))
4825                 result.back() = 'm';
4826             bb = w;
4827             continue;
4828         }
4829         if (this->__am_pm_[0].size() + this->__am_pm_[1].size() > 0)
4830         {
4831             w = bb;
4832             i = __scan_keyword(w, be, this->__am_pm_, this->__am_pm_+2,
4833                                ct, err, false) - this->__am_pm_;
4834             if (i < 2)
4835             {
4836                 result.push_back('%');
4837                 result.push_back('p');
4838                 bb = w;
4839                 continue;
4840             }
4841         }
4842         w = bb;
4843         if (ct.is(ctype_base::digit, *bb))
4844         {
4845             switch(__get_up_to_n_digits(bb, be, err, ct, 4))
4846             {
4847             case 6:
4848                 result.push_back('%');
4849                 result.push_back('w');
4850                 break;
4851             case 7:
4852                 result.push_back('%');
4853                 result.push_back('u');
4854                 break;
4855             case 11:
4856                 result.push_back('%');
4857                 result.push_back('I');
4858                 break;
4859             case 12:
4860                 result.push_back('%');
4861                 result.push_back('m');
4862                 break;
4863             case 23:
4864                 result.push_back('%');
4865                 result.push_back('H');
4866                 break;
4867             case 31:
4868                 result.push_back('%');
4869                 result.push_back('d');
4870                 break;
4871             case 55:
4872                 result.push_back('%');
4873                 result.push_back('M');
4874                 break;
4875             case 59:
4876                 result.push_back('%');
4877                 result.push_back('S');
4878                 break;
4879             case 61:
4880                 result.push_back('%');
4881                 result.push_back('y');
4882                 break;
4883             case 364:
4884                 result.push_back('%');
4885                 result.push_back('j');
4886                 break;
4887             case 2061:
4888                 result.push_back('%');
4889                 result.push_back('Y');
4890                 break;
4891             default:
4892                 for (; w != bb; ++w)
4893                     result.push_back(*w);
4894                 break;
4895             }
4896             continue;
4897         }
4898         if (*bb == '%')
4899         {
4900             result.push_back('%');
4901             result.push_back('%');
4902             ++bb;
4903             continue;
4904         }
4905         result.push_back(*bb);
4906         ++bb;
4907     }
4908     return result;
4909 }
4910
4911 #if defined(__clang__)
4912 #pragma clang diagnostic ignored "-Wmissing-braces"
4913 #endif
4914
4915 template <>
4916 wstring
4917 __time_get_storage<wchar_t>::__analyze(char fmt, const ctype<wchar_t>& ct)
4918 {
4919     tm t = {0};
4920     t.tm_sec = 59;
4921     t.tm_min = 55;
4922     t.tm_hour = 23;
4923     t.tm_mday = 31;
4924     t.tm_mon = 11;
4925     t.tm_year = 161;
4926     t.tm_wday = 6;
4927     t.tm_yday = 364;
4928     t.tm_isdst = -1;
4929     char buf[100];
4930     char f[3] = {0};
4931     f[0] = '%';
4932     f[1] = fmt;
4933     strftime_l(buf, countof(buf), f, &t, __loc_);
4934     wchar_t wbuf[100];
4935     wchar_t* wbb = wbuf;
4936     mbstate_t mb = {0};
4937     const char* bb = buf;
4938     size_t j = __libcpp_mbsrtowcs_l( wbb, &bb, countof(wbuf), &mb, __loc_);
4939     if (j == size_t(-1))
4940         __throw_runtime_error("locale not supported");
4941     wchar_t* wbe = wbb + j;
4942     wstring result;
4943     while (wbb != wbe)
4944     {
4945         if (ct.is(ctype_base::space, *wbb))
4946         {
4947             result.push_back(L' ');
4948             for (++wbb; wbb != wbe && ct.is(ctype_base::space, *wbb); ++wbb)
4949                 ;
4950             continue;
4951         }
4952         wchar_t* w = wbb;
4953         ios_base::iostate err = ios_base::goodbit;
4954         ptrdiff_t i = __scan_keyword(w, wbe, this->__weeks_, this->__weeks_+14,
4955                                ct, err, false)
4956                                - this->__weeks_;
4957         if (i < 14)
4958         {
4959             result.push_back(L'%');
4960             if (i < 7)
4961                 result.push_back(L'A');
4962             else
4963                 result.push_back(L'a');
4964             wbb = w;
4965             continue;
4966         }
4967         w = wbb;
4968         i = __scan_keyword(w, wbe, this->__months_, this->__months_+24,
4969                            ct, err, false)
4970                            - this->__months_;
4971         if (i < 24)
4972         {
4973             result.push_back(L'%');
4974             if (i < 12)
4975                 result.push_back(L'B');
4976             else
4977                 result.push_back(L'b');
4978             if (fmt == 'x' && ct.is(ctype_base::digit, this->__months_[i][0]))
4979                 result.back() = L'm';
4980             wbb = w;
4981             continue;
4982         }
4983         if (this->__am_pm_[0].size() + this->__am_pm_[1].size() > 0)
4984         {
4985             w = wbb;
4986             i = __scan_keyword(w, wbe, this->__am_pm_, this->__am_pm_+2,
4987                                ct, err, false) - this->__am_pm_;
4988             if (i < 2)
4989             {
4990                 result.push_back(L'%');
4991                 result.push_back(L'p');
4992                 wbb = w;
4993                 continue;
4994             }
4995         }
4996         w = wbb;
4997         if (ct.is(ctype_base::digit, *wbb))
4998         {
4999             switch(__get_up_to_n_digits(wbb, wbe, err, ct, 4))
5000             {
5001             case 6:
5002                 result.push_back(L'%');
5003                 result.push_back(L'w');
5004                 break;
5005             case 7:
5006                 result.push_back(L'%');
5007                 result.push_back(L'u');
5008                 break;
5009             case 11:
5010                 result.push_back(L'%');
5011                 result.push_back(L'I');
5012                 break;
5013             case 12:
5014                 result.push_back(L'%');
5015                 result.push_back(L'm');
5016                 break;
5017             case 23:
5018                 result.push_back(L'%');
5019                 result.push_back(L'H');
5020                 break;
5021             case 31:
5022                 result.push_back(L'%');
5023                 result.push_back(L'd');
5024                 break;
5025             case 55:
5026                 result.push_back(L'%');
5027                 result.push_back(L'M');
5028                 break;
5029             case 59:
5030                 result.push_back(L'%');
5031                 result.push_back(L'S');
5032                 break;
5033             case 61:
5034                 result.push_back(L'%');
5035                 result.push_back(L'y');
5036                 break;
5037             case 364:
5038                 result.push_back(L'%');
5039                 result.push_back(L'j');
5040                 break;
5041             case 2061:
5042                 result.push_back(L'%');
5043                 result.push_back(L'Y');
5044                 break;
5045             default:
5046                 for (; w != wbb; ++w)
5047                     result.push_back(*w);
5048                 break;
5049             }
5050             continue;
5051         }
5052         if (ct.narrow(*wbb, 0) == '%')
5053         {
5054             result.push_back(L'%');
5055             result.push_back(L'%');
5056             ++wbb;
5057             continue;
5058         }
5059         result.push_back(*wbb);
5060         ++wbb;
5061     }
5062     return result;
5063 }
5064
5065 template <>
5066 void
5067 __time_get_storage<char>::init(const ctype<char>& ct)
5068 {
5069     tm t = {0};
5070     char buf[100];
5071     // __weeks_
5072     for (int i = 0; i < 7; ++i)
5073     {
5074         t.tm_wday = i;
5075         strftime_l(buf, countof(buf), "%A", &t, __loc_);
5076         __weeks_[i] = buf;
5077         strftime_l(buf, countof(buf), "%a", &t, __loc_);
5078         __weeks_[i+7] = buf;
5079     }
5080     // __months_
5081     for (int i = 0; i < 12; ++i)
5082     {
5083         t.tm_mon = i;
5084         strftime_l(buf, countof(buf), "%B", &t, __loc_);
5085         __months_[i] = buf;
5086         strftime_l(buf, countof(buf), "%b", &t, __loc_);
5087         __months_[i+12] = buf;
5088     }
5089     // __am_pm_
5090     t.tm_hour = 1;
5091     strftime_l(buf, countof(buf), "%p", &t, __loc_);
5092     __am_pm_[0] = buf;
5093     t.tm_hour = 13;
5094     strftime_l(buf, countof(buf), "%p", &t, __loc_);
5095     __am_pm_[1] = buf;
5096     __c_ = __analyze('c', ct);
5097     __r_ = __analyze('r', ct);
5098     __x_ = __analyze('x', ct);
5099     __X_ = __analyze('X', ct);
5100 }
5101
5102 template <>
5103 void
5104 __time_get_storage<wchar_t>::init(const ctype<wchar_t>& ct)
5105 {
5106     tm t = {0};
5107     char buf[100];
5108     wchar_t wbuf[100];
5109     wchar_t* wbe;
5110     mbstate_t mb = {0};
5111     // __weeks_
5112     for (int i = 0; i < 7; ++i)
5113     {
5114         t.tm_wday = i;
5115         strftime_l(buf, countof(buf), "%A", &t, __loc_);
5116         mb = mbstate_t();
5117         const char* bb = buf;
5118         size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_);
5119         if (j == size_t(-1))
5120             __throw_runtime_error("locale not supported");
5121         wbe = wbuf + j;
5122         __weeks_[i].assign(wbuf, wbe);
5123         strftime_l(buf, countof(buf), "%a", &t, __loc_);
5124         mb = mbstate_t();
5125         bb = buf;
5126         j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_);
5127         if (j == size_t(-1))
5128             __throw_runtime_error("locale not supported");
5129         wbe = wbuf + j;
5130         __weeks_[i+7].assign(wbuf, wbe);
5131     }
5132     // __months_
5133     for (int i = 0; i < 12; ++i)
5134     {
5135         t.tm_mon = i;
5136         strftime_l(buf, countof(buf), "%B", &t, __loc_);
5137         mb = mbstate_t();
5138         const char* bb = buf;
5139         size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_);
5140         if (j == size_t(-1))
5141             __throw_runtime_error("locale not supported");
5142         wbe = wbuf + j;
5143         __months_[i].assign(wbuf, wbe);
5144         strftime_l(buf, countof(buf), "%b", &t, __loc_);
5145         mb = mbstate_t();
5146         bb = buf;
5147         j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_);
5148         if (j == size_t(-1))
5149             __throw_runtime_error("locale not supported");
5150         wbe = wbuf + j;
5151         __months_[i+12].assign(wbuf, wbe);
5152     }
5153     // __am_pm_
5154     t.tm_hour = 1;
5155     strftime_l(buf, countof(buf), "%p", &t, __loc_);
5156     mb = mbstate_t();
5157     const char* bb = buf;
5158     size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_);
5159     if (j == size_t(-1))
5160         __throw_runtime_error("locale not supported");
5161     wbe = wbuf + j;
5162     __am_pm_[0].assign(wbuf, wbe);
5163     t.tm_hour = 13;
5164     strftime_l(buf, countof(buf), "%p", &t, __loc_);
5165     mb = mbstate_t();
5166     bb = buf;
5167     j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, __loc_);
5168     if (j == size_t(-1))
5169         __throw_runtime_error("locale not supported");
5170     wbe = wbuf + j;
5171     __am_pm_[1].assign(wbuf, wbe);
5172     __c_ = __analyze('c', ct);
5173     __r_ = __analyze('r', ct);
5174     __x_ = __analyze('x', ct);
5175     __X_ = __analyze('X', ct);
5176 }
5177
5178 template <class CharT>
5179 struct _LIBCPP_HIDDEN __time_get_temp
5180     : public ctype_byname<CharT>
5181 {
5182     explicit __time_get_temp(const char* nm)
5183         : ctype_byname<CharT>(nm, 1) {}
5184     explicit __time_get_temp(const string& nm)
5185         : ctype_byname<CharT>(nm, 1) {}
5186 };
5187
5188 template <>
5189 __time_get_storage<char>::__time_get_storage(const char* __nm)
5190     : __time_get(__nm)
5191 {
5192     const __time_get_temp<char> ct(__nm);
5193     init(ct);
5194 }
5195
5196 template <>
5197 __time_get_storage<char>::__time_get_storage(const string& __nm)
5198     : __time_get(__nm)
5199 {
5200     const __time_get_temp<char> ct(__nm);
5201     init(ct);
5202 }
5203
5204 template <>
5205 __time_get_storage<wchar_t>::__time_get_storage(const char* __nm)
5206     : __time_get(__nm)
5207 {
5208     const __time_get_temp<wchar_t> ct(__nm);
5209     init(ct);
5210 }
5211
5212 template <>
5213 __time_get_storage<wchar_t>::__time_get_storage(const string& __nm)
5214     : __time_get(__nm)
5215 {
5216     const __time_get_temp<wchar_t> ct(__nm);
5217     init(ct);
5218 }
5219
5220 template <>
5221 time_base::dateorder
5222 __time_get_storage<char>::__do_date_order() const
5223 {
5224     unsigned i;
5225     for (i = 0; i < __x_.size(); ++i)
5226         if (__x_[i] == '%')
5227             break;
5228     ++i;
5229     switch (__x_[i])
5230     {
5231     case 'y':
5232     case 'Y':
5233         for (++i; i < __x_.size(); ++i)
5234             if (__x_[i] == '%')
5235                 break;
5236         if (i == __x_.size())
5237             break;
5238         ++i;
5239         switch (__x_[i])
5240         {
5241         case 'm':
5242             for (++i; i < __x_.size(); ++i)
5243                 if (__x_[i] == '%')
5244                     break;
5245             if (i == __x_.size())
5246                 break;
5247             ++i;
5248             if (__x_[i] == 'd')
5249                 return time_base::ymd;
5250             break;
5251         case 'd':
5252             for (++i; i < __x_.size(); ++i)
5253                 if (__x_[i] == '%')
5254                     break;
5255             if (i == __x_.size())
5256                 break;
5257             ++i;
5258             if (__x_[i] == 'm')
5259                 return time_base::ydm;
5260             break;
5261         }
5262         break;
5263     case 'm':
5264         for (++i; i < __x_.size(); ++i)
5265             if (__x_[i] == '%')
5266                 break;
5267         if (i == __x_.size())
5268             break;
5269         ++i;
5270         if (__x_[i] == 'd')
5271         {
5272             for (++i; i < __x_.size(); ++i)
5273                 if (__x_[i] == '%')
5274                     break;
5275             if (i == __x_.size())
5276                 break;
5277             ++i;
5278             if (__x_[i] == 'y' || __x_[i] == 'Y')
5279                 return time_base::mdy;
5280             break;
5281         }
5282         break;
5283     case 'd':
5284         for (++i; i < __x_.size(); ++i)
5285             if (__x_[i] == '%')
5286                 break;
5287         if (i == __x_.size())
5288             break;
5289         ++i;
5290         if (__x_[i] == 'm')
5291         {
5292             for (++i; i < __x_.size(); ++i)
5293                 if (__x_[i] == '%')
5294                     break;
5295             if (i == __x_.size())
5296                 break;
5297             ++i;
5298             if (__x_[i] == 'y' || __x_[i] == 'Y')
5299                 return time_base::dmy;
5300             break;
5301         }
5302         break;
5303     }
5304     return time_base::no_order;
5305 }
5306
5307 template <>
5308 time_base::dateorder
5309 __time_get_storage<wchar_t>::__do_date_order() const
5310 {
5311     unsigned i;
5312     for (i = 0; i < __x_.size(); ++i)
5313         if (__x_[i] == L'%')
5314             break;
5315     ++i;
5316     switch (__x_[i])
5317     {
5318     case L'y':
5319     case L'Y':
5320         for (++i; i < __x_.size(); ++i)
5321             if (__x_[i] == L'%')
5322                 break;
5323         if (i == __x_.size())
5324             break;
5325         ++i;
5326         switch (__x_[i])
5327         {
5328         case L'm':
5329             for (++i; i < __x_.size(); ++i)
5330                 if (__x_[i] == L'%')
5331                     break;
5332             if (i == __x_.size())
5333                 break;
5334             ++i;
5335             if (__x_[i] == L'd')
5336                 return time_base::ymd;
5337             break;
5338         case L'd':
5339             for (++i; i < __x_.size(); ++i)
5340                 if (__x_[i] == L'%')
5341                     break;
5342             if (i == __x_.size())
5343                 break;
5344             ++i;
5345             if (__x_[i] == L'm')
5346                 return time_base::ydm;
5347             break;
5348         }
5349         break;
5350     case L'm':
5351         for (++i; i < __x_.size(); ++i)
5352             if (__x_[i] == L'%')
5353                 break;
5354         if (i == __x_.size())
5355             break;
5356         ++i;
5357         if (__x_[i] == L'd')
5358         {
5359             for (++i; i < __x_.size(); ++i)
5360                 if (__x_[i] == L'%')
5361                     break;
5362             if (i == __x_.size())
5363                 break;
5364             ++i;
5365             if (__x_[i] == L'y' || __x_[i] == L'Y')
5366                 return time_base::mdy;
5367             break;
5368         }
5369         break;
5370     case L'd':
5371         for (++i; i < __x_.size(); ++i)
5372             if (__x_[i] == L'%')
5373                 break;
5374         if (i == __x_.size())
5375             break;
5376         ++i;
5377         if (__x_[i] == L'm')
5378         {
5379             for (++i; i < __x_.size(); ++i)
5380                 if (__x_[i] == L'%')
5381                     break;
5382             if (i == __x_.size())
5383                 break;
5384             ++i;
5385             if (__x_[i] == L'y' || __x_[i] == L'Y')
5386                 return time_base::dmy;
5387             break;
5388         }
5389         break;
5390     }
5391     return time_base::no_order;
5392 }
5393
5394 // time_put
5395
5396 __time_put::__time_put(const char* nm)
5397     : __loc_(newlocale(LC_ALL_MASK, nm, 0))
5398 {
5399     if (__loc_ == 0)
5400         __throw_runtime_error("time_put_byname"
5401                             " failed to construct for " + string(nm));
5402 }
5403
5404 __time_put::__time_put(const string& nm)
5405     : __loc_(newlocale(LC_ALL_MASK, nm.c_str(), 0))
5406 {
5407     if (__loc_ == 0)
5408         __throw_runtime_error("time_put_byname"
5409                             " failed to construct for " + nm);
5410 }
5411
5412 __time_put::~__time_put()
5413 {
5414     if (__loc_ != _LIBCPP_GET_C_LOCALE)
5415         freelocale(__loc_);
5416 }
5417
5418 void
5419 __time_put::__do_put(char* __nb, char*& __ne, const tm* __tm,
5420                      char __fmt, char __mod) const
5421 {
5422     char fmt[] = {'%', __fmt, __mod, 0};
5423     if (__mod != 0)
5424         swap(fmt[1], fmt[2]);
5425     size_t n = strftime_l(__nb, countof(__nb, __ne), fmt, __tm, __loc_);
5426     __ne = __nb + n;
5427 }
5428
5429 void
5430 __time_put::__do_put(wchar_t* __wb, wchar_t*& __we, const tm* __tm,
5431                      char __fmt, char __mod) const
5432 {
5433     char __nar[100];
5434     char* __ne = __nar + 100;
5435     __do_put(__nar, __ne, __tm, __fmt, __mod);
5436     mbstate_t mb = {0};
5437     const char* __nb = __nar;
5438     size_t j = __libcpp_mbsrtowcs_l(__wb, &__nb, countof(__wb, __we), &mb, __loc_);
5439     if (j == size_t(-1))
5440         __throw_runtime_error("locale not supported");
5441     __we = __wb + j;
5442 }
5443
5444 // moneypunct_byname
5445
5446 template <class charT>
5447 static
5448 void
5449 __init_pat(money_base::pattern& pat, basic_string<charT>& __curr_symbol_,
5450            bool intl, char cs_precedes, char sep_by_space, char sign_posn,
5451            charT space_char)
5452 {
5453     const char sign = static_cast<char>(money_base::sign);
5454     const char space = static_cast<char>(money_base::space);
5455     const char none = static_cast<char>(money_base::none);
5456     const char symbol = static_cast<char>(money_base::symbol);
5457     const char value = static_cast<char>(money_base::value);
5458     const bool symbol_contains_sep = intl && __curr_symbol_.size() == 4;
5459
5460     // Comments on case branches reflect 'C11 7.11.2.1 The localeconv
5461     // function'. "Space between sign and symbol or value" means that
5462     // if the sign is adjacent to the symbol, there's a space between
5463     // them, and otherwise there's a space between the sign and value.
5464     //
5465     // C11's localeconv specifies that the fourth character of an
5466     // international curr_symbol is used to separate the sign and
5467     // value when sep_by_space says to do so. C++ can't represent
5468     // that, so we just use a space.  When sep_by_space says to
5469     // separate the symbol and value-or-sign with a space, we rearrange the
5470     // curr_symbol to put its spacing character on the correct side of
5471     // the symbol.
5472     //
5473     // We also need to avoid adding an extra space between the sign
5474     // and value when the currency symbol is suppressed (by not
5475     // setting showbase).  We match glibc's strfmon by interpreting
5476     // sep_by_space==1 as "omit the space when the currency symbol is
5477     // absent".
5478     //
5479     // Users who want to get this right should use ICU instead.
5480
5481     switch (cs_precedes)
5482     {
5483     case 0:  // value before curr_symbol
5484         if (symbol_contains_sep) {
5485             // Move the separator to before the symbol, to place it
5486             // between the value and symbol.
5487             rotate(__curr_symbol_.begin(), __curr_symbol_.begin() + 3,
5488                    __curr_symbol_.end());
5489         }
5490         switch (sign_posn)
5491         {
5492         case 0:  // Parentheses surround the quantity and currency symbol.
5493             pat.field[0] = sign;
5494             pat.field[1] = value;
5495             pat.field[2] = none;  // Any space appears in the symbol.
5496             pat.field[3] = symbol;
5497             switch (sep_by_space)
5498             {
5499             case 0:  // No space separates the currency symbol and value.
5500                 // This case may have changed between C99 and C11;
5501                 // assume the currency symbol matches the intention.
5502             case 2:  // Space between sign and currency or value.
5503                 // The "sign" is two parentheses, so no space here either.
5504                 return;
5505             case 1:  // Space between currency-and-sign or currency and value.
5506                 if (!symbol_contains_sep) {
5507                     // We insert the space into the symbol instead of
5508                     // setting pat.field[2]=space so that when
5509                     // showbase is not set, the space goes away too.
5510                     __curr_symbol_.insert(0, 1, space_char);
5511                 }
5512                 return;
5513             default:
5514                 break;
5515             }
5516             break;
5517         case 1:  // The sign string precedes the quantity and currency symbol.
5518             pat.field[0] = sign;
5519             pat.field[3] = symbol;
5520             switch (sep_by_space)
5521             {
5522             case 0:  // No space separates the currency symbol and value.
5523                 pat.field[1] = value;
5524                 pat.field[2] = none;
5525                 return;
5526             case 1:  // Space between currency-and-sign or currency and value.
5527                 pat.field[1] = value;
5528                 pat.field[2] = none;
5529                 if (!symbol_contains_sep) {
5530                     // We insert the space into the symbol instead of
5531                     // setting pat.field[2]=space so that when
5532                     // showbase is not set, the space goes away too.
5533                     __curr_symbol_.insert(0, 1, space_char);
5534                 }
5535                 return;
5536             case 2:  // Space between sign and currency or value.
5537                 pat.field[1] = space;
5538                 pat.field[2] = value;
5539                 if (symbol_contains_sep) {
5540                     // Remove the separator from the symbol, since it
5541                     // has already appeared after the sign.
5542                     __curr_symbol_.erase(__curr_symbol_.begin());
5543                 }
5544                 return;
5545             default:
5546                 break;
5547             }
5548             break;
5549         case 2:  // The sign string succeeds the quantity and currency symbol.
5550             pat.field[0] = value;
5551             pat.field[3] = sign;
5552             switch (sep_by_space)
5553             {
5554             case 0:  // No space separates the currency symbol and value.
5555                 pat.field[1] = none;
5556                 pat.field[2] = symbol;
5557                 return;
5558             case 1:  // Space between currency-and-sign or currency and value.
5559                 if (!symbol_contains_sep) {
5560                     // We insert the space into the symbol instead of
5561                     // setting pat.field[1]=space so that when
5562                     // showbase is not set, the space goes away too.
5563                     __curr_symbol_.insert(0, 1, space_char);
5564                 }
5565                 pat.field[1] = none;
5566                 pat.field[2] = symbol;
5567                 return;
5568             case 2:  // Space between sign and currency or value.
5569                 pat.field[1] = symbol;
5570                 pat.field[2] = space;
5571                 if (symbol_contains_sep) {
5572                     // Remove the separator from the symbol, since it
5573                     // should not be removed if showbase is absent.
5574                     __curr_symbol_.erase(__curr_symbol_.begin());
5575                 }
5576                 return;
5577             default:
5578                 break;
5579             }
5580             break;
5581         case 3:  // The sign string immediately precedes the currency symbol.
5582             pat.field[0] = value;
5583             pat.field[3] = symbol;
5584             switch (sep_by_space)
5585             {
5586             case 0:  // No space separates the currency symbol and value.
5587                 pat.field[1] = none;
5588                 pat.field[2] = sign;
5589                 return;
5590             case 1:  // Space between currency-and-sign or currency and value.
5591                 pat.field[1] = space;
5592                 pat.field[2] = sign;
5593                 if (symbol_contains_sep) {
5594                     // Remove the separator from the symbol, since it
5595                     // has already appeared before the sign.
5596                     __curr_symbol_.erase(__curr_symbol_.begin());
5597                 }
5598                 return;
5599             case 2:  // Space between sign and currency or value.
5600                 pat.field[1] = sign;
5601                 pat.field[2] = none;
5602                 if (!symbol_contains_sep) {
5603                     // We insert the space into the symbol instead of
5604                     // setting pat.field[2]=space so that when
5605                     // showbase is not set, the space goes away too.
5606                     __curr_symbol_.insert(0, 1, space_char);
5607                 }
5608                 return;
5609             default:
5610                 break;
5611             }
5612             break;
5613         case 4:  // The sign string immediately succeeds the currency symbol.
5614             pat.field[0] = value;
5615             pat.field[3] = sign;
5616             switch (sep_by_space)
5617             {
5618             case 0:  // No space separates the currency symbol and value.
5619                 pat.field[1] = none;
5620                 pat.field[2] = symbol;
5621                 return;
5622             case 1:  // Space between currency-and-sign or currency and value.
5623                 pat.field[1] = none;
5624                 pat.field[2] = symbol;
5625                 if (!symbol_contains_sep) {
5626                     // We insert the space into the symbol instead of
5627                     // setting pat.field[1]=space so that when
5628                     // showbase is not set, the space goes away too.
5629                     __curr_symbol_.insert(0, 1, space_char);
5630                 }
5631                 return;
5632             case 2:  // Space between sign and currency or value.
5633                 pat.field[1] = symbol;
5634                 pat.field[2] = space;
5635                 if (symbol_contains_sep) {
5636                     // Remove the separator from the symbol, since it
5637                     // should not disappear when showbase is absent.
5638                     __curr_symbol_.erase(__curr_symbol_.begin());
5639                 }
5640                 return;
5641             default:
5642                 break;
5643             }
5644             break;
5645         default:
5646             break;
5647         }
5648         break;
5649     case 1:  // curr_symbol before value
5650         switch (sign_posn)
5651         {
5652         case 0:  // Parentheses surround the quantity and currency symbol.
5653             pat.field[0] = sign;
5654             pat.field[1] = symbol;
5655             pat.field[2] = none;  // Any space appears in the symbol.
5656             pat.field[3] = value;
5657             switch (sep_by_space)
5658             {
5659             case 0:  // No space separates the currency symbol and value.
5660                 // This case may have changed between C99 and C11;
5661                 // assume the currency symbol matches the intention.
5662             case 2:  // Space between sign and currency or value.
5663                 // The "sign" is two parentheses, so no space here either.
5664                 return;
5665             case 1:  // Space between currency-and-sign or currency and value.
5666                 if (!symbol_contains_sep) {
5667                     // We insert the space into the symbol instead of
5668                     // setting pat.field[2]=space so that when
5669                     // showbase is not set, the space goes away too.
5670                     __curr_symbol_.insert(0, 1, space_char);
5671                 }
5672                 return;
5673             default:
5674                 break;
5675             }
5676             break;
5677         case 1:  // The sign string precedes the quantity and currency symbol.
5678             pat.field[0] = sign;
5679             pat.field[3] = value;
5680             switch (sep_by_space)
5681             {
5682             case 0:  // No space separates the currency symbol and value.
5683                 pat.field[1] = symbol;
5684                 pat.field[2] = none;
5685                 return;
5686             case 1:  // Space between currency-and-sign or currency and value.
5687                 pat.field[1] = symbol;
5688                 pat.field[2] = none;
5689                 if (!symbol_contains_sep) {
5690                     // We insert the space into the symbol instead of
5691                     // setting pat.field[2]=space so that when
5692                     // showbase is not set, the space goes away too.
5693                     __curr_symbol_.push_back(space_char);
5694                 }
5695                 return;
5696             case 2:  // Space between sign and currency or value.
5697                 pat.field[1] = space;
5698                 pat.field[2] = symbol;
5699                 if (symbol_contains_sep) {
5700                     // Remove the separator from the symbol, since it
5701                     // has already appeared after the sign.
5702                     __curr_symbol_.pop_back();
5703                 }
5704                 return;
5705             default:
5706                 break;
5707             }
5708             break;
5709         case 2:  // The sign string succeeds the quantity and currency symbol.
5710             pat.field[0] = symbol;
5711             pat.field[3] = sign;
5712             switch (sep_by_space)
5713             {
5714             case 0:  // No space separates the currency symbol and value.
5715                 pat.field[1] = none;
5716                 pat.field[2] = value;
5717                 return;
5718             case 1:  // Space between currency-and-sign or currency and value.
5719                 pat.field[1] = none;
5720                 pat.field[2] = value;
5721                 if (!symbol_contains_sep) {
5722                     // We insert the space into the symbol instead of
5723                     // setting pat.field[1]=space so that when
5724                     // showbase is not set, the space goes away too.
5725                     __curr_symbol_.push_back(space_char);
5726                 }
5727                 return;
5728             case 2:  // Space between sign and currency or value.
5729                 pat.field[1] = value;
5730                 pat.field[2] = space;
5731                 if (symbol_contains_sep) {
5732                     // Remove the separator from the symbol, since it
5733                     // will appear before the sign.
5734                     __curr_symbol_.pop_back();
5735                 }
5736                 return;
5737             default:
5738                 break;
5739             }
5740             break;
5741         case 3:  // The sign string immediately precedes the currency symbol.
5742             pat.field[0] = sign;
5743             pat.field[3] = value;
5744             switch (sep_by_space)
5745             {
5746             case 0:  // No space separates the currency symbol and value.
5747                 pat.field[1] = symbol;
5748                 pat.field[2] = none;
5749                 return;
5750             case 1:  // Space between currency-and-sign or currency and value.
5751                 pat.field[1] = symbol;
5752                 pat.field[2] = none;
5753                 if (!symbol_contains_sep) {
5754                     // We insert the space into the symbol instead of
5755                     // setting pat.field[2]=space so that when
5756                     // showbase is not set, the space goes away too.
5757                     __curr_symbol_.push_back(space_char);
5758                 }
5759                 return;
5760             case 2:  // Space between sign and currency or value.
5761                 pat.field[1] = space;
5762                 pat.field[2] = symbol;
5763                 if (symbol_contains_sep) {
5764                     // Remove the separator from the symbol, since it
5765                     // has already appeared after the sign.
5766                     __curr_symbol_.pop_back();
5767                 }
5768                 return;
5769             default:
5770                 break;
5771             }
5772             break;
5773         case 4:  // The sign string immediately succeeds the currency symbol.
5774             pat.field[0] = symbol;
5775             pat.field[3] = value;
5776             switch (sep_by_space)
5777             {
5778             case 0:  // No space separates the currency symbol and value.
5779                 pat.field[1] = sign;
5780                 pat.field[2] = none;
5781                 return;
5782             case 1:  // Space between currency-and-sign or currency and value.
5783                 pat.field[1] = sign;
5784                 pat.field[2] = space;
5785                 if (symbol_contains_sep) {
5786                     // Remove the separator from the symbol, since it
5787                     // should not disappear when showbase is absent.
5788                     __curr_symbol_.pop_back();
5789                 }
5790                 return;
5791             case 2:  // Space between sign and currency or value.
5792                 pat.field[1] = none;
5793                 pat.field[2] = sign;
5794                 if (!symbol_contains_sep) {
5795                     // We insert the space into the symbol instead of
5796                     // setting pat.field[1]=space so that when
5797                     // showbase is not set, the space goes away too.
5798                     __curr_symbol_.push_back(space_char);
5799                 }
5800                 return;
5801            default:
5802                 break;
5803             }
5804             break;
5805         default:
5806             break;
5807         }
5808         break;
5809     default:
5810         break;
5811     }
5812     pat.field[0] = symbol;
5813     pat.field[1] = sign;
5814     pat.field[2] = none;
5815     pat.field[3] = value;
5816 }
5817
5818 template<>
5819 void
5820 moneypunct_byname<char, false>::init(const char* nm)
5821 {
5822     typedef moneypunct<char, false> base;
5823     __locale_unique_ptr loc(newlocale(LC_ALL_MASK, nm, 0), freelocale);
5824     if (loc == nullptr)
5825         __throw_runtime_error("moneypunct_byname"
5826                             " failed to construct for " + string(nm));
5827
5828     lconv* lc = __libcpp_localeconv_l(loc.get());
5829     if (!checked_string_to_char_convert(__decimal_point_,
5830                                         lc->mon_decimal_point,
5831                                         loc.get()))
5832       __decimal_point_ = base::do_decimal_point();
5833     if (!checked_string_to_char_convert(__thousands_sep_,
5834                                         lc->mon_thousands_sep,
5835                                         loc.get()))
5836       __thousands_sep_ = base::do_thousands_sep();
5837
5838     __grouping_ = lc->mon_grouping;
5839     __curr_symbol_ = lc->currency_symbol;
5840     if (lc->frac_digits != CHAR_MAX)
5841         __frac_digits_ = lc->frac_digits;
5842     else
5843         __frac_digits_ = base::do_frac_digits();
5844     if (lc->p_sign_posn == 0)
5845         __positive_sign_ = "()";
5846     else
5847         __positive_sign_ = lc->positive_sign;
5848     if (lc->n_sign_posn == 0)
5849         __negative_sign_ = "()";
5850     else
5851         __negative_sign_ = lc->negative_sign;
5852     // Assume the positive and negative formats will want spaces in
5853     // the same places in curr_symbol since there's no way to
5854     // represent anything else.
5855     string_type __dummy_curr_symbol = __curr_symbol_;
5856     __init_pat(__pos_format_, __dummy_curr_symbol, false,
5857                lc->p_cs_precedes, lc->p_sep_by_space, lc->p_sign_posn, ' ');
5858     __init_pat(__neg_format_, __curr_symbol_, false,
5859                lc->n_cs_precedes, lc->n_sep_by_space, lc->n_sign_posn, ' ');
5860 }
5861
5862 template<>
5863 void
5864 moneypunct_byname<char, true>::init(const char* nm)
5865 {
5866     typedef moneypunct<char, true> base;
5867     __locale_unique_ptr loc(newlocale(LC_ALL_MASK, nm, 0), freelocale);
5868     if (loc == nullptr)
5869         __throw_runtime_error("moneypunct_byname"
5870                             " failed to construct for " + string(nm));
5871
5872     lconv* lc = __libcpp_localeconv_l(loc.get());
5873     if (!checked_string_to_char_convert(__decimal_point_,
5874                                         lc->mon_decimal_point,
5875                                         loc.get()))
5876       __decimal_point_ = base::do_decimal_point();
5877     if (!checked_string_to_char_convert(__thousands_sep_,
5878                                         lc->mon_thousands_sep,
5879                                         loc.get()))
5880       __thousands_sep_ = base::do_thousands_sep();
5881     __grouping_ = lc->mon_grouping;
5882     __curr_symbol_ = lc->int_curr_symbol;
5883     if (lc->int_frac_digits != CHAR_MAX)
5884         __frac_digits_ = lc->int_frac_digits;
5885     else
5886         __frac_digits_ = base::do_frac_digits();
5887 #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
5888     if (lc->p_sign_posn == 0)
5889 #else // _LIBCPP_MSVCRT
5890     if (lc->int_p_sign_posn == 0)
5891 #endif // !_LIBCPP_MSVCRT
5892         __positive_sign_ = "()";
5893     else
5894         __positive_sign_ = lc->positive_sign;
5895 #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
5896     if(lc->n_sign_posn == 0)
5897 #else // _LIBCPP_MSVCRT
5898     if (lc->int_n_sign_posn == 0)
5899 #endif // !_LIBCPP_MSVCRT
5900         __negative_sign_ = "()";
5901     else
5902         __negative_sign_ = lc->negative_sign;
5903     // Assume the positive and negative formats will want spaces in
5904     // the same places in curr_symbol since there's no way to
5905     // represent anything else.
5906     string_type __dummy_curr_symbol = __curr_symbol_;
5907 #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
5908     __init_pat(__pos_format_, __dummy_curr_symbol, true,
5909                lc->p_cs_precedes, lc->p_sep_by_space, lc->p_sign_posn, ' ');
5910     __init_pat(__neg_format_, __curr_symbol_, true,
5911                lc->n_cs_precedes, lc->n_sep_by_space, lc->n_sign_posn, ' ');
5912 #else // _LIBCPP_MSVCRT
5913     __init_pat(__pos_format_, __dummy_curr_symbol, true,
5914                lc->int_p_cs_precedes, lc->int_p_sep_by_space,
5915                lc->int_p_sign_posn, ' ');
5916     __init_pat(__neg_format_, __curr_symbol_, true,
5917                lc->int_n_cs_precedes, lc->int_n_sep_by_space,
5918                lc->int_n_sign_posn, ' ');
5919 #endif // !_LIBCPP_MSVCRT
5920 }
5921
5922 template<>
5923 void
5924 moneypunct_byname<wchar_t, false>::init(const char* nm)
5925 {
5926     typedef moneypunct<wchar_t, false> base;
5927     __locale_unique_ptr loc(newlocale(LC_ALL_MASK, nm, 0), freelocale);
5928     if (loc == nullptr)
5929         __throw_runtime_error("moneypunct_byname"
5930                             " failed to construct for " + string(nm));
5931     lconv* lc = __libcpp_localeconv_l(loc.get());
5932     if (!checked_string_to_wchar_convert(__decimal_point_,
5933                                          lc->mon_decimal_point,
5934                                          loc.get()))
5935       __decimal_point_ = base::do_decimal_point();
5936     if (!checked_string_to_wchar_convert(__thousands_sep_,
5937                                          lc->mon_thousands_sep,
5938                                          loc.get()))
5939       __thousands_sep_ = base::do_thousands_sep();
5940     __grouping_ = lc->mon_grouping;
5941     wchar_t wbuf[100];
5942     mbstate_t mb = {0};
5943     const char* bb = lc->currency_symbol;
5944     size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get());
5945     if (j == size_t(-1))
5946         __throw_runtime_error("locale not supported");
5947     wchar_t* wbe = wbuf + j;
5948     __curr_symbol_.assign(wbuf, wbe);
5949     if (lc->frac_digits != CHAR_MAX)
5950         __frac_digits_ = lc->frac_digits;
5951     else
5952         __frac_digits_ = base::do_frac_digits();
5953     if (lc->p_sign_posn == 0)
5954         __positive_sign_ = L"()";
5955     else
5956     {
5957         mb = mbstate_t();
5958         bb = lc->positive_sign;
5959         j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get());
5960         if (j == size_t(-1))
5961             __throw_runtime_error("locale not supported");
5962         wbe = wbuf + j;
5963         __positive_sign_.assign(wbuf, wbe);
5964     }
5965     if (lc->n_sign_posn == 0)
5966         __negative_sign_ = L"()";
5967     else
5968     {
5969         mb = mbstate_t();
5970         bb = lc->negative_sign;
5971         j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get());
5972         if (j == size_t(-1))
5973             __throw_runtime_error("locale not supported");
5974         wbe = wbuf + j;
5975         __negative_sign_.assign(wbuf, wbe);
5976     }
5977     // Assume the positive and negative formats will want spaces in
5978     // the same places in curr_symbol since there's no way to
5979     // represent anything else.
5980     string_type __dummy_curr_symbol = __curr_symbol_;
5981     __init_pat(__pos_format_, __dummy_curr_symbol, false,
5982                lc->p_cs_precedes, lc->p_sep_by_space, lc->p_sign_posn, L' ');
5983     __init_pat(__neg_format_, __curr_symbol_, false,
5984                lc->n_cs_precedes, lc->n_sep_by_space, lc->n_sign_posn, L' ');
5985 }
5986
5987 template<>
5988 void
5989 moneypunct_byname<wchar_t, true>::init(const char* nm)
5990 {
5991     typedef moneypunct<wchar_t, true> base;
5992     __locale_unique_ptr loc(newlocale(LC_ALL_MASK, nm, 0), freelocale);
5993     if (loc == nullptr)
5994         __throw_runtime_error("moneypunct_byname"
5995                             " failed to construct for " + string(nm));
5996
5997     lconv* lc = __libcpp_localeconv_l(loc.get());
5998     if (!checked_string_to_wchar_convert(__decimal_point_,
5999                                          lc->mon_decimal_point,
6000                                          loc.get()))
6001       __decimal_point_ = base::do_decimal_point();
6002     if (!checked_string_to_wchar_convert(__thousands_sep_,
6003                                          lc->mon_thousands_sep,
6004                                          loc.get()))
6005       __thousands_sep_ = base::do_thousands_sep();
6006     __grouping_ = lc->mon_grouping;
6007     wchar_t wbuf[100];
6008     mbstate_t mb = {0};
6009     const char* bb = lc->int_curr_symbol;
6010     size_t j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get());
6011     if (j == size_t(-1))
6012         __throw_runtime_error("locale not supported");
6013     wchar_t* wbe = wbuf + j;
6014     __curr_symbol_.assign(wbuf, wbe);
6015     if (lc->int_frac_digits != CHAR_MAX)
6016         __frac_digits_ = lc->int_frac_digits;
6017     else
6018         __frac_digits_ = base::do_frac_digits();
6019 #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
6020     if (lc->p_sign_posn == 0)
6021 #else // _LIBCPP_MSVCRT
6022     if (lc->int_p_sign_posn == 0)
6023 #endif // !_LIBCPP_MSVCRT
6024         __positive_sign_ = L"()";
6025     else
6026     {
6027         mb = mbstate_t();
6028         bb = lc->positive_sign;
6029         j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get());
6030         if (j == size_t(-1))
6031             __throw_runtime_error("locale not supported");
6032         wbe = wbuf + j;
6033         __positive_sign_.assign(wbuf, wbe);
6034     }
6035 #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
6036     if (lc->n_sign_posn == 0)
6037 #else // _LIBCPP_MSVCRT
6038     if (lc->int_n_sign_posn == 0)
6039 #endif // !_LIBCPP_MSVCRT
6040         __negative_sign_ = L"()";
6041     else
6042     {
6043         mb = mbstate_t();
6044         bb = lc->negative_sign;
6045         j = __libcpp_mbsrtowcs_l(wbuf, &bb, countof(wbuf), &mb, loc.get());
6046         if (j == size_t(-1))
6047             __throw_runtime_error("locale not supported");
6048         wbe = wbuf + j;
6049         __negative_sign_.assign(wbuf, wbe);
6050     }
6051     // Assume the positive and negative formats will want spaces in
6052     // the same places in curr_symbol since there's no way to
6053     // represent anything else.
6054     string_type __dummy_curr_symbol = __curr_symbol_;
6055 #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
6056     __init_pat(__pos_format_, __dummy_curr_symbol, true,
6057                lc->p_cs_precedes, lc->p_sep_by_space, lc->p_sign_posn, L' ');
6058     __init_pat(__neg_format_, __curr_symbol_, true,
6059                lc->n_cs_precedes, lc->n_sep_by_space, lc->n_sign_posn, L' ');
6060 #else // _LIBCPP_MSVCRT
6061     __init_pat(__pos_format_, __dummy_curr_symbol, true,
6062                lc->int_p_cs_precedes, lc->int_p_sep_by_space,
6063                lc->int_p_sign_posn, L' ');
6064     __init_pat(__neg_format_, __curr_symbol_, true,
6065                lc->int_n_cs_precedes, lc->int_n_sep_by_space,
6066                lc->int_n_sign_posn, L' ');
6067 #endif // !_LIBCPP_MSVCRT
6068 }
6069
6070 void __do_nothing(void*) {}
6071
6072 void __throw_runtime_error(const char* msg)
6073 {
6074 #ifndef _LIBCPP_NO_EXCEPTIONS
6075     throw runtime_error(msg);
6076 #else
6077     (void)msg;
6078     _VSTD::abort();
6079 #endif
6080 }
6081
6082 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS collate<char>;
6083 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS collate<wchar_t>;
6084
6085 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS num_get<char>;
6086 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS num_get<wchar_t>;
6087
6088 template struct _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __num_get<char>;
6089 template struct _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __num_get<wchar_t>;
6090
6091 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS num_put<char>;
6092 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS num_put<wchar_t>;
6093
6094 template struct _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __num_put<char>;
6095 template struct _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __num_put<wchar_t>;
6096
6097 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_get<char>;
6098 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_get<wchar_t>;
6099
6100 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_get_byname<char>;
6101 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_get_byname<wchar_t>;
6102
6103 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_put<char>;
6104 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_put<wchar_t>;
6105
6106 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_put_byname<char>;
6107 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS time_put_byname<wchar_t>;
6108
6109 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct<char, false>;
6110 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct<char, true>;
6111 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct<wchar_t, false>;
6112 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct<wchar_t, true>;
6113
6114 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct_byname<char, false>;
6115 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct_byname<char, true>;
6116 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct_byname<wchar_t, false>;
6117 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS moneypunct_byname<wchar_t, true>;
6118
6119 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS money_get<char>;
6120 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS money_get<wchar_t>;
6121
6122 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __money_get<char>;
6123 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __money_get<wchar_t>;
6124
6125 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS money_put<char>;
6126 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS money_put<wchar_t>;
6127
6128 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __money_put<char>;
6129 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __money_put<wchar_t>;
6130
6131 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS messages<char>;
6132 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS messages<wchar_t>;
6133
6134 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS messages_byname<char>;
6135 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS messages_byname<wchar_t>;
6136
6137 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char, char, mbstate_t>;
6138 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<wchar_t, char, mbstate_t>;
6139 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char16_t, char, mbstate_t>;
6140 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS codecvt_byname<char32_t, char, mbstate_t>;
6141
6142 template class _LIBCPP_CLASS_TEMPLATE_INSTANTIATION_VIS __vector_base_common<true>;
6143
6144 _LIBCPP_END_NAMESPACE_STD