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