blob: 4e9e0c08acf0e603e18aa83755e277340dfbab6b [file] [log] [blame]
Howard Hinnantc51e1022010-05-11 19:42:16 +00001// -*- C++ -*-
2//===----------------------------------------------------------------------===//
3//
Chandler Carruthd2012102019-01-19 10:56:40 +00004// 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
Howard Hinnantc51e1022010-05-11 19:42:16 +00007//
8//===----------------------------------------------------------------------===//
9
10#ifndef _LIBCPP___LOCALE
11#define _LIBCPP___LOCALE
12
13#include <__config>
Louis Dionne73912b22020-11-04 15:01:25 -050014#include <__availability>
Howard Hinnantc51e1022010-05-11 19:42:16 +000015#include <string>
16#include <memory>
17#include <utility>
18#include <mutex>
19#include <cstdint>
20#include <cctype>
Howard Hinnant155c2af2010-05-24 17:49:41 +000021#include <locale.h>
Eric Fiselierbb999f92017-05-31 22:14:05 +000022#if defined(_LIBCPP_MSVCRT_LIKE)
Thomas Anderson094acbc2019-03-27 18:09:30 +000023# include <cstring>
Howard Hinnantae0f80b2011-09-29 20:33:10 +000024# include <support/win32/locale_win32.h>
Xiang Xiao85529232020-11-18 16:16:18 -050025#elif defined(__NuttX__)
26# include <support/nuttx/xlocale.h>
Muiez Ahmedaf108fb2020-11-10 09:54:03 -050027#elif defined(_AIX) || defined(__MVS__)
Howard Hinnantea382952013-08-14 18:00:20 +000028# include <support/ibm/xlocale.h>
Marshall Clow3477ec92014-07-10 15:20:28 +000029#elif defined(__ANDROID__)
Saleem Abdulrasoolac039f32018-04-13 18:14:57 +000030# include <support/android/locale_bionic.h>
Eric Fiselier7274c652014-11-25 21:57:41 +000031#elif defined(__sun__)
Eric Fiselier90adc202015-01-23 22:22:36 +000032# include <xlocale.h>
Eric Fiselier7274c652014-11-25 21:57:41 +000033# include <support/solaris/xlocale.h>
Sergey Dmitrouk9935bd42014-12-12 08:36:16 +000034#elif defined(_NEWLIB_VERSION)
35# include <support/newlib/xlocale.h>
Brad Smithf6f55092021-01-12 14:16:15 -050036#elif defined(__OpenBSD__)
37# include <support/openbsd/xlocale.h>
Eric Fiseliercee57932017-08-03 04:28:10 +000038#elif (defined(__APPLE__) || defined(__FreeBSD__) \
Eric Fiselier7274c652014-11-25 21:57:41 +000039 || defined(__EMSCRIPTEN__) || defined(__IBMCPP__))
Howard Hinnantdd0d7022011-09-22 19:10:18 +000040# include <xlocale.h>
Petr Hosekfdb4a872017-04-13 21:29:21 +000041#elif defined(__Fuchsia__)
42# include <support/fuchsia/xlocale.h>
Dan Gohman280fd6b2019-05-01 16:47:30 +000043#elif defined(__wasi__)
44// WASI libc uses musl's locales support.
45# include <support/musl/xlocale.h>
Vasileios Kalintiris281b4cf2015-11-09 10:21:04 +000046#elif defined(_LIBCPP_HAS_MUSL_LIBC)
47# include <support/musl/xlocale.h>
Petr Hosekfdb4a872017-04-13 21:29:21 +000048#endif
Howard Hinnantc51e1022010-05-11 19:42:16 +000049
Howard Hinnantaaaa52b2011-10-17 20:05:10 +000050#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
Howard Hinnantc51e1022010-05-11 19:42:16 +000051#pragma GCC system_header
Howard Hinnantaaaa52b2011-10-17 20:05:10 +000052#endif
Howard Hinnantc51e1022010-05-11 19:42:16 +000053
54_LIBCPP_BEGIN_NAMESPACE_STD
55
Martin Storsjo5482ac62017-11-23 10:38:18 +000056#if !defined(_LIBCPP_LOCALE__L_EXTENSIONS)
Eric Fiselierebc2d2c2017-05-08 22:02:43 +000057struct __libcpp_locale_guard {
58 _LIBCPP_INLINE_VISIBILITY
59 __libcpp_locale_guard(locale_t& __loc) : __old_loc_(uselocale(__loc)) {}
60
61 _LIBCPP_INLINE_VISIBILITY
62 ~__libcpp_locale_guard() {
63 if (__old_loc_)
64 uselocale(__old_loc_);
65 }
66
67 locale_t __old_loc_;
68private:
69 __libcpp_locale_guard(__libcpp_locale_guard const&);
70 __libcpp_locale_guard& operator=(__libcpp_locale_guard const&);
71};
Martin Storsjo5482ac62017-11-23 10:38:18 +000072#elif defined(_LIBCPP_MSVCRT_LIKE)
73struct __libcpp_locale_guard {
74 __libcpp_locale_guard(locale_t __l) :
Thomas Anderson094acbc2019-03-27 18:09:30 +000075 __status(_configthreadlocale(_ENABLE_PER_THREAD_LOCALE)) {
76 // Setting the locale can be expensive even when the locale given is
77 // already the current locale, so do an explicit check to see if the
78 // current locale is already the one we want.
79 const char* __lc = __setlocale(nullptr);
80 // If every category is the same, the locale string will simply be the
81 // locale name, otherwise it will be a semicolon-separated string listing
82 // each category. In the second case, we know at least one category won't
83 // be what we want, so we only have to check the first case.
Arthur O'Dwyer22236632020-12-07 21:50:15 -050084 if (_VSTD::strcmp(__l.__get_locale(), __lc) != 0) {
Thomas Anderson094acbc2019-03-27 18:09:30 +000085 __locale_all = _strdup(__lc);
86 if (__locale_all == nullptr)
87 __throw_bad_alloc();
88 __setlocale(__l.__get_locale());
89 }
90 }
Martin Storsjo5482ac62017-11-23 10:38:18 +000091 ~__libcpp_locale_guard() {
Thomas Anderson094acbc2019-03-27 18:09:30 +000092 // The CRT documentation doesn't explicitly say, but setlocale() does the
93 // right thing when given a semicolon-separated list of locale settings
94 // for the different categories in the same format as returned by
95 // setlocale(LC_ALL, nullptr).
96 if (__locale_all != nullptr) {
97 __setlocale(__locale_all);
98 free(__locale_all);
99 }
100 _configthreadlocale(__status);
101 }
102 static const char* __setlocale(const char* __locale) {
103 const char* __new_locale = setlocale(LC_ALL, __locale);
104 if (__new_locale == nullptr)
105 __throw_bad_alloc();
106 return __new_locale;
Martin Storsjo5482ac62017-11-23 10:38:18 +0000107 }
108 int __status;
Thomas Anderson094acbc2019-03-27 18:09:30 +0000109 char* __locale_all = nullptr;
Martin Storsjo5482ac62017-11-23 10:38:18 +0000110};
Eric Fiselierebc2d2c2017-05-08 22:02:43 +0000111#endif
112
Howard Hinnant8331b762013-03-06 23:30:19 +0000113class _LIBCPP_TYPE_VIS locale;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000114
Howard Hinnanta54386e2012-09-14 00:39:16 +0000115template <class _Facet>
116_LIBCPP_INLINE_VISIBILITY
117bool
118has_facet(const locale&) _NOEXCEPT;
119
120template <class _Facet>
121_LIBCPP_INLINE_VISIBILITY
122const _Facet&
123use_facet(const locale&);
Howard Hinnantc51e1022010-05-11 19:42:16 +0000124
Howard Hinnant8331b762013-03-06 23:30:19 +0000125class _LIBCPP_TYPE_VIS locale
Howard Hinnantc51e1022010-05-11 19:42:16 +0000126{
127public:
128 // types:
Howard Hinnant8331b762013-03-06 23:30:19 +0000129 class _LIBCPP_TYPE_VIS facet;
130 class _LIBCPP_TYPE_VIS id;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000131
132 typedef int category;
Mehdi Amini228053d2017-05-04 17:08:54 +0000133 _LIBCPP_AVAILABILITY_LOCALE_CATEGORY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000134 static const category // values assigned here are for exposition only
135 none = 0,
136 collate = LC_COLLATE_MASK,
137 ctype = LC_CTYPE_MASK,
138 monetary = LC_MONETARY_MASK,
139 numeric = LC_NUMERIC_MASK,
140 time = LC_TIME_MASK,
141 messages = LC_MESSAGES_MASK,
142 all = collate | ctype | monetary | numeric | time | messages;
143
144 // construct/copy/destroy:
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000145 locale() _NOEXCEPT;
146 locale(const locale&) _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000147 explicit locale(const char*);
148 explicit locale(const string&);
149 locale(const locale&, const char*, category);
150 locale(const locale&, const string&, category);
Howard Hinnantcf823322010-12-17 14:46:43 +0000151 template <class _Facet>
152 _LIBCPP_INLINE_VISIBILITY locale(const locale&, _Facet*);
Howard Hinnantc51e1022010-05-11 19:42:16 +0000153 locale(const locale&, const locale&, category);
154
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000155 ~locale();
Howard Hinnantc51e1022010-05-11 19:42:16 +0000156
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000157 const locale& operator=(const locale&) _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000158
Shoaib Meenai55f3a462017-03-02 03:22:18 +0000159 template <class _Facet>
160 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS
161 locale combine(const locale&) const;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000162
163 // locale operations:
164 string name() const;
165 bool operator==(const locale&) const;
166 bool operator!=(const locale& __y) const {return !(*this == __y);}
167 template <class _CharT, class _Traits, class _Allocator>
Shoaib Meenai55f3a462017-03-02 03:22:18 +0000168 _LIBCPP_METHOD_TEMPLATE_IMPLICIT_INSTANTIATION_VIS
Howard Hinnantc51e1022010-05-11 19:42:16 +0000169 bool operator()(const basic_string<_CharT, _Traits, _Allocator>&,
170 const basic_string<_CharT, _Traits, _Allocator>&) const;
171
172 // global locale objects:
173 static locale global(const locale&);
174 static const locale& classic();
175
176private:
177 class __imp;
178 __imp* __locale_;
179
180 void __install_ctor(const locale&, facet*, long);
181 static locale& __global();
182 bool has_facet(id&) const;
183 const facet* use_facet(id&) const;
184
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000185 template <class _Facet> friend bool has_facet(const locale&) _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000186 template <class _Facet> friend const _Facet& use_facet(const locale&);
187};
188
Howard Hinnant8331b762013-03-06 23:30:19 +0000189class _LIBCPP_TYPE_VIS locale::facet
Howard Hinnantc51e1022010-05-11 19:42:16 +0000190 : public __shared_count
191{
192protected:
Howard Hinnant9833cad2010-09-21 18:58:51 +0000193 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000194 explicit facet(size_t __refs = 0)
195 : __shared_count(static_cast<long>(__refs)-1) {}
196
197 virtual ~facet();
198
199// facet(const facet&) = delete; // effectively done in __shared_count
200// void operator=(const facet&) = delete;
201private:
Howard Hinnant719bda32011-05-28 14:41:13 +0000202 virtual void __on_zero_shared() _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000203};
204
Howard Hinnant8331b762013-03-06 23:30:19 +0000205class _LIBCPP_TYPE_VIS locale::id
Howard Hinnantc51e1022010-05-11 19:42:16 +0000206{
207 once_flag __flag_;
208 int32_t __id_;
Howard Hinnant3b6579a2010-08-22 00:02:43 +0000209
Howard Hinnantc51e1022010-05-11 19:42:16 +0000210 static int32_t __next_id;
211public:
Howard Hinnantac7d9f02012-07-26 16:14:37 +0000212 _LIBCPP_INLINE_VISIBILITY _LIBCPP_CONSTEXPR id() :__id_(0) {}
Howard Hinnantc51e1022010-05-11 19:42:16 +0000213private:
214 void __init();
215 void operator=(const id&); // = delete;
216 id(const id&); // = delete;
217public: // only needed for tests
218 long __get();
219
220 friend class locale;
221 friend class locale::__imp;
222};
223
224template <class _Facet>
225inline _LIBCPP_INLINE_VISIBILITY
226locale::locale(const locale& __other, _Facet* __f)
227{
228 __install_ctor(__other, __f, __f ? __f->id.__get() : 0);
229}
230
231template <class _Facet>
232locale
233locale::combine(const locale& __other) const
234{
Howard Hinnantb1ad5a82011-06-30 21:18:19 +0000235 if (!_VSTD::has_facet<_Facet>(__other))
Marshall Clow8fea1612016-08-25 15:09:01 +0000236 __throw_runtime_error("locale::combine: locale missing facet");
237
Howard Hinnantb1ad5a82011-06-30 21:18:19 +0000238 return locale(*this, &const_cast<_Facet&>(_VSTD::use_facet<_Facet>(__other)));
Howard Hinnantc51e1022010-05-11 19:42:16 +0000239}
240
241template <class _Facet>
242inline _LIBCPP_INLINE_VISIBILITY
243bool
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000244has_facet(const locale& __l) _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +0000245{
246 return __l.has_facet(_Facet::id);
247}
248
249template <class _Facet>
250inline _LIBCPP_INLINE_VISIBILITY
251const _Facet&
252use_facet(const locale& __l)
253{
254 return static_cast<const _Facet&>(*__l.use_facet(_Facet::id));
255}
256
257// template <class _CharT> class collate;
258
259template <class _CharT>
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +0000260class _LIBCPP_TEMPLATE_VIS collate
Howard Hinnantc51e1022010-05-11 19:42:16 +0000261 : public locale::facet
262{
263public:
264 typedef _CharT char_type;
265 typedef basic_string<char_type> string_type;
266
Howard Hinnant9833cad2010-09-21 18:58:51 +0000267 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000268 explicit collate(size_t __refs = 0)
269 : locale::facet(__refs) {}
270
Howard Hinnant9833cad2010-09-21 18:58:51 +0000271 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000272 int compare(const char_type* __lo1, const char_type* __hi1,
273 const char_type* __lo2, const char_type* __hi2) const
274 {
275 return do_compare(__lo1, __hi1, __lo2, __hi2);
276 }
277
Eric Fiselier39b86ea2019-03-08 23:59:29 +0000278 // FIXME(EricWF): The _LIBCPP_ALWAYS_INLINE is needed on Windows to work
279 // around a dllimport bug that expects an external instantiation.
Howard Hinnant9833cad2010-09-21 18:58:51 +0000280 _LIBCPP_INLINE_VISIBILITY
Eric Fiselier39b86ea2019-03-08 23:59:29 +0000281 _LIBCPP_ALWAYS_INLINE
Howard Hinnantc51e1022010-05-11 19:42:16 +0000282 string_type transform(const char_type* __lo, const char_type* __hi) const
283 {
284 return do_transform(__lo, __hi);
285 }
286
Howard Hinnant9833cad2010-09-21 18:58:51 +0000287 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000288 long hash(const char_type* __lo, const char_type* __hi) const
289 {
290 return do_hash(__lo, __hi);
291 }
292
293 static locale::id id;
294
295protected:
296 ~collate();
297 virtual int do_compare(const char_type* __lo1, const char_type* __hi1,
298 const char_type* __lo2, const char_type* __hi2) const;
299 virtual string_type do_transform(const char_type* __lo, const char_type* __hi) const
300 {return string_type(__lo, __hi);}
301 virtual long do_hash(const char_type* __lo, const char_type* __hi) const;
302};
303
304template <class _CharT> locale::id collate<_CharT>::id;
305
306template <class _CharT>
307collate<_CharT>::~collate()
308{
309}
310
311template <class _CharT>
312int
313collate<_CharT>::do_compare(const char_type* __lo1, const char_type* __hi1,
314 const char_type* __lo2, const char_type* __hi2) const
315{
316 for (; __lo2 != __hi2; ++__lo1, ++__lo2)
317 {
318 if (__lo1 == __hi1 || *__lo1 < *__lo2)
319 return -1;
320 if (*__lo2 < *__lo1)
321 return 1;
322 }
323 return __lo1 != __hi1;
324}
325
326template <class _CharT>
327long
Howard Hinnant8c2bf6b2011-10-11 16:00:46 +0000328collate<_CharT>::do_hash(const char_type* __lo, const char_type* __hi) const
Howard Hinnantc51e1022010-05-11 19:42:16 +0000329{
Howard Hinnant8c2bf6b2011-10-11 16:00:46 +0000330 size_t __h = 0;
331 const size_t __sr = __CHAR_BIT__ * sizeof(size_t) - 8;
332 const size_t __mask = size_t(0xF) << (__sr + 4);
333 for(const char_type* __p = __lo; __p != __hi; ++__p)
Howard Hinnantc51e1022010-05-11 19:42:16 +0000334 {
Howard Hinnant28b24882011-12-01 20:21:04 +0000335 __h = (__h << 4) + static_cast<size_t>(*__p);
Howard Hinnant8c2bf6b2011-10-11 16:00:46 +0000336 size_t __g = __h & __mask;
337 __h ^= __g | (__g >> __sr);
Howard Hinnantc51e1022010-05-11 19:42:16 +0000338 }
Howard Hinnant8c2bf6b2011-10-11 16:00:46 +0000339 return static_cast<long>(__h);
Howard Hinnantc51e1022010-05-11 19:42:16 +0000340}
341
Louis Dionneb5ae3a72020-10-02 14:29:48 -0400342_LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS collate<char>)
343_LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS collate<wchar_t>)
Howard Hinnantc51e1022010-05-11 19:42:16 +0000344
345// template <class CharT> class collate_byname;
346
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +0000347template <class _CharT> class _LIBCPP_TEMPLATE_VIS collate_byname;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000348
349template <>
Howard Hinnant8331b762013-03-06 23:30:19 +0000350class _LIBCPP_TYPE_VIS collate_byname<char>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000351 : public collate<char>
352{
353 locale_t __l;
354public:
355 typedef char char_type;
356 typedef basic_string<char_type> string_type;
357
358 explicit collate_byname(const char* __n, size_t __refs = 0);
359 explicit collate_byname(const string& __n, size_t __refs = 0);
360
361protected:
362 ~collate_byname();
363 virtual int do_compare(const char_type* __lo1, const char_type* __hi1,
364 const char_type* __lo2, const char_type* __hi2) const;
365 virtual string_type do_transform(const char_type* __lo, const char_type* __hi) const;
366};
367
368template <>
Howard Hinnant8331b762013-03-06 23:30:19 +0000369class _LIBCPP_TYPE_VIS collate_byname<wchar_t>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000370 : public collate<wchar_t>
371{
372 locale_t __l;
373public:
374 typedef wchar_t char_type;
375 typedef basic_string<char_type> string_type;
376
377 explicit collate_byname(const char* __n, size_t __refs = 0);
378 explicit collate_byname(const string& __n, size_t __refs = 0);
379
380protected:
381 ~collate_byname();
382
383 virtual int do_compare(const char_type* __lo1, const char_type* __hi1,
384 const char_type* __lo2, const char_type* __hi2) const;
385 virtual string_type do_transform(const char_type* __lo, const char_type* __hi) const;
386};
387
388template <class _CharT, class _Traits, class _Allocator>
389bool
390locale::operator()(const basic_string<_CharT, _Traits, _Allocator>& __x,
391 const basic_string<_CharT, _Traits, _Allocator>& __y) const
392{
Howard Hinnantb1ad5a82011-06-30 21:18:19 +0000393 return _VSTD::use_facet<_VSTD::collate<_CharT> >(*this).compare(
Howard Hinnantc51e1022010-05-11 19:42:16 +0000394 __x.data(), __x.data() + __x.size(),
395 __y.data(), __y.data() + __y.size()) < 0;
396}
397
398// template <class charT> class ctype
399
Howard Hinnant8331b762013-03-06 23:30:19 +0000400class _LIBCPP_TYPE_VIS ctype_base
Howard Hinnant9833cad2010-09-21 18:58:51 +0000401{
Howard Hinnantc51e1022010-05-11 19:42:16 +0000402public:
Xiang Xiaoa0562e92020-11-11 15:30:21 -0500403#if defined(_LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE)
404 typedef unsigned long mask;
405 static const mask space = 1<<0;
406 static const mask print = 1<<1;
407 static const mask cntrl = 1<<2;
408 static const mask upper = 1<<3;
409 static const mask lower = 1<<4;
410 static const mask alpha = 1<<5;
411 static const mask digit = 1<<6;
412 static const mask punct = 1<<7;
413 static const mask xdigit = 1<<8;
414 static const mask blank = 1<<9;
415#if defined(__BIONIC__)
416 // Historically this was a part of regex_traits rather than ctype_base. The
417 // historical value of the constant is preserved for ABI compatibility.
418 static const mask __regex_word = 0x8000;
419#else
420 static const mask __regex_word = 1<<10;
421#endif // defined(__BIONIC__)
422#elif defined(__GLIBC__)
Alexis Hunt92b0c812011-07-09 00:56:23 +0000423 typedef unsigned short mask;
Howard Hinnant155c2af2010-05-24 17:49:41 +0000424 static const mask space = _ISspace;
425 static const mask print = _ISprint;
426 static const mask cntrl = _IScntrl;
427 static const mask upper = _ISupper;
428 static const mask lower = _ISlower;
429 static const mask alpha = _ISalpha;
430 static const mask digit = _ISdigit;
431 static const mask punct = _ISpunct;
432 static const mask xdigit = _ISxdigit;
433 static const mask blank = _ISblank;
Mikhail Maltsev014ed062019-06-14 09:04:16 +0000434#if defined(__mips__)
Mikhail Maltsev12eb5af2019-08-20 10:19:55 +0000435 static const mask __regex_word = static_cast<mask>(_ISbit(15));
Mikhail Maltsev014ed062019-06-14 09:04:16 +0000436#else
437 static const mask __regex_word = 0x80;
438#endif
Eric Fiselierbb999f92017-05-31 22:14:05 +0000439#elif defined(_LIBCPP_MSVCRT_LIKE)
Howard Hinnantd7a78632011-09-29 13:33:15 +0000440 typedef unsigned short mask;
Howard Hinnantdd0d7022011-09-22 19:10:18 +0000441 static const mask space = _SPACE;
442 static const mask print = _BLANK|_PUNCT|_ALPHA|_DIGIT;
443 static const mask cntrl = _CONTROL;
444 static const mask upper = _UPPER;
445 static const mask lower = _LOWER;
446 static const mask alpha = _ALPHA;
447 static const mask digit = _DIGIT;
448 static const mask punct = _PUNCT;
449 static const mask xdigit = _HEX;
450 static const mask blank = _BLANK;
Mikhail Maltsev014ed062019-06-14 09:04:16 +0000451 static const mask __regex_word = 0x80;
Jonathan Roelofsae9ab252015-03-11 17:00:28 +0000452# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT
Dan Albertebdf28b2015-03-11 00:51:06 +0000453#elif defined(__APPLE__) || defined(__FreeBSD__) || defined(__EMSCRIPTEN__) || defined(__NetBSD__)
JF Bastien0c265d82015-02-25 22:16:46 +0000454# ifdef __APPLE__
David Chisnall1d581062011-09-21 08:39:44 +0000455 typedef __uint32_t mask;
JF Bastien0c265d82015-02-25 22:16:46 +0000456# elif defined(__FreeBSD__)
David Chisnall1d581062011-09-21 08:39:44 +0000457 typedef unsigned long mask;
Vasileios Kalintirisc5dd8942015-11-24 10:24:54 +0000458# elif defined(__EMSCRIPTEN__) || defined(__NetBSD__)
Howard Hinnant942dbd22013-03-29 18:27:28 +0000459 typedef unsigned short mask;
JF Bastien0c265d82015-02-25 22:16:46 +0000460# endif
David Chisnall1d581062011-09-21 08:39:44 +0000461 static const mask space = _CTYPE_S;
462 static const mask print = _CTYPE_R;
463 static const mask cntrl = _CTYPE_C;
464 static const mask upper = _CTYPE_U;
465 static const mask lower = _CTYPE_L;
466 static const mask alpha = _CTYPE_A;
467 static const mask digit = _CTYPE_D;
468 static const mask punct = _CTYPE_P;
469 static const mask xdigit = _CTYPE_X;
Dan Albert2dca4072014-07-23 19:32:03 +0000470
Joerg Sonnenberger153e4162013-05-17 21:17:34 +0000471# if defined(__NetBSD__)
472 static const mask blank = _CTYPE_BL;
Mikhail Maltsev014ed062019-06-14 09:04:16 +0000473 // NetBSD defines classes up to 0x2000
474 // see sys/ctype_bits.h, _CTYPE_Q
475 static const mask __regex_word = 0x8000;
Joerg Sonnenberger153e4162013-05-17 21:17:34 +0000476# else
David Chisnall1d581062011-09-21 08:39:44 +0000477 static const mask blank = _CTYPE_B;
Mikhail Maltsev014ed062019-06-14 09:04:16 +0000478 static const mask __regex_word = 0x80;
Joerg Sonnenberger153e4162013-05-17 21:17:34 +0000479# endif
Howard Hinnanta47505d2013-08-30 14:42:39 +0000480#elif defined(__sun__) || defined(_AIX)
David Chisnall8074c342012-02-29 13:05:08 +0000481 typedef unsigned int 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;
Mikhail Maltsev014ed062019-06-14 09:04:16 +0000492 static const mask __regex_word = 0x80;
JF Bastien0c265d82015-02-25 22:16:46 +0000493#elif defined(_NEWLIB_VERSION)
494 // Same type as Newlib's _ctype_ array in newlib/libc/include/ctype.h.
495 typedef char mask;
496 static const mask space = _S;
497 static const mask print = _P | _U | _L | _N | _B;
498 static const mask cntrl = _C;
499 static const mask upper = _U;
500 static const mask lower = _L;
501 static const mask alpha = _U | _L;
502 static const mask digit = _N;
503 static const mask punct = _P;
504 static const mask xdigit = _X | _N;
505 static const mask blank = _B;
Mikhail Maltsev014ed062019-06-14 09:04:16 +0000506 static const mask __regex_word = 0x80;
Jonathan Roelofsae9ab252015-03-11 17:00:28 +0000507# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_PRINT
508# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_ALPHA
509# define _LIBCPP_CTYPE_MASK_IS_COMPOSITE_XDIGIT
JF Bastien0c265d82015-02-25 22:16:46 +0000510#else
Xiang Xiaoa0562e92020-11-11 15:30:21 -0500511# error unknown rune table for this platform -- do you mean to define _LIBCPP_PROVIDES_DEFAULT_RUNE_TABLE?
JF Bastien0c265d82015-02-25 22:16:46 +0000512#endif
Howard Hinnantc51e1022010-05-11 19:42:16 +0000513 static const mask alnum = alpha | digit;
514 static const mask graph = alnum | punct;
515
Louis Dionne16fe2952018-07-11 23:14:33 +0000516 _LIBCPP_INLINE_VISIBILITY ctype_base() {}
Howard Hinnantc51e1022010-05-11 19:42:16 +0000517};
518
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +0000519template <class _CharT> class _LIBCPP_TEMPLATE_VIS ctype;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000520
521template <>
Howard Hinnant8331b762013-03-06 23:30:19 +0000522class _LIBCPP_TYPE_VIS ctype<wchar_t>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000523 : public locale::facet,
524 public ctype_base
525{
526public:
527 typedef wchar_t char_type;
Howard Hinnant3b6579a2010-08-22 00:02:43 +0000528
Louis Dionne16fe2952018-07-11 23:14:33 +0000529 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000530 explicit ctype(size_t __refs = 0)
531 : locale::facet(__refs) {}
532
Louis Dionne16fe2952018-07-11 23:14:33 +0000533 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000534 bool is(mask __m, char_type __c) const
535 {
536 return do_is(__m, __c);
537 }
538
Louis Dionne16fe2952018-07-11 23:14:33 +0000539 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000540 const char_type* is(const char_type* __low, const char_type* __high, mask* __vec) const
541 {
542 return do_is(__low, __high, __vec);
543 }
544
Louis Dionne16fe2952018-07-11 23:14:33 +0000545 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000546 const char_type* scan_is(mask __m, const char_type* __low, const char_type* __high) const
547 {
548 return do_scan_is(__m, __low, __high);
549 }
550
Louis Dionne16fe2952018-07-11 23:14:33 +0000551 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000552 const char_type* scan_not(mask __m, const char_type* __low, const char_type* __high) const
553 {
554 return do_scan_not(__m, __low, __high);
555 }
556
Louis Dionne16fe2952018-07-11 23:14:33 +0000557 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000558 char_type toupper(char_type __c) const
559 {
560 return do_toupper(__c);
561 }
562
Louis Dionne16fe2952018-07-11 23:14:33 +0000563 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000564 const char_type* toupper(char_type* __low, const char_type* __high) const
565 {
566 return do_toupper(__low, __high);
567 }
568
Louis Dionne16fe2952018-07-11 23:14:33 +0000569 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000570 char_type tolower(char_type __c) const
571 {
572 return do_tolower(__c);
573 }
574
Louis Dionne16fe2952018-07-11 23:14:33 +0000575 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000576 const char_type* tolower(char_type* __low, const char_type* __high) const
577 {
578 return do_tolower(__low, __high);
579 }
580
Louis Dionne16fe2952018-07-11 23:14:33 +0000581 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000582 char_type widen(char __c) const
583 {
584 return do_widen(__c);
585 }
586
Louis Dionne16fe2952018-07-11 23:14:33 +0000587 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000588 const char* widen(const char* __low, const char* __high, char_type* __to) const
589 {
590 return do_widen(__low, __high, __to);
591 }
592
Louis Dionne16fe2952018-07-11 23:14:33 +0000593 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000594 char narrow(char_type __c, char __dfault) const
595 {
596 return do_narrow(__c, __dfault);
597 }
598
Louis Dionne16fe2952018-07-11 23:14:33 +0000599 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000600 const char_type* narrow(const char_type* __low, const char_type* __high, char __dfault, char* __to) const
601 {
602 return do_narrow(__low, __high, __dfault, __to);
603 }
604
605 static locale::id id;
606
607protected:
608 ~ctype();
609 virtual bool do_is(mask __m, char_type __c) const;
610 virtual const char_type* do_is(const char_type* __low, const char_type* __high, mask* __vec) const;
611 virtual const char_type* do_scan_is(mask __m, const char_type* __low, const char_type* __high) const;
612 virtual const char_type* do_scan_not(mask __m, const char_type* __low, const char_type* __high) const;
613 virtual char_type do_toupper(char_type) const;
614 virtual const char_type* do_toupper(char_type* __low, const char_type* __high) const;
615 virtual char_type do_tolower(char_type) const;
616 virtual const char_type* do_tolower(char_type* __low, const char_type* __high) const;
617 virtual char_type do_widen(char) const;
618 virtual const char* do_widen(const char* __low, const char* __high, char_type* __dest) const;
619 virtual char do_narrow(char_type, char __dfault) const;
620 virtual const char_type* do_narrow(const char_type* __low, const char_type* __high, char __dfault, char* __dest) const;
621};
622
623template <>
Howard Hinnant8331b762013-03-06 23:30:19 +0000624class _LIBCPP_TYPE_VIS ctype<char>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000625 : public locale::facet, public ctype_base
626{
627 const mask* __tab_;
628 bool __del_;
629public:
630 typedef char char_type;
631
Bruce Mitchener170d8972020-11-24 12:53:53 -0500632 explicit ctype(const mask* __tab = nullptr, bool __del = false, size_t __refs = 0);
Howard Hinnantc51e1022010-05-11 19:42:16 +0000633
Louis Dionne16fe2952018-07-11 23:14:33 +0000634 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000635 bool is(mask __m, char_type __c) const
636 {
Marshall Clow11de4872013-10-21 14:41:05 +0000637 return isascii(__c) ? (__tab_[static_cast<int>(__c)] & __m) !=0 : false;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000638 }
639
Louis Dionne16fe2952018-07-11 23:14:33 +0000640 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000641 const char_type* is(const char_type* __low, const char_type* __high, mask* __vec) const
642 {
643 for (; __low != __high; ++__low, ++__vec)
Howard Hinnant28b24882011-12-01 20:21:04 +0000644 *__vec = isascii(*__low) ? __tab_[static_cast<int>(*__low)] : 0;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000645 return __low;
646 }
647
Louis Dionne16fe2952018-07-11 23:14:33 +0000648 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000649 const char_type* scan_is (mask __m, const char_type* __low, const char_type* __high) const
650 {
651 for (; __low != __high; ++__low)
Howard Hinnant28b24882011-12-01 20:21:04 +0000652 if (isascii(*__low) && (__tab_[static_cast<int>(*__low)] & __m))
Howard Hinnantc51e1022010-05-11 19:42:16 +0000653 break;
654 return __low;
655 }
656
Louis Dionne16fe2952018-07-11 23:14:33 +0000657 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000658 const char_type* scan_not(mask __m, const char_type* __low, const char_type* __high) const
659 {
660 for (; __low != __high; ++__low)
Howard Hinnant28b24882011-12-01 20:21:04 +0000661 if (!(isascii(*__low) && (__tab_[static_cast<int>(*__low)] & __m)))
Howard Hinnantc51e1022010-05-11 19:42:16 +0000662 break;
663 return __low;
664 }
665
Louis Dionne16fe2952018-07-11 23:14:33 +0000666 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000667 char_type toupper(char_type __c) const
668 {
669 return do_toupper(__c);
670 }
671
Louis Dionne16fe2952018-07-11 23:14:33 +0000672 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000673 const char_type* toupper(char_type* __low, const char_type* __high) const
674 {
675 return do_toupper(__low, __high);
676 }
677
Louis Dionne16fe2952018-07-11 23:14:33 +0000678 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000679 char_type tolower(char_type __c) const
680 {
681 return do_tolower(__c);
682 }
683
Louis Dionne16fe2952018-07-11 23:14:33 +0000684 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000685 const char_type* tolower(char_type* __low, const char_type* __high) const
686 {
687 return do_tolower(__low, __high);
688 }
689
Louis Dionne16fe2952018-07-11 23:14:33 +0000690 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000691 char_type widen(char __c) const
692 {
693 return do_widen(__c);
694 }
695
Louis Dionne16fe2952018-07-11 23:14:33 +0000696 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000697 const char* widen(const char* __low, const char* __high, char_type* __to) const
698 {
699 return do_widen(__low, __high, __to);
700 }
701
Louis Dionne16fe2952018-07-11 23:14:33 +0000702 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000703 char narrow(char_type __c, char __dfault) const
704 {
705 return do_narrow(__c, __dfault);
706 }
707
Louis Dionne16fe2952018-07-11 23:14:33 +0000708 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000709 const char* narrow(const char_type* __low, const char_type* __high, char __dfault, char* __to) const
710 {
711 return do_narrow(__low, __high, __dfault, __to);
712 }
713
714 static locale::id id;
715
Howard Hinnant155c2af2010-05-24 17:49:41 +0000716#ifdef _CACHED_RUNES
Howard Hinnantc51e1022010-05-11 19:42:16 +0000717 static const size_t table_size = _CACHED_RUNES;
Howard Hinnant155c2af2010-05-24 17:49:41 +0000718#else
719 static const size_t table_size = 256; // FIXME: Don't hardcode this.
720#endif
Louis Dionne16fe2952018-07-11 23:14:33 +0000721 _LIBCPP_INLINE_VISIBILITY const mask* table() const _NOEXCEPT {return __tab_;}
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000722 static const mask* classic_table() _NOEXCEPT;
Vasileios Kalintirisc5dd8942015-11-24 10:24:54 +0000723#if defined(__GLIBC__) || defined(__EMSCRIPTEN__)
Alexis Hunt92b0c812011-07-09 00:56:23 +0000724 static const int* __classic_upper_table() _NOEXCEPT;
725 static const int* __classic_lower_table() _NOEXCEPT;
Alexis Hunt5a4dd562011-07-09 01:09:31 +0000726#endif
Joerg Sonnenberger153e4162013-05-17 21:17:34 +0000727#if defined(__NetBSD__)
728 static const short* __classic_upper_table() _NOEXCEPT;
729 static const short* __classic_lower_table() _NOEXCEPT;
730#endif
Howard Hinnantc51e1022010-05-11 19:42:16 +0000731
732protected:
733 ~ctype();
734 virtual char_type do_toupper(char_type __c) const;
735 virtual const char_type* do_toupper(char_type* __low, const char_type* __high) const;
736 virtual char_type do_tolower(char_type __c) const;
737 virtual const char_type* do_tolower(char_type* __low, const char_type* __high) const;
738 virtual char_type do_widen(char __c) const;
739 virtual const char* do_widen(const char* __low, const char* __high, char_type* __to) const;
740 virtual char do_narrow(char_type __c, char __dfault) const;
741 virtual const char* do_narrow(const char_type* __low, const char_type* __high, char __dfault, char* __to) const;
742};
743
744// template <class CharT> class ctype_byname;
745
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +0000746template <class _CharT> class _LIBCPP_TEMPLATE_VIS ctype_byname;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000747
748template <>
Howard Hinnant8331b762013-03-06 23:30:19 +0000749class _LIBCPP_TYPE_VIS ctype_byname<char>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000750 : public ctype<char>
751{
752 locale_t __l;
753
754public:
755 explicit ctype_byname(const char*, size_t = 0);
756 explicit ctype_byname(const string&, size_t = 0);
757
758protected:
759 ~ctype_byname();
760 virtual char_type do_toupper(char_type) const;
761 virtual const char_type* do_toupper(char_type* __low, const char_type* __high) const;
762 virtual char_type do_tolower(char_type) const;
763 virtual const char_type* do_tolower(char_type* __low, const char_type* __high) const;
764};
765
766template <>
Howard Hinnant8331b762013-03-06 23:30:19 +0000767class _LIBCPP_TYPE_VIS ctype_byname<wchar_t>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000768 : public ctype<wchar_t>
769{
770 locale_t __l;
771
772public:
773 explicit ctype_byname(const char*, size_t = 0);
774 explicit ctype_byname(const string&, size_t = 0);
775
776protected:
777 ~ctype_byname();
778 virtual bool do_is(mask __m, char_type __c) const;
779 virtual const char_type* do_is(const char_type* __low, const char_type* __high, mask* __vec) const;
780 virtual const char_type* do_scan_is(mask __m, const char_type* __low, const char_type* __high) const;
781 virtual const char_type* do_scan_not(mask __m, const char_type* __low, const char_type* __high) const;
782 virtual char_type do_toupper(char_type) const;
783 virtual const char_type* do_toupper(char_type* __low, const char_type* __high) const;
784 virtual char_type do_tolower(char_type) const;
785 virtual const char_type* do_tolower(char_type* __low, const char_type* __high) const;
786 virtual char_type do_widen(char) const;
787 virtual const char* do_widen(const char* __low, const char* __high, char_type* __dest) const;
788 virtual char do_narrow(char_type, char __dfault) const;
789 virtual const char_type* do_narrow(const char_type* __low, const char_type* __high, char __dfault, char* __dest) const;
790};
791
792template <class _CharT>
793inline _LIBCPP_INLINE_VISIBILITY
794bool
795isspace(_CharT __c, const locale& __loc)
796{
797 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::space, __c);
798}
799
800template <class _CharT>
801inline _LIBCPP_INLINE_VISIBILITY
802bool
803isprint(_CharT __c, const locale& __loc)
804{
805 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::print, __c);
806}
807
808template <class _CharT>
809inline _LIBCPP_INLINE_VISIBILITY
810bool
811iscntrl(_CharT __c, const locale& __loc)
812{
813 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::cntrl, __c);
814}
815
816template <class _CharT>
817inline _LIBCPP_INLINE_VISIBILITY
818bool
819isupper(_CharT __c, const locale& __loc)
820{
821 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::upper, __c);
822}
823
824template <class _CharT>
825inline _LIBCPP_INLINE_VISIBILITY
826bool
827islower(_CharT __c, const locale& __loc)
828{
829 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::lower, __c);
830}
831
832template <class _CharT>
833inline _LIBCPP_INLINE_VISIBILITY
834bool
835isalpha(_CharT __c, const locale& __loc)
836{
837 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::alpha, __c);
838}
839
840template <class _CharT>
841inline _LIBCPP_INLINE_VISIBILITY
842bool
843isdigit(_CharT __c, const locale& __loc)
844{
845 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::digit, __c);
846}
847
848template <class _CharT>
849inline _LIBCPP_INLINE_VISIBILITY
850bool
851ispunct(_CharT __c, const locale& __loc)
852{
853 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::punct, __c);
854}
855
856template <class _CharT>
857inline _LIBCPP_INLINE_VISIBILITY
858bool
859isxdigit(_CharT __c, const locale& __loc)
860{
861 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::xdigit, __c);
862}
863
864template <class _CharT>
865inline _LIBCPP_INLINE_VISIBILITY
866bool
867isalnum(_CharT __c, const locale& __loc)
868{
869 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::alnum, __c);
870}
871
872template <class _CharT>
873inline _LIBCPP_INLINE_VISIBILITY
874bool
875isgraph(_CharT __c, const locale& __loc)
876{
877 return use_facet<ctype<_CharT> >(__loc).is(ctype_base::graph, __c);
878}
879
880template <class _CharT>
881inline _LIBCPP_INLINE_VISIBILITY
882_CharT
883toupper(_CharT __c, const locale& __loc)
884{
885 return use_facet<ctype<_CharT> >(__loc).toupper(__c);
886}
887
888template <class _CharT>
889inline _LIBCPP_INLINE_VISIBILITY
890_CharT
891tolower(_CharT __c, const locale& __loc)
892{
893 return use_facet<ctype<_CharT> >(__loc).tolower(__c);
894}
895
896// codecvt_base
897
Howard Hinnant8331b762013-03-06 23:30:19 +0000898class _LIBCPP_TYPE_VIS codecvt_base
Howard Hinnantc51e1022010-05-11 19:42:16 +0000899{
900public:
Louis Dionne16fe2952018-07-11 23:14:33 +0000901 _LIBCPP_INLINE_VISIBILITY codecvt_base() {}
Howard Hinnantc51e1022010-05-11 19:42:16 +0000902 enum result {ok, partial, error, noconv};
903};
904
905// template <class internT, class externT, class stateT> class codecvt;
906
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +0000907template <class _InternT, class _ExternT, class _StateT> class _LIBCPP_TEMPLATE_VIS codecvt;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000908
909// template <> class codecvt<char, char, mbstate_t>
910
911template <>
Howard Hinnant8331b762013-03-06 23:30:19 +0000912class _LIBCPP_TYPE_VIS codecvt<char, char, mbstate_t>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000913 : public locale::facet,
914 public codecvt_base
915{
916public:
917 typedef char intern_type;
918 typedef char extern_type;
919 typedef mbstate_t state_type;
920
Louis Dionne16fe2952018-07-11 23:14:33 +0000921 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000922 explicit codecvt(size_t __refs = 0)
923 : locale::facet(__refs) {}
924
Louis Dionne16fe2952018-07-11 23:14:33 +0000925 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000926 result out(state_type& __st,
927 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
928 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
929 {
930 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
931 }
932
Louis Dionne16fe2952018-07-11 23:14:33 +0000933 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000934 result unshift(state_type& __st,
935 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
936 {
937 return do_unshift(__st, __to, __to_end, __to_nxt);
938 }
939
Louis Dionne16fe2952018-07-11 23:14:33 +0000940 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000941 result in(state_type& __st,
942 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
943 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const
944 {
945 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
946 }
947
Louis Dionne16fe2952018-07-11 23:14:33 +0000948 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000949 int encoding() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +0000950 {
951 return do_encoding();
952 }
953
Louis Dionne16fe2952018-07-11 23:14:33 +0000954 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000955 bool always_noconv() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +0000956 {
957 return do_always_noconv();
958 }
959
Louis Dionne16fe2952018-07-11 23:14:33 +0000960 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000961 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const
962 {
963 return do_length(__st, __frm, __end, __mx);
964 }
965
Louis Dionne16fe2952018-07-11 23:14:33 +0000966 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000967 int max_length() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +0000968 {
969 return do_max_length();
970 }
971
972 static locale::id id;
973
974protected:
Louis Dionne16fe2952018-07-11 23:14:33 +0000975 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +0000976 explicit codecvt(const char*, size_t __refs = 0)
977 : locale::facet(__refs) {}
978
979 ~codecvt();
980
981 virtual result do_out(state_type& __st,
982 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
983 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
984 virtual result do_in(state_type& __st,
985 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
986 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const;
987 virtual result do_unshift(state_type& __st,
988 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000989 virtual int do_encoding() const _NOEXCEPT;
990 virtual bool do_always_noconv() const _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000991 virtual int do_length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
Howard Hinnant7c9e5732011-05-31 15:34:58 +0000992 virtual int do_max_length() const _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +0000993};
994
995// template <> class codecvt<wchar_t, char, mbstate_t>
996
997template <>
Howard Hinnant8331b762013-03-06 23:30:19 +0000998class _LIBCPP_TYPE_VIS codecvt<wchar_t, char, mbstate_t>
Howard Hinnantc51e1022010-05-11 19:42:16 +0000999 : public locale::facet,
1000 public codecvt_base
1001{
1002 locale_t __l;
1003public:
1004 typedef wchar_t intern_type;
1005 typedef char extern_type;
1006 typedef mbstate_t state_type;
1007
1008 explicit codecvt(size_t __refs = 0);
1009
Louis Dionne16fe2952018-07-11 23:14:33 +00001010 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001011 result out(state_type& __st,
1012 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1013 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1014 {
1015 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1016 }
1017
Louis Dionne16fe2952018-07-11 23:14:33 +00001018 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001019 result unshift(state_type& __st,
1020 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1021 {
1022 return do_unshift(__st, __to, __to_end, __to_nxt);
1023 }
1024
Louis Dionne16fe2952018-07-11 23:14:33 +00001025 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001026 result in(state_type& __st,
1027 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1028 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const
1029 {
1030 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1031 }
1032
Louis Dionne16fe2952018-07-11 23:14:33 +00001033 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001034 int encoding() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +00001035 {
1036 return do_encoding();
1037 }
1038
Louis Dionne16fe2952018-07-11 23:14:33 +00001039 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001040 bool always_noconv() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +00001041 {
1042 return do_always_noconv();
1043 }
1044
Louis Dionne16fe2952018-07-11 23:14:33 +00001045 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001046 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const
1047 {
1048 return do_length(__st, __frm, __end, __mx);
1049 }
1050
Louis Dionne16fe2952018-07-11 23:14:33 +00001051 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001052 int max_length() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +00001053 {
1054 return do_max_length();
1055 }
1056
1057 static locale::id id;
1058
1059protected:
1060 explicit codecvt(const char*, size_t __refs = 0);
1061
1062 ~codecvt();
1063
1064 virtual result do_out(state_type& __st,
1065 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1066 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1067 virtual result do_in(state_type& __st,
1068 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1069 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const;
1070 virtual result do_unshift(state_type& __st,
1071 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001072 virtual int do_encoding() const _NOEXCEPT;
1073 virtual bool do_always_noconv() const _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001074 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001075 virtual int do_max_length() const _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001076};
1077
Marek Kurdej718b62c2020-12-02 08:57:02 +01001078// template <> class codecvt<char16_t, char, mbstate_t> // deprecated in C++20
Howard Hinnantc51e1022010-05-11 19:42:16 +00001079
1080template <>
Marek Kurdej718b62c2020-12-02 08:57:02 +01001081class _LIBCPP_TYPE_VIS _LIBCPP_DEPRECATED_IN_CXX20 codecvt<char16_t, char, mbstate_t>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001082 : public locale::facet,
1083 public codecvt_base
1084{
1085public:
1086 typedef char16_t intern_type;
1087 typedef char extern_type;
1088 typedef mbstate_t state_type;
1089
Louis Dionne16fe2952018-07-11 23:14:33 +00001090 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001091 explicit codecvt(size_t __refs = 0)
1092 : locale::facet(__refs) {}
1093
Louis Dionne16fe2952018-07-11 23:14:33 +00001094 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001095 result out(state_type& __st,
1096 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1097 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1098 {
1099 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1100 }
1101
Louis Dionne16fe2952018-07-11 23:14:33 +00001102 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001103 result unshift(state_type& __st,
1104 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1105 {
1106 return do_unshift(__st, __to, __to_end, __to_nxt);
1107 }
1108
Louis Dionne16fe2952018-07-11 23:14:33 +00001109 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001110 result in(state_type& __st,
1111 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1112 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const
1113 {
1114 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1115 }
1116
Louis Dionne16fe2952018-07-11 23:14:33 +00001117 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001118 int encoding() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +00001119 {
1120 return do_encoding();
1121 }
1122
Louis Dionne16fe2952018-07-11 23:14:33 +00001123 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001124 bool always_noconv() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +00001125 {
1126 return do_always_noconv();
1127 }
1128
Louis Dionne16fe2952018-07-11 23:14:33 +00001129 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001130 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const
1131 {
1132 return do_length(__st, __frm, __end, __mx);
1133 }
1134
Louis Dionne16fe2952018-07-11 23:14:33 +00001135 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001136 int max_length() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +00001137 {
1138 return do_max_length();
1139 }
1140
1141 static locale::id id;
1142
1143protected:
Louis Dionne16fe2952018-07-11 23:14:33 +00001144 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001145 explicit codecvt(const char*, size_t __refs = 0)
1146 : locale::facet(__refs) {}
1147
1148 ~codecvt();
1149
1150 virtual result do_out(state_type& __st,
1151 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1152 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1153 virtual result do_in(state_type& __st,
1154 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1155 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const;
1156 virtual result do_unshift(state_type& __st,
1157 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001158 virtual int do_encoding() const _NOEXCEPT;
1159 virtual bool do_always_noconv() const _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001160 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001161 virtual int do_max_length() const _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001162};
1163
Marek Kurdej718b62c2020-12-02 08:57:02 +01001164#ifndef _LIBCPP_NO_HAS_CHAR8_T
1165
1166// template <> class codecvt<char16_t, char8_t, mbstate_t> // C++20
Howard Hinnantc51e1022010-05-11 19:42:16 +00001167
1168template <>
Marek Kurdej718b62c2020-12-02 08:57:02 +01001169class _LIBCPP_TYPE_VIS codecvt<char16_t, char8_t, mbstate_t>
1170 : public locale::facet,
1171 public codecvt_base
1172{
1173public:
1174 typedef char16_t intern_type;
1175 typedef char8_t extern_type;
1176 typedef mbstate_t state_type;
1177
1178 _LIBCPP_INLINE_VISIBILITY
1179 explicit codecvt(size_t __refs = 0)
1180 : locale::facet(__refs) {}
1181
1182 _LIBCPP_INLINE_VISIBILITY
1183 result out(state_type& __st,
1184 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1185 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1186 {
1187 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1188 }
1189
1190 _LIBCPP_INLINE_VISIBILITY
1191 result unshift(state_type& __st,
1192 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1193 {
1194 return do_unshift(__st, __to, __to_end, __to_nxt);
1195 }
1196
1197 _LIBCPP_INLINE_VISIBILITY
1198 result in(state_type& __st,
1199 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1200 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const
1201 {
1202 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1203 }
1204
1205 _LIBCPP_INLINE_VISIBILITY
1206 int encoding() const _NOEXCEPT
1207 {
1208 return do_encoding();
1209 }
1210
1211 _LIBCPP_INLINE_VISIBILITY
1212 bool always_noconv() const _NOEXCEPT
1213 {
1214 return do_always_noconv();
1215 }
1216
1217 _LIBCPP_INLINE_VISIBILITY
1218 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const
1219 {
1220 return do_length(__st, __frm, __end, __mx);
1221 }
1222
1223 _LIBCPP_INLINE_VISIBILITY
1224 int max_length() const _NOEXCEPT
1225 {
1226 return do_max_length();
1227 }
1228
1229 static locale::id id;
1230
1231protected:
1232 _LIBCPP_INLINE_VISIBILITY
1233 explicit codecvt(const char*, size_t __refs = 0)
1234 : locale::facet(__refs) {}
1235
1236 ~codecvt();
1237
1238 virtual result do_out(state_type& __st,
1239 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1240 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1241 virtual result do_in(state_type& __st,
1242 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1243 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const;
1244 virtual result do_unshift(state_type& __st,
1245 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1246 virtual int do_encoding() const _NOEXCEPT;
1247 virtual bool do_always_noconv() const _NOEXCEPT;
1248 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
1249 virtual int do_max_length() const _NOEXCEPT;
1250};
1251
1252#endif
1253
1254// template <> class codecvt<char32_t, char, mbstate_t> // deprecated in C++20
1255
1256template <>
1257class _LIBCPP_TYPE_VIS _LIBCPP_DEPRECATED_IN_CXX20 codecvt<char32_t, char, mbstate_t>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001258 : public locale::facet,
1259 public codecvt_base
1260{
1261public:
1262 typedef char32_t intern_type;
1263 typedef char extern_type;
1264 typedef mbstate_t state_type;
1265
Louis Dionne16fe2952018-07-11 23:14:33 +00001266 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001267 explicit codecvt(size_t __refs = 0)
1268 : locale::facet(__refs) {}
1269
Louis Dionne16fe2952018-07-11 23:14:33 +00001270 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001271 result out(state_type& __st,
1272 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1273 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1274 {
1275 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1276 }
1277
Louis Dionne16fe2952018-07-11 23:14:33 +00001278 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001279 result unshift(state_type& __st,
1280 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1281 {
1282 return do_unshift(__st, __to, __to_end, __to_nxt);
1283 }
1284
Louis Dionne16fe2952018-07-11 23:14:33 +00001285 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001286 result in(state_type& __st,
1287 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1288 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const
1289 {
1290 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1291 }
1292
Louis Dionne16fe2952018-07-11 23:14:33 +00001293 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001294 int encoding() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +00001295 {
1296 return do_encoding();
1297 }
1298
Louis Dionne16fe2952018-07-11 23:14:33 +00001299 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001300 bool always_noconv() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +00001301 {
1302 return do_always_noconv();
1303 }
1304
Louis Dionne16fe2952018-07-11 23:14:33 +00001305 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001306 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const
1307 {
1308 return do_length(__st, __frm, __end, __mx);
1309 }
1310
Louis Dionne16fe2952018-07-11 23:14:33 +00001311 _LIBCPP_INLINE_VISIBILITY
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001312 int max_length() const _NOEXCEPT
Howard Hinnantc51e1022010-05-11 19:42:16 +00001313 {
1314 return do_max_length();
1315 }
1316
1317 static locale::id id;
1318
1319protected:
Louis Dionne16fe2952018-07-11 23:14:33 +00001320 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001321 explicit codecvt(const char*, size_t __refs = 0)
1322 : locale::facet(__refs) {}
1323
1324 ~codecvt();
1325
1326 virtual result do_out(state_type& __st,
1327 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1328 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1329 virtual result do_in(state_type& __st,
1330 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1331 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const;
1332 virtual result do_unshift(state_type& __st,
1333 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001334 virtual int do_encoding() const _NOEXCEPT;
1335 virtual bool do_always_noconv() const _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001336 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
Howard Hinnant7c9e5732011-05-31 15:34:58 +00001337 virtual int do_max_length() const _NOEXCEPT;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001338};
1339
Marek Kurdej718b62c2020-12-02 08:57:02 +01001340#ifndef _LIBCPP_NO_HAS_CHAR8_T
1341
1342// template <> class codecvt<char32_t, char8_t, mbstate_t> // C++20
1343
1344template <>
1345class _LIBCPP_TYPE_VIS codecvt<char32_t, char8_t, mbstate_t>
1346 : public locale::facet,
1347 public codecvt_base
1348{
1349public:
1350 typedef char32_t intern_type;
1351 typedef char8_t extern_type;
1352 typedef mbstate_t state_type;
1353
1354 _LIBCPP_INLINE_VISIBILITY
1355 explicit codecvt(size_t __refs = 0)
1356 : locale::facet(__refs) {}
1357
1358 _LIBCPP_INLINE_VISIBILITY
1359 result out(state_type& __st,
1360 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1361 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1362 {
1363 return do_out(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1364 }
1365
1366 _LIBCPP_INLINE_VISIBILITY
1367 result unshift(state_type& __st,
1368 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const
1369 {
1370 return do_unshift(__st, __to, __to_end, __to_nxt);
1371 }
1372
1373 _LIBCPP_INLINE_VISIBILITY
1374 result in(state_type& __st,
1375 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1376 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const
1377 {
1378 return do_in(__st, __frm, __frm_end, __frm_nxt, __to, __to_end, __to_nxt);
1379 }
1380
1381 _LIBCPP_INLINE_VISIBILITY
1382 int encoding() const _NOEXCEPT
1383 {
1384 return do_encoding();
1385 }
1386
1387 _LIBCPP_INLINE_VISIBILITY
1388 bool always_noconv() const _NOEXCEPT
1389 {
1390 return do_always_noconv();
1391 }
1392
1393 _LIBCPP_INLINE_VISIBILITY
1394 int length(state_type& __st, const extern_type* __frm, const extern_type* __end, size_t __mx) const
1395 {
1396 return do_length(__st, __frm, __end, __mx);
1397 }
1398
1399 _LIBCPP_INLINE_VISIBILITY
1400 int max_length() const _NOEXCEPT
1401 {
1402 return do_max_length();
1403 }
1404
1405 static locale::id id;
1406
1407protected:
1408 _LIBCPP_INLINE_VISIBILITY
1409 explicit codecvt(const char*, size_t __refs = 0)
1410 : locale::facet(__refs) {}
1411
1412 ~codecvt();
1413
1414 virtual result do_out(state_type& __st,
1415 const intern_type* __frm, const intern_type* __frm_end, const intern_type*& __frm_nxt,
1416 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1417 virtual result do_in(state_type& __st,
1418 const extern_type* __frm, const extern_type* __frm_end, const extern_type*& __frm_nxt,
1419 intern_type* __to, intern_type* __to_end, intern_type*& __to_nxt) const;
1420 virtual result do_unshift(state_type& __st,
1421 extern_type* __to, extern_type* __to_end, extern_type*& __to_nxt) const;
1422 virtual int do_encoding() const _NOEXCEPT;
1423 virtual bool do_always_noconv() const _NOEXCEPT;
1424 virtual int do_length(state_type&, const extern_type* __frm, const extern_type* __end, size_t __mx) const;
1425 virtual int do_max_length() const _NOEXCEPT;
1426};
1427
1428#endif
1429
Howard Hinnantc51e1022010-05-11 19:42:16 +00001430// template <class _InternT, class _ExternT, class _StateT> class codecvt_byname
1431
1432template <class _InternT, class _ExternT, class _StateT>
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +00001433class _LIBCPP_TEMPLATE_VIS codecvt_byname
Howard Hinnantc51e1022010-05-11 19:42:16 +00001434 : public codecvt<_InternT, _ExternT, _StateT>
1435{
1436public:
Louis Dionne16fe2952018-07-11 23:14:33 +00001437 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001438 explicit codecvt_byname(const char* __nm, size_t __refs = 0)
1439 : codecvt<_InternT, _ExternT, _StateT>(__nm, __refs) {}
Louis Dionne16fe2952018-07-11 23:14:33 +00001440 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001441 explicit codecvt_byname(const string& __nm, size_t __refs = 0)
1442 : codecvt<_InternT, _ExternT, _StateT>(__nm.c_str(), __refs) {}
1443protected:
1444 ~codecvt_byname();
1445};
1446
Marek Kurdej718b62c2020-12-02 08:57:02 +01001447_LIBCPP_SUPPRESS_DEPRECATED_PUSH
Howard Hinnantc51e1022010-05-11 19:42:16 +00001448template <class _InternT, class _ExternT, class _StateT>
1449codecvt_byname<_InternT, _ExternT, _StateT>::~codecvt_byname()
1450{
1451}
Marek Kurdej718b62c2020-12-02 08:57:02 +01001452_LIBCPP_SUPPRESS_DEPRECATED_POP
Howard Hinnantc51e1022010-05-11 19:42:16 +00001453
Louis Dionneb5ae3a72020-10-02 14:29:48 -04001454_LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char, char, mbstate_t>)
1455_LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<wchar_t, char, mbstate_t>)
Marek Kurdej718b62c2020-12-02 08:57:02 +01001456_LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS _LIBCPP_DEPRECATED_IN_CXX20 codecvt_byname<char16_t, char, mbstate_t>) // deprecated in C++20
1457_LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS _LIBCPP_DEPRECATED_IN_CXX20 codecvt_byname<char32_t, char, mbstate_t>) // deprecated in C++20
1458#ifndef _LIBCPP_NO_HAS_CHAR8_T
1459_LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char16_t, char8_t, mbstate_t>) // C++20
1460_LIBCPP_EXTERN_TEMPLATE(class _LIBCPP_EXTERN_TEMPLATE_TYPE_VIS codecvt_byname<char32_t, char8_t, mbstate_t>) // C++20
1461#endif
Howard Hinnantc51e1022010-05-11 19:42:16 +00001462
Howard Hinnantc834c512011-11-29 18:15:50 +00001463template <size_t _Np>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001464struct __narrow_to_utf8
1465{
1466 template <class _OutputIterator, class _CharT>
1467 _OutputIterator
1468 operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const;
1469};
1470
1471template <>
1472struct __narrow_to_utf8<8>
1473{
1474 template <class _OutputIterator, class _CharT>
Louis Dionne16fe2952018-07-11 23:14:33 +00001475 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001476 _OutputIterator
1477 operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const
1478 {
1479 for (; __wb < __we; ++__wb, ++__s)
1480 *__s = *__wb;
1481 return __s;
1482 }
1483};
1484
Marek Kurdej718b62c2020-12-02 08:57:02 +01001485_LIBCPP_SUPPRESS_DEPRECATED_PUSH
Howard Hinnantc51e1022010-05-11 19:42:16 +00001486template <>
Louis Dionne5254b372018-10-25 12:13:43 +00001487struct _LIBCPP_TEMPLATE_VIS __narrow_to_utf8<16>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001488 : public codecvt<char16_t, char, mbstate_t>
1489{
Louis Dionne16fe2952018-07-11 23:14:33 +00001490 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001491 __narrow_to_utf8() : codecvt<char16_t, char, mbstate_t>(1) {}
Marek Kurdej718b62c2020-12-02 08:57:02 +01001492_LIBCPP_SUPPRESS_DEPRECATED_POP
Howard Hinnantc51e1022010-05-11 19:42:16 +00001493
Louis Dionne5254b372018-10-25 12:13:43 +00001494 _LIBCPP_EXPORTED_FROM_ABI ~__narrow_to_utf8();
Howard Hinnantc51e1022010-05-11 19:42:16 +00001495
1496 template <class _OutputIterator, class _CharT>
Louis Dionne16fe2952018-07-11 23:14:33 +00001497 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001498 _OutputIterator
1499 operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const
1500 {
1501 result __r = ok;
1502 mbstate_t __mb;
1503 while (__wb < __we && __r != error)
1504 {
1505 const int __sz = 32;
1506 char __buf[__sz];
1507 char* __bn;
1508 const char16_t* __wn = (const char16_t*)__wb;
1509 __r = do_out(__mb, (const char16_t*)__wb, (const char16_t*)__we, __wn,
1510 __buf, __buf+__sz, __bn);
1511 if (__r == codecvt_base::error || __wn == (const char16_t*)__wb)
1512 __throw_runtime_error("locale not supported");
1513 for (const char* __p = __buf; __p < __bn; ++__p, ++__s)
1514 *__s = *__p;
1515 __wb = (const _CharT*)__wn;
1516 }
1517 return __s;
1518 }
1519};
1520
Marek Kurdej718b62c2020-12-02 08:57:02 +01001521_LIBCPP_SUPPRESS_DEPRECATED_PUSH
Howard Hinnantc51e1022010-05-11 19:42:16 +00001522template <>
Louis Dionne5254b372018-10-25 12:13:43 +00001523struct _LIBCPP_TEMPLATE_VIS __narrow_to_utf8<32>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001524 : public codecvt<char32_t, char, mbstate_t>
1525{
Louis Dionne16fe2952018-07-11 23:14:33 +00001526 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001527 __narrow_to_utf8() : codecvt<char32_t, char, mbstate_t>(1) {}
Marek Kurdej718b62c2020-12-02 08:57:02 +01001528_LIBCPP_SUPPRESS_DEPRECATED_POP
Howard Hinnantc51e1022010-05-11 19:42:16 +00001529
Louis Dionne5254b372018-10-25 12:13:43 +00001530 _LIBCPP_EXPORTED_FROM_ABI ~__narrow_to_utf8();
Howard Hinnantc51e1022010-05-11 19:42:16 +00001531
1532 template <class _OutputIterator, class _CharT>
Louis Dionne16fe2952018-07-11 23:14:33 +00001533 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001534 _OutputIterator
1535 operator()(_OutputIterator __s, const _CharT* __wb, const _CharT* __we) const
1536 {
1537 result __r = ok;
1538 mbstate_t __mb;
1539 while (__wb < __we && __r != error)
1540 {
1541 const int __sz = 32;
1542 char __buf[__sz];
1543 char* __bn;
1544 const char32_t* __wn = (const char32_t*)__wb;
1545 __r = do_out(__mb, (const char32_t*)__wb, (const char32_t*)__we, __wn,
1546 __buf, __buf+__sz, __bn);
1547 if (__r == codecvt_base::error || __wn == (const char32_t*)__wb)
1548 __throw_runtime_error("locale not supported");
1549 for (const char* __p = __buf; __p < __bn; ++__p, ++__s)
1550 *__s = *__p;
1551 __wb = (const _CharT*)__wn;
1552 }
1553 return __s;
1554 }
1555};
1556
Howard Hinnantc834c512011-11-29 18:15:50 +00001557template <size_t _Np>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001558struct __widen_from_utf8
1559{
1560 template <class _OutputIterator>
1561 _OutputIterator
1562 operator()(_OutputIterator __s, const char* __nb, const char* __ne) const;
1563};
1564
1565template <>
1566struct __widen_from_utf8<8>
1567{
1568 template <class _OutputIterator>
Louis Dionne16fe2952018-07-11 23:14:33 +00001569 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001570 _OutputIterator
1571 operator()(_OutputIterator __s, const char* __nb, const char* __ne) const
1572 {
1573 for (; __nb < __ne; ++__nb, ++__s)
1574 *__s = *__nb;
1575 return __s;
1576 }
1577};
1578
Marek Kurdej718b62c2020-12-02 08:57:02 +01001579_LIBCPP_SUPPRESS_DEPRECATED_PUSH
Howard Hinnantc51e1022010-05-11 19:42:16 +00001580template <>
Louis Dionne5254b372018-10-25 12:13:43 +00001581struct _LIBCPP_TEMPLATE_VIS __widen_from_utf8<16>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001582 : public codecvt<char16_t, char, mbstate_t>
1583{
Louis Dionne16fe2952018-07-11 23:14:33 +00001584 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001585 __widen_from_utf8() : codecvt<char16_t, char, mbstate_t>(1) {}
Marek Kurdej718b62c2020-12-02 08:57:02 +01001586_LIBCPP_SUPPRESS_DEPRECATED_POP
Howard Hinnantc51e1022010-05-11 19:42:16 +00001587
Louis Dionne5254b372018-10-25 12:13:43 +00001588 _LIBCPP_EXPORTED_FROM_ABI ~__widen_from_utf8();
Howard Hinnantc51e1022010-05-11 19:42:16 +00001589
1590 template <class _OutputIterator>
Louis Dionne16fe2952018-07-11 23:14:33 +00001591 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001592 _OutputIterator
1593 operator()(_OutputIterator __s, const char* __nb, const char* __ne) const
1594 {
1595 result __r = ok;
1596 mbstate_t __mb;
1597 while (__nb < __ne && __r != error)
1598 {
1599 const int __sz = 32;
1600 char16_t __buf[__sz];
1601 char16_t* __bn;
1602 const char* __nn = __nb;
1603 __r = do_in(__mb, __nb, __ne - __nb > __sz ? __nb+__sz : __ne, __nn,
1604 __buf, __buf+__sz, __bn);
1605 if (__r == codecvt_base::error || __nn == __nb)
1606 __throw_runtime_error("locale not supported");
1607 for (const char16_t* __p = __buf; __p < __bn; ++__p, ++__s)
Martin Storsjö971fc1c2020-10-27 13:01:54 +02001608 *__s = *__p;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001609 __nb = __nn;
1610 }
1611 return __s;
1612 }
1613};
1614
Marek Kurdej718b62c2020-12-02 08:57:02 +01001615_LIBCPP_SUPPRESS_DEPRECATED_PUSH
Howard Hinnantc51e1022010-05-11 19:42:16 +00001616template <>
Louis Dionne5254b372018-10-25 12:13:43 +00001617struct _LIBCPP_TEMPLATE_VIS __widen_from_utf8<32>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001618 : public codecvt<char32_t, char, mbstate_t>
1619{
Louis Dionne16fe2952018-07-11 23:14:33 +00001620 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001621 __widen_from_utf8() : codecvt<char32_t, char, mbstate_t>(1) {}
Marek Kurdej718b62c2020-12-02 08:57:02 +01001622_LIBCPP_SUPPRESS_DEPRECATED_POP
Howard Hinnantc51e1022010-05-11 19:42:16 +00001623
Louis Dionne5254b372018-10-25 12:13:43 +00001624 _LIBCPP_EXPORTED_FROM_ABI ~__widen_from_utf8();
Howard Hinnantc51e1022010-05-11 19:42:16 +00001625
1626 template <class _OutputIterator>
Louis Dionne16fe2952018-07-11 23:14:33 +00001627 _LIBCPP_INLINE_VISIBILITY
Howard Hinnantc51e1022010-05-11 19:42:16 +00001628 _OutputIterator
1629 operator()(_OutputIterator __s, const char* __nb, const char* __ne) const
1630 {
1631 result __r = ok;
1632 mbstate_t __mb;
1633 while (__nb < __ne && __r != error)
1634 {
1635 const int __sz = 32;
1636 char32_t __buf[__sz];
1637 char32_t* __bn;
1638 const char* __nn = __nb;
1639 __r = do_in(__mb, __nb, __ne - __nb > __sz ? __nb+__sz : __ne, __nn,
1640 __buf, __buf+__sz, __bn);
1641 if (__r == codecvt_base::error || __nn == __nb)
1642 __throw_runtime_error("locale not supported");
1643 for (const char32_t* __p = __buf; __p < __bn; ++__p, ++__s)
Martin Storsjö971fc1c2020-10-27 13:01:54 +02001644 *__s = *__p;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001645 __nb = __nn;
1646 }
1647 return __s;
1648 }
1649};
1650
1651// template <class charT> class numpunct
1652
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +00001653template <class _CharT> class _LIBCPP_TEMPLATE_VIS numpunct;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001654
1655template <>
Howard Hinnant8331b762013-03-06 23:30:19 +00001656class _LIBCPP_TYPE_VIS numpunct<char>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001657 : public locale::facet
1658{
1659public:
1660 typedef char char_type;
1661 typedef basic_string<char_type> string_type;
1662
1663 explicit numpunct(size_t __refs = 0);
1664
Louis Dionne16fe2952018-07-11 23:14:33 +00001665 _LIBCPP_INLINE_VISIBILITY char_type decimal_point() const {return do_decimal_point();}
1666 _LIBCPP_INLINE_VISIBILITY char_type thousands_sep() const {return do_thousands_sep();}
1667 _LIBCPP_INLINE_VISIBILITY string grouping() const {return do_grouping();}
1668 _LIBCPP_INLINE_VISIBILITY string_type truename() const {return do_truename();}
1669 _LIBCPP_INLINE_VISIBILITY string_type falsename() const {return do_falsename();}
Howard Hinnantc51e1022010-05-11 19:42:16 +00001670
1671 static locale::id id;
1672
1673protected:
1674 ~numpunct();
1675 virtual char_type do_decimal_point() const;
1676 virtual char_type do_thousands_sep() const;
1677 virtual string do_grouping() const;
1678 virtual string_type do_truename() const;
1679 virtual string_type do_falsename() const;
1680
1681 char_type __decimal_point_;
1682 char_type __thousands_sep_;
1683 string __grouping_;
1684};
1685
1686template <>
Howard Hinnant8331b762013-03-06 23:30:19 +00001687class _LIBCPP_TYPE_VIS numpunct<wchar_t>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001688 : public locale::facet
1689{
1690public:
1691 typedef wchar_t char_type;
1692 typedef basic_string<char_type> string_type;
1693
1694 explicit numpunct(size_t __refs = 0);
1695
Louis Dionne16fe2952018-07-11 23:14:33 +00001696 _LIBCPP_INLINE_VISIBILITY char_type decimal_point() const {return do_decimal_point();}
1697 _LIBCPP_INLINE_VISIBILITY char_type thousands_sep() const {return do_thousands_sep();}
1698 _LIBCPP_INLINE_VISIBILITY string grouping() const {return do_grouping();}
1699 _LIBCPP_INLINE_VISIBILITY string_type truename() const {return do_truename();}
1700 _LIBCPP_INLINE_VISIBILITY string_type falsename() const {return do_falsename();}
Howard Hinnantc51e1022010-05-11 19:42:16 +00001701
1702 static locale::id id;
1703
1704protected:
1705 ~numpunct();
1706 virtual char_type do_decimal_point() const;
1707 virtual char_type do_thousands_sep() const;
1708 virtual string do_grouping() const;
1709 virtual string_type do_truename() const;
1710 virtual string_type do_falsename() const;
1711
1712 char_type __decimal_point_;
1713 char_type __thousands_sep_;
1714 string __grouping_;
1715};
1716
1717// template <class charT> class numpunct_byname
1718
Eric Fiselierb5eb1bf2017-01-04 23:56:00 +00001719template <class _CharT> class _LIBCPP_TEMPLATE_VIS numpunct_byname;
Howard Hinnantc51e1022010-05-11 19:42:16 +00001720
1721template <>
Howard Hinnant8331b762013-03-06 23:30:19 +00001722class _LIBCPP_TYPE_VIS numpunct_byname<char>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001723: public numpunct<char>
1724{
1725public:
1726 typedef char char_type;
1727 typedef basic_string<char_type> string_type;
1728
1729 explicit numpunct_byname(const char* __nm, size_t __refs = 0);
1730 explicit numpunct_byname(const string& __nm, size_t __refs = 0);
1731
1732protected:
1733 ~numpunct_byname();
1734
1735private:
1736 void __init(const char*);
1737};
1738
1739template <>
Howard Hinnant8331b762013-03-06 23:30:19 +00001740class _LIBCPP_TYPE_VIS numpunct_byname<wchar_t>
Howard Hinnantc51e1022010-05-11 19:42:16 +00001741: public numpunct<wchar_t>
1742{
1743public:
1744 typedef wchar_t char_type;
1745 typedef basic_string<char_type> string_type;
1746
1747 explicit numpunct_byname(const char* __nm, size_t __refs = 0);
1748 explicit numpunct_byname(const string& __nm, size_t __refs = 0);
1749
1750protected:
1751 ~numpunct_byname();
1752
1753private:
1754 void __init(const char*);
1755};
1756
1757_LIBCPP_END_NAMESPACE_STD
1758
1759#endif // _LIBCPP___LOCALE