Added ChaCha20+Poly1305 support (stand-alone, cipher suites).
[BearSSL] / test / test_speed.c
1 /*
2 * Copyright (c) 2016 Thomas Pornin <pornin@bolet.org>
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining
5 * a copy of this software and associated documentation files (the
6 * "Software"), to deal in the Software without restriction, including
7 * without limitation the rights to use, copy, modify, merge, publish,
8 * distribute, sublicense, and/or sell copies of the Software, and to
9 * permit persons to whom the Software is furnished to do so, subject to
10 * the following conditions:
11 *
12 * The above copyright notice and this permission notice shall be
13 * included in all copies or substantial portions of the Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
16 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
17 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
18 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
19 * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
20 * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
21 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22 * SOFTWARE.
23 */
24
25 #include <stdio.h>
26 #include <stdlib.h>
27 #include <string.h>
28 #include <time.h>
29 #include "inner.h"
30
31 #define HASH_SIZE(cname) br_ ## cname ## _SIZE
32
33 #define SPEED_HASH(Name, cname) \
34 static void \
35 test_speed_ ## cname(void) \
36 { \
37 unsigned char buf[8192]; \
38 unsigned char tmp[HASH_SIZE(cname)]; \
39 br_ ## cname ## _context mc; \
40 int i; \
41 long num; \
42 \
43 memset(buf, 'T', sizeof buf); \
44 for (i = 0; i < 10; i ++) { \
45 br_ ## cname ## _init(&mc); \
46 br_ ## cname ## _update(&mc, buf, sizeof buf); \
47 br_ ## cname ## _out(&mc, tmp); \
48 } \
49 num = 10; \
50 for (;;) { \
51 clock_t begin, end; \
52 double tt; \
53 long k; \
54 \
55 br_ ## cname ## _init(&mc); \
56 begin = clock(); \
57 for (k = num; k > 0; k --) { \
58 br_ ## cname ## _update(&mc, buf, sizeof buf); \
59 } \
60 end = clock(); \
61 br_ ## cname ## _out(&mc, tmp); \
62 tt = (double)(end - begin) / CLOCKS_PER_SEC; \
63 if (tt >= 2.0) { \
64 printf("%-30s %8.2f MB/s\n", #Name, \
65 ((double)sizeof buf) * (double)num \
66 / (tt * 1000000.0)); \
67 fflush(stdout); \
68 return; \
69 } \
70 num <<= 1; \
71 } \
72 }
73
74 #define BLOCK_SIZE(cname) br_ ## cname ## _BLOCK_SIZE
75
76 #define SPEED_BLOCKCIPHER_CBC(Name, fname, cname, klen, dir) \
77 static void \
78 test_speed_ ## fname(void) \
79 { \
80 unsigned char key[klen]; \
81 unsigned char buf[8192 - (8192 % BLOCK_SIZE(cname))]; \
82 unsigned char iv[BLOCK_SIZE(cname)]; \
83 const br_block_cbc ## dir ## _class *vt; \
84 br_ ## cname ## _cbc ## dir ## _keys ec; \
85 int i; \
86 long num; \
87 \
88 memset(key, 'T', sizeof key); \
89 memset(buf, 'P', sizeof buf); \
90 memset(iv, 'X', sizeof iv); \
91 vt = &br_ ## cname ## _cbc ## dir ## _vtable; \
92 for (i = 0; i < 10; i ++) { \
93 vt->init(&ec.vtable, key, sizeof key); \
94 vt->run(&ec.vtable, iv, buf, sizeof buf); \
95 } \
96 num = 10; \
97 for (;;) { \
98 clock_t begin, end; \
99 double tt; \
100 long k; \
101 \
102 vt->init(&ec.vtable, key, sizeof key); \
103 begin = clock(); \
104 for (k = num; k > 0; k --) { \
105 vt->run(&ec.vtable, iv, buf, sizeof buf); \
106 } \
107 end = clock(); \
108 tt = (double)(end - begin) / CLOCKS_PER_SEC; \
109 if (tt >= 2.0) { \
110 printf("%-30s %8.2f MB/s\n", #Name, \
111 ((double)sizeof buf) * (double)num \
112 / (tt * 1000000.0)); \
113 fflush(stdout); \
114 return; \
115 } \
116 num <<= 1; \
117 } \
118 }
119
120 #define SPEED_BLOCKCIPHER_CTR(Name, fname, cname, klen) \
121 static void \
122 test_speed_ ## fname(void) \
123 { \
124 unsigned char key[klen]; \
125 unsigned char buf[8192 - (8192 % BLOCK_SIZE(cname))]; \
126 unsigned char iv[BLOCK_SIZE(cname) - 4]; \
127 const br_block_ctr_class *vt; \
128 br_ ## cname ## _ctr_keys ec; \
129 int i; \
130 long num; \
131 \
132 memset(key, 'T', sizeof key); \
133 memset(buf, 'P', sizeof buf); \
134 memset(iv, 'X', sizeof iv); \
135 vt = &br_ ## cname ## _ctr_vtable; \
136 for (i = 0; i < 10; i ++) { \
137 vt->init(&ec.vtable, key, sizeof key); \
138 vt->run(&ec.vtable, iv, 1, buf, sizeof buf); \
139 } \
140 num = 10; \
141 for (;;) { \
142 clock_t begin, end; \
143 double tt; \
144 long k; \
145 \
146 vt->init(&ec.vtable, key, sizeof key); \
147 begin = clock(); \
148 for (k = num; k > 0; k --) { \
149 vt->run(&ec.vtable, iv, 1, buf, sizeof buf); \
150 } \
151 end = clock(); \
152 tt = (double)(end - begin) / CLOCKS_PER_SEC; \
153 if (tt >= 2.0) { \
154 printf("%-30s %8.2f MB/s\n", #Name, \
155 ((double)sizeof buf) * (double)num \
156 / (tt * 1000000.0)); \
157 fflush(stdout); \
158 return; \
159 } \
160 num <<= 1; \
161 } \
162 }
163
164 #define SPEED_CHACHA20(Name, fname) \
165 static void \
166 test_speed_ ## fname(void) \
167 { \
168 unsigned char key[32]; \
169 unsigned char buf[8192]; \
170 unsigned char iv[12]; \
171 int i; \
172 long num; \
173 \
174 memset(key, 'T', sizeof key); \
175 memset(buf, 'P', sizeof buf); \
176 memset(iv, 'X', sizeof iv); \
177 for (i = 0; i < 10; i ++) { \
178 br_ ## fname ## _run(key, iv, i, buf, sizeof buf); \
179 } \
180 num = 10; \
181 for (;;) { \
182 clock_t begin, end; \
183 double tt; \
184 long k; \
185 \
186 begin = clock(); \
187 for (k = num; k > 0; k --) { \
188 br_ ## fname ## _run(key, iv, \
189 (uint32_t)k, buf, sizeof buf); \
190 } \
191 end = clock(); \
192 tt = (double)(end - begin) / CLOCKS_PER_SEC; \
193 if (tt >= 2.0) { \
194 printf("%-30s %8.2f MB/s\n", #Name, \
195 ((double)sizeof buf) * (double)num \
196 / (tt * 1000000.0)); \
197 fflush(stdout); \
198 return; \
199 } \
200 num <<= 1; \
201 } \
202 }
203
204 SPEED_HASH(MD5, md5)
205 SPEED_HASH(SHA-1, sha1)
206 SPEED_HASH(SHA-256, sha256)
207 SPEED_HASH(SHA-512, sha512)
208
209 #define SPEED_AES(iname) \
210 SPEED_BLOCKCIPHER_CBC(AES-128 CBC encrypt (iname), aes128_ ## iname ## _cbcenc, aes_ ## iname, 16, enc) \
211 SPEED_BLOCKCIPHER_CBC(AES-128 CBC decrypt (iname), aes128_ ## iname ## _cbcdec, aes_ ## iname, 16, dec) \
212 SPEED_BLOCKCIPHER_CBC(AES-192 CBC encrypt (iname), aes192_ ## iname ## _cbcenc, aes_ ## iname, 24, enc) \
213 SPEED_BLOCKCIPHER_CBC(AES-192 CBC decrypt (iname), aes192_ ## iname ## _cbcdec, aes_ ## iname, 24, dec) \
214 SPEED_BLOCKCIPHER_CBC(AES-256 CBC encrypt (iname), aes256_ ## iname ## _cbcenc, aes_ ## iname, 32, enc) \
215 SPEED_BLOCKCIPHER_CBC(AES-256 CBC decrypt (iname), aes256_ ## iname ## _cbcdec, aes_ ## iname, 32, dec) \
216 SPEED_BLOCKCIPHER_CTR(AES-128 CTR (iname), aes128_ ## iname ## _ctr, aes_ ## iname, 16) \
217 SPEED_BLOCKCIPHER_CTR(AES-192 CTR (iname), aes192_ ## iname ## _ctr, aes_ ## iname, 24) \
218 SPEED_BLOCKCIPHER_CTR(AES-256 CTR (iname), aes256_ ## iname ## _ctr, aes_ ## iname, 32)
219
220 SPEED_AES(big)
221 SPEED_AES(small)
222 SPEED_AES(ct)
223 SPEED_AES(ct64)
224
225 #define SPEED_DES(iname) \
226 SPEED_BLOCKCIPHER_CBC(DES CBC encrypt (iname), des_ ## iname ## _cbcenc, des_ ## iname, 8, enc) \
227 SPEED_BLOCKCIPHER_CBC(DES CBC decrypt (iname), des_ ## iname ## _cbcdec, des_ ## iname, 8, dec) \
228 SPEED_BLOCKCIPHER_CBC(3DES CBC encrypt (iname), 3des_ ## iname ## _cbcenc, des_ ## iname, 24, enc) \
229 SPEED_BLOCKCIPHER_CBC(3DES CBC decrypt (iname), 3des_ ## iname ## _cbcdec, des_ ## iname, 24, dec)
230
231 SPEED_DES(tab)
232 SPEED_DES(ct)
233
234 SPEED_CHACHA20(ChaCha20, chacha20_ct)
235
236 static void
237 test_speed_ghash_inner(char *name, br_ghash gh)
238 {
239 unsigned char buf[8192], h[16], y[16];
240 int i;
241 long num;
242
243 memset(buf, 'T', sizeof buf);
244 memset(h, 'P', sizeof h);
245 memset(y, 0, sizeof y);
246 for (i = 0; i < 10; i ++) {
247 gh(y, h, buf, sizeof buf);
248 }
249 num = 10;
250 for (;;) {
251 clock_t begin, end;
252 double tt;
253 long k;
254
255 begin = clock();
256 for (k = num; k > 0; k --) {
257 gh(y, h, buf, sizeof buf);
258 }
259 end = clock();
260 tt = (double)(end - begin) / CLOCKS_PER_SEC;
261 if (tt >= 2.0) {
262 printf("%-30s %8.2f MB/s\n", name,
263 ((double)sizeof buf) * (double)num
264 / (tt * 1000000.0));
265 fflush(stdout);
266 return;
267 }
268 num <<= 1;
269 }
270 }
271
272 static void
273 test_speed_ghash_ctmul(void)
274 {
275 test_speed_ghash_inner("GHASH (ctmul)", &br_ghash_ctmul);
276 }
277
278 static void
279 test_speed_ghash_ctmul32(void)
280 {
281 test_speed_ghash_inner("GHASH (ctmul32)", &br_ghash_ctmul32);
282 }
283
284 static void
285 test_speed_ghash_ctmul64(void)
286 {
287 test_speed_ghash_inner("GHASH (ctmul64)", &br_ghash_ctmul64);
288 }
289
290 static const unsigned char RSA_N[] = {
291 0xE9, 0xF2, 0x4A, 0x2F, 0x96, 0xDF, 0x0A, 0x23,
292 0x01, 0x85, 0xF1, 0x2C, 0xB2, 0xA8, 0xEF, 0x23,
293 0xCE, 0x2E, 0xB0, 0x4E, 0x18, 0x31, 0x95, 0x5B,
294 0x98, 0x2D, 0x9B, 0x8C, 0xE3, 0x1A, 0x2B, 0x96,
295 0xB5, 0xC7, 0xEE, 0xED, 0x72, 0x43, 0x2D, 0xFE,
296 0x7F, 0x61, 0x33, 0xEA, 0x14, 0xFC, 0xDE, 0x80,
297 0x17, 0x42, 0xF0, 0xF3, 0xC3, 0xC7, 0x89, 0x47,
298 0x76, 0x5B, 0xFA, 0x33, 0xC4, 0x8C, 0x94, 0xDE,
299 0x6A, 0x75, 0xD8, 0x1A, 0xF4, 0x49, 0xBC, 0xF3,
300 0xB7, 0x9E, 0x2C, 0x8D, 0xEC, 0x5A, 0xEE, 0xBF,
301 0x4B, 0x5A, 0x7F, 0xEF, 0x21, 0x39, 0xDB, 0x1D,
302 0x83, 0x5E, 0x7E, 0x2F, 0xAA, 0x5E, 0xBA, 0x28,
303 0xC3, 0xA2, 0x53, 0x19, 0xFB, 0x2F, 0x78, 0x6B,
304 0x14, 0x60, 0x49, 0x3C, 0xCC, 0x1B, 0xE9, 0x1E,
305 0x3D, 0x10, 0xA4, 0xEB, 0x7F, 0x66, 0x98, 0xF6,
306 0xC3, 0xAC, 0x35, 0xF5, 0x01, 0x84, 0xFF, 0x7D,
307 0x1F, 0x72, 0xBE, 0xB4, 0xD1, 0x89, 0xC8, 0xDD,
308 0x44, 0xE7, 0xB5, 0x2E, 0x2C, 0xE1, 0x85, 0xF5,
309 0x15, 0x50, 0xA9, 0x08, 0xC7, 0x67, 0xD9, 0x2B,
310 0x6C, 0x11, 0xB3, 0xEB, 0x28, 0x8D, 0xF4, 0xCC,
311 0xE3, 0xC3, 0xC5, 0x04, 0x0E, 0x7C, 0x8D, 0xDB,
312 0x39, 0x06, 0x6A, 0x74, 0x75, 0xDF, 0xA8, 0x0F,
313 0xDA, 0x67, 0x5A, 0x73, 0x1E, 0xFD, 0x8E, 0x4C,
314 0xEE, 0x17, 0xEE, 0x1E, 0x67, 0xDB, 0x98, 0x70,
315 0x60, 0xF7, 0xB9, 0xB5, 0x1F, 0x19, 0x93, 0xD6,
316 0x3F, 0x2F, 0x1F, 0xB6, 0x5B, 0x59, 0xAA, 0x85,
317 0xBB, 0x25, 0xE4, 0x13, 0xEF, 0xE7, 0xB9, 0x87,
318 0x9C, 0x3F, 0x5E, 0xE4, 0x08, 0xA3, 0x51, 0xCF,
319 0x8B, 0xAD, 0xF4, 0xE6, 0x1A, 0x5F, 0x51, 0xDD,
320 0xA8, 0xBE, 0xE8, 0xD1, 0x20, 0x19, 0x61, 0x6C,
321 0x18, 0xAB, 0xCA, 0x0A, 0xD9, 0x82, 0xA6, 0x94,
322 0xD5, 0x69, 0x2A, 0xF6, 0x43, 0x66, 0x31, 0x09
323 };
324
325 static const unsigned char RSA_E[] = {
326 0x01, 0x00, 0x01
327 };
328
329 static const unsigned char RSA_P[] = {
330 0xFD, 0x39, 0x40, 0x56, 0x20, 0x80, 0xC5, 0x81,
331 0x4C, 0x5F, 0x0C, 0x1A, 0x52, 0x84, 0x03, 0x2F,
332 0xCE, 0x82, 0xB0, 0xD8, 0x30, 0x23, 0x7F, 0x77,
333 0x45, 0xC2, 0x01, 0xC4, 0x68, 0x96, 0x0D, 0xA7,
334 0x22, 0xA9, 0x6C, 0xA9, 0x1A, 0x33, 0xE5, 0x2F,
335 0xB5, 0x07, 0x9A, 0xF9, 0xEA, 0x33, 0xA5, 0xC8,
336 0x96, 0x60, 0x6A, 0xCA, 0xEB, 0xE5, 0x6E, 0x09,
337 0x46, 0x7E, 0x2D, 0xEF, 0x93, 0x7D, 0x56, 0xED,
338 0x75, 0x70, 0x3B, 0x96, 0xC4, 0xD5, 0xDB, 0x0B,
339 0x3F, 0x69, 0xDF, 0x06, 0x18, 0x76, 0xF4, 0xCF,
340 0xF8, 0x84, 0x22, 0xDF, 0xBD, 0x71, 0x62, 0x7B,
341 0x67, 0x99, 0xBC, 0x09, 0x95, 0x54, 0xA4, 0x98,
342 0x83, 0xF5, 0xA9, 0xCF, 0x09, 0xA5, 0x1F, 0x61,
343 0x25, 0xB4, 0x70, 0x6C, 0x91, 0xB8, 0xB3, 0xD0,
344 0xCE, 0x9C, 0x45, 0x65, 0x9B, 0xEF, 0xD4, 0x70,
345 0xBE, 0x86, 0xD2, 0x98, 0x5D, 0xEB, 0xE3, 0xFF
346 };
347
348 static const unsigned char RSA_Q[] = {
349 0xEC, 0x82, 0xEE, 0x63, 0x5F, 0x40, 0x52, 0xDB,
350 0x38, 0x7A, 0x37, 0x6A, 0x54, 0x5B, 0xD9, 0xA0,
351 0x73, 0xB4, 0xBB, 0x52, 0xB2, 0x84, 0x07, 0xD0,
352 0xCC, 0x82, 0x0D, 0x20, 0xB3, 0xFA, 0xD5, 0xB6,
353 0x25, 0x92, 0x35, 0x4D, 0xB4, 0xC7, 0x36, 0x48,
354 0xCE, 0x5E, 0x21, 0x4A, 0xA6, 0x74, 0x65, 0xF4,
355 0x7D, 0x1D, 0xBC, 0x3B, 0xE2, 0xF4, 0x3E, 0x11,
356 0x58, 0x10, 0x6C, 0x04, 0x46, 0x9E, 0x8D, 0x57,
357 0xE0, 0x04, 0xE2, 0xEC, 0x47, 0xCF, 0xB3, 0x2A,
358 0xFD, 0x4C, 0x55, 0x18, 0xDB, 0xDE, 0x3B, 0xDC,
359 0xF4, 0x5B, 0xDA, 0xF3, 0x1A, 0xC8, 0x41, 0x6F,
360 0x73, 0x3B, 0xFE, 0x3C, 0xA0, 0xDB, 0xBA, 0x6E,
361 0x65, 0xA5, 0xE8, 0x02, 0xA5, 0x6C, 0xEA, 0x03,
362 0xF6, 0x99, 0xF7, 0xCB, 0x4B, 0xB7, 0x11, 0x51,
363 0x93, 0x88, 0x3F, 0xF9, 0x06, 0x85, 0xA9, 0x1E,
364 0xCA, 0x64, 0xF8, 0x11, 0xA5, 0x1A, 0xCA, 0xF7
365 };
366
367 static const unsigned char RSA_DP[] = {
368 0x77, 0x95, 0xE0, 0x02, 0x4C, 0x9B, 0x43, 0xAA,
369 0xCA, 0x4C, 0x60, 0xC4, 0xD5, 0x8F, 0x2E, 0x8A,
370 0x17, 0x36, 0xB5, 0x19, 0x83, 0xB2, 0x5F, 0xF2,
371 0x0D, 0xE9, 0x8F, 0x38, 0x18, 0x44, 0x34, 0xF2,
372 0x67, 0x76, 0x27, 0xB0, 0xBC, 0x85, 0x21, 0x89,
373 0x24, 0x2F, 0x11, 0x4B, 0x51, 0x05, 0x4F, 0x17,
374 0xA9, 0x9C, 0xA3, 0x12, 0x6D, 0xD1, 0x0D, 0xE4,
375 0x27, 0x7C, 0x53, 0x69, 0x3E, 0xF8, 0x04, 0x63,
376 0x64, 0x00, 0xBA, 0xC3, 0x7A, 0xF5, 0x9B, 0xDA,
377 0x75, 0xFA, 0x23, 0xAF, 0x17, 0x42, 0xA6, 0x5E,
378 0xC8, 0xF8, 0x6E, 0x17, 0xC7, 0xB9, 0x92, 0x4E,
379 0xC1, 0x20, 0x63, 0x23, 0x0B, 0x78, 0xCB, 0xBA,
380 0x93, 0x27, 0x23, 0x28, 0x79, 0x5F, 0x97, 0xB0,
381 0x23, 0x44, 0x51, 0x8B, 0x94, 0x4D, 0xEB, 0xED,
382 0x82, 0x85, 0x5E, 0x68, 0x9B, 0xF9, 0xE9, 0x13,
383 0xCD, 0x86, 0x92, 0x52, 0x0E, 0x98, 0xE6, 0x35
384 };
385
386 static const unsigned char RSA_DQ[] = {
387 0xD8, 0xDD, 0x71, 0xB3, 0x62, 0xBA, 0xBB, 0x7E,
388 0xD1, 0xF9, 0x96, 0xE8, 0x83, 0xB3, 0xB9, 0x08,
389 0x9C, 0x30, 0x03, 0x77, 0xDF, 0xC2, 0x9A, 0xDC,
390 0x05, 0x39, 0xD6, 0xC9, 0xBE, 0xDE, 0x68, 0xA9,
391 0xDD, 0x27, 0x84, 0x82, 0xDD, 0x19, 0xB1, 0x97,
392 0xEE, 0xCA, 0x77, 0x22, 0x59, 0x20, 0xEF, 0xFF,
393 0xCF, 0xDD, 0xBD, 0x24, 0xF8, 0x84, 0xD6, 0x88,
394 0xD6, 0xC4, 0x30, 0x17, 0x77, 0x9D, 0x98, 0xA3,
395 0x14, 0x01, 0xC7, 0x05, 0xBB, 0x0F, 0x23, 0x0D,
396 0x6F, 0x37, 0x57, 0xEC, 0x34, 0x67, 0x41, 0x62,
397 0xE8, 0x19, 0x75, 0xD9, 0x66, 0x1C, 0x6B, 0x8B,
398 0xC3, 0x11, 0x26, 0x9C, 0xF7, 0x2E, 0xA3, 0x72,
399 0xE8, 0xF7, 0xC8, 0x96, 0xEC, 0x92, 0xC2, 0xBD,
400 0xA1, 0x98, 0x2A, 0x93, 0x99, 0xB8, 0xA2, 0x43,
401 0xB7, 0xD0, 0xBE, 0x40, 0x1C, 0x8F, 0xE0, 0xB4,
402 0x20, 0x07, 0x97, 0x43, 0xAE, 0xAD, 0xB3, 0x9F
403 };
404
405 static const unsigned char RSA_IQ[] = {
406 0xB7, 0xE2, 0x60, 0xA9, 0x62, 0xEC, 0xEC, 0x0B,
407 0x57, 0x02, 0x96, 0xF9, 0x36, 0x35, 0x2C, 0x37,
408 0xAF, 0xC2, 0xEE, 0x71, 0x49, 0x26, 0x8E, 0x0F,
409 0x27, 0xB1, 0xFA, 0x0F, 0xEA, 0xDC, 0xF0, 0x8B,
410 0x53, 0x6C, 0xB2, 0x46, 0x27, 0xCD, 0x29, 0xA2,
411 0x35, 0x0F, 0x5D, 0x8A, 0x3F, 0x20, 0x8C, 0x13,
412 0x3D, 0xA1, 0xFF, 0x85, 0x91, 0x99, 0xE8, 0x50,
413 0xED, 0xF1, 0x29, 0x00, 0xEE, 0x24, 0x90, 0xB5,
414 0x5F, 0x3A, 0x74, 0x26, 0xD7, 0xA2, 0x24, 0x8D,
415 0x89, 0x88, 0xD8, 0x35, 0x22, 0x22, 0x8A, 0x66,
416 0x5D, 0x5C, 0xDE, 0x83, 0x8C, 0xFA, 0x27, 0xE6,
417 0xB9, 0xEB, 0x72, 0x08, 0xCD, 0x53, 0x4B, 0x93,
418 0x0F, 0xAD, 0xC3, 0xF8, 0x7C, 0xFE, 0x84, 0xD7,
419 0x08, 0xF3, 0xBE, 0x3D, 0x60, 0x1E, 0x95, 0x8D,
420 0x44, 0x5B, 0x65, 0x7E, 0xC1, 0x30, 0xC3, 0x84,
421 0xC0, 0xB0, 0xFE, 0xBF, 0x28, 0x54, 0x1E, 0xC4
422 };
423
424 static const br_rsa_public_key RSA_PK = {
425 (void *)RSA_N, sizeof RSA_N,
426 (void *)RSA_E, sizeof RSA_E
427 };
428
429 static const br_rsa_private_key RSA_SK = {
430 2048,
431 (void *)RSA_P, sizeof RSA_P,
432 (void *)RSA_Q, sizeof RSA_Q,
433 (void *)RSA_DP, sizeof RSA_DP,
434 (void *)RSA_DQ, sizeof RSA_DQ,
435 (void *)RSA_IQ, sizeof RSA_IQ
436 };
437
438 static void
439 test_speed_rsa_inner(char *name,
440 br_rsa_public fpub, br_rsa_private fpriv)
441 {
442 unsigned char tmp[sizeof RSA_N];
443 int i;
444 long num;
445
446 memset(tmp, 'R', sizeof tmp);
447 tmp[0] = 0;
448 for (i = 0; i < 10; i ++) {
449 if (!fpriv(tmp, &RSA_SK)) {
450 abort();
451 }
452 }
453 num = 10;
454 for (;;) {
455 clock_t begin, end;
456 double tt;
457 long k;
458
459 begin = clock();
460 for (k = num; k > 0; k --) {
461 fpriv(tmp, &RSA_SK);
462 }
463 end = clock();
464 tt = (double)(end - begin) / CLOCKS_PER_SEC;
465 if (tt >= 2.0) {
466 printf("%-30s %8.2f priv/s\n", name,
467 (double)num / tt);
468 fflush(stdout);
469 break;
470 }
471 num <<= 1;
472 }
473 for (i = 0; i < 10; i ++) {
474 if (!fpub(tmp, sizeof tmp, &RSA_PK)) {
475 abort();
476 }
477 }
478 num = 10;
479 for (;;) {
480 clock_t begin, end;
481 double tt;
482 long k;
483
484 begin = clock();
485 for (k = num; k > 0; k --) {
486 fpub(tmp, sizeof tmp, &RSA_PK);
487 }
488 end = clock();
489 tt = (double)(end - begin) / CLOCKS_PER_SEC;
490 if (tt >= 2.0) {
491 printf("%-30s %8.2f pub/s\n", name,
492 (double)num / tt);
493 fflush(stdout);
494 break;
495 }
496 num <<= 1;
497 }
498 }
499
500 static void
501 test_speed_rsa_i31(void)
502 {
503 test_speed_rsa_inner("RSA i31",
504 &br_rsa_i31_public, &br_rsa_i31_private);
505 }
506
507 static void
508 test_speed_rsa_i32(void)
509 {
510 test_speed_rsa_inner("RSA i32",
511 &br_rsa_i32_public, &br_rsa_i32_private);
512 }
513
514 static void
515 test_speed_ec_inner(const char *name,
516 const br_ec_impl *impl, const br_ec_curve_def *cd)
517 {
518 unsigned char bx[80], U[160];
519 uint32_t x[22], n[22];
520 size_t nlen, ulen;
521 int i;
522 long num;
523
524 nlen = cd->order_len;
525 br_i31_decode(n, cd->order, nlen);
526 memset(bx, 'T', sizeof bx);
527 br_i31_decode_reduce(x, bx, sizeof bx, n);
528 br_i31_encode(bx, nlen, x);
529 ulen = cd->generator_len;
530 memcpy(U, cd->generator, ulen);
531 for (i = 0; i < 10; i ++) {
532 impl->mul(U, ulen, bx, nlen, cd->curve);
533 }
534 num = 10;
535 for (;;) {
536 clock_t begin, end;
537 double tt;
538 long k;
539
540 begin = clock();
541 for (k = num; k > 0; k --) {
542 impl->mul(U, ulen, bx, nlen, cd->curve);
543 }
544 end = clock();
545 tt = (double)(end - begin) / CLOCKS_PER_SEC;
546 if (tt >= 2.0) {
547 printf("%-30s %8.2f mul/s\n", name,
548 (double)num / tt);
549 fflush(stdout);
550 break;
551 }
552 num <<= 1;
553 }
554 }
555
556 static void
557 test_speed_ec_prime_i31(void)
558 {
559 test_speed_ec_inner("EC i31 P-256", &br_ec_prime_i31, &br_secp256r1);
560 test_speed_ec_inner("EC i31 P-384", &br_ec_prime_i31, &br_secp384r1);
561 test_speed_ec_inner("EC i31 P-521", &br_ec_prime_i31, &br_secp521r1);
562 }
563
564 static void
565 test_speed_ecdsa_inner(const char *name,
566 const br_ec_impl *impl, const br_ec_curve_def *cd,
567 br_ecdsa_sign sign, br_ecdsa_vrfy vrfy)
568 {
569 unsigned char bx[80], U[160], hv[32], sig[160];
570 uint32_t x[22], n[22];
571 size_t nlen, ulen, sig_len;
572 int i;
573 long num;
574 br_ec_private_key sk;
575 br_ec_public_key pk;
576
577 nlen = cd->order_len;
578 br_i31_decode(n, cd->order, nlen);
579 memset(bx, 'T', sizeof bx);
580 br_i31_decode_reduce(x, bx, sizeof bx, n);
581 br_i31_encode(bx, nlen, x);
582 ulen = cd->generator_len;
583 memcpy(U, cd->generator, ulen);
584 impl->mul(U, ulen, bx, nlen, cd->curve);
585 sk.curve = cd->curve;
586 sk.x = bx;
587 sk.xlen = nlen;
588 pk.curve = cd->curve;
589 pk.q = U;
590 pk.qlen = ulen;
591
592 memset(hv, 'H', sizeof hv);
593 sig_len = sign(impl, &br_sha256_vtable, hv, &sk, sig);
594 if (vrfy(impl, hv, sizeof hv, &pk, sig, sig_len) != 1) {
595 fprintf(stderr, "self-test sign/verify failed\n");
596 exit(EXIT_FAILURE);
597 }
598
599 for (i = 0; i < 10; i ++) {
600 hv[1] ++;
601 sign(impl, &br_sha256_vtable, hv, &sk, sig);
602 vrfy(impl, hv, sizeof hv, &pk, sig, sig_len);
603 }
604
605 num = 10;
606 for (;;) {
607 clock_t begin, end;
608 double tt;
609 long k;
610
611 begin = clock();
612 for (k = num; k > 0; k --) {
613 hv[1] ++;
614 sig_len = sign(impl, &br_sha256_vtable, hv, &sk, sig);
615 }
616 end = clock();
617 tt = (double)(end - begin) / CLOCKS_PER_SEC;
618 if (tt >= 2.0) {
619 printf("%-30s %8.2f sign/s\n", name,
620 (double)num / tt);
621 fflush(stdout);
622 break;
623 }
624 num <<= 1;
625 }
626
627 num = 10;
628 for (;;) {
629 clock_t begin, end;
630 double tt;
631 long k;
632
633 begin = clock();
634 for (k = num; k > 0; k --) {
635 vrfy(impl, hv, sizeof hv, &pk, sig, sig_len);
636 }
637 end = clock();
638 tt = (double)(end - begin) / CLOCKS_PER_SEC;
639 if (tt >= 2.0) {
640 printf("%-30s %8.2f verify/s\n", name,
641 (double)num / tt);
642 fflush(stdout);
643 break;
644 }
645 num <<= 1;
646 }
647 }
648
649 static void
650 test_speed_ecdsa_i31(void)
651 {
652 test_speed_ecdsa_inner("ECDSA i31 P-256",
653 &br_ec_prime_i31, &br_secp256r1,
654 &br_ecdsa_i31_sign_asn1,
655 &br_ecdsa_i31_vrfy_asn1);
656 test_speed_ecdsa_inner("ECDSA i31 P-384",
657 &br_ec_prime_i31, &br_secp384r1,
658 &br_ecdsa_i31_sign_asn1,
659 &br_ecdsa_i31_vrfy_asn1);
660 test_speed_ecdsa_inner("ECDSA i31 P-521",
661 &br_ec_prime_i31, &br_secp521r1,
662 &br_ecdsa_i31_sign_asn1,
663 &br_ecdsa_i31_vrfy_asn1);
664 }
665
666 #if 0
667 /* obsolete */
668 static void
669 test_speed_ec_prime_i31_inner(const char *name,
670 const unsigned char *bg, const br_ec_prime_i31_curve *cc)
671 {
672 unsigned char bx[80], point[160];
673 uint32_t x[BR_EC_I31_LEN];
674 br_ec_prime_i31_jacobian P;
675 uint32_t xbl;
676 size_t plen;
677 int i;
678 long num;
679
680 xbl = cc->p[0];
681 xbl -= (xbl >> 5);
682 plen = (xbl + 7) >> 3;
683 memset(bx, 'T', sizeof bx);
684 br_i31_decode_reduce(x, bx, sizeof bx, cc->p);
685 br_i31_encode(bx, plen, x);
686 br_ec_prime_i31_decode(&P, bg, 1 + (plen << 1), cc);
687 for (i = 0; i < 10; i ++) {
688 br_ec_prime_i31_mul(&P, bx, plen, cc);
689 br_ec_prime_i31_encode(point, &P, cc);
690 }
691 num = 10;
692 for (;;) {
693 clock_t begin, end;
694 double tt;
695 long k;
696
697 begin = clock();
698 for (k = num; k > 0; k --) {
699 br_ec_prime_i31_mul(&P, bx, plen, cc);
700 br_ec_prime_i31_encode(point, &P, cc);
701 }
702 end = clock();
703 tt = (double)(end - begin) / CLOCKS_PER_SEC;
704 if (tt >= 2.0) {
705 printf("%-30s %8.2f mul/s\n", name,
706 (double)num / tt);
707 fflush(stdout);
708 break;
709 }
710 num <<= 1;
711 }
712 }
713
714 static void
715 test_speed_ec_prime_i31(void)
716 {
717 test_speed_ec_prime_i31_inner("EC i31 P-256",
718 br_g_secp256r1, &br_ec_prime_i31_secp256r1);
719 test_speed_ec_prime_i31_inner("EC i31 P-384",
720 br_g_secp384r1, &br_ec_prime_i31_secp384r1);
721 test_speed_ec_prime_i31_inner("EC i31 P-521",
722 br_g_secp521r1, &br_ec_prime_i31_secp521r1);
723 }
724
725 static void
726 test_speed_ec_prime_i32_inner(const char *name,
727 const unsigned char *bg, const br_ec_prime_i32_curve *cc)
728 {
729 unsigned char bx[80], point[160];
730 uint32_t x[BR_EC_I32_LEN];
731 br_ec_prime_i32_jacobian P;
732 size_t plen;
733 int i;
734 long num;
735
736 plen = (cc->p[0] + 7) >> 3;
737 memset(bx, 'T', sizeof bx);
738 br_i32_decode_reduce(x, bx, sizeof bx, cc->p);
739 br_i32_encode(bx, plen, x);
740 br_ec_prime_i32_decode(&P, bg, 1 + (plen << 1), cc);
741 for (i = 0; i < 10; i ++) {
742 br_ec_prime_i32_mul(&P, bx, plen, cc);
743 br_ec_prime_i32_encode(point, &P, cc);
744 }
745 num = 10;
746 for (;;) {
747 clock_t begin, end;
748 double tt;
749 long k;
750
751 begin = clock();
752 for (k = num; k > 0; k --) {
753 br_ec_prime_i32_mul(&P, bx, plen, cc);
754 br_ec_prime_i32_encode(point, &P, cc);
755 }
756 end = clock();
757 tt = (double)(end - begin) / CLOCKS_PER_SEC;
758 if (tt >= 2.0) {
759 printf("%-30s %8.2f mul/s\n", name,
760 (double)num / tt);
761 fflush(stdout);
762 break;
763 }
764 num <<= 1;
765 }
766 }
767
768 static void
769 test_speed_ec_prime_i32(void)
770 {
771 test_speed_ec_prime_i32_inner("EC i32 P-256",
772 br_g_secp256r1, &br_ec_prime_i32_secp256r1);
773 test_speed_ec_prime_i32_inner("EC i32 P-384",
774 br_g_secp384r1, &br_ec_prime_i32_secp384r1);
775 test_speed_ec_prime_i32_inner("EC i32 P-521",
776 br_g_secp521r1, &br_ec_prime_i32_secp521r1);
777 }
778 #endif
779
780 static void
781 test_speed_i31(void)
782 {
783 static const unsigned char bp[] = {
784 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00,
785 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
786 0xBC, 0xE6, 0xFA, 0xAD, 0xA7, 0x17, 0x9E, 0x84,
787 0xF3, 0xB9, 0xCA, 0xC2, 0xFC, 0x63, 0x25, 0x51
788 };
789
790 unsigned char tmp[60 + sizeof bp];
791 uint32_t p[10], x[10], y[10], z[10], p0i;
792 int i;
793 long num;
794
795 br_i31_decode(p, bp, sizeof bp);
796 p0i = br_i31_ninv31(p[1]);
797 memset(tmp, 'T', sizeof tmp);
798 br_i31_decode_reduce(x, tmp, sizeof tmp, p);
799 memset(tmp, 'U', sizeof tmp);
800 br_i31_decode_reduce(y, tmp, sizeof tmp, p);
801
802 for (i = 0; i < 10; i ++) {
803 br_i31_to_monty(x, p);
804 }
805 num = 10;
806 for (;;) {
807 clock_t begin, end;
808 double tt;
809 long k;
810
811 begin = clock();
812 for (k = num; k > 0; k --) {
813 br_i31_to_monty(x, p);
814 }
815 end = clock();
816 tt = (double)(end - begin) / CLOCKS_PER_SEC;
817 if (tt >= 2.0) {
818 printf("%-30s %8.2f ops/s\n", "i31 to_monty",
819 (double)num / tt);
820 fflush(stdout);
821 break;
822 }
823 num <<= 1;
824 }
825
826 for (i = 0; i < 10; i ++) {
827 br_i31_from_monty(x, p, p0i);
828 }
829 num = 10;
830 for (;;) {
831 clock_t begin, end;
832 double tt;
833 long k;
834
835 begin = clock();
836 for (k = num; k > 0; k --) {
837 br_i31_from_monty(x, p, p0i);
838 }
839 end = clock();
840 tt = (double)(end - begin) / CLOCKS_PER_SEC;
841 if (tt >= 2.0) {
842 printf("%-30s %8.2f ops/s\n", "i31 from_monty",
843 (double)num / tt);
844 fflush(stdout);
845 break;
846 }
847 num <<= 1;
848 }
849
850 for (i = 0; i < 10; i ++) {
851 br_i31_montymul(z, x, y, p, p0i);
852 }
853 num = 10;
854 for (;;) {
855 clock_t begin, end;
856 double tt;
857 long k;
858
859 begin = clock();
860 for (k = num; k > 0; k --) {
861 br_i31_montymul(z, x, y, p, p0i);
862 }
863 end = clock();
864 tt = (double)(end - begin) / CLOCKS_PER_SEC;
865 if (tt >= 2.0) {
866 printf("%-30s %8.2f ops/s\n", "i31 montymul",
867 (double)num / tt);
868 fflush(stdout);
869 break;
870 }
871 num <<= 1;
872 }
873 }
874
875 #if 0
876
877 static unsigned char P2048[] = {
878 0xFD, 0xB6, 0xE0, 0x3E, 0x00, 0x49, 0x4C, 0xF0, 0x69, 0x3A, 0xDD, 0x7D,
879 0xF8, 0xA2, 0x41, 0xB0, 0x6C, 0x67, 0xC5, 0xBA, 0xB8, 0x46, 0x80, 0xF5,
880 0xBF, 0xAB, 0x98, 0xFC, 0x84, 0x73, 0xA5, 0x63, 0xC9, 0x52, 0x12, 0xDA,
881 0x4C, 0xC1, 0x5B, 0x9D, 0x8D, 0xDF, 0xCD, 0xFE, 0xC5, 0xAD, 0x5A, 0x6F,
882 0xDD, 0x02, 0xD9, 0xEC, 0x71, 0xEF, 0xEB, 0xB6, 0x95, 0xED, 0x94, 0x25,
883 0x0E, 0x63, 0xDD, 0x6A, 0x52, 0xC7, 0x93, 0xAF, 0x85, 0x9D, 0x2C, 0xBE,
884 0x5C, 0xBE, 0x35, 0xD8, 0xDD, 0x39, 0xEF, 0x1B, 0xB1, 0x49, 0x67, 0xB2,
885 0x33, 0xC9, 0x7C, 0xE1, 0x51, 0x79, 0x51, 0x59, 0xCA, 0x6E, 0x2A, 0xDF,
886 0x0D, 0x76, 0x1C, 0xE7, 0xA5, 0xC0, 0x1E, 0x6C, 0x56, 0x3A, 0x32, 0xE5,
887 0xB5, 0xC5, 0xD4, 0xDB, 0xFE, 0xFF, 0xF8, 0xF2, 0x96, 0xA9, 0xC9, 0x65,
888 0x59, 0x9E, 0x01, 0x79, 0x9D, 0x38, 0x68, 0x0F, 0xAD, 0x43, 0x3A, 0xD6,
889 0x84, 0x0A, 0xE2, 0xEF, 0x96, 0xC1, 0x6D, 0x89, 0x74, 0x19, 0x63, 0x82,
890 0x3B, 0xA0, 0x9C, 0xBA, 0x78, 0xDE, 0xDC, 0xC2, 0xE7, 0xD4, 0xFA, 0xD6,
891 0x19, 0x21, 0x29, 0xAE, 0x5E, 0xF4, 0x38, 0x81, 0xC6, 0x9E, 0x0E, 0x3C,
892 0xCD, 0xC0, 0xDC, 0x93, 0x5D, 0xFD, 0x9A, 0x5C, 0xAB, 0x54, 0x1F, 0xFF,
893 0x9C, 0x12, 0x1B, 0x4C, 0xDF, 0x2D, 0x9C, 0x85, 0xF9, 0x68, 0x15, 0x89,
894 0x42, 0x9B, 0x6C, 0x45, 0x89, 0x3A, 0xBC, 0xE9, 0x19, 0x91, 0xBE, 0x0C,
895 0xEF, 0x90, 0xCC, 0xF6, 0xD6, 0xF0, 0x3D, 0x5C, 0xF5, 0xE5, 0x0F, 0x2F,
896 0x02, 0x8A, 0x83, 0x4B, 0x93, 0x2F, 0x14, 0x12, 0x1F, 0x56, 0x9A, 0x12,
897 0x58, 0x88, 0xAE, 0x60, 0xB8, 0x5A, 0xE4, 0xA1, 0xBF, 0x4A, 0x81, 0x84,
898 0xAB, 0xBB, 0xE4, 0xD0, 0x1D, 0x41, 0xD9, 0x0A, 0xAB, 0x1E, 0x47, 0x5B,
899 0x31, 0xAC, 0x2B, 0x73
900 };
901
902 static unsigned char G2048[] = {
903 0x02
904 };
905
906 static void
907 test_speed_modpow(void)
908 {
909 uint32_t mx[65], mp[65], me[65], t1[65], t2[65], len;
910 unsigned char e[64];
911 int i;
912 long num;
913
914 len = br_int_decode(mp, sizeof mp / sizeof mp[0],
915 P2048, sizeof P2048);
916 if (len != 65) {
917 abort();
918 }
919 memset(e, 'P', sizeof e);
920 if (!br_int_decode(me, sizeof me / sizeof me[0], e, sizeof e)) {
921 abort();
922 }
923 if (!br_modint_decode(mx, mp, G2048, sizeof G2048)) {
924 abort();
925 }
926 for (i = 0; i < 10; i ++) {
927 br_modint_to_monty(mx, mp);
928 br_modint_montypow(mx, me, mp, t1, t2);
929 br_modint_from_monty(mx, mp);
930 }
931 num = 10;
932 for (;;) {
933 clock_t begin, end;
934 double tt;
935 long k;
936
937 begin = clock();
938 for (k = num; k > 0; k --) {
939 br_modint_to_monty(mx, mp);
940 br_modint_montypow(mx, me, mp, t1, t2);
941 br_modint_from_monty(mx, mp);
942 }
943 end = clock();
944 tt = (double)(end - begin) / CLOCKS_PER_SEC;
945 if (tt >= 2.0) {
946 printf("%-30s %8.2f exp/s\n", "pow[2048:256]",
947 (double)num / tt);
948 fflush(stdout);
949 return;
950 }
951 num <<= 1;
952 }
953 }
954
955 static void
956 test_speed_moddiv(void)
957 {
958 uint32_t mx[65], my[65], mp[65], t1[65], t2[65], t3[65], len;
959 unsigned char x[255], y[255];
960 int i;
961 long num;
962
963 len = br_int_decode(mp, sizeof mp / sizeof mp[0],
964 P2048, sizeof P2048);
965 if (len != 65) {
966 abort();
967 }
968 memset(x, 'T', sizeof x);
969 memset(y, 'P', sizeof y);
970 if (!br_modint_decode(mx, mp, x, sizeof x)) {
971 abort();
972 }
973 if (!br_modint_decode(my, mp, y, sizeof y)) {
974 abort();
975 }
976 for (i = 0; i < 10; i ++) {
977 br_modint_div(mx, my, mp, t1, t2, t3);
978 }
979 num = 10;
980 for (;;) {
981 clock_t begin, end;
982 double tt;
983 long k;
984
985 begin = clock();
986 for (k = num; k > 0; k --) {
987 br_modint_div(mx, my, mp, t1, t2, t3);
988 }
989 end = clock();
990 tt = (double)(end - begin) / CLOCKS_PER_SEC;
991 if (tt >= 2.0) {
992 printf("%-30s %8.2f div/s\n", "div[2048]",
993 (double)num / tt);
994 fflush(stdout);
995 return;
996 }
997 num <<= 1;
998 }
999 }
1000 #endif
1001
1002 #define STU(x) { test_speed_ ## x, #x }
1003
1004 static const struct {
1005 void (*fn)(void);
1006 char *name;
1007 } tfns[] = {
1008 STU(md5),
1009 STU(sha1),
1010 STU(sha256),
1011 STU(sha512),
1012
1013 STU(aes128_big_cbcenc),
1014 STU(aes128_big_cbcdec),
1015 STU(aes192_big_cbcenc),
1016 STU(aes192_big_cbcdec),
1017 STU(aes256_big_cbcenc),
1018 STU(aes256_big_cbcdec),
1019 STU(aes128_big_ctr),
1020 STU(aes192_big_ctr),
1021 STU(aes256_big_ctr),
1022
1023 STU(aes128_small_cbcenc),
1024 STU(aes128_small_cbcdec),
1025 STU(aes192_small_cbcenc),
1026 STU(aes192_small_cbcdec),
1027 STU(aes256_small_cbcenc),
1028 STU(aes256_small_cbcdec),
1029 STU(aes128_small_ctr),
1030 STU(aes192_small_ctr),
1031 STU(aes256_small_ctr),
1032
1033 STU(aes128_ct_cbcenc),
1034 STU(aes128_ct_cbcdec),
1035 STU(aes192_ct_cbcenc),
1036 STU(aes192_ct_cbcdec),
1037 STU(aes256_ct_cbcenc),
1038 STU(aes256_ct_cbcdec),
1039 STU(aes128_ct_ctr),
1040 STU(aes192_ct_ctr),
1041 STU(aes256_ct_ctr),
1042
1043 STU(aes128_ct64_cbcenc),
1044 STU(aes128_ct64_cbcdec),
1045 STU(aes192_ct64_cbcenc),
1046 STU(aes192_ct64_cbcdec),
1047 STU(aes256_ct64_cbcenc),
1048 STU(aes256_ct64_cbcdec),
1049 STU(aes128_ct64_ctr),
1050 STU(aes192_ct64_ctr),
1051 STU(aes256_ct64_ctr),
1052
1053 STU(des_tab_cbcenc),
1054 STU(des_tab_cbcdec),
1055 STU(3des_tab_cbcenc),
1056 STU(3des_tab_cbcdec),
1057
1058 STU(des_ct_cbcenc),
1059 STU(des_ct_cbcdec),
1060 STU(3des_ct_cbcenc),
1061 STU(3des_ct_cbcdec),
1062
1063 STU(chacha20_ct),
1064
1065 STU(ghash_ctmul),
1066 STU(ghash_ctmul32),
1067 STU(ghash_ctmul64),
1068
1069 STU(rsa_i31),
1070 STU(rsa_i32),
1071 STU(ec_prime_i31),
1072 STU(ecdsa_i31),
1073
1074 STU(i31)
1075 };
1076
1077 static int
1078 eq_name(const char *s1, const char *s2)
1079 {
1080 for (;;) {
1081 int c1, c2;
1082
1083 for (;;) {
1084 c1 = *s1 ++;
1085 if (c1 >= 'A' && c1 <= 'Z') {
1086 c1 += 'a' - 'A';
1087 } else {
1088 switch (c1) {
1089 case '-': case '_': case '.': case ' ':
1090 continue;
1091 }
1092 }
1093 break;
1094 }
1095 for (;;) {
1096 c2 = *s2 ++;
1097 if (c2 >= 'A' && c2 <= 'Z') {
1098 c2 += 'a' - 'A';
1099 } else {
1100 switch (c2) {
1101 case '-': case '_': case '.': case ' ':
1102 continue;
1103 }
1104 }
1105 break;
1106 }
1107 if (c1 != c2) {
1108 return 0;
1109 }
1110 if (c1 == 0) {
1111 return 1;
1112 }
1113 }
1114 }
1115
1116 int
1117 main(int argc, char *argv[])
1118 {
1119 size_t u;
1120
1121 if (argc <= 1) {
1122 printf("usage: testspeed all | name...\n");
1123 printf("individual test names:\n");
1124 for (u = 0; u < (sizeof tfns) / (sizeof tfns[0]); u ++) {
1125 printf(" %s\n", tfns[u].name);
1126 }
1127 } else {
1128 for (u = 0; u < (sizeof tfns) / (sizeof tfns[0]); u ++) {
1129 int i;
1130
1131 for (i = 1; i < argc; i ++) {
1132 if (eq_name(argv[i], tfns[u].name)
1133 || eq_name(argv[i], "all"))
1134 {
1135 tfns[u].fn();
1136 break;
1137 }
1138 }
1139 }
1140 }
1141 return 0;
1142 }