1 //===----------------------------------------------------------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 // <codecvt> 10 11 // template <class Elem, unsigned long Maxcode = 0x10ffff, 12 // codecvt_mode Mode = (codecvt_mode)0> 13 // class codecvt_utf16 14 // : public codecvt<Elem, char, mbstate_t> 15 // { 16 // // unspecified 17 // }; 18 19 // result 20 // out(stateT& state, 21 // const internT* from, const internT* from_end, const internT*& from_next, 22 // externT* to, externT* to_end, externT*& to_next) const; 23 24 #include <codecvt> 25 #include <cassert> 26 27 #include "test_macros.h" 28 29 template <class CharT, size_t = sizeof(CharT)> 30 struct TestHelper; 31 template <class CharT> 32 struct TestHelper<CharT, 2> { 33 static void test(); 34 }; 35 template <class CharT> 36 struct TestHelper<CharT, 4> { 37 static void test(); 38 }; 39 40 template <class CharT> 41 void TestHelper<CharT, 2>::test() { 42 // Nothing to do, the conversion in unsupported 43 } 44 45 template <class CharT> 46 void TestHelper<CharT, 4>::test() { 47 { 48 typedef std::codecvt_utf16<CharT> C; 49 C c; 50 CharT w = 0x40003; 51 char n[4] = {0}; 52 const CharT* wp = nullptr; 53 std::mbstate_t m; 54 char* np = nullptr; 55 std::codecvt_base::result r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 56 assert(r == std::codecvt_base::ok); 57 assert(wp == &w + 1); 58 assert(np == n + 4); 59 assert(n[0] == char(0xD8)); 60 assert(n[1] == char(0xC0)); 61 assert(n[2] == char(0xDC)); 62 assert(n[3] == char(0x03)); 63 64 w = 0x1005; 65 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 66 assert(r == std::codecvt_base::ok); 67 assert(wp == &w + 1); 68 assert(np == n + 2); 69 assert(n[0] == char(0x10)); 70 assert(n[1] == char(0x05)); 71 assert(n[2] == char(0xDC)); 72 assert(n[3] == char(0x03)); 73 74 w = 0x453; 75 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 76 assert(r == std::codecvt_base::ok); 77 assert(wp == &w + 1); 78 assert(np == n + 2); 79 assert(n[0] == char(0x04)); 80 assert(n[1] == char(0x53)); 81 assert(n[2] == char(0xDC)); 82 assert(n[3] == char(0x03)); 83 84 w = 0x56; 85 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 86 assert(r == std::codecvt_base::ok); 87 assert(wp == &w + 1); 88 assert(np == n + 2); 89 assert(n[0] == char(0x00)); 90 assert(n[1] == char(0x56)); 91 assert(n[2] == char(0xDC)); 92 assert(n[3] == char(0x03)); 93 } 94 { 95 typedef std::codecvt_utf16<CharT, 0x1000> C; 96 C c; 97 CharT w = 0x40003; 98 char n[4] = {0}; 99 const CharT* wp = nullptr; 100 std::mbstate_t m; 101 char* np = nullptr; 102 std::codecvt_base::result r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 103 assert(r == std::codecvt_base::error); 104 assert(wp == &w); 105 assert(np == n); 106 assert(n[0] == char(0)); 107 assert(n[1] == char(0)); 108 assert(n[2] == char(0)); 109 assert(n[3] == char(0)); 110 111 w = 0x1005; 112 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 113 assert(r == std::codecvt_base::error); 114 assert(wp == &w); 115 assert(np == n); 116 assert(n[0] == char(0)); 117 assert(n[1] == char(0)); 118 assert(n[2] == char(0)); 119 assert(n[3] == char(0)); 120 121 w = 0x453; 122 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 123 assert(r == std::codecvt_base::ok); 124 assert(wp == &w + 1); 125 assert(np == n + 2); 126 assert(n[0] == char(0x04)); 127 assert(n[1] == char(0x53)); 128 assert(n[2] == char(0)); 129 assert(n[3] == char(0)); 130 131 w = 0x56; 132 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 133 assert(r == std::codecvt_base::ok); 134 assert(wp == &w + 1); 135 assert(np == n + 2); 136 assert(n[0] == char(0x00)); 137 assert(n[1] == char(0x56)); 138 assert(n[2] == char(0)); 139 assert(n[3] == char(0)); 140 } 141 { 142 typedef std::codecvt_utf16<CharT, 0x10ffff, std::generate_header> C; 143 C c; 144 CharT w = 0x40003; 145 char n[6] = {0}; 146 const CharT* wp = nullptr; 147 std::mbstate_t m; 148 char* np = nullptr; 149 std::codecvt_base::result r = c.out(m, &w, &w + 1, wp, n, n + 6, np); 150 assert(r == std::codecvt_base::ok); 151 assert(wp == &w + 1); 152 assert(np == n + 6); 153 assert(n[0] == char(0xFE)); 154 assert(n[1] == char(0xFF)); 155 assert(n[2] == char(0xD8)); 156 assert(n[3] == char(0xC0)); 157 assert(n[4] == char(0xDC)); 158 assert(n[5] == char(0x03)); 159 160 w = 0x1005; 161 r = c.out(m, &w, &w + 1, wp, n, n + 6, np); 162 assert(r == std::codecvt_base::ok); 163 assert(wp == &w + 1); 164 assert(np == n + 4); 165 assert(n[0] == char(0xFE)); 166 assert(n[1] == char(0xFF)); 167 assert(n[2] == char(0x10)); 168 assert(n[3] == char(0x05)); 169 assert(n[4] == char(0xDC)); 170 assert(n[5] == char(0x03)); 171 172 w = 0x453; 173 r = c.out(m, &w, &w + 1, wp, n, n + 6, np); 174 assert(r == std::codecvt_base::ok); 175 assert(wp == &w + 1); 176 assert(np == n + 4); 177 assert(n[0] == char(0xFE)); 178 assert(n[1] == char(0xFF)); 179 assert(n[2] == char(0x04)); 180 assert(n[3] == char(0x53)); 181 assert(n[4] == char(0xDC)); 182 assert(n[5] == char(0x03)); 183 184 w = 0x56; 185 r = c.out(m, &w, &w + 1, wp, n, n + 6, np); 186 assert(r == std::codecvt_base::ok); 187 assert(wp == &w + 1); 188 assert(np == n + 4); 189 assert(n[0] == char(0xFE)); 190 assert(n[1] == char(0xFF)); 191 assert(n[2] == char(0x00)); 192 assert(n[3] == char(0x56)); 193 assert(n[4] == char(0xDC)); 194 assert(n[5] == char(0x03)); 195 } 196 197 { 198 typedef std::codecvt_utf16<CharT, 0x10FFFF, std::little_endian> C; 199 C c; 200 CharT w = 0x40003; 201 char n[4] = {0}; 202 const CharT* wp = nullptr; 203 std::mbstate_t m; 204 char* np = nullptr; 205 std::codecvt_base::result r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 206 assert(r == std::codecvt_base::ok); 207 assert(wp == &w + 1); 208 assert(np == n + 4); 209 assert(n[1] == char(0xD8)); 210 assert(n[0] == char(0xC0)); 211 assert(n[3] == char(0xDC)); 212 assert(n[2] == char(0x03)); 213 214 w = 0x1005; 215 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 216 assert(r == std::codecvt_base::ok); 217 assert(wp == &w + 1); 218 assert(np == n + 2); 219 assert(n[1] == char(0x10)); 220 assert(n[0] == char(0x05)); 221 assert(n[3] == char(0xDC)); 222 assert(n[2] == char(0x03)); 223 224 w = 0x453; 225 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 226 assert(r == std::codecvt_base::ok); 227 assert(wp == &w + 1); 228 assert(np == n + 2); 229 assert(n[1] == char(0x04)); 230 assert(n[0] == char(0x53)); 231 assert(n[3] == char(0xDC)); 232 assert(n[2] == char(0x03)); 233 234 w = 0x56; 235 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 236 assert(r == std::codecvt_base::ok); 237 assert(wp == &w + 1); 238 assert(np == n + 2); 239 assert(n[1] == char(0x00)); 240 assert(n[0] == char(0x56)); 241 assert(n[3] == char(0xDC)); 242 assert(n[2] == char(0x03)); 243 } 244 { 245 typedef std::codecvt_utf16<CharT, 0x1000, std::little_endian> C; 246 C c; 247 CharT w = 0x40003; 248 char n[4] = {0}; 249 const CharT* wp = nullptr; 250 std::mbstate_t m; 251 char* np = nullptr; 252 std::codecvt_base::result r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 253 assert(r == std::codecvt_base::error); 254 assert(wp == &w); 255 assert(np == n); 256 assert(n[1] == char(0)); 257 assert(n[0] == char(0)); 258 assert(n[3] == char(0)); 259 assert(n[2] == char(0)); 260 261 w = 0x1005; 262 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 263 assert(r == std::codecvt_base::error); 264 assert(wp == &w); 265 assert(np == n); 266 assert(n[1] == char(0)); 267 assert(n[0] == char(0)); 268 assert(n[3] == char(0)); 269 assert(n[2] == char(0)); 270 271 w = 0x453; 272 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 273 assert(r == std::codecvt_base::ok); 274 assert(wp == &w + 1); 275 assert(np == n + 2); 276 assert(n[1] == char(0x04)); 277 assert(n[0] == char(0x53)); 278 assert(n[3] == char(0)); 279 assert(n[2] == char(0)); 280 281 w = 0x56; 282 r = c.out(m, &w, &w + 1, wp, n, n + 4, np); 283 assert(r == std::codecvt_base::ok); 284 assert(wp == &w + 1); 285 assert(np == n + 2); 286 assert(n[1] == char(0x00)); 287 assert(n[0] == char(0x56)); 288 assert(n[3] == char(0)); 289 assert(n[2] == char(0)); 290 } 291 { 292 typedef std::codecvt_utf16<CharT, 0x10ffff, 293 std::codecvt_mode(std::generate_header | 294 std::little_endian)> 295 C; 296 C c; 297 CharT w = 0x40003; 298 char n[6] = {0}; 299 const CharT* wp = nullptr; 300 std::mbstate_t m; 301 char* np = nullptr; 302 std::codecvt_base::result r = c.out(m, &w, &w + 1, wp, n, n + 6, np); 303 assert(r == std::codecvt_base::ok); 304 assert(wp == &w + 1); 305 assert(np == n + 6); 306 assert(n[1] == char(0xFE)); 307 assert(n[0] == char(0xFF)); 308 assert(n[3] == char(0xD8)); 309 assert(n[2] == char(0xC0)); 310 assert(n[5] == char(0xDC)); 311 assert(n[4] == char(0x03)); 312 313 w = 0x1005; 314 r = c.out(m, &w, &w + 1, wp, n, n + 6, np); 315 assert(r == std::codecvt_base::ok); 316 assert(wp == &w + 1); 317 assert(np == n + 4); 318 assert(n[1] == char(0xFE)); 319 assert(n[0] == char(0xFF)); 320 assert(n[3] == char(0x10)); 321 assert(n[2] == char(0x05)); 322 assert(n[5] == char(0xDC)); 323 assert(n[4] == char(0x03)); 324 325 w = 0x453; 326 r = c.out(m, &w, &w + 1, wp, n, n + 6, np); 327 assert(r == std::codecvt_base::ok); 328 assert(wp == &w + 1); 329 assert(np == n + 4); 330 assert(n[1] == char(0xFE)); 331 assert(n[0] == char(0xFF)); 332 assert(n[3] == char(0x04)); 333 assert(n[2] == char(0x53)); 334 assert(n[5] == char(0xDC)); 335 assert(n[4] == char(0x03)); 336 337 w = 0x56; 338 r = c.out(m, &w, &w + 1, wp, n, n + 6, np); 339 assert(r == std::codecvt_base::ok); 340 assert(wp == &w + 1); 341 assert(np == n + 4); 342 assert(n[1] == char(0xFE)); 343 assert(n[0] == char(0xFF)); 344 assert(n[3] == char(0x00)); 345 assert(n[2] == char(0x56)); 346 assert(n[5] == char(0xDC)); 347 assert(n[4] == char(0x03)); 348 } 349 } 350 351 int main(int, char**) { 352 TestHelper<char32_t>::test(); 353 #ifndef TEST_HAS_NO_WIDE_CHARACTERS 354 TestHelper<wchar_t>::test(); 355 #endif 356 357 return 0; 358 } 359