35#if __DECCXX_VER >= 60300000 && __DECCXX_VER < 60400000
43# define _RWSTD_NO_ICONV_CONST_CHAR
54#if defined (__SUNPRO_CC) && __SUNPRO_CC <= 0x540 \
55 && (defined (__SunOS_5_8) || defined (__SunOS_5_9))
73#if defined (_RWSTD_NO_MBRLEN) && !defined (_RWSTD_NO_MBRLEN_IN_LIBC)
75# undef _RWSTD_NO_MBRLEN
85#if defined (_RWSTD_NO_MBLEN) && !defined (_RWSTD_NO_MBLEN_IN_LIBC)
87# undef _RWSTD_NO_MBLEN
97#if defined (_RWSTD_NO_MBTOWC) && !defined (_RWSTD_NO_MBTOWC_IN_LIBC)
99# undef _RWSTD_NO_MBTOWC
109#if defined (_RWSTD_NO_WCSRTOMBS) && !defined (_RWSTD_NO_WCSRTOMBS_IN_LIBC)
111# undef _RWSTD_NO_WCSRTOMBS
121#if defined (_RWSTD_NO_WCRTOMB) && !defined (_RWSTD_NO_WCRTOMB_IN_LIBC)
123# undef _RWSTD_NO_WCRTOMB
133#if defined (_RWSTD_NO_WCTOMB) && !defined (_RWSTD_NO_WCTOMB_IN_LIBC)
135# undef _RWSTD_NO_WCTOMB
148#undef _UTF8_MB_CUR_MAX
149#define _UTF8_MB_CUR_MAX 6
193#define ISO2022_TYPE(x) ((x) & __rw_2022_mask)
196#define UCS_TYPE(x) ((x) & __rw_ucs_mask)
197#define UTF_TYPE(x) ((x) & __rw_utf_mask)
199#define IS_UCS(x) (UCS_TYPE (x) == __rw_ucs)
200#define IS_UCS_BE(x) (UCS_TYPE (x) == __rw_ucs_be)
201#define IS_UCS_LE(x) (UCS_TYPE (x) == __rw_ucs_le)
202#define IS_UCS_BE_LE(x) (UCS_TYPE (x) == __rw_ucs_be_le)
203#define IS_UCS_LE_BE(x) (UCS_TYPE (x) == __rw_ucs_le_be)
205#define IS_UTF8(x) (UCS_TYPE (x) == __rw_utf8)
206#define IS_UTF16(x) (UCS_TYPE (x) == __rw_utf16)
207#define IS_UTF16_BE(x) (UCS_TYPE (x) == __rw_utf16_be)
208#define IS_UTF16_LE(x) (UCS_TYPE (x) == __rw_utf16_le)
211#define USE_LIBC(impl, x) \
212 ((!(impl) || ((x) & __rw_use_libc)) && !(UCS_TYPE (x) || UTF_TYPE (x)))
240__rw_n_ucsmods =
sizeof __rw_ucsmods /
sizeof *__rw_ucsmods;
244__rw_mbsinit (
const StateT *psrc)
246#ifndef _RWSTD_NO_MBSINIT
248 return mbsinit (psrc);
254 return !psrc || 0 == memcmp (psrc, &state,
sizeof state);
262#define min(a, b) ((a) < (b) ? (a) : (b))
264#define max(a,b) ((a) > (b)) ? (a) : (b)
267#ifndef _RWSTD_NO_WCHAR_T
282#ifndef _RWSTD_NO_MBRLEN
285 return mbrlen (
str, emax, &state);
287#elif !defined (_RWSTD_NO_MBLEN)
291 return mblen (
str, emax);
301 const char *next =
str;
303 for (; *next && emax; ++next, --emax);
314__rw_xlit (
const _RW::__rw_codecvt_t* impl,
315 const char *utf8s,
size_t sz)
317 const unsigned int*
const ptbls = impl->get_xliteration_tab ();
319 unsigned int index = 0;
321 for (
const unsigned int* ptbl = ptbls;
sz; --
sz, ++utf8s) {
323 typedef unsigned char UChar;
327 if (_RWSTD_UINT_MAX ==
index)
331 if (
index & 0x80000000) {
332 ptbl = ptbls + 256 *
index;
344static _STD::codecvt_base::result
347 const char *from_end,
348 const char* &from_next,
356 _STD::codecvt_base::result
res = _STD::codecvt_base::ok;
360 size_t src_len = from_end - from;
361 size_t dst_size = to_limit - to;
364 const char* psrc = from;
367 while (dst_size && src_len) {
372#ifndef _RWSTD_NO_MBRTOWC
373 nbytes = mbrtowc (pdst, psrc, src_len, &state);
374#elif !defined (_RWSTD_NO_MBTOWC)
375 nbytes = mbtowc (pdst, psrc, src_len);
377 nbytes = _RWSTD_SIZE_MAX;
381 if (nbytes ==
size_t (-1)) {
382 res = _STD::codecvt_base::error;
388 if (nbytes ==
size_t (-2))
410 if (
res == _STD::codecvt_base::ok && src_len && !dst_size) {
412 size_t tmp = __rw_libc_mbrlen (tmp_state, psrc, src_len);
413 if (
tmp <
size_t (-2))
414 res = _STD::codecvt_base::partial;
421static _STD::codecvt_base::result
424 const wchar_t *from_end,
425 const wchar_t* &from_next,
444 const size_t mb_cur_max = size_t (
MB_CUR_MAX);
447 _STD::codecvt_base::result
res = _STD::codecvt_base::ok;
450 size_t dst_free = size_t (to_limit - to_next);
454 char buff [_RWSTD_MB_LEN_MAX];
457 for ( ; from_next < from_end; ++from_next) {
464 char*
const tmpdst = dst_free < mb_cur_max ? buff : to_next;
474#ifndef _RWSTD_NO_WCRTOMB
479 dst_len = wcrtomb (tmpdst, *from_next, &state);
481#elif !defined (_RWSTD_NO_WCTOMB)
484 dst_len = wctomb (tmpdst, *from_next);
489 dst_len = _RWSTD_SIZE_MAX;
494 if (_RWSTD_SIZE_MAX == dst_len) {
495 res = _STD::codecvt_base::error;
508 if (dst_free < mb_cur_max) {
509 if (dst_free < dst_len) {
517 res = _STD::codecvt_base::partial;
523 memcpy (to_next, buff, dst_len);
537static _STD::codecvt_base::result
538__rw_libc_do_unshift (
_RWSTD_MBSTATE_T& state,
char*& to_next,
char* to_limit)
544 char tmp [_RWSTD_MB_LEN_MAX];
548#ifndef _RWSTD_NO_WCRTOMB
549 ret = wcrtomb (
tmp,
wchar_t (0), &state);
550#elif !defined (_RWSTD_NO_WCTOMB)
551 ret = wctomb (
tmp,
wchar_t (0));
553 ret = _RWSTD_SIZE_MAX;
556 if (_RWSTD_SIZE_MAX == ret)
557 return _STD::codecvt_base::error;
559 if (ret >
size_t (to_limit - to_next)) {
562 return _STD::codecvt_base::partial;
566 memcpy (to_next,
tmp, ret);
568 return _STD::codecvt_base::ok;
576__rw_utf8validate (
const char* from,
size_t nbytes)
581 const unsigned char*
const byte =
587 if (2 == nbytes && (
byte [0] & 0xfeU) == 0xfeU)
594 if (0xe0U ==
byte [0] && (
byte [1] & 0xe0U) == 0x80U)
601 if (0xedU ==
byte [0]) {
602 if (
byte [1] >= 0xa0)
605 else if ( 0xefU ==
byte [0] && 0xbfU ==
byte [1]
606 && 0xbeU <=
byte [2] && 0xbfU >=
byte [2])
611 if (4 == nbytes && 0xf0U ==
byte [0] && (
byte [1] & 0xf0U) == 0x80U)
615 if (5 == nbytes && 0xf8U ==
byte [0] && (
byte [1] & 0xf8U) == 0x80U)
619 if (6 == nbytes && 0xfcU ==
byte [0] && (
byte [1] & 0xfcU) == 0x80U)
622 for (
size_t i = 1;
i < nbytes; ++
i) {
623 if ((
byte [
i] & ~0x3fU) != 0x80U)
631static _STD::codecvt_base::result
632__rw_libstd_do_in (
const char *from_end,
633 const char *&from_next,
637 const _RW::__rw_codecvt_t *impl)
647 _STD::codecvt_base::result
res;
649 for (
const unsigned*
const tab = impl ? impl->n_to_w_tab () : 0; ; ) {
651 if (from_next == from_end) {
652 res = _STD::codecvt_base::ok;
656 if (to_next == to_limit) {
657 res = _STD::codecvt_base::partial;
661 const char* from = from_next;
671 const unsigned off = __rw_mbtowco (tab, from, from_end);
673 if (_RWSTD_UINT_MAX ==
off) {
676 res = _STD::codecvt_base::error;
680 if (from == from_next) {
683 res = _STD::codecvt_base::partial;
687 wchar = use_ucs ? impl->get_ucs4_at_offset (
off)
688 : impl->get_internal_at_offset (
off);
694 const char*
tmp = __rw_utf8toucs4 (&wi, from, from_end);
696 if (strict_utf &&
tmp) {
699 const size_t utf_len =
tmp - from;
701 if (utf_len > 1 && !__rw_utf8validate (from, utf_len))
710 res = _STD::codecvt_base::error;
714 if (from_next == from) {
717 res = _STD::codecvt_base::partial;
732static _STD::codecvt_base::result
733__rw_libstd_do_out (
const wchar_t *from,
734 const wchar_t *from_end,
735 const wchar_t *&from_next,
740 const _RW::__rw_codecvt_t *impl)
743 _STD::codecvt_base::result
res = _STD::codecvt_base::ok;
750 const unsigned int*
const tbl =
751 impl ? use_ucs ? impl->utf8_to_ext_tab () : impl->w_to_n_tab () : 0;
753 for (from_next = from, to_next = to; from_next != from_end; ++from_next) {
755 if (to_next == to_limit) {
756 res = _STD::codecvt_base::partial;
772 if ( WIntT (0xd800U) <= wi && wi <= WIntT (0xdfffU)
773 || WIntT (0xfffeU) <= wi && wi <= WIntT (0xffffU)) {
774 res = _STD::codecvt_base::error;
780 const size_t bytes_avail = to_limit - to_next;
787 utf8_len = __rw_itoutf8 (*from_next, utfbuf);
791 const char* utf = utfbuf;
792 unsigned off = __rw_mbtowco (tbl, utf, utf + utf8_len);
797 if (0 && _RWSTD_UINT_MAX ==
off) {
799 off = __rw_xlit (impl, utfbuf, utf8_len);
801 res = _STD::codecvt_base::error;
806 if (_RWSTD_UINT_MAX ==
off) {
808 res = _STD::codecvt_base::error;
814 res = _STD::codecvt_base::ok;
822 utf8_len = *utf ? strlen (utf) : 1;
823 if (bytes_avail < utf8_len) {
824 res = _STD::codecvt_base::partial;
829 memcpy (to_next, utf, utf8_len);
839 utf8_len = __rw_itoutf8 (*from_next, utfbuf);
841 if (bytes_avail < utf8_len) {
842 res = _STD::codecvt_base::partial;
847 memcpy (to_next, utfbuf, utf8_len);
850 utf8_len = __rw_itoutf8 (*from_next, to_next);
864 const char *from_end,
867 const char*
const from_begin = from;
869 for ( ; imax && from < from_end; --imax) {
873 size_t nbytes = from_end - from;
874 if (_RWSTD_MB_LEN_MAX < nbytes)
875 nbytes = _RWSTD_MB_LEN_MAX;
881 nbytes = __rw_libc_mbrlen (state, from, nbytes);
884 if (nbytes >=
size_t (-2))
891 return from - from_begin;
897__rw_utf8_do_length (
const char *from,
898 const char *from_end,
906 const char *from_next = from;
909 for ( ; imax && from_next < from_end; --imax) {
914 const char*
const next = __rw_utf8toucs4 (&wi, from_next, from_end);
917 if (!next || next == from_next)
924 const size_t utf_len = next - from_next;
927 && utf_len > 1 && !__rw_utf8validate (from_next, utf_len))
934 return from_next - from;
961__rw_libstd_do_length (
const char* from,
962 const char* from_end,
965 const _RW::__rw_codecvt_t* impl)
976 const char* from_next = from;
978 const unsigned char*
const limit =
981 const unsigned int*
const tbls =
982 use_ucs ? impl->utf8_to_ext_tab () : impl->n_to_w_tab ();
987 for ( ; imax && from_next < from_end; --imax) {
989 const unsigned char* next =
992 for (
const unsigned* tbl = tbls; tbl [*next] & 0x80000000; ) {
995 if (_RWSTD_UINT_MAX == tbl [*next])
996 return from_next - from;
999 const unsigned index = tbl [*next] & 0x7fffffff;
1000 tbl = tbls + 256 *
index;
1005 return from_next - from;
1012 return from_next - from;
1015 return __rw_utf8_do_length (from, from_end, imax,
flags);
1024_RW::__rw_facet_id codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::id;
1027 codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::
1028codecvt (
size_t __ref )
1029 : _RW::__rw_facet (__ref)
1037 codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::
1045codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::
1046do_always_noconv ()
const _THROWS (())
1053codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::
1054do_encoding ()
const _THROWS (())
1062codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::
1063do_max_length ()
const _THROWS (())
1069 codecvt_base::result
1070codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::
1071do_out (state_type &state,
1072 const intern_type *from,
1073 const intern_type *from_end,
1074 const intern_type *&from_next,
1076 extern_type *to_end,
1077 extern_type *&to_next)
const
1094 const int mbstate_valid = _RW::__rw_mbsinit (&state);
1105 for (; from_next != from_end && to_next != to_end; ++from_next, ++to_next)
1112 return from_next == from_end ? ok : partial;
1116 codecvt_base::result
1117codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::
1118do_in (state_type &state,
1119 const extern_type *from,
1120 const extern_type *from_end,
1121 const extern_type *&from_next,
1123 intern_type *to_end,
1124 intern_type *&to_next)
const
1138 const int mbstate_valid = _RW::__rw_mbsinit (&state);
1145 for (; from_next != from_end && to_next != to_end;
1146 ++from_next, ++to_next) {
1151 return from_next == from_end ? ok : partial;
1155 codecvt_base::result
1156codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::
1157do_unshift (state_type &state,
1159 extern_type *to_end,
1160 extern_type *&to_next)
const
1171 const int mbstate_valid = _RW::__rw_mbsinit (&state);
1182codecvt<wchar_t, char, _RWSTD_MBSTATE_T>::
1183do_length (state_type &state,
1184 const extern_type *from,
1185 const extern_type *from_end,
1194 const int mbstate_valid = _RW::__rw_mbsinit (&state);
1201 const size_t len = from_end - from;
1202 return int (
len < imax ?
len : imax);
1207codecvt_byname<wchar_t, char, _RWSTD_MBSTATE_T>::
1208codecvt_byname (
const char *
name,
size_t ref)
1209 : codecvt<wchar_t, char, _RWSTD_MBSTATE_T>(ref)
1211 _C_flags = _RW::__rw_encoding_from_name (
name);
1218 if (_RW::stateless == (_C_flags & 0xf)) {
1219 const _RW::__rw_setlocale clocale (_C_name,
LC_CTYPE);
1221 _C_flags = mbtowc (0, 0, 0) ? _RW::stateful : _RW::stateless;
1226 char locale_name [256];
1229 const char* mod = strchr (
name,
'@');
1232 const char*
const mod_nam = mod + 1;
1233 const size_t mod_len = strlen (mod_nam);
1236 if (mod_len > 2 && !memcmp (mod_nam,
"UCS", 3)) {
1240 for (
size_t i = 0;
i != _RW::__rw_n_ucsmods; ++
i) {
1241 if (!strcmp (_RW::__rw_ucsmods [
i].mod, mod_nam)) {
1242 flags = _RW::__rw_ucsmods [
i].flags;
1259 memcpy (locale_name,
name, mod -
name);
1260 locale_name [mod -
name] =
'\0';
1268 const size_t name_len = strlen (
name);
1273 const bool pfx_low = !memcmp (
name,
"utf-", 4);
1274 const bool pfx_cap = !pfx_low && !memcmp (
name,
"UTF-", 4);
1278 if (pfx_low || pfx_cap) {
1280 if (5 == name_len &&
'8' ==
name [4])
1282 else if (!strcmp (
name + 4,
"16"))
1285 if (!strcmp (
name + 4,
"16-BE"))
1287 else if (!strcmp (
name + 4,
"16-LE"))
1291 if (!strcmp (
name + 4,
"16-BE"))
1293 else if (!strcmp (
name + 4,
"16-LE"))
1304 *locale_name =
'\0';
1309 if ( this->_C_opts & this->_C_use_libc
1313 this->_C_set_name (
name, _C_namebuf,
sizeof _C_namebuf);
1319 codecvt_byname<wchar_t, char, _RWSTD_MBSTATE_T>::~
1326 codecvt_base::result
1327codecvt_byname<wchar_t, char, _RWSTD_MBSTATE_T>::
1328do_in (state_type& state,
1329 const extern_type* from,
1330 const extern_type* from_end,
1331 const extern_type*& from_next,
1333 intern_type* to_limit,
1334 intern_type*& to_next)
const
1355 case _RW::stateless: {
1358 const _RW::__rw_codecvt_t*
const impl =
1363 const _RW::__rw_setlocale clocale (_C_name,
LC_CTYPE);
1365#ifndef _RWSTD_NO_MBTOWC
1369 const bool mbstate_valid =
1370 mbtowc (0, 0, 0) || _RW::__rw_mbsinit (&state);
1377 res = _RW::__rw_libc_do_in (state,
1378 from, from_end, from_next,
1379 to, to_limit, to_next);
1384 const int mbstate_valid = _RW::__rw_mbsinit (&state);
1389 res = _RW::__rw_libstd_do_in (from_end, from_next,
1396 case _RW::iso2022_jp:
1397 res = _RW::__rw_iso2022jp_do_in (state, from_next, from_end,
1401 case _RW::iso2022_jp2:
1402 res = _RW::__rw_iso2022jp2_do_in (state, from_next, from_end,
1406 case _RW::iso2022_kr:
1407 case _RW::iso2022_cn:
1416 codecvt_base::result
1417codecvt_byname<wchar_t, char, _RWSTD_MBSTATE_T>::
1418do_out (state_type &state,
1419 const intern_type *from,
1420 const intern_type *from_end,
1421 const intern_type *&from_next,
1423 extern_type *to_limit,
1424 extern_type *&to_next)
const
1439 codecvt_base::result
res = codecvt_base::error;
1444 case _RW::stateless: {
1447 const _RW::__rw_codecvt_t* impl =
1452 const _RW::__rw_setlocale clocale (_C_name,
LC_CTYPE);
1454#ifndef _RWSTD_NO_MBTOWC
1458 const bool mbstate_valid =
1459 mbtowc (0, 0, 0) || _RW::__rw_mbsinit (&state);
1466 res = _RW::__rw_libc_do_out (state, from, from_end, from_next,
1467 to, to_limit, to_next);
1471 const int mbstate_valid = _RW::__rw_mbsinit (&state);
1477 res = _RW::__rw_libstd_do_out (from, from_end, from_next,
1478 to, to_limit, to_next,
1483 case _RW::iso2022_jp:
1484 res = _RW::__rw_iso2022jp_do_out (state, from_next, from_end,
1487 case _RW::iso2022_jp2:
1488 res = _RW::__rw_iso2022jp2_do_out (state, from_next, from_end,
1491 case _RW::iso2022_kr:
1492 case _RW::iso2022_cn:
1501 codecvt_base::result
1502codecvt_byname<wchar_t, char, _RWSTD_MBSTATE_T>::
1503do_unshift (state_type& state,
1505 extern_type* to_limit,
1506 extern_type*& to_next)
const
1517 codecvt_base::result
res = codecvt_base::error;
1522 case _RW::stateless:
1524 if (
USE_LIBC (_C_impdata, _C_flags)) {
1526 const _RW::__rw_setlocale clocale (_C_name,
LC_CTYPE);
1528 if (mbtowc (0, 0, 0) == 0) {
1530 const int mbstate_valid = _RW::__rw_mbsinit (&state);
1533 res = mbstate_valid ? noconv : error;
1536 res = _RW::__rw_libc_do_unshift (state, to_next, to_limit);
1542 const int mbstate_valid = _RW::__rw_mbsinit (&state);
1545 res = mbstate_valid ? noconv : error;
1549 case _RW::iso2022_jp:
1550 res = _RW::__rw_iso2022jp_do_unshift (state, to_next, to_limit);
1552 case _RW::iso2022_jp2:
1553 res = _RW::__rw_iso2022jp2_do_unshift (state, to_next, to_limit);
1555 case _RW::iso2022_kr:
1556 case _RW::iso2022_cn:
1566codecvt_byname<wchar_t, char, _RWSTD_MBSTATE_T>::
1567do_length (state_type& state,
1568 const extern_type *from,
1569 const extern_type *from_end,
1583 case _RW::stateless: {
1586 const _RW::__rw_codecvt_t* impl =
1591 const _RW::__rw_setlocale clocale (this->_C_name,
LC_CTYPE);
1593#ifndef _RWSTD_NO_MBTOWC
1597 const bool mbstate_valid =
1598 mbtowc (0, 0, 0) || _RW::__rw_mbsinit (&state);
1605 len = _RW::__rw_libc_do_length (state, from, from_end, cmax);
1609 const int mbstate_valid = _RW::__rw_mbsinit (&state);
1614 len = _RW::__rw_libstd_do_length (from, from_end,
1615 cmax, _C_flags, impl);
1619 case _RW::iso2022_jp:
1620 len = _RW::__rw_iso2022jp_do_length (state, from, from_end, cmax);
1622 case _RW::iso2022_jp2:
1623 len = _RW::__rw_iso2022jp2_do_length (state, from, from_end, cmax);
1625 case _RW::iso2022_kr:
1626 case _RW::iso2022_cn:
1636codecvt_byname<wchar_t, char, _RWSTD_MBSTATE_T>::
1637do_encoding ()
const _THROWS (())
1655 case _RW::stateless: {
1657 const _RW::__rw_codecvt_t* impl =
1663 const _RW::__rw_setlocale clocale (_C_name,
LC_CTYPE);
1665 if (mbtowc (0, 0, 0)) {
1685 enc = 1 < impl->mb_cur_max ? 0 : 1;
1692 case _RW::iso2022_jp:
1693 enc = _RW::__rw_iso2022jp_do_encoding ();
1695 case _RW::iso2022_jp2:
1696 enc = _RW::__rw_iso2022jp2_do_encoding ();
1698 case _RW::iso2022_kr:
1699 case _RW::iso2022_cn:
1709codecvt_byname<wchar_t, char, _RWSTD_MBSTATE_T>::
1710do_max_length ()
const _THROWS (())
1719 case _RW::stateless: {
1721 const _RW::__rw_codecvt_t* impl =
1726 const _RW::__rw_setlocale clocale (_C_name,
LC_CTYPE);
1735 max_len = size_t (impl->mb_cur_max);
1739 case _RW::iso2022_jp:
1740 max_len = _RW::__rw_iso2022jp_do_max_length ();
1742 case _RW::iso2022_jp2:
1743 max_len = _RW::__rw_iso2022jp2_do_max_length ();
1745 case _RW::iso2022_kr:
1746 case _RW::iso2022_cn:
1751 return int (max_len);
1759#ifndef _RWSTD_NO_WCHAR_T
1761# define TARGS_W <wchar_t, char, _RWSTD_MBSTATE_T>
#define _RWSTD_REINTERPRET_CAST(T, x)
#define _RWSTD_UNUSED(arg)
#define _RWSTD_STATIC_CAST(T, x)
#define _RWSTD_NAMESPACE(name)
#define _RWSTD_UWCHAR_INT_T
#define _RWSTD_ASSERT(ignore)
#define _RWSTD_SPECIALIZE_USE_FACET(fid)
#define _RWSTD_DEFINE_FACET_FACTORY(Linkage, Facet, TArgs, fid)
#define USE_LIBC(impl, x)