1// -*- C++ -*- 2//===----------------------------------------------------------------------===// 3// 4// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 5// See https://llvm.org/LICENSE.txt for license information. 6// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 7// 8//===----------------------------------------------------------------------===// 9 10#ifndef _LIBCPP___LOCALE 11#define _LIBCPP___LOCALE 12 13#include <__availability> 14#include <__config> 15#include <__memory/shared_ptr.h> // __shared_count 16#include <__type_traits/make_unsigned.h> 17#include <cctype> 18#include <clocale> 19#include <cstdint> 20#include <cstdlib> 21#include <mutex> 22#include <string> 23 24// Some platforms require more includes than others. Keep the includes on all plaforms for now. 25#include <cstddef> 26#include <cstring> 27 28#ifndef _LIBCPP_HAS_NO_WIDE_CHARACTERS 29# include <cwchar> 30#else 31# include <__std_mbstate_t.h> 32#endif 33 34#if defined(_LIBCPP_MSVCRT_LIKE) 35# include <__support/win32/locale_win32.h> 36#elif defined(_AIX) || defined(__MVS__) 37# include <__support/ibm/xlocale.h> 38#elif defined(__ANDROID__) 39# include <__support/android/locale_bionic.h> 40#elif defined(_NEWLIB_VERSION) 41# include <__support/newlib/xlocale.h> 42#elif defined(__OpenBSD__) 43# include <__support/openbsd/xlocale.h> 44#elif (defined(__APPLE__) || defined(__FreeBSD__)) 45# include <xlocale.h> 46#elif defined(__Fuchsia__) 47# include <__support/fuchsia/xlocale.h> 48#elif defined(__wasi__) 49// WASI libc uses musl's locales support. 50# include <__support/musl/xlocale.h> 51#elif defined(_LIBCPP_HAS_MUSL_LIBC) 52# include <__support/musl/xlocale.h> 53#endif 54 55#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER) 56# pragma GCC system_header 57#endif 58 59_LIBCPP_BEGIN_NAMESPACE_STD 60 61class _LIBCPP_EXPORTED_FROM_ABI locale; 62 63template <class _Facet> 64_LIBCPP_INLINE_VISIBILITY 65bool 66has_facet(const locale&) _NOEXCEPT; 67 68template <class _Facet> 69_LIBCPP_INLINE_VISIBILITY 70const _Facet& 71use_facet(const locale&); 72 73class _LIBCPP_EXPORTED_FROM_ABI locale 74{ 75public: 76 // types: 77 class _LIBCPP_EXPORTED_FROM_ABI facet; 78 class _LIBCPP_EXPORTED_FROM_ABI id; 79 80 typedef int category; 81 _LIBCPP_AVAILABILITY_LOCALE_CATEGORY 82 static const category // values assigned here are for exposition only 83 none = 0, 84 collate = LC_COLLATE_MASK, 85 ctype = LC_CTYPE_MASK, 86 monetary = LC_MONETARY_MASK, 87 numeric = LC_NUMERIC_MASK, 88 time = LC_TIME_MASK, 89 messages = LC_MESSAGES_MASK, 90 all = collate | ctype | monetary | numeric | time | messages; 91 92 // construct/copy/destroy: 93 locale() _NOEXCEPT; 94 locale(const locale&) _NOEXCEPT; 95 explicit locale(const char*); 96 explicit locale(const string&); 97 locale(const locale&, const char*, category); 98 locale(const locale&, const string&, category); 99 template <class _Facet> 100 _LIBCPP_INLINE_VISIBILITY locale(const locale&, _Facet*); 101 locale(const locale&, const locale&, category); 102 103 ~locale(); 104 105 const locale& operator=(const locale&) _NOEXCEPT; 106 107 template <class _Facet> 108 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 109 locale combine(const locale&) const; 110 111 // locale operations: 112 string name() const; 113 bool operator==(const locale&) const; 114#if _LIBCPP_STD_VER <= 17 115 _LIBCPP_HIDE_FROM_ABI bool operator!=(const locale& __y) const {return !(*this == __y);} 116#endif 117 template <class _CharT, class _Traits, class _Allocator> 118 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS 119 bool operator()(const basic_string<_CharT, _Traits, _Allocator>&, 120 const basic_string<_CharT, _Traits, _Allocator>&) const; 121 122 // global locale objects: 123 static locale global(const locale&); 124 static const locale& classic(); 125 126private: 127 class __imp; 128 __imp* __locale_; 129 130 void __install_ctor(const locale&, facet*, long); 131 static locale& __global(); 132 bool has_facet(id&) const; 133 const facet* use_facet(id&) const; 134 135 template <class _Facet> friend bool has_facet(const locale&) _NOEXCEPT; 136 template <class _Facet> friend const _Facet& use_facet(const locale&); 137}; 138 139class _LIBCPP_EXPORTED_FROM_ABI locale::facet 140 : public __shared_count 141{ 142protected: 143 _LIBCPP_INLINE_VISIBILITY 144 explicit facet(size_t __refs = 0) 145 : __shared_count(static_cast<long>(__refs)-1) {} 146 147 ~facet() override; 148 149// facet(const facet&) = delete; // effectively done in __shared_count 150// void operator=(const facet&) = delete; 151private: 152 void __on_zero_shared() _NOEXCEPT override; 153}; 154 155class _LIBCPP_EXPORTED_FROM_ABI locale::id 156{ 157 once_flag __flag_; 158 int32_t __id_; 159 160 static int32_t __next_id; 161public: 162 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR id() :__id_(0) {} 163 void operator=(const id&) = delete; 164 id(const id&) = delete; 165 166private: 167 void __init(); 168public: // only needed for tests 169 long __get(); 170 171 friend class locale; 172 friend class locale::__imp; 173}; 174 175template <class _Facet> 176inline _LIBCPP_INLINE_VISIBILITY 177locale::locale(const locale& __other, _Facet* __f) 178{ 179 __install_ctor(__other, __f, __f ? __f->id.__get() : 0); 180} 181 182template <class _Facet> 183locale 184locale::combine(const locale& __other) const 185{ 186 if (!_VSTD::has_facet<_Facet>(__other)) 187 __throw_runtime_error("locale::combine: locale missing facet"); 188 189 return locale(*this, &const_cast<_Facet&>(_VSTD::use_facet<_Facet>(__other))); 190} 191 192template <class _Facet> 193inline _LIBCPP_INLINE_VISIBILITY 194bool 195has_facet(const locale& __l) _NOEXCEPT 196{ 197 return __l.has_facet(_Facet::id); 198} 199 200template <class _Facet> 201inline _LIBCPP_INLINE_VISIBILITY 202const _Facet& 203use_facet(const locale& __l) 204{ 205 return static_cast<const _Facet&>(*__l.use_facet(_Facet::id)); 206} 207 208// template <class _CharT> class collate; 209 210template <class _CharT> 211class _LIBCPP_TEMPLATE_VIS collate 212 : public locale::facet 213{ 214public: 215 typedef _CharT char_type; 216 typedef basic_string<char_type> string_type; 217 218 _LIBCPP_INLINE_VISIBILITY 219 explicit collate(size_t __refs = 0) 220 : locale::facet(__refs) {} 221 222 _LIBCPP_INLINE_VISIBILITY 223 int compare(const char_type* __lo1, const char_type* __hi1, 224 const char_type* __lo2, const char_type* __hi2) const 225 { 226 return do_compare(__lo1, __hi1, __lo2, __hi2); 227 } 228 229 // FIXME(EricWF): The _LIBCPP_ALWAYS_INLINE is needed on Windows to work 230 // around a dllimport bug that expects an external instantiation. 231 _LIBCPP_INLINE_VISIBILITY 232 _LIBCPP_ALWAYS_INLINE 233 string_type transform(const char_type* __lo, const char_type* __hi) const 234 { 235 return do_transform(__lo, __hi); 236 } 237 238 _LIBCPP_INLINE_VISIBILITY 239 long hash(const char_type* __lo, const char_type* __hi) const 240 { 241 return do_hash(__lo, __hi); 242 } 243 244 static locale::id id; 245 246protected: 247 ~collate() override; 248 virtual int do_compare(const char_type* __lo1, const char_type* __hi1, 249 const char_type* __lo2, const char_type* __hi2) const; 250 virtual string_type do_transform(const char_type* __lo, const char_type* __hi) const 251 {return string_type(__lo, __hi);} 252 virtual long do_hash(const char_type* __lo, const char_type* __hi) const; 253}; 254 255template <class _CharT> locale::id collate<_CharT>::id; 256 257template <class _CharT> 258collate<_CharT>::~collate() 259{ 260} 261 262template <class _CharT> 263int 264collate<_CharT>::do_compare(const char_type* __lo1, const char_type* __hi1, 265 const char_type* __lo2, const char_type* __hi2) const 266{ 267 for (; __lo2 != __hi2; ++__lo1, ++__lo2) 268 { 269 if (__lo1 == __hi1 || *__lo1 < *__lo2) 270 return -1; 271 if (*__lo2 < *__lo1) 272 return 1; 273 } 274 return __lo1 != __hi1; 275} 276 277template <class _CharT> 278long 279collate<_CharT>::do_hash(const char_type* __lo, const char_type* __hi) const 280{ 281 size_t __h = 0; 282 const size_t __sr = __CHAR_BIT__ * sizeof(size_t) - 8; 283 const size_t __mask = size_t(0xF) << (__sr + 4); 284 for(const char_type* __p = __lo; __p != __hi; ++__p) 285 { 286 __h = (__h << 4) + static_cast<size_t>(*__p); 287 size_t __g = __h & __mask; 288 __h ^= __g | (__g >> __sr); 289 } 290 return static_cast<long>(__h); 291} 292 293extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS collate<char>; 294#ifndef _LIBCPP_HAS_NO_WIDE_CHARACTERS 295extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS collate<wchar_t>; 296#endif 297 298// template <class CharT> class collate_byname; 299 300template <class _CharT> class _LIBCPP_TEMPLATE_VIS collate_byname; 301 302template <> 303class _LIBCPP_EXPORTED_FROM_ABI collate_byname<char> 304 : public collate<char> 305{ 306 locale_t __l_; 307public: 308 typedef char char_type; 309 typedef basic_string<char_type> string_type; 310 311 explicit collate_byname(const char* __n, size_t __refs = 0); 312 explicit collate_byname(const string& __n, size_t __refs = 0); 313 314protected: 315 ~collate_byname() override; 316 int do_compare(const char_type* __lo1, const char_type* __hi1, 317 const char_type* __lo2, const char_type* __hi2) const override; 318 string_type do_transform(const char_type* __lo, const char_type* __hi) const override; 319}; 320 321#ifndef _LIBCPP_HAS_NO_WIDE_CHARACTERS 322template <> 323class _LIBCPP_EXPORTED_FROM_ABI collate_byname<wchar_t> 324 : public collate<wchar_t> 325{ 326 locale_t __l_; 327public: 328 typedef wchar_t char_type; 329 typedef basic_string<char_type> string_type; 330 331 explicit collate_byname(const char* __n, size_t __refs = 0); 332 explicit collate_byname(const string& __n, size_t __refs = 0); 333 334protected: 335 ~collate_byname() override; 336 337 int do_compare(const char_type* __lo1, const char_type* __hi1, 338 const char_type* __lo2, const char_type* __hi2) const override; 339 string_type do_transform(const char_type* __lo, const char_type* __hi) const override; 340}; 341#endif 342 343template <class _CharT, class _Traits, class _Allocator> 344bool 345locale::operator()(const basic_string<_CharT, _Traits, _Allocator>& __x, 346 const basic_string<_CharT, _Traits, _Allocator>& __y) const 347{ 348 return _VSTD::use_facet<_VSTD::collate<_CharT> >(*this).compare( 349 __x.data(), __x.data() + __x.size(), 350 __y.data(), __y.data() + __y.size()) < 0; 351} 352 353// template <class charT> class ctype 354 355class _LIBCPP_EXPORTED_FROM_ABI ctype_base 356{ 357public: 358#if defined(_LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE) 359 typedef unsigned long mask; 360 static const mask space = 1<<0; 361 static const mask print = 1<<1; 362 static const mask cntrl = 1<<2; 363 static const mask upper = 1<<3; 364 static const mask lower = 1<<4; 365 static const mask alpha = 1<<5; 366 static const mask digit = 1<<6; 367 static const mask punct = 1<<7; 368 static const mask xdigit = 1<<8; 369 static const mask blank = 1<<9; 370#if defined(__BIONIC__) 371 // Historically this was a part of regex_traits rather than ctype_base. The 372 // historical value of the constant is preserved for ABI compatibility. 373 static const mask __regex_word = 0x8000; 374#else 375 static const mask __regex_word = 1<<10; 376#endif // defined(__BIONIC__) 377#elif defined(__GLIBC__) 378 typedef unsigned short mask; 379 static const mask space = _ISspace; 380 static const mask print = _ISprint; 381 static const mask cntrl = _IScntrl; 382 static const mask upper = _ISupper; 383 static const mask lower = _ISlower; 384 static const mask alpha = _ISalpha; 385 static const mask digit = _ISdigit; 386 static const mask punct = _ISpunct; 387 static const mask xdigit = _ISxdigit; 388 static const mask blank = _ISblank; 389#if defined(__mips__) 390 static const mask __regex_word = static_cast<mask>(_ISbit(15)); 391#else 392 static const mask __regex_word = 0x80; 393#endif 394#elif defined(_LIBCPP_MSVCRT_LIKE) 395 typedef unsigned short mask; 396 static const mask space = _SPACE; 397 static const mask print = _BLANK|_PUNCT|_ALPHA|_DIGIT; 398 static const mask cntrl = _CONTROL; 399 static const mask upper = _UPPER; 400 static const mask lower = _LOWER; 401 static const mask alpha = _ALPHA; 402 static const mask digit = _DIGIT; 403 static const mask punct = _PUNCT; 404 static const mask xdigit = _HEX; 405 static const mask blank = _BLANK; 406 static const mask __regex_word = 0x4000; // 0x8000 and 0x0100 and 0x00ff are used 407# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT 408# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_ALPHA 409#elif defined(__APPLE__) || defined(__FreeBSD__) || defined(__EMSCRIPTEN__) || defined(__NetBSD__) 410# ifdef __APPLE__ 411 typedef __uint32_t mask; 412# elif defined(__FreeBSD__) 413 typedef unsigned long mask; 414# elif defined(__EMSCRIPTEN__) || defined(__NetBSD__) 415 typedef unsigned short mask; 416# endif 417 static const mask space = _CTYPE_S; 418 static const mask print = _CTYPE_R; 419 static const mask cntrl = _CTYPE_C; 420 static const mask upper = _CTYPE_U; 421 static const mask lower = _CTYPE_L; 422 static const mask alpha = _CTYPE_A; 423 static const mask digit = _CTYPE_D; 424 static const mask punct = _CTYPE_P; 425 static const mask xdigit = _CTYPE_X; 426 427# if defined(__NetBSD__) 428 static const mask blank = _CTYPE_BL; 429 // NetBSD defines classes up to 0x2000 430 // see sys/ctype_bits.h, _CTYPE_Q 431 static const mask __regex_word = 0x8000; 432# else 433 static const mask blank = _CTYPE_B; 434 static const mask __regex_word = 0x80; 435# endif 436#elif defined(_AIX) 437 typedef unsigned int mask; 438 static const mask space = _ISSPACE; 439 static const mask print = _ISPRINT; 440 static const mask cntrl = _ISCNTRL; 441 static const mask upper = _ISUPPER; 442 static const mask lower = _ISLOWER; 443 static const mask alpha = _ISALPHA; 444 static const mask digit = _ISDIGIT; 445 static const mask punct = _ISPUNCT; 446 static const mask xdigit = _ISXDIGIT; 447 static const mask blank = _ISBLANK; 448 static const mask __regex_word = 0x8000; 449#elif defined(_NEWLIB_VERSION) 450 // Same type as Newlib's _ctype_ array in newlib/libc/include/ctype.h. 451 typedef char mask; 452 static const mask space = _S; 453 static const mask print = _P | _U | _L | _N | _B; 454 static const mask cntrl = _C; 455 static const mask upper = _U; 456 static const mask lower = _L; 457 static const mask alpha = _U | _L; 458 static const mask digit = _N; 459 static const mask punct = _P; 460 static const mask xdigit = _X | _N; 461 static const mask blank = _B; 462 // mask is already fully saturated, use a different type in regex_type_traits. 463 static const unsigned short __regex_word = 0x100; 464# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT 465# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_ALPHA 466# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_XDIGIT 467#elif defined(__MVS__) 468# if defined(__NATIVE_ASCII_F) 469 typedef unsigned int mask; 470 static const mask space = _ISSPACE_A; 471 static const mask print = _ISPRINT_A; 472 static const mask cntrl = _ISCNTRL_A; 473 static const mask upper = _ISUPPER_A; 474 static const mask lower = _ISLOWER_A; 475 static const mask alpha = _ISALPHA_A; 476 static const mask digit = _ISDIGIT_A; 477 static const mask punct = _ISPUNCT_A; 478 static const mask xdigit = _ISXDIGIT_A; 479 static const mask blank = _ISBLANK_A; 480# else 481 typedef unsigned short mask; 482 static const mask space = __ISSPACE; 483 static const mask print = __ISPRINT; 484 static const mask cntrl = __ISCNTRL; 485 static const mask upper = __ISUPPER; 486 static const mask lower = __ISLOWER; 487 static const mask alpha = __ISALPHA; 488 static const mask digit = __ISDIGIT; 489 static const mask punct = __ISPUNCT; 490 static const mask xdigit = __ISXDIGIT; 491 static const mask blank = __ISBLANK; 492# endif 493 static const mask __regex_word = 0x8000; 494#else 495# error unknown rune table for this platform -- do you mean to define _LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE? 496#endif 497 static const mask alnum = alpha | digit; 498 static const mask graph = alnum | punct; 499 500 _LIBCPP_INLINE_VISIBILITY ctype_base() {} 501 502 static_assert((__regex_word & ~(std::make_unsigned<mask>::type)(space | print | cntrl | upper | lower | alpha | 503 digit | punct | xdigit | blank)) == __regex_word, 504 "__regex_word can't overlap other bits"); 505}; 506 507template <class _CharT> class _LIBCPP_TEMPLATE_VIS ctype; 508 509#ifndef _LIBCPP_HAS_NO_WIDE_CHARACTERS 510template <> 511class _LIBCPP_EXPORTED_FROM_ABI ctype<wchar_t> 512 : public locale::facet, 513 public ctype_base 514{ 515public: 516 typedef wchar_t char_type; 517 518 _LIBCPP_INLINE_VISIBILITY 519 explicit ctype(size_t __refs = 0) 520 : locale::facet(__refs) {} 521 522 _LIBCPP_INLINE_VISIBILITY 523 bool is(mask __m, char_type __c) const 524 { 525 return do_is(__m, __c); 526 } 527 528 _LIBCPP_INLINE_VISIBILITY 529 const char_type* is(const char_type* __low, const char_type* __high, mask* __vec) const 530 { 531 return do_is(__low, __high, __vec); 532 } 533 534 _LIBCPP_INLINE_VISIBILITY 535 const char_type* scan_is(mask __m, const char_type* __low, const char_type* __high) const 536 { 537 return do_scan_is(__m, __low, __high); 538 } 539 540 _LIBCPP_INLINE_VISIBILITY 541 const char_type* scan_not(mask __m, const char_type* __low, const char_type* __high) const 542 { 543 return do_scan_not(__m, __low, __high); 544 } 545 546 _LIBCPP_INLINE_VISIBILITY 547 char_type toupper(char_type __c) const 548 { 549 return do_toupper(__c); 550 } 551 552 _LIBCPP_INLINE_VISIBILITY 553 const char_type* toupper(char_type* __low, const char_type* __high) const 554 { 555 return do_toupper(__low, __high); 556 } 557 558 _LIBCPP_INLINE_VISIBILITY 559 char_type tolower(char_type __c) const 560 { 561 return do_tolower(__c); 562 } 563 564 _LIBCPP_INLINE_VISIBILITY 565 const char_type* tolower(char_type* __low, const char_type* __high) const 566 { 567 return do_tolower(__low, __high); 568 } 569 570 _LIBCPP_INLINE_VISIBILITY 571 char_type widen(char __c) const 572 { 573 return do_widen(__c); 574 } 575 576 _LIBCPP_INLINE_VISIBILITY 577 const char* widen(const char* __low, const char* __high, char_type* __to) const 578 { 579 return do_widen(__low, __high, __to); 580 } 581 582 _LIBCPP_INLINE_VISIBILITY 583 char narrow(char_type __c, char __dfault) const 584 { 585 return do_narrow(__c, __dfault); 586 } 587 588 _LIBCPP_INLINE_VISIBILITY 589 const char_type* narrow(const char_type* __low, const char_type* __high, char __dfault, char* __to) const 590 { 591 return do_narrow(__low, __high, __dfault, __to); 592 } 593 594 static locale::id id; 595 596protected: 597 ~ctype() override; 598 virtual bool do_is(mask __m, char_type __c) const; 599 virtual const char_type* do_is(const char_type* __low, const char_type* __high, mask* __vec) const; 600 virtual const char_type* do_scan_is(mask __m, const char_type* __low, const char_type* __high) const; 601 virtual const char_type* do_scan_not(mask __m, const char_type* __low, const char_type* __high) const; 602 virtual char_type do_toupper(char_type) const; 603 virtual const char_type* do_toupper(char_type* __low, const char_type* __high) const; 604 virtual char_type do_tolower(char_type) const; 605 virtual const char_type* do_tolower(char_type* __low, const char_type* __high) const; 606 virtual char_type do_widen(char) const; 607 virtual const char* do_widen(const char* __low, const char* __high, char_type* __dest) const; 608 virtual char do_narrow(char_type, char __dfault) const; 609 virtual const char_type* do_narrow(const char_type* __low, const char_type* __high, char __dfault, char* __dest) const; 610}; 611#endif // _LIBCPP_HAS_NO_WIDE_CHARACTERS 612 613template <> 614class _LIBCPP_EXPORTED_FROM_ABI ctype<char> 615 : public locale::facet, public ctype_base 616{ 617 const mask* __tab_; 618 bool __del_; 619public: 620 typedef char char_type; 621 622 explicit ctype(const mask* __tab = nullptr, bool __del = false, size_t __refs = 0); 623 624 _LIBCPP_INLINE_VISIBILITY 625 bool is(mask __m, char_type __c) const 626 { 627 return isascii(__c) ? (__tab_[static_cast<int>(__c)] & __m) !=0 : false; 628 } 629 630 _LIBCPP_INLINE_VISIBILITY 631 const char_type* is(const char_type* __low, const char_type* __high, mask* __vec) const 632 { 633 for (; __low != __high; ++__low, ++__vec) 634 *__vec = isascii(*__low) ? __tab_[static_cast<int>(*__low)] : 0; 635 return __low; 636 } 637 638 _LIBCPP_INLINE_VISIBILITY 639 const char_type* scan_is (mask __m, const char_type* __low, const char_type* __high) const 640 { 641 for (; __low != __high; ++__low) 642 if (isascii(*__low) && (__tab_[static_cast<int>(*__low)] & __m)) 643 break; 644 return __low; 645 } 646 647 _LIBCPP_INLINE_VISIBILITY 648 const char_type* scan_not(mask __m, const char_type* __low, const char_type* __high) const 649 { 650 for (; __low != __high; ++__low) 651 if (!isascii(*__low) || !(__tab_[static_cast<int>(*__low)] & __m)) 652 break; 653 return __low; 654 } 655 656 _LIBCPP_INLINE_VISIBILITY 657 char_type toupper(char_type __c) const 658 { 659 return do_toupper(__c); 660 } 661 662 _LIBCPP_INLINE_VISIBILITY 663 const char_type* toupper(char_type* __low, const char_type* __high) const 664 { 665 return do_toupper(__low, __high); 666 } 667 668 _LIBCPP_INLINE_VISIBILITY 669 char_type tolower(char_type __c) const 670 { 671 return do_tolower(__c); 672 } 673 674 _LIBCPP_INLINE_VISIBILITY 675 const char_type* tolower(char_type* __low, const char_type* __high) const 676 { 677 return do_tolower(__low, __high); 678 } 679 680 _LIBCPP_INLINE_VISIBILITY 681 char_type widen(char __c) const 682 { 683 return do_widen(__c); 684 } 685 686 _LIBCPP_INLINE_VISIBILITY 687 const char* widen(const char* __low, const char* __high, char_type* __to) const 688 { 689 return do_widen(__low, __high, __to); 690 } 691 692 _LIBCPP_INLINE_VISIBILITY 693 char narrow(char_type __c, char __dfault) const 694 { 695 return do_narrow(__c, __dfault); 696 } 697 698 _LIBCPP_INLINE_VISIBILITY 699 const char* narrow(const char_type* __low, const char_type* __high, char __dfault, char* __to) const 700 { 701 return do_narrow(__low, __high, __dfault, __to); 702 } 703 704 static locale::id id; 705 706#ifdef _CACHED_RUNES 707 static const size_t table_size = _CACHED_RUNES; 708#else 709 static const size_t table_size = 256; // FIXME: Don't hardcode this. 710#endif 711 _LIBCPP_INLINE_VISIBILITY const mask* table() const _NOEXCEPT {return __tab_;} 712 static const mask* classic_table() _NOEXCEPT; 713#if defined(__GLIBC__) || defined(__EMSCRIPTEN__) 714 static const int* __classic_upper_table() _NOEXCEPT; 715 static const int* __classic_lower_table() _NOEXCEPT; 716#endif 717#if defined(__NetBSD__) 718 static const short* __classic_upper_table() _NOEXCEPT; 719 static const short* __classic_lower_table() _NOEXCEPT; 720#endif 721#if defined(__MVS__) 722 static const unsigned short* __classic_upper_table() _NOEXCEPT; 723 static const unsigned short* __classic_lower_table() _NOEXCEPT; 724#endif 725 726protected: 727 ~ctype() override; 728 virtual char_type do_toupper(char_type __c) const; 729 virtual const char_type* do_toupper(char_type* __low, const char_type* __high) const; 730 virtual char_type do_tolower(char_type __c) const; 731 virtual const char_type* do_tolower(char_type* __low, const char_type* __high) const; 732 virtual char_type do_widen(char __c) const; 733 virtual const char* do_widen(const char* __low, const char* __high, char_type* __to) const; 734 virtual char do_narrow(char_type __c, char __dfault) const; 735 virtual const char* do_narrow(const char_type* __low, const char_type* __high, char __dfault, char* __to) const; 736}; 737 738// template <class CharT> class ctype_byname; 739 740template <class _CharT> class _LIBCPP_TEMPLATE_VIS ctype_byname; 741 742template <> 743class _LIBCPP_EXPORTED_FROM_ABI ctype_byname<char> 744 : public ctype<char> 745{ 746 locale_t __l_; 747 748public: 749 explicit ctype_byname(const char*, size_t = 0); 750 explicit ctype_byname(const string&, size_t = 0); 751 752protected: 753 ~ctype_byname() override; 754 char_type do_toupper(char_type) const override; 755 const char_type* do_toupper(char_type* __low, const char_type* __high) const override; 756 char_type do_tolower(char_type) const override; 757 const char_type* do_tolower(char_type* __low, const char_type* __high) const override; 758}; 759 760#ifndef _LIBCPP_HAS_NO_WIDE_CHARACTERS 761template <> 762class _LIBCPP_EXPORTED_FROM_ABI ctype_byname<wchar_t> 763 : public ctype<wchar_t> 764{ 765 locale_t __l_; 766 767public: 768 explicit ctype_byname(const char*, size_t = 0); 769 explicit ctype_byname(const string&, size_t = 0); 770 771protected: 772 ~ctype_byname() override; 773 bool do_is(mask __m, char_type __c) const override; 774 const char_type* do_is(const char_type* __low, const char_type* __high, mask* __vec) const override; 775 const char_type* do_scan_is(mask __m, const char_type* __low, const char_type* __high) const override; 776 const char_type* do_scan_not(mask __m, const char_type* __low, const char_type* __high) const override; 777 char_type do_toupper(char_type) const override; 778 const char_type* do_toupper(char_type* __low, const char_type* __high) const override; 779 char_type do_tolower(char_type) const override; 780 const char_type* do_tolower(char_type* __low, const char_type* __high) const override; 781 char_type do_widen(char) const override; 782 const char* do_widen(const char* __low, const char* __high, char_type* __dest) const override; 783 char do_narrow(char_type, char __dfault) const override; 784 const char_type* do_narrow(const char_type* __low, const char_type* __high, char __dfault, char* __dest) const override; 785}; 786#endif // _LIBCPP_HAS_NO_WIDE_CHARACTERS 787 788template <class _CharT> 789inline _LIBCPP_INLINE_VISIBILITY 790bool 791isspace(_CharT __c, const locale& __loc) 792{ 793 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::space, __c); 794} 795 796template <class _CharT> 797inline _LIBCPP_INLINE_VISIBILITY 798bool 799isprint(_CharT __c, const locale& __loc) 800{ 801 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::print, __c); 802} 803 804template <class _CharT> 805inline _LIBCPP_INLINE_VISIBILITY 806bool 807iscntrl(_CharT __c, const locale& __loc) 808{ 809 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::cntrl, __c); 810} 811 812template <class _CharT> 813inline _LIBCPP_INLINE_VISIBILITY 814bool 815isupper(_CharT __c, const locale& __loc) 816{ 817 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::upper, __c); 818} 819 820template <class _CharT> 821inline _LIBCPP_INLINE_VISIBILITY 822bool 823islower(_CharT __c, const locale& __loc) 824{ 825 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::lower, __c); 826} 827 828template <class _CharT> 829inline _LIBCPP_INLINE_VISIBILITY 830bool 831isalpha(_CharT __c, const locale& __loc) 832{ 833 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::alpha, __c); 834} 835 836template <class _CharT> 837inline _LIBCPP_INLINE_VISIBILITY 838bool 839isdigit(_CharT __c, const locale& __loc) 840{ 841 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::digit, __c); 842} 843 844template <class _CharT> 845inline _LIBCPP_INLINE_VISIBILITY 846bool 847ispunct(_CharT __c, const locale& __loc) 848{ 849 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::punct, __c); 850} 851 852template <class _CharT> 853inline _LIBCPP_INLINE_VISIBILITY 854bool 855isxdigit(_CharT __c, const locale& __loc) 856{ 857 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::xdigit, __c); 858} 859 860template <class _CharT> 861inline _LIBCPP_INLINE_VISIBILITY 862bool 863isalnum(_CharT __c, const locale& __loc) 864{ 865 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::alnum, __c); 866} 867 868template <class _CharT> 869inline _LIBCPP_INLINE_VISIBILITY 870bool 871isgraph(_CharT __c, const locale& __loc) 872{ 873 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::graph, __c); 874} 875 876template <class _CharT> 877_LIBCPP_HIDE_FROM_ABI bool isblank(_CharT __c, const locale& __loc) { 878 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::blank, __c); 879} 880 881template <class _CharT> 882inline _LIBCPP_INLINE_VISIBILITY 883_CharT 884toupper(_CharT __c, const locale& __loc) 885{ 886 return std::use_facet<ctype<_CharT> >(__loc).toupper(__c); 887} 888 889template <class _CharT> 890inline _LIBCPP_INLINE_VISIBILITY 891_CharT 892tolower(_CharT __c, const locale& __loc) 893{ 894 return std::use_facet<ctype<_CharT> >(__loc).tolower(__c); 895} 896 897// codecvt_base 898 899class _LIBCPP_EXPORTED_FROM_ABI codecvt_base 900{ 901public: 902 _LIBCPP_INLINE_VISIBILITY codecvt_base() {} 903 enum result {ok, partial, error, noconv}; 904}; 905 906// template <class internT, class externT, class stateT> class codecvt; 907 908template <class _InternT, class _ExternT, class _StateT> class _LIBCPP_TEMPLATE_VIS codecvt; 909 910// template <> class codecvt<char, char, mbstate_t> 911 912template <> 913class _LIBCPP_EXPORTED_FROM_ABI codecvt<char, char, mbstate_t> 914 : public locale::facet, 915 public codecvt_base 916{ 917public: 918 typedef char intern_type; 919 typedef char extern_type; 920 typedef mbstate_t state_type; 921 922 _LIBCPP_INLINE_VISIBILITY 923 explicit codecvt(size_t __refs = 0) 924 : locale::facet(__refs) {} 925 926 _LIBCPP_INLINE_VISIBILITY 927 result out(state_type& __st, 928 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 929 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 930 { 931 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 932 } 933 934 _LIBCPP_INLINE_VISIBILITY 935 result unshift(state_type& __st, 936 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 937 { 938 return do_unshift(__st, __to, __to_end, __to_nxt); 939 } 940 941 _LIBCPP_INLINE_VISIBILITY 942 result in(state_type& __st, 943 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 944 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const 945 { 946 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 947 } 948 949 _LIBCPP_INLINE_VISIBILITY 950 int encoding() const _NOEXCEPT 951 { 952 return do_encoding(); 953 } 954 955 _LIBCPP_INLINE_VISIBILITY 956 bool always_noconv() const _NOEXCEPT 957 { 958 return do_always_noconv(); 959 } 960 961 _LIBCPP_INLINE_VISIBILITY 962 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const 963 { 964 return do_length(__st, __frm, __end, __mx); 965 } 966 967 _LIBCPP_INLINE_VISIBILITY 968 int max_length() const _NOEXCEPT 969 { 970 return do_max_length(); 971 } 972 973 static locale::id id; 974 975protected: 976 _LIBCPP_INLINE_VISIBILITY 977 explicit codecvt(const char*, size_t __refs = 0) 978 : locale::facet(__refs) {} 979 980 ~codecvt() override; 981 982 virtual result do_out(state_type& __st, 983 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 984 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 985 virtual result do_in(state_type& __st, 986 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 987 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const; 988 virtual result do_unshift(state_type& __st, 989 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 990 virtual int do_encoding() const _NOEXCEPT; 991 virtual bool do_always_noconv() const _NOEXCEPT; 992 virtual int do_length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const; 993 virtual int do_max_length() const _NOEXCEPT; 994}; 995 996// template <> class codecvt<wchar_t, char, mbstate_t> 997 998#ifndef _LIBCPP_HAS_NO_WIDE_CHARACTERS 999template <> 1000class _LIBCPP_EXPORTED_FROM_ABI codecvt<wchar_t, char, mbstate_t> 1001 : public locale::facet, 1002 public codecvt_base 1003{ 1004 locale_t __l_; 1005public: 1006 typedef wchar_t intern_type; 1007 typedef char extern_type; 1008 typedef mbstate_t state_type; 1009 1010 explicit codecvt(size_t __refs = 0); 1011 1012 _LIBCPP_INLINE_VISIBILITY 1013 result out(state_type& __st, 1014 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1015 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1016 { 1017 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1018 } 1019 1020 _LIBCPP_INLINE_VISIBILITY 1021 result unshift(state_type& __st, 1022 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1023 { 1024 return do_unshift(__st, __to, __to_end, __to_nxt); 1025 } 1026 1027 _LIBCPP_INLINE_VISIBILITY 1028 result in(state_type& __st, 1029 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1030 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const 1031 { 1032 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1033 } 1034 1035 _LIBCPP_INLINE_VISIBILITY 1036 int encoding() const _NOEXCEPT 1037 { 1038 return do_encoding(); 1039 } 1040 1041 _LIBCPP_INLINE_VISIBILITY 1042 bool always_noconv() const _NOEXCEPT 1043 { 1044 return do_always_noconv(); 1045 } 1046 1047 _LIBCPP_INLINE_VISIBILITY 1048 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const 1049 { 1050 return do_length(__st, __frm, __end, __mx); 1051 } 1052 1053 _LIBCPP_INLINE_VISIBILITY 1054 int max_length() const _NOEXCEPT 1055 { 1056 return do_max_length(); 1057 } 1058 1059 static locale::id id; 1060 1061protected: 1062 explicit codecvt(const char*, size_t __refs = 0); 1063 1064 ~codecvt() override; 1065 1066 virtual result do_out(state_type& __st, 1067 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1068 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1069 virtual result do_in(state_type& __st, 1070 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1071 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const; 1072 virtual result do_unshift(state_type& __st, 1073 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1074 virtual int do_encoding() const _NOEXCEPT; 1075 virtual bool do_always_noconv() const _NOEXCEPT; 1076 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const; 1077 virtual int do_max_length() const _NOEXCEPT; 1078}; 1079#endif // _LIBCPP_HAS_NO_WIDE_CHARACTERS 1080 1081// template <> class codecvt<char16_t, char, mbstate_t> // deprecated in C++20 1082 1083template <> 1084class _LIBCPP_DEPRECATED_IN_CXX20 _LIBCPP_EXPORTED_FROM_ABI codecvt<char16_t, char, mbstate_t> 1085 : public locale::facet, 1086 public codecvt_base 1087{ 1088public: 1089 typedef char16_t intern_type; 1090 typedef char extern_type; 1091 typedef mbstate_t state_type; 1092 1093 _LIBCPP_INLINE_VISIBILITY 1094 explicit codecvt(size_t __refs = 0) 1095 : locale::facet(__refs) {} 1096 1097 _LIBCPP_INLINE_VISIBILITY 1098 result out(state_type& __st, 1099 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1100 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1101 { 1102 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1103 } 1104 1105 _LIBCPP_INLINE_VISIBILITY 1106 result unshift(state_type& __st, 1107 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1108 { 1109 return do_unshift(__st, __to, __to_end, __to_nxt); 1110 } 1111 1112 _LIBCPP_INLINE_VISIBILITY 1113 result in(state_type& __st, 1114 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1115 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const 1116 { 1117 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1118 } 1119 1120 _LIBCPP_INLINE_VISIBILITY 1121 int encoding() const _NOEXCEPT 1122 { 1123 return do_encoding(); 1124 } 1125 1126 _LIBCPP_INLINE_VISIBILITY 1127 bool always_noconv() const _NOEXCEPT 1128 { 1129 return do_always_noconv(); 1130 } 1131 1132 _LIBCPP_INLINE_VISIBILITY 1133 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const 1134 { 1135 return do_length(__st, __frm, __end, __mx); 1136 } 1137 1138 _LIBCPP_INLINE_VISIBILITY 1139 int max_length() const _NOEXCEPT 1140 { 1141 return do_max_length(); 1142 } 1143 1144 static locale::id id; 1145 1146protected: 1147 _LIBCPP_INLINE_VISIBILITY 1148 explicit codecvt(const char*, size_t __refs = 0) 1149 : locale::facet(__refs) {} 1150 1151 ~codecvt() override; 1152 1153 virtual result do_out(state_type& __st, 1154 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1155 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1156 virtual result do_in(state_type& __st, 1157 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1158 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const; 1159 virtual result do_unshift(state_type& __st, 1160 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1161 virtual int do_encoding() const _NOEXCEPT; 1162 virtual bool do_always_noconv() const _NOEXCEPT; 1163 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const; 1164 virtual int do_max_length() const _NOEXCEPT; 1165}; 1166 1167#ifndef _LIBCPP_HAS_NO_CHAR8_T 1168 1169// template <> class codecvt<char16_t, char8_t, mbstate_t> // C++20 1170 1171template <> 1172class _LIBCPP_EXPORTED_FROM_ABI codecvt<char16_t, char8_t, mbstate_t> 1173 : public locale::facet, 1174 public codecvt_base 1175{ 1176public: 1177 typedef char16_t intern_type; 1178 typedef char8_t extern_type; 1179 typedef mbstate_t state_type; 1180 1181 _LIBCPP_INLINE_VISIBILITY 1182 explicit codecvt(size_t __refs = 0) 1183 : locale::facet(__refs) {} 1184 1185 _LIBCPP_INLINE_VISIBILITY 1186 result out(state_type& __st, 1187 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1188 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1189 { 1190 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1191 } 1192 1193 _LIBCPP_INLINE_VISIBILITY 1194 result unshift(state_type& __st, 1195 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1196 { 1197 return do_unshift(__st, __to, __to_end, __to_nxt); 1198 } 1199 1200 _LIBCPP_INLINE_VISIBILITY 1201 result in(state_type& __st, 1202 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1203 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const 1204 { 1205 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1206 } 1207 1208 _LIBCPP_INLINE_VISIBILITY 1209 int encoding() const _NOEXCEPT 1210 { 1211 return do_encoding(); 1212 } 1213 1214 _LIBCPP_INLINE_VISIBILITY 1215 bool always_noconv() const _NOEXCEPT 1216 { 1217 return do_always_noconv(); 1218 } 1219 1220 _LIBCPP_INLINE_VISIBILITY 1221 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const 1222 { 1223 return do_length(__st, __frm, __end, __mx); 1224 } 1225 1226 _LIBCPP_INLINE_VISIBILITY 1227 int max_length() const _NOEXCEPT 1228 { 1229 return do_max_length(); 1230 } 1231 1232 static locale::id id; 1233 1234protected: 1235 _LIBCPP_INLINE_VISIBILITY 1236 explicit codecvt(const char*, size_t __refs = 0) 1237 : locale::facet(__refs) {} 1238 1239 ~codecvt() override; 1240 1241 virtual result do_out(state_type& __st, 1242 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1243 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1244 virtual result do_in(state_type& __st, 1245 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1246 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const; 1247 virtual result do_unshift(state_type& __st, 1248 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1249 virtual int do_encoding() const _NOEXCEPT; 1250 virtual bool do_always_noconv() const _NOEXCEPT; 1251 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const; 1252 virtual int do_max_length() const _NOEXCEPT; 1253}; 1254 1255#endif 1256 1257// template <> class codecvt<char32_t, char, mbstate_t> // deprecated in C++20 1258 1259template <> 1260class _LIBCPP_DEPRECATED_IN_CXX20 _LIBCPP_EXPORTED_FROM_ABI codecvt<char32_t, char, mbstate_t> 1261 : public locale::facet, 1262 public codecvt_base 1263{ 1264public: 1265 typedef char32_t intern_type; 1266 typedef char extern_type; 1267 typedef mbstate_t state_type; 1268 1269 _LIBCPP_INLINE_VISIBILITY 1270 explicit codecvt(size_t __refs = 0) 1271 : locale::facet(__refs) {} 1272 1273 _LIBCPP_INLINE_VISIBILITY 1274 result out(state_type& __st, 1275 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1276 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1277 { 1278 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1279 } 1280 1281 _LIBCPP_INLINE_VISIBILITY 1282 result unshift(state_type& __st, 1283 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1284 { 1285 return do_unshift(__st, __to, __to_end, __to_nxt); 1286 } 1287 1288 _LIBCPP_INLINE_VISIBILITY 1289 result in(state_type& __st, 1290 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1291 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const 1292 { 1293 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1294 } 1295 1296 _LIBCPP_INLINE_VISIBILITY 1297 int encoding() const _NOEXCEPT 1298 { 1299 return do_encoding(); 1300 } 1301 1302 _LIBCPP_INLINE_VISIBILITY 1303 bool always_noconv() const _NOEXCEPT 1304 { 1305 return do_always_noconv(); 1306 } 1307 1308 _LIBCPP_INLINE_VISIBILITY 1309 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const 1310 { 1311 return do_length(__st, __frm, __end, __mx); 1312 } 1313 1314 _LIBCPP_INLINE_VISIBILITY 1315 int max_length() const _NOEXCEPT 1316 { 1317 return do_max_length(); 1318 } 1319 1320 static locale::id id; 1321 1322protected: 1323 _LIBCPP_INLINE_VISIBILITY 1324 explicit codecvt(const char*, size_t __refs = 0) 1325 : locale::facet(__refs) {} 1326 1327 ~codecvt() override; 1328 1329 virtual result do_out(state_type& __st, 1330 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1331 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1332 virtual result do_in(state_type& __st, 1333 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1334 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const; 1335 virtual result do_unshift(state_type& __st, 1336 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1337 virtual int do_encoding() const _NOEXCEPT; 1338 virtual bool do_always_noconv() const _NOEXCEPT; 1339 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const; 1340 virtual int do_max_length() const _NOEXCEPT; 1341}; 1342 1343#ifndef _LIBCPP_HAS_NO_CHAR8_T 1344 1345// template <> class codecvt<char32_t, char8_t, mbstate_t> // C++20 1346 1347template <> 1348class _LIBCPP_EXPORTED_FROM_ABI codecvt<char32_t, char8_t, mbstate_t> 1349 : public locale::facet, 1350 public codecvt_base 1351{ 1352public: 1353 typedef char32_t intern_type; 1354 typedef char8_t extern_type; 1355 typedef mbstate_t state_type; 1356 1357 _LIBCPP_INLINE_VISIBILITY 1358 explicit codecvt(size_t __refs = 0) 1359 : locale::facet(__refs) {} 1360 1361 _LIBCPP_INLINE_VISIBILITY 1362 result out(state_type& __st, 1363 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1364 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1365 { 1366 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1367 } 1368 1369 _LIBCPP_INLINE_VISIBILITY 1370 result unshift(state_type& __st, 1371 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const 1372 { 1373 return do_unshift(__st, __to, __to_end, __to_nxt); 1374 } 1375 1376 _LIBCPP_INLINE_VISIBILITY 1377 result in(state_type& __st, 1378 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1379 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const 1380 { 1381 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt); 1382 } 1383 1384 _LIBCPP_INLINE_VISIBILITY 1385 int encoding() const _NOEXCEPT 1386 { 1387 return do_encoding(); 1388 } 1389 1390 _LIBCPP_INLINE_VISIBILITY 1391 bool always_noconv() const _NOEXCEPT 1392 { 1393 return do_always_noconv(); 1394 } 1395 1396 _LIBCPP_INLINE_VISIBILITY 1397 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const 1398 { 1399 return do_length(__st, __frm, __end, __mx); 1400 } 1401 1402 _LIBCPP_INLINE_VISIBILITY 1403 int max_length() const _NOEXCEPT 1404 { 1405 return do_max_length(); 1406 } 1407 1408 static locale::id id; 1409 1410protected: 1411 _LIBCPP_INLINE_VISIBILITY 1412 explicit codecvt(const char*, size_t __refs = 0) 1413 : locale::facet(__refs) {} 1414 1415 ~codecvt() override; 1416 1417 virtual result do_out(state_type& __st, 1418 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt, 1419 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1420 virtual result do_in(state_type& __st, 1421 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt, 1422 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const; 1423 virtual result do_unshift(state_type& __st, 1424 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const; 1425 virtual int do_encoding() const _NOEXCEPT; 1426 virtual bool do_always_noconv() const _NOEXCEPT; 1427 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const; 1428 virtual int do_max_length() const _NOEXCEPT; 1429}; 1430 1431#endif 1432 1433// template <class _InternT, class _ExternT, class _StateT> class codecvt_byname 1434 1435template <class _InternT, class _ExternT, class _StateT> 1436class _LIBCPP_TEMPLATE_VIS codecvt_byname 1437 : public codecvt<_InternT, _ExternT, _StateT> 1438{ 1439public: 1440 _LIBCPP_INLINE_VISIBILITY 1441 explicit codecvt_byname(const char* __nm, size_t __refs = 0) 1442 : codecvt<_InternT, _ExternT, _StateT>(__nm, __refs) {} 1443 _LIBCPP_INLINE_VISIBILITY 1444 explicit codecvt_byname(const string& __nm, size_t __refs = 0) 1445 : codecvt<_InternT, _ExternT, _StateT>(__nm.c_str(), __refs) {} 1446protected: 1447 ~codecvt_byname() override; 1448}; 1449 1450_LIBCPP_SUPPRESS_DEPRECATED_PUSH 1451template <class _InternT, class _ExternT, class _StateT> 1452codecvt_byname<_InternT, _ExternT, _StateT>::~codecvt_byname() 1453{ 1454} 1455_LIBCPP_SUPPRESS_DEPRECATED_POP 1456 1457extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char, char, mbstate_t>; 1458#ifndef _LIBCPP_HAS_NO_WIDE_CHARACTERS 1459extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<wchar_t, char, mbstate_t>; 1460#endif 1461extern template class _LIBCPP_DEPRECATED_IN_CXX20 _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char16_t, char, mbstate_t>; // deprecated in C++20 1462extern template class _LIBCPP_DEPRECATED_IN_CXX20 _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char32_t, char, mbstate_t>; // deprecated in C++20 1463#ifndef _LIBCPP_HAS_NO_CHAR8_T 1464extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char16_t, char8_t, mbstate_t>; // C++20 1465extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char32_t, char8_t, mbstate_t>; // C++20 1466#endif 1467 1468template <size_t _Np> 1469struct __narrow_to_utf8 1470{ 1471 template <class _OutputIterator, class _CharT> 1472 _OutputIterator 1473 operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const; 1474}; 1475 1476template <> 1477struct __narrow_to_utf8<8> 1478{ 1479 template <class _OutputIterator, class _CharT> 1480 _LIBCPP_INLINE_VISIBILITY 1481 _OutputIterator 1482 operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const 1483 { 1484 for (; __wb < __we; ++__wb, ++__s) 1485 *__s = *__wb; 1486 return __s; 1487 } 1488}; 1489 1490_LIBCPP_SUPPRESS_DEPRECATED_PUSH 1491template <> 1492struct _LIBCPP_EXPORTED_FROM_ABI __narrow_to_utf8<16> 1493 : public codecvt<char16_t, char, mbstate_t> 1494{ 1495 _LIBCPP_INLINE_VISIBILITY 1496 __narrow_to_utf8() : codecvt<char16_t, char, mbstate_t>(1) {} 1497_LIBCPP_SUPPRESS_DEPRECATED_POP 1498 1499 ~__narrow_to_utf8() override; 1500 1501 template <class _OutputIterator, class _CharT> 1502 _LIBCPP_INLINE_VISIBILITY 1503 _OutputIterator 1504 operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const 1505 { 1506 result __r = ok; 1507 mbstate_t __mb; 1508 while (__wb < __we && __r != error) 1509 { 1510 const int __sz = 32; 1511 char __buf[__sz]; 1512 char* __bn; 1513 const char16_t* __wn = (const char16_t*)__wb; 1514 __r = do_out(__mb, (const char16_t*)__wb, (const char16_t*)__we, __wn, 1515 __buf, __buf+__sz, __bn); 1516 if (__r == codecvt_base::error || __wn == (const char16_t*)__wb) 1517 __throw_runtime_error("locale not supported"); 1518 for (const char* __p = __buf; __p < __bn; ++__p, ++__s) 1519 *__s = *__p; 1520 __wb = (const _CharT*)__wn; 1521 } 1522 return __s; 1523 } 1524}; 1525 1526_LIBCPP_SUPPRESS_DEPRECATED_PUSH 1527template <> 1528struct _LIBCPP_EXPORTED_FROM_ABI __narrow_to_utf8<32> 1529 : public codecvt<char32_t, char, mbstate_t> 1530{ 1531 _LIBCPP_INLINE_VISIBILITY 1532 __narrow_to_utf8() : codecvt<char32_t, char, mbstate_t>(1) {} 1533_LIBCPP_SUPPRESS_DEPRECATED_POP 1534 1535 ~__narrow_to_utf8() override; 1536 1537 template <class _OutputIterator, class _CharT> 1538 _LIBCPP_INLINE_VISIBILITY 1539 _OutputIterator 1540 operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const 1541 { 1542 result __r = ok; 1543 mbstate_t __mb; 1544 while (__wb < __we && __r != error) 1545 { 1546 const int __sz = 32; 1547 char __buf[__sz]; 1548 char* __bn; 1549 const char32_t* __wn = (const char32_t*)__wb; 1550 __r = do_out(__mb, (const char32_t*)__wb, (const char32_t*)__we, __wn, 1551 __buf, __buf+__sz, __bn); 1552 if (__r == codecvt_base::error || __wn == (const char32_t*)__wb) 1553 __throw_runtime_error("locale not supported"); 1554 for (const char* __p = __buf; __p < __bn; ++__p, ++__s) 1555 *__s = *__p; 1556 __wb = (const _CharT*)__wn; 1557 } 1558 return __s; 1559 } 1560}; 1561 1562template <size_t _Np> 1563struct __widen_from_utf8 1564{ 1565 template <class _OutputIterator> 1566 _OutputIterator 1567 operator()(_OutputIterator __s, const char* __nb, const char* __ne) const; 1568}; 1569 1570template <> 1571struct __widen_from_utf8<8> 1572{ 1573 template <class _OutputIterator> 1574 _LIBCPP_INLINE_VISIBILITY 1575 _OutputIterator 1576 operator()(_OutputIterator __s, const char* __nb, const char* __ne) const 1577 { 1578 for (; __nb < __ne; ++__nb, ++__s) 1579 *__s = *__nb; 1580 return __s; 1581 } 1582}; 1583 1584_LIBCPP_SUPPRESS_DEPRECATED_PUSH 1585template <> 1586struct _LIBCPP_EXPORTED_FROM_ABI __widen_from_utf8<16> 1587 : public codecvt<char16_t, char, mbstate_t> 1588{ 1589 _LIBCPP_INLINE_VISIBILITY 1590 __widen_from_utf8() : codecvt<char16_t, char, mbstate_t>(1) {} 1591_LIBCPP_SUPPRESS_DEPRECATED_POP 1592 1593 ~__widen_from_utf8() override; 1594 1595 template <class _OutputIterator> 1596 _LIBCPP_INLINE_VISIBILITY 1597 _OutputIterator 1598 operator()(_OutputIterator __s, const char* __nb, const char* __ne) const 1599 { 1600 result __r = ok; 1601 mbstate_t __mb; 1602 while (__nb < __ne && __r != error) 1603 { 1604 const int __sz = 32; 1605 char16_t __buf[__sz]; 1606 char16_t* __bn; 1607 const char* __nn = __nb; 1608 __r = do_in(__mb, __nb, __ne - __nb > __sz ? __nb+__sz : __ne, __nn, 1609 __buf, __buf+__sz, __bn); 1610 if (__r == codecvt_base::error || __nn == __nb) 1611 __throw_runtime_error("locale not supported"); 1612 for (const char16_t* __p = __buf; __p < __bn; ++__p, ++__s) 1613 *__s = *__p; 1614 __nb = __nn; 1615 } 1616 return __s; 1617 } 1618}; 1619 1620_LIBCPP_SUPPRESS_DEPRECATED_PUSH 1621template <> 1622struct _LIBCPP_EXPORTED_FROM_ABI __widen_from_utf8<32> 1623 : public codecvt<char32_t, char, mbstate_t> 1624{ 1625 _LIBCPP_INLINE_VISIBILITY 1626 __widen_from_utf8() : codecvt<char32_t, char, mbstate_t>(1) {} 1627_LIBCPP_SUPPRESS_DEPRECATED_POP 1628 1629 ~__widen_from_utf8() override; 1630 1631 template <class _OutputIterator> 1632 _LIBCPP_INLINE_VISIBILITY 1633 _OutputIterator 1634 operator()(_OutputIterator __s, const char* __nb, const char* __ne) const 1635 { 1636 result __r = ok; 1637 mbstate_t __mb; 1638 while (__nb < __ne && __r != error) 1639 { 1640 const int __sz = 32; 1641 char32_t __buf[__sz]; 1642 char32_t* __bn; 1643 const char* __nn = __nb; 1644 __r = do_in(__mb, __nb, __ne - __nb > __sz ? __nb+__sz : __ne, __nn, 1645 __buf, __buf+__sz, __bn); 1646 if (__r == codecvt_base::error || __nn == __nb) 1647 __throw_runtime_error("locale not supported"); 1648 for (const char32_t* __p = __buf; __p < __bn; ++__p, ++__s) 1649 *__s = *__p; 1650 __nb = __nn; 1651 } 1652 return __s; 1653 } 1654}; 1655 1656// template <class charT> class numpunct 1657 1658template <class _CharT> class _LIBCPP_TEMPLATE_VIS numpunct; 1659 1660template <> 1661class _LIBCPP_EXPORTED_FROM_ABI numpunct<char> 1662 : public locale::facet 1663{ 1664public: 1665 typedef char char_type; 1666 typedef basic_string<char_type> string_type; 1667 1668 explicit numpunct(size_t __refs = 0); 1669 1670 _LIBCPP_INLINE_VISIBILITY char_type decimal_point() const {return do_decimal_point();} 1671 _LIBCPP_INLINE_VISIBILITY char_type thousands_sep() const {return do_thousands_sep();} 1672 _LIBCPP_INLINE_VISIBILITY string grouping() const {return do_grouping();} 1673 _LIBCPP_INLINE_VISIBILITY string_type truename() const {return do_truename();} 1674 _LIBCPP_INLINE_VISIBILITY string_type falsename() const {return do_falsename();} 1675 1676 static locale::id id; 1677 1678protected: 1679 ~numpunct() override; 1680 virtual char_type do_decimal_point() const; 1681 virtual char_type do_thousands_sep() const; 1682 virtual string do_grouping() const; 1683 virtual string_type do_truename() const; 1684 virtual string_type do_falsename() const; 1685 1686 char_type __decimal_point_; 1687 char_type __thousands_sep_; 1688 string __grouping_; 1689}; 1690 1691#ifndef _LIBCPP_HAS_NO_WIDE_CHARACTERS 1692template <> 1693class _LIBCPP_EXPORTED_FROM_ABI numpunct<wchar_t> 1694 : public locale::facet 1695{ 1696public: 1697 typedef wchar_t char_type; 1698 typedef basic_string<char_type> string_type; 1699 1700 explicit numpunct(size_t __refs = 0); 1701 1702 _LIBCPP_INLINE_VISIBILITY char_type decimal_point() const {return do_decimal_point();} 1703 _LIBCPP_INLINE_VISIBILITY char_type thousands_sep() const {return do_thousands_sep();} 1704 _LIBCPP_INLINE_VISIBILITY string grouping() const {return do_grouping();} 1705 _LIBCPP_INLINE_VISIBILITY string_type truename() const {return do_truename();} 1706 _LIBCPP_INLINE_VISIBILITY string_type falsename() const {return do_falsename();} 1707 1708 static locale::id id; 1709 1710protected: 1711 ~numpunct() override; 1712 virtual char_type do_decimal_point() const; 1713 virtual char_type do_thousands_sep() const; 1714 virtual string do_grouping() const; 1715 virtual string_type do_truename() const; 1716 virtual string_type do_falsename() const; 1717 1718 char_type __decimal_point_; 1719 char_type __thousands_sep_; 1720 string __grouping_; 1721}; 1722#endif // _LIBCPP_HAS_NO_WIDE_CHARACTERS 1723 1724// template <class charT> class numpunct_byname 1725 1726template <class _CharT> class _LIBCPP_TEMPLATE_VIS numpunct_byname; 1727 1728template <> 1729class _LIBCPP_EXPORTED_FROM_ABI numpunct_byname<char> 1730: public numpunct<char> 1731{ 1732public: 1733 typedef char char_type; 1734 typedef basic_string<char_type> string_type; 1735 1736 explicit numpunct_byname(const char* __nm, size_t __refs = 0); 1737 explicit numpunct_byname(const string& __nm, size_t __refs = 0); 1738 1739protected: 1740 ~numpunct_byname() override; 1741 1742private: 1743 void __init(const char*); 1744}; 1745 1746#ifndef _LIBCPP_HAS_NO_WIDE_CHARACTERS 1747template <> 1748class _LIBCPP_EXPORTED_FROM_ABI numpunct_byname<wchar_t> 1749: public numpunct<wchar_t> 1750{ 1751public: 1752 typedef wchar_t char_type; 1753 typedef basic_string<char_type> string_type; 1754 1755 explicit numpunct_byname(const char* __nm, size_t __refs = 0); 1756 explicit numpunct_byname(const string& __nm, size_t __refs = 0); 1757 1758protected: 1759 ~numpunct_byname() override; 1760 1761private: 1762 void __init(const char*); 1763}; 1764#endif // _LIBCPP_HAS_NO_WIDE_CHARACTERS 1765 1766_LIBCPP_END_NAMESPACE_STD 1767 1768#endif // _LIBCPP___LOCALE 1769