1 /* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this
3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
4 /*
5 * test_string.c
6 *
7 * Tests Strings.
8 *
9 */
10
11 #include "testutil.h"
12 #include "testutil_nss.h"
13
14 static void *plContext = NULL;
15
16 static void
createString(PKIX_PL_String ** testString,PKIX_UInt32 format,char * stringAscii,PKIX_UInt32 length)17 createString(
18 PKIX_PL_String **testString,
19 PKIX_UInt32 format,
20 char *stringAscii,
21 PKIX_UInt32 length)
22 {
23 PKIX_TEST_STD_VARS();
24
25 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_String_Create(format, stringAscii, length, testString, plContext));
26
27 cleanup:
28
29 PKIX_TEST_RETURN();
30 }
31
32 static void
createStringOther(PKIX_PL_String ** testEscAscii,PKIX_PL_String ** testUtf16,PKIX_PL_String ** ampString,PKIX_PL_String ** testDebugAscii,PKIX_PL_String ** testNullString,PKIX_UInt32 * utf16data)33 createStringOther(
34 PKIX_PL_String **testEscAscii,
35 PKIX_PL_String **testUtf16,
36 PKIX_PL_String **ampString,
37 PKIX_PL_String **testDebugAscii,
38 PKIX_PL_String **testNullString,
39 PKIX_UInt32 *utf16data)
40 {
41 char *nullText = "Hi� there!";
42
43 char *escAsciiString =
44 "¡𐀀࿿􀀁";
45
46 char *debugAsciiString =
47 "string with
newlines and	tabs";
48
49 char *utfAmp = "\x00&";
50
51 PKIX_TEST_STD_VARS();
52
53 createString(testEscAscii,
54 PKIX_ESCASCII,
55 escAsciiString,
56 PL_strlen(escAsciiString));
57
58 createString(testUtf16, PKIX_UTF16, (char *)utf16data, 12);
59
60 createString(ampString, PKIX_UTF16, utfAmp, 2);
61
62 createString(testDebugAscii,
63 PKIX_ESCASCII_DEBUG,
64 debugAsciiString,
65 PL_strlen(debugAsciiString));
66
67 createString(testNullString,
68 PKIX_ESCASCII_DEBUG,
69 nullText,
70 PL_strlen(nullText));
71
72 goto cleanup;
73
74 cleanup:
75
76 PKIX_TEST_RETURN();
77 }
78
79 static void
testGetEncoded(PKIX_PL_String * testEscAscii,PKIX_PL_String * testString0,PKIX_PL_String * testDebugAscii,PKIX_PL_String * testNullString,PKIX_UInt32 * utf16data)80 testGetEncoded(
81 PKIX_PL_String *testEscAscii,
82 PKIX_PL_String *testString0,
83 PKIX_PL_String *testDebugAscii,
84 PKIX_PL_String *testNullString,
85 PKIX_UInt32 *utf16data)
86 {
87 char *temp = NULL;
88 void *dest = NULL;
89 void *dest2 = NULL;
90 char *plainText = "string with\nnewlines and\ttabs";
91 PKIX_UInt32 length, length2, i;
92
93 PKIX_TEST_STD_VARS();
94
95 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_String_GetEncoded(testEscAscii,
96 PKIX_UTF16,
97 &dest,
98 &length,
99 plContext));
100 for (i = 0; i < length; i++) {
101 if (((char *)dest)[i] != ((char *)utf16data)[i]) {
102 testError("UTF-16 Data Differs from Source");
103 printf("%d-th char is different -%c-%c-\n", i,
104 ((char *)dest)[i], ((char *)utf16data)[i]);
105 }
106 }
107
108 length = 0;
109 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_Free(dest, plContext));
110
111 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_String_GetEncoded(testNullString,
112 PKIX_UTF16,
113 &dest,
114 &length,
115 plContext));
116
117 length = 0;
118 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_Free(dest, plContext));
119
120 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_String_GetEncoded(testString0,
121 PKIX_ESCASCII_DEBUG,
122 &dest,
123 &length,
124 plContext));
125
126 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_String_GetEncoded(testDebugAscii,
127 PKIX_ESCASCII_DEBUG,
128 &dest2,
129 &length2,
130 plContext));
131
132 for (i = 0; (i < length) && (i < length2); i++)
133 if (((char *)dest)[i] != ((char *)dest2)[i]) {
134 testError("Equivalent strings are unequal");
135 break;
136 }
137
138 length = 0;
139 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_Free(dest, plContext));
140 length2 = 0;
141 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_Free(dest2, plContext));
142
143 temp = PKIX_String2ASCII(testDebugAscii, plContext);
144 if (temp) {
145 if (PL_strcmp(plainText, temp) != 0)
146 testError("Debugged ASCII does not match "
147 "equivalent EscAscii");
148 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_Free(temp, plContext));
149 }
150
151 cleanup:
152
153 PKIX_TEST_RETURN();
154 }
155
156 static void
testSprintf(void)157 testSprintf(void)
158 {
159 PKIX_Int32 x = 0xCAFE;
160 PKIX_Int32 y = -12345;
161 PKIX_PL_String *testString = NULL;
162 PKIX_PL_String *formatString = NULL;
163 PKIX_PL_String *sprintfString = NULL;
164 char *plainText = "Testing Sprintf";
165 char *format = "%s %x %u %d";
166 char *convertedFormat = "%s %lx %lu %ld";
167 char *temp = NULL;
168 char *temp2 = NULL;
169
170 PKIX_TEST_STD_VARS();
171
172 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_String_Create(
173 PKIX_ESCASCII,
174 plainText,
175 PL_strlen(plainText),
176 &testString,
177 plContext));
178
179 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_String_Create(
180 PKIX_ESCASCII,
181 format,
182 11,
183 &formatString,
184 plContext));
185
186 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_Sprintf(&sprintfString,
187 plContext,
188 formatString,
189 testString, x, y, y));
190 PKIX_TEST_DECREF_BC(testString);
191
192 temp = PR_smprintf(convertedFormat, plainText, x, y, y);
193 temp2 = PKIX_String2ASCII(sprintfString, plContext);
194
195 if (PL_strcmp(temp, temp2) != 0)
196 testError("Sprintf produced incorrect output");
197
198 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_Free(temp, plContext));
199 PKIX_TEST_EXPECT_NO_ERROR(PKIX_PL_Free(temp2, plContext));
200
201 PKIX_TEST_DECREF_BC(sprintfString);
202
203 PKIX_TEST_DECREF_BC(formatString);
204
205 cleanup:
206
207 PKIX_TEST_RETURN();
208 }
209
210 static void
testErrorHandling(void)211 testErrorHandling(void)
212 {
213 char *debugAsciiString =
214 "string with
newlines and	tabs";
215
216 PKIX_PL_String *testString = NULL;
217
218 PKIX_TEST_STD_VARS();
219
220 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
221 PKIX_ESCASCII,
222 NULL,
223 50,
224 &testString,
225 plContext));
226
227 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(PKIX_ESCASCII,
228 "blah", 4, NULL, plContext));
229
230 PKIX_TEST_EXPECT_ERROR(PKIX_PL_Sprintf(&testString, plContext, NULL));
231
232 PKIX_TEST_EXPECT_ERROR(PKIX_PL_GetString(0, NULL, &testString, plContext));
233
234 PKIX_TEST_EXPECT_ERROR(PKIX_PL_GetString(0, "blah", 0, plContext));
235
236 /* ---------------------------- */
237 subTest("Unicode Error Handling");
238
239 /* &#x must be followed by 4 hexadecimal digits */
240 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
241 PKIX_ESCASCII,
242 "k;",
243 7,
244 &testString,
245 plContext));
246
247 /* &#x must be followed by 4 hexadecimal digits */
248 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
249 PKIX_ESCASCII,
250 "abc�",
251 8,
252 &testString,
253 plContext));
254
255 /* &#x must be between 00010000-0010FFFF */
256 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
257 PKIX_ESCASCII,
258 "�",
259 11,
260 &testString,
261 plContext));
262
263 /* &#x must be followed by 8 hexadecimal digits */
264 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
265 PKIX_ESCASCII,
266 "က",
267 10,
268 &testString,
269 plContext));
270
271 /* &#x must be followed by 8 hexadecimal digits */
272 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
273 PKIX_ESCASCII,
274 "m00;",
275 10,
276 &testString,
277 plContext));
278
279 /* Byte values D800-DFFF are reserved */
280 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
281 PKIX_ESCASCII,
282 "�",
283 7,
284 &testString,
285 plContext));
286
287 /* Can't use &#x for regular characters */
288 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
289 PKIX_ESCASCII,
290 "2",
291 7,
292 &testString,
293 plContext));
294
295 /* Can't use non-printable characters */
296 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
297 PKIX_ESCASCII,
298 "\xA1",
299 1,
300 &testString,
301 plContext));
302
303 /* Only legal \\ characters are \\, u and U */
304 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
305 PKIX_ESCASCII,
306 "&blah",
307 5,
308 &testString,
309 plContext));
310
311 /* Surrogate pairs must be legal */
312 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
313 PKIX_UTF16,
314 "\xd8\x00\x0\x66",
315 4,
316 &testString,
317 plContext));
318
319 /* Debugged EscASCII should not be accepted as EscASCII */
320 PKIX_TEST_EXPECT_ERROR(PKIX_PL_String_Create(
321 PKIX_ESCASCII,
322 debugAsciiString,
323 PL_strlen(debugAsciiString),
324 &testString,
325 plContext));
326 cleanup:
327
328 PKIX_TEST_RETURN();
329 }
330
331 static void
testDestroy(PKIX_PL_String * string)332 testDestroy(
333 PKIX_PL_String *string)
334 {
335 PKIX_TEST_STD_VARS();
336
337 PKIX_TEST_DECREF_BC(string);
338
339 cleanup:
340
341 PKIX_TEST_RETURN();
342 }
343
344 int
test_string(int argc,char * argv[])345 test_string(int argc, char *argv[])
346 {
347
348 PKIX_PL_String *testString[6] = { NULL };
349 PKIX_PL_String *testNullString = NULL;
350 PKIX_PL_String *testDebugAscii = NULL;
351 PKIX_PL_String *testEscAscii = NULL;
352 PKIX_PL_String *testUtf16 = NULL;
353 PKIX_PL_String *ampString = NULL;
354 unsigned char utf16Data[] = { 0x00, 0xA1, 0xD8, 0x00,
355 0xDC, 0x00, 0x0F, 0xFF,
356 0xDB, 0xC0, 0xDC, 0x01 };
357 PKIX_UInt32 i, size = 6;
358
359 char *plainText[6] = {
360 "string with\nnewlines and\ttabs",
361 "Not an escaped char: &#x0012;",
362 "Encode & with &amp; in ASCII",
363 "¡",
364 "&",
365 "string with\nnewlines and\ttabs"
366 };
367
368 PKIX_UInt32 actualMinorVersion;
369 PKIX_UInt32 j = 0;
370
371 PKIX_TEST_STD_VARS();
372
373 startTests("Strings");
374
375 PKIX_TEST_EXPECT_NO_ERROR(
376 PKIX_PL_NssContext_Create(0, PKIX_FALSE, NULL, &plContext));
377
378 subTest("PKIX_PL_String_Create <ascii format>");
379 for (i = 0; i < size; i++) {
380 testString[i] = NULL;
381 createString(&testString[i],
382 PKIX_ESCASCII,
383 plainText[i],
384 PL_strlen(plainText[i]));
385 }
386
387 subTest("PKIX_PL_String_Create <other formats>");
388 createStringOther(&testEscAscii,
389 &testUtf16,
390 &String,
391 &testDebugAscii,
392 &testNullString,
393 (PKIX_UInt32 *)utf16Data);
394
395 PKIX_TEST_EQ_HASH_TOSTR_DUP(testString[0],
396 testString[5],
397 testString[1],
398 plainText[0],
399 String,
400 PKIX_TRUE);
401
402 subTest("PKIX_PL_String_GetEncoded");
403 testGetEncoded(testEscAscii,
404 testString[0],
405 testDebugAscii,
406 testNullString,
407 (PKIX_UInt32 *)utf16Data);
408
409 subTest("PKIX_PL_Sprintf");
410 testSprintf();
411
412 subTest("PKIX_PL_String_Create <error_handling>");
413 testErrorHandling();
414
415 subTest("PKIX_PL_String_Destroy");
416 for (i = 0; i < size; i++) {
417 testDestroy(testString[i]);
418 }
419 testDestroy(testEscAscii);
420 testDestroy(testUtf16);
421 testDestroy(ampString);
422 testDestroy(testDebugAscii);
423 testDestroy(testNullString);
424
425 cleanup:
426
427 PKIX_Shutdown(plContext);
428
429 PKIX_TEST_RETURN();
430
431 endTests("String");
432
433 return (0);
434 }
435