Home | History | Annotate | Download | only in include
      1 // -*- C++ -*-
      2 //===-------------------------- locale ------------------------------------===//
      3 //
      4 //                     The LLVM Compiler Infrastructure
      5 //
      6 // This file is dual licensed under the MIT and the University of Illinois Open
      7 // Source Licenses. See LICENSE.TXT for details.
      8 //
      9 //===----------------------------------------------------------------------===//
     10 
     11 #ifndef _LIBCPP_LOCALE
     12 #define _LIBCPP_LOCALE
     13 
     14 /*
     15     locale synopsis
     16 
     17 namespace std
     18 {
     19 
     20 class locale
     21 {
     22 public:
     23     // types:
     24     class facet;
     25     class id;
     26 
     27     typedef int category;
     28     static const category // values assigned here are for exposition only
     29         none     = 0x000,
     30         collate  = 0x010,
     31         ctype    = 0x020,
     32         monetary = 0x040,
     33         numeric  = 0x080,
     34         time     = 0x100,
     35         messages = 0x200,
     36         all = collate | ctype | monetary | numeric | time | messages;
     37 
     38     // construct/copy/destroy:
     39     locale() noexcept;
     40     locale(const locale& other) noexcept;
     41     explicit locale(const char* std_name);
     42     explicit locale(const string& std_name);
     43     locale(const locale& other, const char* std_name, category);
     44     locale(const locale& other, const string& std_name, category);
     45     template <class Facet> locale(const locale& other, Facet* f);
     46     locale(const locale& other, const locale& one, category);
     47 
     48     ~locale(); // not virtual
     49 
     50     const locale& operator=(const locale& other) noexcept;
     51 
     52     template <class Facet> locale combine(const locale& other) const;
     53 
     54     // locale operations:
     55     basic_string<char> name() const;
     56     bool operator==(const locale& other) const;
     57     bool operator!=(const locale& other) const;
     58     template <class charT, class Traits, class Allocator>
     59       bool operator()(const basic_string<charT,Traits,Allocator>& s1,
     60                       const basic_string<charT,Traits,Allocator>& s2) const;
     61 
     62     // global locale objects:
     63     static locale global(const locale&);
     64     static const locale& classic();
     65 };
     66 
     67 template <class Facet> const Facet& use_facet(const locale&);
     68 template <class Facet> bool has_facet(const locale&) noexcept;
     69 
     70 // 22.3.3, convenience interfaces:
     71 template <class charT> bool isspace (charT c, const locale& loc);
     72 template <class charT> bool isprint (charT c, const locale& loc);
     73 template <class charT> bool iscntrl (charT c, const locale& loc);
     74 template <class charT> bool isupper (charT c, const locale& loc);
     75 template <class charT> bool islower (charT c, const locale& loc);
     76 template <class charT> bool isalpha (charT c, const locale& loc);
     77 template <class charT> bool isdigit (charT c, const locale& loc);
     78 template <class charT> bool ispunct (charT c, const locale& loc);
     79 template <class charT> bool isxdigit(charT c, const locale& loc);
     80 template <class charT> bool isalnum (charT c, const locale& loc);
     81 template <class charT> bool isgraph (charT c, const locale& loc);
     82 template <class charT> charT toupper(charT c, const locale& loc);
     83 template <class charT> charT tolower(charT c, const locale& loc);
     84 
     85 template<class Codecvt, class Elem = wchar_t,
     86          class Wide_alloc = allocator<Elem>,
     87          class Byte_alloc = allocator<char>>
     88 class wstring_convert
     89 {
     90 public:
     91     typedef basic_string<char, char_traits<char>, Byte_alloc> byte_string;
     92     typedef basic_string<Elem, char_traits<Elem>, Wide_alloc> wide_string;
     93     typedef typename Codecvt::state_type                      state_type;
     94     typedef typename wide_string::traits_type::int_type       int_type;
     95 
     96     explicit wstring_convert(Codecvt* pcvt = new Codecvt);          // explicit in C++14
     97     wstring_convert(Codecvt* pcvt, state_type state);
     98     explicit wstring_convert(const byte_string& byte_err,           // explicit in C++14
     99                     const wide_string& wide_err = wide_string());
    100     wstring_convert(const wstring_convert&) = delete;               // C++14
    101     wstring_convert & operator=(const wstring_convert &) = delete;  // C++14
    102     ~wstring_convert();
    103 
    104     wide_string from_bytes(char byte);
    105     wide_string from_bytes(const char* ptr);
    106     wide_string from_bytes(const byte_string& str);
    107     wide_string from_bytes(const char* first, const char* last);
    108 
    109     byte_string to_bytes(Elem wchar);
    110     byte_string to_bytes(const Elem* wptr);
    111     byte_string to_bytes(const wide_string& wstr);
    112     byte_string to_bytes(const Elem* first, const Elem* last);
    113 
    114     size_t converted() const; // noexcept in C++14
    115     state_type state() const;
    116 };
    117 
    118 template <class Codecvt, class Elem = wchar_t, class Tr = char_traits<Elem>>
    119 class wbuffer_convert
    120     : public basic_streambuf<Elem, Tr>
    121 {
    122 public:
    123     typedef typename Tr::state_type state_type;
    124 
    125     explicit wbuffer_convert(streambuf* bytebuf = 0, Codecvt* pcvt = new Codecvt,
    126                     state_type state = state_type());       // explicit in C++14
    127     wbuffer_convert(const wbuffer_convert&) = delete;               // C++14
    128     wbuffer_convert & operator=(const wbuffer_convert &) = delete;  // C++14
    129     ~wbuffer_convert();                                             // C++14
    130     
    131     streambuf* rdbuf() const;
    132     streambuf* rdbuf(streambuf* bytebuf);
    133 
    134     state_type state() const;
    135 };
    136 
    137 // 22.4.1 and 22.4.1.3, ctype:
    138 class ctype_base;
    139 template <class charT> class ctype;
    140 template <> class ctype<char>; // specialization
    141 template <class charT> class ctype_byname;
    142 template <> class ctype_byname<char>; // specialization
    143 
    144 class codecvt_base;
    145 template <class internT, class externT, class stateT> class codecvt;
    146 template <class internT, class externT, class stateT> class codecvt_byname;
    147 
    148 // 22.4.2 and 22.4.3, numeric:
    149 template <class charT, class InputIterator> class num_get;
    150 template <class charT, class OutputIterator> class num_put;
    151 template <class charT> class numpunct;
    152 template <class charT> class numpunct_byname;
    153 
    154 // 22.4.4, col lation:
    155 template <class charT> class collate;
    156 template <class charT> class collate_byname;
    157 
    158 // 22.4.5, date and time:
    159 class time_base;
    160 template <class charT, class InputIterator> class time_get;
    161 template <class charT, class InputIterator> class time_get_byname;
    162 template <class charT, class OutputIterator> class time_put;
    163 template <class charT, class OutputIterator> class time_put_byname;
    164 
    165 // 22.4.6, money:
    166 class money_base;
    167 template <class charT, class InputIterator> class money_get;
    168 template <class charT, class OutputIterator> class money_put;
    169 template <class charT, bool Intl> class moneypunct;
    170 template <class charT, bool Intl> class moneypunct_byname;
    171 
    172 // 22.4.7, message retrieval:
    173 class messages_base;
    174 template <class charT> class messages;
    175 template <class charT> class messages_byname;
    176 
    177 }  // std
    178 
    179 */
    180 
    181 #include <__config>
    182 #include <__locale>
    183 #include <algorithm>
    184 #include <memory>
    185 #include <ios>
    186 #include <streambuf>
    187 #include <iterator>
    188 #include <limits>
    189 #ifndef __APPLE__
    190 #include <cstdarg>
    191 #endif
    192 #include <cstdlib>
    193 #include <ctime>
    194 #if defined(_LIBCPP_MSVCRT) || defined(__MINGW32__)
    195 #include <support/win32/locale_win32.h>
    196 #elif defined(_NEWLIB_VERSION)
    197 // FIXME: replace all the uses of _NEWLIB_VERSION with __NEWLIB__ preceded by an
    198 // include of <sys/cdefs.h> once https://sourceware.org/ml/newlib-cvs/2014-q3/msg00038.html
    199 // has had a chance to bake for a bit
    200 #include <support/newlib/xlocale.h>
    201 #elif !defined(__ANDROID__)
    202 #include <nl_types.h>
    203 #endif
    204 
    205 #ifdef __APPLE__
    206 #include <Availability.h>
    207 #endif
    208 
    209 #include <__undef_min_max>
    210 
    211 #if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
    212 #pragma GCC system_header
    213 #endif
    214 
    215 _LIBCPP_BEGIN_NAMESPACE_STD
    216 
    217 #if defined(__APPLE__) || defined(__FreeBSD__)
    218 #  define _LIBCPP_GET_C_LOCALE 0
    219 #elif defined(__NetBSD__)
    220 #  define _LIBCPP_GET_C_LOCALE LC_C_LOCALE
    221 #else
    222 #  define _LIBCPP_GET_C_LOCALE __cloc()
    223    // Get the C locale object
    224    _LIBCPP_FUNC_VIS locale_t __cloc();
    225 #define __cloc_defined
    226 #endif
    227 
    228 typedef _VSTD::remove_pointer<locale_t>::type __locale_struct;
    229 typedef _VSTD::unique_ptr<__locale_struct, decltype(&freelocale)> __locale_unique_ptr;
    230 #ifndef _LIBCPP_LOCALE__L_EXTENSIONS
    231 typedef _VSTD::unique_ptr<__locale_struct, decltype(&uselocale)> __locale_raii;
    232 #endif
    233 
    234 // OSX has nice foo_l() functions that let you turn off use of the global
    235 // locale.  Linux, not so much.  The following functions avoid the locale when
    236 // that's possible and otherwise do the wrong thing.  FIXME.
    237 #if defined(__linux__) || defined(__EMSCRIPTEN__) || defined(_AIX) || \
    238     defined(_NEWLIB_VERSION)
    239 
    240 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    241 decltype(MB_CUR_MAX_L(_VSTD::declval<locale_t>()))
    242 inline _LIBCPP_INLINE_VISIBILITY
    243 __mb_cur_max_l(locale_t __l)
    244 {
    245   return MB_CUR_MAX_L(__l);
    246 }
    247 #else  // _LIBCPP_LOCALE__L_EXTENSIONS
    248 inline _LIBCPP_ALWAYS_INLINE
    249 decltype(MB_CUR_MAX) __mb_cur_max_l(locale_t __l)
    250 {
    251   __locale_raii __current(uselocale(__l), uselocale);
    252   return MB_CUR_MAX;
    253 }
    254 #endif // _LIBCPP_LOCALE__L_EXTENSIONS
    255 
    256 inline _LIBCPP_ALWAYS_INLINE
    257 wint_t __btowc_l(int __c, locale_t __l)
    258 {
    259 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    260   return btowc_l(__c, __l);
    261 #else
    262   __locale_raii __current(uselocale(__l), uselocale);
    263   return btowc(__c);
    264 #endif
    265 }
    266 
    267 inline _LIBCPP_ALWAYS_INLINE
    268 int __wctob_l(wint_t __c, locale_t __l)
    269 {
    270 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    271   return wctob_l(__c, __l);
    272 #else
    273   __locale_raii __current(uselocale(__l), uselocale);
    274   return wctob(__c);
    275 #endif
    276 }
    277 
    278 inline _LIBCPP_ALWAYS_INLINE
    279 size_t __wcsnrtombs_l(char *__dest, const wchar_t **__src, size_t __nwc,
    280                       size_t __len, mbstate_t *__ps, locale_t __l)
    281 {
    282 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    283   return wcsnrtombs_l(__dest, __src, __nwc, __len, __ps, __l);
    284 #else
    285   __locale_raii __current(uselocale(__l), uselocale);
    286   return wcsnrtombs(__dest, __src, __nwc, __len, __ps);
    287 #endif
    288 }
    289 
    290 inline _LIBCPP_ALWAYS_INLINE
    291 size_t __wcrtomb_l(char *__s, wchar_t __wc, mbstate_t *__ps, locale_t __l)
    292 {
    293 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    294   return wcrtomb_l(__s, __wc, __ps, __l);
    295 #else
    296   __locale_raii __current(uselocale(__l), uselocale);
    297   return wcrtomb(__s, __wc, __ps);
    298 #endif
    299 }
    300 
    301 inline _LIBCPP_ALWAYS_INLINE
    302 size_t __mbsnrtowcs_l(wchar_t * __dest, const char **__src, size_t __nms,
    303                       size_t __len, mbstate_t *__ps, locale_t __l)
    304 {
    305 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    306   return mbsnrtowcs_l(__dest, __src, __nms, __len, __ps, __l);
    307 #else
    308   __locale_raii __current(uselocale(__l), uselocale);
    309   return mbsnrtowcs(__dest, __src, __nms, __len, __ps);
    310 #endif
    311 }
    312 
    313 inline _LIBCPP_ALWAYS_INLINE
    314 size_t __mbrtowc_l(wchar_t *__pwc, const char *__s, size_t __n,
    315                    mbstate_t *__ps, locale_t __l)
    316 {
    317 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    318   return mbrtowc_l(__pwc, __s, __n, __ps, __l);
    319 #else
    320   __locale_raii __current(uselocale(__l), uselocale);
    321   return mbrtowc(__pwc, __s, __n, __ps);
    322 #endif
    323 }
    324 
    325 inline _LIBCPP_ALWAYS_INLINE
    326 int __mbtowc_l(wchar_t *__pwc, const char *__pmb, size_t __max, locale_t __l)
    327 {
    328 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    329   return mbtowc_l(__pwc, __pmb, __max, __l);
    330 #else
    331   __locale_raii __current(uselocale(__l), uselocale);
    332   return mbtowc(__pwc, __pmb, __max);
    333 #endif
    334 }
    335 
    336 inline _LIBCPP_ALWAYS_INLINE
    337 size_t __mbrlen_l(const char *__s, size_t __n, mbstate_t *__ps, locale_t __l)
    338 {
    339 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    340   return mbrlen_l(__s, __n, __ps, __l);
    341 #else
    342   __locale_raii __current(uselocale(__l), uselocale);
    343   return mbrlen(__s, __n, __ps);
    344 #endif
    345 }
    346 
    347 inline _LIBCPP_ALWAYS_INLINE
    348 lconv *__localeconv_l(locale_t __l)
    349 {
    350 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    351   return localeconv_l(__l);
    352 #else
    353   __locale_raii __current(uselocale(__l), uselocale);
    354   return localeconv();
    355 #endif
    356 }
    357 
    358 inline _LIBCPP_ALWAYS_INLINE
    359 size_t __mbsrtowcs_l(wchar_t *__dest, const char **__src, size_t __len,
    360                      mbstate_t *__ps, locale_t __l)
    361 {
    362 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    363   return mbsrtowcs_l(__dest, __src, __len, __ps, __l);
    364 #else
    365   __locale_raii __current(uselocale(__l), uselocale);
    366   return mbsrtowcs(__dest, __src, __len, __ps);
    367 #endif
    368 }
    369 
    370 inline
    371 int __snprintf_l(char *__s, size_t __n, locale_t __l, const char *__format, ...) {
    372   va_list __va;
    373   va_start(__va, __format);
    374 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    375   int __res = vsnprintf_l(__s, __n, __l, __format, __va);
    376 #else
    377   __locale_raii __current(uselocale(__l), uselocale);
    378   int __res = vsnprintf(__s, __n, __format, __va);
    379 #endif
    380   va_end(__va);
    381   return __res;
    382 }
    383 
    384 inline
    385 int __asprintf_l(char **__s, locale_t __l, const char *__format, ...) {
    386   va_list __va;
    387   va_start(__va, __format);
    388 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    389   int __res = vasprintf_l(__s, __l, __format, __va);
    390 #else
    391   __locale_raii __current(uselocale(__l), uselocale);
    392   int __res = vasprintf(__s, __format, __va);
    393 #endif
    394   va_end(__va);
    395   return __res;
    396 }
    397 
    398 inline
    399 int __sscanf_l(const char *__s, locale_t __l, const char *__format, ...) {
    400   va_list __va;
    401   va_start(__va, __format);
    402 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
    403   int __res = vsscanf_l(__s, __l, __format, __va);
    404 #else
    405   __locale_raii __current(uselocale(__l), uselocale);
    406   int __res = vsscanf(__s, __format, __va);
    407 #endif
    408   va_end(__va);
    409   return __res;
    410 }
    411 
    412 #endif  // __linux__
    413 
    414 // __scan_keyword
    415 // Scans [__b, __e) until a match is found in the basic_strings range
    416 //  [__kb, __ke) or until it can be shown that there is no match in [__kb, __ke).
    417 //  __b will be incremented (visibly), consuming CharT until a match is found
    418 //  or proved to not exist.  A keyword may be "", in which will match anything.
    419 //  If one keyword is a prefix of another, and the next CharT in the input
    420 //  might match another keyword, the algorithm will attempt to find the longest
    421 //  matching keyword.  If the longer matching keyword ends up not matching, then
    422 //  no keyword match is found.  If no keyword match is found, __ke is returned
    423 //  and failbit is set in __err.
    424 //  Else an iterator pointing to the matching keyword is found.  If more than
    425 //  one keyword matches, an iterator to the first matching keyword is returned.
    426 //  If on exit __b == __e, eofbit is set in __err.  If __case_sensitive is false,
    427 //  __ct is used to force to lower case before comparing characters.
    428 //  Examples:
    429 //  Keywords:  "a", "abb"
    430 //  If the input is "a", the first keyword matches and eofbit is set.
    431 //  If the input is "abc", no match is found and "ab" are consumed.
    432 template <class _InputIterator, class _ForwardIterator, class _Ctype>
    433 _LIBCPP_HIDDEN
    434 _ForwardIterator
    435 __scan_keyword(_InputIterator& __b, _InputIterator __e,
    436                _ForwardIterator __kb, _ForwardIterator __ke,
    437                const _Ctype& __ct, ios_base::iostate& __err,
    438                bool __case_sensitive = true)
    439 {
    440     typedef typename iterator_traits<_InputIterator>::value_type _CharT;
    441     size_t __nkw = static_cast<size_t>(_VSTD::distance(__kb, __ke));
    442     const unsigned char __doesnt_match = '\0';
    443     const unsigned char __might_match = '\1';
    444     const unsigned char __does_match = '\2';
    445     unsigned char __statbuf[100];
    446     unsigned char* __status = __statbuf;
    447     unique_ptr<unsigned char, void(*)(void*)> __stat_hold(0, free);
    448     if (__nkw > sizeof(__statbuf))
    449     {
    450         __status = (unsigned char*)malloc(__nkw);
    451         if (__status == 0)
    452             __throw_bad_alloc();
    453         __stat_hold.reset(__status);
    454     }
    455     size_t __n_might_match = __nkw;  // At this point, any keyword might match
    456     size_t __n_does_match = 0;       // but none of them definitely do
    457     // Initialize all statuses to __might_match, except for "" keywords are __does_match
    458     unsigned char* __st = __status;
    459     for (_ForwardIterator __ky = __kb; __ky != __ke; ++__ky, (void) ++__st)
    460     {
    461         if (!__ky->empty())
    462             *__st = __might_match;
    463         else
    464         {
    465             *__st = __does_match;
    466             --__n_might_match;
    467             ++__n_does_match;
    468         }
    469     }
    470     // While there might be a match, test keywords against the next CharT
    471     for (size_t __indx = 0; __b != __e && __n_might_match > 0; ++__indx)
    472     {
    473         // Peek at the next CharT but don't consume it
    474         _CharT __c = *__b;
    475         if (!__case_sensitive)
    476             __c = __ct.toupper(__c);
    477         bool __consume = false;
    478         // For each keyword which might match, see if the __indx character is __c
    479         // If a match if found, consume __c
    480         // If a match is found, and that is the last character in the keyword,
    481         //    then that keyword matches.
    482         // If the keyword doesn't match this character, then change the keyword
    483         //    to doesn't match
    484         __st = __status;
    485         for (_ForwardIterator __ky = __kb; __ky != __ke; ++__ky, (void) ++__st)
    486         {
    487             if (*__st == __might_match)
    488             {
    489                 _CharT __kc = (*__ky)[__indx];
    490                 if (!__case_sensitive)
    491                     __kc = __ct.toupper(__kc);
    492                 if (__c == __kc)
    493                 {
    494                     __consume = true;
    495                     if (__ky->size() == __indx+1)
    496                     {
    497                         *__st = __does_match;
    498                         --__n_might_match;
    499                         ++__n_does_match;
    500                     }
    501                 }
    502                 else
    503                 {
    504                     *__st = __doesnt_match;
    505                     --__n_might_match;
    506                 }
    507             }
    508         }
    509         // consume if we matched a character
    510         if (__consume)
    511         {
    512             ++__b;
    513             // If we consumed a character and there might be a matched keyword that
    514             //   was marked matched on a previous iteration, then such keywords
    515             //   which are now marked as not matching.
    516             if (__n_might_match + __n_does_match > 1)
    517             {
    518                 __st = __status;
    519                 for (_ForwardIterator __ky = __kb; __ky != __ke; ++__ky, (void) ++__st)
    520                 {
    521                     if (*__st == __does_match && __ky->size() != __indx+1)
    522                     {
    523                         *__st = __doesnt_match;
    524                         --__n_does_match;
    525                     }
    526                 }
    527             }
    528         }
    529     }
    530     // We've exited the loop because we hit eof and/or we have no more "might matches".
    531     if (__b == __e)
    532         __err |= ios_base::eofbit;
    533     // Return the first matching result
    534     for (__st = __status; __kb != __ke; ++__kb, (void) ++__st)
    535         if (*__st == __does_match)
    536             break;
    537     if (__kb == __ke)
    538         __err |= ios_base::failbit;
    539     return __kb;
    540 }
    541 
    542 struct _LIBCPP_TYPE_VIS __num_get_base
    543 {
    544     static const int __num_get_buf_sz = 40;
    545 
    546     static int __get_base(ios_base&);
    547     static const char __src[33];
    548 };
    549 
    550 _LIBCPP_FUNC_VIS
    551 void __check_grouping(const string& __grouping, unsigned* __g, unsigned* __g_end,
    552                       ios_base::iostate& __err);
    553 
    554 template <class _CharT>
    555 struct __num_get
    556     : protected __num_get_base
    557 {
    558     static string __stage2_int_prep(ios_base& __iob, _CharT* __atoms, _CharT& __thousands_sep);
    559     static string __stage2_float_prep(ios_base& __iob, _CharT* __atoms, _CharT& __decimal_point,
    560                                       _CharT& __thousands_sep);
    561     static int __stage2_int_loop(_CharT __ct, int __base, char* __a, char*& __a_end,
    562                   unsigned& __dc, _CharT __thousands_sep, const string& __grouping,
    563                   unsigned* __g, unsigned*& __g_end, _CharT* __atoms);
    564     static int __stage2_float_loop(_CharT __ct, bool& __in_units, char& __exp,
    565                                    char* __a, char*& __a_end,
    566                                    _CharT __decimal_point, _CharT __thousands_sep,
    567                                    const string& __grouping, unsigned* __g,
    568                                    unsigned*& __g_end, unsigned& __dc, _CharT* __atoms);
    569 };
    570 
    571 template <class _CharT>
    572 string
    573 __num_get<_CharT>::__stage2_int_prep(ios_base& __iob, _CharT* __atoms, _CharT& __thousands_sep)
    574 {
    575     locale __loc = __iob.getloc();
    576     use_facet<ctype<_CharT> >(__loc).widen(__src, __src + 26, __atoms);
    577     const numpunct<_CharT>& __np = use_facet<numpunct<_CharT> >(__loc);
    578     __thousands_sep = __np.thousands_sep();
    579     return __np.grouping();
    580 }
    581 
    582 template <class _CharT>
    583 string
    584 __num_get<_CharT>::__stage2_float_prep(ios_base& __iob, _CharT* __atoms, _CharT& __decimal_point,
    585                     _CharT& __thousands_sep)
    586 {
    587     locale __loc = __iob.getloc();
    588     use_facet<ctype<_CharT> >(__loc).widen(__src, __src + 32, __atoms);
    589     const numpunct<_CharT>& __np = use_facet<numpunct<_CharT> >(__loc);
    590     __decimal_point = __np.decimal_point();
    591     __thousands_sep = __np.thousands_sep();
    592     return __np.grouping();
    593 }
    594 
    595 template <class _CharT>
    596 int
    597 __num_get<_CharT>::__stage2_int_loop(_CharT __ct, int __base, char* __a, char*& __a_end,
    598                   unsigned& __dc, _CharT __thousands_sep, const string& __grouping,
    599                   unsigned* __g, unsigned*& __g_end, _CharT* __atoms)
    600 {
    601     if (__a_end == __a && (__ct == __atoms[24] || __ct == __atoms[25]))
    602     {
    603         *__a_end++ = __ct == __atoms[24] ? '+' : '-';
    604         __dc = 0;
    605         return 0;
    606     }
    607     if (__grouping.size() != 0 && __ct == __thousands_sep)
    608     {
    609         if (__g_end-__g < __num_get_buf_sz)
    610         {
    611             *__g_end++ = __dc;
    612             __dc = 0;
    613         }
    614         return 0;
    615     }
    616     ptrdiff_t __f = find(__atoms, __atoms + 26, __ct) - __atoms;
    617     if (__f >= 24)
    618         return -1;
    619     switch (__base)
    620     {
    621     case 8:
    622     case 10:
    623         if (__f >= __base)
    624             return -1;
    625         break;
    626     case 16:
    627         if (__f < 22)
    628             break;
    629         if (__a_end != __a && __a_end - __a <= 2 && __a_end[-1] == '0')
    630         {
    631             __dc = 0;
    632             *__a_end++ = __src[__f];
    633             return 0;
    634         }
    635         return -1;
    636     }
    637     *__a_end++ = __src[__f];
    638     ++__dc;
    639     return 0;
    640 }
    641 
    642 template <class _CharT>
    643 int
    644 __num_get<_CharT>::__stage2_float_loop(_CharT __ct, bool& __in_units, char& __exp, char* __a, char*& __a_end,
    645                     _CharT __decimal_point, _CharT __thousands_sep, const string& __grouping,
    646                     unsigned* __g, unsigned*& __g_end, unsigned& __dc, _CharT* __atoms)
    647 {
    648     if (__ct == __decimal_point)
    649     {
    650         if (!__in_units)
    651             return -1;
    652         __in_units = false;
    653         *__a_end++ = '.';
    654         if (__grouping.size() != 0 && __g_end-__g < __num_get_buf_sz)
    655             *__g_end++ = __dc;
    656         return 0;
    657     }
    658     if (__ct == __thousands_sep && __grouping.size() != 0)
    659     {
    660         if (!__in_units)
    661             return -1;
    662         if (__g_end-__g < __num_get_buf_sz)
    663         {
    664             *__g_end++ = __dc;
    665             __dc = 0;
    666         }
    667         return 0;
    668     }
    669     ptrdiff_t __f = find(__atoms, __atoms + 32, __ct) - __atoms;
    670     if (__f >= 32)
    671         return -1;
    672     char __x = __src[__f];
    673     if (__x == '-' || __x == '+')
    674     {
    675         if (__a_end == __a || (__a_end[-1] & 0x5F) == (__exp & 0x7F))
    676         {
    677             *__a_end++ = __x;
    678             return 0;
    679         }
    680         return -1;
    681     }
    682     if (__x == 'x' || __x == 'X')
    683         __exp = 'P';
    684     else if ((__x & 0x5F) == __exp)
    685     {
    686         __exp |= 0x80;
    687         if (__in_units)
    688         {
    689             __in_units = false;
    690             if (__grouping.size() != 0 && __g_end-__g < __num_get_buf_sz)
    691                 *__g_end++ = __dc;
    692         }
    693     }
    694     *__a_end++ = __x;
    695     if (__f >= 22)
    696         return 0;
    697     ++__dc;
    698     return 0;
    699 }
    700 
    701 _LIBCPP_EXTERN_TEMPLATE2(struct _LIBCPP_TYPE_VIS __num_get<char>)
    702 _LIBCPP_EXTERN_TEMPLATE2(struct _LIBCPP_TYPE_VIS __num_get<wchar_t>)
    703 
    704 template <class _CharT, class _InputIterator = istreambuf_iterator<_CharT> >
    705 class _LIBCPP_TYPE_VIS_ONLY num_get
    706     : public locale::facet,
    707       private __num_get<_CharT>
    708 {
    709 public:
    710     typedef _CharT char_type;
    711     typedef _InputIterator iter_type;
    712 
    713     _LIBCPP_ALWAYS_INLINE
    714     explicit num_get(size_t __refs = 0)
    715         : locale::facet(__refs) {}
    716 
    717     _LIBCPP_ALWAYS_INLINE
    718     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    719                   ios_base::iostate& __err, bool& __v) const
    720     {
    721         return do_get(__b, __e, __iob, __err, __v);
    722     }
    723 
    724     _LIBCPP_ALWAYS_INLINE
    725     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    726                   ios_base::iostate& __err, long& __v) const
    727     {
    728         return do_get(__b, __e, __iob, __err, __v);
    729     }
    730 
    731     _LIBCPP_ALWAYS_INLINE
    732     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    733                   ios_base::iostate& __err, long long& __v) const
    734     {
    735         return do_get(__b, __e, __iob, __err, __v);
    736     }
    737 
    738     _LIBCPP_ALWAYS_INLINE
    739     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    740                   ios_base::iostate& __err, unsigned short& __v) const
    741     {
    742         return do_get(__b, __e, __iob, __err, __v);
    743     }
    744 
    745     _LIBCPP_ALWAYS_INLINE
    746     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    747                   ios_base::iostate& __err, unsigned int& __v) const
    748     {
    749         return do_get(__b, __e, __iob, __err, __v);
    750     }
    751 
    752     _LIBCPP_ALWAYS_INLINE
    753     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    754                   ios_base::iostate& __err, unsigned long& __v) const
    755     {
    756         return do_get(__b, __e, __iob, __err, __v);
    757     }
    758 
    759     _LIBCPP_ALWAYS_INLINE
    760     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    761                   ios_base::iostate& __err, unsigned long long& __v) const
    762     {
    763         return do_get(__b, __e, __iob, __err, __v);
    764     }
    765 
    766     _LIBCPP_ALWAYS_INLINE
    767     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    768                   ios_base::iostate& __err, float& __v) const
    769     {
    770         return do_get(__b, __e, __iob, __err, __v);
    771     }
    772 
    773     _LIBCPP_ALWAYS_INLINE
    774     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    775                   ios_base::iostate& __err, double& __v) const
    776     {
    777         return do_get(__b, __e, __iob, __err, __v);
    778     }
    779 
    780     _LIBCPP_ALWAYS_INLINE
    781     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    782                   ios_base::iostate& __err, long double& __v) const
    783     {
    784         return do_get(__b, __e, __iob, __err, __v);
    785     }
    786 
    787     _LIBCPP_ALWAYS_INLINE
    788     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
    789                   ios_base::iostate& __err, void*& __v) const
    790     {
    791         return do_get(__b, __e, __iob, __err, __v);
    792     }
    793 
    794     static locale::id id;
    795 
    796 protected:
    797     _LIBCPP_ALWAYS_INLINE
    798     ~num_get() {}
    799 
    800     template <class _Fp>
    801     iter_type __do_get_floating_point
    802                             (iter_type __b, iter_type __e, ios_base& __iob,
    803                              ios_base::iostate& __err, _Fp& __v) const;
    804 
    805     template <class _Signed>
    806     iter_type __do_get_signed
    807                             (iter_type __b, iter_type __e, ios_base& __iob,
    808                              ios_base::iostate& __err, _Signed& __v) const;
    809 
    810     template <class _Unsigned>
    811     iter_type __do_get_unsigned
    812                             (iter_type __b, iter_type __e, ios_base& __iob,
    813                              ios_base::iostate& __err, _Unsigned& __v) const;
    814 
    815 
    816     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    817                              ios_base::iostate& __err, bool& __v) const;
    818 
    819     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    820                              ios_base::iostate& __err, long& __v) const
    821     { return this->__do_get_signed ( __b, __e, __iob, __err, __v ); }
    822 
    823     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    824                              ios_base::iostate& __err, long long& __v) const
    825     { return this->__do_get_signed ( __b, __e, __iob, __err, __v ); }
    826 
    827     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    828                              ios_base::iostate& __err, unsigned short& __v) const
    829     { return this->__do_get_unsigned ( __b, __e, __iob, __err, __v ); }
    830 
    831     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    832                              ios_base::iostate& __err, unsigned int& __v) const
    833     { return this->__do_get_unsigned ( __b, __e, __iob, __err, __v ); }
    834 
    835     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    836                              ios_base::iostate& __err, unsigned long& __v) const
    837     { return this->__do_get_unsigned ( __b, __e, __iob, __err, __v ); }
    838 
    839     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    840                              ios_base::iostate& __err, unsigned long long& __v) const
    841     { return this->__do_get_unsigned ( __b, __e, __iob, __err, __v ); }
    842 
    843     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    844                              ios_base::iostate& __err, float& __v) const
    845     { return this->__do_get_floating_point ( __b, __e, __iob, __err, __v ); }
    846 
    847     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    848                              ios_base::iostate& __err, double& __v) const
    849     { return this->__do_get_floating_point ( __b, __e, __iob, __err, __v ); }
    850 
    851     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    852                              ios_base::iostate& __err, long double& __v) const
    853     { return this->__do_get_floating_point ( __b, __e, __iob, __err, __v ); }
    854 
    855     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
    856                              ios_base::iostate& __err, void*& __v) const;
    857 };
    858 
    859 template <class _CharT, class _InputIterator>
    860 locale::id
    861 num_get<_CharT, _InputIterator>::id;
    862 
    863 template <class _Tp>
    864 _Tp
    865 __num_get_signed_integral(const char* __a, const char* __a_end,
    866                           ios_base::iostate& __err, int __base)
    867 {
    868     if (__a != __a_end)
    869     {
    870         typename remove_reference<decltype(errno)>::type __save_errno = errno;
    871         errno = 0;
    872         char *__p2;
    873         long long __ll = strtoll_l(__a, &__p2, __base, _LIBCPP_GET_C_LOCALE);
    874         typename remove_reference<decltype(errno)>::type __current_errno = errno;
    875         if (__current_errno == 0)
    876             errno = __save_errno;
    877         if (__p2 != __a_end)
    878         {
    879             __err = ios_base::failbit;
    880             return 0;
    881         }
    882         else if (__current_errno == ERANGE         ||
    883                  __ll < numeric_limits<_Tp>::min() ||
    884                  numeric_limits<_Tp>::max() < __ll)
    885         {
    886             __err = ios_base::failbit;
    887             if (__ll > 0)
    888                 return numeric_limits<_Tp>::max();
    889             else
    890                 return numeric_limits<_Tp>::min();
    891         }
    892         return static_cast<_Tp>(__ll);
    893     }
    894     __err = ios_base::failbit;
    895     return 0;
    896 }
    897 
    898 template <class _Tp>
    899 _Tp
    900 __num_get_unsigned_integral(const char* __a, const char* __a_end,
    901                             ios_base::iostate& __err, int __base)
    902 {
    903     if (__a != __a_end)
    904     {
    905         if (*__a == '-')
    906         {
    907             __err = ios_base::failbit;
    908             return 0;
    909         }
    910         typename remove_reference<decltype(errno)>::type __save_errno = errno;
    911         errno = 0;
    912         char *__p2;
    913         unsigned long long __ll = strtoull_l(__a, &__p2, __base, _LIBCPP_GET_C_LOCALE);
    914         typename remove_reference<decltype(errno)>::type __current_errno = errno;
    915         if (__current_errno == 0)
    916             errno = __save_errno;
    917         if (__p2 != __a_end)
    918         {
    919             __err = ios_base::failbit;
    920             return 0;
    921         }
    922         else if (__current_errno == ERANGE ||
    923                  numeric_limits<_Tp>::max() < __ll)
    924         {
    925             __err = ios_base::failbit;
    926             return numeric_limits<_Tp>::max();
    927         }
    928         return static_cast<_Tp>(__ll);
    929     }
    930     __err = ios_base::failbit;
    931     return 0;
    932 }
    933 
    934 template <class _Tp>
    935 _Tp
    936 __num_get_float(const char* __a, const char* __a_end, ios_base::iostate& __err)
    937 {
    938     if (__a != __a_end)
    939     {
    940         typename remove_reference<decltype(errno)>::type __save_errno = errno;
    941         errno = 0;
    942         char *__p2;
    943         long double __ld = strtold_l(__a, &__p2, _LIBCPP_GET_C_LOCALE);
    944         typename remove_reference<decltype(errno)>::type __current_errno = errno;
    945         if (__current_errno == 0)
    946             errno = __save_errno;
    947         if (__p2 != __a_end)
    948         {
    949             __err = ios_base::failbit;
    950             return 0;
    951         }
    952         else if (__current_errno == ERANGE)
    953             __err = ios_base::failbit;
    954         return static_cast<_Tp>(__ld);
    955     }
    956     __err = ios_base::failbit;
    957     return 0;
    958 }
    959 
    960 template <class _CharT, class _InputIterator>
    961 _InputIterator
    962 num_get<_CharT, _InputIterator>::do_get(iter_type __b, iter_type __e,
    963                                         ios_base& __iob,
    964                                         ios_base::iostate& __err,
    965                                         bool& __v) const
    966 {
    967     if ((__iob.flags() & ios_base::boolalpha) == 0)
    968     {
    969         long __lv = -1;
    970         __b = do_get(__b, __e, __iob, __err, __lv);
    971         switch (__lv)
    972         {
    973         case 0:
    974             __v = false;
    975             break;
    976         case 1:
    977             __v = true;
    978             break;
    979         default:
    980             __v = true;
    981             __err = ios_base::failbit;
    982             break;
    983         }
    984         return __b;
    985     }
    986     const ctype<_CharT>& __ct = use_facet<ctype<_CharT> >(__iob.getloc());
    987     const numpunct<_CharT>& __np = use_facet<numpunct<_CharT> >(__iob.getloc());
    988     typedef typename numpunct<_CharT>::string_type string_type;
    989     const string_type __names[2] = {__np.truename(), __np.falsename()};
    990     const string_type* __i = __scan_keyword(__b, __e, __names, __names+2,
    991                                             __ct, __err);
    992     __v = __i == __names;
    993     return __b;
    994 }
    995 
    996 // signed
    997 
    998 template <class _CharT, class _InputIterator>
    999 template <class _Signed>
   1000 _InputIterator
   1001 num_get<_CharT, _InputIterator>::__do_get_signed(iter_type __b, iter_type __e,
   1002                                         ios_base& __iob,
   1003                                         ios_base::iostate& __err,
   1004                                         _Signed& __v) const
   1005 {
   1006     // Stage 1
   1007     int __base = this->__get_base(__iob);
   1008     // Stage 2
   1009     char_type __atoms[26];
   1010     char_type __thousands_sep;
   1011     string __grouping = this->__stage2_int_prep(__iob, __atoms, __thousands_sep);
   1012     string __buf;
   1013     __buf.resize(__buf.capacity());
   1014     char* __a = &__buf[0];
   1015     char* __a_end = __a;
   1016     unsigned __g[__num_get_base::__num_get_buf_sz];
   1017     unsigned* __g_end = __g;
   1018     unsigned __dc = 0;
   1019     for (; __b != __e; ++__b)
   1020     {
   1021         if (__a_end == __a + __buf.size())
   1022         {
   1023             size_t __tmp = __buf.size();
   1024             __buf.resize(2*__buf.size());
   1025             __buf.resize(__buf.capacity());
   1026             __a = &__buf[0];
   1027             __a_end = __a + __tmp;
   1028         }
   1029         if (this->__stage2_int_loop(*__b, __base, __a, __a_end, __dc,
   1030                                     __thousands_sep, __grouping, __g, __g_end,
   1031                                     __atoms))
   1032             break;
   1033     }
   1034     if (__grouping.size() != 0 && __g_end-__g < __num_get_base::__num_get_buf_sz)
   1035         *__g_end++ = __dc;
   1036     // Stage 3
   1037     __v = __num_get_signed_integral<_Signed>(__a, __a_end, __err, __base);
   1038     // Digit grouping checked
   1039     __check_grouping(__grouping, __g, __g_end, __err);
   1040     // EOF checked
   1041     if (__b == __e)
   1042         __err |= ios_base::eofbit;
   1043     return __b;
   1044 }
   1045 
   1046 // unsigned
   1047 
   1048 template <class _CharT, class _InputIterator>
   1049 template <class _Unsigned>
   1050 _InputIterator
   1051 num_get<_CharT, _InputIterator>::__do_get_unsigned(iter_type __b, iter_type __e,
   1052                                         ios_base& __iob,
   1053                                         ios_base::iostate& __err,
   1054                                         _Unsigned& __v) const
   1055 {
   1056     // Stage 1
   1057     int __base = this->__get_base(__iob);
   1058     // Stage 2
   1059     char_type __atoms[26];
   1060     char_type __thousands_sep;
   1061     string __grouping = this->__stage2_int_prep(__iob, __atoms, __thousands_sep);
   1062     string __buf;
   1063     __buf.resize(__buf.capacity());
   1064     char* __a = &__buf[0];
   1065     char* __a_end = __a;
   1066     unsigned __g[__num_get_base::__num_get_buf_sz];
   1067     unsigned* __g_end = __g;
   1068     unsigned __dc = 0;
   1069     for (; __b != __e; ++__b)
   1070     {
   1071         if (__a_end == __a + __buf.size())
   1072         {
   1073             size_t __tmp = __buf.size();
   1074             __buf.resize(2*__buf.size());
   1075             __buf.resize(__buf.capacity());
   1076             __a = &__buf[0];
   1077             __a_end = __a + __tmp;
   1078         }
   1079         if (this->__stage2_int_loop(*__b, __base, __a, __a_end, __dc,
   1080                                     __thousands_sep, __grouping, __g, __g_end,
   1081                                     __atoms))
   1082             break;
   1083     }
   1084     if (__grouping.size() != 0 && __g_end-__g < __num_get_base::__num_get_buf_sz)
   1085         *__g_end++ = __dc;
   1086     // Stage 3
   1087     __v = __num_get_unsigned_integral<_Unsigned>(__a, __a_end, __err, __base);
   1088     // Digit grouping checked
   1089     __check_grouping(__grouping, __g, __g_end, __err);
   1090     // EOF checked
   1091     if (__b == __e)
   1092         __err |= ios_base::eofbit;
   1093     return __b;
   1094 }
   1095 
   1096 // floating point
   1097 
   1098 template <class _CharT, class _InputIterator>
   1099 template <class _Fp>
   1100 _InputIterator
   1101 num_get<_CharT, _InputIterator>::__do_get_floating_point(iter_type __b, iter_type __e,
   1102                                         ios_base& __iob,
   1103                                         ios_base::iostate& __err,
   1104                                         _Fp& __v) const
   1105 {
   1106     // Stage 1, nothing to do
   1107     // Stage 2
   1108     char_type __atoms[32];
   1109     char_type __decimal_point;
   1110     char_type __thousands_sep;
   1111     string __grouping = this->__stage2_float_prep(__iob, __atoms,
   1112                                                   __decimal_point,
   1113                                                   __thousands_sep);
   1114     string __buf;
   1115     __buf.resize(__buf.capacity());
   1116     char* __a = &__buf[0];
   1117     char* __a_end = __a;
   1118     unsigned __g[__num_get_base::__num_get_buf_sz];
   1119     unsigned* __g_end = __g;
   1120     unsigned __dc = 0;
   1121     bool __in_units = true;
   1122     char __exp = 'E';
   1123     for (; __b != __e; ++__b)
   1124     {
   1125         if (__a_end == __a + __buf.size())
   1126         {
   1127             size_t __tmp = __buf.size();
   1128             __buf.resize(2*__buf.size());
   1129             __buf.resize(__buf.capacity());
   1130             __a = &__buf[0];
   1131             __a_end = __a + __tmp;
   1132         }
   1133         if (this->__stage2_float_loop(*__b, __in_units, __exp, __a, __a_end,
   1134                                       __decimal_point, __thousands_sep,
   1135                                       __grouping, __g, __g_end,
   1136                                       __dc, __atoms))
   1137             break;
   1138     }
   1139     if (__grouping.size() != 0 && __in_units && __g_end-__g < __num_get_base::__num_get_buf_sz)
   1140         *__g_end++ = __dc;
   1141     // Stage 3
   1142     __v = __num_get_float<_Fp>(__a, __a_end, __err);
   1143     // Digit grouping checked
   1144     __check_grouping(__grouping, __g, __g_end, __err);
   1145     // EOF checked
   1146     if (__b == __e)
   1147         __err |= ios_base::eofbit;
   1148     return __b;
   1149 }
   1150 
   1151 template <class _CharT, class _InputIterator>
   1152 _InputIterator
   1153 num_get<_CharT, _InputIterator>::do_get(iter_type __b, iter_type __e,
   1154                                         ios_base& __iob,
   1155                                         ios_base::iostate& __err,
   1156                                         void*& __v) const
   1157 {
   1158     // Stage 1
   1159     int __base = 16;
   1160     // Stage 2
   1161     char_type __atoms[26];
   1162     char_type __thousands_sep = 0;
   1163     string __grouping;
   1164     use_facet<ctype<_CharT> >(__iob.getloc()).widen(__num_get_base::__src,
   1165                                                     __num_get_base::__src + 26, __atoms);
   1166     string __buf;
   1167     __buf.resize(__buf.capacity());
   1168     char* __a = &__buf[0];
   1169     char* __a_end = __a;
   1170     unsigned __g[__num_get_base::__num_get_buf_sz];
   1171     unsigned* __g_end = __g;
   1172     unsigned __dc = 0;
   1173     for (; __b != __e; ++__b)
   1174     {
   1175         if (__a_end == __a + __buf.size())
   1176         {
   1177             size_t __tmp = __buf.size();
   1178             __buf.resize(2*__buf.size());
   1179             __buf.resize(__buf.capacity());
   1180             __a = &__buf[0];
   1181             __a_end = __a + __tmp;
   1182         }
   1183         if (this->__stage2_int_loop(*__b, __base, __a, __a_end, __dc,
   1184                                     __thousands_sep, __grouping,
   1185                                     __g, __g_end, __atoms))
   1186             break;
   1187     }
   1188     // Stage 3
   1189     __buf.resize(__a_end - __a);
   1190 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1191     if (sscanf_l(__buf.c_str(), _LIBCPP_GET_C_LOCALE, "%p", &__v) != 1)
   1192 #else
   1193     if (__sscanf_l(__buf.c_str(), __cloc(), "%p", &__v) != 1)
   1194 #endif
   1195         __err = ios_base::failbit;
   1196     // EOF checked
   1197     if (__b == __e)
   1198         __err |= ios_base::eofbit;
   1199     return __b;
   1200 }
   1201 
   1202 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS num_get<char>)
   1203 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS num_get<wchar_t>)
   1204 
   1205 struct _LIBCPP_TYPE_VIS __num_put_base
   1206 {
   1207 protected:
   1208     static void __format_int(char* __fmt, const char* __len, bool __signd,
   1209                              ios_base::fmtflags __flags);
   1210     static bool __format_float(char* __fmt, const char* __len,
   1211                                ios_base::fmtflags __flags);
   1212     static char* __identify_padding(char* __nb, char* __ne,
   1213                                     const ios_base& __iob);
   1214 };
   1215 
   1216 template <class _CharT>
   1217 struct __num_put
   1218     : protected __num_put_base
   1219 {
   1220     static void __widen_and_group_int(char* __nb, char* __np, char* __ne,
   1221                                       _CharT* __ob, _CharT*& __op, _CharT*& __oe,
   1222                                       const locale& __loc);
   1223     static void __widen_and_group_float(char* __nb, char* __np, char* __ne,
   1224                                         _CharT* __ob, _CharT*& __op, _CharT*& __oe,
   1225                                         const locale& __loc);
   1226 };
   1227 
   1228 template <class _CharT>
   1229 void
   1230 __num_put<_CharT>::__widen_and_group_int(char* __nb, char* __np, char* __ne,
   1231                                          _CharT* __ob, _CharT*& __op, _CharT*& __oe,
   1232                                          const locale& __loc)
   1233 {
   1234     const ctype<_CharT>&    __ct = use_facet<ctype<_CharT> >   (__loc);
   1235     const numpunct<_CharT>& __npt = use_facet<numpunct<_CharT> >(__loc);
   1236     string __grouping = __npt.grouping();
   1237     if (__grouping.empty())
   1238     {
   1239         __ct.widen(__nb, __ne, __ob);
   1240         __oe = __ob + (__ne - __nb);
   1241     }
   1242     else
   1243     {
   1244         __oe = __ob;
   1245         char* __nf = __nb;
   1246         if (*__nf == '-' || *__nf == '+')
   1247             *__oe++ = __ct.widen(*__nf++);
   1248         if (__ne - __nf >= 2 && __nf[0] == '0' && (__nf[1] == 'x' ||
   1249                                                    __nf[1] == 'X'))
   1250         {
   1251             *__oe++ = __ct.widen(*__nf++);
   1252             *__oe++ = __ct.widen(*__nf++);
   1253         }
   1254         reverse(__nf, __ne);
   1255         _CharT __thousands_sep = __npt.thousands_sep();
   1256         unsigned __dc = 0;
   1257         unsigned __dg = 0;
   1258         for (char* __p = __nf; __p < __ne; ++__p)
   1259         {
   1260             if (static_cast<unsigned>(__grouping[__dg]) > 0 &&
   1261                 __dc == static_cast<unsigned>(__grouping[__dg]))
   1262             {
   1263                 *__oe++ = __thousands_sep;
   1264                 __dc = 0;
   1265                 if (__dg < __grouping.size()-1)
   1266                     ++__dg;
   1267             }
   1268             *__oe++ = __ct.widen(*__p);
   1269             ++__dc;
   1270         }
   1271         reverse(__ob + (__nf - __nb), __oe);
   1272     }
   1273     if (__np == __ne)
   1274         __op = __oe;
   1275     else
   1276         __op = __ob + (__np - __nb);
   1277 }
   1278 
   1279 template <class _CharT>
   1280 void
   1281 __num_put<_CharT>::__widen_and_group_float(char* __nb, char* __np, char* __ne,
   1282                                            _CharT* __ob, _CharT*& __op, _CharT*& __oe,
   1283                                            const locale& __loc)
   1284 {
   1285     const ctype<_CharT>&    __ct = use_facet<ctype<_CharT> >   (__loc);
   1286     const numpunct<_CharT>& __npt = use_facet<numpunct<_CharT> >(__loc);
   1287     string __grouping = __npt.grouping();
   1288     __oe = __ob;
   1289     char* __nf = __nb;
   1290     if (*__nf == '-' || *__nf == '+')
   1291         *__oe++ = __ct.widen(*__nf++);
   1292     char* __ns;
   1293     if (__ne - __nf >= 2 && __nf[0] == '0' && (__nf[1] == 'x' ||
   1294                                                __nf[1] == 'X'))
   1295     {
   1296         *__oe++ = __ct.widen(*__nf++);
   1297         *__oe++ = __ct.widen(*__nf++);
   1298         for (__ns = __nf; __ns < __ne; ++__ns)
   1299             if (!isxdigit_l(*__ns, _LIBCPP_GET_C_LOCALE))
   1300                 break;
   1301     }
   1302     else
   1303     {
   1304         for (__ns = __nf; __ns < __ne; ++__ns)
   1305             if (!isdigit_l(*__ns, _LIBCPP_GET_C_LOCALE))
   1306                 break;
   1307     }
   1308     if (__grouping.empty())
   1309     {
   1310         __ct.widen(__nf, __ns, __oe);
   1311         __oe += __ns - __nf;
   1312     }
   1313     else
   1314     {
   1315         reverse(__nf, __ns);
   1316         _CharT __thousands_sep = __npt.thousands_sep();
   1317         unsigned __dc = 0;
   1318         unsigned __dg = 0;
   1319         for (char* __p = __nf; __p < __ns; ++__p)
   1320         {
   1321             if (__grouping[__dg] > 0 && __dc == static_cast<unsigned>(__grouping[__dg]))
   1322             {
   1323                 *__oe++ = __thousands_sep;
   1324                 __dc = 0;
   1325                 if (__dg < __grouping.size()-1)
   1326                     ++__dg;
   1327             }
   1328             *__oe++ = __ct.widen(*__p);
   1329             ++__dc;
   1330         }
   1331         reverse(__ob + (__nf - __nb), __oe);
   1332     }
   1333     for (__nf = __ns; __nf < __ne; ++__nf)
   1334     {
   1335         if (*__nf == '.')
   1336         {
   1337             *__oe++ = __npt.decimal_point();
   1338             ++__nf;
   1339             break;
   1340         }
   1341         else
   1342             *__oe++ = __ct.widen(*__nf);
   1343     }
   1344     __ct.widen(__nf, __ne, __oe);
   1345     __oe += __ne - __nf;
   1346     if (__np == __ne)
   1347         __op = __oe;
   1348     else
   1349         __op = __ob + (__np - __nb);
   1350 }
   1351 
   1352 _LIBCPP_EXTERN_TEMPLATE2(struct _LIBCPP_TYPE_VIS __num_put<char>)
   1353 _LIBCPP_EXTERN_TEMPLATE2(struct _LIBCPP_TYPE_VIS __num_put<wchar_t>)
   1354 
   1355 template <class _CharT, class _OutputIterator = ostreambuf_iterator<_CharT> >
   1356 class _LIBCPP_TYPE_VIS_ONLY num_put
   1357     : public locale::facet,
   1358       private __num_put<_CharT>
   1359 {
   1360 public:
   1361     typedef _CharT char_type;
   1362     typedef _OutputIterator iter_type;
   1363 
   1364     _LIBCPP_ALWAYS_INLINE
   1365     explicit num_put(size_t __refs = 0)
   1366         : locale::facet(__refs) {}
   1367 
   1368     _LIBCPP_ALWAYS_INLINE
   1369     iter_type put(iter_type __s, ios_base& __iob, char_type __fl,
   1370                   bool __v) const
   1371     {
   1372         return do_put(__s, __iob, __fl, __v);
   1373     }
   1374 
   1375     _LIBCPP_ALWAYS_INLINE
   1376     iter_type put(iter_type __s, ios_base& __iob, char_type __fl,
   1377                   long __v) const
   1378     {
   1379         return do_put(__s, __iob, __fl, __v);
   1380     }
   1381 
   1382     _LIBCPP_ALWAYS_INLINE
   1383     iter_type put(iter_type __s, ios_base& __iob, char_type __fl,
   1384                   long long __v) const
   1385     {
   1386         return do_put(__s, __iob, __fl, __v);
   1387     }
   1388 
   1389     _LIBCPP_ALWAYS_INLINE
   1390     iter_type put(iter_type __s, ios_base& __iob, char_type __fl,
   1391                   unsigned long __v) const
   1392     {
   1393         return do_put(__s, __iob, __fl, __v);
   1394     }
   1395 
   1396     _LIBCPP_ALWAYS_INLINE
   1397     iter_type put(iter_type __s, ios_base& __iob, char_type __fl,
   1398                   unsigned long long __v) const
   1399     {
   1400         return do_put(__s, __iob, __fl, __v);
   1401     }
   1402 
   1403     _LIBCPP_ALWAYS_INLINE
   1404     iter_type put(iter_type __s, ios_base& __iob, char_type __fl,
   1405                   double __v) const
   1406     {
   1407         return do_put(__s, __iob, __fl, __v);
   1408     }
   1409 
   1410     _LIBCPP_ALWAYS_INLINE
   1411     iter_type put(iter_type __s, ios_base& __iob, char_type __fl,
   1412                   long double __v) const
   1413     {
   1414         return do_put(__s, __iob, __fl, __v);
   1415     }
   1416 
   1417     _LIBCPP_ALWAYS_INLINE
   1418     iter_type put(iter_type __s, ios_base& __iob, char_type __fl,
   1419                   const void* __v) const
   1420     {
   1421         return do_put(__s, __iob, __fl, __v);
   1422     }
   1423 
   1424     static locale::id id;
   1425 
   1426 protected:
   1427     _LIBCPP_ALWAYS_INLINE
   1428     ~num_put() {}
   1429 
   1430     virtual iter_type do_put(iter_type __s, ios_base& __iob, char_type __fl,
   1431                              bool __v) const;
   1432     virtual iter_type do_put(iter_type __s, ios_base& __iob, char_type __fl,
   1433                              long __v) const;
   1434     virtual iter_type do_put(iter_type __s, ios_base& __iob, char_type __fl,
   1435                              long long __v) const;
   1436     virtual iter_type do_put(iter_type __s, ios_base& __iob, char_type __fl,
   1437                              unsigned long) const;
   1438     virtual iter_type do_put(iter_type __s, ios_base& __iob, char_type __fl,
   1439                              unsigned long long) const;
   1440     virtual iter_type do_put(iter_type __s, ios_base& __iob, char_type __fl,
   1441                              double __v) const;
   1442     virtual iter_type do_put(iter_type __s, ios_base& __iob, char_type __fl,
   1443                              long double __v) const;
   1444     virtual iter_type do_put(iter_type __s, ios_base& __iob, char_type __fl,
   1445                              const void* __v) const;
   1446 };
   1447 
   1448 template <class _CharT, class _OutputIterator>
   1449 locale::id
   1450 num_put<_CharT, _OutputIterator>::id;
   1451 
   1452 template <class _CharT, class _OutputIterator>
   1453 _LIBCPP_HIDDEN
   1454 _OutputIterator
   1455 __pad_and_output(_OutputIterator __s,
   1456                  const _CharT* __ob, const _CharT* __op, const _CharT* __oe,
   1457                  ios_base& __iob, _CharT __fl)
   1458 {
   1459     streamsize __sz = __oe - __ob;
   1460     streamsize __ns = __iob.width();
   1461     if (__ns > __sz)
   1462         __ns -= __sz;
   1463     else
   1464         __ns = 0;
   1465     for (;__ob < __op; ++__ob, ++__s)
   1466         *__s = *__ob;
   1467     for (; __ns; --__ns, ++__s)
   1468         *__s = __fl;
   1469     for (; __ob < __oe; ++__ob, ++__s)
   1470         *__s = *__ob;
   1471     __iob.width(0);
   1472     return __s;
   1473 }
   1474 
   1475 #if !defined(__APPLE__) || \
   1476     (defined(__MAC_OS_X_VERSION_MIN_REQUIRED) && __MAC_OS_X_VERSION_MIN_REQUIRED > __MAC_10_8) || \
   1477     (defined(__IPHONE_OS_VERSION_MIN_REQUIRED) && __IPHONE_OS_VERSION_MIN_REQUIRED > __IPHONE_6_0)
   1478 
   1479 template <class _CharT, class _Traits>
   1480 _LIBCPP_HIDDEN
   1481 ostreambuf_iterator<_CharT, _Traits>
   1482 __pad_and_output(ostreambuf_iterator<_CharT, _Traits> __s,
   1483                  const _CharT* __ob, const _CharT* __op, const _CharT* __oe,
   1484                  ios_base& __iob, _CharT __fl)
   1485 {
   1486     if (__s.__sbuf_ == nullptr)
   1487         return __s;
   1488     streamsize __sz = __oe - __ob;
   1489     streamsize __ns = __iob.width();
   1490     if (__ns > __sz)
   1491         __ns -= __sz;
   1492     else
   1493         __ns = 0;
   1494     streamsize __np = __op - __ob;
   1495     if (__np > 0)
   1496     {
   1497         if (__s.__sbuf_->sputn(__ob, __np) != __np)
   1498         {
   1499             __s.__sbuf_ = nullptr;
   1500             return __s;
   1501         }
   1502     }
   1503     if (__ns > 0)
   1504     {
   1505         basic_string<_CharT, _Traits> __sp(__ns, __fl);
   1506         if (__s.__sbuf_->sputn(__sp.data(), __ns) != __ns)
   1507         {
   1508             __s.__sbuf_ = nullptr;
   1509             return __s;
   1510         }
   1511     }
   1512     __np = __oe - __op;
   1513     if (__np > 0)
   1514     {
   1515         if (__s.__sbuf_->sputn(__op, __np) != __np)
   1516         {
   1517             __s.__sbuf_ = nullptr;
   1518             return __s;
   1519         }
   1520     }
   1521     __iob.width(0);
   1522     return __s;
   1523 }
   1524 
   1525 #endif
   1526 
   1527 template <class _CharT, class _OutputIterator>
   1528 _OutputIterator
   1529 num_put<_CharT, _OutputIterator>::do_put(iter_type __s, ios_base& __iob,
   1530                                          char_type __fl, bool __v) const
   1531 {
   1532     if ((__iob.flags() & ios_base::boolalpha) == 0)
   1533         return do_put(__s, __iob, __fl, (unsigned long)__v);
   1534     const numpunct<char_type>& __np = use_facet<numpunct<char_type> >(__iob.getloc());
   1535     typedef typename numpunct<char_type>::string_type string_type;
   1536 #if _LIBCPP_DEBUG_LEVEL >= 2
   1537     string_type __tmp(__v ? __np.truename() : __np.falsename());
   1538     string_type __nm = _VSTD::move(__tmp);
   1539 #else
   1540     string_type __nm = __v ? __np.truename() : __np.falsename();
   1541 #endif
   1542     for (typename string_type::iterator __i = __nm.begin(); __i != __nm.end(); ++__i, ++__s)
   1543         *__s = *__i;
   1544     return __s;
   1545 }
   1546 
   1547 template <class _CharT, class _OutputIterator>
   1548 _OutputIterator
   1549 num_put<_CharT, _OutputIterator>::do_put(iter_type __s, ios_base& __iob,
   1550                                          char_type __fl, long __v) const
   1551 {
   1552     // Stage 1 - Get number in narrow char
   1553     char __fmt[6] = {'%', 0};
   1554     const char* __len = "l";
   1555     this->__format_int(__fmt+1, __len, true, __iob.flags());
   1556     const unsigned __nbuf = (numeric_limits<long>::digits / 3)
   1557                           + ((numeric_limits<long>::digits % 3) != 0)
   1558                           + 1;
   1559     char __nar[__nbuf];
   1560 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1561     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
   1562 #else
   1563     int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
   1564 #endif
   1565     char* __ne = __nar + __nc;
   1566     char* __np = this->__identify_padding(__nar, __ne, __iob);
   1567     // Stage 2 - Widen __nar while adding thousands separators
   1568     char_type __o[2*(__nbuf-1) - 1];
   1569     char_type* __op;  // pad here
   1570     char_type* __oe;  // end of output
   1571     this->__widen_and_group_int(__nar, __np, __ne, __o, __op, __oe, __iob.getloc());
   1572     // [__o, __oe) contains thousands_sep'd wide number
   1573     // Stage 3 & 4
   1574     return __pad_and_output(__s, __o, __op, __oe, __iob, __fl);
   1575 }
   1576 
   1577 template <class _CharT, class _OutputIterator>
   1578 _OutputIterator
   1579 num_put<_CharT, _OutputIterator>::do_put(iter_type __s, ios_base& __iob,
   1580                                          char_type __fl, long long __v) const
   1581 {
   1582     // Stage 1 - Get number in narrow char
   1583     char __fmt[8] = {'%', 0};
   1584     const char* __len = "ll";
   1585     this->__format_int(__fmt+1, __len, true, __iob.flags());
   1586     const unsigned __nbuf = (numeric_limits<long long>::digits / 3)
   1587                           + ((numeric_limits<long long>::digits % 3) != 0)
   1588                           + 2;
   1589     char __nar[__nbuf];
   1590 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1591     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
   1592 #else
   1593     int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
   1594 #endif
   1595     char* __ne = __nar + __nc;
   1596     char* __np = this->__identify_padding(__nar, __ne, __iob);
   1597     // Stage 2 - Widen __nar while adding thousands separators
   1598     char_type __o[2*(__nbuf-1) - 1];
   1599     char_type* __op;  // pad here
   1600     char_type* __oe;  // end of output
   1601     this->__widen_and_group_int(__nar, __np, __ne, __o, __op, __oe, __iob.getloc());
   1602     // [__o, __oe) contains thousands_sep'd wide number
   1603     // Stage 3 & 4
   1604     return __pad_and_output(__s, __o, __op, __oe, __iob, __fl);
   1605 }
   1606 
   1607 template <class _CharT, class _OutputIterator>
   1608 _OutputIterator
   1609 num_put<_CharT, _OutputIterator>::do_put(iter_type __s, ios_base& __iob,
   1610                                          char_type __fl, unsigned long __v) const
   1611 {
   1612     // Stage 1 - Get number in narrow char
   1613     char __fmt[6] = {'%', 0};
   1614     const char* __len = "l";
   1615     this->__format_int(__fmt+1, __len, false, __iob.flags());
   1616     const unsigned __nbuf = (numeric_limits<unsigned long>::digits / 3)
   1617                           + ((numeric_limits<unsigned long>::digits % 3) != 0)
   1618                           + 1;
   1619     char __nar[__nbuf];
   1620 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1621     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
   1622 #else
   1623     int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
   1624 #endif
   1625     char* __ne = __nar + __nc;
   1626     char* __np = this->__identify_padding(__nar, __ne, __iob);
   1627     // Stage 2 - Widen __nar while adding thousands separators
   1628     char_type __o[2*(__nbuf-1) - 1];
   1629     char_type* __op;  // pad here
   1630     char_type* __oe;  // end of output
   1631     this->__widen_and_group_int(__nar, __np, __ne, __o, __op, __oe, __iob.getloc());
   1632     // [__o, __oe) contains thousands_sep'd wide number
   1633     // Stage 3 & 4
   1634     return __pad_and_output(__s, __o, __op, __oe, __iob, __fl);
   1635 }
   1636 
   1637 template <class _CharT, class _OutputIterator>
   1638 _OutputIterator
   1639 num_put<_CharT, _OutputIterator>::do_put(iter_type __s, ios_base& __iob,
   1640                                          char_type __fl, unsigned long long __v) const
   1641 {
   1642     // Stage 1 - Get number in narrow char
   1643     char __fmt[8] = {'%', 0};
   1644     const char* __len = "ll";
   1645     this->__format_int(__fmt+1, __len, false, __iob.flags());
   1646     const unsigned __nbuf = (numeric_limits<unsigned long long>::digits / 3)
   1647                           + ((numeric_limits<unsigned long long>::digits % 3) != 0)
   1648                           + 1;
   1649     char __nar[__nbuf];
   1650 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1651     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
   1652 #else
   1653     int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
   1654 #endif
   1655     char* __ne = __nar + __nc;
   1656     char* __np = this->__identify_padding(__nar, __ne, __iob);
   1657     // Stage 2 - Widen __nar while adding thousands separators
   1658     char_type __o[2*(__nbuf-1) - 1];
   1659     char_type* __op;  // pad here
   1660     char_type* __oe;  // end of output
   1661     this->__widen_and_group_int(__nar, __np, __ne, __o, __op, __oe, __iob.getloc());
   1662     // [__o, __oe) contains thousands_sep'd wide number
   1663     // Stage 3 & 4
   1664     return __pad_and_output(__s, __o, __op, __oe, __iob, __fl);
   1665 }
   1666 
   1667 template <class _CharT, class _OutputIterator>
   1668 _OutputIterator
   1669 num_put<_CharT, _OutputIterator>::do_put(iter_type __s, ios_base& __iob,
   1670                                          char_type __fl, double __v) const
   1671 {
   1672     // Stage 1 - Get number in narrow char
   1673     char __fmt[8] = {'%', 0};
   1674     const char* __len = "";
   1675     bool __specify_precision = this->__format_float(__fmt+1, __len, __iob.flags());
   1676     const unsigned __nbuf = 30;
   1677     char __nar[__nbuf];
   1678     char* __nb = __nar;
   1679     int __nc;
   1680     if (__specify_precision)
   1681 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1682         __nc = snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt,
   1683                                    (int)__iob.precision(), __v);
   1684 #else
   1685         __nc = __snprintf_l(__nb, __nbuf, __cloc(), __fmt,
   1686                             (int)__iob.precision(), __v);
   1687 #endif
   1688     else
   1689 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1690         __nc = snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt, __v);
   1691 #else
   1692         __nc = __snprintf_l(__nb, __nbuf, __cloc(), __fmt, __v);
   1693 #endif
   1694     unique_ptr<char, void(*)(void*)> __nbh(0, free);
   1695     if (__nc > static_cast<int>(__nbuf-1))
   1696     {
   1697         if (__specify_precision)
   1698 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1699             __nc = asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, (int)__iob.precision(), __v);
   1700 #else
   1701             __nc = __asprintf_l(&__nb, __cloc(), __fmt,
   1702                               (int)__iob.precision(), __v);
   1703 #endif
   1704         else
   1705 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1706             __nc = asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, __v);
   1707 #else
   1708             __nc = __asprintf_l(&__nb, __cloc(), __fmt, (int)__iob.precision(), __v);
   1709 #endif
   1710         if (__nb == 0)
   1711             __throw_bad_alloc();
   1712         __nbh.reset(__nb);
   1713     }
   1714     char* __ne = __nb + __nc;
   1715     char* __np = this->__identify_padding(__nb, __ne, __iob);
   1716     // Stage 2 - Widen __nar while adding thousands separators
   1717     char_type __o[2*(__nbuf-1) - 1];
   1718     char_type* __ob = __o;
   1719     unique_ptr<char_type, void(*)(void*)> __obh(0, free);
   1720     if (__nb != __nar)
   1721     {
   1722         __ob = (char_type*)malloc(2*static_cast<size_t>(__nc)*sizeof(char_type));
   1723         if (__ob == 0)
   1724             __throw_bad_alloc();
   1725         __obh.reset(__ob);
   1726     }
   1727     char_type* __op;  // pad here
   1728     char_type* __oe;  // end of output
   1729     this->__widen_and_group_float(__nb, __np, __ne, __ob, __op, __oe, __iob.getloc());
   1730     // [__o, __oe) contains thousands_sep'd wide number
   1731     // Stage 3 & 4
   1732     __s = __pad_and_output(__s, __ob, __op, __oe, __iob, __fl);
   1733     return __s;
   1734 }
   1735 
   1736 template <class _CharT, class _OutputIterator>
   1737 _OutputIterator
   1738 num_put<_CharT, _OutputIterator>::do_put(iter_type __s, ios_base& __iob,
   1739                                          char_type __fl, long double __v) const
   1740 {
   1741     // Stage 1 - Get number in narrow char
   1742     char __fmt[8] = {'%', 0};
   1743     const char* __len = "L";
   1744     bool __specify_precision = this->__format_float(__fmt+1, __len, __iob.flags());
   1745     const unsigned __nbuf = 30;
   1746     char __nar[__nbuf];
   1747     char* __nb = __nar;
   1748     int __nc;
   1749     if (__specify_precision)
   1750 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1751         __nc = snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt,
   1752                                    (int)__iob.precision(), __v);
   1753 #else
   1754         __nc = __snprintf_l(__nb, __nbuf, __cloc(), __fmt,
   1755                             (int)__iob.precision(), __v);
   1756 #endif
   1757     else
   1758 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1759         __nc = snprintf_l(__nb, __nbuf, _LIBCPP_GET_C_LOCALE, __fmt, __v);
   1760 #else
   1761         __nc = __snprintf_l(__nb, __nbuf, __cloc(), __fmt, __v);
   1762 #endif
   1763     unique_ptr<char, void(*)(void*)> __nbh(0, free);
   1764     if (__nc > static_cast<int>(__nbuf-1))
   1765     {
   1766         if (__specify_precision)
   1767 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1768             __nc = asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, (int)__iob.precision(), __v);
   1769 #else
   1770             __nc = __asprintf_l(&__nb, __cloc(), __fmt,
   1771                               (int)__iob.precision(), __v);
   1772 #endif
   1773         else
   1774 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1775             __nc = asprintf_l(&__nb, _LIBCPP_GET_C_LOCALE, __fmt, __v);
   1776 #else
   1777             __nc = __asprintf_l(&__nb, __cloc(), __fmt, __v);
   1778 #endif
   1779         if (__nb == 0)
   1780             __throw_bad_alloc();
   1781         __nbh.reset(__nb);
   1782     }
   1783     char* __ne = __nb + __nc;
   1784     char* __np = this->__identify_padding(__nb, __ne, __iob);
   1785     // Stage 2 - Widen __nar while adding thousands separators
   1786     char_type __o[2*(__nbuf-1) - 1];
   1787     char_type* __ob = __o;
   1788     unique_ptr<char_type, void(*)(void*)> __obh(0, free);
   1789     if (__nb != __nar)
   1790     {
   1791         __ob = (char_type*)malloc(2*static_cast<size_t>(__nc)*sizeof(char_type));
   1792         if (__ob == 0)
   1793             __throw_bad_alloc();
   1794         __obh.reset(__ob);
   1795     }
   1796     char_type* __op;  // pad here
   1797     char_type* __oe;  // end of output
   1798     this->__widen_and_group_float(__nb, __np, __ne, __ob, __op, __oe, __iob.getloc());
   1799     // [__o, __oe) contains thousands_sep'd wide number
   1800     // Stage 3 & 4
   1801     __s = __pad_and_output(__s, __ob, __op, __oe, __iob, __fl);
   1802     return __s;
   1803 }
   1804 
   1805 template <class _CharT, class _OutputIterator>
   1806 _OutputIterator
   1807 num_put<_CharT, _OutputIterator>::do_put(iter_type __s, ios_base& __iob,
   1808                                          char_type __fl, const void* __v) const
   1809 {
   1810     // Stage 1 - Get pointer in narrow char
   1811     char __fmt[6] = "%p";
   1812     const unsigned __nbuf = 20;
   1813     char __nar[__nbuf];
   1814 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   1815     int __nc = snprintf_l(__nar, sizeof(__nar), _LIBCPP_GET_C_LOCALE, __fmt, __v);
   1816 #else
   1817     int __nc = __snprintf_l(__nar, sizeof(__nar), __cloc(), __fmt, __v);
   1818 #endif
   1819     char* __ne = __nar + __nc;
   1820     char* __np = this->__identify_padding(__nar, __ne, __iob);
   1821     // Stage 2 - Widen __nar
   1822     char_type __o[2*(__nbuf-1) - 1];
   1823     char_type* __op;  // pad here
   1824     char_type* __oe;  // end of output
   1825     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__iob.getloc());
   1826     __ct.widen(__nar, __ne, __o);
   1827     __oe = __o + (__ne - __nar);
   1828     if (__np == __ne)
   1829         __op = __oe;
   1830     else
   1831         __op = __o + (__np - __nar);
   1832     // [__o, __oe) contains wide number
   1833     // Stage 3 & 4
   1834     return __pad_and_output(__s, __o, __op, __oe, __iob, __fl);
   1835 }
   1836 
   1837 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS num_put<char>)
   1838 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS num_put<wchar_t>)
   1839 
   1840 template <class _CharT, class _InputIterator>
   1841 _LIBCPP_HIDDEN
   1842 int
   1843 __get_up_to_n_digits(_InputIterator& __b, _InputIterator __e,
   1844                      ios_base::iostate& __err, const ctype<_CharT>& __ct, int __n)
   1845 {
   1846     // Precondition:  __n >= 1
   1847     if (__b == __e)
   1848     {
   1849         __err |= ios_base::eofbit | ios_base::failbit;
   1850         return 0;
   1851     }
   1852     // get first digit
   1853     _CharT __c = *__b;
   1854     if (!__ct.is(ctype_base::digit, __c))
   1855     {
   1856         __err |= ios_base::failbit;
   1857         return 0;
   1858     }
   1859     int __r = __ct.narrow(__c, 0) - '0';
   1860     for (++__b, (void) --__n; __b != __e && __n > 0; ++__b, (void) --__n)
   1861     {
   1862         // get next digit
   1863         __c = *__b;
   1864         if (!__ct.is(ctype_base::digit, __c))
   1865             return __r;
   1866         __r = __r * 10 + __ct.narrow(__c, 0) - '0';
   1867     }
   1868     if (__b == __e)
   1869         __err |= ios_base::eofbit;
   1870     return __r;
   1871 }
   1872 
   1873 class _LIBCPP_TYPE_VIS time_base
   1874 {
   1875 public:
   1876     enum dateorder {no_order, dmy, mdy, ymd, ydm};
   1877 };
   1878 
   1879 template <class _CharT>
   1880 class _LIBCPP_TYPE_VIS_ONLY __time_get_c_storage
   1881 {
   1882 protected:
   1883     typedef basic_string<_CharT> string_type;
   1884 
   1885     virtual const string_type* __weeks() const;
   1886     virtual const string_type* __months() const;
   1887     virtual const string_type* __am_pm() const;
   1888     virtual const string_type& __c() const;
   1889     virtual const string_type& __r() const;
   1890     virtual const string_type& __x() const;
   1891     virtual const string_type& __X() const;
   1892 };
   1893 
   1894 template <class _CharT, class _InputIterator = istreambuf_iterator<_CharT> >
   1895 class _LIBCPP_TYPE_VIS_ONLY time_get
   1896     : public locale::facet,
   1897       public time_base,
   1898       private __time_get_c_storage<_CharT>
   1899 {
   1900 public:
   1901     typedef _CharT                  char_type;
   1902     typedef _InputIterator          iter_type;
   1903     typedef time_base::dateorder    dateorder;
   1904     typedef basic_string<char_type> string_type;
   1905 
   1906     _LIBCPP_ALWAYS_INLINE
   1907     explicit time_get(size_t __refs = 0)
   1908         : locale::facet(__refs) {}
   1909 
   1910     _LIBCPP_ALWAYS_INLINE
   1911     dateorder date_order() const
   1912     {
   1913         return this->do_date_order();
   1914     }
   1915 
   1916     _LIBCPP_ALWAYS_INLINE
   1917     iter_type get_time(iter_type __b, iter_type __e, ios_base& __iob,
   1918                        ios_base::iostate& __err, tm* __tm) const
   1919     {
   1920         return do_get_time(__b, __e, __iob, __err, __tm);
   1921     }
   1922 
   1923     _LIBCPP_ALWAYS_INLINE
   1924     iter_type get_date(iter_type __b, iter_type __e, ios_base& __iob,
   1925                        ios_base::iostate& __err, tm* __tm) const
   1926     {
   1927         return do_get_date(__b, __e, __iob, __err, __tm);
   1928     }
   1929 
   1930     _LIBCPP_ALWAYS_INLINE
   1931     iter_type get_weekday(iter_type __b, iter_type __e, ios_base& __iob,
   1932                           ios_base::iostate& __err, tm* __tm) const
   1933     {
   1934         return do_get_weekday(__b, __e, __iob, __err, __tm);
   1935     }
   1936 
   1937     _LIBCPP_ALWAYS_INLINE
   1938     iter_type get_monthname(iter_type __b, iter_type __e, ios_base& __iob,
   1939                             ios_base::iostate& __err, tm* __tm) const
   1940     {
   1941         return do_get_monthname(__b, __e, __iob, __err, __tm);
   1942     }
   1943 
   1944     _LIBCPP_ALWAYS_INLINE
   1945     iter_type get_year(iter_type __b, iter_type __e, ios_base& __iob,
   1946                        ios_base::iostate& __err, tm* __tm) const
   1947     {
   1948         return do_get_year(__b, __e, __iob, __err, __tm);
   1949     }
   1950 
   1951     _LIBCPP_ALWAYS_INLINE
   1952     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
   1953                   ios_base::iostate& __err, tm *__tm,
   1954                   char __fmt, char __mod = 0) const
   1955     {
   1956         return do_get(__b, __e, __iob, __err, __tm, __fmt, __mod);
   1957     }
   1958 
   1959     iter_type get(iter_type __b, iter_type __e, ios_base& __iob,
   1960                   ios_base::iostate& __err, tm* __tm,
   1961                   const char_type* __fmtb, const char_type* __fmte) const;
   1962 
   1963     static locale::id id;
   1964 
   1965 protected:
   1966     _LIBCPP_ALWAYS_INLINE
   1967     ~time_get() {}
   1968 
   1969     virtual dateorder do_date_order() const;
   1970     virtual iter_type do_get_time(iter_type __b, iter_type __e, ios_base& __iob,
   1971                                   ios_base::iostate& __err, tm* __tm) const;
   1972     virtual iter_type do_get_date(iter_type __b, iter_type __e, ios_base& __iob,
   1973                                   ios_base::iostate& __err, tm* __tm) const;
   1974     virtual iter_type do_get_weekday(iter_type __b, iter_type __e, ios_base& __iob,
   1975                                      ios_base::iostate& __err, tm* __tm) const;
   1976     virtual iter_type do_get_monthname(iter_type __b, iter_type __e, ios_base& __iob,
   1977                                        ios_base::iostate& __err, tm* __tm) const;
   1978     virtual iter_type do_get_year(iter_type __b, iter_type __e, ios_base& __iob,
   1979                                   ios_base::iostate& __err, tm* __tm) const;
   1980     virtual iter_type do_get(iter_type __b, iter_type __e, ios_base& __iob,
   1981                              ios_base::iostate& __err, tm* __tm,
   1982                              char __fmt, char __mod) const;
   1983 private:
   1984     void __get_white_space(iter_type& __b, iter_type __e,
   1985                            ios_base::iostate& __err, const ctype<char_type>& __ct) const;
   1986     void __get_percent(iter_type& __b, iter_type __e, ios_base::iostate& __err,
   1987                        const ctype<char_type>& __ct) const;
   1988 
   1989     void __get_weekdayname(int& __m,
   1990                            iter_type& __b, iter_type __e,
   1991                            ios_base::iostate& __err,
   1992                            const ctype<char_type>& __ct) const;
   1993     void __get_monthname(int& __m,
   1994                          iter_type& __b, iter_type __e,
   1995                          ios_base::iostate& __err,
   1996                          const ctype<char_type>& __ct) const;
   1997     void __get_day(int& __d,
   1998                    iter_type& __b, iter_type __e,
   1999                    ios_base::iostate& __err,
   2000                    const ctype<char_type>& __ct) const;
   2001     void __get_month(int& __m,
   2002                      iter_type& __b, iter_type __e,
   2003                      ios_base::iostate& __err,
   2004                      const ctype<char_type>& __ct) const;
   2005     void __get_year(int& __y,
   2006                    iter_type& __b, iter_type __e,
   2007                    ios_base::iostate& __err,
   2008                    const ctype<char_type>& __ct) const;
   2009     void __get_year4(int& __y,
   2010                     iter_type& __b, iter_type __e,
   2011                     ios_base::iostate& __err,
   2012                     const ctype<char_type>& __ct) const;
   2013     void __get_hour(int& __d,
   2014                     iter_type& __b, iter_type __e,
   2015                     ios_base::iostate& __err,
   2016                     const ctype<char_type>& __ct) const;
   2017     void __get_12_hour(int& __h,
   2018                        iter_type& __b, iter_type __e,
   2019                        ios_base::iostate& __err,
   2020                        const ctype<char_type>& __ct) const;
   2021     void __get_am_pm(int& __h,
   2022                      iter_type& __b, iter_type __e,
   2023                      ios_base::iostate& __err,
   2024                      const ctype<char_type>& __ct) const;
   2025     void __get_minute(int& __m,
   2026                       iter_type& __b, iter_type __e,
   2027                       ios_base::iostate& __err,
   2028                       const ctype<char_type>& __ct) const;
   2029     void __get_second(int& __s,
   2030                       iter_type& __b, iter_type __e,
   2031                       ios_base::iostate& __err,
   2032                       const ctype<char_type>& __ct) const;
   2033     void __get_weekday(int& __w,
   2034                        iter_type& __b, iter_type __e,
   2035                        ios_base::iostate& __err,
   2036                        const ctype<char_type>& __ct) const;
   2037     void __get_day_year_num(int& __w,
   2038                             iter_type& __b, iter_type __e,
   2039                             ios_base::iostate& __err,
   2040                             const ctype<char_type>& __ct) const;
   2041 };
   2042 
   2043 template <class _CharT, class _InputIterator>
   2044 locale::id
   2045 time_get<_CharT, _InputIterator>::id;
   2046 
   2047 // time_get primitives
   2048 
   2049 template <class _CharT, class _InputIterator>
   2050 void
   2051 time_get<_CharT, _InputIterator>::__get_weekdayname(int& __w,
   2052                                                     iter_type& __b, iter_type __e,
   2053                                                     ios_base::iostate& __err,
   2054                                                     const ctype<char_type>& __ct) const
   2055 {
   2056     // Note:  ignoring case comes from the POSIX strptime spec
   2057     const string_type* __wk = this->__weeks();
   2058     ptrdiff_t __i = __scan_keyword(__b, __e, __wk, __wk+14, __ct, __err, false) - __wk;
   2059     if (__i < 14)
   2060         __w = __i % 7;
   2061 }
   2062 
   2063 template <class _CharT, class _InputIterator>
   2064 void
   2065 time_get<_CharT, _InputIterator>::__get_monthname(int& __m,
   2066                                                   iter_type& __b, iter_type __e,
   2067                                                   ios_base::iostate& __err,
   2068                                                   const ctype<char_type>& __ct) const
   2069 {
   2070     // Note:  ignoring case comes from the POSIX strptime spec
   2071     const string_type* __month = this->__months();
   2072     ptrdiff_t __i = __scan_keyword(__b, __e, __month, __month+24, __ct, __err, false) - __month;
   2073     if (__i < 24)
   2074         __m = __i % 12;
   2075 }
   2076 
   2077 template <class _CharT, class _InputIterator>
   2078 void
   2079 time_get<_CharT, _InputIterator>::__get_day(int& __d,
   2080                                             iter_type& __b, iter_type __e,
   2081                                             ios_base::iostate& __err,
   2082                                             const ctype<char_type>& __ct) const
   2083 {
   2084     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 2);
   2085     if (!(__err & ios_base::failbit) && 1 <= __t && __t <= 31)
   2086         __d = __t;
   2087     else
   2088         __err |= ios_base::failbit;
   2089 }
   2090 
   2091 template <class _CharT, class _InputIterator>
   2092 void
   2093 time_get<_CharT, _InputIterator>::__get_month(int& __m,
   2094                                               iter_type& __b, iter_type __e,
   2095                                               ios_base::iostate& __err,
   2096                                               const ctype<char_type>& __ct) const
   2097 {
   2098     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 2) - 1;
   2099     if (!(__err & ios_base::failbit) && __t <= 11)
   2100         __m = __t;
   2101     else
   2102         __err |= ios_base::failbit;
   2103 }
   2104 
   2105 template <class _CharT, class _InputIterator>
   2106 void
   2107 time_get<_CharT, _InputIterator>::__get_year(int& __y,
   2108                                              iter_type& __b, iter_type __e,
   2109                                              ios_base::iostate& __err,
   2110                                              const ctype<char_type>& __ct) const
   2111 {
   2112     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 4);
   2113     if (!(__err & ios_base::failbit))
   2114     {
   2115         if (__t < 69)
   2116             __t += 2000;
   2117         else if (69 <= __t && __t <= 99)
   2118             __t += 1900;
   2119         __y = __t - 1900;
   2120     }
   2121 }
   2122 
   2123 template <class _CharT, class _InputIterator>
   2124 void
   2125 time_get<_CharT, _InputIterator>::__get_year4(int& __y,
   2126                                               iter_type& __b, iter_type __e,
   2127                                               ios_base::iostate& __err,
   2128                                               const ctype<char_type>& __ct) const
   2129 {
   2130     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 4);
   2131     if (!(__err & ios_base::failbit))
   2132         __y = __t - 1900;
   2133 }
   2134 
   2135 template <class _CharT, class _InputIterator>
   2136 void
   2137 time_get<_CharT, _InputIterator>::__get_hour(int& __h,
   2138                                              iter_type& __b, iter_type __e,
   2139                                              ios_base::iostate& __err,
   2140                                              const ctype<char_type>& __ct) const
   2141 {
   2142     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 2);
   2143     if (!(__err & ios_base::failbit) && __t <= 23)
   2144         __h = __t;
   2145     else
   2146         __err |= ios_base::failbit;
   2147 }
   2148 
   2149 template <class _CharT, class _InputIterator>
   2150 void
   2151 time_get<_CharT, _InputIterator>::__get_12_hour(int& __h,
   2152                                                 iter_type& __b, iter_type __e,
   2153                                                 ios_base::iostate& __err,
   2154                                                 const ctype<char_type>& __ct) const
   2155 {
   2156     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 2);
   2157     if (!(__err & ios_base::failbit) && 1 <= __t && __t <= 12)
   2158         __h = __t;
   2159     else
   2160         __err |= ios_base::failbit;
   2161 }
   2162 
   2163 template <class _CharT, class _InputIterator>
   2164 void
   2165 time_get<_CharT, _InputIterator>::__get_minute(int& __m,
   2166                                                iter_type& __b, iter_type __e,
   2167                                                ios_base::iostate& __err,
   2168                                                const ctype<char_type>& __ct) const
   2169 {
   2170     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 2);
   2171     if (!(__err & ios_base::failbit) && __t <= 59)
   2172         __m = __t;
   2173     else
   2174         __err |= ios_base::failbit;
   2175 }
   2176 
   2177 template <class _CharT, class _InputIterator>
   2178 void
   2179 time_get<_CharT, _InputIterator>::__get_second(int& __s,
   2180                                                iter_type& __b, iter_type __e,
   2181                                                ios_base::iostate& __err,
   2182                                                const ctype<char_type>& __ct) const
   2183 {
   2184     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 2);
   2185     if (!(__err & ios_base::failbit) && __t <= 60)
   2186         __s = __t;
   2187     else
   2188         __err |= ios_base::failbit;
   2189 }
   2190 
   2191 template <class _CharT, class _InputIterator>
   2192 void
   2193 time_get<_CharT, _InputIterator>::__get_weekday(int& __w,
   2194                                                 iter_type& __b, iter_type __e,
   2195                                                 ios_base::iostate& __err,
   2196                                                 const ctype<char_type>& __ct) const
   2197 {
   2198     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 1);
   2199     if (!(__err & ios_base::failbit) && __t <= 6)
   2200         __w = __t;
   2201     else
   2202         __err |= ios_base::failbit;
   2203 }
   2204 
   2205 template <class _CharT, class _InputIterator>
   2206 void
   2207 time_get<_CharT, _InputIterator>::__get_day_year_num(int& __d,
   2208                                                      iter_type& __b, iter_type __e,
   2209                                                      ios_base::iostate& __err,
   2210                                                      const ctype<char_type>& __ct) const
   2211 {
   2212     int __t = __get_up_to_n_digits(__b, __e, __err, __ct, 3);
   2213     if (!(__err & ios_base::failbit) && __t <= 365)
   2214         __d = __t;
   2215     else
   2216         __err |= ios_base::failbit;
   2217 }
   2218 
   2219 template <class _CharT, class _InputIterator>
   2220 void
   2221 time_get<_CharT, _InputIterator>::__get_white_space(iter_type& __b, iter_type __e,
   2222                                                     ios_base::iostate& __err,
   2223                                                     const ctype<char_type>& __ct) const
   2224 {
   2225     for (; __b != __e && __ct.is(ctype_base::space, *__b); ++__b)
   2226         ;
   2227     if (__b == __e)
   2228         __err |= ios_base::eofbit;
   2229 }
   2230 
   2231 template <class _CharT, class _InputIterator>
   2232 void
   2233 time_get<_CharT, _InputIterator>::__get_am_pm(int& __h,
   2234                                               iter_type& __b, iter_type __e,
   2235                                               ios_base::iostate& __err,
   2236                                               const ctype<char_type>& __ct) const
   2237 {
   2238     const string_type* __ap = this->__am_pm();
   2239     if (__ap[0].size() + __ap[1].size() == 0)
   2240     {
   2241         __err |= ios_base::failbit;
   2242         return;
   2243     }
   2244     ptrdiff_t __i = __scan_keyword(__b, __e, __ap, __ap+2, __ct, __err, false) - __ap;
   2245     if (__i == 0 && __h == 12)
   2246         __h = 0;
   2247     else if (__i == 1 && __h < 12)
   2248         __h += 12;
   2249 }
   2250 
   2251 template <class _CharT, class _InputIterator>
   2252 void
   2253 time_get<_CharT, _InputIterator>::__get_percent(iter_type& __b, iter_type __e,
   2254                                                 ios_base::iostate& __err,
   2255                                                 const ctype<char_type>& __ct) const
   2256 {
   2257     if (__b == __e)
   2258     {
   2259         __err |= ios_base::eofbit | ios_base::failbit;
   2260         return;
   2261     }
   2262     if (__ct.narrow(*__b, 0) != '%')
   2263         __err |= ios_base::failbit;
   2264     else if(++__b == __e)
   2265         __err |= ios_base::eofbit;
   2266 }
   2267 
   2268 // time_get end primitives
   2269 
   2270 template <class _CharT, class _InputIterator>
   2271 _InputIterator
   2272 time_get<_CharT, _InputIterator>::get(iter_type __b, iter_type __e,
   2273                                       ios_base& __iob,
   2274                                       ios_base::iostate& __err, tm* __tm,
   2275                                       const char_type* __fmtb, const char_type* __fmte) const
   2276 {
   2277     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__iob.getloc());
   2278     __err = ios_base::goodbit;
   2279     while (__fmtb != __fmte && __err == ios_base::goodbit)
   2280     {
   2281         if (__b == __e)
   2282         {
   2283             __err = ios_base::failbit;
   2284             break;
   2285         }
   2286         if (__ct.narrow(*__fmtb, 0) == '%')
   2287         {
   2288             if (++__fmtb == __fmte)
   2289             {
   2290                 __err = ios_base::failbit;
   2291                 break;
   2292             }
   2293             char __cmd = __ct.narrow(*__fmtb, 0);
   2294             char __opt = '\0';
   2295             if (__cmd == 'E' || __cmd == '0')
   2296             {
   2297                 if (++__fmtb == __fmte)
   2298                 {
   2299                     __err = ios_base::failbit;
   2300                     break;
   2301                 }
   2302                 __opt = __cmd;
   2303                 __cmd = __ct.narrow(*__fmtb, 0);
   2304             }
   2305             __b = do_get(__b, __e, __iob, __err, __tm, __cmd, __opt);
   2306             ++__fmtb;
   2307         }
   2308         else if (__ct.is(ctype_base::space, *__fmtb))
   2309         {
   2310             for (++__fmtb; __fmtb != __fmte && __ct.is(ctype_base::space, *__fmtb); ++__fmtb)
   2311                 ;
   2312             for (        ;    __b != __e    && __ct.is(ctype_base::space, *__b);    ++__b)
   2313                 ;
   2314         }
   2315         else if (__ct.toupper(*__b) == __ct.toupper(*__fmtb))
   2316         {
   2317             ++__b;
   2318             ++__fmtb;
   2319         }
   2320         else
   2321             __err = ios_base::failbit;
   2322     }
   2323     if (__b == __e)
   2324         __err |= ios_base::eofbit;
   2325     return __b;
   2326 }
   2327 
   2328 template <class _CharT, class _InputIterator>
   2329 typename time_get<_CharT, _InputIterator>::dateorder
   2330 time_get<_CharT, _InputIterator>::do_date_order() const
   2331 {
   2332     return mdy;
   2333 }
   2334 
   2335 template <class _CharT, class _InputIterator>
   2336 _InputIterator
   2337 time_get<_CharT, _InputIterator>::do_get_time(iter_type __b, iter_type __e,
   2338                                               ios_base& __iob,
   2339                                               ios_base::iostate& __err,
   2340                                               tm* __tm) const
   2341 {
   2342     const char_type __fmt[] = {'%', 'H', ':', '%', 'M', ':', '%', 'S'};
   2343     return get(__b, __e, __iob, __err, __tm, __fmt, __fmt + sizeof(__fmt)/sizeof(__fmt[0]));
   2344 }
   2345 
   2346 template <class _CharT, class _InputIterator>
   2347 _InputIterator
   2348 time_get<_CharT, _InputIterator>::do_get_date(iter_type __b, iter_type __e,
   2349                                               ios_base& __iob,
   2350                                               ios_base::iostate& __err,
   2351                                               tm* __tm) const
   2352 {
   2353     const string_type& __fmt = this->__x();
   2354     return get(__b, __e, __iob, __err, __tm, __fmt.data(), __fmt.data() + __fmt.size());
   2355 }
   2356 
   2357 template <class _CharT, class _InputIterator>
   2358 _InputIterator
   2359 time_get<_CharT, _InputIterator>::do_get_weekday(iter_type __b, iter_type __e,
   2360                                                  ios_base& __iob,
   2361                                                  ios_base::iostate& __err,
   2362                                                  tm* __tm) const
   2363 {
   2364     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__iob.getloc());
   2365     __get_weekdayname(__tm->tm_wday, __b, __e, __err, __ct);
   2366     return __b;
   2367 }
   2368 
   2369 template <class _CharT, class _InputIterator>
   2370 _InputIterator
   2371 time_get<_CharT, _InputIterator>::do_get_monthname(iter_type __b, iter_type __e,
   2372                                                    ios_base& __iob,
   2373                                                    ios_base::iostate& __err,
   2374                                                    tm* __tm) const
   2375 {
   2376     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__iob.getloc());
   2377     __get_monthname(__tm->tm_mon, __b, __e, __err, __ct);
   2378     return __b;
   2379 }
   2380 
   2381 template <class _CharT, class _InputIterator>
   2382 _InputIterator
   2383 time_get<_CharT, _InputIterator>::do_get_year(iter_type __b, iter_type __e,
   2384                                               ios_base& __iob,
   2385                                               ios_base::iostate& __err,
   2386                                               tm* __tm) const
   2387 {
   2388     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__iob.getloc());
   2389     __get_year(__tm->tm_year, __b, __e, __err, __ct);
   2390     return __b;
   2391 }
   2392 
   2393 template <class _CharT, class _InputIterator>
   2394 _InputIterator
   2395 time_get<_CharT, _InputIterator>::do_get(iter_type __b, iter_type __e,
   2396                                          ios_base& __iob,
   2397                                          ios_base::iostate& __err, tm* __tm,
   2398                                          char __fmt, char) const
   2399 {
   2400     __err = ios_base::goodbit;
   2401     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__iob.getloc());
   2402     switch (__fmt)
   2403     {
   2404     case 'a':
   2405     case 'A':
   2406         __get_weekdayname(__tm->tm_wday, __b, __e, __err, __ct);
   2407         break;
   2408     case 'b':
   2409     case 'B':
   2410     case 'h':
   2411         __get_monthname(__tm->tm_mon, __b, __e, __err, __ct);
   2412         break;
   2413     case 'c':
   2414         {
   2415         const string_type& __fm = this->__c();
   2416         __b = get(__b, __e, __iob, __err, __tm, __fm.data(), __fm.data() + __fm.size());
   2417         }
   2418         break;
   2419     case 'd':
   2420     case 'e':
   2421         __get_day(__tm->tm_mday, __b, __e, __err, __ct);
   2422         break;
   2423     case 'D':
   2424         {
   2425         const char_type __fm[] = {'%', 'm', '/', '%', 'd', '/', '%', 'y'};
   2426         __b = get(__b, __e, __iob, __err, __tm, __fm, __fm + sizeof(__fm)/sizeof(__fm[0]));
   2427         }
   2428         break;
   2429     case 'F':
   2430         {
   2431         const char_type __fm[] = {'%', 'Y', '-', '%', 'm', '-', '%', 'd'};
   2432         __b = get(__b, __e, __iob, __err, __tm, __fm, __fm + sizeof(__fm)/sizeof(__fm[0]));
   2433         }
   2434         break;
   2435     case 'H':
   2436         __get_hour(__tm->tm_hour, __b, __e, __err, __ct);
   2437         break;
   2438     case 'I':
   2439         __get_12_hour(__tm->tm_hour, __b, __e, __err, __ct);
   2440         break;
   2441     case 'j':
   2442         __get_day_year_num(__tm->tm_yday, __b, __e, __err, __ct);
   2443         break;
   2444     case 'm':
   2445         __get_month(__tm->tm_mon, __b, __e, __err, __ct);
   2446         break;
   2447     case 'M':
   2448         __get_minute(__tm->tm_min, __b, __e, __err, __ct);
   2449         break;
   2450     case 'n':
   2451     case 't':
   2452         __get_white_space(__b, __e, __err, __ct);
   2453         break;
   2454     case 'p':
   2455         __get_am_pm(__tm->tm_hour, __b, __e, __err, __ct);
   2456         break;
   2457     case 'r':
   2458         {
   2459         const char_type __fm[] = {'%', 'I', ':', '%', 'M', ':', '%', 'S', ' ', '%', 'p'};
   2460         __b = get(__b, __e, __iob, __err, __tm, __fm, __fm + sizeof(__fm)/sizeof(__fm[0]));
   2461         }
   2462         break;
   2463     case 'R':
   2464         {
   2465         const char_type __fm[] = {'%', 'H', ':', '%', 'M'};
   2466         __b = get(__b, __e, __iob, __err, __tm, __fm, __fm + sizeof(__fm)/sizeof(__fm[0]));
   2467         }
   2468         break;
   2469     case 'S':
   2470         __get_second(__tm->tm_sec, __b, __e, __err, __ct);
   2471         break;
   2472     case 'T':
   2473         {
   2474         const char_type __fm[] = {'%', 'H', ':', '%', 'M', ':', '%', 'S'};
   2475         __b = get(__b, __e, __iob, __err, __tm, __fm, __fm + sizeof(__fm)/sizeof(__fm[0]));
   2476         }
   2477         break;
   2478     case 'w':
   2479         __get_weekday(__tm->tm_wday, __b, __e, __err, __ct);
   2480         break;
   2481     case 'x':
   2482         return do_get_date(__b, __e, __iob, __err, __tm);
   2483     case 'X':
   2484         {
   2485         const string_type& __fm = this->__X();
   2486         __b = get(__b, __e, __iob, __err, __tm, __fm.data(), __fm.data() + __fm.size());
   2487         }
   2488         break;
   2489     case 'y':
   2490         __get_year(__tm->tm_year, __b, __e, __err, __ct);
   2491         break;
   2492     case 'Y':
   2493         __get_year4(__tm->tm_year, __b, __e, __err, __ct);
   2494         break;
   2495     case '%':
   2496         __get_percent(__b, __e, __err, __ct);
   2497         break;
   2498     default:
   2499         __err |= ios_base::failbit;
   2500     }
   2501     return __b;
   2502 }
   2503 
   2504 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS time_get<char>)
   2505 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS time_get<wchar_t>)
   2506 
   2507 class _LIBCPP_TYPE_VIS __time_get
   2508 {
   2509 protected:
   2510     locale_t __loc_;
   2511 
   2512     __time_get(const char* __nm);
   2513     __time_get(const string& __nm);
   2514     ~__time_get();
   2515 };
   2516 
   2517 template <class _CharT>
   2518 class _LIBCPP_TYPE_VIS_ONLY __time_get_storage
   2519     : public __time_get
   2520 {
   2521 protected:
   2522     typedef basic_string<_CharT> string_type;
   2523 
   2524     string_type __weeks_[14];
   2525     string_type __months_[24];
   2526     string_type __am_pm_[2];
   2527     string_type __c_;
   2528     string_type __r_;
   2529     string_type __x_;
   2530     string_type __X_;
   2531 
   2532     explicit __time_get_storage(const char* __nm);
   2533     explicit __time_get_storage(const string& __nm);
   2534 
   2535     _LIBCPP_ALWAYS_INLINE ~__time_get_storage() {}
   2536 
   2537     time_base::dateorder __do_date_order() const;
   2538 
   2539 private:
   2540     void init(const ctype<_CharT>&);
   2541     string_type __analyze(char __fmt, const ctype<_CharT>&);
   2542 };
   2543 
   2544 template <class _CharT, class _InputIterator = istreambuf_iterator<_CharT> >
   2545 class _LIBCPP_TYPE_VIS_ONLY time_get_byname
   2546     : public time_get<_CharT, _InputIterator>,
   2547       private __time_get_storage<_CharT>
   2548 {
   2549 public:
   2550     typedef time_base::dateorder    dateorder;
   2551     typedef _InputIterator          iter_type;
   2552     typedef _CharT                  char_type;
   2553     typedef basic_string<char_type> string_type;
   2554 
   2555     _LIBCPP_INLINE_VISIBILITY
   2556     explicit time_get_byname(const char* __nm, size_t __refs = 0)
   2557         : time_get<_CharT, _InputIterator>(__refs),
   2558           __time_get_storage<_CharT>(__nm) {}
   2559     _LIBCPP_INLINE_VISIBILITY
   2560     explicit time_get_byname(const string& __nm, size_t __refs = 0)
   2561         : time_get<_CharT, _InputIterator>(__refs),
   2562           __time_get_storage<_CharT>(__nm) {}
   2563 
   2564 protected:
   2565     _LIBCPP_INLINE_VISIBILITY
   2566     ~time_get_byname() {}
   2567 
   2568     _LIBCPP_INLINE_VISIBILITY
   2569     virtual dateorder do_date_order() const {return this->__do_date_order();}
   2570 private:
   2571     _LIBCPP_INLINE_VISIBILITY
   2572     virtual const string_type* __weeks() const  {return this->__weeks_;}
   2573     _LIBCPP_INLINE_VISIBILITY
   2574     virtual const string_type* __months() const {return this->__months_;}
   2575     _LIBCPP_INLINE_VISIBILITY
   2576     virtual const string_type* __am_pm() const  {return this->__am_pm_;}
   2577     _LIBCPP_INLINE_VISIBILITY
   2578     virtual const string_type& __c() const      {return this->__c_;}
   2579     _LIBCPP_INLINE_VISIBILITY
   2580     virtual const string_type& __r() const      {return this->__r_;}
   2581     _LIBCPP_INLINE_VISIBILITY
   2582     virtual const string_type& __x() const      {return this->__x_;}
   2583     _LIBCPP_INLINE_VISIBILITY
   2584     virtual const string_type& __X() const      {return this->__X_;}
   2585 };
   2586 
   2587 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS time_get_byname<char>)
   2588 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS time_get_byname<wchar_t>)
   2589 
   2590 class _LIBCPP_TYPE_VIS __time_put
   2591 {
   2592     locale_t __loc_;
   2593 protected:
   2594     _LIBCPP_ALWAYS_INLINE __time_put() : __loc_(_LIBCPP_GET_C_LOCALE) {}
   2595     __time_put(const char* __nm);
   2596     __time_put(const string& __nm);
   2597     ~__time_put();
   2598     void __do_put(char* __nb, char*& __ne, const tm* __tm,
   2599                   char __fmt, char __mod) const;
   2600     void __do_put(wchar_t* __wb, wchar_t*& __we, const tm* __tm,
   2601                   char __fmt, char __mod) const;
   2602 };
   2603 
   2604 template <class _CharT, class _OutputIterator = ostreambuf_iterator<_CharT> >
   2605 class _LIBCPP_TYPE_VIS_ONLY time_put
   2606     : public locale::facet,
   2607       private __time_put
   2608 {
   2609 public:
   2610     typedef _CharT char_type;
   2611     typedef _OutputIterator iter_type;
   2612 
   2613     _LIBCPP_ALWAYS_INLINE
   2614     explicit time_put(size_t __refs = 0)
   2615         : locale::facet(__refs) {}
   2616 
   2617     iter_type put(iter_type __s, ios_base& __iob, char_type __fl, const tm* __tm,
   2618                   const char_type* __pb, const char_type* __pe) const;
   2619 
   2620     _LIBCPP_ALWAYS_INLINE
   2621     iter_type put(iter_type __s, ios_base& __iob, char_type __fl,
   2622                   const tm* __tm, char __fmt, char __mod = 0) const
   2623     {
   2624         return do_put(__s, __iob, __fl, __tm, __fmt, __mod);
   2625     }
   2626 
   2627     static locale::id id;
   2628 
   2629 protected:
   2630     _LIBCPP_ALWAYS_INLINE
   2631     ~time_put() {}
   2632     virtual iter_type do_put(iter_type __s, ios_base&, char_type, const tm* __tm,
   2633                              char __fmt, char __mod) const;
   2634 
   2635     _LIBCPP_ALWAYS_INLINE
   2636     explicit time_put(const char* __nm, size_t __refs)
   2637         : locale::facet(__refs),
   2638           __time_put(__nm) {}
   2639     _LIBCPP_ALWAYS_INLINE
   2640     explicit time_put(const string& __nm, size_t __refs)
   2641         : locale::facet(__refs),
   2642           __time_put(__nm) {}
   2643 };
   2644 
   2645 template <class _CharT, class _OutputIterator>
   2646 locale::id
   2647 time_put<_CharT, _OutputIterator>::id;
   2648 
   2649 template <class _CharT, class _OutputIterator>
   2650 _OutputIterator
   2651 time_put<_CharT, _OutputIterator>::put(iter_type __s, ios_base& __iob,
   2652                                        char_type __fl, const tm* __tm,
   2653                                        const char_type* __pb,
   2654                                        const char_type* __pe) const
   2655 {
   2656     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__iob.getloc());
   2657     for (; __pb != __pe; ++__pb)
   2658     {
   2659         if (__ct.narrow(*__pb, 0) == '%')
   2660         {
   2661             if (++__pb == __pe)
   2662             {
   2663                 *__s++ = __pb[-1];
   2664                 break;
   2665             }
   2666             char __mod = 0;
   2667             char __fmt = __ct.narrow(*__pb, 0);
   2668             if (__fmt == 'E' || __fmt == 'O')
   2669             {
   2670                 if (++__pb == __pe)
   2671                 {
   2672                     *__s++ = __pb[-2];
   2673                     *__s++ = __pb[-1];
   2674                     break;
   2675                 }
   2676                 __mod = __fmt;
   2677                 __fmt = __ct.narrow(*__pb, 0);
   2678             }
   2679             __s = do_put(__s, __iob, __fl, __tm, __fmt, __mod);
   2680         }
   2681         else
   2682             *__s++ = *__pb;
   2683     }
   2684     return __s;
   2685 }
   2686 
   2687 template <class _CharT, class _OutputIterator>
   2688 _OutputIterator
   2689 time_put<_CharT, _OutputIterator>::do_put(iter_type __s, ios_base&,
   2690                                           char_type, const tm* __tm,
   2691                                           char __fmt, char __mod) const
   2692 {
   2693     char_type __nar[100];
   2694     char_type* __nb = __nar;
   2695     char_type* __ne = __nb + 100;
   2696     __do_put(__nb, __ne, __tm, __fmt, __mod);
   2697     return _VSTD::copy(__nb, __ne, __s);
   2698 }
   2699 
   2700 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS time_put<char>)
   2701 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS time_put<wchar_t>)
   2702 
   2703 template <class _CharT, class _OutputIterator = ostreambuf_iterator<_CharT> >
   2704 class _LIBCPP_TYPE_VIS_ONLY time_put_byname
   2705     : public time_put<_CharT, _OutputIterator>
   2706 {
   2707 public:
   2708     _LIBCPP_ALWAYS_INLINE
   2709     explicit time_put_byname(const char* __nm, size_t __refs = 0)
   2710         : time_put<_CharT, _OutputIterator>(__nm, __refs) {}
   2711 
   2712     _LIBCPP_ALWAYS_INLINE
   2713     explicit time_put_byname(const string& __nm, size_t __refs = 0)
   2714         : time_put<_CharT, _OutputIterator>(__nm, __refs) {}
   2715 
   2716 protected:
   2717     _LIBCPP_ALWAYS_INLINE
   2718     ~time_put_byname() {}
   2719 };
   2720 
   2721 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS time_put_byname<char>)
   2722 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS time_put_byname<wchar_t>)
   2723 
   2724 // money_base
   2725 
   2726 class _LIBCPP_TYPE_VIS money_base
   2727 {
   2728 public:
   2729     enum part {none, space, symbol, sign, value};
   2730     struct pattern {char field[4];};
   2731 
   2732     _LIBCPP_ALWAYS_INLINE money_base() {}
   2733 };
   2734 
   2735 // moneypunct
   2736 
   2737 template <class _CharT, bool _International = false>
   2738 class _LIBCPP_TYPE_VIS_ONLY moneypunct
   2739     : public locale::facet,
   2740       public money_base
   2741 {
   2742 public:
   2743     typedef _CharT                  char_type;
   2744     typedef basic_string<char_type> string_type;
   2745 
   2746     _LIBCPP_ALWAYS_INLINE
   2747     explicit moneypunct(size_t __refs = 0)
   2748         : locale::facet(__refs) {}
   2749 
   2750     _LIBCPP_ALWAYS_INLINE char_type   decimal_point() const {return do_decimal_point();}
   2751     _LIBCPP_ALWAYS_INLINE char_type   thousands_sep() const {return do_thousands_sep();}
   2752     _LIBCPP_ALWAYS_INLINE string      grouping()      const {return do_grouping();}
   2753     _LIBCPP_ALWAYS_INLINE string_type curr_symbol()   const {return do_curr_symbol();}
   2754     _LIBCPP_ALWAYS_INLINE string_type positive_sign() const {return do_positive_sign();}
   2755     _LIBCPP_ALWAYS_INLINE string_type negative_sign() const {return do_negative_sign();}
   2756     _LIBCPP_ALWAYS_INLINE int         frac_digits()   const {return do_frac_digits();}
   2757     _LIBCPP_ALWAYS_INLINE pattern     pos_format()    const {return do_pos_format();}
   2758     _LIBCPP_ALWAYS_INLINE pattern     neg_format()    const {return do_neg_format();}
   2759 
   2760     static locale::id id;
   2761     static const bool intl = _International;
   2762 
   2763 protected:
   2764     _LIBCPP_ALWAYS_INLINE
   2765     ~moneypunct() {}
   2766 
   2767     virtual char_type   do_decimal_point() const {return numeric_limits<char_type>::max();}
   2768     virtual char_type   do_thousands_sep() const {return numeric_limits<char_type>::max();}
   2769     virtual string      do_grouping()      const {return string();}
   2770     virtual string_type do_curr_symbol()   const {return string_type();}
   2771     virtual string_type do_positive_sign() const {return string_type();}
   2772     virtual string_type do_negative_sign() const {return string_type(1, '-');}
   2773     virtual int         do_frac_digits()   const {return 0;}
   2774     virtual pattern     do_pos_format()    const
   2775         {pattern __p = {{symbol, sign, none, value}}; return __p;}
   2776     virtual pattern     do_neg_format()    const
   2777         {pattern __p = {{symbol, sign, none, value}}; return __p;}
   2778 };
   2779 
   2780 template <class _CharT, bool _International>
   2781 locale::id
   2782 moneypunct<_CharT, _International>::id;
   2783 
   2784 template <class _CharT, bool _International>
   2785 const bool
   2786 moneypunct<_CharT, _International>::intl;
   2787 
   2788 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS moneypunct<char, false>)
   2789 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS moneypunct<char, true>)
   2790 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS moneypunct<wchar_t, false>)
   2791 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS moneypunct<wchar_t, true>)
   2792 
   2793 // moneypunct_byname
   2794 
   2795 template <class _CharT, bool _International = false>
   2796 class _LIBCPP_TYPE_VIS_ONLY moneypunct_byname
   2797     : public moneypunct<_CharT, _International>
   2798 {
   2799 public:
   2800     typedef money_base::pattern  pattern;
   2801     typedef _CharT                  char_type;
   2802     typedef basic_string<char_type> string_type;
   2803 
   2804     _LIBCPP_ALWAYS_INLINE
   2805     explicit moneypunct_byname(const char* __nm, size_t __refs = 0)
   2806         : moneypunct<_CharT, _International>(__refs) {init(__nm);}
   2807 
   2808     _LIBCPP_ALWAYS_INLINE
   2809     explicit moneypunct_byname(const string& __nm, size_t __refs = 0)
   2810         : moneypunct<_CharT, _International>(__refs) {init(__nm.c_str());}
   2811 
   2812 protected:
   2813     _LIBCPP_ALWAYS_INLINE
   2814     ~moneypunct_byname() {}
   2815 
   2816     virtual char_type   do_decimal_point() const {return __decimal_point_;}
   2817     virtual char_type   do_thousands_sep() const {return __thousands_sep_;}
   2818     virtual string      do_grouping()      const {return __grouping_;}
   2819     virtual string_type do_curr_symbol()   const {return __curr_symbol_;}
   2820     virtual string_type do_positive_sign() const {return __positive_sign_;}
   2821     virtual string_type do_negative_sign() const {return __negative_sign_;}
   2822     virtual int         do_frac_digits()   const {return __frac_digits_;}
   2823     virtual pattern     do_pos_format()    const {return __pos_format_;}
   2824     virtual pattern     do_neg_format()    const {return __neg_format_;}
   2825 
   2826 private:
   2827     char_type   __decimal_point_;
   2828     char_type   __thousands_sep_;
   2829     string      __grouping_;
   2830     string_type __curr_symbol_;
   2831     string_type __positive_sign_;
   2832     string_type __negative_sign_;
   2833     int         __frac_digits_;
   2834     pattern     __pos_format_;
   2835     pattern     __neg_format_;
   2836 
   2837     void init(const char*);
   2838 };
   2839 
   2840 template<> void moneypunct_byname<char, false>::init(const char*);
   2841 template<> void moneypunct_byname<char, true>::init(const char*);
   2842 template<> void moneypunct_byname<wchar_t, false>::init(const char*);
   2843 template<> void moneypunct_byname<wchar_t, true>::init(const char*);
   2844 
   2845 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS moneypunct_byname<char, false>)
   2846 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS moneypunct_byname<char, true>)
   2847 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS moneypunct_byname<wchar_t, false>)
   2848 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS moneypunct_byname<wchar_t, true>)
   2849 
   2850 // money_get
   2851 
   2852 template <class _CharT>
   2853 class __money_get
   2854 {
   2855 protected:
   2856     typedef _CharT                  char_type;
   2857     typedef basic_string<char_type> string_type;
   2858 
   2859     _LIBCPP_ALWAYS_INLINE __money_get() {}
   2860 
   2861     static void __gather_info(bool __intl, const locale& __loc,
   2862                               money_base::pattern& __pat, char_type& __dp,
   2863                               char_type& __ts, string& __grp,
   2864                               string_type& __sym, string_type& __psn,
   2865                               string_type& __nsn, int& __fd);
   2866 };
   2867 
   2868 template <class _CharT>
   2869 void
   2870 __money_get<_CharT>::__gather_info(bool __intl, const locale& __loc,
   2871                                    money_base::pattern& __pat, char_type& __dp,
   2872                                    char_type& __ts, string& __grp,
   2873                                    string_type& __sym, string_type& __psn,
   2874                                    string_type& __nsn, int& __fd)
   2875 {
   2876     if (__intl)
   2877     {
   2878         const moneypunct<char_type, true>& __mp =
   2879             use_facet<moneypunct<char_type, true> >(__loc);
   2880         __pat = __mp.neg_format();
   2881         __nsn = __mp.negative_sign();
   2882         __psn = __mp.positive_sign();
   2883         __dp = __mp.decimal_point();
   2884         __ts = __mp.thousands_sep();
   2885         __grp = __mp.grouping();
   2886         __sym = __mp.curr_symbol();
   2887         __fd = __mp.frac_digits();
   2888     }
   2889     else
   2890     {
   2891         const moneypunct<char_type, false>& __mp =
   2892             use_facet<moneypunct<char_type, false> >(__loc);
   2893         __pat = __mp.neg_format();
   2894         __nsn = __mp.negative_sign();
   2895         __psn = __mp.positive_sign();
   2896         __dp = __mp.decimal_point();
   2897         __ts = __mp.thousands_sep();
   2898         __grp = __mp.grouping();
   2899         __sym = __mp.curr_symbol();
   2900         __fd = __mp.frac_digits();
   2901     }
   2902 }
   2903 
   2904 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS __money_get<char>)
   2905 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS __money_get<wchar_t>)
   2906 
   2907 template <class _CharT, class _InputIterator = istreambuf_iterator<_CharT> >
   2908 class _LIBCPP_TYPE_VIS_ONLY money_get
   2909     : public locale::facet,
   2910       private __money_get<_CharT>
   2911 {
   2912 public:
   2913     typedef _CharT                  char_type;
   2914     typedef _InputIterator          iter_type;
   2915     typedef basic_string<char_type> string_type;
   2916 
   2917     _LIBCPP_ALWAYS_INLINE
   2918     explicit money_get(size_t __refs = 0)
   2919         : locale::facet(__refs) {}
   2920 
   2921     _LIBCPP_ALWAYS_INLINE
   2922     iter_type get(iter_type __b, iter_type __e, bool __intl, ios_base& __iob,
   2923                   ios_base::iostate& __err, long double& __v) const
   2924     {
   2925         return do_get(__b, __e, __intl, __iob, __err, __v);
   2926     }
   2927 
   2928     _LIBCPP_ALWAYS_INLINE
   2929     iter_type get(iter_type __b, iter_type __e, bool __intl, ios_base& __iob,
   2930                   ios_base::iostate& __err, string_type& __v) const
   2931     {
   2932         return do_get(__b, __e, __intl, __iob, __err, __v);
   2933     }
   2934 
   2935     static locale::id id;
   2936 
   2937 protected:
   2938 
   2939     _LIBCPP_ALWAYS_INLINE
   2940     ~money_get() {}
   2941 
   2942     virtual iter_type do_get(iter_type __b, iter_type __e, bool __intl,
   2943                              ios_base& __iob, ios_base::iostate& __err,
   2944                              long double& __v) const;
   2945     virtual iter_type do_get(iter_type __b, iter_type __e, bool __intl,
   2946                              ios_base& __iob, ios_base::iostate& __err,
   2947                              string_type& __v) const;
   2948 
   2949 private:
   2950     static bool __do_get(iter_type& __b, iter_type __e,
   2951                          bool __intl, const locale& __loc,
   2952                          ios_base::fmtflags __flags, ios_base::iostate& __err,
   2953                          bool& __neg, const ctype<char_type>& __ct,
   2954                          unique_ptr<char_type, void(*)(void*)>& __wb,
   2955                          char_type*& __wn, char_type* __we);
   2956 };
   2957 
   2958 template <class _CharT, class _InputIterator>
   2959 locale::id
   2960 money_get<_CharT, _InputIterator>::id;
   2961 
   2962 _LIBCPP_FUNC_VIS void __do_nothing(void*);
   2963 
   2964 template <class _Tp>
   2965 _LIBCPP_HIDDEN
   2966 void
   2967 __double_or_nothing(unique_ptr<_Tp, void(*)(void*)>& __b, _Tp*& __n, _Tp*& __e)
   2968 {
   2969     bool __owns = __b.get_deleter() != __do_nothing;
   2970     size_t __cur_cap = static_cast<size_t>(__e-__b.get()) * sizeof(_Tp);
   2971     size_t __new_cap = __cur_cap < numeric_limits<size_t>::max() / 2 ?
   2972                        2 * __cur_cap : numeric_limits<size_t>::max();
   2973     if (__new_cap == 0)
   2974         __new_cap = sizeof(_Tp);
   2975     size_t __n_off = static_cast<size_t>(__n - __b.get());
   2976     _Tp* __t = (_Tp*)realloc(__owns ? __b.get() : 0, __new_cap);
   2977     if (__t == 0)
   2978         __throw_bad_alloc();
   2979     if (__owns)
   2980         __b.release();
   2981     __b = unique_ptr<_Tp, void(*)(void*)>(__t, free);
   2982     __new_cap /= sizeof(_Tp);
   2983     __n = __b.get() + __n_off;
   2984     __e = __b.get() + __new_cap;
   2985 }
   2986 
   2987 // true == success
   2988 template <class _CharT, class _InputIterator>
   2989 bool
   2990 money_get<_CharT, _InputIterator>::__do_get(iter_type& __b, iter_type __e,
   2991                                             bool __intl, const locale& __loc,
   2992                                             ios_base::fmtflags __flags,
   2993                                             ios_base::iostate& __err,
   2994                                             bool& __neg,
   2995                                             const ctype<char_type>& __ct,
   2996                                             unique_ptr<char_type, void(*)(void*)>& __wb,
   2997                                             char_type*& __wn, char_type* __we)
   2998 {
   2999     const unsigned __bz = 100;
   3000     unsigned __gbuf[__bz];
   3001     unique_ptr<unsigned, void(*)(void*)> __gb(__gbuf, __do_nothing);
   3002     unsigned* __gn = __gb.get();
   3003     unsigned* __ge = __gn + __bz;
   3004     money_base::pattern __pat;
   3005     char_type __dp;
   3006     char_type __ts;
   3007     string __grp;
   3008     string_type __sym;
   3009     string_type __psn;
   3010     string_type __nsn;
   3011     // Capture the spaces read into money_base::{space,none} so they
   3012     // can be compared to initial spaces in __sym.
   3013     string_type __spaces;
   3014     int __fd;
   3015     __money_get<_CharT>::__gather_info(__intl, __loc, __pat, __dp, __ts, __grp,
   3016                                        __sym, __psn, __nsn, __fd);
   3017     const string_type* __trailing_sign = 0;
   3018     __wn = __wb.get();
   3019     for (unsigned __p = 0; __p < 4 && __b != __e; ++__p)
   3020     {
   3021         switch (__pat.field[__p])
   3022         {
   3023         case money_base::space:
   3024             if (__p != 3)
   3025             {
   3026                 if (__ct.is(ctype_base::space, *__b))
   3027                     __spaces.push_back(*__b++);
   3028                 else
   3029                 {
   3030                     __err |= ios_base::failbit;
   3031                     return false;
   3032                 }
   3033             }
   3034             // drop through
   3035         case money_base::none:
   3036             if (__p != 3)
   3037             {
   3038                 while (__b != __e && __ct.is(ctype_base::space, *__b))
   3039                     __spaces.push_back(*__b++);
   3040             }
   3041             break;
   3042         case money_base::sign:
   3043             if (__psn.size() + __nsn.size() > 0)
   3044             {
   3045                 if (__psn.size() == 0 || __nsn.size() == 0)
   3046                 {   // sign is optional
   3047                     if (__psn.size() > 0)
   3048                     {   // __nsn.size() == 0
   3049                         if (*__b == __psn[0])
   3050                         {
   3051                             ++__b;
   3052                             if (__psn.size() > 1)
   3053                                 __trailing_sign = &__psn;
   3054                         }
   3055                         else
   3056                             __neg = true;
   3057                     }
   3058                     else if (*__b == __nsn[0])  // __nsn.size() > 0 &&  __psn.size() == 0
   3059                     {
   3060                         ++__b;
   3061                         __neg = true;
   3062                         if (__nsn.size() > 1)
   3063                             __trailing_sign = &__nsn;
   3064                     }
   3065                 }
   3066                 else  // sign is required
   3067                 {
   3068                     if (*__b == __psn[0])
   3069                     {
   3070                         ++__b;
   3071                         if (__psn.size() > 1)
   3072                             __trailing_sign = &__psn;
   3073                     }
   3074                     else if (*__b == __nsn[0])
   3075                     {
   3076                         ++__b;
   3077                         __neg = true;
   3078                         if (__nsn.size() > 1)
   3079                             __trailing_sign = &__nsn;
   3080                     }
   3081                     else
   3082                     {
   3083                         __err |= ios_base::failbit;
   3084                         return false;
   3085                     }
   3086                 }
   3087             }
   3088             break;
   3089         case money_base::symbol:
   3090             {
   3091             bool __more_needed = __trailing_sign ||
   3092                                  (__p < 2)       ||
   3093                                  (__p == 2 && __pat.field[3] != static_cast<char>(money_base::none));
   3094             bool __sb = (__flags & ios_base::showbase) != 0;
   3095             if (__sb || __more_needed)
   3096             {
   3097                 typename string_type::const_iterator __sym_space_end = __sym.begin();
   3098                 if (__p > 0 && (__pat.field[__p - 1] == money_base::none ||
   3099                                 __pat.field[__p - 1] == money_base::space)) {
   3100                     // Match spaces we've already read against spaces at
   3101                     // the beginning of __sym.
   3102                     while (__sym_space_end != __sym.end() &&
   3103                            __ct.is(ctype_base::space, *__sym_space_end))
   3104                         ++__sym_space_end;
   3105                     const size_t __num_spaces = __sym_space_end - __sym.begin();
   3106                     if (__num_spaces > __spaces.size() ||
   3107                         !equal(__spaces.end() - __num_spaces, __spaces.end(),
   3108                                __sym.begin())) {
   3109                         // No match. Put __sym_space_end back at the
   3110                         // beginning of __sym, which will prevent a
   3111                         // match in the next loop.
   3112                         __sym_space_end = __sym.begin();
   3113                     }
   3114                 }
   3115                 typename string_type::const_iterator __sym_curr_char = __sym_space_end;
   3116                 while (__sym_curr_char != __sym.end() && __b != __e &&
   3117                        *__b == *__sym_curr_char) {
   3118                     ++__b;
   3119                     ++__sym_curr_char;
   3120                 }
   3121                 if (__sb && __sym_curr_char != __sym.end())
   3122                 {
   3123                     __err |= ios_base::failbit;
   3124                     return false;
   3125                 }
   3126             }
   3127             }
   3128             break;
   3129         case money_base::value:
   3130             {
   3131             unsigned __ng = 0;
   3132             for (; __b != __e; ++__b)
   3133             {
   3134                 char_type __c = *__b;
   3135                 if (__ct.is(ctype_base::digit, __c))
   3136                 {
   3137                     if (__wn == __we)
   3138                         __double_or_nothing(__wb, __wn, __we);
   3139                     *__wn++ = __c;
   3140                     ++__ng;
   3141                 }
   3142                 else if (__grp.size() > 0 && __ng > 0 && __c == __ts)
   3143                 {
   3144                     if (__gn == __ge)
   3145                         __double_or_nothing(__gb, __gn, __ge);
   3146                     *__gn++ = __ng;
   3147                     __ng = 0;
   3148                 }
   3149                 else
   3150                     break;
   3151             }
   3152             if (__gb.get() != __gn && __ng > 0)
   3153             {
   3154                 if (__gn == __ge)
   3155                     __double_or_nothing(__gb, __gn, __ge);
   3156                 *__gn++ = __ng;
   3157             }
   3158             if (__fd > 0)
   3159             {
   3160                 if (__b == __e || *__b != __dp)
   3161                 {
   3162                     __err |= ios_base::failbit;
   3163                     return false;
   3164                 }
   3165                 for (++__b; __fd > 0; --__fd, ++__b)
   3166                 {
   3167                     if (__b == __e || !__ct.is(ctype_base::digit, *__b))
   3168                     {
   3169                         __err |= ios_base::failbit;
   3170                         return false;
   3171                     }
   3172                     if (__wn == __we)
   3173                         __double_or_nothing(__wb, __wn, __we);
   3174                     *__wn++ = *__b;
   3175                 }
   3176             }
   3177             if (__wn == __wb.get())
   3178             {
   3179                 __err |= ios_base::failbit;
   3180                 return false;
   3181             }
   3182             }
   3183             break;
   3184         }
   3185     }
   3186     if (__trailing_sign)
   3187     {
   3188         for (unsigned __i = 1; __i < __trailing_sign->size(); ++__i, ++__b)
   3189         {
   3190             if (__b == __e || *__b != (*__trailing_sign)[__i])
   3191             {
   3192                 __err |= ios_base::failbit;
   3193                 return false;
   3194             }
   3195         }
   3196     }
   3197     if (__gb.get() != __gn)
   3198     {
   3199         ios_base::iostate __et = ios_base::goodbit;
   3200         __check_grouping(__grp, __gb.get(), __gn, __et);
   3201         if (__et)
   3202         {
   3203             __err |= ios_base::failbit;
   3204             return false;
   3205         }
   3206     }
   3207     return true;
   3208 }
   3209 
   3210 template <class _CharT, class _InputIterator>
   3211 _InputIterator
   3212 money_get<_CharT, _InputIterator>::do_get(iter_type __b, iter_type __e,
   3213                                           bool __intl, ios_base& __iob,
   3214                                           ios_base::iostate& __err,
   3215                                           long double& __v) const
   3216 {
   3217     const int __bz = 100;
   3218     char_type __wbuf[__bz];
   3219     unique_ptr<char_type, void(*)(void*)> __wb(__wbuf, __do_nothing);
   3220     char_type* __wn;
   3221     char_type* __we = __wbuf + __bz;
   3222     locale __loc = __iob.getloc();
   3223     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__loc);
   3224     bool __neg = false;
   3225     if (__do_get(__b, __e, __intl, __loc, __iob.flags(), __err, __neg, __ct,
   3226                  __wb, __wn, __we))
   3227     {
   3228         const char __src[] = "0123456789";
   3229         char_type __atoms[sizeof(__src)-1];
   3230         __ct.widen(__src, __src + (sizeof(__src)-1), __atoms);
   3231         char __nbuf[__bz];
   3232         char* __nc = __nbuf;
   3233         unique_ptr<char, void(*)(void*)> __h(0, free);
   3234         if (__wn - __wb.get() > __bz-2)
   3235         {
   3236             __h.reset((char*)malloc(static_cast<size_t>(__wn - __wb.get() + 2)));
   3237             if (__h.get() == 0)
   3238                 __throw_bad_alloc();
   3239             __nc = __h.get();
   3240         }
   3241         if (__neg)
   3242             *__nc++ = '-';
   3243         for (const char_type* __w = __wb.get(); __w < __wn; ++__w, ++__nc)
   3244             *__nc = __src[find(__atoms, _VSTD::end(__atoms), *__w) - __atoms];
   3245         *__nc = char();
   3246         if (sscanf(__nbuf, "%Lf", &__v) != 1)
   3247             __throw_runtime_error("money_get error");
   3248     }
   3249     if (__b == __e)
   3250         __err |= ios_base::eofbit;
   3251     return __b;
   3252 }
   3253 
   3254 template <class _CharT, class _InputIterator>
   3255 _InputIterator
   3256 money_get<_CharT, _InputIterator>::do_get(iter_type __b, iter_type __e,
   3257                                           bool __intl, ios_base& __iob,
   3258                                           ios_base::iostate& __err,
   3259                                           string_type& __v) const
   3260 {
   3261     const int __bz = 100;
   3262     char_type __wbuf[__bz];
   3263     unique_ptr<char_type, void(*)(void*)> __wb(__wbuf, __do_nothing);
   3264     char_type* __wn;
   3265     char_type* __we = __wbuf + __bz;
   3266     locale __loc = __iob.getloc();
   3267     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__loc);
   3268     bool __neg = false;
   3269     if (__do_get(__b, __e, __intl, __loc, __iob.flags(), __err, __neg, __ct,
   3270                  __wb, __wn, __we))
   3271     {
   3272         __v.clear();
   3273         if (__neg)
   3274             __v.push_back(__ct.widen('-'));
   3275         char_type __z = __ct.widen('0');
   3276         char_type* __w;
   3277         for (__w = __wb.get(); __w < __wn-1; ++__w)
   3278             if (*__w != __z)
   3279                 break;
   3280         __v.append(__w, __wn);
   3281     }
   3282     if (__b == __e)
   3283         __err |= ios_base::eofbit;
   3284     return __b;
   3285 }
   3286 
   3287 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS money_get<char>)
   3288 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS money_get<wchar_t>)
   3289 
   3290 // money_put
   3291 
   3292 template <class _CharT>
   3293 class __money_put
   3294 {
   3295 protected:
   3296     typedef _CharT                  char_type;
   3297     typedef basic_string<char_type> string_type;
   3298 
   3299     _LIBCPP_ALWAYS_INLINE __money_put() {}
   3300 
   3301     static void __gather_info(bool __intl, bool __neg, const locale& __loc,
   3302                               money_base::pattern& __pat, char_type& __dp,
   3303                               char_type& __ts, string& __grp,
   3304                               string_type& __sym, string_type& __sn,
   3305                               int& __fd);
   3306     static void __format(char_type* __mb, char_type*& __mi, char_type*& __me,
   3307                          ios_base::fmtflags __flags,
   3308                          const char_type* __db, const char_type* __de,
   3309                          const ctype<char_type>& __ct, bool __neg,
   3310                          const money_base::pattern& __pat, char_type __dp,
   3311                          char_type __ts, const string& __grp,
   3312                          const string_type& __sym, const string_type& __sn,
   3313                          int __fd);
   3314 };
   3315 
   3316 template <class _CharT>
   3317 void
   3318 __money_put<_CharT>::__gather_info(bool __intl, bool __neg, const locale& __loc,
   3319                                    money_base::pattern& __pat, char_type& __dp,
   3320                                    char_type& __ts, string& __grp,
   3321                                    string_type& __sym, string_type& __sn,
   3322                                    int& __fd)
   3323 {
   3324     if (__intl)
   3325     {
   3326         const moneypunct<char_type, true>& __mp =
   3327             use_facet<moneypunct<char_type, true> >(__loc);
   3328         if (__neg)
   3329         {
   3330             __pat = __mp.neg_format();
   3331             __sn = __mp.negative_sign();
   3332         }
   3333         else
   3334         {
   3335             __pat = __mp.pos_format();
   3336             __sn = __mp.positive_sign();
   3337         }
   3338         __dp = __mp.decimal_point();
   3339         __ts = __mp.thousands_sep();
   3340         __grp = __mp.grouping();
   3341         __sym = __mp.curr_symbol();
   3342         __fd = __mp.frac_digits();
   3343     }
   3344     else
   3345     {
   3346         const moneypunct<char_type, false>& __mp =
   3347             use_facet<moneypunct<char_type, false> >(__loc);
   3348         if (__neg)
   3349         {
   3350             __pat = __mp.neg_format();
   3351             __sn = __mp.negative_sign();
   3352         }
   3353         else
   3354         {
   3355             __pat = __mp.pos_format();
   3356             __sn = __mp.positive_sign();
   3357         }
   3358         __dp = __mp.decimal_point();
   3359         __ts = __mp.thousands_sep();
   3360         __grp = __mp.grouping();
   3361         __sym = __mp.curr_symbol();
   3362         __fd = __mp.frac_digits();
   3363     }
   3364 }
   3365 
   3366 template <class _CharT>
   3367 void
   3368 __money_put<_CharT>::__format(char_type* __mb, char_type*& __mi, char_type*& __me,
   3369                               ios_base::fmtflags __flags,
   3370                               const char_type* __db, const char_type* __de,
   3371                               const ctype<char_type>& __ct, bool __neg,
   3372                               const money_base::pattern& __pat, char_type __dp,
   3373                               char_type __ts, const string& __grp,
   3374                               const string_type& __sym, const string_type& __sn,
   3375                               int __fd)
   3376 {
   3377     __me = __mb;
   3378     for (unsigned __p = 0; __p < 4; ++__p)
   3379     {
   3380         switch (__pat.field[__p])
   3381         {
   3382         case money_base::none:
   3383             __mi = __me;
   3384             break;
   3385         case money_base::space:
   3386             __mi = __me;
   3387             *__me++ = __ct.widen(' ');
   3388             break;
   3389         case money_base::sign:
   3390             if (!__sn.empty())
   3391                 *__me++ = __sn[0];
   3392             break;
   3393         case money_base::symbol:
   3394             if (!__sym.empty() && (__flags & ios_base::showbase))
   3395                 __me = _VSTD::copy(__sym.begin(), __sym.end(), __me);
   3396             break;
   3397         case money_base::value:
   3398             {
   3399             // remember start of value so we can reverse it
   3400             char_type* __t = __me;
   3401             // find beginning of digits
   3402             if (__neg)
   3403                 ++__db;
   3404             // find end of digits
   3405             const char_type* __d;
   3406             for (__d = __db; __d < __de; ++__d)
   3407                 if (!__ct.is(ctype_base::digit, *__d))
   3408                     break;
   3409             // print fractional part
   3410             if (__fd > 0)
   3411             {
   3412                 int __f;
   3413                 for (__f = __fd; __d > __db && __f > 0; --__f)
   3414                     *__me++ = *--__d;
   3415                 char_type __z = __f > 0 ? __ct.widen('0') : char_type();
   3416                 for (; __f > 0; --__f)
   3417                     *__me++ = __z;
   3418                 *__me++ = __dp;
   3419             }
   3420             // print units part
   3421             if (__d == __db)
   3422             {
   3423                 *__me++ = __ct.widen('0');
   3424             }
   3425             else
   3426             {
   3427                 unsigned __ng = 0;
   3428                 unsigned __ig = 0;
   3429                 unsigned __gl = __grp.empty() ? numeric_limits<unsigned>::max()
   3430                                               : static_cast<unsigned>(__grp[__ig]);
   3431                 while (__d != __db)
   3432                 {
   3433                     if (__ng == __gl)
   3434                     {
   3435                         *__me++ = __ts;
   3436                         __ng = 0;
   3437                         if (++__ig < __grp.size())
   3438                             __gl = __grp[__ig] == numeric_limits<char>::max() ?
   3439                                         numeric_limits<unsigned>::max() :
   3440                                         static_cast<unsigned>(__grp[__ig]);
   3441                     }
   3442                     *__me++ = *--__d;
   3443                     ++__ng;
   3444                 }
   3445             }
   3446             // reverse it
   3447             reverse(__t, __me);
   3448             }
   3449             break;
   3450         }
   3451     }
   3452     // print rest of sign, if any
   3453     if (__sn.size() > 1)
   3454         __me = _VSTD::copy(__sn.begin()+1, __sn.end(), __me);
   3455     // set alignment
   3456     if ((__flags & ios_base::adjustfield) == ios_base::left)
   3457         __mi = __me;
   3458     else if ((__flags & ios_base::adjustfield) != ios_base::internal)
   3459         __mi = __mb;
   3460 }
   3461 
   3462 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS __money_put<char>)
   3463 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS __money_put<wchar_t>)
   3464 
   3465 template <class _CharT, class _OutputIterator = ostreambuf_iterator<_CharT> >
   3466 class _LIBCPP_TYPE_VIS_ONLY money_put
   3467     : public locale::facet,
   3468       private __money_put<_CharT>
   3469 {
   3470 public:
   3471     typedef _CharT                  char_type;
   3472     typedef _OutputIterator         iter_type;
   3473     typedef basic_string<char_type> string_type;
   3474 
   3475     _LIBCPP_ALWAYS_INLINE
   3476     explicit money_put(size_t __refs = 0)
   3477         : locale::facet(__refs) {}
   3478 
   3479     _LIBCPP_ALWAYS_INLINE
   3480     iter_type put(iter_type __s, bool __intl, ios_base& __iob, char_type __fl,
   3481                   long double __units) const
   3482     {
   3483         return do_put(__s, __intl, __iob, __fl, __units);
   3484     }
   3485 
   3486     _LIBCPP_ALWAYS_INLINE
   3487     iter_type put(iter_type __s, bool __intl, ios_base& __iob, char_type __fl,
   3488                   const string_type& __digits) const
   3489     {
   3490         return do_put(__s, __intl, __iob, __fl, __digits);
   3491     }
   3492 
   3493     static locale::id id;
   3494 
   3495 protected:
   3496     _LIBCPP_ALWAYS_INLINE
   3497     ~money_put() {}
   3498 
   3499     virtual iter_type do_put(iter_type __s, bool __intl, ios_base& __iob,
   3500                              char_type __fl, long double __units) const;
   3501     virtual iter_type do_put(iter_type __s, bool __intl, ios_base& __iob,
   3502                              char_type __fl, const string_type& __digits) const;
   3503 };
   3504 
   3505 template <class _CharT, class _OutputIterator>
   3506 locale::id
   3507 money_put<_CharT, _OutputIterator>::id;
   3508 
   3509 template <class _CharT, class _OutputIterator>
   3510 _OutputIterator
   3511 money_put<_CharT, _OutputIterator>::do_put(iter_type __s, bool __intl,
   3512                                            ios_base& __iob, char_type __fl,
   3513                                            long double __units) const
   3514 {
   3515     // convert to char
   3516     const size_t __bs = 100;
   3517     char __buf[__bs];
   3518     char* __bb = __buf;
   3519     char_type __digits[__bs];
   3520     char_type* __db = __digits;
   3521     size_t __n = static_cast<size_t>(snprintf(__bb, __bs, "%.0Lf", __units));
   3522     unique_ptr<char, void(*)(void*)> __hn(0, free);
   3523     unique_ptr<char_type, void(*)(void*)> __hd(0, free);
   3524     // secure memory for digit storage
   3525     if (__n > __bs-1)
   3526     {
   3527 #ifdef _LIBCPP_LOCALE__L_EXTENSIONS
   3528         __n = static_cast<size_t>(asprintf_l(&__bb, _LIBCPP_GET_C_LOCALE, "%.0Lf", __units));
   3529 #else
   3530         __n = __asprintf_l(&__bb, __cloc(), "%.0Lf", __units);
   3531 #endif
   3532         if (__bb == 0)
   3533             __throw_bad_alloc();
   3534         __hn.reset(__bb);
   3535         __hd.reset((char_type*)malloc(__n * sizeof(char_type)));
   3536         if (__hd == nullptr)
   3537             __throw_bad_alloc();
   3538         __db = __hd.get();
   3539     }
   3540     // gather info
   3541     locale __loc = __iob.getloc();
   3542     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__loc);
   3543     __ct.widen(__bb, __bb + __n, __db);
   3544     bool __neg = __n > 0 && __bb[0] == '-';
   3545     money_base::pattern __pat;
   3546     char_type __dp;
   3547     char_type __ts;
   3548     string __grp;
   3549     string_type __sym;
   3550     string_type __sn;
   3551     int __fd;
   3552     this->__gather_info(__intl, __neg, __loc, __pat, __dp, __ts, __grp, __sym, __sn, __fd);
   3553     // secure memory for formatting
   3554     char_type __mbuf[__bs];
   3555     char_type* __mb = __mbuf;
   3556     unique_ptr<char_type, void(*)(void*)> __hw(0, free);
   3557     size_t __exn = static_cast<int>(__n) > __fd ?
   3558                    (__n - static_cast<size_t>(__fd)) * 2 + __sn.size() +
   3559                     __sym.size() + static_cast<size_t>(__fd) + 1
   3560                  : __sn.size() + __sym.size() + static_cast<size_t>(__fd) + 2;
   3561     if (__exn > __bs)
   3562     {
   3563         __hw.reset((char_type*)malloc(__exn * sizeof(char_type)));
   3564         __mb = __hw.get();
   3565         if (__mb == 0)
   3566             __throw_bad_alloc();
   3567     }
   3568     // format
   3569     char_type* __mi;
   3570     char_type* __me;
   3571     this->__format(__mb, __mi, __me, __iob.flags(),
   3572                    __db, __db + __n, __ct,
   3573                    __neg, __pat, __dp, __ts, __grp, __sym, __sn, __fd);
   3574     return __pad_and_output(__s, __mb, __mi, __me, __iob, __fl);
   3575 }
   3576 
   3577 template <class _CharT, class _OutputIterator>
   3578 _OutputIterator
   3579 money_put<_CharT, _OutputIterator>::do_put(iter_type __s, bool __intl,
   3580                                            ios_base& __iob, char_type __fl,
   3581                                            const string_type& __digits) const
   3582 {
   3583     // gather info
   3584     locale __loc = __iob.getloc();
   3585     const ctype<char_type>& __ct = use_facet<ctype<char_type> >(__loc);
   3586     bool __neg = __digits.size() > 0 && __digits[0] == __ct.widen('-');
   3587     money_base::pattern __pat;
   3588     char_type __dp;
   3589     char_type __ts;
   3590     string __grp;
   3591     string_type __sym;
   3592     string_type __sn;
   3593     int __fd;
   3594     this->__gather_info(__intl, __neg, __loc, __pat, __dp, __ts, __grp, __sym, __sn, __fd);
   3595     // secure memory for formatting
   3596     char_type __mbuf[100];
   3597     char_type* __mb = __mbuf;
   3598     unique_ptr<char_type, void(*)(void*)> __h(0, free);
   3599     size_t __exn = static_cast<int>(__digits.size()) > __fd ?
   3600                    (__digits.size() - static_cast<size_t>(__fd)) * 2 +
   3601                     __sn.size() + __sym.size() + static_cast<size_t>(__fd) + 1
   3602                  : __sn.size() + __sym.size() + static_cast<size_t>(__fd) + 2;
   3603     if (__exn > 100)
   3604     {
   3605         __h.reset((char_type*)malloc(__exn * sizeof(char_type)));
   3606         __mb = __h.get();
   3607         if (__mb == 0)
   3608             __throw_bad_alloc();
   3609     }
   3610     // format
   3611     char_type* __mi;
   3612     char_type* __me;
   3613     this->__format(__mb, __mi, __me, __iob.flags(),
   3614                    __digits.data(), __digits.data() + __digits.size(), __ct,
   3615                    __neg, __pat, __dp, __ts, __grp, __sym, __sn, __fd);
   3616     return __pad_and_output(__s, __mb, __mi, __me, __iob, __fl);
   3617 }
   3618 
   3619 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS money_put<char>)
   3620 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS money_put<wchar_t>)
   3621 
   3622 // messages
   3623 
   3624 class _LIBCPP_TYPE_VIS messages_base
   3625 {
   3626 public:
   3627     typedef ptrdiff_t catalog;
   3628 
   3629     _LIBCPP_ALWAYS_INLINE messages_base() {}
   3630 };
   3631 
   3632 template <class _CharT>
   3633 class _LIBCPP_TYPE_VIS_ONLY messages
   3634     : public locale::facet,
   3635       public messages_base
   3636 {
   3637 public:
   3638     typedef _CharT               char_type;
   3639     typedef basic_string<_CharT> string_type;
   3640 
   3641     _LIBCPP_ALWAYS_INLINE
   3642     explicit messages(size_t __refs = 0)
   3643         : locale::facet(__refs) {}
   3644 
   3645     _LIBCPP_ALWAYS_INLINE
   3646     catalog open(const basic_string<char>& __nm, const locale& __loc) const
   3647     {
   3648         return do_open(__nm, __loc);
   3649     }
   3650 
   3651     _LIBCPP_ALWAYS_INLINE
   3652     string_type get(catalog __c, int __set, int __msgid,
   3653                     const string_type& __dflt) const
   3654     {
   3655         return do_get(__c, __set, __msgid, __dflt);
   3656     }
   3657 
   3658     _LIBCPP_ALWAYS_INLINE
   3659     void close(catalog __c) const
   3660     {
   3661         do_close(__c);
   3662     }
   3663 
   3664     static locale::id id;
   3665 
   3666 protected:
   3667     _LIBCPP_ALWAYS_INLINE
   3668     ~messages() {}
   3669 
   3670     virtual catalog do_open(const basic_string<char>&, const locale&) const;
   3671     virtual string_type do_get(catalog, int __set, int __msgid,
   3672                                const string_type& __dflt) const;
   3673     virtual void do_close(catalog) const;
   3674 };
   3675 
   3676 template <class _CharT>
   3677 locale::id
   3678 messages<_CharT>::id;
   3679 
   3680 template <class _CharT>
   3681 typename messages<_CharT>::catalog
   3682 messages<_CharT>::do_open(const basic_string<char>& __nm, const locale&) const
   3683 {
   3684 #if defined(_WIN32) || defined(__ANDROID__) || defined(_NEWLIB_VERSION)
   3685     return -1;
   3686 #else // _WIN32 || __ANDROID__
   3687     catalog __cat = (catalog)catopen(__nm.c_str(), NL_CAT_LOCALE);
   3688     if (__cat != -1)
   3689         __cat = static_cast<catalog>((static_cast<size_t>(__cat) >> 1));
   3690     return __cat;
   3691 #endif // _WIN32 || __ANDROID__
   3692 }
   3693 
   3694 template <class _CharT>
   3695 typename messages<_CharT>::string_type
   3696 messages<_CharT>::do_get(catalog __c, int __set, int __msgid,
   3697                          const string_type& __dflt) const
   3698 {
   3699 #if defined(_WIN32) || defined(__ANDROID__) || defined(_NEWLIB_VERSION)
   3700     return __dflt;
   3701 #else // _WIN32
   3702     string __ndflt;
   3703     __narrow_to_utf8<sizeof(char_type)*__CHAR_BIT__>()(back_inserter(__ndflt),
   3704                                                        __dflt.c_str(),
   3705                                                        __dflt.c_str() + __dflt.size());
   3706     if (__c != -1)
   3707         __c <<= 1;
   3708     nl_catd __cat = (nl_catd)__c;
   3709     char* __n = catgets(__cat, __set, __msgid, __ndflt.c_str());
   3710     string_type __w;
   3711     __widen_from_utf8<sizeof(char_type)*__CHAR_BIT__>()(back_inserter(__w),
   3712                                                         __n, __n + strlen(__n));
   3713     return __w;
   3714 #endif // _WIN32
   3715 }
   3716 
   3717 template <class _CharT>
   3718 void
   3719 messages<_CharT>::do_close(catalog __c) const
   3720 {
   3721 #if !defined(_WIN32) && !defined(__ANDROID__) && !defined(_NEWLIB_VERSION)
   3722     if (__c != -1)
   3723         __c <<= 1;
   3724     nl_catd __cat = (nl_catd)__c;
   3725     catclose(__cat);
   3726 #endif // !_WIN32
   3727 }
   3728 
   3729 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS messages<char>)
   3730 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS messages<wchar_t>)
   3731 
   3732 template <class _CharT>
   3733 class _LIBCPP_TYPE_VIS_ONLY messages_byname
   3734     : public messages<_CharT>
   3735 {
   3736 public:
   3737     typedef messages_base::catalog catalog;
   3738     typedef basic_string<_CharT> string_type;
   3739 
   3740     _LIBCPP_ALWAYS_INLINE
   3741     explicit messages_byname(const char*, size_t __refs = 0)
   3742         : messages<_CharT>(__refs) {}
   3743 
   3744     _LIBCPP_ALWAYS_INLINE
   3745     explicit messages_byname(const string&, size_t __refs = 0)
   3746         : messages<_CharT>(__refs) {}
   3747 
   3748 protected:
   3749     _LIBCPP_ALWAYS_INLINE
   3750     ~messages_byname() {}
   3751 };
   3752 
   3753 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS messages_byname<char>)
   3754 _LIBCPP_EXTERN_TEMPLATE2(class _LIBCPP_TYPE_VIS messages_byname<wchar_t>)
   3755 
   3756 template<class _Codecvt, class _Elem = wchar_t,
   3757          class _Wide_alloc = allocator<_Elem>,
   3758          class _Byte_alloc = allocator<char> >
   3759 class _LIBCPP_TYPE_VIS_ONLY wstring_convert
   3760 {
   3761 public:
   3762     typedef basic_string<char, char_traits<char>, _Byte_alloc>   byte_string;
   3763     typedef basic_string<_Elem, char_traits<_Elem>, _Wide_alloc> wide_string;
   3764     typedef typename _Codecvt::state_type                        state_type;
   3765     typedef typename wide_string::traits_type::int_type          int_type;
   3766 
   3767 private:
   3768     byte_string __byte_err_string_;
   3769     wide_string __wide_err_string_;
   3770     _Codecvt* __cvtptr_;
   3771     state_type __cvtstate_;
   3772     size_t __cvtcount_;
   3773 
   3774     wstring_convert(const wstring_convert& __wc);
   3775     wstring_convert& operator=(const wstring_convert& __wc);
   3776 public:
   3777     _LIBCPP_EXPLICIT_AFTER_CXX11 wstring_convert(_Codecvt* __pcvt = new _Codecvt);
   3778     wstring_convert(_Codecvt* __pcvt, state_type __state);
   3779     _LIBCPP_EXPLICIT_AFTER_CXX11 wstring_convert(const byte_string& __byte_err,
   3780                     const wide_string& __wide_err = wide_string());
   3781 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
   3782     wstring_convert(wstring_convert&& __wc);
   3783 #endif
   3784     ~wstring_convert();
   3785 
   3786     _LIBCPP_ALWAYS_INLINE
   3787     wide_string from_bytes(char __byte)
   3788         {return from_bytes(&__byte, &__byte+1);}
   3789     _LIBCPP_ALWAYS_INLINE
   3790     wide_string from_bytes(const char* __ptr)
   3791         {return from_bytes(__ptr, __ptr + char_traits<char>::length(__ptr));}
   3792     _LIBCPP_ALWAYS_INLINE
   3793     wide_string from_bytes(const byte_string& __str)
   3794         {return from_bytes(__str.data(), __str.data() + __str.size());}
   3795     wide_string from_bytes(const char* __first, const char* __last);
   3796 
   3797     _LIBCPP_ALWAYS_INLINE
   3798     byte_string to_bytes(_Elem __wchar)
   3799         {return to_bytes(&__wchar, &__wchar+1);}
   3800     _LIBCPP_ALWAYS_INLINE
   3801     byte_string to_bytes(const _Elem* __wptr)
   3802         {return to_bytes(__wptr, __wptr + char_traits<_Elem>::length(__wptr));}
   3803     _LIBCPP_ALWAYS_INLINE
   3804     byte_string to_bytes(const wide_string& __wstr)
   3805         {return to_bytes(__wstr.data(), __wstr.data() + __wstr.size());}
   3806     byte_string to_bytes(const _Elem* __first, const _Elem* __last);
   3807 
   3808     _LIBCPP_ALWAYS_INLINE
   3809     size_t converted() const _NOEXCEPT {return __cvtcount_;}
   3810     _LIBCPP_ALWAYS_INLINE
   3811     state_type state() const {return __cvtstate_;}
   3812 };
   3813 
   3814 template<class _Codecvt, class _Elem, class _Wide_alloc, class _Byte_alloc>
   3815 inline _LIBCPP_ALWAYS_INLINE
   3816 wstring_convert<_Codecvt, _Elem, _Wide_alloc, _Byte_alloc>::
   3817     wstring_convert(_Codecvt* __pcvt)
   3818         : __cvtptr_(__pcvt), __cvtstate_(), __cvtcount_(0)
   3819 {
   3820 }
   3821 
   3822 template<class _Codecvt, class _Elem, class _Wide_alloc, class _Byte_alloc>
   3823 inline _LIBCPP_ALWAYS_INLINE
   3824 wstring_convert<_Codecvt, _Elem, _Wide_alloc, _Byte_alloc>::
   3825     wstring_convert(_Codecvt* __pcvt, state_type __state)
   3826         : __cvtptr_(__pcvt), __cvtstate_(__state), __cvtcount_(0)
   3827 {
   3828 }
   3829 
   3830 template<class _Codecvt, class _Elem, class _Wide_alloc, class _Byte_alloc>
   3831 wstring_convert<_Codecvt, _Elem, _Wide_alloc, _Byte_alloc>::
   3832     wstring_convert(const byte_string& __byte_err, const wide_string& __wide_err)
   3833         : __byte_err_string_(__byte_err), __wide_err_string_(__wide_err),
   3834           __cvtstate_(), __cvtcount_(0)
   3835 {
   3836     __cvtptr_ = new _Codecvt;
   3837 }
   3838 
   3839 #ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
   3840 
   3841 template<class _Codecvt, class _Elem, class _Wide_alloc, class _Byte_alloc>
   3842 inline _LIBCPP_ALWAYS_INLINE
   3843 wstring_convert<_Codecvt, _Elem, _Wide_alloc, _Byte_alloc>::
   3844     wstring_convert(wstring_convert&& __wc)
   3845         : __byte_err_string_(_VSTD::move(__wc.__byte_err_string_)),
   3846           __wide_err_string_(_VSTD::move(__wc.__wide_err_string_)),
   3847           __cvtptr_(__wc.__cvtptr_),
   3848           __cvtstate_(__wc.__cvtstate_), __cvtcount_(__wc.__cvtstate_)
   3849 {
   3850     __wc.__cvtptr_ = nullptr;
   3851 }
   3852 
   3853 #endif  // _LIBCPP_HAS_NO_RVALUE_REFERENCES
   3854 
   3855 template<class _Codecvt, class _Elem, class _Wide_alloc, class _Byte_alloc>
   3856 wstring_convert<_Codecvt, _Elem, _Wide_alloc, _Byte_alloc>::~wstring_convert()
   3857 {
   3858     delete __cvtptr_;
   3859 }
   3860 
   3861 template<class _Codecvt, class _Elem, class _Wide_alloc, class _Byte_alloc>
   3862 typename wstring_convert<_Codecvt, _Elem, _Wide_alloc, _Byte_alloc>::wide_string
   3863 wstring_convert<_Codecvt, _Elem, _Wide_alloc, _Byte_alloc>::
   3864     from_bytes(const char* __frm, const char* __frm_end)
   3865 {
   3866     __cvtcount_ = 0;
   3867     if (__cvtptr_ != nullptr)
   3868     {
   3869         wide_string __ws(2*(__frm_end - __frm), _Elem());
   3870         if (__frm != __frm_end)
   3871             __ws.resize(__ws.capacity());
   3872         codecvt_base::result __r = codecvt_base::ok;
   3873         state_type __st = __cvtstate_;
   3874         if (__frm != __frm_end)
   3875         {
   3876             _Elem* __to = &__ws[0];
   3877             _Elem* __to_end = __to + __ws.size();
   3878             const char* __frm_nxt;
   3879             do
   3880             {
   3881                 _Elem* __to_nxt;
   3882                 __r = __cvtptr_->in(__st, __frm, __frm_end, __frm_nxt,
   3883                                           __to, __to_end, __to_nxt);
   3884                 __cvtcount_ += __frm_nxt - __frm;
   3885                 if (__frm_nxt == __frm)
   3886                 {
   3887                     __r = codecvt_base::error;
   3888                 }
   3889                 else if (__r == codecvt_base::noconv)
   3890                 {
   3891                     __ws.resize(__to - &__ws[0]);
   3892                     // This only gets executed if _Elem is char
   3893                     __ws.append((const _Elem*)__frm, (const _Elem*)__frm_end);
   3894                     __frm = __frm_nxt;
   3895                     __r = codecvt_base::ok;
   3896                 }
   3897                 else if (__r == codecvt_base::ok)
   3898                 {
   3899                     __ws.resize(__to_nxt - &__ws[0]);
   3900                     __frm = __frm_nxt;
   3901                 }
   3902                 else if (__r == codecvt_base::partial)
   3903                 {
   3904                     ptrdiff_t __s = __to_nxt - &__ws[0];
   3905                     __ws.resize(2 * __s);
   3906                     __to = &__ws[0] + __s;
   3907                     __to_end = &__ws[0] + __ws.size();
   3908                     __frm = __frm_nxt;
   3909                 }
   3910             } while (__r == codecvt_base::partial && __frm_nxt < __frm_end);
   3911         }
   3912         if (__r == codecvt_base::ok)
   3913             return __ws;
   3914     }
   3915 #ifndef _LIBCPP_NO_EXCEPTIONS
   3916     if (__wide_err_string_.empty())
   3917         throw range_error("wstring_convert: from_bytes error");
   3918 #endif  // _LIBCPP_NO_EXCEPTIONS
   3919     return __wide_err_string_;
   3920 }
   3921 
   3922 template<class _Codecvt, class _Elem, class _Wide_alloc, class _Byte_alloc>
   3923 typename wstring_convert<_Codecvt, _Elem, _Wide_alloc, _Byte_alloc>::byte_string
   3924 wstring_convert<_Codecvt, _Elem, _Wide_alloc, _Byte_alloc>::
   3925     to_bytes(const _Elem* __frm, const _Elem* __frm_end)
   3926 {
   3927     __cvtcount_ = 0;
   3928     if (__cvtptr_ != nullptr)
   3929     {
   3930         byte_string __bs(2*(__frm_end - __frm), char());
   3931         if (__frm != __frm_end)
   3932             __bs.resize(__bs.capacity());
   3933         codecvt_base::result __r = codecvt_base::ok;
   3934         state_type __st = __cvtstate_;
   3935         if (__frm != __frm_end)
   3936         {
   3937             char* __to = &__bs[0];
   3938             char* __to_end = __to + __bs.size();
   3939             const _Elem* __frm_nxt;
   3940             do
   3941             {
   3942                 char* __to_nxt;
   3943                 __r = __cvtptr_->out(__st, __frm, __frm_end, __frm_nxt,
   3944                                            __to, __to_end, __to_nxt);
   3945                 __cvtcount_ += __frm_nxt - __frm;
   3946                 if (__frm_nxt == __frm)
   3947                 {
   3948                     __r = codecvt_base::error;
   3949                 }
   3950                 else if (__r == codecvt_base::noconv)
   3951                 {
   3952                     __bs.resize(__to - &__bs[0]);
   3953                     // This only gets executed if _Elem is char
   3954                     __bs.append((const char*)__frm, (const char*)__frm_end);
   3955                     __frm = __frm_nxt;
   3956                     __r = codecvt_base::ok;
   3957                 }
   3958                 else if (__r == codecvt_base::ok)
   3959                 {
   3960                     __bs.resize(__to_nxt - &__bs[0]);
   3961                     __frm = __frm_nxt;
   3962                 }
   3963                 else if (__r == codecvt_base::partial)
   3964                 {
   3965                     ptrdiff_t __s = __to_nxt - &__bs[0];
   3966                     __bs.resize(2 * __s);
   3967                     __to = &__bs[0] + __s;
   3968                     __to_end = &__bs[0] + __bs.size();
   3969                     __frm = __frm_nxt;
   3970                 }
   3971             } while (__r == codecvt_base::partial && __frm_nxt < __frm_end);
   3972         }
   3973         if (__r == codecvt_base::ok)
   3974         {
   3975             size_t __s = __bs.size();
   3976             __bs.resize(__bs.capacity());
   3977             char* __to = &__bs[0] + __s;
   3978             char* __to_end = __to + __bs.size();
   3979             do
   3980             {
   3981                 char* __to_nxt;
   3982                 __r = __cvtptr_->unshift(__st, __to, __to_end, __to_nxt);
   3983                 if (__r == codecvt_base::noconv)
   3984                 {
   3985                     __bs.resize(__to - &__bs[0]);
   3986                     __r = codecvt_base::ok;
   3987                 }
   3988                 else if (__r == codecvt_base::ok)
   3989                 {
   3990                     __bs.resize(__to_nxt - &__bs[0]);
   3991                 }
   3992                 else if (__r == codecvt_base::partial)
   3993                 {
   3994                     ptrdiff_t __sp = __to_nxt - &__bs[0];
   3995                     __bs.resize(2 * __sp);
   3996                     __to = &__bs[0] + __sp;
   3997                     __to_end = &__bs[0] + __bs.size();
   3998                 }
   3999             } while (__r == codecvt_base::partial);
   4000             if (__r == codecvt_base::ok)
   4001                 return __bs;
   4002         }
   4003     }
   4004 #ifndef _LIBCPP_NO_EXCEPTIONS
   4005     if (__byte_err_string_.empty())
   4006         throw range_error("wstring_convert: to_bytes error");
   4007 #endif  // _LIBCPP_NO_EXCEPTIONS
   4008     return __byte_err_string_;
   4009 }
   4010 
   4011 template <class _Codecvt, class _Elem = wchar_t, class _Tr = char_traits<_Elem> >
   4012 class _LIBCPP_TYPE_VIS_ONLY wbuffer_convert
   4013     : public basic_streambuf<_Elem, _Tr>
   4014 {
   4015 public:
   4016     // types:
   4017     typedef _Elem                          char_type;
   4018     typedef _Tr                            traits_type;
   4019     typedef typename traits_type::int_type int_type;
   4020     typedef typename traits_type::pos_type pos_type;
   4021     typedef typename traits_type::off_type off_type;
   4022     typedef typename _Codecvt::state_type  state_type;
   4023 
   4024 private:
   4025     char*       __extbuf_;
   4026     const char* __extbufnext_;
   4027     const char* __extbufend_;
   4028     char __extbuf_min_[8];
   4029     size_t __ebs_;
   4030     char_type* __intbuf_;
   4031     size_t __ibs_;
   4032     streambuf* __bufptr_;
   4033     _Codecvt* __cv_;
   4034     state_type __st_;
   4035     ios_base::openmode __cm_;
   4036     bool __owns_eb_;
   4037     bool __owns_ib_;
   4038     bool __always_noconv_;
   4039 
   4040     wbuffer_convert(const wbuffer_convert&);
   4041     wbuffer_convert& operator=(const wbuffer_convert&);
   4042 public:
   4043     _LIBCPP_EXPLICIT_AFTER_CXX11 wbuffer_convert(streambuf* __bytebuf = 0, 
   4044             _Codecvt* __pcvt = new _Codecvt, state_type __state = state_type());
   4045     ~wbuffer_convert();
   4046 
   4047     _LIBCPP_INLINE_VISIBILITY
   4048     streambuf* rdbuf() const {return __bufptr_;}
   4049     _LIBCPP_INLINE_VISIBILITY
   4050     streambuf* rdbuf(streambuf* __bytebuf)
   4051     {
   4052         streambuf* __r = __bufptr_;
   4053         __bufptr_ = __bytebuf;
   4054         return __r;
   4055     }
   4056 
   4057     _LIBCPP_INLINE_VISIBILITY
   4058     state_type state() const {return __st_;}
   4059 
   4060 protected:
   4061     virtual int_type underflow();
   4062     virtual int_type pbackfail(int_type __c = traits_type::eof());
   4063     virtual int_type overflow (int_type __c = traits_type::eof());
   4064     virtual basic_streambuf<char_type, traits_type>* setbuf(char_type* __s,
   4065                                                             streamsize __n);
   4066     virtual pos_type seekoff(off_type __off, ios_base::seekdir __way,
   4067                              ios_base::openmode __wch = ios_base::in | ios_base::out);
   4068     virtual pos_type seekpos(pos_type __sp,
   4069                              ios_base::openmode __wch = ios_base::in | ios_base::out);
   4070     virtual int sync();
   4071 
   4072 private:
   4073     bool __read_mode();
   4074     void __write_mode();
   4075     wbuffer_convert* __close();
   4076 };
   4077 
   4078 template <class _Codecvt, class _Elem, class _Tr>
   4079 wbuffer_convert<_Codecvt, _Elem, _Tr>::
   4080     wbuffer_convert(streambuf* __bytebuf, _Codecvt* __pcvt, state_type __state)
   4081     : __extbuf_(0),
   4082       __extbufnext_(0),
   4083       __extbufend_(0),
   4084       __ebs_(0),
   4085       __intbuf_(0),
   4086       __ibs_(0),
   4087       __bufptr_(__bytebuf),
   4088       __cv_(__pcvt),
   4089       __st_(__state),
   4090       __cm_(0),
   4091       __owns_eb_(false),
   4092       __owns_ib_(false),
   4093       __always_noconv_(__cv_ ? __cv_->always_noconv() : false)
   4094 {
   4095     setbuf(0, 4096);
   4096 }
   4097 
   4098 template <class _Codecvt, class _Elem, class _Tr>
   4099 wbuffer_convert<_Codecvt, _Elem, _Tr>::~wbuffer_convert()
   4100 {
   4101     __close();
   4102     delete __cv_;
   4103     if (__owns_eb_)
   4104         delete [] __extbuf_;
   4105     if (__owns_ib_)
   4106         delete [] __intbuf_;
   4107 }
   4108 
   4109 template <class _Codecvt, class _Elem, class _Tr>
   4110 typename wbuffer_convert<_Codecvt, _Elem, _Tr>::int_type
   4111 wbuffer_convert<_Codecvt, _Elem, _Tr>::underflow()
   4112 {
   4113     if (__cv_ == 0 || __bufptr_ == 0)
   4114         return traits_type::eof();
   4115     bool __initial = __read_mode();
   4116     char_type __1buf;
   4117     if (this->gptr() == 0)
   4118         this->setg(&__1buf, &__1buf+1, &__1buf+1);
   4119     const size_t __unget_sz = __initial ? 0 : min<size_t>((this->egptr() - this->eback()) / 2, 4);
   4120     int_type __c = traits_type::eof();
   4121     if (this->gptr() == this->egptr())
   4122     {
   4123         memmove(this->eback(), this->egptr() - __unget_sz, __unget_sz * sizeof(char_type));
   4124         if (__always_noconv_)
   4125         {
   4126             streamsize __nmemb = static_cast<streamsize>(this->egptr() - this->eback() - __unget_sz);
   4127             __nmemb = __bufptr_->sgetn((char*)this->eback() + __unget_sz, __nmemb);
   4128             if (__nmemb != 0)
   4129             {
   4130                 this->setg(this->eback(),
   4131                            this->eback() + __unget_sz,
   4132                            this->eback() + __unget_sz + __nmemb);
   4133                 __c = *this->gptr();
   4134             }
   4135         }
   4136         else
   4137         {
   4138             memmove(__extbuf_, __extbufnext_, __extbufend_ - __extbufnext_);
   4139             __extbufnext_ = __extbuf_ + (__extbufend_ - __extbufnext_);
   4140             __extbufend_ = __extbuf_ + (__extbuf_ == __extbuf_min_ ? sizeof(__extbuf_min_) : __ebs_);
   4141             streamsize __nmemb = _VSTD::min(static_cast<streamsize>(this->egptr() - this->eback() - __unget_sz),
   4142                                  static_cast<streamsize>(__extbufend_ - __extbufnext_));
   4143             codecvt_base::result __r;
   4144             state_type __svs = __st_;
   4145             streamsize __nr = __bufptr_->sgetn(const_cast<char*>(__extbufnext_), __nmemb);
   4146             if (__nr != 0)
   4147             {
   4148                 __extbufend_ = __extbufnext_ + __nr;
   4149                 char_type*  __inext;
   4150                 __r = __cv_->in(__st_, __extbuf_, __extbufend_, __extbufnext_,
   4151                                        this->eback() + __unget_sz,
   4152                                        this->egptr(), __inext);
   4153                 if (__r == codecvt_base::noconv)
   4154                 {
   4155                     this->setg((char_type*)__extbuf_, (char_type*)__extbuf_, (char_type*)__extbufend_);
   4156                     __c = *this->gptr();
   4157                 }
   4158                 else if (__inext != this->eback() + __unget_sz)
   4159                 {
   4160                     this->setg(this->eback(), this->eback() + __unget_sz, __inext);
   4161                     __c = *this->gptr();
   4162                 }
   4163             }
   4164         }
   4165     }
   4166     else
   4167         __c = *this->gptr();
   4168     if (this->eback() == &__1buf)
   4169         this->setg(0, 0, 0);
   4170     return __c;
   4171 }
   4172 
   4173 template <class _Codecvt, class _Elem, class _Tr>
   4174 typename wbuffer_convert<_Codecvt, _Elem, _Tr>::int_type
   4175 wbuffer_convert<_Codecvt, _Elem, _Tr>::pbackfail(int_type __c)
   4176 {
   4177     if (__cv_ != 0 && __bufptr_ != 0 && this->eback() < this->gptr())
   4178     {
   4179         if (traits_type::eq_int_type(__c, traits_type::eof()))
   4180         {
   4181             this->gbump(-1);
   4182             return traits_type::not_eof(__c);
   4183         }
   4184         if (traits_type::eq(traits_type::to_char_type(__c), this->gptr()[-1]))
   4185         {
   4186             this->gbump(-1);
   4187             *this->gptr() = traits_type::to_char_type(__c);
   4188             return __c;
   4189         }
   4190     }
   4191     return traits_type::eof();
   4192 }
   4193 
   4194 template <class _Codecvt, class _Elem, class _Tr>
   4195 typename wbuffer_convert<_Codecvt, _Elem, _Tr>::int_type
   4196 wbuffer_convert<_Codecvt, _Elem, _Tr>::overflow(int_type __c)
   4197 {
   4198     if (__cv_ == 0 || __bufptr_ == 0)
   4199         return traits_type::eof();
   4200     __write_mode();
   4201     char_type __1buf;
   4202     char_type* __pb_save = this->pbase();
   4203     char_type* __epb_save = this->epptr();
   4204     if (!traits_type::eq_int_type(__c, traits_type::eof()))
   4205     {
   4206         if (this->pptr() == 0)
   4207             this->setp(&__1buf, &__1buf+1);
   4208         *this->pptr() = traits_type::to_char_type(__c);
   4209         this->pbump(1);
   4210     }
   4211     if (this->pptr() != this->pbase())
   4212     {
   4213         if (__always_noconv_)
   4214         {
   4215             streamsize __nmemb = static_cast<streamsize>(this->pptr() - this->pbase());
   4216             if (__bufptr_->sputn((const char*)this->pbase(), __nmemb) != __nmemb)
   4217                 return traits_type::eof();
   4218         }
   4219         else
   4220         {
   4221             char* __extbe = __extbuf_;
   4222             codecvt_base::result __r;
   4223             do
   4224             {
   4225                 const char_type* __e;
   4226                 __r = __cv_->out(__st_, this->pbase(), this->pptr(), __e,
   4227                                         __extbuf_, __extbuf_ + __ebs_, __extbe);
   4228                 if (__e == this->pbase())
   4229                     return traits_type::eof();
   4230                 if (__r == codecvt_base::noconv)
   4231                 {
   4232                     streamsize __nmemb = static_cast<size_t>(this->pptr() - this->pbase());
   4233                     if (__bufptr_->sputn((const char*)this->pbase(), __nmemb) != __nmemb)
   4234                         return traits_type::eof();
   4235                 }
   4236                 else if (__r == codecvt_base::ok || __r == codecvt_base::partial)
   4237                 {
   4238                     streamsize __nmemb = static_cast<size_t>(__extbe - __extbuf_);
   4239                     if (__bufptr_->sputn(__extbuf_, __nmemb) != __nmemb)
   4240                         return traits_type::eof();
   4241                     if (__r == codecvt_base::partial)
   4242                     {
   4243                         this->setp((char_type*)__e, this->pptr());
   4244                         this->pbump(this->epptr() - this->pbase());
   4245                     }
   4246                 }
   4247                 else
   4248                     return traits_type::eof();
   4249             } while (__r == codecvt_base::partial);
   4250         }
   4251         this->setp(__pb_save, __epb_save);
   4252     }
   4253     return traits_type::not_eof(__c);
   4254 }
   4255 
   4256 template <class _Codecvt, class _Elem, class _Tr>
   4257 basic_streambuf<_Elem, _Tr>*
   4258 wbuffer_convert<_Codecvt, _Elem, _Tr>::setbuf(char_type* __s, streamsize __n)
   4259 {
   4260     this->setg(0, 0, 0);
   4261     this->setp(0, 0);
   4262     if (__owns_eb_)
   4263         delete [] __extbuf_;
   4264     if (__owns_ib_)
   4265         delete [] __intbuf_;
   4266     __ebs_ = __n;
   4267     if (__ebs_ > sizeof(__extbuf_min_))
   4268     {
   4269         if (__always_noconv_ && __s)
   4270         {
   4271             __extbuf_ = (char*)__s;
   4272             __owns_eb_ = false;
   4273         }
   4274         else
   4275         {
   4276             __extbuf_ = new char[__ebs_];
   4277             __owns_eb_ = true;
   4278         }
   4279     }
   4280     else
   4281     {
   4282         __extbuf_ = __extbuf_min_;
   4283         __ebs_ = sizeof(__extbuf_min_);
   4284         __owns_eb_ = false;
   4285     }
   4286     if (!__always_noconv_)
   4287     {
   4288         __ibs_ = max<streamsize>(__n, sizeof(__extbuf_min_));
   4289         if (__s && __ibs_ >= sizeof(__extbuf_min_))
   4290         {
   4291             __intbuf_ = __s;
   4292             __owns_ib_ = false;
   4293         }
   4294         else
   4295         {
   4296             __intbuf_ = new char_type[__ibs_];
   4297             __owns_ib_ = true;
   4298         }
   4299     }
   4300     else
   4301     {
   4302         __ibs_ = 0;
   4303         __intbuf_ = 0;
   4304         __owns_ib_ = false;
   4305     }
   4306     return this;
   4307 }
   4308 
   4309 template <class _Codecvt, class _Elem, class _Tr>
   4310 typename wbuffer_convert<_Codecvt, _Elem, _Tr>::pos_type
   4311 wbuffer_convert<_Codecvt, _Elem, _Tr>::seekoff(off_type __off, ios_base::seekdir __way,
   4312                                         ios_base::openmode __om)
   4313 {
   4314     int __width = __cv_->encoding();
   4315     if (__cv_ == 0 || __bufptr_ == 0 || (__width <= 0 && __off != 0) || sync())
   4316         return pos_type(off_type(-1));
   4317     // __width > 0 || __off == 0
   4318     switch (__way)
   4319     {
   4320     case ios_base::beg:
   4321         break;
   4322     case ios_base::cur:
   4323         break;
   4324     case ios_base::end:
   4325         break;
   4326     default:
   4327         return pos_type(off_type(-1));
   4328     }
   4329     pos_type __r = __bufptr_->pubseekoff(__width * __off, __way, __om);
   4330     __r.state(__st_);
   4331     return __r;
   4332 }
   4333 
   4334 template <class _Codecvt, class _Elem, class _Tr>
   4335 typename wbuffer_convert<_Codecvt, _Elem, _Tr>::pos_type
   4336 wbuffer_convert<_Codecvt, _Elem, _Tr>::seekpos(pos_type __sp, ios_base::openmode __wch)
   4337 {
   4338     if (__cv_ == 0 || __bufptr_ == 0 || sync())
   4339         return pos_type(off_type(-1));
   4340     if (__bufptr_->pubseekpos(__sp, __wch) == pos_type(off_type(-1)))
   4341         return pos_type(off_type(-1));
   4342     return __sp;
   4343 }
   4344 
   4345 template <class _Codecvt, class _Elem, class _Tr>
   4346 int
   4347 wbuffer_convert<_Codecvt, _Elem, _Tr>::sync()
   4348 {
   4349     if (__cv_ == 0 || __bufptr_ == 0)
   4350         return 0;
   4351     if (__cm_ & ios_base::out)
   4352     {
   4353         if (this->pptr() != this->pbase())
   4354             if (overflow() == traits_type::eof())
   4355                 return -1;
   4356         codecvt_base::result __r;
   4357         do
   4358         {
   4359             char* __extbe;
   4360             __r = __cv_->unshift(__st_, __extbuf_, __extbuf_ + __ebs_, __extbe);
   4361             streamsize __nmemb = static_cast<streamsize>(__extbe - __extbuf_);
   4362             if (__bufptr_->sputn(__extbuf_, __nmemb) != __nmemb)
   4363                 return -1;
   4364         } while (__r == codecvt_base::partial);
   4365         if (__r == codecvt_base::error)
   4366             return -1;
   4367         if (__bufptr_->pubsync())
   4368             return -1;
   4369     }
   4370     else if (__cm_ & ios_base::in)
   4371     {
   4372         off_type __c;
   4373         if (__always_noconv_)
   4374             __c = this->egptr() - this->gptr();
   4375         else
   4376         {
   4377             int __width = __cv_->encoding();
   4378             __c = __extbufend_ - __extbufnext_;
   4379             if (__width > 0)
   4380                 __c += __width * (this->egptr() - this->gptr());
   4381             else
   4382             {
   4383                 if (this->gptr() != this->egptr())
   4384                 {
   4385                     reverse(this->gptr(), this->egptr());
   4386                     codecvt_base::result __r;
   4387                     const char_type* __e = this->gptr();
   4388                     char* __extbe;
   4389                     do
   4390                     {
   4391                         __r = __cv_->out(__st_, __e, this->egptr(), __e,
   4392                                          __extbuf_, __extbuf_ + __ebs_, __extbe);
   4393                         switch (__r)
   4394                         {
   4395                         case codecvt_base::noconv:
   4396                             __c += this->egptr() - this->gptr();
   4397                             break;
   4398                         case codecvt_base::ok:
   4399                         case codecvt_base::partial:
   4400                             __c += __extbe - __extbuf_;
   4401                             break;
   4402                         default:
   4403                             return -1;
   4404                         }
   4405                     } while (__r == codecvt_base::partial);
   4406                 }
   4407             }
   4408         }
   4409         if (__bufptr_->pubseekoff(-__c, ios_base::cur, __cm_) == pos_type(off_type(-1)))
   4410             return -1;
   4411         this->setg(0, 0, 0);
   4412         __cm_ = 0;
   4413     }
   4414     return 0;
   4415 }
   4416 
   4417 template <class _Codecvt, class _Elem, class _Tr>
   4418 bool
   4419 wbuffer_convert<_Codecvt, _Elem, _Tr>::__read_mode()
   4420 {
   4421     if (!(__cm_ & ios_base::in))
   4422     {
   4423         this->setp(0, 0);
   4424         if (__always_noconv_)
   4425             this->setg((char_type*)__extbuf_,
   4426                        (char_type*)__extbuf_ + __ebs_,
   4427                        (char_type*)__extbuf_ + __ebs_);
   4428         else
   4429             this->setg(__intbuf_, __intbuf_ + __ibs_, __intbuf_ + __ibs_);
   4430         __cm_ = ios_base::in;
   4431         return true;
   4432     }
   4433     return false;
   4434 }
   4435 
   4436 template <class _Codecvt, class _Elem, class _Tr>
   4437 void
   4438 wbuffer_convert<_Codecvt, _Elem, _Tr>::__write_mode()
   4439 {
   4440     if (!(__cm_ & ios_base::out))
   4441     {
   4442         this->setg(0, 0, 0);
   4443         if (__ebs_ > sizeof(__extbuf_min_))
   4444         {
   4445             if (__always_noconv_)
   4446                 this->setp((char_type*)__extbuf_,
   4447                            (char_type*)__extbuf_ + (__ebs_ - 1));
   4448             else
   4449                 this->setp(__intbuf_, __intbuf_ + (__ibs_ - 1));
   4450         }
   4451         else
   4452             this->setp(0, 0);
   4453         __cm_ = ios_base::out;
   4454     }
   4455 }
   4456 
   4457 template <class _Codecvt, class _Elem, class _Tr>
   4458 wbuffer_convert<_Codecvt, _Elem, _Tr>*
   4459 wbuffer_convert<_Codecvt, _Elem, _Tr>::__close()
   4460 {
   4461     wbuffer_convert* __rt = 0;
   4462     if (__cv_ != 0 && __bufptr_ != 0)
   4463     {
   4464         __rt = this;
   4465         if ((__cm_ & ios_base::out) && sync())
   4466             __rt = 0;
   4467     }
   4468     return __rt;
   4469 }
   4470 
   4471 _LIBCPP_END_NAMESPACE_STD
   4472 
   4473 #endif  // _LIBCPP_LOCALE
   4474