1 // © 2016 and later: Unicode, Inc. and others.
2 // License & terms of use: http://www.unicode.org/copyright.html
3 /*
4 *******************************************************************************
5 *
6 * Copyright (C) 2003-2016, International Business Machines
7 * Corporation and others. All Rights Reserved.
8 *
9 *******************************************************************************
10 * file name: testidna.cpp
11 * encoding: UTF-8
12 * tab size: 8 (not used)
13 * indentation:4
14 *
15 * created on: 2003feb1
16 * created by: Ram Viswanadha
17 */
18
19 #include "unicode/utypes.h"
20
21 #if !UCONFIG_NO_IDNA && !UCONFIG_NO_TRANSLITERATION
22
23 #include <time.h>
24 #include <limits.h>
25 #include <stdlib.h>
26 #include <string.h>
27 #include "unicode/localpointer.h"
28 #include "unicode/ustring.h"
29 #include "unicode/usprep.h"
30 #include "unicode/uniset.h"
31 #include "unicode/utf16.h"
32 #include "cmemory.h"
33 #include "testidna.h"
34 #include "idnaref.h"
35 #include "nptrans.h"
36 #include "unicode/putil.h"
37 #include "idnaconf.h"
38
39 static const UChar unicodeIn[][41] ={
40 {
41 0x0644, 0x064A, 0x0647, 0x0645, 0x0627, 0x0628, 0x062A, 0x0643, 0x0644,
42 0x0645, 0x0648, 0x0634, 0x0639, 0x0631, 0x0628, 0x064A, 0x061F, 0x0000
43 },
44 {
45 0x4ED6, 0x4EEC, 0x4E3A, 0x4EC0, 0x4E48, 0x4E0D, 0x8BF4, 0x4E2D, 0x6587,
46 0x0000
47 },
48 {
49 0x0050, 0x0072, 0x006F, 0x010D, 0x0070, 0x0072, 0x006F, 0x0073, 0x0074,
50 0x011B, 0x006E, 0x0065, 0x006D, 0x006C, 0x0075, 0x0076, 0x00ED, 0x010D,
51 0x0065, 0x0073, 0x006B, 0x0079, 0x0000
52 },
53 {
54 0x05DC, 0x05DE, 0x05D4, 0x05D4, 0x05DD, 0x05E4, 0x05E9, 0x05D5, 0x05D8,
55 0x05DC, 0x05D0, 0x05DE, 0x05D3, 0x05D1, 0x05E8, 0x05D9, 0x05DD, 0x05E2,
56 0x05D1, 0x05E8, 0x05D9, 0x05EA, 0x0000
57 },
58 {
59 0x092F, 0x0939, 0x0932, 0x094B, 0x0917, 0x0939, 0x093F, 0x0928, 0x094D,
60 0x0926, 0x0940, 0x0915, 0x094D, 0x092F, 0x094B, 0x0902, 0x0928, 0x0939,
61 0x0940, 0x0902, 0x092C, 0x094B, 0x0932, 0x0938, 0x0915, 0x0924, 0x0947,
62 0x0939, 0x0948, 0x0902, 0x0000
63 },
64 {
65 0x306A, 0x305C, 0x307F, 0x3093, 0x306A, 0x65E5, 0x672C, 0x8A9E, 0x3092,
66 0x8A71, 0x3057, 0x3066, 0x304F, 0x308C, 0x306A, 0x3044, 0x306E, 0x304B,
67 0x0000
68 },
69 /*
70 {
71 0xC138, 0xACC4, 0xC758, 0xBAA8, 0xB4E0, 0xC0AC, 0xB78C, 0xB4E4, 0xC774,
72 0xD55C, 0xAD6D, 0xC5B4, 0xB97C, 0xC774, 0xD574, 0xD55C, 0xB2E4, 0xBA74,
73 0xC5BC, 0xB9C8, 0xB098, 0xC88B, 0xC744, 0xAE4C, 0x0000
74 },
75 */
76 {
77 0x043F, 0x043E, 0x0447, 0x0435, 0x043C, 0x0443, 0x0436, 0x0435, 0x043E,
78 0x043D, 0x0438, 0x043D, 0x0435, 0x0433, 0x043E, 0x0432, 0x043E, 0x0440,
79 0x044F, 0x0442, 0x043F, 0x043E, 0x0440, 0x0443, 0x0441, 0x0441, 0x043A,
80 0x0438, 0x0000
81 },
82 {
83 0x0050, 0x006F, 0x0072, 0x0071, 0x0075, 0x00E9, 0x006E, 0x006F, 0x0070,
84 0x0075, 0x0065, 0x0064, 0x0065, 0x006E, 0x0073, 0x0069, 0x006D, 0x0070,
85 0x006C, 0x0065, 0x006D, 0x0065, 0x006E, 0x0074, 0x0065, 0x0068, 0x0061,
86 0x0062, 0x006C, 0x0061, 0x0072, 0x0065, 0x006E, 0x0045, 0x0073, 0x0070,
87 0x0061, 0x00F1, 0x006F, 0x006C, 0x0000
88 },
89 {
90 0x4ED6, 0x5011, 0x7232, 0x4EC0, 0x9EBD, 0x4E0D, 0x8AAA, 0x4E2D, 0x6587,
91 0x0000
92 },
93 {
94 0x0054, 0x1EA1, 0x0069, 0x0073, 0x0061, 0x006F, 0x0068, 0x1ECD, 0x006B,
95 0x0068, 0x00F4, 0x006E, 0x0067, 0x0074, 0x0068, 0x1EC3, 0x0063, 0x0068,
96 0x1EC9, 0x006E, 0x00F3, 0x0069, 0x0074, 0x0069, 0x1EBF, 0x006E, 0x0067,
97 0x0056, 0x0069, 0x1EC7, 0x0074, 0x0000
98 },
99 {
100 0x0033, 0x5E74, 0x0042, 0x7D44, 0x91D1, 0x516B, 0x5148, 0x751F, 0x0000
101 },
102 {
103 0x5B89, 0x5BA4, 0x5948, 0x7F8E, 0x6075, 0x002D, 0x0077, 0x0069, 0x0074,
104 0x0068, 0x002D, 0x0053, 0x0055, 0x0050, 0x0045, 0x0052, 0x002D, 0x004D,
105 0x004F, 0x004E, 0x004B, 0x0045, 0x0059, 0x0053, 0x0000
106 },
107 {
108 0x0048, 0x0065, 0x006C, 0x006C, 0x006F, 0x002D, 0x0041, 0x006E, 0x006F,
109 0x0074, 0x0068, 0x0065, 0x0072, 0x002D, 0x0057, 0x0061, 0x0079, 0x002D,
110 0x305D, 0x308C, 0x305E, 0x308C, 0x306E, 0x5834, 0x6240, 0x0000
111 },
112 {
113 0x3072, 0x3068, 0x3064, 0x5C4B, 0x6839, 0x306E, 0x4E0B, 0x0032, 0x0000
114 },
115 {
116 0x004D, 0x0061, 0x006A, 0x0069, 0x3067, 0x004B, 0x006F, 0x0069, 0x3059,
117 0x308B, 0x0035, 0x79D2, 0x524D, 0x0000
118 },
119 {
120 0x30D1, 0x30D5, 0x30A3, 0x30FC, 0x0064, 0x0065, 0x30EB, 0x30F3, 0x30D0,
121 0x0000
122 },
123 {
124 0x305D, 0x306E, 0x30B9, 0x30D4, 0x30FC, 0x30C9, 0x3067, 0x0000
125 },
126 // test non-BMP code points
127 {
128 0xD800, 0xDF00, 0xD800, 0xDF01, 0xD800, 0xDF02, 0xD800, 0xDF03, 0xD800, 0xDF05,
129 0xD800, 0xDF06, 0xD800, 0xDF07, 0xD800, 0xDF09, 0xD800, 0xDF0A, 0xD800, 0xDF0B,
130 0x0000
131 },
132 {
133 0xD800, 0xDF0D, 0xD800, 0xDF0C, 0xD800, 0xDF1E, 0xD800, 0xDF0F, 0xD800, 0xDF16,
134 0xD800, 0xDF15, 0xD800, 0xDF14, 0xD800, 0xDF12, 0xD800, 0xDF10, 0xD800, 0xDF20,
135 0xD800, 0xDF21,
136 0x0000
137 },
138 // Greek
139 {
140 0x03b5, 0x03bb, 0x03bb, 0x03b7, 0x03bd, 0x03b9, 0x03ba, 0x03ac
141 },
142 // Maltese
143 {
144 0x0062, 0x006f, 0x006e, 0x0121, 0x0075, 0x0073, 0x0061, 0x0127,
145 0x0127, 0x0061
146 },
147 // Russian
148 {
149 0x043f, 0x043e, 0x0447, 0x0435, 0x043c, 0x0443, 0x0436, 0x0435,
150 0x043e, 0x043d, 0x0438, 0x043d, 0x0435, 0x0433, 0x043e, 0x0432,
151 0x043e, 0x0440, 0x044f, 0x0442, 0x043f, 0x043e, 0x0440, 0x0443,
152 0x0441, 0x0441, 0x043a, 0x0438
153 },
154 {
155 0xFB00, 0xFB01
156 }
157
158 };
159
160 static const char *asciiIn[] = {
161 "xn--egbpdaj6bu4bxfgehfvwxn",
162 "xn--ihqwcrb4cv8a8dqg056pqjye",
163 "xn--Proprostnemluvesky-uyb24dma41a",
164 "xn--4dbcagdahymbxekheh6e0a7fei0b",
165 "xn--i1baa7eci9glrd9b2ae1bj0hfcgg6iyaf8o0a1dig0cd",
166 "xn--n8jok5ay5dzabd5bym9f0cm5685rrjetr6pdxa",
167 /* "xn--989aomsvi5e83db1d2a355cv1e0vak1dwrv93d5xbh15a0dt30a5jpsd879ccm6fea98c",*/
168 "xn--b1abfaaepdrnnbgefbaDotcwatmq2g4l",
169 "xn--PorqunopuedensimplementehablarenEspaol-fmd56a",
170 "xn--ihqwctvzc91f659drss3x8bo0yb",
171 "xn--TisaohkhngthchnitingVit-kjcr8268qyxafd2f1b9g",
172 "xn--3B-ww4c5e180e575a65lsy2b",
173 "xn---with-SUPER-MONKEYS-pc58ag80a8qai00g7n9n",
174 "xn--Hello-Another-Way--fc4qua05auwb3674vfr0b",
175 "xn--2-u9tlzr9756bt3uc0v",
176 "xn--MajiKoi5-783gue6qz075azm5e",
177 "xn--de-jg4avhby1noc0d",
178 "xn--d9juau41awczczp",
179 "XN--097CCDEKGHQJK",
180 "XN--db8CBHEJLGH4E0AL",
181 "xn--hxargifdar", // Greek
182 "xn--bonusaa-5bb1da", // Maltese
183 "xn--b1abfaaepdrnnbgefbadotcwatmq2g4l", // Russian (Cyrillic)
184 "fffi"
185 };
186
187 static const char *domainNames[] = {
188 "slip129-37-118-146.nc.us.ibm.net",
189 "saratoga.pe.utexas.edu",
190 "dial-120-45.ots.utexas.edu",
191 "woo-085.dorms.waller.net",
192 "hd30-049.hil.compuserve.com",
193 "pem203-31.pe.ttu.edu",
194 "56K-227.MaxTNT3.pdq.net",
195 "dial-36-2.ots.utexas.edu",
196 "slip129-37-23-152.ga.us.ibm.net",
197 "ts45ip119.cadvision.com",
198 "sdn-ts-004txaustP05.dialsprint.net",
199 "bar-tnt1s66.erols.com",
200 "101.st-louis-15.mo.dial-access.att.net",
201 "h92-245.Arco.COM",
202 "dial-13-2.ots.utexas.edu",
203 "net-redynet29.datamarkets.com.ar",
204 "ccs-shiva28.reacciun.net.ve",
205 "7.houston-11.tx.dial-access.att.net",
206 "ingw129-37-120-26.mo.us.ibm.net",
207 "dialup6.austintx.com",
208 "dns2.tpao.gov.tr",
209 "slip129-37-119-194.nc.us.ibm.net",
210 "cs7.dillons.co.uk.203.119.193.in-addr.arpa",
211 "swprd1.innovplace.saskatoon.sk.ca",
212 "bikini.bologna.maraut.it",
213 "node91.subnet159-198-79.baxter.com",
214 "cust19.max5.new-york.ny.ms.uu.net",
215 "balexander.slip.andrew.cmu.edu",
216 "pool029.max2.denver.co.dynip.alter.net",
217 "cust49.max9.new-york.ny.ms.uu.net",
218 "s61.abq-dialin2.hollyberry.com",
219 "\\u0917\\u0928\\u0947\\u0936.sanjose.ibm.com", //':'(0x003a) produces U_IDNA_STD3_ASCII_RULES_ERROR
220 "www.xn--vea.com",
221 // "www.\\u00E0\\u00B3\\u00AF.com",//' ' (0x0020) produces U_IDNA_STD3_ASCII_RULES_ERROR
222 "www.\\u00C2\\u00A4.com",
223 "www.\\u00C2\\u00A3.com",
224 // "\\u0025", //'%' (0x0025) produces U_IDNA_STD3_ASCII_RULES_ERROR
225 // "\\u005C\\u005C", //'\' (0x005C) produces U_IDNA_STD3_ASCII_RULES_ERROR
226 //"@",
227 //"\\u002F",
228 //"www.\\u0021.com",
229 //"www.\\u0024.com",
230 //"\\u003f",
231 // These yield U_IDNA_PROHIBITED_ERROR
232 //"\\u00CF\\u0082.com",
233 //"\\u00CE\\u00B2\\u00C3\\u009Fss.com",
234 //"\\u00E2\\u0098\\u00BA.com",
235 "\\u00C3\\u00BC.com",
236
237 };
238
239 typedef struct ErrorCases ErrorCases;
240
241 static const struct ErrorCases{
242
243 UChar unicode[100];
244 const char *ascii;
245 UErrorCode expected;
246 UBool useSTD3ASCIIRules;
247 UBool testToUnicode;
248 UBool testLabel;
249 } errorCases[] = {
250 {
251
252 {
253 0x0077, 0x0077, 0x0077, 0x002e, /* www. */
254 0xC138, 0xACC4, 0xC758, 0xBAA8, 0xB4E0, 0xC0AC, 0xB78C, 0xB4E4, 0xC774,
255 0x070F,/*prohibited*/
256 0xD55C, 0xAD6D, 0xC5B4, 0xB97C, 0xC774, 0xD574, 0xD55C, 0xB2E4, 0xBA74,
257 0x002e, 0x0063, 0x006f, 0x006d, /* com. */
258 0x0000
259 },
260 "www.XN--8mb5595fsoa28orucya378bqre2tcwop06c5qbw82a1rffmae0361dea96b.com",
261 U_IDNA_PROHIBITED_ERROR,
262 false, false, true
263 },
264
265 {
266 {
267 0x0077, 0x0077, 0x0077, 0x002e, /* www. */
268 0xC138, 0xACC4, 0xC758, 0xBAA8, 0xB4E0, 0xC0AC, 0xB78C, 0xB4E4, 0xC774,
269 0x0221, 0x0234/*Unassigned code points*/,
270 0x002e, 0x0063, 0x006f, 0x006d, /* com. */
271 0x0000
272 },
273 "www.XN--6lA2Bz548Fj1GuA391Bf1Gb1N59Ab29A7iA.com",
274
275 U_IDNA_UNASSIGNED_ERROR,
276 false, false, true
277 },
278 {
279 {
280 0x0077, 0x0077, 0x0077, 0x002e, /* www. */
281 0xC138, 0xACC4, 0xC758, 0xBAA8, 0xB4E0, 0xC0AC, 0xB78C, 0xB4E4, 0xC774,
282 0x0644, 0x064A, 0x0647,/*Arabic code points. Cannot mix RTL with LTR*/
283 0xD55C, 0xAD6D, 0xC5B4, 0xB97C, 0xC774, 0xD574, 0xD55C, 0xB2E4, 0xBA74,
284 0x002e, 0x0063, 0x006f, 0x006d, /* com. */
285 0x0000
286 },
287 "www.xn--ghBGI4851OiyA33VqrD6Az86C4qF83CtRv93D5xBk15AzfG0nAgA0578DeA71C.com",
288 U_IDNA_CHECK_BIDI_ERROR,
289 false, false, true
290 },
291 {
292 {
293 0x0077, 0x0077, 0x0077, 0x002e, /* www. */
294 /* labels cannot begin with an HYPHEN */
295 0x002D, 0xACC4, 0xC758, 0xBAA8, 0xB4E0, 0xC0AC, 0xB78C, 0xB4E4, 0xC774,
296 0x002E,
297 0xD55C, 0xAD6D, 0xC5B4, 0xB97C, 0xC774, 0xD574, 0xD55C, 0xB2E4, 0xBA74,
298 0x002e, 0x0063, 0x006f, 0x006d, /* com. */
299 0x0000
300
301 },
302 "www.xn----b95Ew8SqA315Ao5FbuMlnNmhA.com",
303 U_IDNA_STD3_ASCII_RULES_ERROR,
304 true, false, false
305 },
306 {
307 {
308 /* correct ACE-prefix followed by unicode */
309 0x0077, 0x0077, 0x0077, 0x002e, /* www. */
310 0x0078, 0x006e, 0x002d,0x002d, /* ACE Prefix */
311 0x002D, 0xACC4, 0xC758, 0xBAA8, 0xB4E0, 0xC0AC, 0xB78C, 0xB4E4, 0xC774,
312 0x002D,
313 0xD55C, 0xAD6D, 0xC5B4, 0xB97C, 0xC774, 0xD574, 0xD55C, 0xB2E4, 0xBA74,
314 0x002e, 0x0063, 0x006f, 0x006d, /* com. */
315 0x0000
316
317 },
318 /* wrong ACE-prefix followed by valid ACE-encoded ASCII */
319 "www.XY-----b91I0V65S96C2A355Cw1E5yCeQr19CsnP1mFfmAE0361DeA96B.com",
320 U_IDNA_ACE_PREFIX_ERROR,
321 false, false, false
322 },
323 /* cannot verify U_IDNA_VERIFICATION_ERROR */
324
325 {
326 {
327 0x0077, 0x0077, 0x0077, 0x002e, /* www. */
328 0xC138, 0xACC4, 0xC758, 0xBAA8, 0xB4E0, 0xC0AC, 0xB78C, 0xB4E4, 0xC774,
329 0xD55C, 0xAD6D, 0xC5B4, 0xB97C, 0xC774, 0xD574, 0xD55C, 0xB2E4, 0xBA74,
330 0xC5BC, 0xB9C8, 0xB098, 0xC88B, 0xC744, 0xAE4C,
331 0x002e, 0x0063, 0x006f, 0x006d, /* com. */
332 0x0000
333 },
334 "www.xn--989AoMsVi5E83Db1D2A355Cv1E0vAk1DwRv93D5xBh15A0Dt30A5JpSD879Ccm6FeA98C.com",
335 U_IDNA_LABEL_TOO_LONG_ERROR,
336 false, false, true
337 },
338
339 {
340 {
341 0x0077, 0x0077, 0x0077, 0x002e, /* www. */
342 0x0030, 0x0644, 0x064A, 0x0647, 0x0031, /* Arabic code points squashed between EN codepoints */
343 0x002e, 0x0063, 0x006f, 0x006d, /* com. */
344 0x0000
345 },
346 "www.xn--01-tvdmo.com",
347 U_IDNA_CHECK_BIDI_ERROR,
348 false, false, true
349 },
350
351 {
352 {
353 0x0077, 0x0077, 0x0077, 0x002e, // www.
354 0x206C, 0x0644, 0x064A, 0x0647, 0x206D, // Arabic code points squashed between BN codepoints
355 0x002e, 0x0063, 0x006f, 0x006d, // com.
356 0x0000
357 },
358 "www.XN--ghbgi278xia.com",
359 U_IDNA_PROHIBITED_ERROR,
360 false, false, true
361 },
362 {
363 {
364 0x0077, 0x0077, 0x0077, 0x002e, // www.
365 0x002D, 0x0041, 0x0042, 0x0043, 0x0044, 0x0045, // HYPHEN at the start of label
366 0x002e, 0x0063, 0x006f, 0x006d, // com.
367 0x0000
368 },
369 "www.-abcde.com",
370 U_IDNA_STD3_ASCII_RULES_ERROR,
371 true, false, false
372 },
373 {
374 {
375 0x0077, 0x0077, 0x0077, 0x002e, // www.
376 0x0041, 0x0042, 0x0043, 0x0044, 0x0045,0x002D, // HYPHEN at the end of the label
377 0x002e, 0x0063, 0x006f, 0x006d, // com.
378 0x0000
379 },
380 "www.abcde-.com",
381 U_IDNA_STD3_ASCII_RULES_ERROR,
382 true, false, false
383 },
384 {
385 {
386 0x0077, 0x0077, 0x0077, 0x002e, // www.
387 0x0041, 0x0042, 0x0043, 0x0044, 0x0045,0x0040, // Containing non LDH code point
388 0x002e, 0x0063, 0x006f, 0x006d, // com.
389 0x0000
390 },
391 "www.abcde@.com",
392 U_IDNA_STD3_ASCII_RULES_ERROR,
393 true, false, false
394 },
395 {
396 {
397 0x0077, 0x0077, 0x0077, 0x002e, // www.
398 // zero length label
399 0x002e, 0x0063, 0x006f, 0x006d, // com.
400 0x0000
401 },
402 "www..com",
403 U_IDNA_ZERO_LENGTH_LABEL_ERROR,
404 true, false, false
405 },
406 {
407 {0},
408 NULL,
409 U_ILLEGAL_ARGUMENT_ERROR,
410 true, true, false
411 }
412 };
413
414
415
416
417 #define MAX_DEST_SIZE 300
418
debug(const UChar * src,int32_t srcLength,int32_t options)419 void TestIDNA::debug(const UChar* src, int32_t srcLength, int32_t options){
420 UParseError parseError;
421 UErrorCode transStatus = U_ZERO_ERROR;
422 UErrorCode prepStatus = U_ZERO_ERROR;
423 NamePrepTransform* trans = NamePrepTransform::createInstance(parseError,transStatus);
424 int32_t prepOptions = (((options & UIDNA_ALLOW_UNASSIGNED) != 0) ? USPREP_ALLOW_UNASSIGNED: 0);
425 LocalUStringPrepProfilePointer prep(usprep_openByType(USPREP_RFC3491_NAMEPREP,&prepStatus));
426 UChar *transOut=NULL, *prepOut=NULL;
427 int32_t transOutLength=0, prepOutLength=0;
428
429
430 transOutLength = trans->process(src,srcLength,transOut, 0, prepOptions>0, &parseError, transStatus);
431 if( transStatus == U_BUFFER_OVERFLOW_ERROR){
432 transStatus = U_ZERO_ERROR;
433 transOut = (UChar*) malloc(U_SIZEOF_UCHAR * transOutLength);
434 transOutLength = trans->process(src,srcLength,transOut, transOutLength, prepOptions>0, &parseError, transStatus);
435 }
436
437 prepOutLength = usprep_prepare(prep.getAlias(), src, srcLength, prepOut, 0, prepOptions, &parseError, &prepStatus);
438
439 if( prepStatus == U_BUFFER_OVERFLOW_ERROR){
440 prepStatus = U_ZERO_ERROR;
441 prepOut = (UChar*) malloc(U_SIZEOF_UCHAR * prepOutLength);
442 prepOutLength = usprep_prepare(prep.getAlias(), src, srcLength, prepOut, prepOutLength, prepOptions, &parseError, &prepStatus);
443 }
444
445 if(UnicodeString(transOut,transOutLength)!= UnicodeString(prepOut, prepOutLength)){
446 errln("Failed. Expected: " + prettify(UnicodeString(transOut, transOutLength))
447 + " Got: " + prettify(UnicodeString(prepOut,prepOutLength)));
448 }
449 free(transOut);
450 free(prepOut);
451 delete trans;
452 }
453
testAPI(const UChar * src,const UChar * expected,const char * testName,UBool useSTD3ASCIIRules,UErrorCode expectedStatus,UBool doCompare,UBool testUnassigned,TestFunc func,UBool testSTD3ASCIIRules)454 void TestIDNA::testAPI(const UChar* src, const UChar* expected, const char* testName,
455 UBool useSTD3ASCIIRules,UErrorCode expectedStatus,
456 UBool doCompare, UBool testUnassigned, TestFunc func, UBool testSTD3ASCIIRules){
457
458 UErrorCode status = U_ZERO_ERROR;
459 UChar destStack[MAX_DEST_SIZE];
460 int32_t destLen = 0;
461 UChar* dest = NULL;
462 int32_t expectedLen = (expected != NULL) ? u_strlen(expected) : 0;
463 int32_t options = (useSTD3ASCIIRules == true) ? UIDNA_USE_STD3_RULES : UIDNA_DEFAULT;
464 UParseError parseError;
465 int32_t tSrcLen = 0;
466 UChar* tSrc = NULL;
467
468 if(src != NULL){
469 tSrcLen = u_strlen(src);
470 tSrc =(UChar*) malloc( U_SIZEOF_UCHAR * tSrcLen );
471 memcpy(tSrc,src,tSrcLen * U_SIZEOF_UCHAR);
472 }
473
474 // test null-terminated source and return value of number of UChars required
475 destLen = func(src,-1,NULL,0,options, &parseError , &status);
476 if (status == U_FILE_ACCESS_ERROR) {
477 dataerrln("U_FILE_ACCESS_ERROR. Skipping the remainder of this test.");
478 return;
479 }
480 if(status == U_BUFFER_OVERFLOW_ERROR){
481 status = U_ZERO_ERROR; // reset error code
482 if(destLen+1 < MAX_DEST_SIZE){
483 dest = destStack;
484 destLen = func(src,-1,dest,destLen+1,options, &parseError, &status);
485 // TODO : compare output with expected
486 if(U_SUCCESS(status) && expectedStatus != U_IDNA_STD3_ASCII_RULES_ERROR&& (doCompare==true) && u_strCaseCompare(dest,destLen, expected,expectedLen,0,&status)!=0){
487 errln("Did not get the expected result for "+UnicodeString(testName) +" null terminated source. Expected : "
488 + prettify(UnicodeString(expected,expectedLen))
489 + " Got: " + prettify(UnicodeString(dest,destLen))
490 );
491 }
492 }else{
493 errln( "%s null terminated source failed. Requires destCapacity > 300\n",testName);
494 }
495 }
496
497 if(status != expectedStatus){
498 errcheckln(status, "Did not get the expected error for "+
499 UnicodeString(testName)+
500 " null terminated source. Expected: " +UnicodeString(u_errorName(expectedStatus))
501 + " Got: "+ UnicodeString(u_errorName(status))
502 + " Source: " + prettify(UnicodeString(src))
503 );
504 free(tSrc);
505 return;
506 }
507 if(testUnassigned ){
508 status = U_ZERO_ERROR;
509 destLen = func(src,-1,NULL,0,options | UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
510 if(status == U_BUFFER_OVERFLOW_ERROR){
511 status = U_ZERO_ERROR; // reset error code
512 if(destLen+1 < MAX_DEST_SIZE){
513 dest = destStack;
514 destLen = func(src,-1,dest,destLen+1,options | UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
515 // TODO : compare output with expected
516 if(U_SUCCESS(status) && (doCompare==true) && u_strCaseCompare(dest,destLen, expected,expectedLen,0,&status)!=0){
517 //errln("Did not get the expected result for %s null terminated source with both options set.\n",testName);
518 errln("Did not get the expected result for "+UnicodeString(testName) +
519 " null terminated source "+ prettify(src) +
520 " with both options set. Expected: "+ prettify(UnicodeString(expected,expectedLen))+
521 "Got: " + prettify(UnicodeString(dest,destLen)));
522
523 debug(src,-1,options | UIDNA_ALLOW_UNASSIGNED);
524
525 }
526 }else{
527 errln( "%s null terminated source failed. Requires destCapacity > 300\n",testName);
528 }
529 }
530 //testing query string
531 if(status != expectedStatus && expectedStatus != U_IDNA_UNASSIGNED_ERROR){
532 errln( "Did not get the expected error for "+
533 UnicodeString(testName)+
534 " null terminated source with options set. Expected: " +UnicodeString(u_errorName(expectedStatus))
535 + " Got: "+ UnicodeString(u_errorName(status))
536 + " Source: " + prettify(UnicodeString(src))
537 );
538 }
539 }
540
541 status = U_ZERO_ERROR;
542
543 // test source with lengthand return value of number of UChars required
544 destLen = func(tSrc, tSrcLen, NULL,0,options, &parseError, &status);
545 if(status == U_BUFFER_OVERFLOW_ERROR){
546 status = U_ZERO_ERROR; // reset error code
547 if(destLen+1 < MAX_DEST_SIZE){
548 dest = destStack;
549 destLen = func(src,u_strlen(src),dest,destLen+1,options, &parseError, &status);
550 // TODO : compare output with expected
551 if(U_SUCCESS(status) && (doCompare==true) && u_strCaseCompare(dest,destLen, expected,expectedLen,0,&status)!=0){
552 errln("Did not get the expected result for %s with source length.\n",testName);
553 }
554 }else{
555 errln( "%s with source length failed. Requires destCapacity > 300\n",testName);
556 }
557 }
558
559 if(status != expectedStatus){
560 errln( "Did not get the expected error for "+
561 UnicodeString(testName)+
562 " with source length. Expected: " +UnicodeString(u_errorName(expectedStatus))
563 + " Got: "+ UnicodeString(u_errorName(status))
564 + " Source: " + prettify(UnicodeString(src))
565 );
566 }
567 if(testUnassigned){
568 status = U_ZERO_ERROR;
569
570 destLen = func(tSrc,tSrcLen,NULL,0,options | UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
571
572 if(status == U_BUFFER_OVERFLOW_ERROR){
573 status = U_ZERO_ERROR; // reset error code
574 if(destLen+1 < MAX_DEST_SIZE){
575 dest = destStack;
576 destLen = func(src,u_strlen(src),dest,destLen+1,options | UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
577 // TODO : compare output with expected
578 if(U_SUCCESS(status) && (doCompare==true) && u_strCaseCompare(dest,destLen, expected,expectedLen,0,&status)!=0){
579 errln("Did not get the expected result for %s with source length and both options set.\n",testName);
580 }
581 }else{
582 errln( "%s with source length failed. Requires destCapacity > 300\n",testName);
583 }
584 }
585 //testing query string
586 if(status != expectedStatus && expectedStatus != U_IDNA_UNASSIGNED_ERROR){
587 errln( "Did not get the expected error for "+
588 UnicodeString(testName)+
589 " with source length and options set. Expected: " +UnicodeString(u_errorName(expectedStatus))
590 + " Got: "+ UnicodeString(u_errorName(status))
591 + " Source: " + prettify(UnicodeString(src))
592 );
593 }
594 }
595
596 status = U_ZERO_ERROR;
597 if(testSTD3ASCIIRules==true){
598 destLen = func(src,-1,NULL,0,options | UIDNA_USE_STD3_RULES, &parseError, &status);
599 if(status == U_BUFFER_OVERFLOW_ERROR){
600 status = U_ZERO_ERROR; // reset error code
601 if(destLen+1 < MAX_DEST_SIZE){
602 dest = destStack;
603 destLen = func(src,-1,dest,destLen+1,options | UIDNA_USE_STD3_RULES, &parseError, &status);
604 // TODO : compare output with expected
605 if(U_SUCCESS(status) && (doCompare==true) && u_strCaseCompare(dest,destLen, expected,expectedLen,0,&status)!=0){
606 //errln("Did not get the expected result for %s null terminated source with both options set.\n",testName);
607 errln("Did not get the expected result for "+UnicodeString(testName) +" null terminated source with both options set. Expected: "+ prettify(UnicodeString(expected,expectedLen)));
608
609 }
610 }else{
611 errln( "%s null terminated source failed. Requires destCapacity > 300\n",testName);
612 }
613 }
614 //testing query string
615 if(status != expectedStatus){
616 errln( "Did not get the expected error for "+
617 UnicodeString(testName)+
618 " null terminated source with options set. Expected: " +UnicodeString(u_errorName(expectedStatus))
619 + " Got: "+ UnicodeString(u_errorName(status))
620 + " Source: " + prettify(UnicodeString(src))
621 );
622 }
623
624 status = U_ZERO_ERROR;
625
626 destLen = func(tSrc,tSrcLen,NULL,0,options | UIDNA_USE_STD3_RULES, &parseError, &status);
627
628 if(status == U_BUFFER_OVERFLOW_ERROR){
629 status = U_ZERO_ERROR; // reset error code
630 if(destLen+1 < MAX_DEST_SIZE){
631 dest = destStack;
632 destLen = func(src,u_strlen(src),dest,destLen+1,options | UIDNA_USE_STD3_RULES, &parseError, &status);
633 // TODO : compare output with expected
634 if(U_SUCCESS(status) && (doCompare==true) && u_strCaseCompare(dest,destLen, expected,expectedLen,0,&status)!=0){
635 errln("Did not get the expected result for %s with source length and both options set.\n",testName);
636 }
637 }else{
638 errln( "%s with source length failed. Requires destCapacity > 300\n",testName);
639 }
640 }
641 //testing query string
642 if(status != expectedStatus && expectedStatus != U_IDNA_UNASSIGNED_ERROR){
643 errln( "Did not get the expected error for "+
644 UnicodeString(testName)+
645 " with source length and options set. Expected: " +UnicodeString(u_errorName(expectedStatus))
646 + " Got: "+ UnicodeString(u_errorName(status))
647 + " Source: " + prettify(UnicodeString(src))
648 );
649 }
650 }
651 free(tSrc);
652 }
653
testCompare(const UChar * s1,int32_t s1Len,const UChar * s2,int32_t s2Len,const char * testName,CompareFunc func,UBool isEqual)654 void TestIDNA::testCompare(const UChar* s1, int32_t s1Len,
655 const UChar* s2, int32_t s2Len,
656 const char* testName, CompareFunc func,
657 UBool isEqual){
658
659 UErrorCode status = U_ZERO_ERROR;
660 int32_t retVal = func(s1,-1,s2,-1,UIDNA_DEFAULT,&status);
661
662 if(isEqual==true && retVal !=0){
663 errln("Did not get the expected result for %s with null termniated strings.\n",testName);
664 }
665 if(U_FAILURE(status)){
666 errcheckln(status, "%s null terminated source failed. Error: %s", testName,u_errorName(status));
667 }
668
669 status = U_ZERO_ERROR;
670 retVal = func(s1,-1,s2,-1,UIDNA_ALLOW_UNASSIGNED,&status);
671
672 if(isEqual==true && retVal !=0){
673 errln("Did not get the expected result for %s with null termniated strings with options set.\n", testName);
674 }
675 if(U_FAILURE(status)){
676 errcheckln(status, "%s null terminated source and options set failed. Error: %s",testName, u_errorName(status));
677 }
678
679 status = U_ZERO_ERROR;
680 retVal = func(s1,s1Len,s2,s2Len,UIDNA_DEFAULT,&status);
681
682 if(isEqual==true && retVal !=0){
683 errln("Did not get the expected result for %s with string length.\n",testName);
684 }
685 if(U_FAILURE(status)){
686 errcheckln(status, "%s with string length. Error: %s",testName, u_errorName(status));
687 }
688
689 status = U_ZERO_ERROR;
690 retVal = func(s1,s1Len,s2,s2Len,UIDNA_ALLOW_UNASSIGNED,&status);
691
692 if(isEqual==true && retVal !=0){
693 errln("Did not get the expected result for %s with string length and options set.\n",testName);
694 }
695 if(U_FAILURE(status)){
696 errcheckln(status, "%s with string length and options set. Error: %s", u_errorName(status), testName);
697 }
698 }
699
testToASCII(const char * testName,TestFunc func)700 void TestIDNA::testToASCII(const char* testName, TestFunc func){
701
702 int32_t i;
703 UChar buf[MAX_DEST_SIZE];
704
705 for(i=0;i< UPRV_LENGTHOF(unicodeIn); i++){
706 u_charsToUChars(asciiIn[i],buf, (int32_t)(strlen(asciiIn[i])+1));
707 testAPI(unicodeIn[i], buf,testName, false,U_ZERO_ERROR, true, true, func);
708
709 }
710 }
711
testToUnicode(const char * testName,TestFunc func)712 void TestIDNA::testToUnicode(const char* testName, TestFunc func){
713
714 int32_t i;
715 UChar buf[MAX_DEST_SIZE];
716
717 for(i=0;i< UPRV_LENGTHOF(asciiIn); i++){
718 u_charsToUChars(asciiIn[i],buf, (int32_t)(strlen(asciiIn[i])+1));
719 testAPI(buf,unicodeIn[i],testName,false,U_ZERO_ERROR, true, true, func);
720 }
721 }
722
723
testIDNToUnicode(const char * testName,TestFunc func)724 void TestIDNA::testIDNToUnicode(const char* testName, TestFunc func){
725 int32_t i;
726 UChar buf[MAX_DEST_SIZE];
727 UChar expected[MAX_DEST_SIZE];
728 UErrorCode status = U_ZERO_ERROR;
729 int32_t bufLen = 0;
730 UParseError parseError;
731 for(i=0;i< UPRV_LENGTHOF(domainNames); i++){
732 bufLen = (int32_t)strlen(domainNames[i]);
733 bufLen = u_unescape(domainNames[i],buf, bufLen+1);
734 func(buf,bufLen,expected,MAX_DEST_SIZE, UIDNA_ALLOW_UNASSIGNED, &parseError,&status);
735 if(U_FAILURE(status)){
736 errcheckln(status, "%s failed to convert domainNames[%i].Error: %s",testName, i, u_errorName(status));
737 break;
738 }
739 testAPI(buf,expected,testName,false,U_ZERO_ERROR, true, true, func);
740 //test toUnicode with all labels in the string
741 testAPI(buf,expected,testName, false,U_ZERO_ERROR, true, true, func);
742 if(U_FAILURE(status)){
743 errln( "%s failed to convert domainNames[%i].Error: %s \n",testName,i, u_errorName(status));
744 break;
745 }
746 }
747
748 }
749
testIDNToASCII(const char * testName,TestFunc func)750 void TestIDNA::testIDNToASCII(const char* testName, TestFunc func){
751 int32_t i;
752 UChar buf[MAX_DEST_SIZE];
753 UChar expected[MAX_DEST_SIZE];
754 UErrorCode status = U_ZERO_ERROR;
755 int32_t bufLen = 0;
756 UParseError parseError;
757 for(i=0;i< UPRV_LENGTHOF(domainNames); i++){
758 bufLen = (int32_t)strlen(domainNames[i]);
759 bufLen = u_unescape(domainNames[i],buf, bufLen+1);
760 func(buf,bufLen,expected,MAX_DEST_SIZE, UIDNA_ALLOW_UNASSIGNED, &parseError,&status);
761 if(U_FAILURE(status)){
762 errcheckln(status, "%s failed to convert domainNames[%i].Error: %s",testName,i, u_errorName(status));
763 break;
764 }
765 testAPI(buf,expected,testName, false,U_ZERO_ERROR, true, true, func);
766 //test toASCII with all labels in the string
767 testAPI(buf,expected,testName, false,U_ZERO_ERROR, false, true, func);
768 if(U_FAILURE(status)){
769 errln( "%s failed to convert domainNames[%i].Error: %s \n",testName,i, u_errorName(status));
770 break;
771 }
772 }
773
774 }
775
testCompare(const char * testName,CompareFunc func)776 void TestIDNA::testCompare(const char* testName, CompareFunc func){
777 int32_t i;
778
779
780 UChar www[] = {0x0057, 0x0057, 0x0057, 0x002E, 0x0000};
781 UChar com[] = {0x002E, 0x0043, 0x004F, 0x004D, 0x0000};
782 UChar buf[MAX_DEST_SIZE]={0x0057, 0x0057, 0x0057, 0x002E, 0x0000};
783
784 UnicodeString source(www), uni0(www),uni1(www), ascii0(www), ascii1(www);
785
786 uni0.append(unicodeIn[0]);
787 uni0.append(com);
788 uni0.append((UChar)0x0000);
789
790 uni1.append(unicodeIn[1]);
791 uni1.append(com);
792 uni1.append((UChar)0x0000);
793
794 ascii0.append(asciiIn[0]);
795 ascii0.append(com);
796 ascii0.append((UChar)0x0000);
797
798 ascii1.append(asciiIn[1]);
799 ascii1.append(com);
800 ascii1.append((UChar)0x0000);
801
802 for(i=0;i< UPRV_LENGTHOF(unicodeIn); i++){
803
804 u_charsToUChars(asciiIn[i],buf+4, (int32_t)(strlen(asciiIn[i])+1));
805 u_strcat(buf,com);
806
807 // for every entry in unicodeIn array
808 // prepend www. and append .com
809 source.truncate(4);
810 source.append(unicodeIn[i]);
811 source.append(com);
812 source.append((UChar)0x0000);
813 // a) compare it with itself
814 const UChar* src = source.getBuffer();
815 int32_t srcLen = u_strlen(src); //subtract null
816
817 testCompare(src,srcLen,src,srcLen,testName, func, true);
818
819 // b) compare it with asciiIn equivalent
820 testCompare(src,srcLen,buf,u_strlen(buf),testName, func,true);
821
822 // c) compare it with unicodeIn not equivalent
823 if(i==0){
824 testCompare(src,srcLen,uni1.getBuffer(),uni1.length()-1,testName, func,false);
825 }else{
826 testCompare(src,srcLen,uni0.getBuffer(),uni0.length()-1,testName, func,false);
827 }
828 // d) compare it with asciiIn not equivalent
829 if(i==0){
830 testCompare(src,srcLen,ascii1.getBuffer(),ascii1.length()-1,testName, func,false);
831 }else{
832 testCompare(src,srcLen,ascii0.getBuffer(),ascii0.length()-1,testName, func,false);
833 }
834
835 }
836 }
837
838 #if 0
839
840 static int32_t
841 getNextSeperator(UChar *src,int32_t srcLength,
842 UChar **limit){
843 if(srcLength == -1){
844 int32_t i;
845 for(i=0 ; ;i++){
846 if(src[i] == 0){
847 *limit = src + i; // point to null
848 return i;
849 }
850 if(src[i]==0x002e){
851 *limit = src + (i+1); // go past the delimiter
852 return i;
853 }
854 }
855 // we have not found the delimiter
856 if(i==srcLength){
857 *limit = src+srcLength;
858 }
859 return i;
860 }else{
861 int32_t i;
862 for(i=0;i<srcLength;i++){
863 if(src[i]==0x002e){
864 *limit = src + (i+1); // go past the delimiter
865 return i;
866 }
867 }
868 // we have not found the delimiter
869 if(i==srcLength){
870 *limit = src+srcLength;
871 }
872 return i;
873 }
874 }
875
876 void printPunycodeOutput(){
877
878 UChar dest[MAX_DEST_SIZE];
879 int32_t destCapacity=MAX_DEST_SIZE;
880 UChar* start;
881 UChar* limit;
882 int32_t labelLen=0;
883 UBool caseFlags[MAX_DEST_SIZE];
884
885 for(int32_t i=0;i< UPRV_LENGTHOF(errorCases);i++){
886 ErrorCases errorCase = errorCases[i];
887 UErrorCode status = U_ZERO_ERROR;
888 start = errorCase.unicode;
889 int32_t srcLen = u_strlen(start);
890 labelLen = getNextSeperator(start,srcLen,&limit);
891 start = limit;
892 labelLen=getNextSeperator(start,srcLen-labelLen,&limit);
893 int32_t destLen = u_strToPunycode(dest,destCapacity,start,labelLen,caseFlags, &status);
894 if(U_FAILURE(status)){
895 printf("u_strToPunycode failed for index %i\n",i);
896 continue;
897 }
898 for(int32_t j=0; j<destLen; j++){
899 printf("%c",(char)dest[j]);
900 }
901 printf("\n");
902 }
903 }
904 #endif
905
testErrorCases(const char * IDNToASCIIName,TestFunc IDNToASCII,const char * IDNToUnicodeName,TestFunc IDNToUnicode)906 void TestIDNA::testErrorCases(const char* IDNToASCIIName, TestFunc IDNToASCII,
907 const char* IDNToUnicodeName, TestFunc IDNToUnicode){
908 UChar buf[MAX_DEST_SIZE];
909 int32_t bufLen=0;
910
911 for(int32_t i=0;i< UPRV_LENGTHOF(errorCases);i++){
912 ErrorCases errorCase = errorCases[i];
913 UChar* src =NULL;
914 if(errorCase.ascii != NULL){
915 bufLen = (int32_t)strlen(errorCase.ascii);
916 u_charsToUChars(errorCase.ascii,buf, bufLen+1);
917 }else{
918 bufLen = 1 ;
919 memset(buf,0,U_SIZEOF_UCHAR*MAX_DEST_SIZE);
920 }
921
922 if(errorCase.unicode[0]!=0){
923 src = errorCase.unicode;
924 }
925 // test toASCII
926 testAPI(src,buf,
927 IDNToASCIIName, errorCase.useSTD3ASCIIRules,
928 errorCase.expected, true, true, IDNToASCII);
929 if(errorCase.testLabel ==true){
930 testAPI(src,buf,
931 IDNToASCIIName, errorCase.useSTD3ASCIIRules,
932 errorCase.expected, false,true, IDNToASCII);
933 }
934 if(errorCase.testToUnicode ==true){
935 testAPI((src==NULL)? NULL : buf,src,
936 IDNToUnicodeName, errorCase.useSTD3ASCIIRules,
937 errorCase.expected, true, true, IDNToUnicode);
938 }
939
940 }
941
942 }
943 /*
944 void TestIDNA::testConformance(const char* toASCIIName, TestFunc toASCII,
945 const char* IDNToASCIIName, TestFunc IDNToASCII,
946 const char* IDNToUnicodeName, TestFunc IDNToUnicode,
947 const char* toUnicodeName, TestFunc toUnicode){
948 UChar src[MAX_DEST_SIZE];
949 int32_t srcLen=0;
950 UChar expected[MAX_DEST_SIZE];
951 int32_t expectedLen = 0;
952 for(int32_t i=0;i< UPRV_LENGTHOF(conformanceTestCases);i++){
953 const char* utf8Chars1 = conformanceTestCases[i].in;
954 int32_t utf8Chars1Len = (int32_t)strlen(utf8Chars1);
955 const char* utf8Chars2 = conformanceTestCases[i].out;
956 int32_t utf8Chars2Len = (utf8Chars2 == NULL) ? 0 : (int32_t)strlen(utf8Chars2);
957
958 UErrorCode status = U_ZERO_ERROR;
959 u_strFromUTF8(src,MAX_DEST_SIZE,&srcLen,utf8Chars1,utf8Chars1Len,&status);
960 if(U_FAILURE(status)){
961 errln(UnicodeString("Conversion of UTF8 source in conformanceTestCases[") + i +UnicodeString( "].in ( ")+prettify(utf8Chars1) +UnicodeString(" ) failed. Error: ")+ UnicodeString(u_errorName(status)));
962 continue;
963 }
964 if(utf8Chars2 != NULL){
965 u_strFromUTF8(expected,MAX_DEST_SIZE,&expectedLen,utf8Chars2,utf8Chars2Len, &status);
966 if(U_FAILURE(status)){
967 errln(UnicodeString("Conversion of UTF8 source in conformanceTestCases[") + i +UnicodeString( "].in ( ")+prettify(utf8Chars1) +UnicodeString(" ) failed. Error: ")+ UnicodeString(u_errorName(status)));
968 continue;
969 }
970 }
971
972 if(conformanceTestCases[i].expectedStatus != U_ZERO_ERROR){
973 // test toASCII
974 testAPI(src,expected,
975 IDNToASCIIName, false,
976 conformanceTestCases[i].expectedStatus,
977 true,
978 (conformanceTestCases[i].expectedStatus != U_IDNA_UNASSIGNED_ERROR),
979 IDNToASCII);
980
981 testAPI(src,expected,
982 toASCIIName, false,
983 conformanceTestCases[i].expectedStatus, true,
984 (conformanceTestCases[i].expectedStatus != U_IDNA_UNASSIGNED_ERROR),
985 toASCII);
986 }
987
988 testAPI(src,src,
989 IDNToUnicodeName, false,
990 conformanceTestCases[i].expectedStatus, true, true, IDNToUnicode);
991 testAPI(src,src,
992 toUnicodeName, false,
993 conformanceTestCases[i].expectedStatus, true, true, toUnicode);
994
995 }
996
997 }
998 */
999 // test and ascertain
1000 // func(func(func(src))) == func(src)
testChaining(const UChar * src,int32_t numIterations,const char * testName,UBool useSTD3ASCIIRules,UBool caseInsensitive,TestFunc func)1001 void TestIDNA::testChaining(const UChar* src,int32_t numIterations,const char* testName,
1002 UBool useSTD3ASCIIRules, UBool caseInsensitive, TestFunc func){
1003 UChar even[MAX_DEST_SIZE];
1004 UChar odd[MAX_DEST_SIZE];
1005 UChar expected[MAX_DEST_SIZE];
1006 int32_t i=0,evenLen=0,oddLen=0,expectedLen=0;
1007 UErrorCode status = U_ZERO_ERROR;
1008 int32_t srcLen = u_strlen(src);
1009 int32_t options = (useSTD3ASCIIRules == true) ? UIDNA_USE_STD3_RULES : UIDNA_DEFAULT;
1010 UParseError parseError;
1011
1012 // test null-terminated source
1013 expectedLen = func(src,-1,expected,MAX_DEST_SIZE, options, &parseError, &status);
1014 if(U_FAILURE(status)){
1015 errcheckln(status, "%s null terminated source failed. Error: %s",testName, u_errorName(status));
1016 }
1017 memcpy(odd,expected,(expectedLen+1) * U_SIZEOF_UCHAR);
1018 memcpy(even,expected,(expectedLen+1) * U_SIZEOF_UCHAR);
1019 for(;i<=numIterations; i++){
1020 if((i%2) ==0){
1021 evenLen = func(odd,-1,even,MAX_DEST_SIZE,options, &parseError, &status);
1022 if(U_FAILURE(status)){
1023 errcheckln(status, "%s null terminated source failed - %s",testName, u_errorName(status));
1024 break;
1025 }
1026 }else{
1027 oddLen = func(even,-1,odd,MAX_DEST_SIZE,options, &parseError, &status);
1028 if(U_FAILURE(status)){
1029 errln("%s null terminated source failed\n",testName);
1030 break;
1031 }
1032 }
1033 }
1034 if(caseInsensitive ==true){
1035 if( u_strCaseCompare(even,evenLen, expected,expectedLen, 0, &status) !=0 ||
1036 u_strCaseCompare(odd,oddLen, expected,expectedLen, 0, &status) !=0 ){
1037
1038 errln("Chaining for %s null terminated source failed\n",testName);
1039 }
1040 }else{
1041 if( u_strncmp(even,expected,expectedLen) != 0 ||
1042 u_strncmp(odd,expected,expectedLen) !=0 ){
1043
1044 errln("Chaining for %s null terminated source failed\n",testName);
1045 }
1046 }
1047
1048 // test null-terminated source
1049 status = U_ZERO_ERROR;
1050 expectedLen = func(src,-1,expected,MAX_DEST_SIZE,options|UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
1051 if(U_FAILURE(status)){
1052 errcheckln(status, "%s null terminated source with options set failed. Error: %s",testName, u_errorName(status));
1053 }
1054 memcpy(odd,expected,(expectedLen+1) * U_SIZEOF_UCHAR);
1055 memcpy(even,expected,(expectedLen+1) * U_SIZEOF_UCHAR);
1056 for(;i<=numIterations; i++){
1057 if((i%2) ==0){
1058 evenLen = func(odd,-1,even,MAX_DEST_SIZE,options|UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
1059 if(U_FAILURE(status)){
1060 errcheckln(status, "%s null terminated source with options set failed - %s",testName, u_errorName(status));
1061 break;
1062 }
1063 }else{
1064 oddLen = func(even,-1,odd,MAX_DEST_SIZE,options|UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
1065 if(U_FAILURE(status)){
1066 errln("%s null terminated source with options set failed\n",testName);
1067 break;
1068 }
1069 }
1070 }
1071 if(caseInsensitive ==true){
1072 if( u_strCaseCompare(even,evenLen, expected,expectedLen, 0, &status) !=0 ||
1073 u_strCaseCompare(odd,oddLen, expected,expectedLen, 0, &status) !=0 ){
1074
1075 errln("Chaining for %s null terminated source with options set failed\n",testName);
1076 }
1077 }else{
1078 if( u_strncmp(even,expected,expectedLen) != 0 ||
1079 u_strncmp(odd,expected,expectedLen) !=0 ){
1080
1081 errln("Chaining for %s null terminated source with options set failed\n",testName);
1082 }
1083 }
1084
1085
1086 // test source with length
1087 status = U_ZERO_ERROR;
1088 expectedLen = func(src,srcLen,expected,MAX_DEST_SIZE,options, &parseError, &status);
1089 if(U_FAILURE(status)){
1090 errcheckln(status, "%s null terminated source failed. Error: %s",testName, u_errorName(status));
1091 }
1092 memcpy(odd,expected,(expectedLen+1) * U_SIZEOF_UCHAR);
1093 memcpy(even,expected,(expectedLen+1) * U_SIZEOF_UCHAR);
1094 for(;i<=numIterations; i++){
1095 if((i%2) ==0){
1096 evenLen = func(odd,oddLen,even,MAX_DEST_SIZE,options, &parseError, &status);
1097 if(U_FAILURE(status)){
1098 errcheckln(status, "%s source with source length failed - %s",testName, u_errorName(status));
1099 break;
1100 }
1101 }else{
1102 oddLen = func(even,evenLen,odd,MAX_DEST_SIZE,options, &parseError, &status);
1103 if(U_FAILURE(status)){
1104 errcheckln(status, "%s source with source length failed - %s",testName, u_errorName(status));
1105 break;
1106 }
1107 }
1108 }
1109 if(caseInsensitive ==true){
1110 if( u_strCaseCompare(even,evenLen, expected,expectedLen, 0, &status) !=0 ||
1111 u_strCaseCompare(odd,oddLen, expected,expectedLen, 0, &status) !=0 ){
1112
1113 errln("Chaining for %s source with source length failed\n",testName);
1114 }
1115 }else{
1116 if( u_strncmp(even,expected,expectedLen) != 0 ||
1117 u_strncmp(odd,expected,expectedLen) !=0 ){
1118
1119 errln("Chaining for %s source with source length failed\n",testName);
1120 }
1121 }
1122 status = U_ZERO_ERROR;
1123 expectedLen = func(src,srcLen,expected,MAX_DEST_SIZE,options|UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
1124 if(U_FAILURE(status)){
1125 errcheckln(status, "%s null terminated source with options set failed. Error: %s",testName, u_errorName(status));
1126 }
1127 memcpy(odd,expected,(expectedLen+1) * U_SIZEOF_UCHAR);
1128 memcpy(even,expected,(expectedLen+1) * U_SIZEOF_UCHAR);
1129 for(;i<=numIterations; i++){
1130 if((i%2) ==0){
1131 evenLen = func(odd,oddLen,even,MAX_DEST_SIZE,options|UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
1132 if(U_FAILURE(status)){
1133 errcheckln(status, "%s source with source length and options set failed - %s",testName, u_errorName(status));
1134 break;
1135 }
1136 }else{
1137 oddLen = func(even,evenLen,odd,MAX_DEST_SIZE,options|UIDNA_ALLOW_UNASSIGNED, &parseError, &status);
1138 if(U_FAILURE(status)){
1139 errcheckln(status, "%s source with source length and options set failed - %s",testName, u_errorName(status));
1140 break;
1141 }
1142 }
1143 }
1144 if(caseInsensitive ==true){
1145 if( u_strCaseCompare(even,evenLen, expected,expectedLen, 0, &status) !=0 ||
1146 u_strCaseCompare(odd,oddLen, expected,expectedLen, 0, &status) !=0 ){
1147
1148 errln("Chaining for %s source with source length and options set failed\n",testName);
1149 }
1150 }else{
1151 if( u_strncmp(even,expected,expectedLen) != 0 ||
1152 u_strncmp(odd,expected,expectedLen) !=0 ){
1153
1154 errln("Chaining for %s source with source length and options set failed\n",testName);
1155 }
1156 }
1157 }
testChaining(const char * toASCIIName,TestFunc toASCII,const char * toUnicodeName,TestFunc toUnicode)1158 void TestIDNA::testChaining(const char* toASCIIName, TestFunc toASCII,
1159 const char* toUnicodeName, TestFunc toUnicode){
1160 int32_t i;
1161 UChar buf[MAX_DEST_SIZE];
1162
1163 for(i=0;i< UPRV_LENGTHOF(asciiIn); i++){
1164 u_charsToUChars(asciiIn[i],buf, (int32_t)(strlen(asciiIn[i])+1));
1165 testChaining(buf,5,toUnicodeName, false, false, toUnicode);
1166 }
1167 for(i=0;i< UPRV_LENGTHOF(unicodeIn); i++){
1168 testChaining(unicodeIn[i], 5,toASCIIName, false, true, toASCII);
1169 }
1170 }
1171
1172
testRootLabelSeparator(const char * testName,CompareFunc func,const char * IDNToASCIIName,TestFunc IDNToASCII,const char * IDNToUnicodeName,TestFunc IDNToUnicode)1173 void TestIDNA::testRootLabelSeparator(const char* testName, CompareFunc func,
1174 const char* IDNToASCIIName, TestFunc IDNToASCII,
1175 const char* IDNToUnicodeName, TestFunc IDNToUnicode){
1176 int32_t i;
1177
1178
1179 UChar www[] = {0x0057, 0x0057, 0x0057, 0x002E, 0x0000};
1180 UChar com[] = {0x002E, 0x0043, 0x004F, 0x004D, 0x002E, /* root label separator */0x0000};
1181 UChar buf[MAX_DEST_SIZE]={0x0057, 0x0057, 0x0057, 0x002E, 0x0000};
1182
1183 UnicodeString source(www), uni0(www),uni1(www), ascii0(www), ascii1(www);
1184
1185 uni0.append(unicodeIn[0]);
1186 uni0.append(com);
1187 uni0.append((UChar)0x0000);
1188
1189 uni1.append(unicodeIn[1]);
1190 uni1.append(com);
1191 uni1.append((UChar)0x0000);
1192
1193 ascii0.append(asciiIn[0]);
1194 ascii0.append(com);
1195 ascii0.append((UChar)0x0000);
1196
1197 ascii1.append(asciiIn[1]);
1198 ascii1.append(com);
1199 ascii1.append((UChar)0x0000);
1200
1201 for(i=0;i< UPRV_LENGTHOF(unicodeIn); i++){
1202
1203 u_charsToUChars(asciiIn[i],buf+4, (int32_t)(strlen(asciiIn[i])+1));
1204 u_strcat(buf,com);
1205
1206 // for every entry in unicodeIn array
1207 // prepend www. and append .com
1208 source.truncate(4);
1209 source.append(unicodeIn[i]);
1210 source.append(com);
1211 source.append((UChar)0x0000);
1212
1213 const UChar* src = source.getBuffer();
1214 int32_t srcLen = u_strlen(src); //subtract null
1215
1216 // b) compare it with asciiIn equivalent
1217 testCompare(src,srcLen,buf,u_strlen(buf),testName, func,true);
1218
1219 // a) compare it with itself
1220 testCompare(src,srcLen,src,srcLen,testName, func,true);
1221
1222
1223 // IDNToASCII comparison
1224 testAPI(src,buf,IDNToASCIIName,false,U_ZERO_ERROR,true, true, IDNToASCII);
1225 // IDNToUnicode comparison
1226 testAPI(buf,src,IDNToUnicodeName, false,U_ZERO_ERROR, true, true, IDNToUnicode);
1227
1228 // c) compare it with unicodeIn not equivalent
1229 if(i==0){
1230 testCompare(src,srcLen,uni1.getBuffer(),uni1.length()-1,testName, func,false);
1231 }else{
1232 testCompare(src,srcLen,uni0.getBuffer(),uni0.length()-1,testName, func,false);
1233 }
1234 // d) compare it with asciiIn not equivalent
1235 if(i==0){
1236 testCompare(src,srcLen,ascii1.getBuffer(),ascii1.length()-1,testName, func,false);
1237 }else{
1238 testCompare(src,srcLen,ascii0.getBuffer(),ascii0.length()-1,testName, func,false);
1239 }
1240 }
1241 }
1242
1243 //---------------------------------------------
1244 // runIndexedTest
1245 //---------------------------------------------
1246
1247 extern IntlTest *createUTS46Test();
1248
runIndexedTest(int32_t index,UBool exec,const char * & name,char * par)1249 void TestIDNA::runIndexedTest( int32_t index, UBool exec, const char* &name, char* par)
1250 {
1251 if (exec) logln((UnicodeString)"TestSuite IDNA API ");
1252 switch (index) {
1253
1254 case 0: name = "TestToASCII"; if (exec) TestToASCII(); break;
1255 case 1: name = "TestToUnicode"; if (exec) TestToUnicode(); break;
1256 case 2: name = "TestIDNToASCII"; if (exec) TestIDNToASCII(); break;
1257 case 3: name = "TestIDNToUnicode"; if (exec) TestIDNToUnicode(); break;
1258 case 4: name = "TestCompare"; if (exec) TestCompare(); break;
1259 case 5: name = "TestErrorCases"; if (exec) TestErrorCases(); break;
1260 case 6: name = "TestChaining"; if (exec) TestChaining(); break;
1261 case 7: name = "TestRootLabelSeparator"; if(exec) TestRootLabelSeparator(); break;
1262 case 8: name = "TestCompareReferenceImpl"; if(exec) TestCompareReferenceImpl(); break;
1263 case 9: name = "TestDataFile"; if(exec) TestDataFile(); break;
1264 #if !UCONFIG_NO_FILE_IO && !UCONFIG_NO_LEGACY_CONVERSION
1265 case 10: name = "TestRefIDNA"; if(exec) TestRefIDNA(); break;
1266 case 11: name = "TestIDNAMonkeyTest"; if(exec) TestIDNAMonkeyTest(); break;
1267 #else
1268 case 10: case 11: name = "skip"; break;
1269 #endif
1270 case 12:
1271 {
1272 name = "TestConformanceTestVectors";
1273 if(exec){
1274 logln("TestSuite IDNA conf----"); logln();
1275 IdnaConfTest test;
1276 callTest(test, par);
1277 }
1278 break;
1279 }
1280 case 13:
1281 name = "UTS46Test";
1282 if (exec) {
1283 logln("TestSuite UTS46Test---"); logln();
1284 LocalPointer<IntlTest> test(createUTS46Test());
1285 callTest(*test, par);
1286 }
1287 break;
1288 default: name = ""; break; /*needed to end loop*/
1289 }
1290 }
TestToASCII()1291 void TestIDNA::TestToASCII(){
1292 testToASCII("uidna_toASCII", uidna_toASCII);
1293 }
TestToUnicode()1294 void TestIDNA::TestToUnicode(){
1295 testToUnicode("uidna_toUnicode", uidna_toUnicode);
1296 }
TestIDNToASCII()1297 void TestIDNA::TestIDNToASCII(){
1298 testIDNToASCII("uidna_IDNToASCII", uidna_IDNToASCII);
1299 }
TestIDNToUnicode()1300 void TestIDNA::TestIDNToUnicode(){
1301 testIDNToUnicode("uidna_IDNToUnicode", uidna_IDNToUnicode);
1302 }
TestCompare()1303 void TestIDNA::TestCompare(){
1304 UErrorCode status = U_ZERO_ERROR;
1305 uidna_close(uidna_openUTS46(0, &status)); // Fail quickly if no data.
1306 if (assertSuccess("", status, true, __FILE__, __LINE__)) {
1307 testCompare("uidna_compare",uidna_compare);
1308 }
1309 }
TestErrorCases()1310 void TestIDNA::TestErrorCases(){
1311 testErrorCases( "uidna_IDNToASCII",uidna_IDNToASCII,
1312 "uidna_IDNToUnicode",uidna_IDNToUnicode);
1313 }
TestRootLabelSeparator()1314 void TestIDNA::TestRootLabelSeparator(){
1315 UErrorCode status = U_ZERO_ERROR;
1316 uidna_close(uidna_openUTS46(0, &status)); // Fail quickly if no data.
1317 if (assertSuccess("", status, true, __FILE__, __LINE__)) {
1318 testRootLabelSeparator( "uidna_compare",uidna_compare,
1319 "uidna_IDNToASCII", uidna_IDNToASCII,
1320 "uidna_IDNToUnicode",uidna_IDNToUnicode
1321 );
1322 }
1323 }
TestChaining()1324 void TestIDNA::TestChaining(){
1325 testChaining("uidna_toASCII",uidna_toASCII, "uidna_toUnicode", uidna_toUnicode);
1326 }
1327
1328
1329 static const int loopCount = 100;
1330 static const int maxCharCount = 20;
1331
1332 static uint32_t
randul()1333 randul()
1334 {
1335 static UBool initialized = false;
1336 if (!initialized)
1337 {
1338 srand((unsigned)time(NULL));
1339 initialized = true;
1340 }
1341 // Assume rand has at least 12 bits of precision
1342 uint32_t l = 0;
1343 for (uint32_t i=0; i<sizeof(l); ++i)
1344 ((char*)&l)[i] = (char)((rand() & 0x0FF0) >> 4);
1345 return l;
1346 }
1347
1348 /**
1349 * Return a random integer i where 0 <= i < n.
1350 * A special function that gets random codepoints from planes 0,1,2 and 14
1351 */
rand_uni()1352 static int32_t rand_uni()
1353 {
1354 int32_t retVal = (int32_t)(randul()& 0x3FFFF);
1355 if(retVal >= 0x30000){
1356 retVal+=0xB0000;
1357 }
1358 return retVal;
1359 }
1360
randi(int32_t n)1361 static int32_t randi(int32_t n){
1362 return (int32_t) (randul() % (n+1));
1363 }
1364
getTestSource(UnicodeString & fillIn)1365 void getTestSource(UnicodeString& fillIn) {
1366 int32_t i = 0;
1367 int32_t charCount = (randi(maxCharCount) + 1);
1368 while (i <charCount ) {
1369 int32_t codepoint = rand_uni();
1370 if(codepoint == 0x0000){
1371 continue;
1372 }
1373 fillIn.append((UChar32)codepoint);
1374 i++;
1375 }
1376
1377 }
1378
testCompareReferenceImpl(UnicodeString & src,TestFunc refIDNA,const char * refIDNAName,TestFunc uIDNA,const char * uIDNAName,int32_t options)1379 UnicodeString TestIDNA::testCompareReferenceImpl(UnicodeString& src,
1380 TestFunc refIDNA, const char* refIDNAName,
1381 TestFunc uIDNA, const char* uIDNAName,
1382 int32_t options){
1383
1384 const UChar* srcUChars = src.getBuffer();
1385 UChar exp[MAX_DEST_SIZE]={0};
1386 int32_t expCap = MAX_DEST_SIZE, expLen=0;
1387 UErrorCode expStatus = U_ZERO_ERROR;
1388 UParseError parseError;
1389
1390 logln("Comparing "+ UnicodeString(refIDNAName)
1391 + " with "+ UnicodeString(uIDNAName)
1392 +" for input: " + prettify(srcUChars));
1393
1394 expLen = refIDNA(srcUChars, src.length()-1, exp, expCap,
1395 options, &parseError, &expStatus);
1396
1397 UChar got[MAX_DEST_SIZE]={0};
1398 int32_t gotCap = MAX_DEST_SIZE, gotLen=0;
1399 UErrorCode gotStatus = U_ZERO_ERROR;
1400
1401 gotLen = uIDNA(srcUChars, src.length()-1, got, gotCap,
1402 options, &parseError, &gotStatus);
1403
1404 if(expStatus != gotStatus){
1405 errln("Did not get the expected status while comparing " + UnicodeString(refIDNAName)
1406 + " with " + UnicodeString(uIDNAName)
1407 + " Expected: " + UnicodeString(u_errorName(expStatus))
1408 + " Got: " + UnicodeString(u_errorName(gotStatus))
1409 + " for Source: "+ prettify(srcUChars)
1410 + " Options: " + options);
1411 return UnicodeString("");
1412 }
1413
1414 // now we know that both implementations yielded same error
1415 if(U_SUCCESS(expStatus)){
1416 // compare the outputs if status == U_ZERO_ERROR
1417 if(u_strCompare(exp, expLen, got, gotLen, true) != 0){
1418 errln("Did not get the expected output while comparing " + UnicodeString(refIDNAName)
1419 + " with " + UnicodeString(uIDNAName)
1420 + " Expected: " + prettify(UnicodeString(exp, expLen))
1421 + " Got: " + prettify(UnicodeString(got, gotLen))
1422 + " for Source: "+ prettify(srcUChars)
1423 + " Options: " + options);
1424 }
1425 return UnicodeString(exp, expLen);
1426
1427 }else{
1428 logln("Got the same error while comparing "
1429 + UnicodeString(refIDNAName)
1430 + " with "+ UnicodeString(uIDNAName)
1431 +" for input: " + prettify(srcUChars));
1432 }
1433 return UnicodeString("");
1434 }
1435
testCompareReferenceImpl(const UChar * src,int32_t srcLen)1436 void TestIDNA::testCompareReferenceImpl(const UChar* src, int32_t srcLen){
1437 UnicodeString label(src,srcLen);
1438 label.append((UChar)0x0000);
1439
1440 //test idnaref_toASCII and idnare
1441 UnicodeString asciiLabel = testCompareReferenceImpl(label,
1442 idnaref_toASCII, "idnaref_toASCII",
1443 uidna_toASCII, "uidna_toASCII",
1444 UIDNA_ALLOW_UNASSIGNED);
1445 testCompareReferenceImpl(label,
1446 idnaref_toASCII, "idnaref_toASCII",
1447 uidna_toASCII, "uidna_toASCII",
1448 UIDNA_DEFAULT);
1449 testCompareReferenceImpl(label,
1450 idnaref_toASCII, "idnaref_toASCII",
1451 uidna_toASCII, "uidna_toASCII",
1452 UIDNA_USE_STD3_RULES);
1453 testCompareReferenceImpl(label,
1454 idnaref_toASCII, "idnaref_toASCII",
1455 uidna_toASCII, "uidna_toASCII",
1456 UIDNA_USE_STD3_RULES | UIDNA_ALLOW_UNASSIGNED);
1457
1458 if(asciiLabel.length()!=0){
1459 asciiLabel.append((UChar)0x0000);
1460
1461 // test toUnciode
1462 testCompareReferenceImpl(asciiLabel,
1463 idnaref_toUnicode, "idnaref_toUnicode",
1464 uidna_toUnicode, "uidna_toUnicode",
1465 UIDNA_ALLOW_UNASSIGNED);
1466 testCompareReferenceImpl(asciiLabel,
1467 idnaref_toUnicode, "idnaref_toUnicode",
1468 uidna_toUnicode, "uidna_toUnicode",
1469 UIDNA_DEFAULT);
1470 testCompareReferenceImpl(asciiLabel,
1471 idnaref_toUnicode, "idnaref_toUnicode",
1472 uidna_toUnicode, "uidna_toUnicode",
1473 UIDNA_USE_STD3_RULES);
1474 testCompareReferenceImpl(asciiLabel,
1475 idnaref_toUnicode, "idnaref_toUnicode",
1476 uidna_toUnicode, "uidna_toUnicode",
1477 UIDNA_USE_STD3_RULES | UIDNA_ALLOW_UNASSIGNED);
1478 }
1479
1480 }
1481 const char* failures[] ={
1482 "\\uAA42\\U0001F8DD\\U00019D01\\U000149A3\\uD385\\U000EE0F5\\U00018B92\\U000179D1\\U00018624\\U0002227F\\U000E83C0\\U000E8DCD\\u5460\\U00017F34\\U0001570B\\u43D1\\U0002C9C9\\U000281EC\\u2105\\U000180AE\\uC5D4",
1483 "\\U0002F5A6\\uD638\\u0D0A\\u9E9C\\uFE5B\\U0001FCCB\\u66C4",
1484 };
1485
TestIDNAMonkeyTest()1486 void TestIDNA::TestIDNAMonkeyTest(){
1487 UnicodeString source;
1488 UErrorCode status = U_ZERO_ERROR;
1489 int i;
1490
1491 getInstance(status); // Init prep
1492 if (U_FAILURE(status)) {
1493 dataerrln("Test could not initialize. Got %s", u_errorName(status));
1494 return;
1495 }
1496
1497 for(i=0; i<loopCount; i++){
1498 source.truncate(0);
1499 getTestSource(source);
1500 source.append((UChar)0x0000);
1501 const UChar* src = source.getBuffer();
1502 testCompareReferenceImpl(src,source.length()-1);
1503 testCompareReferenceImpl(src,source.length()-1);
1504 }
1505
1506 /* for debugging */
1507 for (i=0; i<UPRV_LENGTHOF(failures); i++){
1508 source.truncate(0);
1509 source.append( UnicodeString(failures[i], -1, US_INV) );
1510 source = source.unescape();
1511 source.append((UChar)0x0000);
1512 const UChar *src = source.getBuffer();
1513 testCompareReferenceImpl(src,source.length()-1);
1514 //debug(source.getBuffer(),source.length(),UIDNA_ALLOW_UNASSIGNED);
1515 }
1516
1517
1518 source.truncate(0);
1519 source.append(UNICODE_STRING_SIMPLE("\\uCF18\\U00021161\\U000EEF11\\U0002BB82\\U0001D63C"));
1520 debug(source.getBuffer(),source.length(),UIDNA_ALLOW_UNASSIGNED);
1521
1522 { // test deletion of code points
1523 UnicodeString source("\\u043f\\u00AD\\u034f\\u043e\\u0447\\u0435\\u043c\\u0443\\u0436\\u0435\\u043e\\u043d\\u0438\\u043d\\u0435\\u0433\\u043e\\u0432\\u043e\\u0440\\u044f\\u0442\\u043f\\u043e\\u0440\\u0443\\u0441\\u0441\\u043a\\u0438\\u0000", -1, US_INV);
1524 source = source.unescape();
1525 UnicodeString expected("\\u043f\\u043e\\u0447\\u0435\\u043c\\u0443\\u0436\\u0435\\u043e\\u043d\\u0438\\u043d\\u0435\\u0433\\u043e\\u0432\\u043e\\u0440\\u044f\\u0442\\u043f\\u043e\\u0440\\u0443\\u0441\\u0441\\u043a\\u0438\\u0000", -1, US_INV);
1526 expected = expected.unescape();
1527 UnicodeString ascii("xn--b1abfaaepdrnnbgefbadotcwatmq2g4l");
1528 ascii.append((UChar)0x0000);
1529 testAPI(source.getBuffer(),ascii.getBuffer(), "uidna_toASCII", false, U_ZERO_ERROR, true, true, uidna_toASCII);
1530
1531 testAPI(source.getBuffer(),ascii.getBuffer(), "idnaref_toASCII", false, U_ZERO_ERROR, true, true, idnaref_toASCII);
1532
1533 testCompareReferenceImpl(source.getBuffer(), source.length()-1);
1534 }
1535
1536 }
1537
TestCompareReferenceImpl()1538 void TestIDNA::TestCompareReferenceImpl(){
1539
1540 UChar src [2] = {0,0};
1541 int32_t srcLen = 0;
1542
1543 // data even OK?
1544 UErrorCode dataStatus = U_ZERO_ERROR;
1545 loadTestData(dataStatus);
1546 if(U_FAILURE(dataStatus)) {
1547 dataerrln("Couldn't load test data: %s\n", u_errorName(dataStatus)); // save us from thousands and thousands of errors
1548 return;
1549 }
1550 uidna_close(uidna_openUTS46(0, &dataStatus)); // Fail quickly if no data.
1551 if (!assertSuccess("", dataStatus, true, __FILE__, __LINE__)) { return; }
1552
1553 for (int32_t i = 0; i <= 0x10FFFF; i++){
1554 if (quick == true && i > 0x0FFF){
1555 return;
1556 }
1557 if(i == 0x30000){
1558 // jump to E0000, no characters assigned in plain 3 to plain 13 as of Unicode 6.0
1559 i = 0xE0000;
1560 }
1561 if (i > 0xFFFF){
1562 src[0] = U16_LEAD(i);
1563 src[1] = U16_TRAIL(i);
1564 srcLen =2;
1565 } else {
1566 src[0] = (UChar)i;
1567 src[1] = 0;
1568 srcLen = 1;
1569 }
1570 testCompareReferenceImpl(src, srcLen);
1571 }
1572 }
1573
TestRefIDNA()1574 void TestIDNA::TestRefIDNA(){
1575 UErrorCode status = U_ZERO_ERROR;
1576
1577 getInstance(status); // Init prep. Abort test early if no data.
1578 if (!assertSuccess("", status, true, __FILE__, __LINE__)) { return; }
1579
1580 testToASCII("idnaref_toASCII", idnaref_toASCII);
1581 testToUnicode("idnaref_toUnicode", idnaref_toUnicode);
1582 testIDNToASCII("idnaref_IDNToASCII", idnaref_IDNToASCII);
1583 testIDNToUnicode("idnaref_IDNToUnicode", idnaref_IDNToUnicode);
1584 testCompare("idnaref_compare",idnaref_compare);
1585 testErrorCases( "idnaref_IDNToASCII",idnaref_IDNToASCII,
1586 "idnaref_IDNToUnicode",idnaref_IDNToUnicode);
1587 testChaining("idnaref_toASCII",idnaref_toASCII, "idnaref_toUnicode", idnaref_toUnicode);
1588
1589 testRootLabelSeparator( "idnaref_compare",idnaref_compare,
1590 "idnaref_IDNToASCII", idnaref_IDNToASCII,
1591 "idnaref_IDNToUnicode",idnaref_IDNToUnicode
1592 );
1593 testChaining("idnaref_toASCII",idnaref_toASCII, "idnaref_toUnicode", idnaref_toUnicode);
1594 }
1595
1596
TestDataFile()1597 void TestIDNA::TestDataFile(){
1598 testData(*this);
1599 }
1600
~TestIDNA()1601 TestIDNA::~TestIDNA(){
1602 delete gPrep;
1603 gPrep = NULL;
1604 }
1605
getInstance(UErrorCode & status)1606 NamePrepTransform* TestIDNA::getInstance(UErrorCode& status){
1607 if(gPrep == NULL){
1608 UParseError parseError;
1609 gPrep = NamePrepTransform::createInstance(parseError, status);
1610 if(gPrep == NULL){
1611 //status = U_MEMORY_ALLOCATION_ERROR;
1612 return NULL;
1613 }
1614 }
1615 return gPrep;
1616
1617 }
1618 #endif /* #if !UCONFIG_NO_IDNA */
1619