blob: b0d3d6a8a62f317a8f570ffda013c0edc4f044de [file] [log] [blame]
Benny Prijono015cbfd2007-02-25 15:38:32 +00001/* $Id$ */
2/*
Benny Prijono844653c2008-12-23 17:27:53 +00003 * Copyright (C) 2008-2009 Teluu Inc. (http://www.teluu.com)
Benny Prijono32177c02008-06-20 22:44:47 +00004 * Copyright (C) 2003-2008 Benny Prijono <benny@prijono.org>
Benny Prijono015cbfd2007-02-25 15:38:32 +00005 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 */
20#include "test.h"
21#include <pjlib-util.h>
22#include <pjlib.h>
23
24
25#if INCLUDE_ENCRYPTION_TEST
26
27/*
28 * Encryption algorithm tests.
29 */
30#define THIS_FILE "encryption.c"
31
32
33/*
34 * SHA1 test from the original sha1.c source file.
35 */
36static char *sha1_test_data[] = {
37 "abc",
38 "abcdbcdecdefdefgefghfghighijhijkijkljklmklmnlmnomnopnopq",
39 "A million repetitions of 'a'"
40};
41static char *sha1_test_results[] = {
42 "A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D",
43 "84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1",
44 "34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F"
45};
46
47
48static void digest_to_hex(const pj_uint8_t digest[PJ_SHA1_DIGEST_SIZE],
49 char *output)
50{
51 int i,j;
52 char *c = output;
53
54 for (i = 0; i < PJ_SHA1_DIGEST_SIZE/4; i++) {
55 for (j = 0; j < 4; j++) {
56 sprintf(c,"%02X", digest[i*4+j]);
57 c += 2;
58 }
59 sprintf(c, " ");
60 c += 1;
61 }
62 *(c - 1) = '\0';
63}
64
65static int sha1_test1(void)
66{
Benny Prijono5cd804a2009-05-12 08:01:56 +000067 enum { MILLION = 1000000 };
Benny Prijono015cbfd2007-02-25 15:38:32 +000068 int k;
69 pj_sha1_context context;
70 pj_uint8_t digest[20];
71 char output[80];
Benny Prijono5cd804a2009-05-12 08:01:56 +000072 pj_pool_t *pool;
73 pj_uint8_t *block;
Benny Prijono015cbfd2007-02-25 15:38:32 +000074
75 PJ_LOG(3, (THIS_FILE, " SHA1 test vector 1 from sha1.c.."));
76
77 for (k = 0; k < 2; k++){
78 pj_sha1_init(&context);
79 pj_sha1_update(&context, (pj_uint8_t*)sha1_test_data[k],
80 pj_ansi_strlen(sha1_test_data[k]));
81 pj_sha1_final(&context, digest);
82 digest_to_hex(digest, output);
83
84 if (pj_ansi_strcmp(output, sha1_test_results[k])) {
85 PJ_LOG(3, (THIS_FILE, " incorrect hash result on k=%d", k));
86 return -10;
87 }
88 }
89
90 /* million 'a' vector we feed separately */
91 pj_sha1_init(&context);
Benny Prijono5cd804a2009-05-12 08:01:56 +000092 for (k = 0; k < MILLION; k++)
Benny Prijono015cbfd2007-02-25 15:38:32 +000093 pj_sha1_update(&context, (pj_uint8_t*)"a", 1);
94 pj_sha1_final(&context, digest);
95 digest_to_hex(digest, output);
96 if (strcmp(output, sha1_test_results[2])) {
97 PJ_LOG(3, (THIS_FILE, " incorrect hash result!"));
98 return -20;
99 }
100
Benny Prijono5cd804a2009-05-12 08:01:56 +0000101 /* million 'a' test, using block */
102 pool = pj_pool_create(mem, "sha1test", 256, 512, NULL);
103 block = (pj_uint8_t*)pj_pool_alloc(pool, MILLION);
104 pj_memset(block, 'a', MILLION);
105
106 pj_sha1_init(&context);
107 pj_sha1_update(&context, block, MILLION);
108 pj_sha1_final(&context, digest);
109 digest_to_hex(digest, output);
110 if (strcmp(output, sha1_test_results[2])) {
111 pj_pool_release(pool);
112 PJ_LOG(3, (THIS_FILE, " incorrect hash result for block update!"));
113 return -21;
114 }
115
116 /* verify that original buffer was not modified */
117 for (k=0; k<MILLION; ++k) {
118 if (block[k] != 'a') {
119 pj_pool_release(pool);
120 PJ_LOG(3, (THIS_FILE, " block was modified!"));
121 return -22;
122 }
123 }
124
125 pj_pool_release(pool);
126
Benny Prijono015cbfd2007-02-25 15:38:32 +0000127 /* success */
128 return(0);
129}
130
131
132/*
133 * SHA1 test from RFC 3174
134 */
135/*
136 * Define patterns for testing
137 */
138#define TEST1 "abc"
139#define TEST2a "abcdbcdecdefdefgefghfghighijhi"
140#define TEST2b "jkijkljklmklmnlmnomnopnopq"
141#define TEST2 TEST2a TEST2b
142#define TEST3 "a"
143#define TEST4a "01234567012345670123456701234567"
144#define TEST4b "01234567012345670123456701234567"
145 /* an exact multiple of 512 bits */
146#define TEST4 TEST4a TEST4b
147
148static char *testarray[4] =
149{
150 TEST1,
151 TEST2,
152 TEST3,
153 TEST4
154};
155static int repeatcount[4] = { 1, 1, 1000000, 10 };
156static char *resultarray[4] =
157{
158 "A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D",
159 "84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1",
160 "34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F",
161 "DEA356A2 CDDD90C7 A7ECEDC5 EBB56393 4F460452"
162};
163
164static int sha1_test2(void)
165{
166 pj_sha1_context sha;
167 int i;
168 pj_uint8_t digest[20];
169 char char_digest[64];
170
171 PJ_LOG(3, (THIS_FILE, " SHA1 test vector 2 from rfc 3174.."));
172
173 for(i = 0; i < 4; ++i) {
174 int j;
175
176 pj_sha1_init(&sha);
177
178 for(j = 0; j < repeatcount[i]; ++j) {
179 pj_sha1_update(&sha,
180 (const pj_uint8_t *) testarray[i],
181 pj_ansi_strlen(testarray[i]));
182 }
183
184 pj_sha1_final(&sha, digest);
185
186 digest_to_hex(digest, char_digest);
187 if (pj_ansi_strcmp(char_digest, resultarray[i])) {
188 PJ_LOG(3, (THIS_FILE, " digest mismatch in test %d", i));
189 return -40;
190 }
191 }
192
193 return 0;
194}
195
196
197/*
198 * HMAC-MD5 and HMAC-SHA1 test vectors from RFC 2202
199 */
200struct rfc2202_test
201{
202 char *key;
203 unsigned key_len;
204 char *input;
205 unsigned input_len;
206 char *md5_digest;
207 char *sha1_digest;
208};
209
210
211struct rfc2202_test rfc2202_test_vector[] =
212{
213 {
214 "\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b",
215 16,
216 "Hi There",
217 8,
218 "\x92\x94\x72\x7a\x36\x38\xbb\x1c\x13\xf4\x8e\xf8\x15\x8b\xfc\x9d",
219 NULL
220 },
221 {
222 "\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b"
223 "\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b",
224 20,
225 "Hi There",
226 8,
227 NULL,
228 "\xb6\x17\x31\x86\x55\x05\x72\x64\xe2\x8b\xc0\xb6\xfb\x37\x8c\x8e\xf1\x46\xbe\x00"
229 },
230 {
231 "Jefe",
232 4,
233 "what do ya want for nothing?",
234 28,
235 "\x75\x0c\x78\x3e\x6a\xb0\xb5\x03\xea\xa8\x6e\x31\x0a\x5d\xb7\x38",
236 "\xef\xfc\xdf\x6a\xe5\xeb\x2f\xa2\xd2\x74\x16\xd5\xf1\x84\xdf\x9c\x25\x9a\x7c\x79"
237 },
238 {
239 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
240 "\xaa\xaa\xaa\xaa\xaa\xaa",
241 16,
242 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
243 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
244 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
245 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
246 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd",
247 50,
248 "\x56\xbe\x34\x52\x1d\x14\x4c\x88\xdb\xb8\xc7\x33\xf0\xe8\xb3\xf6",
249 NULL
250 },
251 {
252 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
253 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa",
254 20,
255 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
256 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
257 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
258 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
259 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd",
260 50,
261 NULL,
262 "\x12\x5d\x73\x42\xb9\xac\x11\xcd\x91\xa3\x9a\xf4\x8a\xa1\x7b\x4f\x63\xf1\x75\xd3"
263 },
264 {
265 "\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19",
266 25,
267 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd"
268 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd"
269 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd"
270 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd"
271 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd",
272 50,
273 "\x69\x7e\xaf\x0a\xca\x3a\x3a\xea\x3a\x75\x16\x47\x46\xff\xaa\x79",
274 "\x4c\x90\x07\xf4\x02\x62\x50\xc6\xbc\x84\x14\xf9\xbf\x50\xc8\x6c\x2d\x72\x35\xda"
275 },
276 {
277 "\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c"
278 "\x0c\x0c\x0c\x0c\x0c\x0c",
279 16,
280 "Test With Truncation",
281 20,
282 "\x56\x46\x1e\xf2\x34\x2e\xdc\x00\xf9\xba\xb9\x95\x69\x0e\xfd\x4c",
283 NULL
284 },
285 {
286 "\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c"
287 "\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c",
288 20,
289 "Test With Truncation",
290 20,
291 NULL,
292 "\x4c\x1a\x03\x42\x4b\x55\xe0\x7f\xe7\xf2\x7b\xe1\xd5\x8b\xb9\x32\x4a\x9a\x5a\x04"
293 },
294 {
295 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
296 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
297 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
298 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
299 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
300 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
301 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
302 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa",
303 80,
304 "Test Using Larger Than Block-Size Key - Hash Key First",
305 54,
306 "\x6b\x1a\xb7\xfe\x4b\xd7\xbf\x8f\x0b\x62\xe6\xce\x61\xb9\xd0\xcd",
307 "\xaa\x4a\xe5\xe1\x52\x72\xd0\x0e\x95\x70\x56\x37\xce\x8a\x3b\x55\xed\x40\x21\x12"
308 },
309 {
310 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
311 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
312 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
313 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
314 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
315 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
316 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
317 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa",
318 80,
319 "Test Using Larger Than Block-Size Key and Larger Than One Block-Size Data",
320 73,
321 "\x6f\x63\x0f\xad\x67\xcd\xa0\xee\x1f\xb1\xf5\x62\xdb\x3a\xa5\x3e",
322 "\xe8\xe9\x9d\x0f\x45\x23\x7d\x78\x6d\x6b\xba\xa7\x96\x5c\x78\x08\xbb\xff\x1a\x91"
323 }
324};
325
326
327static int rfc2202_test(void)
328{
329 unsigned i;
330
331 PJ_LOG(3, (THIS_FILE, " verifying test vectors from rfc 2202.."));
332
333 /* Verify that test vectors are valid */
334 for (i=0; i<PJ_ARRAY_SIZE(rfc2202_test_vector); ++i) {
335 PJ_ASSERT_RETURN(pj_ansi_strlen(rfc2202_test_vector[i].input) ==
336 rfc2202_test_vector[i].input_len, -50);
337 PJ_ASSERT_RETURN(pj_ansi_strlen(rfc2202_test_vector[i].key) ==
338 rfc2202_test_vector[i].key_len, -52);
339 PJ_ASSERT_RETURN(rfc2202_test_vector[i].md5_digest==NULL ||
340 pj_ansi_strlen(rfc2202_test_vector[i].md5_digest)<=16,
341 -54);
342 PJ_ASSERT_RETURN(rfc2202_test_vector[i].sha1_digest==NULL ||
343 pj_ansi_strlen(rfc2202_test_vector[i].sha1_digest)<=20,
344 -56);
345 }
346
347 /* Test HMAC-MD5 */
348 PJ_LOG(3, (THIS_FILE, " HMAC-MD5 test vectors from rfc 2202.."));
349 for (i=0; i<PJ_ARRAY_SIZE(rfc2202_test_vector); ++i) {
350 pj_uint8_t digest_buf[18], *digest;
351
352 if (rfc2202_test_vector[i].md5_digest == NULL)
353 continue;
354
355 digest_buf[0] = '\0';
356 digest_buf[17] = '\0';
357
358 digest = digest_buf+1;
359
360 pj_hmac_md5((pj_uint8_t*)rfc2202_test_vector[i].input,
361 rfc2202_test_vector[i].input_len,
362 (pj_uint8_t*)rfc2202_test_vector[i].key,
363 rfc2202_test_vector[i].key_len,
364 digest);
365
366 /* Check for overwrites */
367 if (digest_buf[0] != '\0' || digest_buf[17] != '\0') {
368 PJ_LOG(3, (THIS_FILE, " error: overwriting outside buffer on test %d", i));
369 return -60;
370 }
371
372 /* Compare digest */
373 if (pj_memcmp(rfc2202_test_vector[i].md5_digest, digest, 16)) {
374 PJ_LOG(3, (THIS_FILE, " error: digest mismatch on test %d", i));
375 return -65;
376 }
377 }
378
379 /* Test HMAC-SHA1 */
380 PJ_LOG(3, (THIS_FILE, " HMAC-SHA1 test vectors from rfc 2202.."));
381 for (i=0; i<PJ_ARRAY_SIZE(rfc2202_test_vector); ++i) {
382 pj_uint8_t digest_buf[22], *digest;
383
384 if (rfc2202_test_vector[i].sha1_digest == NULL)
385 continue;
386
387 digest_buf[0] = '\0';
388 digest_buf[21] = '\0';
389
390 digest = digest_buf+1;
391
392 pj_hmac_sha1((pj_uint8_t*)rfc2202_test_vector[i].input,
393 rfc2202_test_vector[i].input_len,
394 (pj_uint8_t*)rfc2202_test_vector[i].key,
395 rfc2202_test_vector[i].key_len,
396 digest);
397
398 /* Check for overwrites */
399 if (digest_buf[0] != '\0' || digest_buf[21] != '\0') {
400 PJ_LOG(3, (THIS_FILE, " error: overwriting outside buffer on test %d", i));
401 return -70;
402 }
403
404 /* Compare digest */
405 if (pj_memcmp(rfc2202_test_vector[i].sha1_digest, digest, 20)) {
406 PJ_LOG(3, (THIS_FILE, " error: digest mismatch on test %d", i));
407 return -75;
408 }
409 }
410
411
412 /* Success */
413 return 0;
414}
415
Benny Prijono3dc1f402007-02-26 02:33:14 +0000416/* CRC32 test data, generated from crc32 test on a Linux box */
Benny Prijonoa1e69682007-05-11 15:14:34 +0000417struct crc32_test_t
Benny Prijono3dc1f402007-02-26 02:33:14 +0000418{
419 char *input;
420 pj_uint32_t crc;
421} crc32_test_data[] =
422{
423 {
424 "",
425 0x0
426 },
427 {
428 "Hello World",
429 0x4a17b156
430 },
431 {
432 /* Something read from /dev/random */
433 "\x21\x21\x98\x10\x62\x59\xbc\x58\x42\x24\xe5\xf3\x92\x0a\x68\x3c\xa7\x67\x73\xc3",
434 0x506693be
435 },
436 {
437 "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
438 0xcab11777
439 },
440 {
441 "123456789",
442 0xCBF43926
443 }
444};
445
446/*
447 * CRC32 test
448 */
449static int crc32_test(void)
450{
451 unsigned i;
452
453 PJ_LOG(3, (THIS_FILE, " crc32 test.."));
454
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000455 /* testing pj_crc32_calc */
Benny Prijono3dc1f402007-02-26 02:33:14 +0000456 for (i=0; i<PJ_ARRAY_SIZE(crc32_test_data); ++i) {
457 pj_uint32_t crc;
458
459 crc = pj_crc32_calc((pj_uint8_t*)crc32_test_data[i].input,
460 pj_ansi_strlen(crc32_test_data[i].input));
461 if (crc != crc32_test_data[i].crc) {
462 PJ_LOG(3,(THIS_FILE, " error: crc mismatch on test %d", i));
463 return -80;
464 }
465 }
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000466
467 /* testing incremental CRC32 calculation */
468 for (i=0; i<PJ_ARRAY_SIZE(crc32_test_data); ++i) {
469 pj_crc32_context ctx;
470 pj_uint32_t crc0, crc1;
471 unsigned len;
472
473 len = pj_ansi_strlen(crc32_test_data[i].input);
474 crc0 = pj_crc32_calc((pj_uint8_t*)crc32_test_data[i].input, len);
475
476 pj_crc32_init(&ctx);
477 pj_crc32_update(&ctx, (pj_uint8_t*)crc32_test_data[i].input,
478 len / 2);
479
480 if (len/2 > 0) {
481 pj_crc32_update(&ctx, (pj_uint8_t*)crc32_test_data[i].input + len/2,
482 len - len/2);
483 }
484
485 crc1 = pj_crc32_final(&ctx);
486
487 if (crc0 != crc1) {
488 PJ_LOG(3,(THIS_FILE,
489 " error: crc algorithm error on test %d", i));
490 return -85;
491 }
492
493 }
Benny Prijono3dc1f402007-02-26 02:33:14 +0000494 return 0;
495}
496
Benny Prijono91430b22010-10-26 23:53:28 +0000497enum
498{
499 ENCODE = 1,
500 DECODE = 2,
501 ENCODE_DECODE = 3
502};
Benny Prijono015cbfd2007-02-25 15:38:32 +0000503
Benny Prijono7977f9f2007-10-10 11:37:56 +0000504/*
505 * Base64 test vectors (RFC 4648)
506 */
507static struct base64_test_vec
508{
509 const char *base256;
510 const char *base64;
Benny Prijono91430b22010-10-26 23:53:28 +0000511 unsigned flag;
Benny Prijono7977f9f2007-10-10 11:37:56 +0000512} base64_test_vec[] =
513{
514 {
515 "",
Benny Prijono91430b22010-10-26 23:53:28 +0000516 "",
517 ENCODE_DECODE
Benny Prijono7977f9f2007-10-10 11:37:56 +0000518 },
519 {
520 "f",
Benny Prijono91430b22010-10-26 23:53:28 +0000521 "Zg==",
522 ENCODE_DECODE
Benny Prijono7977f9f2007-10-10 11:37:56 +0000523 },
524 {
525 "fo",
Benny Prijono91430b22010-10-26 23:53:28 +0000526 "Zm8=",
527 ENCODE_DECODE
Benny Prijono7977f9f2007-10-10 11:37:56 +0000528 },
529 {
530 "foo",
Benny Prijono91430b22010-10-26 23:53:28 +0000531 "Zm9v",
532 ENCODE_DECODE
Benny Prijono7977f9f2007-10-10 11:37:56 +0000533 },
534 {
535 "foob",
Benny Prijono91430b22010-10-26 23:53:28 +0000536 "Zm9vYg==",
537 ENCODE_DECODE
Benny Prijono7977f9f2007-10-10 11:37:56 +0000538 },
539 {
540 "fooba",
541 "Zm9vYmE=",
Benny Prijono91430b22010-10-26 23:53:28 +0000542 ENCODE_DECODE
Benny Prijono7977f9f2007-10-10 11:37:56 +0000543 },
544 {
545 "foobar",
Benny Prijono91430b22010-10-26 23:53:28 +0000546 "Zm9vYmFy",
547 ENCODE_DECODE
Benny Prijono7977f9f2007-10-10 11:37:56 +0000548 },
549 {
550 "\x14\xfb\x9c\x03\xd9\x7e",
Benny Prijono91430b22010-10-26 23:53:28 +0000551 "FPucA9l+",
552 ENCODE_DECODE
Benny Prijono7977f9f2007-10-10 11:37:56 +0000553 },
554 {
555 "\x14\xfb\x9c\x03\xd9",
Benny Prijono91430b22010-10-26 23:53:28 +0000556 "FPucA9k=",
557 ENCODE_DECODE
Benny Prijono7977f9f2007-10-10 11:37:56 +0000558 },
559 {
560 "\x14\xfb\x9c\x03",
Benny Prijono91430b22010-10-26 23:53:28 +0000561 "FPucAw==",
562 ENCODE_DECODE
563 },
564 /* with whitespaces */
565 {
566 "foobar",
567 "Zm9v\r\nYmFy",
568 DECODE
569 },
570 {
571 "foobar",
572 "\nZ\r\nm 9\tv\nYm\nF\ny\n",
573 DECODE
574 },
Benny Prijono7977f9f2007-10-10 11:37:56 +0000575};
576
577
578static int base64_test(void)
579{
580 unsigned i;
581 char output[80];
582 pj_status_t rc;
583
584 PJ_LOG(3, (THIS_FILE, " base64 test.."));
585
586 for (i=0; i<PJ_ARRAY_SIZE(base64_test_vec); ++i) {
Benny Prijono7977f9f2007-10-10 11:37:56 +0000587 pj_str_t input;
Benny Prijono91430b22010-10-26 23:53:28 +0000588 int out_len;
Benny Prijono7977f9f2007-10-10 11:37:56 +0000589
Benny Prijono91430b22010-10-26 23:53:28 +0000590 /* Encode test */
591 if (base64_test_vec[i].flag & ENCODE) {
592 out_len = sizeof(output);
593 rc = pj_base64_encode((pj_uint8_t*)base64_test_vec[i].base256,
594 strlen(base64_test_vec[i].base256),
595 output, &out_len);
596 if (rc != PJ_SUCCESS)
597 return -90;
Benny Prijono7977f9f2007-10-10 11:37:56 +0000598
Benny Prijono91430b22010-10-26 23:53:28 +0000599 if (out_len != (int)strlen(base64_test_vec[i].base64))
600 return -91;
Benny Prijono7977f9f2007-10-10 11:37:56 +0000601
Benny Prijono91430b22010-10-26 23:53:28 +0000602 output[out_len] = '\0';
603 if (strcmp(output, base64_test_vec[i].base64) != 0)
604 return -92;
605 }
Benny Prijono7977f9f2007-10-10 11:37:56 +0000606
607 /* Decode test */
Benny Prijono91430b22010-10-26 23:53:28 +0000608 if (base64_test_vec[i].flag & DECODE) {
609 out_len = sizeof(output);
610 input.ptr = (char*)base64_test_vec[i].base64;
611 input.slen = strlen(base64_test_vec[i].base64);
612 rc = pj_base64_decode(&input, (pj_uint8_t*)output, &out_len);
613 if (rc != PJ_SUCCESS)
614 return -95;
Benny Prijono7977f9f2007-10-10 11:37:56 +0000615
Benny Prijono91430b22010-10-26 23:53:28 +0000616 if (out_len != (int)strlen(base64_test_vec[i].base256))
617 return -96;
Benny Prijono7977f9f2007-10-10 11:37:56 +0000618
Benny Prijono91430b22010-10-26 23:53:28 +0000619 output[out_len] = '\0';
Benny Prijono7977f9f2007-10-10 11:37:56 +0000620
Benny Prijono91430b22010-10-26 23:53:28 +0000621 if (strcmp(output, base64_test_vec[i].base256) != 0)
622 return -97;
623 }
Benny Prijono7977f9f2007-10-10 11:37:56 +0000624 }
625
626 return 0;
627}
628
629
Benny Prijono015cbfd2007-02-25 15:38:32 +0000630int encryption_test()
631{
632 int rc;
633
Benny Prijono7977f9f2007-10-10 11:37:56 +0000634 rc = base64_test();
635 if (rc != 0)
636 return rc;
637
Benny Prijono015cbfd2007-02-25 15:38:32 +0000638 rc = sha1_test1();
639 if (rc != 0)
640 return rc;
641
642 rc = sha1_test2();
643 if (rc != 0)
644 return rc;
645
646 rc = rfc2202_test();
647 if (rc != 0)
648 return rc;
649
Benny Prijono3dc1f402007-02-26 02:33:14 +0000650 rc = crc32_test();
651 if (rc != 0)
652 return rc;
653
Benny Prijono015cbfd2007-02-25 15:38:32 +0000654 return 0;
655}
656
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000657static void crc32_update(pj_crc32_context *c, const pj_uint8_t *data,
658 pj_size_t nbytes)
659{
660 pj_crc32_update(c, data, nbytes);
661}
662
663static void crc32_final(pj_crc32_context *ctx, pj_uint32_t *digest)
664{
665 *digest = pj_crc32_final(ctx);
666}
667
668int encryption_benchmark()
669{
670 pj_pool_t *pool;
671 pj_uint8_t *input;
672 union {
673 pj_md5_context md5_context;
674 pj_sha1_context sha1_context;
675 } context;
676 pj_uint8_t digest[32];
677 pj_size_t input_len;
678 struct algorithm
679 {
680 const char *name;
681 void (*init_context)(void*);
682 void (*update)(void*, const pj_uint8_t*, unsigned);
683 void (*final)(void*, void*);
684 pj_uint32_t t;
685 } algorithms[] =
686 {
687 {
688 "MD5 ",
Benny Prijonof83dc1d2007-02-28 14:35:50 +0000689 (void (*)(void*))&pj_md5_init,
690 (void (*)(void*, const pj_uint8_t*, unsigned))&pj_md5_update,
691 (void (*)(void*, void*))&pj_md5_final
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000692 },
693 {
694 "SHA1 ",
Benny Prijonof83dc1d2007-02-28 14:35:50 +0000695 (void (*)(void*))&pj_sha1_init,
696 (void (*)(void*, const pj_uint8_t*, unsigned))&pj_sha1_update,
697 (void (*)(void*, void*))&pj_sha1_final
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000698 },
699 {
700 "CRC32",
Benny Prijonof83dc1d2007-02-28 14:35:50 +0000701 (void (*)(void*))&pj_crc32_init,
702 (void (*)(void*, const pj_uint8_t*, unsigned))&crc32_update,
703 (void (*)(void*, void*))&crc32_final
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000704 }
705 };
706#if defined(PJ_DEBUG) && PJ_DEBUG!=0
707 enum { LOOP = 1000 };
708#else
709 enum { LOOP = 10000 };
710#endif
711 unsigned i;
712 double total_len;
713
714 input_len = 2048;
715 total_len = input_len * LOOP;
716 pool = pj_pool_create(mem, "enc", input_len+256, 0, NULL);
717 if (!pool)
718 return PJ_ENOMEM;
719
Benny Prijonoa1e69682007-05-11 15:14:34 +0000720 input = (pj_uint8_t*)pj_pool_alloc(pool, input_len);
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000721 pj_memset(input, '\xaa', input_len);
722
723 PJ_LOG(3, (THIS_FILE, " feeding %d Mbytes of data",
724 (unsigned)(total_len/1024/1024)));
725
726 /* Dry run */
727 for (i=0; i<PJ_ARRAY_SIZE(algorithms); ++i) {
728 algorithms[i].init_context(&context);
729 algorithms[i].update(&context, input, input_len);
730 algorithms[i].final(&context, digest);
731 }
732
733 /* Run */
734 for (i=0; i<PJ_ARRAY_SIZE(algorithms); ++i) {
735 int j;
736 pj_timestamp t1, t2;
737
738 pj_get_timestamp(&t1);
739 algorithms[i].init_context(&context);
740 for (j=0; j<LOOP; ++j) {
741 algorithms[i].update(&context, input, input_len);
742 }
743 algorithms[i].final(&context, digest);
744 pj_get_timestamp(&t2);
745
746 algorithms[i].t = pj_elapsed_usec(&t1, &t2);
747 }
748
749 /* Results */
750 for (i=0; i<PJ_ARRAY_SIZE(algorithms); ++i) {
751 double bytes;
752
753 bytes = (total_len * 1000000 / algorithms[i].t);
754 PJ_LOG(3, (THIS_FILE, " %s:%8d usec (%3d.%03d Mbytes/sec)",
755 algorithms[i].name, algorithms[i].t,
756 (unsigned)(bytes / 1024 / 1024),
757 ((unsigned)(bytes) % (1024 * 1024)) / 1024));
758 }
759
760 return 0;
761}
762
Benny Prijono015cbfd2007-02-25 15:38:32 +0000763
764
765#endif /* INCLUDE_ENCRYPTION_TEST */
766