Warning, /include/c++/v1/__locale is written in an unsupported language. File is not indexed.
0001 // -*- C++ -*-
0002 //===----------------------------------------------------------------------===//
0003 //
0004 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
0005 // See https://llvm.org/LICENSE.txt for license information.
0006 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
0007 //
0008 //===----------------------------------------------------------------------===//
0009
0010 #ifndef _LIBCPP___LOCALE
0011 #define _LIBCPP___LOCALE
0012
0013 #include <__config>
0014
0015 #if _LIBCPP_HAS_LOCALIZATION
0016
0017 #include <__locale_dir/locale_base_api.h>
0018 #include <__memory/shared_count.h>
0019 #include <__mutex/once_flag.h>
0020 #include <__type_traits/make_unsigned.h>
0021 #include <__utility/no_destroy.h>
0022 #include <__utility/private_constructor_tag.h>
0023 #include <cctype>
0024 #include <clocale>
0025 #include <cstdint>
0026 #include <cstdlib>
0027 #include <string>
0028
0029 // Some platforms require more includes than others. Keep the includes on all plaforms for now.
0030 # include <cstddef>
0031 # include <cstring>
0032
0033 # if _LIBCPP_HAS_WIDE_CHARACTERS
0034 # include <cwchar>
0035 # else
0036 # include <__std_mbstate_t.h>
0037 # endif
0038
0039 # if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
0040 # pragma GCC system_header
0041 # endif
0042
0043 _LIBCPP_BEGIN_NAMESPACE_STD
0044
0045 class _LIBCPP_EXPORTED_FROM_ABI locale;
0046
0047 template <class _Facet>
0048 _LIBCPP_HIDE_FROM_ABI bool has_facet(const locale&) _NOEXCEPT;
0049
0050 template <class _Facet>
0051 _LIBCPP_HIDE_FROM_ABI const _Facet& use_facet(const locale&);
0052
0053 class _LIBCPP_EXPORTED_FROM_ABI locale {
0054 public:
0055 // locale is essentially a shared_ptr that doesn't support weak_ptrs and never got a move constructor.
0056 using __trivially_relocatable _LIBCPP_NODEBUG = locale;
0057
0058 // types:
0059 class _LIBCPP_EXPORTED_FROM_ABI facet;
0060 class _LIBCPP_EXPORTED_FROM_ABI id;
0061
0062 typedef int category;
0063
0064 static const category // values assigned here are for exposition only
0065 none = 0,
0066 collate = _LIBCPP_COLLATE_MASK, ctype = _LIBCPP_CTYPE_MASK, monetary = _LIBCPP_MONETARY_MASK,
0067 numeric = _LIBCPP_NUMERIC_MASK, time = _LIBCPP_TIME_MASK, messages = _LIBCPP_MESSAGES_MASK,
0068 all = collate | ctype | monetary | numeric | time | messages;
0069
0070 // construct/copy/destroy:
0071 locale() _NOEXCEPT;
0072 locale(const locale&) _NOEXCEPT;
0073 explicit locale(const char*);
0074 explicit locale(const string&);
0075 locale(const locale&, const char*, category);
0076 locale(const locale&, const string&, category);
0077 template <class _Facet>
0078 _LIBCPP_HIDE_FROM_ABI locale(const locale&, _Facet*);
0079 locale(const locale&, const locale&, category);
0080
0081 ~locale();
0082
0083 const locale& operator=(const locale&) _NOEXCEPT;
0084
0085 template <class _Facet>
0086 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS locale combine(const locale&) const;
0087
0088 // locale operations:
0089 string name() const;
0090 bool operator==(const locale&) const;
0091 # if _LIBCPP_STD_VER <= 17
0092 _LIBCPP_HIDE_FROM_ABI bool operator!=(const locale& __y) const { return !(*this == __y); }
0093 # endif
0094 template <class _CharT, class _Traits, class _Allocator>
0095 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS bool
0096 operator()(const basic_string<_CharT, _Traits, _Allocator>&, const basic_string<_CharT, _Traits, _Allocator>&) const;
0097
0098 // global locale objects:
0099 static locale global(const locale&);
0100 static const locale& classic();
0101
0102 private:
0103 class __imp;
0104 __imp* __locale_;
0105
0106 template <class>
0107 friend struct __no_destroy;
0108 _LIBCPP_HIDE_FROM_ABI explicit locale(__private_constructor_tag, __imp* __loc) : __locale_(__loc) {}
0109
0110 void __install_ctor(const locale&, facet*, long);
0111 static locale& __global();
0112 bool has_facet(id&) const;
0113 const facet* use_facet(id&) const;
0114
0115 template <class _Facet>
0116 friend bool has_facet(const locale&) _NOEXCEPT;
0117 template <class _Facet>
0118 friend const _Facet& use_facet(const locale&);
0119 };
0120
0121 class _LIBCPP_EXPORTED_FROM_ABI locale::facet : public __shared_count {
0122 protected:
0123 _LIBCPP_HIDE_FROM_ABI explicit facet(size_t __refs = 0) : __shared_count(static_cast<long>(__refs) - 1) {}
0124
0125 ~facet() override;
0126
0127 // facet(const facet&) = delete; // effectively done in __shared_count
0128 // void operator=(const facet&) = delete;
0129
0130 private:
0131 void __on_zero_shared() _NOEXCEPT override;
0132 };
0133
0134 class _LIBCPP_EXPORTED_FROM_ABI locale::id {
0135 once_flag __flag_;
0136 int32_t __id_;
0137
0138 static int32_t __next_id;
0139
0140 public:
0141 _LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR id() : __id_(0) {}
0142 void operator=(const id&) = delete;
0143 id(const id&) = delete;
0144
0145 public: // only needed for tests
0146 long __get();
0147
0148 friend class locale;
0149 friend class locale::__imp;
0150 };
0151
0152 template <class _Facet>
0153 inline _LIBCPP_HIDE_FROM_ABI locale::locale(const locale& __other, _Facet* __f) {
0154 __install_ctor(__other, __f, __f ? __f->id.__get() : 0);
0155 }
0156
0157 template <class _Facet>
0158 locale locale::combine(const locale& __other) const {
0159 if (!std::has_facet<_Facet>(__other))
0160 __throw_runtime_error("locale::combine: locale missing facet");
0161
0162 return locale(*this, &const_cast<_Facet&>(std::use_facet<_Facet>(__other)));
0163 }
0164
0165 template <class _Facet>
0166 inline _LIBCPP_HIDE_FROM_ABI bool has_facet(const locale& __l) _NOEXCEPT {
0167 return __l.has_facet(_Facet::id);
0168 }
0169
0170 template <class _Facet>
0171 inline _LIBCPP_HIDE_FROM_ABI const _Facet& use_facet(const locale& __l) {
0172 return static_cast<const _Facet&>(*__l.use_facet(_Facet::id));
0173 }
0174
0175 // template <class _CharT> class collate;
0176
0177 template <class _CharT>
0178 class _LIBCPP_TEMPLATE_VIS collate : public locale::facet {
0179 public:
0180 typedef _CharT char_type;
0181 typedef basic_string<char_type> string_type;
0182
0183 _LIBCPP_HIDE_FROM_ABI explicit collate(size_t __refs = 0) : locale::facet(__refs) {}
0184
0185 _LIBCPP_HIDE_FROM_ABI int
0186 compare(const char_type* __lo1, const char_type* __hi1, const char_type* __lo2, const char_type* __hi2) const {
0187 return do_compare(__lo1, __hi1, __lo2, __hi2);
0188 }
0189
0190 // FIXME(EricWF): The _LIBCPP_ALWAYS_INLINE is needed on Windows to work
0191 // around a dllimport bug that expects an external instantiation.
0192 _LIBCPP_HIDE_FROM_ABI _LIBCPP_ALWAYS_INLINE string_type
0193 transform(const char_type* __lo, const char_type* __hi) const {
0194 return do_transform(__lo, __hi);
0195 }
0196
0197 _LIBCPP_HIDE_FROM_ABI long hash(const char_type* __lo, const char_type* __hi) const { return do_hash(__lo, __hi); }
0198
0199 static locale::id id;
0200
0201 protected:
0202 ~collate() override;
0203 virtual int
0204 do_compare(const char_type* __lo1, const char_type* __hi1, const char_type* __lo2, const char_type* __hi2) const;
0205 virtual string_type do_transform(const char_type* __lo, const char_type* __hi) const {
0206 return string_type(__lo, __hi);
0207 }
0208 virtual long do_hash(const char_type* __lo, const char_type* __hi) const;
0209 };
0210
0211 template <class _CharT>
0212 locale::id collate<_CharT>::id;
0213
0214 template <class _CharT>
0215 collate<_CharT>::~collate() {}
0216
0217 template <class _CharT>
0218 int collate<_CharT>::do_compare(
0219 const char_type* __lo1, const char_type* __hi1, const char_type* __lo2, const char_type* __hi2) const {
0220 for (; __lo2 != __hi2; ++__lo1, ++__lo2) {
0221 if (__lo1 == __hi1 || *__lo1 < *__lo2)
0222 return -1;
0223 if (*__lo2 < *__lo1)
0224 return 1;
0225 }
0226 return __lo1 != __hi1;
0227 }
0228
0229 template <class _CharT>
0230 long collate<_CharT>::do_hash(const char_type* __lo, const char_type* __hi) const {
0231 size_t __h = 0;
0232 const size_t __sr = __CHAR_BIT__ * sizeof(size_t) - 8;
0233 const size_t __mask = size_t(0xF) << (__sr + 4);
0234 for (const char_type* __p = __lo; __p != __hi; ++__p) {
0235 __h = (__h << 4) + static_cast<size_t>(*__p);
0236 size_t __g = __h & __mask;
0237 __h ^= __g | (__g >> __sr);
0238 }
0239 return static_cast<long>(__h);
0240 }
0241
0242 extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS collate<char>;
0243 # if _LIBCPP_HAS_WIDE_CHARACTERS
0244 extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS collate<wchar_t>;
0245 # endif
0246
0247 // template <class CharT> class collate_byname;
0248
0249 template <class _CharT>
0250 class _LIBCPP_TEMPLATE_VIS collate_byname;
0251
0252 template <>
0253 class _LIBCPP_EXPORTED_FROM_ABI collate_byname<char> : public collate<char> {
0254 __locale::__locale_t __l_;
0255
0256 public:
0257 typedef char char_type;
0258 typedef basic_string<char_type> string_type;
0259
0260 explicit collate_byname(const char* __n, size_t __refs = 0);
0261 explicit collate_byname(const string& __n, size_t __refs = 0);
0262
0263 protected:
0264 ~collate_byname() override;
0265 int do_compare(
0266 const char_type* __lo1, const char_type* __hi1, const char_type* __lo2, const char_type* __hi2) const override;
0267 string_type do_transform(const char_type* __lo, const char_type* __hi) const override;
0268 };
0269
0270 # if _LIBCPP_HAS_WIDE_CHARACTERS
0271 template <>
0272 class _LIBCPP_EXPORTED_FROM_ABI collate_byname<wchar_t> : public collate<wchar_t> {
0273 __locale::__locale_t __l_;
0274
0275 public:
0276 typedef wchar_t char_type;
0277 typedef basic_string<char_type> string_type;
0278
0279 explicit collate_byname(const char* __n, size_t __refs = 0);
0280 explicit collate_byname(const string& __n, size_t __refs = 0);
0281
0282 protected:
0283 ~collate_byname() override;
0284
0285 int do_compare(
0286 const char_type* __lo1, const char_type* __hi1, const char_type* __lo2, const char_type* __hi2) const override;
0287 string_type do_transform(const char_type* __lo, const char_type* __hi) const override;
0288 };
0289 # endif
0290
0291 template <class _CharT, class _Traits, class _Allocator>
0292 bool locale::operator()(const basic_string<_CharT, _Traits, _Allocator>& __x,
0293 const basic_string<_CharT, _Traits, _Allocator>& __y) const {
0294 return std::use_facet<std::collate<_CharT> >(*this).compare(
0295 __x.data(), __x.data() + __x.size(), __y.data(), __y.data() + __y.size()) < 0;
0296 }
0297
0298 // template <class charT> class ctype
0299
0300 class _LIBCPP_EXPORTED_FROM_ABI ctype_base {
0301 public:
0302 # if defined(_LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE)
0303 typedef unsigned long mask;
0304 static const mask space = 1 << 0;
0305 static const mask print = 1 << 1;
0306 static const mask cntrl = 1 << 2;
0307 static const mask upper = 1 << 3;
0308 static const mask lower = 1 << 4;
0309 static const mask alpha = 1 << 5;
0310 static const mask digit = 1 << 6;
0311 static const mask punct = 1 << 7;
0312 static const mask xdigit = 1 << 8;
0313 static const mask blank = 1 << 9;
0314 # if defined(__BIONIC__)
0315 // Historically this was a part of regex_traits rather than ctype_base. The
0316 // historical value of the constant is preserved for ABI compatibility.
0317 static const mask __regex_word = 0x8000;
0318 # else
0319 static const mask __regex_word = 1 << 10;
0320 # endif // defined(__BIONIC__)
0321 # elif defined(__GLIBC__)
0322 typedef unsigned short mask;
0323 static const mask space = _ISspace;
0324 static const mask print = _ISprint;
0325 static const mask cntrl = _IScntrl;
0326 static const mask upper = _ISupper;
0327 static const mask lower = _ISlower;
0328 static const mask alpha = _ISalpha;
0329 static const mask digit = _ISdigit;
0330 static const mask punct = _ISpunct;
0331 static const mask xdigit = _ISxdigit;
0332 static const mask blank = _ISblank;
0333 # if defined(__mips__) || (BYTE_ORDER == BIG_ENDIAN)
0334 static const mask __regex_word = static_cast<mask>(_ISbit(15));
0335 # else
0336 static const mask __regex_word = 0x80;
0337 # endif
0338 # elif defined(_LIBCPP_MSVCRT_LIKE)
0339 typedef unsigned short mask;
0340 static const mask space = _SPACE;
0341 static const mask print = _BLANK | _PUNCT | _ALPHA | _DIGIT;
0342 static const mask cntrl = _CONTROL;
0343 static const mask upper = _UPPER;
0344 static const mask lower = _LOWER;
0345 static const mask alpha = _ALPHA;
0346 static const mask digit = _DIGIT;
0347 static const mask punct = _PUNCT;
0348 static const mask xdigit = _HEX;
0349 static const mask blank = _BLANK;
0350 static const mask __regex_word = 0x4000; // 0x8000 and 0x0100 and 0x00ff are used
0351 # define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT
0352 # define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_ALPHA
0353 # elif defined(__APPLE__) || defined(__FreeBSD__) || defined(__NetBSD__)
0354 # ifdef __APPLE__
0355 typedef uint32_t mask;
0356 # elif defined(__FreeBSD__)
0357 typedef unsigned long mask;
0358 # elif defined(__NetBSD__)
0359 typedef unsigned short mask;
0360 # endif
0361 static const mask space = _CTYPE_S;
0362 static const mask print = _CTYPE_R;
0363 static const mask cntrl = _CTYPE_C;
0364 static const mask upper = _CTYPE_U;
0365 static const mask lower = _CTYPE_L;
0366 static const mask alpha = _CTYPE_A;
0367 static const mask digit = _CTYPE_D;
0368 static const mask punct = _CTYPE_P;
0369 static const mask xdigit = _CTYPE_X;
0370
0371 # if defined(__NetBSD__)
0372 static const mask blank = _CTYPE_BL;
0373 // NetBSD defines classes up to 0x2000
0374 // see sys/ctype_bits.h, _CTYPE_Q
0375 static const mask __regex_word = 0x8000;
0376 # else
0377 static const mask blank = _CTYPE_B;
0378 static const mask __regex_word = 0x80;
0379 # endif
0380 # elif defined(_AIX)
0381 typedef unsigned int mask;
0382 static const mask space = _ISSPACE;
0383 static const mask print = _ISPRINT;
0384 static const mask cntrl = _ISCNTRL;
0385 static const mask upper = _ISUPPER;
0386 static const mask lower = _ISLOWER;
0387 static const mask alpha = _ISALPHA;
0388 static const mask digit = _ISDIGIT;
0389 static const mask punct = _ISPUNCT;
0390 static const mask xdigit = _ISXDIGIT;
0391 static const mask blank = _ISBLANK;
0392 static const mask __regex_word = 0x8000;
0393 # elif defined(_NEWLIB_VERSION)
0394 // Same type as Newlib's _ctype_ array in newlib/libc/include/ctype.h.
0395 typedef char mask;
0396 // In case char is signed, static_cast is needed to avoid warning on
0397 // positive value becomming negative.
0398 static const mask space = static_cast<mask>(_S);
0399 static const mask print = static_cast<mask>(_P | _U | _L | _N | _B);
0400 static const mask cntrl = static_cast<mask>(_C);
0401 static const mask upper = static_cast<mask>(_U);
0402 static const mask lower = static_cast<mask>(_L);
0403 static const mask alpha = static_cast<mask>(_U | _L);
0404 static const mask digit = static_cast<mask>(_N);
0405 static const mask punct = static_cast<mask>(_P);
0406 static const mask xdigit = static_cast<mask>(_X | _N);
0407 static const mask blank = static_cast<mask>(_B);
0408 // mask is already fully saturated, use a different type in regex_type_traits.
0409 static const unsigned short __regex_word = 0x100;
0410 # define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT
0411 # define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_ALPHA
0412 # define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_XDIGIT
0413 # elif defined(__MVS__)
0414 # if defined(__NATIVE_ASCII_F)
0415 typedef unsigned int mask;
0416 static const mask space = _ISSPACE_A;
0417 static const mask print = _ISPRINT_A;
0418 static const mask cntrl = _ISCNTRL_A;
0419 static const mask upper = _ISUPPER_A;
0420 static const mask lower = _ISLOWER_A;
0421 static const mask alpha = _ISALPHA_A;
0422 static const mask digit = _ISDIGIT_A;
0423 static const mask punct = _ISPUNCT_A;
0424 static const mask xdigit = _ISXDIGIT_A;
0425 static const mask blank = _ISBLANK_A;
0426 # else
0427 typedef unsigned short mask;
0428 static const mask space = __ISSPACE;
0429 static const mask print = __ISPRINT;
0430 static const mask cntrl = __ISCNTRL;
0431 static const mask upper = __ISUPPER;
0432 static const mask lower = __ISLOWER;
0433 static const mask alpha = __ISALPHA;
0434 static const mask digit = __ISDIGIT;
0435 static const mask punct = __ISPUNCT;
0436 static const mask xdigit = __ISXDIGIT;
0437 static const mask blank = __ISBLANK;
0438 # endif
0439 static const mask __regex_word = 0x8000;
0440 # else
0441 # error unknown rune table for this platform -- do you mean to define _LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE?
0442 # endif
0443 static const mask alnum = alpha | digit;
0444 static const mask graph = alnum | punct;
0445
0446 _LIBCPP_HIDE_FROM_ABI ctype_base() {}
0447
0448 static_assert((__regex_word & ~(std::make_unsigned<mask>::type)(space | print | cntrl | upper | lower | alpha |
0449 digit | punct | xdigit | blank)) == __regex_word,
0450 "__regex_word can't overlap other bits");
0451 };
0452
0453 template <class _CharT>
0454 class _LIBCPP_TEMPLATE_VIS ctype;
0455
0456 # if _LIBCPP_HAS_WIDE_CHARACTERS
0457 template <>
0458 class _LIBCPP_EXPORTED_FROM_ABI ctype<wchar_t> : public locale::facet, public ctype_base {
0459 public:
0460 typedef wchar_t char_type;
0461
0462 _LIBCPP_HIDE_FROM_ABI explicit ctype(size_t __refs = 0) : locale::facet(__refs) {}
0463
0464 _LIBCPP_HIDE_FROM_ABI bool is(mask __m, char_type __c) const { return do_is(__m, __c); }
0465
0466 _LIBCPP_HIDE_FROM_ABI const char_type* is(const char_type* __low, const char_type* __high, mask* __vec) const {
0467 return do_is(__low, __high, __vec);
0468 }
0469
0470 _LIBCPP_HIDE_FROM_ABI const char_type* scan_is(mask __m, const char_type* __low, const char_type* __high) const {
0471 return do_scan_is(__m, __low, __high);
0472 }
0473
0474 _LIBCPP_HIDE_FROM_ABI const char_type* scan_not(mask __m, const char_type* __low, const char_type* __high) const {
0475 return do_scan_not(__m, __low, __high);
0476 }
0477
0478 _LIBCPP_HIDE_FROM_ABI char_type toupper(char_type __c) const { return do_toupper(__c); }
0479
0480 _LIBCPP_HIDE_FROM_ABI const char_type* toupper(char_type* __low, const char_type* __high) const {
0481 return do_toupper(__low, __high);
0482 }
0483
0484 _LIBCPP_HIDE_FROM_ABI char_type tolower(char_type __c) const { return do_tolower(__c); }
0485
0486 _LIBCPP_HIDE_FROM_ABI const char_type* tolower(char_type* __low, const char_type* __high) const {
0487 return do_tolower(__low, __high);
0488 }
0489
0490 _LIBCPP_HIDE_FROM_ABI char_type widen(char __c) const { return do_widen(__c); }
0491
0492 _LIBCPP_HIDE_FROM_ABI const char* widen(const char* __low, const char* __high, char_type* __to) const {
0493 return do_widen(__low, __high, __to);
0494 }
0495
0496 _LIBCPP_HIDE_FROM_ABI char narrow(char_type __c, char __dfault) const { return do_narrow(__c, __dfault); }
0497
0498 _LIBCPP_HIDE_FROM_ABI const char_type*
0499 narrow(const char_type* __low, const char_type* __high, char __dfault, char* __to) const {
0500 return do_narrow(__low, __high, __dfault, __to);
0501 }
0502
0503 static locale::id id;
0504
0505 protected:
0506 ~ctype() override;
0507 virtual bool do_is(mask __m, char_type __c) const;
0508 virtual const char_type* do_is(const char_type* __low, const char_type* __high, mask* __vec) const;
0509 virtual const char_type* do_scan_is(mask __m, const char_type* __low, const char_type* __high) const;
0510 virtual const char_type* do_scan_not(mask __m, const char_type* __low, const char_type* __high) const;
0511 virtual char_type do_toupper(char_type) const;
0512 virtual const char_type* do_toupper(char_type* __low, const char_type* __high) const;
0513 virtual char_type do_tolower(char_type) const;
0514 virtual const char_type* do_tolower(char_type* __low, const char_type* __high) const;
0515 virtual char_type do_widen(char) const;
0516 virtual const char* do_widen(const char* __low, const char* __high, char_type* __dest) const;
0517 virtual char do_narrow(char_type, char __dfault) const;
0518 virtual const char_type*
0519 do_narrow(const char_type* __low, const char_type* __high, char __dfault, char* __dest) const;
0520 };
0521 # endif // _LIBCPP_HAS_WIDE_CHARACTERS
0522
0523 inline _LIBCPP_HIDE_FROM_ABI bool __libcpp_isascii(int __c) { return (__c & ~0x7F) == 0; }
0524
0525 template <>
0526 class _LIBCPP_EXPORTED_FROM_ABI ctype<char> : public locale::facet, public ctype_base {
0527 const mask* __tab_;
0528 bool __del_;
0529
0530 public:
0531 typedef char char_type;
0532
0533 explicit ctype(const mask* __tab = nullptr, bool __del = false, size_t __refs = 0);
0534
0535 _LIBCPP_HIDE_FROM_ABI bool is(mask __m, char_type __c) const {
0536 return std::__libcpp_isascii(__c) ? (__tab_[static_cast<int>(__c)] & __m) != 0 : false;
0537 }
0538
0539 _LIBCPP_HIDE_FROM_ABI const char_type* is(const char_type* __low, const char_type* __high, mask* __vec) const {
0540 for (; __low != __high; ++__low, ++__vec)
0541 *__vec = std::__libcpp_isascii(*__low) ? __tab_[static_cast<int>(*__low)] : 0;
0542 return __low;
0543 }
0544
0545 _LIBCPP_HIDE_FROM_ABI const char_type* scan_is(mask __m, const char_type* __low, const char_type* __high) const {
0546 for (; __low != __high; ++__low)
0547 if (std::__libcpp_isascii(*__low) && (__tab_[static_cast<int>(*__low)] & __m))
0548 break;
0549 return __low;
0550 }
0551
0552 _LIBCPP_HIDE_FROM_ABI const char_type* scan_not(mask __m, const char_type* __low, const char_type* __high) const {
0553 for (; __low != __high; ++__low)
0554 if (!std::__libcpp_isascii(*__low) || !(__tab_[static_cast<int>(*__low)] & __m))
0555 break;
0556 return __low;
0557 }
0558
0559 _LIBCPP_HIDE_FROM_ABI char_type toupper(char_type __c) const { return do_toupper(__c); }
0560
0561 _LIBCPP_HIDE_FROM_ABI const char_type* toupper(char_type* __low, const char_type* __high) const {
0562 return do_toupper(__low, __high);
0563 }
0564
0565 _LIBCPP_HIDE_FROM_ABI char_type tolower(char_type __c) const { return do_tolower(__c); }
0566
0567 _LIBCPP_HIDE_FROM_ABI const char_type* tolower(char_type* __low, const char_type* __high) const {
0568 return do_tolower(__low, __high);
0569 }
0570
0571 _LIBCPP_HIDE_FROM_ABI char_type widen(char __c) const { return do_widen(__c); }
0572
0573 _LIBCPP_HIDE_FROM_ABI const char* widen(const char* __low, const char* __high, char_type* __to) const {
0574 return do_widen(__low, __high, __to);
0575 }
0576
0577 _LIBCPP_HIDE_FROM_ABI char narrow(char_type __c, char __dfault) const { return do_narrow(__c, __dfault); }
0578
0579 _LIBCPP_HIDE_FROM_ABI const char*
0580 narrow(const char_type* __low, const char_type* __high, char __dfault, char* __to) const {
0581 return do_narrow(__low, __high, __dfault, __to);
0582 }
0583
0584 static locale::id id;
0585
0586 # ifdef _CACHED_RUNES
0587 static const size_t table_size = _CACHED_RUNES;
0588 # else
0589 static const size_t table_size = 256; // FIXME: Don't hardcode this.
0590 # endif
0591 _LIBCPP_HIDE_FROM_ABI const mask* table() const _NOEXCEPT { return __tab_; }
0592 static const mask* classic_table() _NOEXCEPT;
0593 # if defined(__GLIBC__) || defined(__EMSCRIPTEN__)
0594 static const int* __classic_upper_table() _NOEXCEPT;
0595 static const int* __classic_lower_table() _NOEXCEPT;
0596 # endif
0597 # if defined(__NetBSD__)
0598 static const short* __classic_upper_table() _NOEXCEPT;
0599 static const short* __classic_lower_table() _NOEXCEPT;
0600 # endif
0601 # if defined(__MVS__)
0602 static const unsigned short* __classic_upper_table() _NOEXCEPT;
0603 static const unsigned short* __classic_lower_table() _NOEXCEPT;
0604 # endif
0605
0606 protected:
0607 ~ctype() override;
0608 virtual char_type do_toupper(char_type __c) const;
0609 virtual const char_type* do_toupper(char_type* __low, const char_type* __high) const;
0610 virtual char_type do_tolower(char_type __c) const;
0611 virtual const char_type* do_tolower(char_type* __low, const char_type* __high) const;
0612 virtual char_type do_widen(char __c) const;
0613 virtual const char* do_widen(const char* __low, const char* __high, char_type* __to) const;
0614 virtual char do_narrow(char_type __c, char __dfault) const;
0615 virtual const char* do_narrow(const char_type* __low, const char_type* __high, char __dfault, char* __to) const;
0616 };
0617
0618 // template <class CharT> class ctype_byname;
0619
0620 template <class _CharT>
0621 class _LIBCPP_TEMPLATE_VIS ctype_byname;
0622
0623 template <>
0624 class _LIBCPP_EXPORTED_FROM_ABI ctype_byname<char> : public ctype<char> {
0625 __locale::__locale_t __l_;
0626
0627 public:
0628 explicit ctype_byname(const char*, size_t = 0);
0629 explicit ctype_byname(const string&, size_t = 0);
0630
0631 protected:
0632 ~ctype_byname() override;
0633 char_type do_toupper(char_type) const override;
0634 const char_type* do_toupper(char_type* __low, const char_type* __high) const override;
0635 char_type do_tolower(char_type) const override;
0636 const char_type* do_tolower(char_type* __low, const char_type* __high) const override;
0637 };
0638
0639 # if _LIBCPP_HAS_WIDE_CHARACTERS
0640 template <>
0641 class _LIBCPP_EXPORTED_FROM_ABI ctype_byname<wchar_t> : public ctype<wchar_t> {
0642 __locale::__locale_t __l_;
0643
0644 public:
0645 explicit ctype_byname(const char*, size_t = 0);
0646 explicit ctype_byname(const string&, size_t = 0);
0647
0648 protected:
0649 ~ctype_byname() override;
0650 bool do_is(mask __m, char_type __c) const override;
0651 const char_type* do_is(const char_type* __low, const char_type* __high, mask* __vec) const override;
0652 const char_type* do_scan_is(mask __m, const char_type* __low, const char_type* __high) const override;
0653 const char_type* do_scan_not(mask __m, const char_type* __low, const char_type* __high) const override;
0654 char_type do_toupper(char_type) const override;
0655 const char_type* do_toupper(char_type* __low, const char_type* __high) const override;
0656 char_type do_tolower(char_type) const override;
0657 const char_type* do_tolower(char_type* __low, const char_type* __high) const override;
0658 char_type do_widen(char) const override;
0659 const char* do_widen(const char* __low, const char* __high, char_type* __dest) const override;
0660 char do_narrow(char_type, char __dfault) const override;
0661 const char_type*
0662 do_narrow(const char_type* __low, const char_type* __high, char __dfault, char* __dest) const override;
0663 };
0664 # endif // _LIBCPP_HAS_WIDE_CHARACTERS
0665
0666 template <class _CharT>
0667 inline _LIBCPP_HIDE_FROM_ABI bool isspace(_CharT __c, const locale& __loc) {
0668 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::space, __c);
0669 }
0670
0671 template <class _CharT>
0672 inline _LIBCPP_HIDE_FROM_ABI bool isprint(_CharT __c, const locale& __loc) {
0673 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::print, __c);
0674 }
0675
0676 template <class _CharT>
0677 inline _LIBCPP_HIDE_FROM_ABI bool iscntrl(_CharT __c, const locale& __loc) {
0678 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::cntrl, __c);
0679 }
0680
0681 template <class _CharT>
0682 inline _LIBCPP_HIDE_FROM_ABI bool isupper(_CharT __c, const locale& __loc) {
0683 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::upper, __c);
0684 }
0685
0686 template <class _CharT>
0687 inline _LIBCPP_HIDE_FROM_ABI bool islower(_CharT __c, const locale& __loc) {
0688 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::lower, __c);
0689 }
0690
0691 template <class _CharT>
0692 inline _LIBCPP_HIDE_FROM_ABI bool isalpha(_CharT __c, const locale& __loc) {
0693 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::alpha, __c);
0694 }
0695
0696 template <class _CharT>
0697 inline _LIBCPP_HIDE_FROM_ABI bool isdigit(_CharT __c, const locale& __loc) {
0698 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::digit, __c);
0699 }
0700
0701 template <class _CharT>
0702 inline _LIBCPP_HIDE_FROM_ABI bool ispunct(_CharT __c, const locale& __loc) {
0703 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::punct, __c);
0704 }
0705
0706 template <class _CharT>
0707 inline _LIBCPP_HIDE_FROM_ABI bool isxdigit(_CharT __c, const locale& __loc) {
0708 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::xdigit, __c);
0709 }
0710
0711 template <class _CharT>
0712 inline _LIBCPP_HIDE_FROM_ABI bool isalnum(_CharT __c, const locale& __loc) {
0713 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::alnum, __c);
0714 }
0715
0716 template <class _CharT>
0717 inline _LIBCPP_HIDE_FROM_ABI bool isgraph(_CharT __c, const locale& __loc) {
0718 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::graph, __c);
0719 }
0720
0721 template <class _CharT>
0722 _LIBCPP_HIDE_FROM_ABI bool isblank(_CharT __c, const locale& __loc) {
0723 return std::use_facet<ctype<_CharT> >(__loc).is(ctype_base::blank, __c);
0724 }
0725
0726 template <class _CharT>
0727 inline _LIBCPP_HIDE_FROM_ABI _CharT toupper(_CharT __c, const locale& __loc) {
0728 return std::use_facet<ctype<_CharT> >(__loc).toupper(__c);
0729 }
0730
0731 template <class _CharT>
0732 inline _LIBCPP_HIDE_FROM_ABI _CharT tolower(_CharT __c, const locale& __loc) {
0733 return std::use_facet<ctype<_CharT> >(__loc).tolower(__c);
0734 }
0735
0736 // codecvt_base
0737
0738 class _LIBCPP_EXPORTED_FROM_ABI codecvt_base {
0739 public:
0740 _LIBCPP_HIDE_FROM_ABI codecvt_base() {}
0741 enum result { ok, partial, error, noconv };
0742 };
0743
0744 // template <class internT, class externT, class stateT> class codecvt;
0745
0746 template <class _InternT, class _ExternT, class _StateT>
0747 class _LIBCPP_TEMPLATE_VIS codecvt;
0748
0749 // template <> class codecvt<char, char, mbstate_t>
0750
0751 template <>
0752 class _LIBCPP_EXPORTED_FROM_ABI codecvt<char, char, mbstate_t> : public locale::facet, public codecvt_base {
0753 public:
0754 typedef char intern_type;
0755 typedef char extern_type;
0756 typedef mbstate_t state_type;
0757
0758 _LIBCPP_HIDE_FROM_ABI explicit codecvt(size_t __refs = 0) : locale::facet(__refs) {}
0759
0760 _LIBCPP_HIDE_FROM_ABI result
0761 out(state_type& __st,
0762 const intern_type* __frm,
0763 const intern_type* __frm_end,
0764 const intern_type*& __frm_nxt,
0765 extern_type* __to,
0766 extern_type* __to_end,
0767 extern_type*& __to_nxt) const {
0768 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
0769 }
0770
0771 _LIBCPP_HIDE_FROM_ABI result
0772 unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const {
0773 return do_unshift(__st, __to, __to_end, __to_nxt);
0774 }
0775
0776 _LIBCPP_HIDE_FROM_ABI result
0777 in(state_type& __st,
0778 const extern_type* __frm,
0779 const extern_type* __frm_end,
0780 const extern_type*& __frm_nxt,
0781 intern_type* __to,
0782 intern_type* __to_end,
0783 intern_type*& __to_nxt) const {
0784 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
0785 }
0786
0787 _LIBCPP_HIDE_FROM_ABI int encoding() const _NOEXCEPT { return do_encoding(); }
0788
0789 _LIBCPP_HIDE_FROM_ABI bool always_noconv() const _NOEXCEPT { return do_always_noconv(); }
0790
0791 _LIBCPP_HIDE_FROM_ABI int
0792 length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const {
0793 return do_length(__st, __frm, __end, __mx);
0794 }
0795
0796 _LIBCPP_HIDE_FROM_ABI int max_length() const _NOEXCEPT { return do_max_length(); }
0797
0798 static locale::id id;
0799
0800 protected:
0801 _LIBCPP_HIDE_FROM_ABI explicit codecvt(const char*, size_t __refs = 0) : locale::facet(__refs) {}
0802
0803 ~codecvt() override;
0804
0805 virtual result
0806 do_out(state_type& __st,
0807 const intern_type* __frm,
0808 const intern_type* __frm_end,
0809 const intern_type*& __frm_nxt,
0810 extern_type* __to,
0811 extern_type* __to_end,
0812 extern_type*& __to_nxt) const;
0813 virtual result
0814 do_in(state_type& __st,
0815 const extern_type* __frm,
0816 const extern_type* __frm_end,
0817 const extern_type*& __frm_nxt,
0818 intern_type* __to,
0819 intern_type* __to_end,
0820 intern_type*& __to_nxt) const;
0821 virtual result do_unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
0822 virtual int do_encoding() const _NOEXCEPT;
0823 virtual bool do_always_noconv() const _NOEXCEPT;
0824 virtual int do_length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
0825 virtual int do_max_length() const _NOEXCEPT;
0826 };
0827
0828 // template <> class codecvt<wchar_t, char, mbstate_t>
0829
0830 # if _LIBCPP_HAS_WIDE_CHARACTERS
0831 template <>
0832 class _LIBCPP_EXPORTED_FROM_ABI codecvt<wchar_t, char, mbstate_t> : public locale::facet, public codecvt_base {
0833 __locale::__locale_t __l_;
0834
0835 public:
0836 typedef wchar_t intern_type;
0837 typedef char extern_type;
0838 typedef mbstate_t state_type;
0839
0840 explicit codecvt(size_t __refs = 0);
0841
0842 _LIBCPP_HIDE_FROM_ABI result
0843 out(state_type& __st,
0844 const intern_type* __frm,
0845 const intern_type* __frm_end,
0846 const intern_type*& __frm_nxt,
0847 extern_type* __to,
0848 extern_type* __to_end,
0849 extern_type*& __to_nxt) const {
0850 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
0851 }
0852
0853 _LIBCPP_HIDE_FROM_ABI result
0854 unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const {
0855 return do_unshift(__st, __to, __to_end, __to_nxt);
0856 }
0857
0858 _LIBCPP_HIDE_FROM_ABI result
0859 in(state_type& __st,
0860 const extern_type* __frm,
0861 const extern_type* __frm_end,
0862 const extern_type*& __frm_nxt,
0863 intern_type* __to,
0864 intern_type* __to_end,
0865 intern_type*& __to_nxt) const {
0866 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
0867 }
0868
0869 _LIBCPP_HIDE_FROM_ABI int encoding() const _NOEXCEPT { return do_encoding(); }
0870
0871 _LIBCPP_HIDE_FROM_ABI bool always_noconv() const _NOEXCEPT { return do_always_noconv(); }
0872
0873 _LIBCPP_HIDE_FROM_ABI int
0874 length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const {
0875 return do_length(__st, __frm, __end, __mx);
0876 }
0877
0878 _LIBCPP_HIDE_FROM_ABI int max_length() const _NOEXCEPT { return do_max_length(); }
0879
0880 static locale::id id;
0881
0882 protected:
0883 explicit codecvt(const char*, size_t __refs = 0);
0884
0885 ~codecvt() override;
0886
0887 virtual result
0888 do_out(state_type& __st,
0889 const intern_type* __frm,
0890 const intern_type* __frm_end,
0891 const intern_type*& __frm_nxt,
0892 extern_type* __to,
0893 extern_type* __to_end,
0894 extern_type*& __to_nxt) const;
0895 virtual result
0896 do_in(state_type& __st,
0897 const extern_type* __frm,
0898 const extern_type* __frm_end,
0899 const extern_type*& __frm_nxt,
0900 intern_type* __to,
0901 intern_type* __to_end,
0902 intern_type*& __to_nxt) const;
0903 virtual result do_unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
0904 virtual int do_encoding() const _NOEXCEPT;
0905 virtual bool do_always_noconv() const _NOEXCEPT;
0906 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
0907 virtual int do_max_length() const _NOEXCEPT;
0908 };
0909 # endif // _LIBCPP_HAS_WIDE_CHARACTERS
0910
0911 // template <> class codecvt<char16_t, char, mbstate_t> // deprecated in C++20
0912
0913 template <>
0914 class _LIBCPP_DEPRECATED_IN_CXX20 _LIBCPP_EXPORTED_FROM_ABI codecvt<char16_t, char, mbstate_t>
0915 : public locale::facet, public codecvt_base {
0916 public:
0917 typedef char16_t intern_type;
0918 typedef char extern_type;
0919 typedef mbstate_t state_type;
0920
0921 _LIBCPP_HIDE_FROM_ABI explicit codecvt(size_t __refs = 0) : locale::facet(__refs) {}
0922
0923 _LIBCPP_HIDE_FROM_ABI result
0924 out(state_type& __st,
0925 const intern_type* __frm,
0926 const intern_type* __frm_end,
0927 const intern_type*& __frm_nxt,
0928 extern_type* __to,
0929 extern_type* __to_end,
0930 extern_type*& __to_nxt) const {
0931 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
0932 }
0933
0934 _LIBCPP_HIDE_FROM_ABI result
0935 unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const {
0936 return do_unshift(__st, __to, __to_end, __to_nxt);
0937 }
0938
0939 _LIBCPP_HIDE_FROM_ABI result
0940 in(state_type& __st,
0941 const extern_type* __frm,
0942 const extern_type* __frm_end,
0943 const extern_type*& __frm_nxt,
0944 intern_type* __to,
0945 intern_type* __to_end,
0946 intern_type*& __to_nxt) const {
0947 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
0948 }
0949
0950 _LIBCPP_HIDE_FROM_ABI int encoding() const _NOEXCEPT { return do_encoding(); }
0951
0952 _LIBCPP_HIDE_FROM_ABI bool always_noconv() const _NOEXCEPT { return do_always_noconv(); }
0953
0954 _LIBCPP_HIDE_FROM_ABI int
0955 length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const {
0956 return do_length(__st, __frm, __end, __mx);
0957 }
0958
0959 _LIBCPP_HIDE_FROM_ABI int max_length() const _NOEXCEPT { return do_max_length(); }
0960
0961 static locale::id id;
0962
0963 protected:
0964 _LIBCPP_HIDE_FROM_ABI explicit codecvt(const char*, size_t __refs = 0) : locale::facet(__refs) {}
0965
0966 ~codecvt() override;
0967
0968 virtual result
0969 do_out(state_type& __st,
0970 const intern_type* __frm,
0971 const intern_type* __frm_end,
0972 const intern_type*& __frm_nxt,
0973 extern_type* __to,
0974 extern_type* __to_end,
0975 extern_type*& __to_nxt) const;
0976 virtual result
0977 do_in(state_type& __st,
0978 const extern_type* __frm,
0979 const extern_type* __frm_end,
0980 const extern_type*& __frm_nxt,
0981 intern_type* __to,
0982 intern_type* __to_end,
0983 intern_type*& __to_nxt) const;
0984 virtual result do_unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
0985 virtual int do_encoding() const _NOEXCEPT;
0986 virtual bool do_always_noconv() const _NOEXCEPT;
0987 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
0988 virtual int do_max_length() const _NOEXCEPT;
0989 };
0990
0991 # if _LIBCPP_HAS_CHAR8_T
0992
0993 // template <> class codecvt<char16_t, char8_t, mbstate_t> // C++20
0994
0995 template <>
0996 class _LIBCPP_EXPORTED_FROM_ABI codecvt<char16_t, char8_t, mbstate_t> : public locale::facet, public codecvt_base {
0997 public:
0998 typedef char16_t intern_type;
0999 typedef char8_t extern_type;
1000 typedef mbstate_t state_type;
1001
1002 _LIBCPP_HIDE_FROM_ABI explicit codecvt(size_t __refs = 0) : locale::facet(__refs) {}
1003
1004 _LIBCPP_HIDE_FROM_ABI result
1005 out(state_type& __st,
1006 const intern_type* __frm,
1007 const intern_type* __frm_end,
1008 const intern_type*& __frm_nxt,
1009 extern_type* __to,
1010 extern_type* __to_end,
1011 extern_type*& __to_nxt) const {
1012 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1013 }
1014
1015 _LIBCPP_HIDE_FROM_ABI result
1016 unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const {
1017 return do_unshift(__st, __to, __to_end, __to_nxt);
1018 }
1019
1020 _LIBCPP_HIDE_FROM_ABI result
1021 in(state_type& __st,
1022 const extern_type* __frm,
1023 const extern_type* __frm_end,
1024 const extern_type*& __frm_nxt,
1025 intern_type* __to,
1026 intern_type* __to_end,
1027 intern_type*& __to_nxt) const {
1028 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1029 }
1030
1031 _LIBCPP_HIDE_FROM_ABI int encoding() const _NOEXCEPT { return do_encoding(); }
1032
1033 _LIBCPP_HIDE_FROM_ABI bool always_noconv() const _NOEXCEPT { return do_always_noconv(); }
1034
1035 _LIBCPP_HIDE_FROM_ABI int
1036 length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const {
1037 return do_length(__st, __frm, __end, __mx);
1038 }
1039
1040 _LIBCPP_HIDE_FROM_ABI int max_length() const _NOEXCEPT { return do_max_length(); }
1041
1042 static locale::id id;
1043
1044 protected:
1045 _LIBCPP_HIDE_FROM_ABI explicit codecvt(const char*, size_t __refs = 0) : locale::facet(__refs) {}
1046
1047 ~codecvt() override;
1048
1049 virtual result
1050 do_out(state_type& __st,
1051 const intern_type* __frm,
1052 const intern_type* __frm_end,
1053 const intern_type*& __frm_nxt,
1054 extern_type* __to,
1055 extern_type* __to_end,
1056 extern_type*& __to_nxt) const;
1057 virtual result
1058 do_in(state_type& __st,
1059 const extern_type* __frm,
1060 const extern_type* __frm_end,
1061 const extern_type*& __frm_nxt,
1062 intern_type* __to,
1063 intern_type* __to_end,
1064 intern_type*& __to_nxt) const;
1065 virtual result do_unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1066 virtual int do_encoding() const _NOEXCEPT;
1067 virtual bool do_always_noconv() const _NOEXCEPT;
1068 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
1069 virtual int do_max_length() const _NOEXCEPT;
1070 };
1071
1072 # endif
1073
1074 // template <> class codecvt<char32_t, char, mbstate_t> // deprecated in C++20
1075
1076 template <>
1077 class _LIBCPP_DEPRECATED_IN_CXX20 _LIBCPP_EXPORTED_FROM_ABI codecvt<char32_t, char, mbstate_t>
1078 : public locale::facet, public codecvt_base {
1079 public:
1080 typedef char32_t intern_type;
1081 typedef char extern_type;
1082 typedef mbstate_t state_type;
1083
1084 _LIBCPP_HIDE_FROM_ABI explicit codecvt(size_t __refs = 0) : locale::facet(__refs) {}
1085
1086 _LIBCPP_HIDE_FROM_ABI result
1087 out(state_type& __st,
1088 const intern_type* __frm,
1089 const intern_type* __frm_end,
1090 const intern_type*& __frm_nxt,
1091 extern_type* __to,
1092 extern_type* __to_end,
1093 extern_type*& __to_nxt) const {
1094 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1095 }
1096
1097 _LIBCPP_HIDE_FROM_ABI result
1098 unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const {
1099 return do_unshift(__st, __to, __to_end, __to_nxt);
1100 }
1101
1102 _LIBCPP_HIDE_FROM_ABI result
1103 in(state_type& __st,
1104 const extern_type* __frm,
1105 const extern_type* __frm_end,
1106 const extern_type*& __frm_nxt,
1107 intern_type* __to,
1108 intern_type* __to_end,
1109 intern_type*& __to_nxt) const {
1110 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1111 }
1112
1113 _LIBCPP_HIDE_FROM_ABI int encoding() const _NOEXCEPT { return do_encoding(); }
1114
1115 _LIBCPP_HIDE_FROM_ABI bool always_noconv() const _NOEXCEPT { return do_always_noconv(); }
1116
1117 _LIBCPP_HIDE_FROM_ABI int
1118 length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const {
1119 return do_length(__st, __frm, __end, __mx);
1120 }
1121
1122 _LIBCPP_HIDE_FROM_ABI int max_length() const _NOEXCEPT { return do_max_length(); }
1123
1124 static locale::id id;
1125
1126 protected:
1127 _LIBCPP_HIDE_FROM_ABI explicit codecvt(const char*, size_t __refs = 0) : locale::facet(__refs) {}
1128
1129 ~codecvt() override;
1130
1131 virtual result
1132 do_out(state_type& __st,
1133 const intern_type* __frm,
1134 const intern_type* __frm_end,
1135 const intern_type*& __frm_nxt,
1136 extern_type* __to,
1137 extern_type* __to_end,
1138 extern_type*& __to_nxt) const;
1139 virtual result
1140 do_in(state_type& __st,
1141 const extern_type* __frm,
1142 const extern_type* __frm_end,
1143 const extern_type*& __frm_nxt,
1144 intern_type* __to,
1145 intern_type* __to_end,
1146 intern_type*& __to_nxt) const;
1147 virtual result do_unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1148 virtual int do_encoding() const _NOEXCEPT;
1149 virtual bool do_always_noconv() const _NOEXCEPT;
1150 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
1151 virtual int do_max_length() const _NOEXCEPT;
1152 };
1153
1154 # if _LIBCPP_HAS_CHAR8_T
1155
1156 // template <> class codecvt<char32_t, char8_t, mbstate_t> // C++20
1157
1158 template <>
1159 class _LIBCPP_EXPORTED_FROM_ABI codecvt<char32_t, char8_t, mbstate_t> : public locale::facet, public codecvt_base {
1160 public:
1161 typedef char32_t intern_type;
1162 typedef char8_t extern_type;
1163 typedef mbstate_t state_type;
1164
1165 _LIBCPP_HIDE_FROM_ABI explicit codecvt(size_t __refs = 0) : locale::facet(__refs) {}
1166
1167 _LIBCPP_HIDE_FROM_ABI result
1168 out(state_type& __st,
1169 const intern_type* __frm,
1170 const intern_type* __frm_end,
1171 const intern_type*& __frm_nxt,
1172 extern_type* __to,
1173 extern_type* __to_end,
1174 extern_type*& __to_nxt) const {
1175 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1176 }
1177
1178 _LIBCPP_HIDE_FROM_ABI result
1179 unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const {
1180 return do_unshift(__st, __to, __to_end, __to_nxt);
1181 }
1182
1183 _LIBCPP_HIDE_FROM_ABI result
1184 in(state_type& __st,
1185 const extern_type* __frm,
1186 const extern_type* __frm_end,
1187 const extern_type*& __frm_nxt,
1188 intern_type* __to,
1189 intern_type* __to_end,
1190 intern_type*& __to_nxt) const {
1191 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1192 }
1193
1194 _LIBCPP_HIDE_FROM_ABI int encoding() const _NOEXCEPT { return do_encoding(); }
1195
1196 _LIBCPP_HIDE_FROM_ABI bool always_noconv() const _NOEXCEPT { return do_always_noconv(); }
1197
1198 _LIBCPP_HIDE_FROM_ABI int
1199 length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const {
1200 return do_length(__st, __frm, __end, __mx);
1201 }
1202
1203 _LIBCPP_HIDE_FROM_ABI int max_length() const _NOEXCEPT { return do_max_length(); }
1204
1205 static locale::id id;
1206
1207 protected:
1208 _LIBCPP_HIDE_FROM_ABI explicit codecvt(const char*, size_t __refs = 0) : locale::facet(__refs) {}
1209
1210 ~codecvt() override;
1211
1212 virtual result
1213 do_out(state_type& __st,
1214 const intern_type* __frm,
1215 const intern_type* __frm_end,
1216 const intern_type*& __frm_nxt,
1217 extern_type* __to,
1218 extern_type* __to_end,
1219 extern_type*& __to_nxt) const;
1220 virtual result
1221 do_in(state_type& __st,
1222 const extern_type* __frm,
1223 const extern_type* __frm_end,
1224 const extern_type*& __frm_nxt,
1225 intern_type* __to,
1226 intern_type* __to_end,
1227 intern_type*& __to_nxt) const;
1228 virtual result do_unshift(state_type& __st, extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1229 virtual int do_encoding() const _NOEXCEPT;
1230 virtual bool do_always_noconv() const _NOEXCEPT;
1231 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
1232 virtual int do_max_length() const _NOEXCEPT;
1233 };
1234
1235 # endif
1236
1237 // template <class _InternT, class _ExternT, class _StateT> class codecvt_byname
1238
1239 template <class _InternT, class _ExternT, class _StateT>
1240 class _LIBCPP_TEMPLATE_VIS codecvt_byname : public codecvt<_InternT, _ExternT, _StateT> {
1241 public:
1242 _LIBCPP_HIDE_FROM_ABI explicit codecvt_byname(const char* __nm, size_t __refs = 0)
1243 : codecvt<_InternT, _ExternT, _StateT>(__nm, __refs) {}
1244 _LIBCPP_HIDE_FROM_ABI explicit codecvt_byname(const string& __nm, size_t __refs = 0)
1245 : codecvt<_InternT, _ExternT, _StateT>(__nm.c_str(), __refs) {}
1246
1247 protected:
1248 ~codecvt_byname() override;
1249 };
1250
1251 _LIBCPP_SUPPRESS_DEPRECATED_PUSH
1252 template <class _InternT, class _ExternT, class _StateT>
1253 codecvt_byname<_InternT, _ExternT, _StateT>::~codecvt_byname() {}
1254 _LIBCPP_SUPPRESS_DEPRECATED_POP
1255
1256 extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char, char, mbstate_t>;
1257 # if _LIBCPP_HAS_WIDE_CHARACTERS
1258 extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<wchar_t, char, mbstate_t>;
1259 # endif
1260 extern template class _LIBCPP_DEPRECATED_IN_CXX20
1261 _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char16_t, char, mbstate_t>; // deprecated in C++20
1262 extern template class _LIBCPP_DEPRECATED_IN_CXX20
1263 _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char32_t, char, mbstate_t>; // deprecated in C++20
1264 # if _LIBCPP_HAS_CHAR8_T
1265 extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char16_t, char8_t, mbstate_t>; // C++20
1266 extern template class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char32_t, char8_t, mbstate_t>; // C++20
1267 # endif
1268
1269 template <size_t _Np>
1270 struct __narrow_to_utf8 {
1271 template <class _OutputIterator, class _CharT>
1272 _OutputIterator operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const;
1273 };
1274
1275 template <>
1276 struct __narrow_to_utf8<8> {
1277 template <class _OutputIterator, class _CharT>
1278 _LIBCPP_HIDE_FROM_ABI _OutputIterator operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const {
1279 for (; __wb < __we; ++__wb, ++__s)
1280 *__s = *__wb;
1281 return __s;
1282 }
1283 };
1284
1285 _LIBCPP_SUPPRESS_DEPRECATED_PUSH
1286 template <>
1287 struct _LIBCPP_EXPORTED_FROM_ABI __narrow_to_utf8<16> : public codecvt<char16_t, char, mbstate_t> {
1288 _LIBCPP_HIDE_FROM_ABI __narrow_to_utf8() : codecvt<char16_t, char, mbstate_t>(1) {}
1289 _LIBCPP_SUPPRESS_DEPRECATED_POP
1290
1291 ~__narrow_to_utf8() override;
1292
1293 template <class _OutputIterator, class _CharT>
1294 _LIBCPP_HIDE_FROM_ABI _OutputIterator operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const {
1295 result __r = ok;
1296 mbstate_t __mb;
1297 while (__wb < __we && __r != error) {
1298 const int __sz = 32;
1299 char __buf[__sz];
1300 char* __bn;
1301 const char16_t* __wn = (const char16_t*)__wb;
1302 __r = do_out(__mb, (const char16_t*)__wb, (const char16_t*)__we, __wn, __buf, __buf + __sz, __bn);
1303 if (__r == codecvt_base::error || __wn == (const char16_t*)__wb)
1304 __throw_runtime_error("locale not supported");
1305 for (const char* __p = __buf; __p < __bn; ++__p, ++__s)
1306 *__s = *__p;
1307 __wb = (const _CharT*)__wn;
1308 }
1309 return __s;
1310 }
1311 };
1312
1313 _LIBCPP_SUPPRESS_DEPRECATED_PUSH
1314 template <>
1315 struct _LIBCPP_EXPORTED_FROM_ABI __narrow_to_utf8<32> : public codecvt<char32_t, char, mbstate_t> {
1316 _LIBCPP_HIDE_FROM_ABI __narrow_to_utf8() : codecvt<char32_t, char, mbstate_t>(1) {}
1317 _LIBCPP_SUPPRESS_DEPRECATED_POP
1318
1319 ~__narrow_to_utf8() override;
1320
1321 template <class _OutputIterator, class _CharT>
1322 _LIBCPP_HIDE_FROM_ABI _OutputIterator operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const {
1323 result __r = ok;
1324 mbstate_t __mb;
1325 while (__wb < __we && __r != error) {
1326 const int __sz = 32;
1327 char __buf[__sz];
1328 char* __bn;
1329 const char32_t* __wn = (const char32_t*)__wb;
1330 __r = do_out(__mb, (const char32_t*)__wb, (const char32_t*)__we, __wn, __buf, __buf + __sz, __bn);
1331 if (__r == codecvt_base::error || __wn == (const char32_t*)__wb)
1332 __throw_runtime_error("locale not supported");
1333 for (const char* __p = __buf; __p < __bn; ++__p, ++__s)
1334 *__s = *__p;
1335 __wb = (const _CharT*)__wn;
1336 }
1337 return __s;
1338 }
1339 };
1340
1341 template <size_t _Np>
1342 struct __widen_from_utf8 {
1343 template <class _OutputIterator>
1344 _OutputIterator operator()(_OutputIterator __s, const char* __nb, const char* __ne) const;
1345 };
1346
1347 template <>
1348 struct __widen_from_utf8<8> {
1349 template <class _OutputIterator>
1350 _LIBCPP_HIDE_FROM_ABI _OutputIterator operator()(_OutputIterator __s, const char* __nb, const char* __ne) const {
1351 for (; __nb < __ne; ++__nb, ++__s)
1352 *__s = *__nb;
1353 return __s;
1354 }
1355 };
1356
1357 _LIBCPP_SUPPRESS_DEPRECATED_PUSH
1358 template <>
1359 struct _LIBCPP_EXPORTED_FROM_ABI __widen_from_utf8<16> : public codecvt<char16_t, char, mbstate_t> {
1360 _LIBCPP_HIDE_FROM_ABI __widen_from_utf8() : codecvt<char16_t, char, mbstate_t>(1) {}
1361 _LIBCPP_SUPPRESS_DEPRECATED_POP
1362
1363 ~__widen_from_utf8() override;
1364
1365 template <class _OutputIterator>
1366 _LIBCPP_HIDE_FROM_ABI _OutputIterator operator()(_OutputIterator __s, const char* __nb, const char* __ne) const {
1367 result __r = ok;
1368 mbstate_t __mb;
1369 while (__nb < __ne && __r != error) {
1370 const int __sz = 32;
1371 char16_t __buf[__sz];
1372 char16_t* __bn;
1373 const char* __nn = __nb;
1374 __r = do_in(__mb, __nb, __ne - __nb > __sz ? __nb + __sz : __ne, __nn, __buf, __buf + __sz, __bn);
1375 if (__r == codecvt_base::error || __nn == __nb)
1376 __throw_runtime_error("locale not supported");
1377 for (const char16_t* __p = __buf; __p < __bn; ++__p, ++__s)
1378 *__s = *__p;
1379 __nb = __nn;
1380 }
1381 return __s;
1382 }
1383 };
1384
1385 _LIBCPP_SUPPRESS_DEPRECATED_PUSH
1386 template <>
1387 struct _LIBCPP_EXPORTED_FROM_ABI __widen_from_utf8<32> : public codecvt<char32_t, char, mbstate_t> {
1388 _LIBCPP_HIDE_FROM_ABI __widen_from_utf8() : codecvt<char32_t, char, mbstate_t>(1) {}
1389 _LIBCPP_SUPPRESS_DEPRECATED_POP
1390
1391 ~__widen_from_utf8() override;
1392
1393 template <class _OutputIterator>
1394 _LIBCPP_HIDE_FROM_ABI _OutputIterator operator()(_OutputIterator __s, const char* __nb, const char* __ne) const {
1395 result __r = ok;
1396 mbstate_t __mb;
1397 while (__nb < __ne && __r != error) {
1398 const int __sz = 32;
1399 char32_t __buf[__sz];
1400 char32_t* __bn;
1401 const char* __nn = __nb;
1402 __r = do_in(__mb, __nb, __ne - __nb > __sz ? __nb + __sz : __ne, __nn, __buf, __buf + __sz, __bn);
1403 if (__r == codecvt_base::error || __nn == __nb)
1404 __throw_runtime_error("locale not supported");
1405 for (const char32_t* __p = __buf; __p < __bn; ++__p, ++__s)
1406 *__s = *__p;
1407 __nb = __nn;
1408 }
1409 return __s;
1410 }
1411 };
1412
1413 // template <class charT> class numpunct
1414
1415 template <class _CharT>
1416 class _LIBCPP_TEMPLATE_VIS numpunct;
1417
1418 template <>
1419 class _LIBCPP_EXPORTED_FROM_ABI numpunct<char> : public locale::facet {
1420 public:
1421 typedef char char_type;
1422 typedef basic_string<char_type> string_type;
1423
1424 explicit numpunct(size_t __refs = 0);
1425
1426 _LIBCPP_HIDE_FROM_ABI char_type decimal_point() const { return do_decimal_point(); }
1427 _LIBCPP_HIDE_FROM_ABI char_type thousands_sep() const { return do_thousands_sep(); }
1428 _LIBCPP_HIDE_FROM_ABI string grouping() const { return do_grouping(); }
1429 _LIBCPP_HIDE_FROM_ABI string_type truename() const { return do_truename(); }
1430 _LIBCPP_HIDE_FROM_ABI string_type falsename() const { return do_falsename(); }
1431
1432 static locale::id id;
1433
1434 protected:
1435 ~numpunct() override;
1436 virtual char_type do_decimal_point() const;
1437 virtual char_type do_thousands_sep() const;
1438 virtual string do_grouping() const;
1439 virtual string_type do_truename() const;
1440 virtual string_type do_falsename() const;
1441
1442 char_type __decimal_point_;
1443 char_type __thousands_sep_;
1444 string __grouping_;
1445 };
1446
1447 # if _LIBCPP_HAS_WIDE_CHARACTERS
1448 template <>
1449 class _LIBCPP_EXPORTED_FROM_ABI numpunct<wchar_t> : public locale::facet {
1450 public:
1451 typedef wchar_t char_type;
1452 typedef basic_string<char_type> string_type;
1453
1454 explicit numpunct(size_t __refs = 0);
1455
1456 _LIBCPP_HIDE_FROM_ABI char_type decimal_point() const { return do_decimal_point(); }
1457 _LIBCPP_HIDE_FROM_ABI char_type thousands_sep() const { return do_thousands_sep(); }
1458 _LIBCPP_HIDE_FROM_ABI string grouping() const { return do_grouping(); }
1459 _LIBCPP_HIDE_FROM_ABI string_type truename() const { return do_truename(); }
1460 _LIBCPP_HIDE_FROM_ABI string_type falsename() const { return do_falsename(); }
1461
1462 static locale::id id;
1463
1464 protected:
1465 ~numpunct() override;
1466 virtual char_type do_decimal_point() const;
1467 virtual char_type do_thousands_sep() const;
1468 virtual string do_grouping() const;
1469 virtual string_type do_truename() const;
1470 virtual string_type do_falsename() const;
1471
1472 char_type __decimal_point_;
1473 char_type __thousands_sep_;
1474 string __grouping_;
1475 };
1476 # endif // _LIBCPP_HAS_WIDE_CHARACTERS
1477
1478 // template <class charT> class numpunct_byname
1479
1480 template <class _CharT>
1481 class _LIBCPP_TEMPLATE_VIS numpunct_byname;
1482
1483 template <>
1484 class _LIBCPP_EXPORTED_FROM_ABI numpunct_byname<char> : public numpunct<char> {
1485 public:
1486 typedef char char_type;
1487 typedef basic_string<char_type> string_type;
1488
1489 explicit numpunct_byname(const char* __nm, size_t __refs = 0);
1490 explicit numpunct_byname(const string& __nm, size_t __refs = 0);
1491
1492 protected:
1493 ~numpunct_byname() override;
1494
1495 private:
1496 void __init(const char*);
1497 };
1498
1499 # if _LIBCPP_HAS_WIDE_CHARACTERS
1500 template <>
1501 class _LIBCPP_EXPORTED_FROM_ABI numpunct_byname<wchar_t> : public numpunct<wchar_t> {
1502 public:
1503 typedef wchar_t char_type;
1504 typedef basic_string<char_type> string_type;
1505
1506 explicit numpunct_byname(const char* __nm, size_t __refs = 0);
1507 explicit numpunct_byname(const string& __nm, size_t __refs = 0);
1508
1509 protected:
1510 ~numpunct_byname() override;
1511
1512 private:
1513 void __init(const char*);
1514 };
1515 # endif // _LIBCPP_HAS_WIDE_CHARACTERS
1516
1517 _LIBCPP_END_NAMESPACE_STD
1518
1519 #endif // _LIBCPP_HAS_LOCALIZATION
1520
1521 #endif // _LIBCPP___LOCALE