blob: c31bea95e0e12221abef03ebdce8776c38a4f253 [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{
67 int k;
68 pj_sha1_context context;
69 pj_uint8_t digest[20];
70 char output[80];
71
72 PJ_LOG(3, (THIS_FILE, " SHA1 test vector 1 from sha1.c.."));
73
74 for (k = 0; k < 2; k++){
75 pj_sha1_init(&context);
76 pj_sha1_update(&context, (pj_uint8_t*)sha1_test_data[k],
77 pj_ansi_strlen(sha1_test_data[k]));
78 pj_sha1_final(&context, digest);
79 digest_to_hex(digest, output);
80
81 if (pj_ansi_strcmp(output, sha1_test_results[k])) {
82 PJ_LOG(3, (THIS_FILE, " incorrect hash result on k=%d", k));
83 return -10;
84 }
85 }
86
87 /* million 'a' vector we feed separately */
88 pj_sha1_init(&context);
89 for (k = 0; k < 1000000; k++)
90 pj_sha1_update(&context, (pj_uint8_t*)"a", 1);
91 pj_sha1_final(&context, digest);
92 digest_to_hex(digest, output);
93 if (strcmp(output, sha1_test_results[2])) {
94 PJ_LOG(3, (THIS_FILE, " incorrect hash result!"));
95 return -20;
96 }
97
98 /* success */
99 return(0);
100}
101
102
103/*
104 * SHA1 test from RFC 3174
105 */
106/*
107 * Define patterns for testing
108 */
109#define TEST1 "abc"
110#define TEST2a "abcdbcdecdefdefgefghfghighijhi"
111#define TEST2b "jkijkljklmklmnlmnomnopnopq"
112#define TEST2 TEST2a TEST2b
113#define TEST3 "a"
114#define TEST4a "01234567012345670123456701234567"
115#define TEST4b "01234567012345670123456701234567"
116 /* an exact multiple of 512 bits */
117#define TEST4 TEST4a TEST4b
118
119static char *testarray[4] =
120{
121 TEST1,
122 TEST2,
123 TEST3,
124 TEST4
125};
126static int repeatcount[4] = { 1, 1, 1000000, 10 };
127static char *resultarray[4] =
128{
129 "A9993E36 4706816A BA3E2571 7850C26C 9CD0D89D",
130 "84983E44 1C3BD26E BAAE4AA1 F95129E5 E54670F1",
131 "34AA973C D4C4DAA4 F61EEB2B DBAD2731 6534016F",
132 "DEA356A2 CDDD90C7 A7ECEDC5 EBB56393 4F460452"
133};
134
135static int sha1_test2(void)
136{
137 pj_sha1_context sha;
138 int i;
139 pj_uint8_t digest[20];
140 char char_digest[64];
141
142 PJ_LOG(3, (THIS_FILE, " SHA1 test vector 2 from rfc 3174.."));
143
144 for(i = 0; i < 4; ++i) {
145 int j;
146
147 pj_sha1_init(&sha);
148
149 for(j = 0; j < repeatcount[i]; ++j) {
150 pj_sha1_update(&sha,
151 (const pj_uint8_t *) testarray[i],
152 pj_ansi_strlen(testarray[i]));
153 }
154
155 pj_sha1_final(&sha, digest);
156
157 digest_to_hex(digest, char_digest);
158 if (pj_ansi_strcmp(char_digest, resultarray[i])) {
159 PJ_LOG(3, (THIS_FILE, " digest mismatch in test %d", i));
160 return -40;
161 }
162 }
163
164 return 0;
165}
166
167
168/*
169 * HMAC-MD5 and HMAC-SHA1 test vectors from RFC 2202
170 */
171struct rfc2202_test
172{
173 char *key;
174 unsigned key_len;
175 char *input;
176 unsigned input_len;
177 char *md5_digest;
178 char *sha1_digest;
179};
180
181
182struct rfc2202_test rfc2202_test_vector[] =
183{
184 {
185 "\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b",
186 16,
187 "Hi There",
188 8,
189 "\x92\x94\x72\x7a\x36\x38\xbb\x1c\x13\xf4\x8e\xf8\x15\x8b\xfc\x9d",
190 NULL
191 },
192 {
193 "\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b"
194 "\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b\x0b",
195 20,
196 "Hi There",
197 8,
198 NULL,
199 "\xb6\x17\x31\x86\x55\x05\x72\x64\xe2\x8b\xc0\xb6\xfb\x37\x8c\x8e\xf1\x46\xbe\x00"
200 },
201 {
202 "Jefe",
203 4,
204 "what do ya want for nothing?",
205 28,
206 "\x75\x0c\x78\x3e\x6a\xb0\xb5\x03\xea\xa8\x6e\x31\x0a\x5d\xb7\x38",
207 "\xef\xfc\xdf\x6a\xe5\xeb\x2f\xa2\xd2\x74\x16\xd5\xf1\x84\xdf\x9c\x25\x9a\x7c\x79"
208 },
209 {
210 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
211 "\xaa\xaa\xaa\xaa\xaa\xaa",
212 16,
213 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
214 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
215 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
216 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
217 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd",
218 50,
219 "\x56\xbe\x34\x52\x1d\x14\x4c\x88\xdb\xb8\xc7\x33\xf0\xe8\xb3\xf6",
220 NULL
221 },
222 {
223 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
224 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa",
225 20,
226 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
227 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
228 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
229 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd"
230 "\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd\xdd",
231 50,
232 NULL,
233 "\x12\x5d\x73\x42\xb9\xac\x11\xcd\x91\xa3\x9a\xf4\x8a\xa1\x7b\x4f\x63\xf1\x75\xd3"
234 },
235 {
236 "\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",
237 25,
238 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd"
239 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd"
240 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd"
241 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd"
242 "\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd\xcd",
243 50,
244 "\x69\x7e\xaf\x0a\xca\x3a\x3a\xea\x3a\x75\x16\x47\x46\xff\xaa\x79",
245 "\x4c\x90\x07\xf4\x02\x62\x50\xc6\xbc\x84\x14\xf9\xbf\x50\xc8\x6c\x2d\x72\x35\xda"
246 },
247 {
248 "\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c"
249 "\x0c\x0c\x0c\x0c\x0c\x0c",
250 16,
251 "Test With Truncation",
252 20,
253 "\x56\x46\x1e\xf2\x34\x2e\xdc\x00\xf9\xba\xb9\x95\x69\x0e\xfd\x4c",
254 NULL
255 },
256 {
257 "\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c"
258 "\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c\x0c",
259 20,
260 "Test With Truncation",
261 20,
262 NULL,
263 "\x4c\x1a\x03\x42\x4b\x55\xe0\x7f\xe7\xf2\x7b\xe1\xd5\x8b\xb9\x32\x4a\x9a\x5a\x04"
264 },
265 {
266 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
267 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
268 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
269 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
270 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
271 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
272 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
273 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa",
274 80,
275 "Test Using Larger Than Block-Size Key - Hash Key First",
276 54,
277 "\x6b\x1a\xb7\xfe\x4b\xd7\xbf\x8f\x0b\x62\xe6\xce\x61\xb9\xd0\xcd",
278 "\xaa\x4a\xe5\xe1\x52\x72\xd0\x0e\x95\x70\x56\x37\xce\x8a\x3b\x55\xed\x40\x21\x12"
279 },
280 {
281 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
282 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
283 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
284 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
285 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
286 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
287 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa"
288 "\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa\xaa",
289 80,
290 "Test Using Larger Than Block-Size Key and Larger Than One Block-Size Data",
291 73,
292 "\x6f\x63\x0f\xad\x67\xcd\xa0\xee\x1f\xb1\xf5\x62\xdb\x3a\xa5\x3e",
293 "\xe8\xe9\x9d\x0f\x45\x23\x7d\x78\x6d\x6b\xba\xa7\x96\x5c\x78\x08\xbb\xff\x1a\x91"
294 }
295};
296
297
298static int rfc2202_test(void)
299{
300 unsigned i;
301
302 PJ_LOG(3, (THIS_FILE, " verifying test vectors from rfc 2202.."));
303
304 /* Verify that test vectors are valid */
305 for (i=0; i<PJ_ARRAY_SIZE(rfc2202_test_vector); ++i) {
306 PJ_ASSERT_RETURN(pj_ansi_strlen(rfc2202_test_vector[i].input) ==
307 rfc2202_test_vector[i].input_len, -50);
308 PJ_ASSERT_RETURN(pj_ansi_strlen(rfc2202_test_vector[i].key) ==
309 rfc2202_test_vector[i].key_len, -52);
310 PJ_ASSERT_RETURN(rfc2202_test_vector[i].md5_digest==NULL ||
311 pj_ansi_strlen(rfc2202_test_vector[i].md5_digest)<=16,
312 -54);
313 PJ_ASSERT_RETURN(rfc2202_test_vector[i].sha1_digest==NULL ||
314 pj_ansi_strlen(rfc2202_test_vector[i].sha1_digest)<=20,
315 -56);
316 }
317
318 /* Test HMAC-MD5 */
319 PJ_LOG(3, (THIS_FILE, " HMAC-MD5 test vectors from rfc 2202.."));
320 for (i=0; i<PJ_ARRAY_SIZE(rfc2202_test_vector); ++i) {
321 pj_uint8_t digest_buf[18], *digest;
322
323 if (rfc2202_test_vector[i].md5_digest == NULL)
324 continue;
325
326 digest_buf[0] = '\0';
327 digest_buf[17] = '\0';
328
329 digest = digest_buf+1;
330
331 pj_hmac_md5((pj_uint8_t*)rfc2202_test_vector[i].input,
332 rfc2202_test_vector[i].input_len,
333 (pj_uint8_t*)rfc2202_test_vector[i].key,
334 rfc2202_test_vector[i].key_len,
335 digest);
336
337 /* Check for overwrites */
338 if (digest_buf[0] != '\0' || digest_buf[17] != '\0') {
339 PJ_LOG(3, (THIS_FILE, " error: overwriting outside buffer on test %d", i));
340 return -60;
341 }
342
343 /* Compare digest */
344 if (pj_memcmp(rfc2202_test_vector[i].md5_digest, digest, 16)) {
345 PJ_LOG(3, (THIS_FILE, " error: digest mismatch on test %d", i));
346 return -65;
347 }
348 }
349
350 /* Test HMAC-SHA1 */
351 PJ_LOG(3, (THIS_FILE, " HMAC-SHA1 test vectors from rfc 2202.."));
352 for (i=0; i<PJ_ARRAY_SIZE(rfc2202_test_vector); ++i) {
353 pj_uint8_t digest_buf[22], *digest;
354
355 if (rfc2202_test_vector[i].sha1_digest == NULL)
356 continue;
357
358 digest_buf[0] = '\0';
359 digest_buf[21] = '\0';
360
361 digest = digest_buf+1;
362
363 pj_hmac_sha1((pj_uint8_t*)rfc2202_test_vector[i].input,
364 rfc2202_test_vector[i].input_len,
365 (pj_uint8_t*)rfc2202_test_vector[i].key,
366 rfc2202_test_vector[i].key_len,
367 digest);
368
369 /* Check for overwrites */
370 if (digest_buf[0] != '\0' || digest_buf[21] != '\0') {
371 PJ_LOG(3, (THIS_FILE, " error: overwriting outside buffer on test %d", i));
372 return -70;
373 }
374
375 /* Compare digest */
376 if (pj_memcmp(rfc2202_test_vector[i].sha1_digest, digest, 20)) {
377 PJ_LOG(3, (THIS_FILE, " error: digest mismatch on test %d", i));
378 return -75;
379 }
380 }
381
382
383 /* Success */
384 return 0;
385}
386
Benny Prijono3dc1f402007-02-26 02:33:14 +0000387/* CRC32 test data, generated from crc32 test on a Linux box */
Benny Prijonoa1e69682007-05-11 15:14:34 +0000388struct crc32_test_t
Benny Prijono3dc1f402007-02-26 02:33:14 +0000389{
390 char *input;
391 pj_uint32_t crc;
392} crc32_test_data[] =
393{
394 {
395 "",
396 0x0
397 },
398 {
399 "Hello World",
400 0x4a17b156
401 },
402 {
403 /* Something read from /dev/random */
404 "\x21\x21\x98\x10\x62\x59\xbc\x58\x42\x24\xe5\xf3\x92\x0a\x68\x3c\xa7\x67\x73\xc3",
405 0x506693be
406 },
407 {
408 "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa",
409 0xcab11777
410 },
411 {
412 "123456789",
413 0xCBF43926
414 }
415};
416
417/*
418 * CRC32 test
419 */
420static int crc32_test(void)
421{
422 unsigned i;
423
424 PJ_LOG(3, (THIS_FILE, " crc32 test.."));
425
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000426 /* testing pj_crc32_calc */
Benny Prijono3dc1f402007-02-26 02:33:14 +0000427 for (i=0; i<PJ_ARRAY_SIZE(crc32_test_data); ++i) {
428 pj_uint32_t crc;
429
430 crc = pj_crc32_calc((pj_uint8_t*)crc32_test_data[i].input,
431 pj_ansi_strlen(crc32_test_data[i].input));
432 if (crc != crc32_test_data[i].crc) {
433 PJ_LOG(3,(THIS_FILE, " error: crc mismatch on test %d", i));
434 return -80;
435 }
436 }
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000437
438 /* testing incremental CRC32 calculation */
439 for (i=0; i<PJ_ARRAY_SIZE(crc32_test_data); ++i) {
440 pj_crc32_context ctx;
441 pj_uint32_t crc0, crc1;
442 unsigned len;
443
444 len = pj_ansi_strlen(crc32_test_data[i].input);
445 crc0 = pj_crc32_calc((pj_uint8_t*)crc32_test_data[i].input, len);
446
447 pj_crc32_init(&ctx);
448 pj_crc32_update(&ctx, (pj_uint8_t*)crc32_test_data[i].input,
449 len / 2);
450
451 if (len/2 > 0) {
452 pj_crc32_update(&ctx, (pj_uint8_t*)crc32_test_data[i].input + len/2,
453 len - len/2);
454 }
455
456 crc1 = pj_crc32_final(&ctx);
457
458 if (crc0 != crc1) {
459 PJ_LOG(3,(THIS_FILE,
460 " error: crc algorithm error on test %d", i));
461 return -85;
462 }
463
464 }
Benny Prijono3dc1f402007-02-26 02:33:14 +0000465 return 0;
466}
467
Benny Prijono015cbfd2007-02-25 15:38:32 +0000468
Benny Prijono7977f9f2007-10-10 11:37:56 +0000469/*
470 * Base64 test vectors (RFC 4648)
471 */
472static struct base64_test_vec
473{
474 const char *base256;
475 const char *base64;
476} base64_test_vec[] =
477{
478 {
479 "",
480 ""
481 },
482 {
483 "f",
484 "Zg=="
485 },
486 {
487 "fo",
488 "Zm8="
489 },
490 {
491 "foo",
492 "Zm9v"
493 },
494 {
495 "foob",
496 "Zm9vYg=="
497 },
498 {
499 "fooba",
500 "Zm9vYmE=",
501 },
502 {
503 "foobar",
504 "Zm9vYmFy"
505 },
506 {
507 "\x14\xfb\x9c\x03\xd9\x7e",
508 "FPucA9l+"
509 },
510 {
511 "\x14\xfb\x9c\x03\xd9",
512 "FPucA9k="
513 },
514 {
515 "\x14\xfb\x9c\x03",
516 "FPucAw=="
517 }
518};
519
520
521static int base64_test(void)
522{
523 unsigned i;
524 char output[80];
525 pj_status_t rc;
526
527 PJ_LOG(3, (THIS_FILE, " base64 test.."));
528
529 for (i=0; i<PJ_ARRAY_SIZE(base64_test_vec); ++i) {
530 /* Encode test */
531 pj_str_t input;
532 int out_len = sizeof(output);
533
Benny Prijonob071a782007-10-10 13:12:37 +0000534 rc = pj_base64_encode((pj_uint8_t*)base64_test_vec[i].base256,
Benny Prijono7977f9f2007-10-10 11:37:56 +0000535 strlen(base64_test_vec[i].base256),
536 output, &out_len);
537 if (rc != PJ_SUCCESS)
538 return -90;
539
Benny Prijonof0f8fd12007-11-10 12:05:59 +0000540 if (out_len != (int)strlen(base64_test_vec[i].base64))
Benny Prijono7977f9f2007-10-10 11:37:56 +0000541 return -91;
542
543 output[out_len] = '\0';
544 if (strcmp(output, base64_test_vec[i].base64) != 0)
545 return -92;
546
547 /* Decode test */
548 out_len = sizeof(output);
Benny Prijonob071a782007-10-10 13:12:37 +0000549 input.ptr = (char*)base64_test_vec[i].base64;
Benny Prijono7977f9f2007-10-10 11:37:56 +0000550 input.slen = strlen(base64_test_vec[i].base64);
551 rc = pj_base64_decode(&input, (pj_uint8_t*)output, &out_len);
552 if (rc != PJ_SUCCESS)
553 return -95;
554
Benny Prijonof0f8fd12007-11-10 12:05:59 +0000555 if (out_len != (int)strlen(base64_test_vec[i].base256))
Benny Prijono7977f9f2007-10-10 11:37:56 +0000556 return -96;
557
558 output[out_len] = '\0';
559
560 if (strcmp(output, base64_test_vec[i].base256) != 0)
561 return -97;
562 }
563
564 return 0;
565}
566
567
Benny Prijono015cbfd2007-02-25 15:38:32 +0000568int encryption_test()
569{
570 int rc;
571
Benny Prijono7977f9f2007-10-10 11:37:56 +0000572 rc = base64_test();
573 if (rc != 0)
574 return rc;
575
Benny Prijono015cbfd2007-02-25 15:38:32 +0000576 rc = sha1_test1();
577 if (rc != 0)
578 return rc;
579
580 rc = sha1_test2();
581 if (rc != 0)
582 return rc;
583
584 rc = rfc2202_test();
585 if (rc != 0)
586 return rc;
587
Benny Prijono3dc1f402007-02-26 02:33:14 +0000588 rc = crc32_test();
589 if (rc != 0)
590 return rc;
591
Benny Prijono015cbfd2007-02-25 15:38:32 +0000592 return 0;
593}
594
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000595static void crc32_update(pj_crc32_context *c, const pj_uint8_t *data,
596 pj_size_t nbytes)
597{
598 pj_crc32_update(c, data, nbytes);
599}
600
601static void crc32_final(pj_crc32_context *ctx, pj_uint32_t *digest)
602{
603 *digest = pj_crc32_final(ctx);
604}
605
606int encryption_benchmark()
607{
608 pj_pool_t *pool;
609 pj_uint8_t *input;
610 union {
611 pj_md5_context md5_context;
612 pj_sha1_context sha1_context;
613 } context;
614 pj_uint8_t digest[32];
615 pj_size_t input_len;
616 struct algorithm
617 {
618 const char *name;
619 void (*init_context)(void*);
620 void (*update)(void*, const pj_uint8_t*, unsigned);
621 void (*final)(void*, void*);
622 pj_uint32_t t;
623 } algorithms[] =
624 {
625 {
626 "MD5 ",
Benny Prijonof83dc1d2007-02-28 14:35:50 +0000627 (void (*)(void*))&pj_md5_init,
628 (void (*)(void*, const pj_uint8_t*, unsigned))&pj_md5_update,
629 (void (*)(void*, void*))&pj_md5_final
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000630 },
631 {
632 "SHA1 ",
Benny Prijonof83dc1d2007-02-28 14:35:50 +0000633 (void (*)(void*))&pj_sha1_init,
634 (void (*)(void*, const pj_uint8_t*, unsigned))&pj_sha1_update,
635 (void (*)(void*, void*))&pj_sha1_final
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000636 },
637 {
638 "CRC32",
Benny Prijonof83dc1d2007-02-28 14:35:50 +0000639 (void (*)(void*))&pj_crc32_init,
640 (void (*)(void*, const pj_uint8_t*, unsigned))&crc32_update,
641 (void (*)(void*, void*))&crc32_final
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000642 }
643 };
644#if defined(PJ_DEBUG) && PJ_DEBUG!=0
645 enum { LOOP = 1000 };
646#else
647 enum { LOOP = 10000 };
648#endif
649 unsigned i;
650 double total_len;
651
652 input_len = 2048;
653 total_len = input_len * LOOP;
654 pool = pj_pool_create(mem, "enc", input_len+256, 0, NULL);
655 if (!pool)
656 return PJ_ENOMEM;
657
Benny Prijonoa1e69682007-05-11 15:14:34 +0000658 input = (pj_uint8_t*)pj_pool_alloc(pool, input_len);
Benny Prijono8fe2ed52007-02-26 22:31:06 +0000659 pj_memset(input, '\xaa', input_len);
660
661 PJ_LOG(3, (THIS_FILE, " feeding %d Mbytes of data",
662 (unsigned)(total_len/1024/1024)));
663
664 /* Dry run */
665 for (i=0; i<PJ_ARRAY_SIZE(algorithms); ++i) {
666 algorithms[i].init_context(&context);
667 algorithms[i].update(&context, input, input_len);
668 algorithms[i].final(&context, digest);
669 }
670
671 /* Run */
672 for (i=0; i<PJ_ARRAY_SIZE(algorithms); ++i) {
673 int j;
674 pj_timestamp t1, t2;
675
676 pj_get_timestamp(&t1);
677 algorithms[i].init_context(&context);
678 for (j=0; j<LOOP; ++j) {
679 algorithms[i].update(&context, input, input_len);
680 }
681 algorithms[i].final(&context, digest);
682 pj_get_timestamp(&t2);
683
684 algorithms[i].t = pj_elapsed_usec(&t1, &t2);
685 }
686
687 /* Results */
688 for (i=0; i<PJ_ARRAY_SIZE(algorithms); ++i) {
689 double bytes;
690
691 bytes = (total_len * 1000000 / algorithms[i].t);
692 PJ_LOG(3, (THIS_FILE, " %s:%8d usec (%3d.%03d Mbytes/sec)",
693 algorithms[i].name, algorithms[i].t,
694 (unsigned)(bytes / 1024 / 1024),
695 ((unsigned)(bytes) % (1024 * 1024)) / 1024));
696 }
697
698 return 0;
699}
700
Benny Prijono015cbfd2007-02-25 15:38:32 +0000701
702
703#endif /* INCLUDE_ENCRYPTION_TEST */
704