xref: /freebsd/crypto/openssl/apps/speed.c (revision 5b56413d04e608379c9a306373554a8e4d321bc0)
1 /*
2  * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved.
3  * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved
4  *
5  * Licensed under the Apache License 2.0 (the "License").  You may not use
6  * this file except in compliance with the License.  You can obtain a copy
7  * in the file LICENSE in the source distribution or at
8  * https://www.openssl.org/source/license.html
9  */
10 
11 #undef SECONDS
12 #define SECONDS          3
13 #define PKEY_SECONDS    10
14 
15 #define RSA_SECONDS     PKEY_SECONDS
16 #define DSA_SECONDS     PKEY_SECONDS
17 #define ECDSA_SECONDS   PKEY_SECONDS
18 #define ECDH_SECONDS    PKEY_SECONDS
19 #define EdDSA_SECONDS   PKEY_SECONDS
20 #define SM2_SECONDS     PKEY_SECONDS
21 #define FFDH_SECONDS    PKEY_SECONDS
22 
23 /* We need to use some deprecated APIs */
24 #define OPENSSL_SUPPRESS_DEPRECATED
25 
26 #include <stdio.h>
27 #include <stdlib.h>
28 #include <string.h>
29 #include <math.h>
30 #include "apps.h"
31 #include "progs.h"
32 #include "internal/numbers.h"
33 #include <openssl/crypto.h>
34 #include <openssl/rand.h>
35 #include <openssl/err.h>
36 #include <openssl/evp.h>
37 #include <openssl/objects.h>
38 #include <openssl/core_names.h>
39 #include <openssl/async.h>
40 #if !defined(OPENSSL_SYS_MSDOS)
41 # include <unistd.h>
42 #endif
43 
44 #if defined(__TANDEM)
45 # if defined(OPENSSL_TANDEM_FLOSS)
46 #  include <floss.h(floss_fork)>
47 # endif
48 #endif
49 
50 #if defined(_WIN32)
51 # include <windows.h>
52 #endif
53 
54 #include <openssl/bn.h>
55 #include <openssl/rsa.h>
56 #include "./testrsa.h"
57 #ifndef OPENSSL_NO_DH
58 # include <openssl/dh.h>
59 #endif
60 #include <openssl/x509.h>
61 #include <openssl/dsa.h>
62 #include "./testdsa.h"
63 #include <openssl/modes.h>
64 
65 #ifndef HAVE_FORK
66 # if defined(OPENSSL_SYS_VMS) || defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_VXWORKS)
67 #  define HAVE_FORK 0
68 # else
69 #  define HAVE_FORK 1
70 #  include <sys/wait.h>
71 # endif
72 #endif
73 
74 #if HAVE_FORK
75 # undef NO_FORK
76 #else
77 # define NO_FORK
78 #endif
79 
80 #define MAX_MISALIGNMENT 63
81 #define MAX_ECDH_SIZE   256
82 #define MISALIGN        64
83 #define MAX_FFDH_SIZE 1024
84 
85 #ifndef RSA_DEFAULT_PRIME_NUM
86 # define RSA_DEFAULT_PRIME_NUM 2
87 #endif
88 
89 typedef struct openssl_speed_sec_st {
90     int sym;
91     int rsa;
92     int dsa;
93     int ecdsa;
94     int ecdh;
95     int eddsa;
96     int sm2;
97     int ffdh;
98 } openssl_speed_sec_t;
99 
100 static volatile int run = 0;
101 
102 static int mr = 0;  /* machine-readeable output format to merge fork results */
103 static int usertime = 1;
104 
105 static double Time_F(int s);
106 static void print_message(const char *s, long num, int length, int tm);
107 static void pkey_print_message(const char *str, const char *str2,
108                                long num, unsigned int bits, int sec);
109 static void print_result(int alg, int run_no, int count, double time_used);
110 #ifndef NO_FORK
111 static int do_multi(int multi, int size_num);
112 #endif
113 
114 static const int lengths_list[] = {
115     16, 64, 256, 1024, 8 * 1024, 16 * 1024
116 };
117 #define SIZE_NUM         OSSL_NELEM(lengths_list)
118 static const int *lengths = lengths_list;
119 
120 static const int aead_lengths_list[] = {
121     2, 31, 136, 1024, 8 * 1024, 16 * 1024
122 };
123 
124 #define START   0
125 #define STOP    1
126 
127 #ifdef SIGALRM
128 
129 static void alarmed(int sig)
130 {
131     signal(SIGALRM, alarmed);
132     run = 0;
133 }
134 
135 static double Time_F(int s)
136 {
137     double ret = app_tminterval(s, usertime);
138     if (s == STOP)
139         alarm(0);
140     return ret;
141 }
142 
143 #elif defined(_WIN32)
144 
145 # define SIGALRM -1
146 
147 static unsigned int lapse;
148 static volatile unsigned int schlock;
149 static void alarm_win32(unsigned int secs)
150 {
151     lapse = secs * 1000;
152 }
153 
154 # define alarm alarm_win32
155 
156 static DWORD WINAPI sleepy(VOID * arg)
157 {
158     schlock = 1;
159     Sleep(lapse);
160     run = 0;
161     return 0;
162 }
163 
164 static double Time_F(int s)
165 {
166     double ret;
167     static HANDLE thr;
168 
169     if (s == START) {
170         schlock = 0;
171         thr = CreateThread(NULL, 4096, sleepy, NULL, 0, NULL);
172         if (thr == NULL) {
173             DWORD err = GetLastError();
174             BIO_printf(bio_err, "unable to CreateThread (%lu)", err);
175             ExitProcess(err);
176         }
177         while (!schlock)
178             Sleep(0);           /* scheduler spinlock */
179         ret = app_tminterval(s, usertime);
180     } else {
181         ret = app_tminterval(s, usertime);
182         if (run)
183             TerminateThread(thr, 0);
184         CloseHandle(thr);
185     }
186 
187     return ret;
188 }
189 #else
190 # error "SIGALRM not defined and the platform is not Windows"
191 #endif
192 
193 static void multiblock_speed(const EVP_CIPHER *evp_cipher, int lengths_single,
194                              const openssl_speed_sec_t *seconds);
195 
196 static int opt_found(const char *name, unsigned int *result,
197                      const OPT_PAIR pairs[], unsigned int nbelem)
198 {
199     unsigned int idx;
200 
201     for (idx = 0; idx < nbelem; ++idx, pairs++)
202         if (strcmp(name, pairs->name) == 0) {
203             *result = pairs->retval;
204             return 1;
205         }
206     return 0;
207 }
208 #define opt_found(value, pairs, result)\
209     opt_found(value, result, pairs, OSSL_NELEM(pairs))
210 
211 typedef enum OPTION_choice {
212     OPT_COMMON,
213     OPT_ELAPSED, OPT_EVP, OPT_HMAC, OPT_DECRYPT, OPT_ENGINE, OPT_MULTI,
214     OPT_MR, OPT_MB, OPT_MISALIGN, OPT_ASYNCJOBS, OPT_R_ENUM, OPT_PROV_ENUM,
215     OPT_PRIMES, OPT_SECONDS, OPT_BYTES, OPT_AEAD, OPT_CMAC
216 } OPTION_CHOICE;
217 
218 const OPTIONS speed_options[] = {
219     {OPT_HELP_STR, 1, '-', "Usage: %s [options] [algorithm...]\n"},
220 
221     OPT_SECTION("General"),
222     {"help", OPT_HELP, '-', "Display this summary"},
223     {"mb", OPT_MB, '-',
224      "Enable (tls1>=1) multi-block mode on EVP-named cipher"},
225     {"mr", OPT_MR, '-', "Produce machine readable output"},
226 #ifndef NO_FORK
227     {"multi", OPT_MULTI, 'p', "Run benchmarks in parallel"},
228 #endif
229 #ifndef OPENSSL_NO_ASYNC
230     {"async_jobs", OPT_ASYNCJOBS, 'p',
231      "Enable async mode and start specified number of jobs"},
232 #endif
233 #ifndef OPENSSL_NO_ENGINE
234     {"engine", OPT_ENGINE, 's', "Use engine, possibly a hardware device"},
235 #endif
236     {"primes", OPT_PRIMES, 'p', "Specify number of primes (for RSA only)"},
237 
238     OPT_SECTION("Selection"),
239     {"evp", OPT_EVP, 's', "Use EVP-named cipher or digest"},
240     {"hmac", OPT_HMAC, 's', "HMAC using EVP-named digest"},
241     {"cmac", OPT_CMAC, 's', "CMAC using EVP-named cipher"},
242     {"decrypt", OPT_DECRYPT, '-',
243      "Time decryption instead of encryption (only EVP)"},
244     {"aead", OPT_AEAD, '-',
245      "Benchmark EVP-named AEAD cipher in TLS-like sequence"},
246 
247     OPT_SECTION("Timing"),
248     {"elapsed", OPT_ELAPSED, '-',
249      "Use wall-clock time instead of CPU user time as divisor"},
250     {"seconds", OPT_SECONDS, 'p',
251      "Run benchmarks for specified amount of seconds"},
252     {"bytes", OPT_BYTES, 'p',
253      "Run [non-PKI] benchmarks on custom-sized buffer"},
254     {"misalign", OPT_MISALIGN, 'p',
255      "Use specified offset to mis-align buffers"},
256 
257     OPT_R_OPTIONS,
258     OPT_PROV_OPTIONS,
259 
260     OPT_PARAMETERS(),
261     {"algorithm", 0, 0, "Algorithm(s) to test (optional; otherwise tests all)"},
262     {NULL}
263 };
264 
265 enum {
266     D_MD2, D_MDC2, D_MD4, D_MD5, D_SHA1, D_RMD160,
267     D_SHA256, D_SHA512, D_WHIRLPOOL, D_HMAC,
268     D_CBC_DES, D_EDE3_DES, D_RC4, D_CBC_IDEA, D_CBC_SEED,
269     D_CBC_RC2, D_CBC_RC5, D_CBC_BF, D_CBC_CAST,
270     D_CBC_128_AES, D_CBC_192_AES, D_CBC_256_AES,
271     D_CBC_128_CML, D_CBC_192_CML, D_CBC_256_CML,
272     D_EVP, D_GHASH, D_RAND, D_EVP_CMAC, ALGOR_NUM
273 };
274 /* name of algorithms to test. MUST BE KEEP IN SYNC with above enum ! */
275 static const char *names[ALGOR_NUM] = {
276     "md2", "mdc2", "md4", "md5", "sha1", "rmd160",
277     "sha256", "sha512", "whirlpool", "hmac(md5)",
278     "des-cbc", "des-ede3", "rc4", "idea-cbc", "seed-cbc",
279     "rc2-cbc", "rc5-cbc", "blowfish", "cast-cbc",
280     "aes-128-cbc", "aes-192-cbc", "aes-256-cbc",
281     "camellia-128-cbc", "camellia-192-cbc", "camellia-256-cbc",
282     "evp", "ghash", "rand", "cmac"
283 };
284 
285 /* list of configured algorithm (remaining), with some few alias */
286 static const OPT_PAIR doit_choices[] = {
287     {"md2", D_MD2},
288     {"mdc2", D_MDC2},
289     {"md4", D_MD4},
290     {"md5", D_MD5},
291     {"hmac", D_HMAC},
292     {"sha1", D_SHA1},
293     {"sha256", D_SHA256},
294     {"sha512", D_SHA512},
295     {"whirlpool", D_WHIRLPOOL},
296     {"ripemd", D_RMD160},
297     {"rmd160", D_RMD160},
298     {"ripemd160", D_RMD160},
299     {"rc4", D_RC4},
300     {"des-cbc", D_CBC_DES},
301     {"des-ede3", D_EDE3_DES},
302     {"aes-128-cbc", D_CBC_128_AES},
303     {"aes-192-cbc", D_CBC_192_AES},
304     {"aes-256-cbc", D_CBC_256_AES},
305     {"camellia-128-cbc", D_CBC_128_CML},
306     {"camellia-192-cbc", D_CBC_192_CML},
307     {"camellia-256-cbc", D_CBC_256_CML},
308     {"rc2-cbc", D_CBC_RC2},
309     {"rc2", D_CBC_RC2},
310     {"rc5-cbc", D_CBC_RC5},
311     {"rc5", D_CBC_RC5},
312     {"idea-cbc", D_CBC_IDEA},
313     {"idea", D_CBC_IDEA},
314     {"seed-cbc", D_CBC_SEED},
315     {"seed", D_CBC_SEED},
316     {"bf-cbc", D_CBC_BF},
317     {"blowfish", D_CBC_BF},
318     {"bf", D_CBC_BF},
319     {"cast-cbc", D_CBC_CAST},
320     {"cast", D_CBC_CAST},
321     {"cast5", D_CBC_CAST},
322     {"ghash", D_GHASH},
323     {"rand", D_RAND}
324 };
325 
326 static double results[ALGOR_NUM][SIZE_NUM];
327 
328 enum { R_DSA_512, R_DSA_1024, R_DSA_2048, DSA_NUM };
329 static const OPT_PAIR dsa_choices[DSA_NUM] = {
330     {"dsa512", R_DSA_512},
331     {"dsa1024", R_DSA_1024},
332     {"dsa2048", R_DSA_2048}
333 };
334 static double dsa_results[DSA_NUM][2];  /* 2 ops: sign then verify */
335 
336 enum {
337     R_RSA_512, R_RSA_1024, R_RSA_2048, R_RSA_3072, R_RSA_4096, R_RSA_7680,
338     R_RSA_15360, RSA_NUM
339 };
340 static const OPT_PAIR rsa_choices[RSA_NUM] = {
341     {"rsa512", R_RSA_512},
342     {"rsa1024", R_RSA_1024},
343     {"rsa2048", R_RSA_2048},
344     {"rsa3072", R_RSA_3072},
345     {"rsa4096", R_RSA_4096},
346     {"rsa7680", R_RSA_7680},
347     {"rsa15360", R_RSA_15360}
348 };
349 
350 static double rsa_results[RSA_NUM][2];  /* 2 ops: sign then verify */
351 
352 #ifndef OPENSSL_NO_DH
353 enum ff_params_t {
354     R_FFDH_2048, R_FFDH_3072, R_FFDH_4096, R_FFDH_6144, R_FFDH_8192, FFDH_NUM
355 };
356 
357 static const OPT_PAIR ffdh_choices[FFDH_NUM] = {
358     {"ffdh2048", R_FFDH_2048},
359     {"ffdh3072", R_FFDH_3072},
360     {"ffdh4096", R_FFDH_4096},
361     {"ffdh6144", R_FFDH_6144},
362     {"ffdh8192", R_FFDH_8192},
363 };
364 
365 static double ffdh_results[FFDH_NUM][1];  /* 1 op: derivation */
366 #endif /* OPENSSL_NO_DH */
367 
368 enum ec_curves_t {
369     R_EC_P160, R_EC_P192, R_EC_P224, R_EC_P256, R_EC_P384, R_EC_P521,
370 #ifndef OPENSSL_NO_EC2M
371     R_EC_K163, R_EC_K233, R_EC_K283, R_EC_K409, R_EC_K571,
372     R_EC_B163, R_EC_B233, R_EC_B283, R_EC_B409, R_EC_B571,
373 #endif
374     R_EC_BRP256R1, R_EC_BRP256T1, R_EC_BRP384R1, R_EC_BRP384T1,
375     R_EC_BRP512R1, R_EC_BRP512T1, ECDSA_NUM
376 };
377 /* list of ecdsa curves */
378 static const OPT_PAIR ecdsa_choices[ECDSA_NUM] = {
379     {"ecdsap160", R_EC_P160},
380     {"ecdsap192", R_EC_P192},
381     {"ecdsap224", R_EC_P224},
382     {"ecdsap256", R_EC_P256},
383     {"ecdsap384", R_EC_P384},
384     {"ecdsap521", R_EC_P521},
385 #ifndef OPENSSL_NO_EC2M
386     {"ecdsak163", R_EC_K163},
387     {"ecdsak233", R_EC_K233},
388     {"ecdsak283", R_EC_K283},
389     {"ecdsak409", R_EC_K409},
390     {"ecdsak571", R_EC_K571},
391     {"ecdsab163", R_EC_B163},
392     {"ecdsab233", R_EC_B233},
393     {"ecdsab283", R_EC_B283},
394     {"ecdsab409", R_EC_B409},
395     {"ecdsab571", R_EC_B571},
396 #endif
397     {"ecdsabrp256r1", R_EC_BRP256R1},
398     {"ecdsabrp256t1", R_EC_BRP256T1},
399     {"ecdsabrp384r1", R_EC_BRP384R1},
400     {"ecdsabrp384t1", R_EC_BRP384T1},
401     {"ecdsabrp512r1", R_EC_BRP512R1},
402     {"ecdsabrp512t1", R_EC_BRP512T1}
403 };
404 enum { R_EC_X25519 = ECDSA_NUM, R_EC_X448, EC_NUM };
405 /* list of ecdh curves, extension of |ecdsa_choices| list above */
406 static const OPT_PAIR ecdh_choices[EC_NUM] = {
407     {"ecdhp160", R_EC_P160},
408     {"ecdhp192", R_EC_P192},
409     {"ecdhp224", R_EC_P224},
410     {"ecdhp256", R_EC_P256},
411     {"ecdhp384", R_EC_P384},
412     {"ecdhp521", R_EC_P521},
413 #ifndef OPENSSL_NO_EC2M
414     {"ecdhk163", R_EC_K163},
415     {"ecdhk233", R_EC_K233},
416     {"ecdhk283", R_EC_K283},
417     {"ecdhk409", R_EC_K409},
418     {"ecdhk571", R_EC_K571},
419     {"ecdhb163", R_EC_B163},
420     {"ecdhb233", R_EC_B233},
421     {"ecdhb283", R_EC_B283},
422     {"ecdhb409", R_EC_B409},
423     {"ecdhb571", R_EC_B571},
424 #endif
425     {"ecdhbrp256r1", R_EC_BRP256R1},
426     {"ecdhbrp256t1", R_EC_BRP256T1},
427     {"ecdhbrp384r1", R_EC_BRP384R1},
428     {"ecdhbrp384t1", R_EC_BRP384T1},
429     {"ecdhbrp512r1", R_EC_BRP512R1},
430     {"ecdhbrp512t1", R_EC_BRP512T1},
431     {"ecdhx25519", R_EC_X25519},
432     {"ecdhx448", R_EC_X448}
433 };
434 
435 static double ecdh_results[EC_NUM][1];      /* 1 op: derivation */
436 static double ecdsa_results[ECDSA_NUM][2];  /* 2 ops: sign then verify */
437 
438 enum { R_EC_Ed25519, R_EC_Ed448, EdDSA_NUM };
439 static const OPT_PAIR eddsa_choices[EdDSA_NUM] = {
440     {"ed25519", R_EC_Ed25519},
441     {"ed448", R_EC_Ed448}
442 
443 };
444 static double eddsa_results[EdDSA_NUM][2];    /* 2 ops: sign then verify */
445 
446 #ifndef OPENSSL_NO_SM2
447 enum { R_EC_CURVESM2, SM2_NUM };
448 static const OPT_PAIR sm2_choices[SM2_NUM] = {
449     {"curveSM2", R_EC_CURVESM2}
450 };
451 # define SM2_ID        "TLSv1.3+GM+Cipher+Suite"
452 # define SM2_ID_LEN    sizeof("TLSv1.3+GM+Cipher+Suite") - 1
453 static double sm2_results[SM2_NUM][2];    /* 2 ops: sign then verify */
454 #endif /* OPENSSL_NO_SM2 */
455 
456 #define COND(unused_cond) (run && count < INT_MAX)
457 #define COUNT(d) (count)
458 
459 typedef struct loopargs_st {
460     ASYNC_JOB *inprogress_job;
461     ASYNC_WAIT_CTX *wait_ctx;
462     unsigned char *buf;
463     unsigned char *buf2;
464     unsigned char *buf_malloc;
465     unsigned char *buf2_malloc;
466     unsigned char *key;
467     size_t buflen;
468     size_t sigsize;
469     EVP_PKEY_CTX *rsa_sign_ctx[RSA_NUM];
470     EVP_PKEY_CTX *rsa_verify_ctx[RSA_NUM];
471     EVP_PKEY_CTX *dsa_sign_ctx[DSA_NUM];
472     EVP_PKEY_CTX *dsa_verify_ctx[DSA_NUM];
473     EVP_PKEY_CTX *ecdsa_sign_ctx[ECDSA_NUM];
474     EVP_PKEY_CTX *ecdsa_verify_ctx[ECDSA_NUM];
475     EVP_PKEY_CTX *ecdh_ctx[EC_NUM];
476     EVP_MD_CTX *eddsa_ctx[EdDSA_NUM];
477     EVP_MD_CTX *eddsa_ctx2[EdDSA_NUM];
478 #ifndef OPENSSL_NO_SM2
479     EVP_MD_CTX *sm2_ctx[SM2_NUM];
480     EVP_MD_CTX *sm2_vfy_ctx[SM2_NUM];
481     EVP_PKEY *sm2_pkey[SM2_NUM];
482 #endif
483     unsigned char *secret_a;
484     unsigned char *secret_b;
485     size_t outlen[EC_NUM];
486 #ifndef OPENSSL_NO_DH
487     EVP_PKEY_CTX *ffdh_ctx[FFDH_NUM];
488     unsigned char *secret_ff_a;
489     unsigned char *secret_ff_b;
490 #endif
491     EVP_CIPHER_CTX *ctx;
492     EVP_MAC_CTX *mctx;
493 } loopargs_t;
494 static int run_benchmark(int async_jobs, int (*loop_function) (void *),
495                          loopargs_t * loopargs);
496 
497 static unsigned int testnum;
498 
499 /* Nb of iterations to do per algorithm and key-size */
500 static long c[ALGOR_NUM][SIZE_NUM];
501 
502 static char *evp_mac_mdname = "md5";
503 static char *evp_hmac_name = NULL;
504 static const char *evp_md_name = NULL;
505 static char *evp_mac_ciphername = "aes-128-cbc";
506 static char *evp_cmac_name = NULL;
507 
508 static int have_md(const char *name)
509 {
510     int ret = 0;
511     EVP_MD *md = NULL;
512 
513     if (opt_md_silent(name, &md)) {
514         EVP_MD_CTX *ctx = EVP_MD_CTX_new();
515 
516         if (ctx != NULL && EVP_DigestInit(ctx, md) > 0)
517             ret = 1;
518         EVP_MD_CTX_free(ctx);
519         EVP_MD_free(md);
520     }
521     return ret;
522 }
523 
524 static int have_cipher(const char *name)
525 {
526     int ret = 0;
527     EVP_CIPHER *cipher = NULL;
528 
529     if (opt_cipher_silent(name, &cipher)) {
530         EVP_CIPHER_CTX *ctx = EVP_CIPHER_CTX_new();
531 
532         if (ctx != NULL
533             && EVP_CipherInit_ex(ctx, cipher, NULL, NULL, NULL, 1) > 0)
534             ret = 1;
535         EVP_CIPHER_CTX_free(ctx);
536         EVP_CIPHER_free(cipher);
537     }
538     return ret;
539 }
540 
541 static int EVP_Digest_loop(const char *mdname, int algindex, void *args)
542 {
543     loopargs_t *tempargs = *(loopargs_t **) args;
544     unsigned char *buf = tempargs->buf;
545     unsigned char digest[EVP_MAX_MD_SIZE];
546     int count;
547     EVP_MD *md = NULL;
548 
549     if (!opt_md_silent(mdname, &md))
550         return -1;
551     for (count = 0; COND(c[algindex][testnum]); count++) {
552         if (!EVP_Digest(buf, (size_t)lengths[testnum], digest, NULL, md,
553                         NULL)) {
554             count = -1;
555             break;
556         }
557     }
558     EVP_MD_free(md);
559     return count;
560 }
561 
562 static int EVP_Digest_md_loop(void *args)
563 {
564     return EVP_Digest_loop(evp_md_name, D_EVP, args);
565 }
566 
567 static int EVP_Digest_MD2_loop(void *args)
568 {
569     return EVP_Digest_loop("md2", D_MD2, args);
570 }
571 
572 static int EVP_Digest_MDC2_loop(void *args)
573 {
574     return EVP_Digest_loop("mdc2", D_MDC2, args);
575 }
576 
577 static int EVP_Digest_MD4_loop(void *args)
578 {
579     return EVP_Digest_loop("md4", D_MD4, args);
580 }
581 
582 static int MD5_loop(void *args)
583 {
584     return EVP_Digest_loop("md5", D_MD5, args);
585 }
586 
587 static int EVP_MAC_loop(int algindex, void *args)
588 {
589     loopargs_t *tempargs = *(loopargs_t **) args;
590     unsigned char *buf = tempargs->buf;
591     EVP_MAC_CTX *mctx = tempargs->mctx;
592     unsigned char mac[EVP_MAX_MD_SIZE];
593     int count;
594 
595     for (count = 0; COND(c[algindex][testnum]); count++) {
596         size_t outl;
597 
598         if (!EVP_MAC_init(mctx, NULL, 0, NULL)
599             || !EVP_MAC_update(mctx, buf, lengths[testnum])
600             || !EVP_MAC_final(mctx, mac, &outl, sizeof(mac)))
601             return -1;
602     }
603     return count;
604 }
605 
606 static int HMAC_loop(void *args)
607 {
608     return EVP_MAC_loop(D_HMAC, args);
609 }
610 
611 static int CMAC_loop(void *args)
612 {
613     return EVP_MAC_loop(D_EVP_CMAC, args);
614 }
615 
616 static int SHA1_loop(void *args)
617 {
618     return EVP_Digest_loop("sha1", D_SHA1, args);
619 }
620 
621 static int SHA256_loop(void *args)
622 {
623     return EVP_Digest_loop("sha256", D_SHA256, args);
624 }
625 
626 static int SHA512_loop(void *args)
627 {
628     return EVP_Digest_loop("sha512", D_SHA512, args);
629 }
630 
631 static int WHIRLPOOL_loop(void *args)
632 {
633     return EVP_Digest_loop("whirlpool", D_WHIRLPOOL, args);
634 }
635 
636 static int EVP_Digest_RMD160_loop(void *args)
637 {
638     return EVP_Digest_loop("ripemd160", D_RMD160, args);
639 }
640 
641 static int algindex;
642 
643 static int EVP_Cipher_loop(void *args)
644 {
645     loopargs_t *tempargs = *(loopargs_t **) args;
646     unsigned char *buf = tempargs->buf;
647     int count;
648 
649     if (tempargs->ctx == NULL)
650         return -1;
651     for (count = 0; COND(c[algindex][testnum]); count++)
652         if (EVP_Cipher(tempargs->ctx, buf, buf, (size_t)lengths[testnum]) <= 0)
653             return -1;
654     return count;
655 }
656 
657 static int GHASH_loop(void *args)
658 {
659     loopargs_t *tempargs = *(loopargs_t **) args;
660     unsigned char *buf = tempargs->buf;
661     EVP_MAC_CTX *mctx = tempargs->mctx;
662     int count;
663 
664     /* just do the update in the loop to be comparable with 1.1.1 */
665     for (count = 0; COND(c[D_GHASH][testnum]); count++) {
666         if (!EVP_MAC_update(mctx, buf, lengths[testnum]))
667             return -1;
668     }
669     return count;
670 }
671 
672 #define MAX_BLOCK_SIZE 128
673 
674 static unsigned char iv[2 * MAX_BLOCK_SIZE / 8];
675 
676 static EVP_CIPHER_CTX *init_evp_cipher_ctx(const char *ciphername,
677                                            const unsigned char *key,
678                                            int keylen)
679 {
680     EVP_CIPHER_CTX *ctx = NULL;
681     EVP_CIPHER *cipher = NULL;
682 
683     if (!opt_cipher_silent(ciphername, &cipher))
684         return NULL;
685 
686     if ((ctx = EVP_CIPHER_CTX_new()) == NULL)
687         goto end;
688 
689     if (!EVP_CipherInit_ex(ctx, cipher, NULL, NULL, NULL, 1)) {
690         EVP_CIPHER_CTX_free(ctx);
691         ctx = NULL;
692         goto end;
693     }
694 
695     if (EVP_CIPHER_CTX_set_key_length(ctx, keylen) <= 0) {
696         EVP_CIPHER_CTX_free(ctx);
697         ctx = NULL;
698         goto end;
699     }
700 
701     if (!EVP_CipherInit_ex(ctx, NULL, NULL, key, iv, 1)) {
702         EVP_CIPHER_CTX_free(ctx);
703         ctx = NULL;
704         goto end;
705     }
706 
707 end:
708     EVP_CIPHER_free(cipher);
709     return ctx;
710 }
711 
712 static int RAND_bytes_loop(void *args)
713 {
714     loopargs_t *tempargs = *(loopargs_t **) args;
715     unsigned char *buf = tempargs->buf;
716     int count;
717 
718     for (count = 0; COND(c[D_RAND][testnum]); count++)
719         RAND_bytes(buf, lengths[testnum]);
720     return count;
721 }
722 
723 static int decrypt = 0;
724 static int EVP_Update_loop(void *args)
725 {
726     loopargs_t *tempargs = *(loopargs_t **) args;
727     unsigned char *buf = tempargs->buf;
728     EVP_CIPHER_CTX *ctx = tempargs->ctx;
729     int outl, count, rc;
730     unsigned char faketag[16] = { 0xcc };
731 
732     if (decrypt) {
733         if (EVP_CIPHER_get_flags(EVP_CIPHER_CTX_get0_cipher(ctx)) & EVP_CIPH_FLAG_AEAD_CIPHER) {
734             (void)EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_SET_TAG, sizeof(faketag), faketag);
735         }
736         for (count = 0; COND(c[D_EVP][testnum]); count++) {
737             rc = EVP_DecryptUpdate(ctx, buf, &outl, buf, lengths[testnum]);
738             if (rc != 1) {
739                 /* reset iv in case of counter overflow */
740                 EVP_CipherInit_ex(ctx, NULL, NULL, NULL, iv, -1);
741             }
742         }
743     } else {
744         for (count = 0; COND(c[D_EVP][testnum]); count++) {
745             rc = EVP_EncryptUpdate(ctx, buf, &outl, buf, lengths[testnum]);
746             if (rc != 1) {
747                 /* reset iv in case of counter overflow */
748                 EVP_CipherInit_ex(ctx, NULL, NULL, NULL, iv, -1);
749             }
750         }
751     }
752     if (decrypt)
753         EVP_DecryptFinal_ex(ctx, buf, &outl);
754     else
755         EVP_EncryptFinal_ex(ctx, buf, &outl);
756     return count;
757 }
758 
759 /*
760  * CCM does not support streaming. For the purpose of performance measurement,
761  * each message is encrypted using the same (key,iv)-pair. Do not use this
762  * code in your application.
763  */
764 static int EVP_Update_loop_ccm(void *args)
765 {
766     loopargs_t *tempargs = *(loopargs_t **) args;
767     unsigned char *buf = tempargs->buf;
768     EVP_CIPHER_CTX *ctx = tempargs->ctx;
769     int outl, count;
770     unsigned char tag[12];
771 
772     if (decrypt) {
773         for (count = 0; COND(c[D_EVP][testnum]); count++) {
774             (void)EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_SET_TAG, sizeof(tag),
775                                       tag);
776             /* reset iv */
777             (void)EVP_DecryptInit_ex(ctx, NULL, NULL, NULL, iv);
778             /* counter is reset on every update */
779             (void)EVP_DecryptUpdate(ctx, buf, &outl, buf, lengths[testnum]);
780         }
781     } else {
782         for (count = 0; COND(c[D_EVP][testnum]); count++) {
783             /* restore iv length field */
784             (void)EVP_EncryptUpdate(ctx, NULL, &outl, NULL, lengths[testnum]);
785             /* counter is reset on every update */
786             (void)EVP_EncryptUpdate(ctx, buf, &outl, buf, lengths[testnum]);
787         }
788     }
789     if (decrypt)
790         (void)EVP_DecryptFinal_ex(ctx, buf, &outl);
791     else
792         (void)EVP_EncryptFinal_ex(ctx, buf, &outl);
793     return count;
794 }
795 
796 /*
797  * To make AEAD benchmarking more relevant perform TLS-like operations,
798  * 13-byte AAD followed by payload. But don't use TLS-formatted AAD, as
799  * payload length is not actually limited by 16KB...
800  */
801 static int EVP_Update_loop_aead(void *args)
802 {
803     loopargs_t *tempargs = *(loopargs_t **) args;
804     unsigned char *buf = tempargs->buf;
805     EVP_CIPHER_CTX *ctx = tempargs->ctx;
806     int outl, count;
807     unsigned char aad[13] = { 0xcc };
808     unsigned char faketag[16] = { 0xcc };
809 
810     if (decrypt) {
811         for (count = 0; COND(c[D_EVP][testnum]); count++) {
812             (void)EVP_DecryptInit_ex(ctx, NULL, NULL, NULL, iv);
813             (void)EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_SET_TAG,
814                                       sizeof(faketag), faketag);
815             (void)EVP_DecryptUpdate(ctx, NULL, &outl, aad, sizeof(aad));
816             (void)EVP_DecryptUpdate(ctx, buf, &outl, buf, lengths[testnum]);
817             (void)EVP_DecryptFinal_ex(ctx, buf + outl, &outl);
818         }
819     } else {
820         for (count = 0; COND(c[D_EVP][testnum]); count++) {
821             (void)EVP_EncryptInit_ex(ctx, NULL, NULL, NULL, iv);
822             (void)EVP_EncryptUpdate(ctx, NULL, &outl, aad, sizeof(aad));
823             (void)EVP_EncryptUpdate(ctx, buf, &outl, buf, lengths[testnum]);
824             (void)EVP_EncryptFinal_ex(ctx, buf + outl, &outl);
825         }
826     }
827     return count;
828 }
829 
830 static long rsa_c[RSA_NUM][2];  /* # RSA iteration test */
831 
832 static int RSA_sign_loop(void *args)
833 {
834     loopargs_t *tempargs = *(loopargs_t **) args;
835     unsigned char *buf = tempargs->buf;
836     unsigned char *buf2 = tempargs->buf2;
837     size_t *rsa_num = &tempargs->sigsize;
838     EVP_PKEY_CTX **rsa_sign_ctx = tempargs->rsa_sign_ctx;
839     int ret, count;
840 
841     for (count = 0; COND(rsa_c[testnum][0]); count++) {
842         *rsa_num = tempargs->buflen;
843         ret = EVP_PKEY_sign(rsa_sign_ctx[testnum], buf2, rsa_num, buf, 36);
844         if (ret <= 0) {
845             BIO_printf(bio_err, "RSA sign failure\n");
846             ERR_print_errors(bio_err);
847             count = -1;
848             break;
849         }
850     }
851     return count;
852 }
853 
854 static int RSA_verify_loop(void *args)
855 {
856     loopargs_t *tempargs = *(loopargs_t **) args;
857     unsigned char *buf = tempargs->buf;
858     unsigned char *buf2 = tempargs->buf2;
859     size_t rsa_num = tempargs->sigsize;
860     EVP_PKEY_CTX **rsa_verify_ctx = tempargs->rsa_verify_ctx;
861     int ret, count;
862 
863     for (count = 0; COND(rsa_c[testnum][1]); count++) {
864         ret = EVP_PKEY_verify(rsa_verify_ctx[testnum], buf2, rsa_num, buf, 36);
865         if (ret <= 0) {
866             BIO_printf(bio_err, "RSA verify failure\n");
867             ERR_print_errors(bio_err);
868             count = -1;
869             break;
870         }
871     }
872     return count;
873 }
874 
875 #ifndef OPENSSL_NO_DH
876 static long ffdh_c[FFDH_NUM][1];
877 
878 static int FFDH_derive_key_loop(void *args)
879 {
880     loopargs_t *tempargs = *(loopargs_t **) args;
881     EVP_PKEY_CTX *ffdh_ctx = tempargs->ffdh_ctx[testnum];
882     unsigned char *derived_secret = tempargs->secret_ff_a;
883     int count;
884 
885     for (count = 0; COND(ffdh_c[testnum][0]); count++) {
886         /* outlen can be overwritten with a too small value (no padding used) */
887         size_t outlen = MAX_FFDH_SIZE;
888 
889         EVP_PKEY_derive(ffdh_ctx, derived_secret, &outlen);
890     }
891     return count;
892 }
893 #endif /* OPENSSL_NO_DH */
894 
895 static long dsa_c[DSA_NUM][2];
896 static int DSA_sign_loop(void *args)
897 {
898     loopargs_t *tempargs = *(loopargs_t **) args;
899     unsigned char *buf = tempargs->buf;
900     unsigned char *buf2 = tempargs->buf2;
901     size_t *dsa_num = &tempargs->sigsize;
902     EVP_PKEY_CTX **dsa_sign_ctx = tempargs->dsa_sign_ctx;
903     int ret, count;
904 
905     for (count = 0; COND(dsa_c[testnum][0]); count++) {
906         *dsa_num = tempargs->buflen;
907         ret = EVP_PKEY_sign(dsa_sign_ctx[testnum], buf2, dsa_num, buf, 20);
908         if (ret <= 0) {
909             BIO_printf(bio_err, "DSA sign failure\n");
910             ERR_print_errors(bio_err);
911             count = -1;
912             break;
913         }
914     }
915     return count;
916 }
917 
918 static int DSA_verify_loop(void *args)
919 {
920     loopargs_t *tempargs = *(loopargs_t **) args;
921     unsigned char *buf = tempargs->buf;
922     unsigned char *buf2 = tempargs->buf2;
923     size_t dsa_num = tempargs->sigsize;
924     EVP_PKEY_CTX **dsa_verify_ctx = tempargs->dsa_verify_ctx;
925     int ret, count;
926 
927     for (count = 0; COND(dsa_c[testnum][1]); count++) {
928         ret = EVP_PKEY_verify(dsa_verify_ctx[testnum], buf2, dsa_num, buf, 20);
929         if (ret <= 0) {
930             BIO_printf(bio_err, "DSA verify failure\n");
931             ERR_print_errors(bio_err);
932             count = -1;
933             break;
934         }
935     }
936     return count;
937 }
938 
939 static long ecdsa_c[ECDSA_NUM][2];
940 static int ECDSA_sign_loop(void *args)
941 {
942     loopargs_t *tempargs = *(loopargs_t **) args;
943     unsigned char *buf = tempargs->buf;
944     unsigned char *buf2 = tempargs->buf2;
945     size_t *ecdsa_num = &tempargs->sigsize;
946     EVP_PKEY_CTX **ecdsa_sign_ctx = tempargs->ecdsa_sign_ctx;
947     int ret, count;
948 
949     for (count = 0; COND(ecdsa_c[testnum][0]); count++) {
950         *ecdsa_num = tempargs->buflen;
951         ret = EVP_PKEY_sign(ecdsa_sign_ctx[testnum], buf2, ecdsa_num, buf, 20);
952         if (ret <= 0) {
953             BIO_printf(bio_err, "ECDSA sign failure\n");
954             ERR_print_errors(bio_err);
955             count = -1;
956             break;
957         }
958     }
959     return count;
960 }
961 
962 static int ECDSA_verify_loop(void *args)
963 {
964     loopargs_t *tempargs = *(loopargs_t **) args;
965     unsigned char *buf = tempargs->buf;
966     unsigned char *buf2 = tempargs->buf2;
967     size_t ecdsa_num = tempargs->sigsize;
968     EVP_PKEY_CTX **ecdsa_verify_ctx = tempargs->ecdsa_verify_ctx;
969     int ret, count;
970 
971     for (count = 0; COND(ecdsa_c[testnum][1]); count++) {
972         ret = EVP_PKEY_verify(ecdsa_verify_ctx[testnum], buf2, ecdsa_num,
973                               buf, 20);
974         if (ret <= 0) {
975             BIO_printf(bio_err, "ECDSA verify failure\n");
976             ERR_print_errors(bio_err);
977             count = -1;
978             break;
979         }
980     }
981     return count;
982 }
983 
984 /* ******************************************************************** */
985 static long ecdh_c[EC_NUM][1];
986 
987 static int ECDH_EVP_derive_key_loop(void *args)
988 {
989     loopargs_t *tempargs = *(loopargs_t **) args;
990     EVP_PKEY_CTX *ctx = tempargs->ecdh_ctx[testnum];
991     unsigned char *derived_secret = tempargs->secret_a;
992     int count;
993     size_t *outlen = &(tempargs->outlen[testnum]);
994 
995     for (count = 0; COND(ecdh_c[testnum][0]); count++)
996         EVP_PKEY_derive(ctx, derived_secret, outlen);
997 
998     return count;
999 }
1000 
1001 static long eddsa_c[EdDSA_NUM][2];
1002 static int EdDSA_sign_loop(void *args)
1003 {
1004     loopargs_t *tempargs = *(loopargs_t **) args;
1005     unsigned char *buf = tempargs->buf;
1006     EVP_MD_CTX **edctx = tempargs->eddsa_ctx;
1007     unsigned char *eddsasig = tempargs->buf2;
1008     size_t *eddsasigsize = &tempargs->sigsize;
1009     int ret, count;
1010 
1011     for (count = 0; COND(eddsa_c[testnum][0]); count++) {
1012         ret = EVP_DigestSignInit(edctx[testnum], NULL, NULL, NULL, NULL);
1013         if (ret == 0) {
1014             BIO_printf(bio_err, "EdDSA sign init failure\n");
1015             ERR_print_errors(bio_err);
1016             count = -1;
1017             break;
1018         }
1019         ret = EVP_DigestSign(edctx[testnum], eddsasig, eddsasigsize, buf, 20);
1020         if (ret == 0) {
1021             BIO_printf(bio_err, "EdDSA sign failure\n");
1022             ERR_print_errors(bio_err);
1023             count = -1;
1024             break;
1025         }
1026     }
1027     return count;
1028 }
1029 
1030 static int EdDSA_verify_loop(void *args)
1031 {
1032     loopargs_t *tempargs = *(loopargs_t **) args;
1033     unsigned char *buf = tempargs->buf;
1034     EVP_MD_CTX **edctx = tempargs->eddsa_ctx2;
1035     unsigned char *eddsasig = tempargs->buf2;
1036     size_t eddsasigsize = tempargs->sigsize;
1037     int ret, count;
1038 
1039     for (count = 0; COND(eddsa_c[testnum][1]); count++) {
1040         ret = EVP_DigestVerifyInit(edctx[testnum], NULL, NULL, NULL, NULL);
1041         if (ret == 0) {
1042             BIO_printf(bio_err, "EdDSA verify init failure\n");
1043             ERR_print_errors(bio_err);
1044             count = -1;
1045             break;
1046         }
1047         ret = EVP_DigestVerify(edctx[testnum], eddsasig, eddsasigsize, buf, 20);
1048         if (ret != 1) {
1049             BIO_printf(bio_err, "EdDSA verify failure\n");
1050             ERR_print_errors(bio_err);
1051             count = -1;
1052             break;
1053         }
1054     }
1055     return count;
1056 }
1057 
1058 #ifndef OPENSSL_NO_SM2
1059 static long sm2_c[SM2_NUM][2];
1060 static int SM2_sign_loop(void *args)
1061 {
1062     loopargs_t *tempargs = *(loopargs_t **) args;
1063     unsigned char *buf = tempargs->buf;
1064     EVP_MD_CTX **sm2ctx = tempargs->sm2_ctx;
1065     unsigned char *sm2sig = tempargs->buf2;
1066     size_t sm2sigsize;
1067     int ret, count;
1068     EVP_PKEY **sm2_pkey = tempargs->sm2_pkey;
1069     const size_t max_size = EVP_PKEY_get_size(sm2_pkey[testnum]);
1070 
1071     for (count = 0; COND(sm2_c[testnum][0]); count++) {
1072         sm2sigsize = max_size;
1073 
1074         if (!EVP_DigestSignInit(sm2ctx[testnum], NULL, EVP_sm3(),
1075                                 NULL, sm2_pkey[testnum])) {
1076             BIO_printf(bio_err, "SM2 init sign failure\n");
1077             ERR_print_errors(bio_err);
1078             count = -1;
1079             break;
1080         }
1081         ret = EVP_DigestSign(sm2ctx[testnum], sm2sig, &sm2sigsize,
1082                              buf, 20);
1083         if (ret == 0) {
1084             BIO_printf(bio_err, "SM2 sign failure\n");
1085             ERR_print_errors(bio_err);
1086             count = -1;
1087             break;
1088         }
1089         /* update the latest returned size and always use the fixed buffer size */
1090         tempargs->sigsize = sm2sigsize;
1091     }
1092 
1093     return count;
1094 }
1095 
1096 static int SM2_verify_loop(void *args)
1097 {
1098     loopargs_t *tempargs = *(loopargs_t **) args;
1099     unsigned char *buf = tempargs->buf;
1100     EVP_MD_CTX **sm2ctx = tempargs->sm2_vfy_ctx;
1101     unsigned char *sm2sig = tempargs->buf2;
1102     size_t sm2sigsize = tempargs->sigsize;
1103     int ret, count;
1104     EVP_PKEY **sm2_pkey = tempargs->sm2_pkey;
1105 
1106     for (count = 0; COND(sm2_c[testnum][1]); count++) {
1107         if (!EVP_DigestVerifyInit(sm2ctx[testnum], NULL, EVP_sm3(),
1108                                   NULL, sm2_pkey[testnum])) {
1109             BIO_printf(bio_err, "SM2 verify init failure\n");
1110             ERR_print_errors(bio_err);
1111             count = -1;
1112             break;
1113         }
1114         ret = EVP_DigestVerify(sm2ctx[testnum], sm2sig, sm2sigsize,
1115                                buf, 20);
1116         if (ret != 1) {
1117             BIO_printf(bio_err, "SM2 verify failure\n");
1118             ERR_print_errors(bio_err);
1119             count = -1;
1120             break;
1121         }
1122     }
1123     return count;
1124 }
1125 #endif                         /* OPENSSL_NO_SM2 */
1126 
1127 static int run_benchmark(int async_jobs,
1128                          int (*loop_function) (void *), loopargs_t * loopargs)
1129 {
1130     int job_op_count = 0;
1131     int total_op_count = 0;
1132     int num_inprogress = 0;
1133     int error = 0, i = 0, ret = 0;
1134     OSSL_ASYNC_FD job_fd = 0;
1135     size_t num_job_fds = 0;
1136 
1137     if (async_jobs == 0) {
1138         return loop_function((void *)&loopargs);
1139     }
1140 
1141     for (i = 0; i < async_jobs && !error; i++) {
1142         loopargs_t *looparg_item = loopargs + i;
1143 
1144         /* Copy pointer content (looparg_t item address) into async context */
1145         ret = ASYNC_start_job(&loopargs[i].inprogress_job, loopargs[i].wait_ctx,
1146                               &job_op_count, loop_function,
1147                               (void *)&looparg_item, sizeof(looparg_item));
1148         switch (ret) {
1149         case ASYNC_PAUSE:
1150             ++num_inprogress;
1151             break;
1152         case ASYNC_FINISH:
1153             if (job_op_count == -1) {
1154                 error = 1;
1155             } else {
1156                 total_op_count += job_op_count;
1157             }
1158             break;
1159         case ASYNC_NO_JOBS:
1160         case ASYNC_ERR:
1161             BIO_printf(bio_err, "Failure in the job\n");
1162             ERR_print_errors(bio_err);
1163             error = 1;
1164             break;
1165         }
1166     }
1167 
1168     while (num_inprogress > 0) {
1169 #if defined(OPENSSL_SYS_WINDOWS)
1170         DWORD avail = 0;
1171 #elif defined(OPENSSL_SYS_UNIX)
1172         int select_result = 0;
1173         OSSL_ASYNC_FD max_fd = 0;
1174         fd_set waitfdset;
1175 
1176         FD_ZERO(&waitfdset);
1177 
1178         for (i = 0; i < async_jobs && num_inprogress > 0; i++) {
1179             if (loopargs[i].inprogress_job == NULL)
1180                 continue;
1181 
1182             if (!ASYNC_WAIT_CTX_get_all_fds
1183                 (loopargs[i].wait_ctx, NULL, &num_job_fds)
1184                 || num_job_fds > 1) {
1185                 BIO_printf(bio_err, "Too many fds in ASYNC_WAIT_CTX\n");
1186                 ERR_print_errors(bio_err);
1187                 error = 1;
1188                 break;
1189             }
1190             ASYNC_WAIT_CTX_get_all_fds(loopargs[i].wait_ctx, &job_fd,
1191                                        &num_job_fds);
1192             FD_SET(job_fd, &waitfdset);
1193             if (job_fd > max_fd)
1194                 max_fd = job_fd;
1195         }
1196 
1197         if (max_fd >= (OSSL_ASYNC_FD)FD_SETSIZE) {
1198             BIO_printf(bio_err,
1199                        "Error: max_fd (%d) must be smaller than FD_SETSIZE (%d). "
1200                        "Decrease the value of async_jobs\n",
1201                        max_fd, FD_SETSIZE);
1202             ERR_print_errors(bio_err);
1203             error = 1;
1204             break;
1205         }
1206 
1207         select_result = select(max_fd + 1, &waitfdset, NULL, NULL, NULL);
1208         if (select_result == -1 && errno == EINTR)
1209             continue;
1210 
1211         if (select_result == -1) {
1212             BIO_printf(bio_err, "Failure in the select\n");
1213             ERR_print_errors(bio_err);
1214             error = 1;
1215             break;
1216         }
1217 
1218         if (select_result == 0)
1219             continue;
1220 #endif
1221 
1222         for (i = 0; i < async_jobs; i++) {
1223             if (loopargs[i].inprogress_job == NULL)
1224                 continue;
1225 
1226             if (!ASYNC_WAIT_CTX_get_all_fds
1227                 (loopargs[i].wait_ctx, NULL, &num_job_fds)
1228                 || num_job_fds > 1) {
1229                 BIO_printf(bio_err, "Too many fds in ASYNC_WAIT_CTX\n");
1230                 ERR_print_errors(bio_err);
1231                 error = 1;
1232                 break;
1233             }
1234             ASYNC_WAIT_CTX_get_all_fds(loopargs[i].wait_ctx, &job_fd,
1235                                        &num_job_fds);
1236 
1237 #if defined(OPENSSL_SYS_UNIX)
1238             if (num_job_fds == 1 && !FD_ISSET(job_fd, &waitfdset))
1239                 continue;
1240 #elif defined(OPENSSL_SYS_WINDOWS)
1241             if (num_job_fds == 1
1242                 && !PeekNamedPipe(job_fd, NULL, 0, NULL, &avail, NULL)
1243                 && avail > 0)
1244                 continue;
1245 #endif
1246 
1247             ret = ASYNC_start_job(&loopargs[i].inprogress_job,
1248                                   loopargs[i].wait_ctx, &job_op_count,
1249                                   loop_function, (void *)(loopargs + i),
1250                                   sizeof(loopargs_t));
1251             switch (ret) {
1252             case ASYNC_PAUSE:
1253                 break;
1254             case ASYNC_FINISH:
1255                 if (job_op_count == -1) {
1256                     error = 1;
1257                 } else {
1258                     total_op_count += job_op_count;
1259                 }
1260                 --num_inprogress;
1261                 loopargs[i].inprogress_job = NULL;
1262                 break;
1263             case ASYNC_NO_JOBS:
1264             case ASYNC_ERR:
1265                 --num_inprogress;
1266                 loopargs[i].inprogress_job = NULL;
1267                 BIO_printf(bio_err, "Failure in the job\n");
1268                 ERR_print_errors(bio_err);
1269                 error = 1;
1270                 break;
1271             }
1272         }
1273     }
1274 
1275     return error ? -1 : total_op_count;
1276 }
1277 
1278 typedef struct ec_curve_st {
1279     const char *name;
1280     unsigned int nid;
1281     unsigned int bits;
1282     size_t sigsize; /* only used for EdDSA curves */
1283 } EC_CURVE;
1284 
1285 static EVP_PKEY *get_ecdsa(const EC_CURVE *curve)
1286 {
1287     EVP_PKEY_CTX *kctx = NULL;
1288     EVP_PKEY *key = NULL;
1289 
1290     /* Ensure that the error queue is empty */
1291     if (ERR_peek_error()) {
1292         BIO_printf(bio_err,
1293                    "WARNING: the error queue contains previous unhandled errors.\n");
1294         ERR_print_errors(bio_err);
1295     }
1296 
1297     /*
1298      * Let's try to create a ctx directly from the NID: this works for
1299      * curves like Curve25519 that are not implemented through the low
1300      * level EC interface.
1301      * If this fails we try creating a EVP_PKEY_EC generic param ctx,
1302      * then we set the curve by NID before deriving the actual keygen
1303      * ctx for that specific curve.
1304      */
1305     kctx = EVP_PKEY_CTX_new_id(curve->nid, NULL);
1306     if (kctx == NULL) {
1307         EVP_PKEY_CTX *pctx = NULL;
1308         EVP_PKEY *params = NULL;
1309         /*
1310          * If we reach this code EVP_PKEY_CTX_new_id() failed and a
1311          * "int_ctx_new:unsupported algorithm" error was added to the
1312          * error queue.
1313          * We remove it from the error queue as we are handling it.
1314          */
1315         unsigned long error = ERR_peek_error();
1316 
1317         if (error == ERR_peek_last_error() /* oldest and latest errors match */
1318             /* check that the error origin matches */
1319             && ERR_GET_LIB(error) == ERR_LIB_EVP
1320             && (ERR_GET_REASON(error) == EVP_R_UNSUPPORTED_ALGORITHM
1321                 || ERR_GET_REASON(error) == ERR_R_UNSUPPORTED))
1322             ERR_get_error(); /* pop error from queue */
1323         if (ERR_peek_error()) {
1324             BIO_printf(bio_err,
1325                        "Unhandled error in the error queue during EC key setup.\n");
1326             ERR_print_errors(bio_err);
1327             return NULL;
1328         }
1329 
1330         /* Create the context for parameter generation */
1331         if ((pctx = EVP_PKEY_CTX_new_from_name(NULL, "EC", NULL)) == NULL
1332             || EVP_PKEY_paramgen_init(pctx) <= 0
1333             || EVP_PKEY_CTX_set_ec_paramgen_curve_nid(pctx,
1334                                                       curve->nid) <= 0
1335             || EVP_PKEY_paramgen(pctx, &params) <= 0) {
1336             BIO_printf(bio_err, "EC params init failure.\n");
1337             ERR_print_errors(bio_err);
1338             EVP_PKEY_CTX_free(pctx);
1339             return NULL;
1340         }
1341         EVP_PKEY_CTX_free(pctx);
1342 
1343         /* Create the context for the key generation */
1344         kctx = EVP_PKEY_CTX_new(params, NULL);
1345         EVP_PKEY_free(params);
1346     }
1347     if (kctx == NULL
1348         || EVP_PKEY_keygen_init(kctx) <= 0
1349         || EVP_PKEY_keygen(kctx, &key) <= 0) {
1350         BIO_printf(bio_err, "EC key generation failure.\n");
1351         ERR_print_errors(bio_err);
1352         key = NULL;
1353     }
1354     EVP_PKEY_CTX_free(kctx);
1355     return key;
1356 }
1357 
1358 #define stop_it(do_it, test_num)\
1359     memset(do_it + test_num, 0, OSSL_NELEM(do_it) - test_num);
1360 
1361 int speed_main(int argc, char **argv)
1362 {
1363     ENGINE *e = NULL;
1364     loopargs_t *loopargs = NULL;
1365     const char *prog;
1366     const char *engine_id = NULL;
1367     EVP_CIPHER *evp_cipher = NULL;
1368     EVP_MAC *mac = NULL;
1369     double d = 0.0;
1370     OPTION_CHOICE o;
1371     int async_init = 0, multiblock = 0, pr_header = 0;
1372     uint8_t doit[ALGOR_NUM] = { 0 };
1373     int ret = 1, misalign = 0, lengths_single = 0, aead = 0;
1374     long count = 0;
1375     unsigned int size_num = SIZE_NUM;
1376     unsigned int i, k, loopargs_len = 0, async_jobs = 0;
1377     int keylen;
1378     int buflen;
1379     BIGNUM *bn = NULL;
1380     EVP_PKEY_CTX *genctx = NULL;
1381 #ifndef NO_FORK
1382     int multi = 0;
1383 #endif
1384     long op_count = 1;
1385     openssl_speed_sec_t seconds = { SECONDS, RSA_SECONDS, DSA_SECONDS,
1386                                     ECDSA_SECONDS, ECDH_SECONDS,
1387                                     EdDSA_SECONDS, SM2_SECONDS,
1388                                     FFDH_SECONDS };
1389 
1390     static const unsigned char key32[32] = {
1391         0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0,
1392         0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12,
1393         0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, 0x34,
1394         0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, 0x34, 0x56
1395     };
1396     static const unsigned char deskey[] = {
1397         0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, /* key1 */
1398         0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, /* key2 */
1399         0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, 0x34  /* key3 */
1400     };
1401     static const struct {
1402         const unsigned char *data;
1403         unsigned int length;
1404         unsigned int bits;
1405     } rsa_keys[] = {
1406         {   test512,   sizeof(test512),   512 },
1407         {  test1024,  sizeof(test1024),  1024 },
1408         {  test2048,  sizeof(test2048),  2048 },
1409         {  test3072,  sizeof(test3072),  3072 },
1410         {  test4096,  sizeof(test4096),  4096 },
1411         {  test7680,  sizeof(test7680),  7680 },
1412         { test15360, sizeof(test15360), 15360 }
1413     };
1414     uint8_t rsa_doit[RSA_NUM] = { 0 };
1415     int primes = RSA_DEFAULT_PRIME_NUM;
1416 #ifndef OPENSSL_NO_DH
1417     typedef struct ffdh_params_st {
1418         const char *name;
1419         unsigned int nid;
1420         unsigned int bits;
1421     } FFDH_PARAMS;
1422 
1423     static const FFDH_PARAMS ffdh_params[FFDH_NUM] = {
1424         {"ffdh2048", NID_ffdhe2048, 2048},
1425         {"ffdh3072", NID_ffdhe3072, 3072},
1426         {"ffdh4096", NID_ffdhe4096, 4096},
1427         {"ffdh6144", NID_ffdhe6144, 6144},
1428         {"ffdh8192", NID_ffdhe8192, 8192}
1429     };
1430     uint8_t ffdh_doit[FFDH_NUM] = { 0 };
1431 
1432 #endif /* OPENSSL_NO_DH */
1433     static const unsigned int dsa_bits[DSA_NUM] = { 512, 1024, 2048 };
1434     uint8_t dsa_doit[DSA_NUM] = { 0 };
1435     /*
1436      * We only test over the following curves as they are representative, To
1437      * add tests over more curves, simply add the curve NID and curve name to
1438      * the following arrays and increase the |ecdh_choices| and |ecdsa_choices|
1439      * lists accordingly.
1440      */
1441     static const EC_CURVE ec_curves[EC_NUM] = {
1442         /* Prime Curves */
1443         {"secp160r1", NID_secp160r1, 160},
1444         {"nistp192", NID_X9_62_prime192v1, 192},
1445         {"nistp224", NID_secp224r1, 224},
1446         {"nistp256", NID_X9_62_prime256v1, 256},
1447         {"nistp384", NID_secp384r1, 384},
1448         {"nistp521", NID_secp521r1, 521},
1449 #ifndef OPENSSL_NO_EC2M
1450         /* Binary Curves */
1451         {"nistk163", NID_sect163k1, 163},
1452         {"nistk233", NID_sect233k1, 233},
1453         {"nistk283", NID_sect283k1, 283},
1454         {"nistk409", NID_sect409k1, 409},
1455         {"nistk571", NID_sect571k1, 571},
1456         {"nistb163", NID_sect163r2, 163},
1457         {"nistb233", NID_sect233r1, 233},
1458         {"nistb283", NID_sect283r1, 283},
1459         {"nistb409", NID_sect409r1, 409},
1460         {"nistb571", NID_sect571r1, 571},
1461 #endif
1462         {"brainpoolP256r1", NID_brainpoolP256r1, 256},
1463         {"brainpoolP256t1", NID_brainpoolP256t1, 256},
1464         {"brainpoolP384r1", NID_brainpoolP384r1, 384},
1465         {"brainpoolP384t1", NID_brainpoolP384t1, 384},
1466         {"brainpoolP512r1", NID_brainpoolP512r1, 512},
1467         {"brainpoolP512t1", NID_brainpoolP512t1, 512},
1468         /* Other and ECDH only ones */
1469         {"X25519", NID_X25519, 253},
1470         {"X448", NID_X448, 448}
1471     };
1472     static const EC_CURVE ed_curves[EdDSA_NUM] = {
1473         /* EdDSA */
1474         {"Ed25519", NID_ED25519, 253, 64},
1475         {"Ed448", NID_ED448, 456, 114}
1476     };
1477 #ifndef OPENSSL_NO_SM2
1478     static const EC_CURVE sm2_curves[SM2_NUM] = {
1479         /* SM2 */
1480         {"CurveSM2", NID_sm2, 256}
1481     };
1482     uint8_t sm2_doit[SM2_NUM] = { 0 };
1483 #endif
1484     uint8_t ecdsa_doit[ECDSA_NUM] = { 0 };
1485     uint8_t ecdh_doit[EC_NUM] = { 0 };
1486     uint8_t eddsa_doit[EdDSA_NUM] = { 0 };
1487 
1488     /* checks declarated curves against choices list. */
1489     OPENSSL_assert(ed_curves[EdDSA_NUM - 1].nid == NID_ED448);
1490     OPENSSL_assert(strcmp(eddsa_choices[EdDSA_NUM - 1].name, "ed448") == 0);
1491 
1492     OPENSSL_assert(ec_curves[EC_NUM - 1].nid == NID_X448);
1493     OPENSSL_assert(strcmp(ecdh_choices[EC_NUM - 1].name, "ecdhx448") == 0);
1494 
1495     OPENSSL_assert(ec_curves[ECDSA_NUM - 1].nid == NID_brainpoolP512t1);
1496     OPENSSL_assert(strcmp(ecdsa_choices[ECDSA_NUM - 1].name, "ecdsabrp512t1") == 0);
1497 
1498 #ifndef OPENSSL_NO_SM2
1499     OPENSSL_assert(sm2_curves[SM2_NUM - 1].nid == NID_sm2);
1500     OPENSSL_assert(strcmp(sm2_choices[SM2_NUM - 1].name, "curveSM2") == 0);
1501 #endif
1502 
1503     prog = opt_init(argc, argv, speed_options);
1504     while ((o = opt_next()) != OPT_EOF) {
1505         switch (o) {
1506         case OPT_EOF:
1507         case OPT_ERR:
1508  opterr:
1509             BIO_printf(bio_err, "%s: Use -help for summary.\n", prog);
1510             goto end;
1511         case OPT_HELP:
1512             opt_help(speed_options);
1513             ret = 0;
1514             goto end;
1515         case OPT_ELAPSED:
1516             usertime = 0;
1517             break;
1518         case OPT_EVP:
1519             if (doit[D_EVP]) {
1520                 BIO_printf(bio_err, "%s: -evp option cannot be used more than once\n", prog);
1521                 goto opterr;
1522             }
1523             ERR_set_mark();
1524             if (!opt_cipher_silent(opt_arg(), &evp_cipher)) {
1525                 if (have_md(opt_arg()))
1526                     evp_md_name = opt_arg();
1527             }
1528             if (evp_cipher == NULL && evp_md_name == NULL) {
1529                 ERR_clear_last_mark();
1530                 BIO_printf(bio_err,
1531                            "%s: %s is an unknown cipher or digest\n",
1532                            prog, opt_arg());
1533                 goto end;
1534             }
1535             ERR_pop_to_mark();
1536             doit[D_EVP] = 1;
1537             break;
1538         case OPT_HMAC:
1539             if (!have_md(opt_arg())) {
1540                 BIO_printf(bio_err, "%s: %s is an unknown digest\n",
1541                            prog, opt_arg());
1542                 goto end;
1543             }
1544             evp_mac_mdname = opt_arg();
1545             doit[D_HMAC] = 1;
1546             break;
1547         case OPT_CMAC:
1548             if (!have_cipher(opt_arg())) {
1549                 BIO_printf(bio_err, "%s: %s is an unknown cipher\n",
1550                            prog, opt_arg());
1551                 goto end;
1552             }
1553             evp_mac_ciphername = opt_arg();
1554             doit[D_EVP_CMAC] = 1;
1555             break;
1556         case OPT_DECRYPT:
1557             decrypt = 1;
1558             break;
1559         case OPT_ENGINE:
1560             /*
1561              * In a forked execution, an engine might need to be
1562              * initialised by each child process, not by the parent.
1563              * So store the name here and run setup_engine() later on.
1564              */
1565             engine_id = opt_arg();
1566             break;
1567         case OPT_MULTI:
1568 #ifndef NO_FORK
1569             multi = atoi(opt_arg());
1570             if ((size_t)multi >= SIZE_MAX / sizeof(int)) {
1571                 BIO_printf(bio_err, "%s: multi argument too large\n", prog);
1572                 return 0;
1573             }
1574 #endif
1575             break;
1576         case OPT_ASYNCJOBS:
1577 #ifndef OPENSSL_NO_ASYNC
1578             async_jobs = atoi(opt_arg());
1579             if (!ASYNC_is_capable()) {
1580                 BIO_printf(bio_err,
1581                            "%s: async_jobs specified but async not supported\n",
1582                            prog);
1583                 goto opterr;
1584             }
1585             if (async_jobs > 99999) {
1586                 BIO_printf(bio_err, "%s: too many async_jobs\n", prog);
1587                 goto opterr;
1588             }
1589 #endif
1590             break;
1591         case OPT_MISALIGN:
1592             misalign = opt_int_arg();
1593             if (misalign > MISALIGN) {
1594                 BIO_printf(bio_err,
1595                            "%s: Maximum offset is %d\n", prog, MISALIGN);
1596                 goto opterr;
1597             }
1598             break;
1599         case OPT_MR:
1600             mr = 1;
1601             break;
1602         case OPT_MB:
1603             multiblock = 1;
1604 #ifdef OPENSSL_NO_MULTIBLOCK
1605             BIO_printf(bio_err,
1606                        "%s: -mb specified but multi-block support is disabled\n",
1607                        prog);
1608             goto end;
1609 #endif
1610             break;
1611         case OPT_R_CASES:
1612             if (!opt_rand(o))
1613                 goto end;
1614             break;
1615         case OPT_PROV_CASES:
1616             if (!opt_provider(o))
1617                 goto end;
1618             break;
1619         case OPT_PRIMES:
1620             primes = opt_int_arg();
1621             break;
1622         case OPT_SECONDS:
1623             seconds.sym = seconds.rsa = seconds.dsa = seconds.ecdsa
1624                         = seconds.ecdh = seconds.eddsa
1625                         = seconds.sm2 = seconds.ffdh = atoi(opt_arg());
1626             break;
1627         case OPT_BYTES:
1628             lengths_single = atoi(opt_arg());
1629             lengths = &lengths_single;
1630             size_num = 1;
1631             break;
1632         case OPT_AEAD:
1633             aead = 1;
1634             break;
1635         }
1636     }
1637 
1638     /* Remaining arguments are algorithms. */
1639     argc = opt_num_rest();
1640     argv = opt_rest();
1641 
1642     if (!app_RAND_load())
1643         goto end;
1644 
1645     for (; *argv; argv++) {
1646         const char *algo = *argv;
1647 
1648         if (opt_found(algo, doit_choices, &i)) {
1649             doit[i] = 1;
1650             continue;
1651         }
1652         if (strcmp(algo, "des") == 0) {
1653             doit[D_CBC_DES] = doit[D_EDE3_DES] = 1;
1654             continue;
1655         }
1656         if (strcmp(algo, "sha") == 0) {
1657             doit[D_SHA1] = doit[D_SHA256] = doit[D_SHA512] = 1;
1658             continue;
1659         }
1660 #ifndef OPENSSL_NO_DEPRECATED_3_0
1661         if (strcmp(algo, "openssl") == 0) /* just for compatibility */
1662             continue;
1663 #endif
1664         if (strncmp(algo, "rsa", 3) == 0) {
1665             if (algo[3] == '\0') {
1666                 memset(rsa_doit, 1, sizeof(rsa_doit));
1667                 continue;
1668             }
1669             if (opt_found(algo, rsa_choices, &i)) {
1670                 rsa_doit[i] = 1;
1671                 continue;
1672             }
1673         }
1674 #ifndef OPENSSL_NO_DH
1675         if (strncmp(algo, "ffdh", 4) == 0) {
1676             if (algo[4] == '\0') {
1677                 memset(ffdh_doit, 1, sizeof(ffdh_doit));
1678                 continue;
1679             }
1680             if (opt_found(algo, ffdh_choices, &i)) {
1681                 ffdh_doit[i] = 2;
1682                 continue;
1683             }
1684         }
1685 #endif
1686         if (strncmp(algo, "dsa", 3) == 0) {
1687             if (algo[3] == '\0') {
1688                 memset(dsa_doit, 1, sizeof(dsa_doit));
1689                 continue;
1690             }
1691             if (opt_found(algo, dsa_choices, &i)) {
1692                 dsa_doit[i] = 2;
1693                 continue;
1694             }
1695         }
1696         if (strcmp(algo, "aes") == 0) {
1697             doit[D_CBC_128_AES] = doit[D_CBC_192_AES] = doit[D_CBC_256_AES] = 1;
1698             continue;
1699         }
1700         if (strcmp(algo, "camellia") == 0) {
1701             doit[D_CBC_128_CML] = doit[D_CBC_192_CML] = doit[D_CBC_256_CML] = 1;
1702             continue;
1703         }
1704         if (strncmp(algo, "ecdsa", 5) == 0) {
1705             if (algo[5] == '\0') {
1706                 memset(ecdsa_doit, 1, sizeof(ecdsa_doit));
1707                 continue;
1708             }
1709             if (opt_found(algo, ecdsa_choices, &i)) {
1710                 ecdsa_doit[i] = 2;
1711                 continue;
1712             }
1713         }
1714         if (strncmp(algo, "ecdh", 4) == 0) {
1715             if (algo[4] == '\0') {
1716                 memset(ecdh_doit, 1, sizeof(ecdh_doit));
1717                 continue;
1718             }
1719             if (opt_found(algo, ecdh_choices, &i)) {
1720                 ecdh_doit[i] = 2;
1721                 continue;
1722             }
1723         }
1724         if (strcmp(algo, "eddsa") == 0) {
1725             memset(eddsa_doit, 1, sizeof(eddsa_doit));
1726             continue;
1727         }
1728         if (opt_found(algo, eddsa_choices, &i)) {
1729             eddsa_doit[i] = 2;
1730             continue;
1731         }
1732 #ifndef OPENSSL_NO_SM2
1733         if (strcmp(algo, "sm2") == 0) {
1734             memset(sm2_doit, 1, sizeof(sm2_doit));
1735             continue;
1736         }
1737         if (opt_found(algo, sm2_choices, &i)) {
1738             sm2_doit[i] = 2;
1739             continue;
1740         }
1741 #endif
1742         BIO_printf(bio_err, "%s: Unknown algorithm %s\n", prog, algo);
1743         goto end;
1744     }
1745 
1746     /* Sanity checks */
1747     if (aead) {
1748         if (evp_cipher == NULL) {
1749             BIO_printf(bio_err, "-aead can be used only with an AEAD cipher\n");
1750             goto end;
1751         } else if (!(EVP_CIPHER_get_flags(evp_cipher) &
1752                      EVP_CIPH_FLAG_AEAD_CIPHER)) {
1753             BIO_printf(bio_err, "%s is not an AEAD cipher\n",
1754                        EVP_CIPHER_get0_name(evp_cipher));
1755             goto end;
1756         }
1757     }
1758     if (multiblock) {
1759         if (evp_cipher == NULL) {
1760             BIO_printf(bio_err, "-mb can be used only with a multi-block"
1761                                 " capable cipher\n");
1762             goto end;
1763         } else if (!(EVP_CIPHER_get_flags(evp_cipher) &
1764                      EVP_CIPH_FLAG_TLS1_1_MULTIBLOCK)) {
1765             BIO_printf(bio_err, "%s is not a multi-block capable\n",
1766                        EVP_CIPHER_get0_name(evp_cipher));
1767             goto end;
1768         } else if (async_jobs > 0) {
1769             BIO_printf(bio_err, "Async mode is not supported with -mb");
1770             goto end;
1771         }
1772     }
1773 
1774     /* Initialize the job pool if async mode is enabled */
1775     if (async_jobs > 0) {
1776         async_init = ASYNC_init_thread(async_jobs, async_jobs);
1777         if (!async_init) {
1778             BIO_printf(bio_err, "Error creating the ASYNC job pool\n");
1779             goto end;
1780         }
1781     }
1782 
1783     loopargs_len = (async_jobs == 0 ? 1 : async_jobs);
1784     loopargs =
1785         app_malloc(loopargs_len * sizeof(loopargs_t), "array of loopargs");
1786     memset(loopargs, 0, loopargs_len * sizeof(loopargs_t));
1787 
1788     for (i = 0; i < loopargs_len; i++) {
1789         if (async_jobs > 0) {
1790             loopargs[i].wait_ctx = ASYNC_WAIT_CTX_new();
1791             if (loopargs[i].wait_ctx == NULL) {
1792                 BIO_printf(bio_err, "Error creating the ASYNC_WAIT_CTX\n");
1793                 goto end;
1794             }
1795         }
1796 
1797         buflen = lengths[size_num - 1];
1798         if (buflen < 36)    /* size of random vector in RSA benchmark */
1799             buflen = 36;
1800         if (INT_MAX - (MAX_MISALIGNMENT + 1) < buflen) {
1801             BIO_printf(bio_err, "Error: buffer size too large\n");
1802             goto end;
1803         }
1804         buflen += MAX_MISALIGNMENT + 1;
1805         loopargs[i].buf_malloc = app_malloc(buflen, "input buffer");
1806         loopargs[i].buf2_malloc = app_malloc(buflen, "input buffer");
1807         memset(loopargs[i].buf_malloc, 0, buflen);
1808         memset(loopargs[i].buf2_malloc, 0, buflen);
1809 
1810         /* Align the start of buffers on a 64 byte boundary */
1811         loopargs[i].buf = loopargs[i].buf_malloc + misalign;
1812         loopargs[i].buf2 = loopargs[i].buf2_malloc + misalign;
1813         loopargs[i].buflen = buflen - misalign;
1814         loopargs[i].sigsize = buflen - misalign;
1815         loopargs[i].secret_a = app_malloc(MAX_ECDH_SIZE, "ECDH secret a");
1816         loopargs[i].secret_b = app_malloc(MAX_ECDH_SIZE, "ECDH secret b");
1817 #ifndef OPENSSL_NO_DH
1818         loopargs[i].secret_ff_a = app_malloc(MAX_FFDH_SIZE, "FFDH secret a");
1819         loopargs[i].secret_ff_b = app_malloc(MAX_FFDH_SIZE, "FFDH secret b");
1820 #endif
1821     }
1822 
1823 #ifndef NO_FORK
1824     if (multi && do_multi(multi, size_num))
1825         goto show_res;
1826 #endif
1827 
1828     /* Initialize the engine after the fork */
1829     e = setup_engine(engine_id, 0);
1830 
1831     /* No parameters; turn on everything. */
1832     if (argc == 0 && !doit[D_EVP] && !doit[D_HMAC] && !doit[D_EVP_CMAC]) {
1833         memset(doit, 1, sizeof(doit));
1834         doit[D_EVP] = doit[D_EVP_CMAC] = 0;
1835         ERR_set_mark();
1836         for (i = D_MD2; i <= D_WHIRLPOOL; i++) {
1837             if (!have_md(names[i]))
1838                 doit[i] = 0;
1839         }
1840         for (i = D_CBC_DES; i <= D_CBC_256_CML; i++) {
1841             if (!have_cipher(names[i]))
1842                 doit[i] = 0;
1843         }
1844         if ((mac = EVP_MAC_fetch(app_get0_libctx(), "GMAC",
1845                                  app_get0_propq())) != NULL) {
1846             EVP_MAC_free(mac);
1847             mac = NULL;
1848         } else {
1849             doit[D_GHASH] = 0;
1850         }
1851         if ((mac = EVP_MAC_fetch(app_get0_libctx(), "HMAC",
1852                                  app_get0_propq())) != NULL) {
1853             EVP_MAC_free(mac);
1854             mac = NULL;
1855         } else {
1856             doit[D_HMAC] = 0;
1857         }
1858         ERR_pop_to_mark();
1859         memset(rsa_doit, 1, sizeof(rsa_doit));
1860 #ifndef OPENSSL_NO_DH
1861         memset(ffdh_doit, 1, sizeof(ffdh_doit));
1862 #endif
1863         memset(dsa_doit, 1, sizeof(dsa_doit));
1864         memset(ecdsa_doit, 1, sizeof(ecdsa_doit));
1865         memset(ecdh_doit, 1, sizeof(ecdh_doit));
1866         memset(eddsa_doit, 1, sizeof(eddsa_doit));
1867 #ifndef OPENSSL_NO_SM2
1868         memset(sm2_doit, 1, sizeof(sm2_doit));
1869 #endif
1870     }
1871     for (i = 0; i < ALGOR_NUM; i++)
1872         if (doit[i])
1873             pr_header++;
1874 
1875     if (usertime == 0 && !mr)
1876         BIO_printf(bio_err,
1877                    "You have chosen to measure elapsed time "
1878                    "instead of user CPU time.\n");
1879 
1880 #if SIGALRM > 0
1881     signal(SIGALRM, alarmed);
1882 #endif
1883 
1884     if (doit[D_MD2]) {
1885         for (testnum = 0; testnum < size_num; testnum++) {
1886             print_message(names[D_MD2], c[D_MD2][testnum], lengths[testnum],
1887                           seconds.sym);
1888             Time_F(START);
1889             count = run_benchmark(async_jobs, EVP_Digest_MD2_loop, loopargs);
1890             d = Time_F(STOP);
1891             print_result(D_MD2, testnum, count, d);
1892             if (count < 0)
1893                 break;
1894         }
1895     }
1896 
1897     if (doit[D_MDC2]) {
1898         for (testnum = 0; testnum < size_num; testnum++) {
1899             print_message(names[D_MDC2], c[D_MDC2][testnum], lengths[testnum],
1900                           seconds.sym);
1901             Time_F(START);
1902             count = run_benchmark(async_jobs, EVP_Digest_MDC2_loop, loopargs);
1903             d = Time_F(STOP);
1904             print_result(D_MDC2, testnum, count, d);
1905             if (count < 0)
1906                 break;
1907         }
1908     }
1909 
1910     if (doit[D_MD4]) {
1911         for (testnum = 0; testnum < size_num; testnum++) {
1912             print_message(names[D_MD4], c[D_MD4][testnum], lengths[testnum],
1913                           seconds.sym);
1914             Time_F(START);
1915             count = run_benchmark(async_jobs, EVP_Digest_MD4_loop, loopargs);
1916             d = Time_F(STOP);
1917             print_result(D_MD4, testnum, count, d);
1918             if (count < 0)
1919                 break;
1920         }
1921     }
1922 
1923     if (doit[D_MD5]) {
1924         for (testnum = 0; testnum < size_num; testnum++) {
1925             print_message(names[D_MD5], c[D_MD5][testnum], lengths[testnum],
1926                           seconds.sym);
1927             Time_F(START);
1928             count = run_benchmark(async_jobs, MD5_loop, loopargs);
1929             d = Time_F(STOP);
1930             print_result(D_MD5, testnum, count, d);
1931             if (count < 0)
1932                 break;
1933         }
1934     }
1935 
1936     if (doit[D_SHA1]) {
1937         for (testnum = 0; testnum < size_num; testnum++) {
1938             print_message(names[D_SHA1], c[D_SHA1][testnum], lengths[testnum],
1939                           seconds.sym);
1940             Time_F(START);
1941             count = run_benchmark(async_jobs, SHA1_loop, loopargs);
1942             d = Time_F(STOP);
1943             print_result(D_SHA1, testnum, count, d);
1944             if (count < 0)
1945                 break;
1946         }
1947     }
1948 
1949     if (doit[D_SHA256]) {
1950         for (testnum = 0; testnum < size_num; testnum++) {
1951             print_message(names[D_SHA256], c[D_SHA256][testnum],
1952                           lengths[testnum], seconds.sym);
1953             Time_F(START);
1954             count = run_benchmark(async_jobs, SHA256_loop, loopargs);
1955             d = Time_F(STOP);
1956             print_result(D_SHA256, testnum, count, d);
1957             if (count < 0)
1958                 break;
1959         }
1960     }
1961 
1962     if (doit[D_SHA512]) {
1963         for (testnum = 0; testnum < size_num; testnum++) {
1964             print_message(names[D_SHA512], c[D_SHA512][testnum],
1965                           lengths[testnum], seconds.sym);
1966             Time_F(START);
1967             count = run_benchmark(async_jobs, SHA512_loop, loopargs);
1968             d = Time_F(STOP);
1969             print_result(D_SHA512, testnum, count, d);
1970             if (count < 0)
1971                 break;
1972         }
1973     }
1974 
1975     if (doit[D_WHIRLPOOL]) {
1976         for (testnum = 0; testnum < size_num; testnum++) {
1977             print_message(names[D_WHIRLPOOL], c[D_WHIRLPOOL][testnum],
1978                           lengths[testnum], seconds.sym);
1979             Time_F(START);
1980             count = run_benchmark(async_jobs, WHIRLPOOL_loop, loopargs);
1981             d = Time_F(STOP);
1982             print_result(D_WHIRLPOOL, testnum, count, d);
1983             if (count < 0)
1984                 break;
1985         }
1986     }
1987 
1988     if (doit[D_RMD160]) {
1989         for (testnum = 0; testnum < size_num; testnum++) {
1990             print_message(names[D_RMD160], c[D_RMD160][testnum],
1991                           lengths[testnum], seconds.sym);
1992             Time_F(START);
1993             count = run_benchmark(async_jobs, EVP_Digest_RMD160_loop, loopargs);
1994             d = Time_F(STOP);
1995             print_result(D_RMD160, testnum, count, d);
1996             if (count < 0)
1997                 break;
1998         }
1999     }
2000 
2001     if (doit[D_HMAC]) {
2002         static const char hmac_key[] = "This is a key...";
2003         int len = strlen(hmac_key);
2004         OSSL_PARAM params[3];
2005 
2006         mac = EVP_MAC_fetch(app_get0_libctx(), "HMAC", app_get0_propq());
2007         if (mac == NULL || evp_mac_mdname == NULL)
2008             goto end;
2009 
2010         evp_hmac_name = app_malloc(sizeof("hmac()") + strlen(evp_mac_mdname),
2011                                    "HMAC name");
2012         sprintf(evp_hmac_name, "hmac(%s)", evp_mac_mdname);
2013         names[D_HMAC] = evp_hmac_name;
2014 
2015         params[0] =
2016             OSSL_PARAM_construct_utf8_string(OSSL_MAC_PARAM_DIGEST,
2017                                              evp_mac_mdname, 0);
2018         params[1] =
2019             OSSL_PARAM_construct_octet_string(OSSL_MAC_PARAM_KEY,
2020                                               (char *)hmac_key, len);
2021         params[2] = OSSL_PARAM_construct_end();
2022 
2023         for (i = 0; i < loopargs_len; i++) {
2024             loopargs[i].mctx = EVP_MAC_CTX_new(mac);
2025             if (loopargs[i].mctx == NULL)
2026                 goto end;
2027 
2028             if (!EVP_MAC_CTX_set_params(loopargs[i].mctx, params))
2029                 goto skip_hmac; /* Digest not found */
2030         }
2031         for (testnum = 0; testnum < size_num; testnum++) {
2032             print_message(names[D_HMAC], c[D_HMAC][testnum], lengths[testnum],
2033                           seconds.sym);
2034             Time_F(START);
2035             count = run_benchmark(async_jobs, HMAC_loop, loopargs);
2036             d = Time_F(STOP);
2037             print_result(D_HMAC, testnum, count, d);
2038             if (count < 0)
2039                 break;
2040         }
2041         for (i = 0; i < loopargs_len; i++)
2042             EVP_MAC_CTX_free(loopargs[i].mctx);
2043         EVP_MAC_free(mac);
2044         mac = NULL;
2045     }
2046 skip_hmac:
2047     if (doit[D_CBC_DES]) {
2048         int st = 1;
2049 
2050         for (i = 0; st && i < loopargs_len; i++) {
2051             loopargs[i].ctx = init_evp_cipher_ctx("des-cbc", deskey,
2052                                                   sizeof(deskey) / 3);
2053             st = loopargs[i].ctx != NULL;
2054         }
2055         algindex = D_CBC_DES;
2056         for (testnum = 0; st && testnum < size_num; testnum++) {
2057             print_message(names[D_CBC_DES], c[D_CBC_DES][testnum],
2058                           lengths[testnum], seconds.sym);
2059             Time_F(START);
2060             count = run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2061             d = Time_F(STOP);
2062             print_result(D_CBC_DES, testnum, count, d);
2063         }
2064         for (i = 0; i < loopargs_len; i++)
2065             EVP_CIPHER_CTX_free(loopargs[i].ctx);
2066     }
2067 
2068     if (doit[D_EDE3_DES]) {
2069         int st = 1;
2070 
2071         for (i = 0; st && i < loopargs_len; i++) {
2072             loopargs[i].ctx = init_evp_cipher_ctx("des-ede3-cbc", deskey,
2073                                                   sizeof(deskey));
2074             st = loopargs[i].ctx != NULL;
2075         }
2076         algindex = D_EDE3_DES;
2077         for (testnum = 0; st && testnum < size_num; testnum++) {
2078             print_message(names[D_EDE3_DES], c[D_EDE3_DES][testnum],
2079                           lengths[testnum], seconds.sym);
2080             Time_F(START);
2081             count =
2082                 run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2083             d = Time_F(STOP);
2084             print_result(D_EDE3_DES, testnum, count, d);
2085         }
2086         for (i = 0; i < loopargs_len; i++)
2087             EVP_CIPHER_CTX_free(loopargs[i].ctx);
2088     }
2089 
2090     for (k = 0; k < 3; k++) {
2091         algindex = D_CBC_128_AES + k;
2092         if (doit[algindex]) {
2093             int st = 1;
2094 
2095             keylen = 16 + k * 8;
2096             for (i = 0; st && i < loopargs_len; i++) {
2097                 loopargs[i].ctx = init_evp_cipher_ctx(names[algindex],
2098                                                       key32, keylen);
2099                 st = loopargs[i].ctx != NULL;
2100             }
2101 
2102             for (testnum = 0; st && testnum < size_num; testnum++) {
2103                 print_message(names[algindex], c[algindex][testnum],
2104                               lengths[testnum], seconds.sym);
2105                 Time_F(START);
2106                 count =
2107                     run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2108                 d = Time_F(STOP);
2109                 print_result(algindex, testnum, count, d);
2110             }
2111             for (i = 0; i < loopargs_len; i++)
2112                 EVP_CIPHER_CTX_free(loopargs[i].ctx);
2113         }
2114     }
2115 
2116     for (k = 0; k < 3; k++) {
2117         algindex = D_CBC_128_CML + k;
2118         if (doit[algindex]) {
2119             int st = 1;
2120 
2121             keylen = 16 + k * 8;
2122             for (i = 0; st && i < loopargs_len; i++) {
2123                 loopargs[i].ctx = init_evp_cipher_ctx(names[algindex],
2124                                                       key32, keylen);
2125                 st = loopargs[i].ctx != NULL;
2126             }
2127 
2128             for (testnum = 0; st && testnum < size_num; testnum++) {
2129                 print_message(names[algindex], c[algindex][testnum],
2130                               lengths[testnum], seconds.sym);
2131                 Time_F(START);
2132                 count =
2133                     run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2134                 d = Time_F(STOP);
2135                 print_result(algindex, testnum, count, d);
2136             }
2137             for (i = 0; i < loopargs_len; i++)
2138                 EVP_CIPHER_CTX_free(loopargs[i].ctx);
2139         }
2140     }
2141 
2142     for (algindex = D_RC4; algindex <= D_CBC_CAST; algindex++) {
2143         if (doit[algindex]) {
2144             int st = 1;
2145 
2146             keylen = 16;
2147             for (i = 0; st && i < loopargs_len; i++) {
2148                 loopargs[i].ctx = init_evp_cipher_ctx(names[algindex],
2149                                                       key32, keylen);
2150                 st = loopargs[i].ctx != NULL;
2151             }
2152 
2153             for (testnum = 0; st && testnum < size_num; testnum++) {
2154                 print_message(names[algindex], c[algindex][testnum],
2155                               lengths[testnum], seconds.sym);
2156                 Time_F(START);
2157                 count =
2158                     run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2159                 d = Time_F(STOP);
2160                 print_result(algindex, testnum, count, d);
2161             }
2162             for (i = 0; i < loopargs_len; i++)
2163                 EVP_CIPHER_CTX_free(loopargs[i].ctx);
2164         }
2165     }
2166     if (doit[D_GHASH]) {
2167         static const char gmac_iv[] = "0123456789ab";
2168         OSSL_PARAM params[3];
2169 
2170         mac = EVP_MAC_fetch(app_get0_libctx(), "GMAC", app_get0_propq());
2171         if (mac == NULL)
2172             goto end;
2173 
2174         params[0] = OSSL_PARAM_construct_utf8_string(OSSL_ALG_PARAM_CIPHER,
2175                                                      "aes-128-gcm", 0);
2176         params[1] = OSSL_PARAM_construct_octet_string(OSSL_MAC_PARAM_IV,
2177                                                       (char *)gmac_iv,
2178                                                       sizeof(gmac_iv) - 1);
2179         params[2] = OSSL_PARAM_construct_end();
2180 
2181         for (i = 0; i < loopargs_len; i++) {
2182             loopargs[i].mctx = EVP_MAC_CTX_new(mac);
2183             if (loopargs[i].mctx == NULL)
2184                 goto end;
2185 
2186             if (!EVP_MAC_init(loopargs[i].mctx, key32, 16, params))
2187                 goto end;
2188         }
2189         for (testnum = 0; testnum < size_num; testnum++) {
2190             print_message(names[D_GHASH], c[D_GHASH][testnum], lengths[testnum],
2191                           seconds.sym);
2192             Time_F(START);
2193             count = run_benchmark(async_jobs, GHASH_loop, loopargs);
2194             d = Time_F(STOP);
2195             print_result(D_GHASH, testnum, count, d);
2196             if (count < 0)
2197                 break;
2198         }
2199         for (i = 0; i < loopargs_len; i++)
2200             EVP_MAC_CTX_free(loopargs[i].mctx);
2201         EVP_MAC_free(mac);
2202         mac = NULL;
2203     }
2204 
2205     if (doit[D_RAND]) {
2206         for (testnum = 0; testnum < size_num; testnum++) {
2207             print_message(names[D_RAND], c[D_RAND][testnum], lengths[testnum],
2208                           seconds.sym);
2209             Time_F(START);
2210             count = run_benchmark(async_jobs, RAND_bytes_loop, loopargs);
2211             d = Time_F(STOP);
2212             print_result(D_RAND, testnum, count, d);
2213         }
2214     }
2215 
2216     if (doit[D_EVP]) {
2217         if (evp_cipher != NULL) {
2218             int (*loopfunc) (void *) = EVP_Update_loop;
2219 
2220             if (multiblock && (EVP_CIPHER_get_flags(evp_cipher) &
2221                                EVP_CIPH_FLAG_TLS1_1_MULTIBLOCK)) {
2222                 multiblock_speed(evp_cipher, lengths_single, &seconds);
2223                 ret = 0;
2224                 goto end;
2225             }
2226 
2227             names[D_EVP] = EVP_CIPHER_get0_name(evp_cipher);
2228 
2229             if (EVP_CIPHER_get_mode(evp_cipher) == EVP_CIPH_CCM_MODE) {
2230                 loopfunc = EVP_Update_loop_ccm;
2231             } else if (aead && (EVP_CIPHER_get_flags(evp_cipher) &
2232                                 EVP_CIPH_FLAG_AEAD_CIPHER)) {
2233                 loopfunc = EVP_Update_loop_aead;
2234                 if (lengths == lengths_list) {
2235                     lengths = aead_lengths_list;
2236                     size_num = OSSL_NELEM(aead_lengths_list);
2237                 }
2238             }
2239 
2240             for (testnum = 0; testnum < size_num; testnum++) {
2241                 print_message(names[D_EVP], c[D_EVP][testnum], lengths[testnum],
2242                               seconds.sym);
2243 
2244                 for (k = 0; k < loopargs_len; k++) {
2245                     loopargs[k].ctx = EVP_CIPHER_CTX_new();
2246                     if (loopargs[k].ctx == NULL) {
2247                         BIO_printf(bio_err, "\nEVP_CIPHER_CTX_new failure\n");
2248                         exit(1);
2249                     }
2250                     if (!EVP_CipherInit_ex(loopargs[k].ctx, evp_cipher, NULL,
2251                                            NULL, iv, decrypt ? 0 : 1)) {
2252                         BIO_printf(bio_err, "\nEVP_CipherInit_ex failure\n");
2253                         ERR_print_errors(bio_err);
2254                         exit(1);
2255                     }
2256 
2257                     EVP_CIPHER_CTX_set_padding(loopargs[k].ctx, 0);
2258 
2259                     keylen = EVP_CIPHER_CTX_get_key_length(loopargs[k].ctx);
2260                     loopargs[k].key = app_malloc(keylen, "evp_cipher key");
2261                     EVP_CIPHER_CTX_rand_key(loopargs[k].ctx, loopargs[k].key);
2262                     if (!EVP_CipherInit_ex(loopargs[k].ctx, NULL, NULL,
2263                                            loopargs[k].key, NULL, -1)) {
2264                         BIO_printf(bio_err, "\nEVP_CipherInit_ex failure\n");
2265                         ERR_print_errors(bio_err);
2266                         exit(1);
2267                     }
2268                     OPENSSL_clear_free(loopargs[k].key, keylen);
2269 
2270                     /* SIV mode only allows for a single Update operation */
2271                     if (EVP_CIPHER_get_mode(evp_cipher) == EVP_CIPH_SIV_MODE)
2272                         (void)EVP_CIPHER_CTX_ctrl(loopargs[k].ctx,
2273                                                   EVP_CTRL_SET_SPEED, 1, NULL);
2274                 }
2275 
2276                 Time_F(START);
2277                 count = run_benchmark(async_jobs, loopfunc, loopargs);
2278                 d = Time_F(STOP);
2279                 for (k = 0; k < loopargs_len; k++)
2280                     EVP_CIPHER_CTX_free(loopargs[k].ctx);
2281                 print_result(D_EVP, testnum, count, d);
2282             }
2283         } else if (evp_md_name != NULL) {
2284             names[D_EVP] = evp_md_name;
2285 
2286             for (testnum = 0; testnum < size_num; testnum++) {
2287                 print_message(names[D_EVP], c[D_EVP][testnum], lengths[testnum],
2288                               seconds.sym);
2289                 Time_F(START);
2290                 count = run_benchmark(async_jobs, EVP_Digest_md_loop, loopargs);
2291                 d = Time_F(STOP);
2292                 print_result(D_EVP, testnum, count, d);
2293                 if (count < 0)
2294                     break;
2295             }
2296         }
2297     }
2298 
2299     if (doit[D_EVP_CMAC]) {
2300         OSSL_PARAM params[3];
2301         EVP_CIPHER *cipher = NULL;
2302 
2303         mac = EVP_MAC_fetch(app_get0_libctx(), "CMAC", app_get0_propq());
2304         if (mac == NULL || evp_mac_ciphername == NULL)
2305             goto end;
2306         if (!opt_cipher(evp_mac_ciphername, &cipher))
2307             goto end;
2308 
2309         keylen = EVP_CIPHER_get_key_length(cipher);
2310         EVP_CIPHER_free(cipher);
2311         if (keylen <= 0 || keylen > (int)sizeof(key32)) {
2312             BIO_printf(bio_err, "\nRequested CMAC cipher with unsupported key length.\n");
2313             goto end;
2314         }
2315         evp_cmac_name = app_malloc(sizeof("cmac()")
2316                                    + strlen(evp_mac_ciphername), "CMAC name");
2317         sprintf(evp_cmac_name, "cmac(%s)", evp_mac_ciphername);
2318         names[D_EVP_CMAC] = evp_cmac_name;
2319 
2320         params[0] = OSSL_PARAM_construct_utf8_string(OSSL_ALG_PARAM_CIPHER,
2321                                                      evp_mac_ciphername, 0);
2322         params[1] = OSSL_PARAM_construct_octet_string(OSSL_MAC_PARAM_KEY,
2323                                                       (char *)key32, keylen);
2324         params[2] = OSSL_PARAM_construct_end();
2325 
2326         for (i = 0; i < loopargs_len; i++) {
2327             loopargs[i].mctx = EVP_MAC_CTX_new(mac);
2328             if (loopargs[i].mctx == NULL)
2329                 goto end;
2330 
2331             if (!EVP_MAC_CTX_set_params(loopargs[i].mctx, params))
2332                 goto end;
2333         }
2334 
2335         for (testnum = 0; testnum < size_num; testnum++) {
2336             print_message(names[D_EVP_CMAC], c[D_EVP_CMAC][testnum],
2337                           lengths[testnum], seconds.sym);
2338             Time_F(START);
2339             count = run_benchmark(async_jobs, CMAC_loop, loopargs);
2340             d = Time_F(STOP);
2341             print_result(D_EVP_CMAC, testnum, count, d);
2342             if (count < 0)
2343                 break;
2344         }
2345         for (i = 0; i < loopargs_len; i++)
2346             EVP_MAC_CTX_free(loopargs[i].mctx);
2347         EVP_MAC_free(mac);
2348         mac = NULL;
2349     }
2350 
2351     for (i = 0; i < loopargs_len; i++)
2352         if (RAND_bytes(loopargs[i].buf, 36) <= 0)
2353             goto end;
2354 
2355     for (testnum = 0; testnum < RSA_NUM; testnum++) {
2356         EVP_PKEY *rsa_key = NULL;
2357         int st = 0;
2358 
2359         if (!rsa_doit[testnum])
2360             continue;
2361 
2362         if (primes > RSA_DEFAULT_PRIME_NUM) {
2363             /* we haven't set keys yet,  generate multi-prime RSA keys */
2364             bn = BN_new();
2365             st = bn != NULL
2366                 && BN_set_word(bn, RSA_F4)
2367                 && init_gen_str(&genctx, "RSA", NULL, 0, NULL, NULL)
2368                 && EVP_PKEY_CTX_set_rsa_keygen_bits(genctx, rsa_keys[testnum].bits) > 0
2369                 && EVP_PKEY_CTX_set1_rsa_keygen_pubexp(genctx, bn) > 0
2370                 && EVP_PKEY_CTX_set_rsa_keygen_primes(genctx, primes) > 0
2371                 && EVP_PKEY_keygen(genctx, &rsa_key);
2372             BN_free(bn);
2373             bn = NULL;
2374             EVP_PKEY_CTX_free(genctx);
2375             genctx = NULL;
2376         } else {
2377             const unsigned char *p = rsa_keys[testnum].data;
2378 
2379             st = (rsa_key = d2i_PrivateKey(EVP_PKEY_RSA, NULL, &p,
2380                                            rsa_keys[testnum].length)) != NULL;
2381         }
2382 
2383         for (i = 0; st && i < loopargs_len; i++) {
2384             loopargs[i].rsa_sign_ctx[testnum] = EVP_PKEY_CTX_new(rsa_key, NULL);
2385             loopargs[i].sigsize = loopargs[i].buflen;
2386             if (loopargs[i].rsa_sign_ctx[testnum] == NULL
2387                 || EVP_PKEY_sign_init(loopargs[i].rsa_sign_ctx[testnum]) <= 0
2388                 || EVP_PKEY_sign(loopargs[i].rsa_sign_ctx[testnum],
2389                                  loopargs[i].buf2,
2390                                  &loopargs[i].sigsize,
2391                                  loopargs[i].buf, 36) <= 0)
2392                 st = 0;
2393         }
2394         if (!st) {
2395             BIO_printf(bio_err,
2396                        "RSA sign setup failure.  No RSA sign will be done.\n");
2397             ERR_print_errors(bio_err);
2398             op_count = 1;
2399         } else {
2400             pkey_print_message("private", "rsa",
2401                                rsa_c[testnum][0], rsa_keys[testnum].bits,
2402                                seconds.rsa);
2403             /* RSA_blinding_on(rsa_key[testnum],NULL); */
2404             Time_F(START);
2405             count = run_benchmark(async_jobs, RSA_sign_loop, loopargs);
2406             d = Time_F(STOP);
2407             BIO_printf(bio_err,
2408                        mr ? "+R1:%ld:%d:%.2f\n"
2409                        : "%ld %u bits private RSA's in %.2fs\n",
2410                        count, rsa_keys[testnum].bits, d);
2411             rsa_results[testnum][0] = (double)count / d;
2412             op_count = count;
2413         }
2414 
2415         for (i = 0; st && i < loopargs_len; i++) {
2416             loopargs[i].rsa_verify_ctx[testnum] = EVP_PKEY_CTX_new(rsa_key,
2417                                                                    NULL);
2418             if (loopargs[i].rsa_verify_ctx[testnum] == NULL
2419                 || EVP_PKEY_verify_init(loopargs[i].rsa_verify_ctx[testnum]) <= 0
2420                 || EVP_PKEY_verify(loopargs[i].rsa_verify_ctx[testnum],
2421                                    loopargs[i].buf2,
2422                                    loopargs[i].sigsize,
2423                                    loopargs[i].buf, 36) <= 0)
2424                 st = 0;
2425         }
2426         if (!st) {
2427             BIO_printf(bio_err,
2428                        "RSA verify setup failure.  No RSA verify will be done.\n");
2429             ERR_print_errors(bio_err);
2430             rsa_doit[testnum] = 0;
2431         } else {
2432             pkey_print_message("public", "rsa",
2433                                rsa_c[testnum][1], rsa_keys[testnum].bits,
2434                                seconds.rsa);
2435             Time_F(START);
2436             count = run_benchmark(async_jobs, RSA_verify_loop, loopargs);
2437             d = Time_F(STOP);
2438             BIO_printf(bio_err,
2439                        mr ? "+R2:%ld:%d:%.2f\n"
2440                        : "%ld %u bits public RSA's in %.2fs\n",
2441                        count, rsa_keys[testnum].bits, d);
2442             rsa_results[testnum][1] = (double)count / d;
2443         }
2444 
2445         if (op_count <= 1) {
2446             /* if longer than 10s, don't do any more */
2447             stop_it(rsa_doit, testnum);
2448         }
2449         EVP_PKEY_free(rsa_key);
2450     }
2451 
2452     for (testnum = 0; testnum < DSA_NUM; testnum++) {
2453         EVP_PKEY *dsa_key = NULL;
2454         int st;
2455 
2456         if (!dsa_doit[testnum])
2457             continue;
2458 
2459         st = (dsa_key = get_dsa(dsa_bits[testnum])) != NULL;
2460 
2461         for (i = 0; st && i < loopargs_len; i++) {
2462             loopargs[i].dsa_sign_ctx[testnum] = EVP_PKEY_CTX_new(dsa_key,
2463                                                                  NULL);
2464             loopargs[i].sigsize = loopargs[i].buflen;
2465             if (loopargs[i].dsa_sign_ctx[testnum] == NULL
2466                 || EVP_PKEY_sign_init(loopargs[i].dsa_sign_ctx[testnum]) <= 0
2467 
2468                 || EVP_PKEY_sign(loopargs[i].dsa_sign_ctx[testnum],
2469                                  loopargs[i].buf2,
2470                                  &loopargs[i].sigsize,
2471                                  loopargs[i].buf, 20) <= 0)
2472                 st = 0;
2473         }
2474         if (!st) {
2475             BIO_printf(bio_err,
2476                        "DSA sign setup failure.  No DSA sign will be done.\n");
2477             ERR_print_errors(bio_err);
2478             op_count = 1;
2479         } else {
2480             pkey_print_message("sign", "dsa",
2481                                dsa_c[testnum][0], dsa_bits[testnum],
2482                                seconds.dsa);
2483             Time_F(START);
2484             count = run_benchmark(async_jobs, DSA_sign_loop, loopargs);
2485             d = Time_F(STOP);
2486             BIO_printf(bio_err,
2487                        mr ? "+R3:%ld:%u:%.2f\n"
2488                        : "%ld %u bits DSA signs in %.2fs\n",
2489                        count, dsa_bits[testnum], d);
2490             dsa_results[testnum][0] = (double)count / d;
2491             op_count = count;
2492         }
2493 
2494         for (i = 0; st && i < loopargs_len; i++) {
2495             loopargs[i].dsa_verify_ctx[testnum] = EVP_PKEY_CTX_new(dsa_key,
2496                                                                    NULL);
2497             if (loopargs[i].dsa_verify_ctx[testnum] == NULL
2498                 || EVP_PKEY_verify_init(loopargs[i].dsa_verify_ctx[testnum]) <= 0
2499                 || EVP_PKEY_verify(loopargs[i].dsa_verify_ctx[testnum],
2500                                    loopargs[i].buf2,
2501                                    loopargs[i].sigsize,
2502                                    loopargs[i].buf, 36) <= 0)
2503                 st = 0;
2504         }
2505         if (!st) {
2506             BIO_printf(bio_err,
2507                        "DSA verify setup failure.  No DSA verify will be done.\n");
2508             ERR_print_errors(bio_err);
2509             dsa_doit[testnum] = 0;
2510         } else {
2511             pkey_print_message("verify", "dsa",
2512                                dsa_c[testnum][1], dsa_bits[testnum],
2513                                seconds.dsa);
2514             Time_F(START);
2515             count = run_benchmark(async_jobs, DSA_verify_loop, loopargs);
2516             d = Time_F(STOP);
2517             BIO_printf(bio_err,
2518                        mr ? "+R4:%ld:%u:%.2f\n"
2519                        : "%ld %u bits DSA verify in %.2fs\n",
2520                        count, dsa_bits[testnum], d);
2521             dsa_results[testnum][1] = (double)count / d;
2522         }
2523 
2524         if (op_count <= 1) {
2525             /* if longer than 10s, don't do any more */
2526             stop_it(dsa_doit, testnum);
2527         }
2528         EVP_PKEY_free(dsa_key);
2529     }
2530 
2531     for (testnum = 0; testnum < ECDSA_NUM; testnum++) {
2532         EVP_PKEY *ecdsa_key = NULL;
2533         int st;
2534 
2535         if (!ecdsa_doit[testnum])
2536             continue;
2537 
2538         st = (ecdsa_key = get_ecdsa(&ec_curves[testnum])) != NULL;
2539 
2540         for (i = 0; st && i < loopargs_len; i++) {
2541             loopargs[i].ecdsa_sign_ctx[testnum] = EVP_PKEY_CTX_new(ecdsa_key,
2542                                                                    NULL);
2543             loopargs[i].sigsize = loopargs[i].buflen;
2544             if (loopargs[i].ecdsa_sign_ctx[testnum] == NULL
2545                 || EVP_PKEY_sign_init(loopargs[i].ecdsa_sign_ctx[testnum]) <= 0
2546 
2547                 || EVP_PKEY_sign(loopargs[i].ecdsa_sign_ctx[testnum],
2548                                  loopargs[i].buf2,
2549                                  &loopargs[i].sigsize,
2550                                  loopargs[i].buf, 20) <= 0)
2551                 st = 0;
2552         }
2553         if (!st) {
2554             BIO_printf(bio_err,
2555                        "ECDSA sign setup failure.  No ECDSA sign will be done.\n");
2556             ERR_print_errors(bio_err);
2557             op_count = 1;
2558         } else {
2559             pkey_print_message("sign", "ecdsa",
2560                                ecdsa_c[testnum][0], ec_curves[testnum].bits,
2561                                seconds.ecdsa);
2562             Time_F(START);
2563             count = run_benchmark(async_jobs, ECDSA_sign_loop, loopargs);
2564             d = Time_F(STOP);
2565             BIO_printf(bio_err,
2566                        mr ? "+R5:%ld:%u:%.2f\n"
2567                        : "%ld %u bits ECDSA signs in %.2fs\n",
2568                        count, ec_curves[testnum].bits, d);
2569             ecdsa_results[testnum][0] = (double)count / d;
2570             op_count = count;
2571         }
2572 
2573         for (i = 0; st && i < loopargs_len; i++) {
2574             loopargs[i].ecdsa_verify_ctx[testnum] = EVP_PKEY_CTX_new(ecdsa_key,
2575                                                                      NULL);
2576             if (loopargs[i].ecdsa_verify_ctx[testnum] == NULL
2577                 || EVP_PKEY_verify_init(loopargs[i].ecdsa_verify_ctx[testnum]) <= 0
2578                 || EVP_PKEY_verify(loopargs[i].ecdsa_verify_ctx[testnum],
2579                                    loopargs[i].buf2,
2580                                    loopargs[i].sigsize,
2581                                    loopargs[i].buf, 20) <= 0)
2582                 st = 0;
2583         }
2584         if (!st) {
2585             BIO_printf(bio_err,
2586                        "ECDSA verify setup failure.  No ECDSA verify will be done.\n");
2587             ERR_print_errors(bio_err);
2588             ecdsa_doit[testnum] = 0;
2589         } else {
2590             pkey_print_message("verify", "ecdsa",
2591                                ecdsa_c[testnum][1], ec_curves[testnum].bits,
2592                                seconds.ecdsa);
2593             Time_F(START);
2594             count = run_benchmark(async_jobs, ECDSA_verify_loop, loopargs);
2595             d = Time_F(STOP);
2596             BIO_printf(bio_err,
2597                        mr ? "+R6:%ld:%u:%.2f\n"
2598                        : "%ld %u bits ECDSA verify in %.2fs\n",
2599                        count, ec_curves[testnum].bits, d);
2600             ecdsa_results[testnum][1] = (double)count / d;
2601         }
2602 
2603         if (op_count <= 1) {
2604             /* if longer than 10s, don't do any more */
2605             stop_it(ecdsa_doit, testnum);
2606         }
2607     }
2608 
2609     for (testnum = 0; testnum < EC_NUM; testnum++) {
2610         int ecdh_checks = 1;
2611 
2612         if (!ecdh_doit[testnum])
2613             continue;
2614 
2615         for (i = 0; i < loopargs_len; i++) {
2616             EVP_PKEY_CTX *test_ctx = NULL;
2617             EVP_PKEY_CTX *ctx = NULL;
2618             EVP_PKEY *key_A = NULL;
2619             EVP_PKEY *key_B = NULL;
2620             size_t outlen;
2621             size_t test_outlen;
2622 
2623             if ((key_A = get_ecdsa(&ec_curves[testnum])) == NULL /* generate secret key A */
2624                 || (key_B = get_ecdsa(&ec_curves[testnum])) == NULL /* generate secret key B */
2625                 || (ctx = EVP_PKEY_CTX_new(key_A, NULL)) == NULL /* derivation ctx from skeyA */
2626                 || EVP_PKEY_derive_init(ctx) <= 0 /* init derivation ctx */
2627                 || EVP_PKEY_derive_set_peer(ctx, key_B) <= 0 /* set peer pubkey in ctx */
2628                 || EVP_PKEY_derive(ctx, NULL, &outlen) <= 0 /* determine max length */
2629                 || outlen == 0 /* ensure outlen is a valid size */
2630                 || outlen > MAX_ECDH_SIZE /* avoid buffer overflow */) {
2631                 ecdh_checks = 0;
2632                 BIO_printf(bio_err, "ECDH key generation failure.\n");
2633                 ERR_print_errors(bio_err);
2634                 op_count = 1;
2635                 break;
2636             }
2637 
2638             /*
2639              * Here we perform a test run, comparing the output of a*B and b*A;
2640              * we try this here and assume that further EVP_PKEY_derive calls
2641              * never fail, so we can skip checks in the actually benchmarked
2642              * code, for maximum performance.
2643              */
2644             if ((test_ctx = EVP_PKEY_CTX_new(key_B, NULL)) == NULL /* test ctx from skeyB */
2645                 || EVP_PKEY_derive_init(test_ctx) <= 0 /* init derivation test_ctx */
2646                 || EVP_PKEY_derive_set_peer(test_ctx, key_A) <= 0 /* set peer pubkey in test_ctx */
2647                 || EVP_PKEY_derive(test_ctx, NULL, &test_outlen) <= 0 /* determine max length */
2648                 || EVP_PKEY_derive(ctx, loopargs[i].secret_a, &outlen) <= 0 /* compute a*B */
2649                 || EVP_PKEY_derive(test_ctx, loopargs[i].secret_b, &test_outlen) <= 0 /* compute b*A */
2650                 || test_outlen != outlen /* compare output length */) {
2651                 ecdh_checks = 0;
2652                 BIO_printf(bio_err, "ECDH computation failure.\n");
2653                 ERR_print_errors(bio_err);
2654                 op_count = 1;
2655                 break;
2656             }
2657 
2658             /* Compare the computation results: CRYPTO_memcmp() returns 0 if equal */
2659             if (CRYPTO_memcmp(loopargs[i].secret_a,
2660                               loopargs[i].secret_b, outlen)) {
2661                 ecdh_checks = 0;
2662                 BIO_printf(bio_err, "ECDH computations don't match.\n");
2663                 ERR_print_errors(bio_err);
2664                 op_count = 1;
2665                 break;
2666             }
2667 
2668             loopargs[i].ecdh_ctx[testnum] = ctx;
2669             loopargs[i].outlen[testnum] = outlen;
2670 
2671             EVP_PKEY_free(key_A);
2672             EVP_PKEY_free(key_B);
2673             EVP_PKEY_CTX_free(test_ctx);
2674             test_ctx = NULL;
2675         }
2676         if (ecdh_checks != 0) {
2677             pkey_print_message("", "ecdh",
2678                                ecdh_c[testnum][0],
2679                                ec_curves[testnum].bits, seconds.ecdh);
2680             Time_F(START);
2681             count =
2682                 run_benchmark(async_jobs, ECDH_EVP_derive_key_loop, loopargs);
2683             d = Time_F(STOP);
2684             BIO_printf(bio_err,
2685                        mr ? "+R7:%ld:%d:%.2f\n" :
2686                        "%ld %u-bits ECDH ops in %.2fs\n", count,
2687                        ec_curves[testnum].bits, d);
2688             ecdh_results[testnum][0] = (double)count / d;
2689             op_count = count;
2690         }
2691 
2692         if (op_count <= 1) {
2693             /* if longer than 10s, don't do any more */
2694             stop_it(ecdh_doit, testnum);
2695         }
2696     }
2697 
2698     for (testnum = 0; testnum < EdDSA_NUM; testnum++) {
2699         int st = 1;
2700         EVP_PKEY *ed_pkey = NULL;
2701         EVP_PKEY_CTX *ed_pctx = NULL;
2702 
2703         if (!eddsa_doit[testnum])
2704             continue;           /* Ignore Curve */
2705         for (i = 0; i < loopargs_len; i++) {
2706             loopargs[i].eddsa_ctx[testnum] = EVP_MD_CTX_new();
2707             if (loopargs[i].eddsa_ctx[testnum] == NULL) {
2708                 st = 0;
2709                 break;
2710             }
2711             loopargs[i].eddsa_ctx2[testnum] = EVP_MD_CTX_new();
2712             if (loopargs[i].eddsa_ctx2[testnum] == NULL) {
2713                 st = 0;
2714                 break;
2715             }
2716 
2717             if ((ed_pctx = EVP_PKEY_CTX_new_id(ed_curves[testnum].nid,
2718                                                NULL)) == NULL
2719                 || EVP_PKEY_keygen_init(ed_pctx) <= 0
2720                 || EVP_PKEY_keygen(ed_pctx, &ed_pkey) <= 0) {
2721                 st = 0;
2722                 EVP_PKEY_CTX_free(ed_pctx);
2723                 break;
2724             }
2725             EVP_PKEY_CTX_free(ed_pctx);
2726 
2727             if (!EVP_DigestSignInit(loopargs[i].eddsa_ctx[testnum], NULL, NULL,
2728                                     NULL, ed_pkey)) {
2729                 st = 0;
2730                 EVP_PKEY_free(ed_pkey);
2731                 break;
2732             }
2733             if (!EVP_DigestVerifyInit(loopargs[i].eddsa_ctx2[testnum], NULL,
2734                                       NULL, NULL, ed_pkey)) {
2735                 st = 0;
2736                 EVP_PKEY_free(ed_pkey);
2737                 break;
2738             }
2739 
2740             EVP_PKEY_free(ed_pkey);
2741             ed_pkey = NULL;
2742         }
2743         if (st == 0) {
2744             BIO_printf(bio_err, "EdDSA failure.\n");
2745             ERR_print_errors(bio_err);
2746             op_count = 1;
2747         } else {
2748             for (i = 0; i < loopargs_len; i++) {
2749                 /* Perform EdDSA signature test */
2750                 loopargs[i].sigsize = ed_curves[testnum].sigsize;
2751                 st = EVP_DigestSign(loopargs[i].eddsa_ctx[testnum],
2752                                     loopargs[i].buf2, &loopargs[i].sigsize,
2753                                     loopargs[i].buf, 20);
2754                 if (st == 0)
2755                     break;
2756             }
2757             if (st == 0) {
2758                 BIO_printf(bio_err,
2759                            "EdDSA sign failure.  No EdDSA sign will be done.\n");
2760                 ERR_print_errors(bio_err);
2761                 op_count = 1;
2762             } else {
2763                 pkey_print_message("sign", ed_curves[testnum].name,
2764                                    eddsa_c[testnum][0],
2765                                    ed_curves[testnum].bits, seconds.eddsa);
2766                 Time_F(START);
2767                 count = run_benchmark(async_jobs, EdDSA_sign_loop, loopargs);
2768                 d = Time_F(STOP);
2769 
2770                 BIO_printf(bio_err,
2771                            mr ? "+R8:%ld:%u:%s:%.2f\n" :
2772                            "%ld %u bits %s signs in %.2fs \n",
2773                            count, ed_curves[testnum].bits,
2774                            ed_curves[testnum].name, d);
2775                 eddsa_results[testnum][0] = (double)count / d;
2776                 op_count = count;
2777             }
2778             /* Perform EdDSA verification test */
2779             for (i = 0; i < loopargs_len; i++) {
2780                 st = EVP_DigestVerify(loopargs[i].eddsa_ctx2[testnum],
2781                                       loopargs[i].buf2, loopargs[i].sigsize,
2782                                       loopargs[i].buf, 20);
2783                 if (st != 1)
2784                     break;
2785             }
2786             if (st != 1) {
2787                 BIO_printf(bio_err,
2788                            "EdDSA verify failure.  No EdDSA verify will be done.\n");
2789                 ERR_print_errors(bio_err);
2790                 eddsa_doit[testnum] = 0;
2791             } else {
2792                 pkey_print_message("verify", ed_curves[testnum].name,
2793                                    eddsa_c[testnum][1],
2794                                    ed_curves[testnum].bits, seconds.eddsa);
2795                 Time_F(START);
2796                 count = run_benchmark(async_jobs, EdDSA_verify_loop, loopargs);
2797                 d = Time_F(STOP);
2798                 BIO_printf(bio_err,
2799                            mr ? "+R9:%ld:%u:%s:%.2f\n"
2800                            : "%ld %u bits %s verify in %.2fs\n",
2801                            count, ed_curves[testnum].bits,
2802                            ed_curves[testnum].name, d);
2803                 eddsa_results[testnum][1] = (double)count / d;
2804             }
2805 
2806             if (op_count <= 1) {
2807                 /* if longer than 10s, don't do any more */
2808                 stop_it(eddsa_doit, testnum);
2809             }
2810         }
2811     }
2812 
2813 #ifndef OPENSSL_NO_SM2
2814     for (testnum = 0; testnum < SM2_NUM; testnum++) {
2815         int st = 1;
2816         EVP_PKEY *sm2_pkey = NULL;
2817 
2818         if (!sm2_doit[testnum])
2819             continue;           /* Ignore Curve */
2820         /* Init signing and verification */
2821         for (i = 0; i < loopargs_len; i++) {
2822             EVP_PKEY_CTX *sm2_pctx = NULL;
2823             EVP_PKEY_CTX *sm2_vfy_pctx = NULL;
2824             EVP_PKEY_CTX *pctx = NULL;
2825             st = 0;
2826 
2827             loopargs[i].sm2_ctx[testnum] = EVP_MD_CTX_new();
2828             loopargs[i].sm2_vfy_ctx[testnum] = EVP_MD_CTX_new();
2829             if (loopargs[i].sm2_ctx[testnum] == NULL
2830                     || loopargs[i].sm2_vfy_ctx[testnum] == NULL)
2831                 break;
2832 
2833             sm2_pkey = NULL;
2834 
2835             st = !((pctx = EVP_PKEY_CTX_new_id(EVP_PKEY_SM2, NULL)) == NULL
2836                 || EVP_PKEY_keygen_init(pctx) <= 0
2837                 || EVP_PKEY_CTX_set_ec_paramgen_curve_nid(pctx,
2838                     sm2_curves[testnum].nid) <= 0
2839                 || EVP_PKEY_keygen(pctx, &sm2_pkey) <= 0);
2840             EVP_PKEY_CTX_free(pctx);
2841             if (st == 0)
2842                 break;
2843 
2844             st = 0; /* set back to zero */
2845             /* attach it sooner to rely on main final cleanup */
2846             loopargs[i].sm2_pkey[testnum] = sm2_pkey;
2847             loopargs[i].sigsize = EVP_PKEY_get_size(sm2_pkey);
2848 
2849             sm2_pctx = EVP_PKEY_CTX_new(sm2_pkey, NULL);
2850             sm2_vfy_pctx = EVP_PKEY_CTX_new(sm2_pkey, NULL);
2851             if (sm2_pctx == NULL || sm2_vfy_pctx == NULL) {
2852                 EVP_PKEY_CTX_free(sm2_vfy_pctx);
2853                 break;
2854             }
2855 
2856             /* attach them directly to respective ctx */
2857             EVP_MD_CTX_set_pkey_ctx(loopargs[i].sm2_ctx[testnum], sm2_pctx);
2858             EVP_MD_CTX_set_pkey_ctx(loopargs[i].sm2_vfy_ctx[testnum], sm2_vfy_pctx);
2859 
2860             /*
2861              * No need to allow user to set an explicit ID here, just use
2862              * the one defined in the 'draft-yang-tls-tl13-sm-suites' I-D.
2863              */
2864             if (EVP_PKEY_CTX_set1_id(sm2_pctx, SM2_ID, SM2_ID_LEN) != 1
2865                 || EVP_PKEY_CTX_set1_id(sm2_vfy_pctx, SM2_ID, SM2_ID_LEN) != 1)
2866                 break;
2867 
2868             if (!EVP_DigestSignInit(loopargs[i].sm2_ctx[testnum], NULL,
2869                                     EVP_sm3(), NULL, sm2_pkey))
2870                 break;
2871             if (!EVP_DigestVerifyInit(loopargs[i].sm2_vfy_ctx[testnum], NULL,
2872                                       EVP_sm3(), NULL, sm2_pkey))
2873                 break;
2874             st = 1;         /* mark loop as succeeded */
2875         }
2876         if (st == 0) {
2877             BIO_printf(bio_err, "SM2 init failure.\n");
2878             ERR_print_errors(bio_err);
2879             op_count = 1;
2880         } else {
2881             for (i = 0; i < loopargs_len; i++) {
2882                 /* Perform SM2 signature test */
2883                 st = EVP_DigestSign(loopargs[i].sm2_ctx[testnum],
2884                                     loopargs[i].buf2, &loopargs[i].sigsize,
2885                                     loopargs[i].buf, 20);
2886                 if (st == 0)
2887                     break;
2888             }
2889             if (st == 0) {
2890                 BIO_printf(bio_err,
2891                            "SM2 sign failure.  No SM2 sign will be done.\n");
2892                 ERR_print_errors(bio_err);
2893                 op_count = 1;
2894             } else {
2895                 pkey_print_message("sign", sm2_curves[testnum].name,
2896                                    sm2_c[testnum][0],
2897                                    sm2_curves[testnum].bits, seconds.sm2);
2898                 Time_F(START);
2899                 count = run_benchmark(async_jobs, SM2_sign_loop, loopargs);
2900                 d = Time_F(STOP);
2901 
2902                 BIO_printf(bio_err,
2903                            mr ? "+R10:%ld:%u:%s:%.2f\n" :
2904                            "%ld %u bits %s signs in %.2fs \n",
2905                            count, sm2_curves[testnum].bits,
2906                            sm2_curves[testnum].name, d);
2907                 sm2_results[testnum][0] = (double)count / d;
2908                 op_count = count;
2909             }
2910 
2911             /* Perform SM2 verification test */
2912             for (i = 0; i < loopargs_len; i++) {
2913                 st = EVP_DigestVerify(loopargs[i].sm2_vfy_ctx[testnum],
2914                                       loopargs[i].buf2, loopargs[i].sigsize,
2915                                       loopargs[i].buf, 20);
2916                 if (st != 1)
2917                     break;
2918             }
2919             if (st != 1) {
2920                 BIO_printf(bio_err,
2921                            "SM2 verify failure.  No SM2 verify will be done.\n");
2922                 ERR_print_errors(bio_err);
2923                 sm2_doit[testnum] = 0;
2924             } else {
2925                 pkey_print_message("verify", sm2_curves[testnum].name,
2926                                    sm2_c[testnum][1],
2927                                    sm2_curves[testnum].bits, seconds.sm2);
2928                 Time_F(START);
2929                 count = run_benchmark(async_jobs, SM2_verify_loop, loopargs);
2930                 d = Time_F(STOP);
2931                 BIO_printf(bio_err,
2932                            mr ? "+R11:%ld:%u:%s:%.2f\n"
2933                            : "%ld %u bits %s verify in %.2fs\n",
2934                            count, sm2_curves[testnum].bits,
2935                            sm2_curves[testnum].name, d);
2936                 sm2_results[testnum][1] = (double)count / d;
2937             }
2938 
2939             if (op_count <= 1) {
2940                 /* if longer than 10s, don't do any more */
2941                 for (testnum++; testnum < SM2_NUM; testnum++)
2942                     sm2_doit[testnum] = 0;
2943             }
2944         }
2945     }
2946 #endif                         /* OPENSSL_NO_SM2 */
2947 
2948 #ifndef OPENSSL_NO_DH
2949     for (testnum = 0; testnum < FFDH_NUM; testnum++) {
2950         int ffdh_checks = 1;
2951 
2952         if (!ffdh_doit[testnum])
2953             continue;
2954 
2955         for (i = 0; i < loopargs_len; i++) {
2956             EVP_PKEY *pkey_A = NULL;
2957             EVP_PKEY *pkey_B = NULL;
2958             EVP_PKEY_CTX *ffdh_ctx = NULL;
2959             EVP_PKEY_CTX *test_ctx = NULL;
2960             size_t secret_size;
2961             size_t test_out;
2962 
2963             /* Ensure that the error queue is empty */
2964             if (ERR_peek_error()) {
2965                 BIO_printf(bio_err,
2966                            "WARNING: the error queue contains previous unhandled errors.\n");
2967                 ERR_print_errors(bio_err);
2968             }
2969 
2970             pkey_A = EVP_PKEY_new();
2971             if (!pkey_A) {
2972                 BIO_printf(bio_err, "Error while initialising EVP_PKEY (out of memory?).\n");
2973                 ERR_print_errors(bio_err);
2974                 op_count = 1;
2975                 ffdh_checks = 0;
2976                 break;
2977             }
2978             pkey_B = EVP_PKEY_new();
2979             if (!pkey_B) {
2980                 BIO_printf(bio_err, "Error while initialising EVP_PKEY (out of memory?).\n");
2981                 ERR_print_errors(bio_err);
2982                 op_count = 1;
2983                 ffdh_checks = 0;
2984                 break;
2985             }
2986 
2987             ffdh_ctx = EVP_PKEY_CTX_new_id(EVP_PKEY_DH, NULL);
2988             if (!ffdh_ctx) {
2989                 BIO_printf(bio_err, "Error while allocating EVP_PKEY_CTX.\n");
2990                 ERR_print_errors(bio_err);
2991                 op_count = 1;
2992                 ffdh_checks = 0;
2993                 break;
2994             }
2995 
2996             if (EVP_PKEY_keygen_init(ffdh_ctx) <= 0) {
2997                 BIO_printf(bio_err, "Error while initialising EVP_PKEY_CTX.\n");
2998                 ERR_print_errors(bio_err);
2999                 op_count = 1;
3000                 ffdh_checks = 0;
3001                 break;
3002             }
3003             if (EVP_PKEY_CTX_set_dh_nid(ffdh_ctx, ffdh_params[testnum].nid) <= 0) {
3004                 BIO_printf(bio_err, "Error setting DH key size for keygen.\n");
3005                 ERR_print_errors(bio_err);
3006                 op_count = 1;
3007                 ffdh_checks = 0;
3008                 break;
3009             }
3010 
3011             if (EVP_PKEY_keygen(ffdh_ctx, &pkey_A) <= 0 ||
3012                 EVP_PKEY_keygen(ffdh_ctx, &pkey_B) <= 0) {
3013                 BIO_printf(bio_err, "FFDH key generation failure.\n");
3014                 ERR_print_errors(bio_err);
3015                 op_count = 1;
3016                 ffdh_checks = 0;
3017                 break;
3018             }
3019 
3020             EVP_PKEY_CTX_free(ffdh_ctx);
3021 
3022             /*
3023              * check if the derivation works correctly both ways so that
3024              * we know if future derive calls will fail, and we can skip
3025              * error checking in benchmarked code
3026              */
3027             ffdh_ctx = EVP_PKEY_CTX_new(pkey_A, NULL);
3028             if (ffdh_ctx == NULL) {
3029                 BIO_printf(bio_err, "Error while allocating EVP_PKEY_CTX.\n");
3030                 ERR_print_errors(bio_err);
3031                 op_count = 1;
3032                 ffdh_checks = 0;
3033                 break;
3034             }
3035             if (EVP_PKEY_derive_init(ffdh_ctx) <= 0) {
3036                 BIO_printf(bio_err, "FFDH derivation context init failure.\n");
3037                 ERR_print_errors(bio_err);
3038                 op_count = 1;
3039                 ffdh_checks = 0;
3040                 break;
3041             }
3042             if (EVP_PKEY_derive_set_peer(ffdh_ctx, pkey_B) <= 0) {
3043                 BIO_printf(bio_err, "Assigning peer key for derivation failed.\n");
3044                 ERR_print_errors(bio_err);
3045                 op_count = 1;
3046                 ffdh_checks = 0;
3047                 break;
3048             }
3049             if (EVP_PKEY_derive(ffdh_ctx, NULL, &secret_size) <= 0) {
3050                 BIO_printf(bio_err, "Checking size of shared secret failed.\n");
3051                 ERR_print_errors(bio_err);
3052                 op_count = 1;
3053                 ffdh_checks = 0;
3054                 break;
3055             }
3056             if (secret_size > MAX_FFDH_SIZE) {
3057                 BIO_printf(bio_err, "Assertion failure: shared secret too large.\n");
3058                 op_count = 1;
3059                 ffdh_checks = 0;
3060                 break;
3061             }
3062             if (EVP_PKEY_derive(ffdh_ctx,
3063                                 loopargs[i].secret_ff_a,
3064                                 &secret_size) <= 0) {
3065                 BIO_printf(bio_err, "Shared secret derive failure.\n");
3066                 ERR_print_errors(bio_err);
3067                 op_count = 1;
3068                 ffdh_checks = 0;
3069                 break;
3070             }
3071             /* Now check from side B */
3072             test_ctx = EVP_PKEY_CTX_new(pkey_B, NULL);
3073             if (!test_ctx) {
3074                 BIO_printf(bio_err, "Error while allocating EVP_PKEY_CTX.\n");
3075                 ERR_print_errors(bio_err);
3076                 op_count = 1;
3077                 ffdh_checks = 0;
3078                 break;
3079             }
3080             if (EVP_PKEY_derive_init(test_ctx) <= 0 ||
3081                 EVP_PKEY_derive_set_peer(test_ctx, pkey_A) <= 0 ||
3082                 EVP_PKEY_derive(test_ctx, NULL, &test_out) <= 0 ||
3083                 EVP_PKEY_derive(test_ctx, loopargs[i].secret_ff_b, &test_out) <= 0 ||
3084                 test_out != secret_size) {
3085                 BIO_printf(bio_err, "FFDH computation failure.\n");
3086                 op_count = 1;
3087                 ffdh_checks = 0;
3088                 break;
3089             }
3090 
3091             /* compare the computed secrets */
3092             if (CRYPTO_memcmp(loopargs[i].secret_ff_a,
3093                               loopargs[i].secret_ff_b, secret_size)) {
3094                 BIO_printf(bio_err, "FFDH computations don't match.\n");
3095                 ERR_print_errors(bio_err);
3096                 op_count = 1;
3097                 ffdh_checks = 0;
3098                 break;
3099             }
3100 
3101             loopargs[i].ffdh_ctx[testnum] = ffdh_ctx;
3102 
3103             EVP_PKEY_free(pkey_A);
3104             pkey_A = NULL;
3105             EVP_PKEY_free(pkey_B);
3106             pkey_B = NULL;
3107             EVP_PKEY_CTX_free(test_ctx);
3108             test_ctx = NULL;
3109         }
3110         if (ffdh_checks != 0) {
3111             pkey_print_message("", "ffdh", ffdh_c[testnum][0],
3112                                ffdh_params[testnum].bits, seconds.ffdh);
3113             Time_F(START);
3114             count =
3115                 run_benchmark(async_jobs, FFDH_derive_key_loop, loopargs);
3116             d = Time_F(STOP);
3117             BIO_printf(bio_err,
3118                        mr ? "+R12:%ld:%d:%.2f\n" :
3119                        "%ld %u-bits FFDH ops in %.2fs\n", count,
3120                        ffdh_params[testnum].bits, d);
3121             ffdh_results[testnum][0] = (double)count / d;
3122             op_count = count;
3123         }
3124         if (op_count <= 1) {
3125             /* if longer than 10s, don't do any more */
3126             stop_it(ffdh_doit, testnum);
3127         }
3128     }
3129 #endif  /* OPENSSL_NO_DH */
3130 #ifndef NO_FORK
3131  show_res:
3132 #endif
3133     if (!mr) {
3134         printf("version: %s\n", OpenSSL_version(OPENSSL_FULL_VERSION_STRING));
3135         printf("%s\n", OpenSSL_version(OPENSSL_BUILT_ON));
3136         printf("options: %s\n", BN_options());
3137         printf("%s\n", OpenSSL_version(OPENSSL_CFLAGS));
3138         printf("%s\n", OpenSSL_version(OPENSSL_CPU_INFO));
3139     }
3140 
3141     if (pr_header) {
3142         if (mr) {
3143             printf("+H");
3144         } else {
3145             printf("The 'numbers' are in 1000s of bytes per second processed.\n");
3146             printf("type        ");
3147         }
3148         for (testnum = 0; testnum < size_num; testnum++)
3149             printf(mr ? ":%d" : "%7d bytes", lengths[testnum]);
3150         printf("\n");
3151     }
3152 
3153     for (k = 0; k < ALGOR_NUM; k++) {
3154         const char *alg_name = names[k];
3155 
3156         if (!doit[k])
3157             continue;
3158 
3159         if (k == D_EVP) {
3160             if (evp_cipher == NULL)
3161                 alg_name = evp_md_name;
3162             else if ((alg_name = EVP_CIPHER_get0_name(evp_cipher)) == NULL)
3163                 app_bail_out("failed to get name of cipher '%s'\n", evp_cipher);
3164         }
3165 
3166         if (mr)
3167             printf("+F:%u:%s", k, alg_name);
3168         else
3169             printf("%-13s", alg_name);
3170         for (testnum = 0; testnum < size_num; testnum++) {
3171             if (results[k][testnum] > 10000 && !mr)
3172                 printf(" %11.2fk", results[k][testnum] / 1e3);
3173             else
3174                 printf(mr ? ":%.2f" : " %11.2f ", results[k][testnum]);
3175         }
3176         printf("\n");
3177     }
3178     testnum = 1;
3179     for (k = 0; k < RSA_NUM; k++) {
3180         if (!rsa_doit[k])
3181             continue;
3182         if (testnum && !mr) {
3183             printf("%18ssign    verify    sign/s verify/s\n", " ");
3184             testnum = 0;
3185         }
3186         if (mr)
3187             printf("+F2:%u:%u:%f:%f\n",
3188                    k, rsa_keys[k].bits, rsa_results[k][0], rsa_results[k][1]);
3189         else
3190             printf("rsa %4u bits %8.6fs %8.6fs %8.1f %8.1f\n",
3191                    rsa_keys[k].bits, 1.0 / rsa_results[k][0], 1.0 / rsa_results[k][1],
3192                    rsa_results[k][0], rsa_results[k][1]);
3193     }
3194     testnum = 1;
3195     for (k = 0; k < DSA_NUM; k++) {
3196         if (!dsa_doit[k])
3197             continue;
3198         if (testnum && !mr) {
3199             printf("%18ssign    verify    sign/s verify/s\n", " ");
3200             testnum = 0;
3201         }
3202         if (mr)
3203             printf("+F3:%u:%u:%f:%f\n",
3204                    k, dsa_bits[k], dsa_results[k][0], dsa_results[k][1]);
3205         else
3206             printf("dsa %4u bits %8.6fs %8.6fs %8.1f %8.1f\n",
3207                    dsa_bits[k], 1.0 / dsa_results[k][0], 1.0 / dsa_results[k][1],
3208                    dsa_results[k][0], dsa_results[k][1]);
3209     }
3210     testnum = 1;
3211     for (k = 0; k < OSSL_NELEM(ecdsa_doit); k++) {
3212         if (!ecdsa_doit[k])
3213             continue;
3214         if (testnum && !mr) {
3215             printf("%30ssign    verify    sign/s verify/s\n", " ");
3216             testnum = 0;
3217         }
3218 
3219         if (mr)
3220             printf("+F4:%u:%u:%f:%f\n",
3221                    k, ec_curves[k].bits,
3222                    ecdsa_results[k][0], ecdsa_results[k][1]);
3223         else
3224             printf("%4u bits ecdsa (%s) %8.4fs %8.4fs %8.1f %8.1f\n",
3225                    ec_curves[k].bits, ec_curves[k].name,
3226                    1.0 / ecdsa_results[k][0], 1.0 / ecdsa_results[k][1],
3227                    ecdsa_results[k][0], ecdsa_results[k][1]);
3228     }
3229 
3230     testnum = 1;
3231     for (k = 0; k < EC_NUM; k++) {
3232         if (!ecdh_doit[k])
3233             continue;
3234         if (testnum && !mr) {
3235             printf("%30sop      op/s\n", " ");
3236             testnum = 0;
3237         }
3238         if (mr)
3239             printf("+F5:%u:%u:%f:%f\n",
3240                    k, ec_curves[k].bits,
3241                    ecdh_results[k][0], 1.0 / ecdh_results[k][0]);
3242 
3243         else
3244             printf("%4u bits ecdh (%s) %8.4fs %8.1f\n",
3245                    ec_curves[k].bits, ec_curves[k].name,
3246                    1.0 / ecdh_results[k][0], ecdh_results[k][0]);
3247     }
3248 
3249     testnum = 1;
3250     for (k = 0; k < OSSL_NELEM(eddsa_doit); k++) {
3251         if (!eddsa_doit[k])
3252             continue;
3253         if (testnum && !mr) {
3254             printf("%30ssign    verify    sign/s verify/s\n", " ");
3255             testnum = 0;
3256         }
3257 
3258         if (mr)
3259             printf("+F6:%u:%u:%s:%f:%f\n",
3260                    k, ed_curves[k].bits, ed_curves[k].name,
3261                    eddsa_results[k][0], eddsa_results[k][1]);
3262         else
3263             printf("%4u bits EdDSA (%s) %8.4fs %8.4fs %8.1f %8.1f\n",
3264                    ed_curves[k].bits, ed_curves[k].name,
3265                    1.0 / eddsa_results[k][0], 1.0 / eddsa_results[k][1],
3266                    eddsa_results[k][0], eddsa_results[k][1]);
3267     }
3268 
3269 #ifndef OPENSSL_NO_SM2
3270     testnum = 1;
3271     for (k = 0; k < OSSL_NELEM(sm2_doit); k++) {
3272         if (!sm2_doit[k])
3273             continue;
3274         if (testnum && !mr) {
3275             printf("%30ssign    verify    sign/s verify/s\n", " ");
3276             testnum = 0;
3277         }
3278 
3279         if (mr)
3280             printf("+F7:%u:%u:%s:%f:%f\n",
3281                    k, sm2_curves[k].bits, sm2_curves[k].name,
3282                    sm2_results[k][0], sm2_results[k][1]);
3283         else
3284             printf("%4u bits SM2 (%s) %8.4fs %8.4fs %8.1f %8.1f\n",
3285                    sm2_curves[k].bits, sm2_curves[k].name,
3286                    1.0 / sm2_results[k][0], 1.0 / sm2_results[k][1],
3287                    sm2_results[k][0], sm2_results[k][1]);
3288     }
3289 #endif
3290 #ifndef OPENSSL_NO_DH
3291     testnum = 1;
3292     for (k = 0; k < FFDH_NUM; k++) {
3293         if (!ffdh_doit[k])
3294             continue;
3295         if (testnum && !mr) {
3296             printf("%23sop     op/s\n", " ");
3297             testnum = 0;
3298         }
3299         if (mr)
3300             printf("+F8:%u:%u:%f:%f\n",
3301                    k, ffdh_params[k].bits,
3302                    ffdh_results[k][0], 1.0 / ffdh_results[k][0]);
3303 
3304         else
3305             printf("%4u bits ffdh %8.4fs %8.1f\n",
3306                    ffdh_params[k].bits,
3307                    1.0 / ffdh_results[k][0], ffdh_results[k][0]);
3308     }
3309 #endif /* OPENSSL_NO_DH */
3310 
3311     ret = 0;
3312 
3313  end:
3314     ERR_print_errors(bio_err);
3315     for (i = 0; i < loopargs_len; i++) {
3316         OPENSSL_free(loopargs[i].buf_malloc);
3317         OPENSSL_free(loopargs[i].buf2_malloc);
3318 
3319         BN_free(bn);
3320         EVP_PKEY_CTX_free(genctx);
3321         for (k = 0; k < RSA_NUM; k++) {
3322             EVP_PKEY_CTX_free(loopargs[i].rsa_sign_ctx[k]);
3323             EVP_PKEY_CTX_free(loopargs[i].rsa_verify_ctx[k]);
3324         }
3325 #ifndef OPENSSL_NO_DH
3326         OPENSSL_free(loopargs[i].secret_ff_a);
3327         OPENSSL_free(loopargs[i].secret_ff_b);
3328         for (k = 0; k < FFDH_NUM; k++)
3329             EVP_PKEY_CTX_free(loopargs[i].ffdh_ctx[k]);
3330 #endif
3331         for (k = 0; k < DSA_NUM; k++) {
3332             EVP_PKEY_CTX_free(loopargs[i].dsa_sign_ctx[k]);
3333             EVP_PKEY_CTX_free(loopargs[i].dsa_verify_ctx[k]);
3334         }
3335         for (k = 0; k < ECDSA_NUM; k++) {
3336             EVP_PKEY_CTX_free(loopargs[i].ecdsa_sign_ctx[k]);
3337             EVP_PKEY_CTX_free(loopargs[i].ecdsa_verify_ctx[k]);
3338         }
3339         for (k = 0; k < EC_NUM; k++)
3340             EVP_PKEY_CTX_free(loopargs[i].ecdh_ctx[k]);
3341         for (k = 0; k < EdDSA_NUM; k++) {
3342             EVP_MD_CTX_free(loopargs[i].eddsa_ctx[k]);
3343             EVP_MD_CTX_free(loopargs[i].eddsa_ctx2[k]);
3344         }
3345 #ifndef OPENSSL_NO_SM2
3346         for (k = 0; k < SM2_NUM; k++) {
3347             EVP_PKEY_CTX *pctx = NULL;
3348 
3349             /* free signing ctx */
3350             if (loopargs[i].sm2_ctx[k] != NULL
3351                 && (pctx = EVP_MD_CTX_get_pkey_ctx(loopargs[i].sm2_ctx[k])) != NULL)
3352                 EVP_PKEY_CTX_free(pctx);
3353             EVP_MD_CTX_free(loopargs[i].sm2_ctx[k]);
3354             /* free verification ctx */
3355             if (loopargs[i].sm2_vfy_ctx[k] != NULL
3356                 && (pctx = EVP_MD_CTX_get_pkey_ctx(loopargs[i].sm2_vfy_ctx[k])) != NULL)
3357                 EVP_PKEY_CTX_free(pctx);
3358             EVP_MD_CTX_free(loopargs[i].sm2_vfy_ctx[k]);
3359             /* free pkey */
3360             EVP_PKEY_free(loopargs[i].sm2_pkey[k]);
3361         }
3362 #endif
3363         OPENSSL_free(loopargs[i].secret_a);
3364         OPENSSL_free(loopargs[i].secret_b);
3365     }
3366     OPENSSL_free(evp_hmac_name);
3367     OPENSSL_free(evp_cmac_name);
3368 
3369     if (async_jobs > 0) {
3370         for (i = 0; i < loopargs_len; i++)
3371             ASYNC_WAIT_CTX_free(loopargs[i].wait_ctx);
3372     }
3373 
3374     if (async_init) {
3375         ASYNC_cleanup_thread();
3376     }
3377     OPENSSL_free(loopargs);
3378     release_engine(e);
3379     EVP_CIPHER_free(evp_cipher);
3380     EVP_MAC_free(mac);
3381     return ret;
3382 }
3383 
3384 static void print_message(const char *s, long num, int length, int tm)
3385 {
3386     BIO_printf(bio_err,
3387                mr ? "+DT:%s:%d:%d\n"
3388                : "Doing %s for %ds on %d size blocks: ", s, tm, length);
3389     (void)BIO_flush(bio_err);
3390     run = 1;
3391     alarm(tm);
3392 }
3393 
3394 static void pkey_print_message(const char *str, const char *str2, long num,
3395                                unsigned int bits, int tm)
3396 {
3397     BIO_printf(bio_err,
3398                mr ? "+DTP:%d:%s:%s:%d\n"
3399                : "Doing %u bits %s %s's for %ds: ", bits, str, str2, tm);
3400     (void)BIO_flush(bio_err);
3401     run = 1;
3402     alarm(tm);
3403 }
3404 
3405 static void print_result(int alg, int run_no, int count, double time_used)
3406 {
3407     if (count == -1) {
3408         BIO_printf(bio_err, "%s error!\n", names[alg]);
3409         ERR_print_errors(bio_err);
3410         return;
3411     }
3412     BIO_printf(bio_err,
3413                mr ? "+R:%d:%s:%f\n"
3414                : "%d %s's in %.2fs\n", count, names[alg], time_used);
3415     results[alg][run_no] = ((double)count) / time_used * lengths[run_no];
3416 }
3417 
3418 #ifndef NO_FORK
3419 static char *sstrsep(char **string, const char *delim)
3420 {
3421     char isdelim[256];
3422     char *token = *string;
3423 
3424     if (**string == 0)
3425         return NULL;
3426 
3427     memset(isdelim, 0, sizeof(isdelim));
3428     isdelim[0] = 1;
3429 
3430     while (*delim) {
3431         isdelim[(unsigned char)(*delim)] = 1;
3432         delim++;
3433     }
3434 
3435     while (!isdelim[(unsigned char)(**string)])
3436         (*string)++;
3437 
3438     if (**string) {
3439         **string = 0;
3440         (*string)++;
3441     }
3442 
3443     return token;
3444 }
3445 
3446 static int do_multi(int multi, int size_num)
3447 {
3448     int n;
3449     int fd[2];
3450     int *fds;
3451     int status;
3452     static char sep[] = ":";
3453 
3454     fds = app_malloc(sizeof(*fds) * multi, "fd buffer for do_multi");
3455     for (n = 0; n < multi; ++n) {
3456         if (pipe(fd) == -1) {
3457             BIO_printf(bio_err, "pipe failure\n");
3458             exit(1);
3459         }
3460         fflush(stdout);
3461         (void)BIO_flush(bio_err);
3462         if (fork()) {
3463             close(fd[1]);
3464             fds[n] = fd[0];
3465         } else {
3466             close(fd[0]);
3467             close(1);
3468             if (dup(fd[1]) == -1) {
3469                 BIO_printf(bio_err, "dup failed\n");
3470                 exit(1);
3471             }
3472             close(fd[1]);
3473             mr = 1;
3474             usertime = 0;
3475             OPENSSL_free(fds);
3476             return 0;
3477         }
3478         printf("Forked child %d\n", n);
3479     }
3480 
3481     /* for now, assume the pipe is long enough to take all the output */
3482     for (n = 0; n < multi; ++n) {
3483         FILE *f;
3484         char buf[1024];
3485         char *p;
3486 
3487         if ((f = fdopen(fds[n], "r")) == NULL) {
3488             BIO_printf(bio_err, "fdopen failure with 0x%x\n",
3489                        errno);
3490             OPENSSL_free(fds);
3491             return 1;
3492         }
3493         while (fgets(buf, sizeof(buf), f)) {
3494             p = strchr(buf, '\n');
3495             if (p)
3496                 *p = '\0';
3497             if (buf[0] != '+') {
3498                 BIO_printf(bio_err,
3499                            "Don't understand line '%s' from child %d\n", buf,
3500                            n);
3501                 continue;
3502             }
3503             printf("Got: %s from %d\n", buf, n);
3504             if (strncmp(buf, "+F:", 3) == 0) {
3505                 int alg;
3506                 int j;
3507 
3508                 p = buf + 3;
3509                 alg = atoi(sstrsep(&p, sep));
3510                 sstrsep(&p, sep);
3511                 for (j = 0; j < size_num; ++j)
3512                     results[alg][j] += atof(sstrsep(&p, sep));
3513             } else if (strncmp(buf, "+F2:", 4) == 0) {
3514                 int k;
3515                 double d;
3516 
3517                 p = buf + 4;
3518                 k = atoi(sstrsep(&p, sep));
3519                 sstrsep(&p, sep);
3520 
3521                 d = atof(sstrsep(&p, sep));
3522                 rsa_results[k][0] += d;
3523 
3524                 d = atof(sstrsep(&p, sep));
3525                 rsa_results[k][1] += d;
3526             } else if (strncmp(buf, "+F3:", 4) == 0) {
3527                 int k;
3528                 double d;
3529 
3530                 p = buf + 4;
3531                 k = atoi(sstrsep(&p, sep));
3532                 sstrsep(&p, sep);
3533 
3534                 d = atof(sstrsep(&p, sep));
3535                 dsa_results[k][0] += d;
3536 
3537                 d = atof(sstrsep(&p, sep));
3538                 dsa_results[k][1] += d;
3539             } else if (strncmp(buf, "+F4:", 4) == 0) {
3540                 int k;
3541                 double d;
3542 
3543                 p = buf + 4;
3544                 k = atoi(sstrsep(&p, sep));
3545                 sstrsep(&p, sep);
3546 
3547                 d = atof(sstrsep(&p, sep));
3548                 ecdsa_results[k][0] += d;
3549 
3550                 d = atof(sstrsep(&p, sep));
3551                 ecdsa_results[k][1] += d;
3552             } else if (strncmp(buf, "+F5:", 4) == 0) {
3553                 int k;
3554                 double d;
3555 
3556                 p = buf + 4;
3557                 k = atoi(sstrsep(&p, sep));
3558                 sstrsep(&p, sep);
3559 
3560                 d = atof(sstrsep(&p, sep));
3561                 ecdh_results[k][0] += d;
3562             } else if (strncmp(buf, "+F6:", 4) == 0) {
3563                 int k;
3564                 double d;
3565 
3566                 p = buf + 4;
3567                 k = atoi(sstrsep(&p, sep));
3568                 sstrsep(&p, sep);
3569                 sstrsep(&p, sep);
3570 
3571                 d = atof(sstrsep(&p, sep));
3572                 eddsa_results[k][0] += d;
3573 
3574                 d = atof(sstrsep(&p, sep));
3575                 eddsa_results[k][1] += d;
3576 # ifndef OPENSSL_NO_SM2
3577             } else if (strncmp(buf, "+F7:", 4) == 0) {
3578                 int k;
3579                 double d;
3580 
3581                 p = buf + 4;
3582                 k = atoi(sstrsep(&p, sep));
3583                 sstrsep(&p, sep);
3584                 sstrsep(&p, sep);
3585 
3586                 d = atof(sstrsep(&p, sep));
3587                 sm2_results[k][0] += d;
3588 
3589                 d = atof(sstrsep(&p, sep));
3590                 sm2_results[k][1] += d;
3591 # endif /* OPENSSL_NO_SM2 */
3592 # ifndef OPENSSL_NO_DH
3593             } else if (strncmp(buf, "+F8:", 4) == 0) {
3594                 int k;
3595                 double d;
3596 
3597                 p = buf + 4;
3598                 k = atoi(sstrsep(&p, sep));
3599                 sstrsep(&p, sep);
3600 
3601                 d = atof(sstrsep(&p, sep));
3602                 ffdh_results[k][0] += d;
3603 # endif /* OPENSSL_NO_DH */
3604             } else if (strncmp(buf, "+H:", 3) == 0) {
3605                 ;
3606             } else {
3607                 BIO_printf(bio_err, "Unknown type '%s' from child %d\n", buf,
3608                            n);
3609             }
3610         }
3611 
3612         fclose(f);
3613     }
3614     OPENSSL_free(fds);
3615     for (n = 0; n < multi; ++n) {
3616         while (wait(&status) == -1)
3617             if (errno != EINTR) {
3618                 BIO_printf(bio_err, "Waitng for child failed with 0x%x\n",
3619                            errno);
3620                 return 1;
3621             }
3622         if (WIFEXITED(status) && WEXITSTATUS(status)) {
3623             BIO_printf(bio_err, "Child exited with %d\n", WEXITSTATUS(status));
3624         } else if (WIFSIGNALED(status)) {
3625             BIO_printf(bio_err, "Child terminated by signal %d\n",
3626                        WTERMSIG(status));
3627         }
3628     }
3629     return 1;
3630 }
3631 #endif
3632 
3633 static void multiblock_speed(const EVP_CIPHER *evp_cipher, int lengths_single,
3634                              const openssl_speed_sec_t *seconds)
3635 {
3636     static const int mblengths_list[] =
3637         { 8 * 1024, 2 * 8 * 1024, 4 * 8 * 1024, 8 * 8 * 1024, 8 * 16 * 1024 };
3638     const int *mblengths = mblengths_list;
3639     int j, count, keylen, num = OSSL_NELEM(mblengths_list);
3640     const char *alg_name;
3641     unsigned char *inp = NULL, *out = NULL, *key, no_key[32], no_iv[16];
3642     EVP_CIPHER_CTX *ctx = NULL;
3643     double d = 0.0;
3644 
3645     if (lengths_single) {
3646         mblengths = &lengths_single;
3647         num = 1;
3648     }
3649 
3650     inp = app_malloc(mblengths[num - 1], "multiblock input buffer");
3651     out = app_malloc(mblengths[num - 1] + 1024, "multiblock output buffer");
3652     if ((ctx = EVP_CIPHER_CTX_new()) == NULL)
3653         app_bail_out("failed to allocate cipher context\n");
3654     if (!EVP_EncryptInit_ex(ctx, evp_cipher, NULL, NULL, no_iv))
3655         app_bail_out("failed to initialise cipher context\n");
3656 
3657     if ((keylen = EVP_CIPHER_CTX_get_key_length(ctx)) < 0) {
3658         BIO_printf(bio_err, "Impossible negative key length: %d\n", keylen);
3659         goto err;
3660     }
3661     key = app_malloc(keylen, "evp_cipher key");
3662     if (EVP_CIPHER_CTX_rand_key(ctx, key) <= 0)
3663         app_bail_out("failed to generate random cipher key\n");
3664     if (!EVP_EncryptInit_ex(ctx, NULL, NULL, key, NULL))
3665         app_bail_out("failed to set cipher key\n");
3666     OPENSSL_clear_free(key, keylen);
3667 
3668     if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_SET_MAC_KEY,
3669                              sizeof(no_key), no_key) <= 0)
3670         app_bail_out("failed to set AEAD key\n");
3671     if ((alg_name = EVP_CIPHER_get0_name(evp_cipher)) == NULL)
3672         app_bail_out("failed to get cipher name\n");
3673 
3674     for (j = 0; j < num; j++) {
3675         print_message(alg_name, 0, mblengths[j], seconds->sym);
3676         Time_F(START);
3677         for (count = 0; run && count < INT_MAX; count++) {
3678             unsigned char aad[EVP_AEAD_TLS1_AAD_LEN];
3679             EVP_CTRL_TLS1_1_MULTIBLOCK_PARAM mb_param;
3680             size_t len = mblengths[j];
3681             int packlen;
3682 
3683             memset(aad, 0, 8);  /* avoid uninitialized values */
3684             aad[8] = 23;        /* SSL3_RT_APPLICATION_DATA */
3685             aad[9] = 3;         /* version */
3686             aad[10] = 2;
3687             aad[11] = 0;        /* length */
3688             aad[12] = 0;
3689             mb_param.out = NULL;
3690             mb_param.inp = aad;
3691             mb_param.len = len;
3692             mb_param.interleave = 8;
3693 
3694             packlen = EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_TLS1_1_MULTIBLOCK_AAD,
3695                                           sizeof(mb_param), &mb_param);
3696 
3697             if (packlen > 0) {
3698                 mb_param.out = out;
3699                 mb_param.inp = inp;
3700                 mb_param.len = len;
3701                 (void)EVP_CIPHER_CTX_ctrl(ctx,
3702                                           EVP_CTRL_TLS1_1_MULTIBLOCK_ENCRYPT,
3703                                           sizeof(mb_param), &mb_param);
3704             } else {
3705                 int pad;
3706 
3707                 if (RAND_bytes(inp, 16) <= 0)
3708                     app_bail_out("error setting random bytes\n");
3709                 len += 16;
3710                 aad[11] = (unsigned char)(len >> 8);
3711                 aad[12] = (unsigned char)(len);
3712                 pad = EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_TLS1_AAD,
3713                                           EVP_AEAD_TLS1_AAD_LEN, aad);
3714                 EVP_Cipher(ctx, out, inp, len + pad);
3715             }
3716         }
3717         d = Time_F(STOP);
3718         BIO_printf(bio_err, mr ? "+R:%d:%s:%f\n"
3719                    : "%d %s's in %.2fs\n", count, "evp", d);
3720         results[D_EVP][j] = ((double)count) / d * mblengths[j];
3721     }
3722 
3723     if (mr) {
3724         fprintf(stdout, "+H");
3725         for (j = 0; j < num; j++)
3726             fprintf(stdout, ":%d", mblengths[j]);
3727         fprintf(stdout, "\n");
3728         fprintf(stdout, "+F:%d:%s", D_EVP, alg_name);
3729         for (j = 0; j < num; j++)
3730             fprintf(stdout, ":%.2f", results[D_EVP][j]);
3731         fprintf(stdout, "\n");
3732     } else {
3733         fprintf(stdout,
3734                 "The 'numbers' are in 1000s of bytes per second processed.\n");
3735         fprintf(stdout, "type                    ");
3736         for (j = 0; j < num; j++)
3737             fprintf(stdout, "%7d bytes", mblengths[j]);
3738         fprintf(stdout, "\n");
3739         fprintf(stdout, "%-24s", alg_name);
3740 
3741         for (j = 0; j < num; j++) {
3742             if (results[D_EVP][j] > 10000)
3743                 fprintf(stdout, " %11.2fk", results[D_EVP][j] / 1e3);
3744             else
3745                 fprintf(stdout, " %11.2f ", results[D_EVP][j]);
3746         }
3747         fprintf(stdout, "\n");
3748     }
3749 
3750  err:
3751     OPENSSL_free(inp);
3752     OPENSSL_free(out);
3753     EVP_CIPHER_CTX_free(ctx);
3754 }
3755