speed: Fix memory leaks
[openssl.git] / apps / speed.c
1 /*
2  * Copyright 1995-2023 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 #define KEM_SECONDS     PKEY_SECONDS
23 #define SIG_SECONDS     PKEY_SECONDS
24
25 #define MAX_ALGNAME_SUFFIX 100
26
27 /* We need to use some deprecated APIs */
28 #define OPENSSL_SUPPRESS_DEPRECATED
29
30 #include <stdio.h>
31 #include <stdlib.h>
32 #include <string.h>
33 #include <math.h>
34 #include "apps.h"
35 #include "progs.h"
36 #include "internal/nelem.h"
37 #include "internal/numbers.h"
38 #include <openssl/crypto.h>
39 #include <openssl/rand.h>
40 #include <openssl/err.h>
41 #include <openssl/evp.h>
42 #include <openssl/objects.h>
43 #include <openssl/core_names.h>
44 #include <openssl/async.h>
45 #include <openssl/provider.h>
46 #if !defined(OPENSSL_SYS_MSDOS)
47 # include <unistd.h>
48 #endif
49
50 #if defined(__TANDEM)
51 # if defined(OPENSSL_TANDEM_FLOSS)
52 #  include <floss.h(floss_fork)>
53 # endif
54 #endif
55
56 #if defined(_WIN32)
57 # include <windows.h>
58 /*
59  * While VirtualLock is available under the app partition (e.g. UWP),
60  * the headers do not define the API. Define it ourselves instead.
61  */
62 WINBASEAPI
63 BOOL
64 WINAPI
65 VirtualLock(
66     _In_ LPVOID lpAddress,
67     _In_ SIZE_T dwSize
68     );
69 #endif
70
71 #if defined(OPENSSL_SYS_LINUX)
72 # include <sys/mman.h>
73 #endif
74
75 #include <openssl/bn.h>
76 #include <openssl/rsa.h>
77 #include "./testrsa.h"
78 #ifndef OPENSSL_NO_DH
79 # include <openssl/dh.h>
80 #endif
81 #include <openssl/x509.h>
82 #include <openssl/dsa.h>
83 #include "./testdsa.h"
84 #include <openssl/modes.h>
85
86 #ifndef HAVE_FORK
87 # if defined(OPENSSL_SYS_VMS) || defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_VXWORKS)
88 #  define HAVE_FORK 0
89 # else
90 #  define HAVE_FORK 1
91 #  include <sys/wait.h>
92 # endif
93 #endif
94
95 #if HAVE_FORK
96 # undef NO_FORK
97 #else
98 # define NO_FORK
99 #endif
100
101 #define MAX_MISALIGNMENT 63
102 #define MAX_ECDH_SIZE   256
103 #define MISALIGN        64
104 #define MAX_FFDH_SIZE 1024
105
106 #ifndef RSA_DEFAULT_PRIME_NUM
107 # define RSA_DEFAULT_PRIME_NUM 2
108 #endif
109
110 typedef struct openssl_speed_sec_st {
111     int sym;
112     int rsa;
113     int dsa;
114     int ecdsa;
115     int ecdh;
116     int eddsa;
117     int sm2;
118     int ffdh;
119     int kem;
120     int sig;
121 } openssl_speed_sec_t;
122
123 static volatile int run = 0;
124
125 static int mr = 0;  /* machine-readeable output format to merge fork results */
126 static int usertime = 1;
127
128 static double Time_F(int s);
129 static void print_message(const char *s, int length, int tm);
130 static void pkey_print_message(const char *str, const char *str2,
131                                unsigned int bits, int sec);
132 static void kskey_print_message(const char *str, const char *str2, int tm);
133 static void print_result(int alg, int run_no, int count, double time_used);
134 #ifndef NO_FORK
135 static int do_multi(int multi, int size_num);
136 #endif
137
138 static int domlock = 0;
139
140 static const int lengths_list[] = {
141     16, 64, 256, 1024, 8 * 1024, 16 * 1024
142 };
143 #define SIZE_NUM         OSSL_NELEM(lengths_list)
144 static const int *lengths = lengths_list;
145
146 static const int aead_lengths_list[] = {
147     2, 31, 136, 1024, 8 * 1024, 16 * 1024
148 };
149
150 #define START   0
151 #define STOP    1
152
153 #ifdef SIGALRM
154
155 static void alarmed(ossl_unused int sig)
156 {
157     signal(SIGALRM, alarmed);
158     run = 0;
159 }
160
161 static double Time_F(int s)
162 {
163     double ret = app_tminterval(s, usertime);
164     if (s == STOP)
165         alarm(0);
166     return ret;
167 }
168
169 #elif defined(_WIN32)
170
171 # define SIGALRM -1
172
173 static unsigned int lapse;
174 static volatile unsigned int schlock;
175 static void alarm_win32(unsigned int secs)
176 {
177     lapse = secs * 1000;
178 }
179
180 # define alarm alarm_win32
181
182 static DWORD WINAPI sleepy(VOID * arg)
183 {
184     schlock = 1;
185     Sleep(lapse);
186     run = 0;
187     return 0;
188 }
189
190 static double Time_F(int s)
191 {
192     double ret;
193     static HANDLE thr;
194
195     if (s == START) {
196         schlock = 0;
197         thr = CreateThread(NULL, 4096, sleepy, NULL, 0, NULL);
198         if (thr == NULL) {
199             DWORD err = GetLastError();
200             BIO_printf(bio_err, "unable to CreateThread (%lu)", err);
201             ExitProcess(err);
202         }
203         while (!schlock)
204             Sleep(0);           /* scheduler spinlock */
205         ret = app_tminterval(s, usertime);
206     } else {
207         ret = app_tminterval(s, usertime);
208         if (run)
209             TerminateThread(thr, 0);
210         CloseHandle(thr);
211     }
212
213     return ret;
214 }
215 #else
216 # error "SIGALRM not defined and the platform is not Windows"
217 #endif
218
219 static void multiblock_speed(const EVP_CIPHER *evp_cipher, int lengths_single,
220                              const openssl_speed_sec_t *seconds);
221
222 static int opt_found(const char *name, unsigned int *result,
223                      const OPT_PAIR pairs[], unsigned int nbelem)
224 {
225     unsigned int idx;
226
227     for (idx = 0; idx < nbelem; ++idx, pairs++)
228         if (strcmp(name, pairs->name) == 0) {
229             *result = pairs->retval;
230             return 1;
231         }
232     return 0;
233 }
234 #define opt_found(value, pairs, result)\
235     opt_found(value, result, pairs, OSSL_NELEM(pairs))
236
237 typedef enum OPTION_choice {
238     OPT_COMMON,
239     OPT_ELAPSED, OPT_EVP, OPT_HMAC, OPT_DECRYPT, OPT_ENGINE, OPT_MULTI,
240     OPT_MR, OPT_MB, OPT_MISALIGN, OPT_ASYNCJOBS, OPT_R_ENUM, OPT_PROV_ENUM, OPT_CONFIG,
241     OPT_PRIMES, OPT_SECONDS, OPT_BYTES, OPT_AEAD, OPT_CMAC, OPT_MLOCK, OPT_KEM, OPT_SIG
242 } OPTION_CHOICE;
243
244 const OPTIONS speed_options[] = {
245     {OPT_HELP_STR, 1, '-',
246      "Usage: %s [options] [algorithm...]\n"
247      "All +int options consider prefix '0' as base-8 input, "
248      "prefix '0x'/'0X' as base-16 input.\n"
249     },
250
251     OPT_SECTION("General"),
252     {"help", OPT_HELP, '-', "Display this summary"},
253     {"mb", OPT_MB, '-',
254      "Enable (tls1>=1) multi-block mode on EVP-named cipher"},
255     {"mr", OPT_MR, '-', "Produce machine readable output"},
256 #ifndef NO_FORK
257     {"multi", OPT_MULTI, 'p', "Run benchmarks in parallel"},
258 #endif
259 #ifndef OPENSSL_NO_ASYNC
260     {"async_jobs", OPT_ASYNCJOBS, 'p',
261      "Enable async mode and start specified number of jobs"},
262 #endif
263 #ifndef OPENSSL_NO_ENGINE
264     {"engine", OPT_ENGINE, 's', "Use engine, possibly a hardware device"},
265 #endif
266     {"primes", OPT_PRIMES, 'p', "Specify number of primes (for RSA only)"},
267     {"mlock", OPT_MLOCK, '-', "Lock memory for better result determinism"},
268     OPT_CONFIG_OPTION,
269
270     OPT_SECTION("Selection"),
271     {"evp", OPT_EVP, 's', "Use EVP-named cipher or digest"},
272     {"hmac", OPT_HMAC, 's', "HMAC using EVP-named digest"},
273     {"cmac", OPT_CMAC, 's', "CMAC using EVP-named cipher"},
274     {"decrypt", OPT_DECRYPT, '-',
275      "Time decryption instead of encryption (only EVP)"},
276     {"aead", OPT_AEAD, '-',
277      "Benchmark EVP-named AEAD cipher in TLS-like sequence"},
278     {"kem-algorithms", OPT_KEM, '-',
279      "Benchmark KEM algorithms"},
280     {"signature-algorithms", OPT_SIG, '-',
281      "Benchmark signature algorithms"},
282
283     OPT_SECTION("Timing"),
284     {"elapsed", OPT_ELAPSED, '-',
285      "Use wall-clock time instead of CPU user time as divisor"},
286     {"seconds", OPT_SECONDS, 'p',
287      "Run benchmarks for specified amount of seconds"},
288     {"bytes", OPT_BYTES, 'p',
289      "Run [non-PKI] benchmarks on custom-sized buffer"},
290     {"misalign", OPT_MISALIGN, 'p',
291      "Use specified offset to mis-align buffers"},
292
293     OPT_R_OPTIONS,
294     OPT_PROV_OPTIONS,
295
296     OPT_PARAMETERS(),
297     {"algorithm", 0, 0, "Algorithm(s) to test (optional; otherwise tests all)"},
298     {NULL}
299 };
300
301 enum {
302     D_MD2, D_MDC2, D_MD4, D_MD5, D_SHA1, D_RMD160,
303     D_SHA256, D_SHA512, D_WHIRLPOOL, D_HMAC,
304     D_CBC_DES, D_EDE3_DES, D_RC4, D_CBC_IDEA, D_CBC_SEED,
305     D_CBC_RC2, D_CBC_RC5, D_CBC_BF, D_CBC_CAST,
306     D_CBC_128_AES, D_CBC_192_AES, D_CBC_256_AES,
307     D_CBC_128_CML, D_CBC_192_CML, D_CBC_256_CML,
308     D_EVP, D_GHASH, D_RAND, D_EVP_CMAC, ALGOR_NUM
309 };
310 /* name of algorithms to test. MUST BE KEEP IN SYNC with above enum ! */
311 static const char *names[ALGOR_NUM] = {
312     "md2", "mdc2", "md4", "md5", "sha1", "rmd160",
313     "sha256", "sha512", "whirlpool", "hmac(md5)",
314     "des-cbc", "des-ede3", "rc4", "idea-cbc", "seed-cbc",
315     "rc2-cbc", "rc5-cbc", "blowfish", "cast-cbc",
316     "aes-128-cbc", "aes-192-cbc", "aes-256-cbc",
317     "camellia-128-cbc", "camellia-192-cbc", "camellia-256-cbc",
318     "evp", "ghash", "rand", "cmac"
319 };
320
321 /* list of configured algorithm (remaining), with some few alias */
322 static const OPT_PAIR doit_choices[] = {
323     {"md2", D_MD2},
324     {"mdc2", D_MDC2},
325     {"md4", D_MD4},
326     {"md5", D_MD5},
327     {"hmac", D_HMAC},
328     {"sha1", D_SHA1},
329     {"sha256", D_SHA256},
330     {"sha512", D_SHA512},
331     {"whirlpool", D_WHIRLPOOL},
332     {"ripemd", D_RMD160},
333     {"rmd160", D_RMD160},
334     {"ripemd160", D_RMD160},
335     {"rc4", D_RC4},
336     {"des-cbc", D_CBC_DES},
337     {"des-ede3", D_EDE3_DES},
338     {"aes-128-cbc", D_CBC_128_AES},
339     {"aes-192-cbc", D_CBC_192_AES},
340     {"aes-256-cbc", D_CBC_256_AES},
341     {"camellia-128-cbc", D_CBC_128_CML},
342     {"camellia-192-cbc", D_CBC_192_CML},
343     {"camellia-256-cbc", D_CBC_256_CML},
344     {"rc2-cbc", D_CBC_RC2},
345     {"rc2", D_CBC_RC2},
346     {"rc5-cbc", D_CBC_RC5},
347     {"rc5", D_CBC_RC5},
348     {"idea-cbc", D_CBC_IDEA},
349     {"idea", D_CBC_IDEA},
350     {"seed-cbc", D_CBC_SEED},
351     {"seed", D_CBC_SEED},
352     {"bf-cbc", D_CBC_BF},
353     {"blowfish", D_CBC_BF},
354     {"bf", D_CBC_BF},
355     {"cast-cbc", D_CBC_CAST},
356     {"cast", D_CBC_CAST},
357     {"cast5", D_CBC_CAST},
358     {"ghash", D_GHASH},
359     {"rand", D_RAND}
360 };
361
362 static double results[ALGOR_NUM][SIZE_NUM];
363
364 enum { R_DSA_1024, R_DSA_2048, DSA_NUM };
365 static const OPT_PAIR dsa_choices[DSA_NUM] = {
366     {"dsa1024", R_DSA_1024},
367     {"dsa2048", R_DSA_2048}
368 };
369 static double dsa_results[DSA_NUM][2];  /* 2 ops: sign then verify */
370
371 enum {
372     R_RSA_512, R_RSA_1024, R_RSA_2048, R_RSA_3072, R_RSA_4096, R_RSA_7680,
373     R_RSA_15360, RSA_NUM
374 };
375 static const OPT_PAIR rsa_choices[RSA_NUM] = {
376     {"rsa512", R_RSA_512},
377     {"rsa1024", R_RSA_1024},
378     {"rsa2048", R_RSA_2048},
379     {"rsa3072", R_RSA_3072},
380     {"rsa4096", R_RSA_4096},
381     {"rsa7680", R_RSA_7680},
382     {"rsa15360", R_RSA_15360}
383 };
384
385 static double rsa_results[RSA_NUM][4];  /* 4 ops: sign, verify, encrypt, decrypt */
386
387 #ifndef OPENSSL_NO_DH
388 enum ff_params_t {
389     R_FFDH_2048, R_FFDH_3072, R_FFDH_4096, R_FFDH_6144, R_FFDH_8192, FFDH_NUM
390 };
391
392 static const OPT_PAIR ffdh_choices[FFDH_NUM] = {
393     {"ffdh2048", R_FFDH_2048},
394     {"ffdh3072", R_FFDH_3072},
395     {"ffdh4096", R_FFDH_4096},
396     {"ffdh6144", R_FFDH_6144},
397     {"ffdh8192", R_FFDH_8192},
398 };
399
400 static double ffdh_results[FFDH_NUM][1];  /* 1 op: derivation */
401 #endif /* OPENSSL_NO_DH */
402
403 enum ec_curves_t {
404     R_EC_P160, R_EC_P192, R_EC_P224, R_EC_P256, R_EC_P384, R_EC_P521,
405 #ifndef OPENSSL_NO_EC2M
406     R_EC_K163, R_EC_K233, R_EC_K283, R_EC_K409, R_EC_K571,
407     R_EC_B163, R_EC_B233, R_EC_B283, R_EC_B409, R_EC_B571,
408 #endif
409     R_EC_BRP256R1, R_EC_BRP256T1, R_EC_BRP384R1, R_EC_BRP384T1,
410     R_EC_BRP512R1, R_EC_BRP512T1, ECDSA_NUM
411 };
412 /* list of ecdsa curves */
413 static const OPT_PAIR ecdsa_choices[ECDSA_NUM] = {
414     {"ecdsap160", R_EC_P160},
415     {"ecdsap192", R_EC_P192},
416     {"ecdsap224", R_EC_P224},
417     {"ecdsap256", R_EC_P256},
418     {"ecdsap384", R_EC_P384},
419     {"ecdsap521", R_EC_P521},
420 #ifndef OPENSSL_NO_EC2M
421     {"ecdsak163", R_EC_K163},
422     {"ecdsak233", R_EC_K233},
423     {"ecdsak283", R_EC_K283},
424     {"ecdsak409", R_EC_K409},
425     {"ecdsak571", R_EC_K571},
426     {"ecdsab163", R_EC_B163},
427     {"ecdsab233", R_EC_B233},
428     {"ecdsab283", R_EC_B283},
429     {"ecdsab409", R_EC_B409},
430     {"ecdsab571", R_EC_B571},
431 #endif
432     {"ecdsabrp256r1", R_EC_BRP256R1},
433     {"ecdsabrp256t1", R_EC_BRP256T1},
434     {"ecdsabrp384r1", R_EC_BRP384R1},
435     {"ecdsabrp384t1", R_EC_BRP384T1},
436     {"ecdsabrp512r1", R_EC_BRP512R1},
437     {"ecdsabrp512t1", R_EC_BRP512T1}
438 };
439 enum {
440 #ifndef OPENSSL_NO_ECX
441     R_EC_X25519 = ECDSA_NUM, R_EC_X448, EC_NUM
442 #else
443     EC_NUM = ECDSA_NUM
444 #endif
445 };
446 /* list of ecdh curves, extension of |ecdsa_choices| list above */
447 static const OPT_PAIR ecdh_choices[EC_NUM] = {
448     {"ecdhp160", R_EC_P160},
449     {"ecdhp192", R_EC_P192},
450     {"ecdhp224", R_EC_P224},
451     {"ecdhp256", R_EC_P256},
452     {"ecdhp384", R_EC_P384},
453     {"ecdhp521", R_EC_P521},
454 #ifndef OPENSSL_NO_EC2M
455     {"ecdhk163", R_EC_K163},
456     {"ecdhk233", R_EC_K233},
457     {"ecdhk283", R_EC_K283},
458     {"ecdhk409", R_EC_K409},
459     {"ecdhk571", R_EC_K571},
460     {"ecdhb163", R_EC_B163},
461     {"ecdhb233", R_EC_B233},
462     {"ecdhb283", R_EC_B283},
463     {"ecdhb409", R_EC_B409},
464     {"ecdhb571", R_EC_B571},
465 #endif
466     {"ecdhbrp256r1", R_EC_BRP256R1},
467     {"ecdhbrp256t1", R_EC_BRP256T1},
468     {"ecdhbrp384r1", R_EC_BRP384R1},
469     {"ecdhbrp384t1", R_EC_BRP384T1},
470     {"ecdhbrp512r1", R_EC_BRP512R1},
471     {"ecdhbrp512t1", R_EC_BRP512T1},
472 #ifndef OPENSSL_NO_ECX
473     {"ecdhx25519", R_EC_X25519},
474     {"ecdhx448", R_EC_X448}
475 #endif
476 };
477
478 static double ecdh_results[EC_NUM][1];      /* 1 op: derivation */
479 static double ecdsa_results[ECDSA_NUM][2];  /* 2 ops: sign then verify */
480
481 #ifndef OPENSSL_NO_ECX
482 enum { R_EC_Ed25519, R_EC_Ed448, EdDSA_NUM };
483 static const OPT_PAIR eddsa_choices[EdDSA_NUM] = {
484     {"ed25519", R_EC_Ed25519},
485     {"ed448", R_EC_Ed448}
486
487 };
488 static double eddsa_results[EdDSA_NUM][2];    /* 2 ops: sign then verify */
489 #endif /* OPENSSL_NO_ECX */
490
491 #ifndef OPENSSL_NO_SM2
492 enum { R_EC_CURVESM2, SM2_NUM };
493 static const OPT_PAIR sm2_choices[SM2_NUM] = {
494     {"curveSM2", R_EC_CURVESM2}
495 };
496 # define SM2_ID        "TLSv1.3+GM+Cipher+Suite"
497 # define SM2_ID_LEN    sizeof("TLSv1.3+GM+Cipher+Suite") - 1
498 static double sm2_results[SM2_NUM][2];    /* 2 ops: sign then verify */
499 #endif /* OPENSSL_NO_SM2 */
500
501 #define MAX_KEM_NUM 111
502 static size_t kems_algs_len = 0;
503 static char *kems_algname[MAX_KEM_NUM] = { NULL };
504 static double kems_results[MAX_KEM_NUM][3];  /* keygen, encaps, decaps */
505
506 #define MAX_SIG_NUM 111
507 static size_t sigs_algs_len = 0;
508 static char *sigs_algname[MAX_SIG_NUM] = { NULL };
509 static double sigs_results[MAX_SIG_NUM][3];  /* keygen, sign, verify */
510
511 #define COND(unused_cond) (run && count < INT_MAX)
512 #define COUNT(d) (count)
513
514 typedef struct loopargs_st {
515     ASYNC_JOB *inprogress_job;
516     ASYNC_WAIT_CTX *wait_ctx;
517     unsigned char *buf;
518     unsigned char *buf2;
519     unsigned char *buf_malloc;
520     unsigned char *buf2_malloc;
521     unsigned char *key;
522     size_t buflen;
523     size_t sigsize;
524     size_t encsize;
525     EVP_PKEY_CTX *rsa_sign_ctx[RSA_NUM];
526     EVP_PKEY_CTX *rsa_verify_ctx[RSA_NUM];
527     EVP_PKEY_CTX *rsa_encrypt_ctx[RSA_NUM];
528     EVP_PKEY_CTX *rsa_decrypt_ctx[RSA_NUM];
529     EVP_PKEY_CTX *dsa_sign_ctx[DSA_NUM];
530     EVP_PKEY_CTX *dsa_verify_ctx[DSA_NUM];
531     EVP_PKEY_CTX *ecdsa_sign_ctx[ECDSA_NUM];
532     EVP_PKEY_CTX *ecdsa_verify_ctx[ECDSA_NUM];
533     EVP_PKEY_CTX *ecdh_ctx[EC_NUM];
534 #ifndef OPENSSL_NO_ECX
535     EVP_MD_CTX *eddsa_ctx[EdDSA_NUM];
536     EVP_MD_CTX *eddsa_ctx2[EdDSA_NUM];
537 #endif /* OPENSSL_NO_ECX */
538 #ifndef OPENSSL_NO_SM2
539     EVP_MD_CTX *sm2_ctx[SM2_NUM];
540     EVP_MD_CTX *sm2_vfy_ctx[SM2_NUM];
541     EVP_PKEY *sm2_pkey[SM2_NUM];
542 #endif
543     unsigned char *secret_a;
544     unsigned char *secret_b;
545     size_t outlen[EC_NUM];
546 #ifndef OPENSSL_NO_DH
547     EVP_PKEY_CTX *ffdh_ctx[FFDH_NUM];
548     unsigned char *secret_ff_a;
549     unsigned char *secret_ff_b;
550 #endif
551     EVP_CIPHER_CTX *ctx;
552     EVP_MAC_CTX *mctx;
553     EVP_PKEY_CTX *kem_gen_ctx[MAX_KEM_NUM];
554     EVP_PKEY_CTX *kem_encaps_ctx[MAX_KEM_NUM];
555     EVP_PKEY_CTX *kem_decaps_ctx[MAX_KEM_NUM];
556     size_t kem_out_len[MAX_KEM_NUM];
557     size_t kem_secret_len[MAX_KEM_NUM];
558     unsigned char *kem_out[MAX_KEM_NUM];
559     unsigned char *kem_send_secret[MAX_KEM_NUM];
560     unsigned char *kem_rcv_secret[MAX_KEM_NUM];
561     EVP_PKEY_CTX *sig_gen_ctx[MAX_KEM_NUM];
562     EVP_PKEY_CTX *sig_sign_ctx[MAX_KEM_NUM];
563     EVP_PKEY_CTX *sig_verify_ctx[MAX_KEM_NUM];
564     size_t sig_max_sig_len[MAX_KEM_NUM];
565     size_t sig_act_sig_len[MAX_KEM_NUM];
566     unsigned char *sig_sig[MAX_KEM_NUM];
567 } loopargs_t;
568 static int run_benchmark(int async_jobs, int (*loop_function) (void *),
569                          loopargs_t *loopargs);
570
571 static unsigned int testnum;
572
573 static char *evp_mac_mdname = "md5";
574 static char *evp_hmac_name = NULL;
575 static const char *evp_md_name = NULL;
576 static char *evp_mac_ciphername = "aes-128-cbc";
577 static char *evp_cmac_name = NULL;
578
579 static int have_md(const char *name)
580 {
581     int ret = 0;
582     EVP_MD *md = NULL;
583
584     if (opt_md_silent(name, &md)) {
585         EVP_MD_CTX *ctx = EVP_MD_CTX_new();
586
587         if (ctx != NULL && EVP_DigestInit(ctx, md) > 0)
588             ret = 1;
589         EVP_MD_CTX_free(ctx);
590         EVP_MD_free(md);
591     }
592     return ret;
593 }
594
595 static int have_cipher(const char *name)
596 {
597     int ret = 0;
598     EVP_CIPHER *cipher = NULL;
599
600     if (opt_cipher_silent(name, &cipher)) {
601         EVP_CIPHER_CTX *ctx = EVP_CIPHER_CTX_new();
602
603         if (ctx != NULL
604             && EVP_CipherInit_ex(ctx, cipher, NULL, NULL, NULL, 1) > 0)
605             ret = 1;
606         EVP_CIPHER_CTX_free(ctx);
607         EVP_CIPHER_free(cipher);
608     }
609     return ret;
610 }
611
612 static int EVP_Digest_loop(const char *mdname, ossl_unused int algindex, void *args)
613 {
614     loopargs_t *tempargs = *(loopargs_t **) args;
615     unsigned char *buf = tempargs->buf;
616     unsigned char digest[EVP_MAX_MD_SIZE];
617     int count;
618     EVP_MD *md = NULL;
619
620     if (!opt_md_silent(mdname, &md))
621         return -1;
622     for (count = 0; COND(c[algindex][testnum]); count++) {
623         if (!EVP_Digest(buf, (size_t)lengths[testnum], digest, NULL, md,
624                         NULL)) {
625             count = -1;
626             break;
627         }
628     }
629     EVP_MD_free(md);
630     return count;
631 }
632
633 static int EVP_Digest_md_loop(void *args)
634 {
635     return EVP_Digest_loop(evp_md_name, D_EVP, args);
636 }
637
638 static int EVP_Digest_MD2_loop(void *args)
639 {
640     return EVP_Digest_loop("md2", D_MD2, args);
641 }
642
643 static int EVP_Digest_MDC2_loop(void *args)
644 {
645     return EVP_Digest_loop("mdc2", D_MDC2, args);
646 }
647
648 static int EVP_Digest_MD4_loop(void *args)
649 {
650     return EVP_Digest_loop("md4", D_MD4, args);
651 }
652
653 static int MD5_loop(void *args)
654 {
655     return EVP_Digest_loop("md5", D_MD5, args);
656 }
657
658 static int EVP_MAC_loop(ossl_unused int algindex, void *args)
659 {
660     loopargs_t *tempargs = *(loopargs_t **) args;
661     unsigned char *buf = tempargs->buf;
662     EVP_MAC_CTX *mctx = tempargs->mctx;
663     unsigned char mac[EVP_MAX_MD_SIZE];
664     int count;
665
666     for (count = 0; COND(c[algindex][testnum]); count++) {
667         size_t outl;
668
669         if (!EVP_MAC_init(mctx, NULL, 0, NULL)
670             || !EVP_MAC_update(mctx, buf, lengths[testnum])
671             || !EVP_MAC_final(mctx, mac, &outl, sizeof(mac)))
672             return -1;
673     }
674     return count;
675 }
676
677 static int HMAC_loop(void *args)
678 {
679     return EVP_MAC_loop(D_HMAC, args);
680 }
681
682 static int CMAC_loop(void *args)
683 {
684     return EVP_MAC_loop(D_EVP_CMAC, args);
685 }
686
687 static int SHA1_loop(void *args)
688 {
689     return EVP_Digest_loop("sha1", D_SHA1, args);
690 }
691
692 static int SHA256_loop(void *args)
693 {
694     return EVP_Digest_loop("sha256", D_SHA256, args);
695 }
696
697 static int SHA512_loop(void *args)
698 {
699     return EVP_Digest_loop("sha512", D_SHA512, args);
700 }
701
702 static int WHIRLPOOL_loop(void *args)
703 {
704     return EVP_Digest_loop("whirlpool", D_WHIRLPOOL, args);
705 }
706
707 static int EVP_Digest_RMD160_loop(void *args)
708 {
709     return EVP_Digest_loop("ripemd160", D_RMD160, args);
710 }
711
712 static int algindex;
713
714 static int EVP_Cipher_loop(void *args)
715 {
716     loopargs_t *tempargs = *(loopargs_t **) args;
717     unsigned char *buf = tempargs->buf;
718     int count;
719
720     if (tempargs->ctx == NULL)
721         return -1;
722     for (count = 0; COND(c[algindex][testnum]); count++)
723         if (EVP_Cipher(tempargs->ctx, buf, buf, (size_t)lengths[testnum]) <= 0)
724             return -1;
725     return count;
726 }
727
728 static int GHASH_loop(void *args)
729 {
730     loopargs_t *tempargs = *(loopargs_t **) args;
731     unsigned char *buf = tempargs->buf;
732     EVP_MAC_CTX *mctx = tempargs->mctx;
733     int count;
734
735     /* just do the update in the loop to be comparable with 1.1.1 */
736     for (count = 0; COND(c[D_GHASH][testnum]); count++) {
737         if (!EVP_MAC_update(mctx, buf, lengths[testnum]))
738             return -1;
739     }
740     return count;
741 }
742
743 #define MAX_BLOCK_SIZE 128
744
745 static unsigned char iv[2 * MAX_BLOCK_SIZE / 8];
746
747 static EVP_CIPHER_CTX *init_evp_cipher_ctx(const char *ciphername,
748                                            const unsigned char *key,
749                                            int keylen)
750 {
751     EVP_CIPHER_CTX *ctx = NULL;
752     EVP_CIPHER *cipher = NULL;
753
754     if (!opt_cipher_silent(ciphername, &cipher))
755         return NULL;
756
757     if ((ctx = EVP_CIPHER_CTX_new()) == NULL)
758         goto end;
759
760     if (!EVP_CipherInit_ex(ctx, cipher, NULL, NULL, NULL, 1)) {
761         EVP_CIPHER_CTX_free(ctx);
762         ctx = NULL;
763         goto end;
764     }
765
766     if (EVP_CIPHER_CTX_set_key_length(ctx, keylen) <= 0) {
767         EVP_CIPHER_CTX_free(ctx);
768         ctx = NULL;
769         goto end;
770     }
771
772     if (!EVP_CipherInit_ex(ctx, NULL, NULL, key, iv, 1)) {
773         EVP_CIPHER_CTX_free(ctx);
774         ctx = NULL;
775         goto end;
776     }
777
778 end:
779     EVP_CIPHER_free(cipher);
780     return ctx;
781 }
782
783 static int RAND_bytes_loop(void *args)
784 {
785     loopargs_t *tempargs = *(loopargs_t **) args;
786     unsigned char *buf = tempargs->buf;
787     int count;
788
789     for (count = 0; COND(c[D_RAND][testnum]); count++)
790         RAND_bytes(buf, lengths[testnum]);
791     return count;
792 }
793
794 static int decrypt = 0;
795 static int EVP_Update_loop(void *args)
796 {
797     loopargs_t *tempargs = *(loopargs_t **) args;
798     unsigned char *buf = tempargs->buf;
799     EVP_CIPHER_CTX *ctx = tempargs->ctx;
800     int outl, count, rc;
801
802     if (decrypt) {
803         for (count = 0; COND(c[D_EVP][testnum]); count++) {
804             rc = EVP_DecryptUpdate(ctx, buf, &outl, buf, lengths[testnum]);
805             if (rc != 1) {
806                 /* reset iv in case of counter overflow */
807                 rc = EVP_CipherInit_ex(ctx, NULL, NULL, NULL, iv, -1);
808             }
809         }
810     } else {
811         for (count = 0; COND(c[D_EVP][testnum]); count++) {
812             rc = EVP_EncryptUpdate(ctx, buf, &outl, buf, lengths[testnum]);
813             if (rc != 1) {
814                 /* reset iv in case of counter overflow */
815                 rc = EVP_CipherInit_ex(ctx, NULL, NULL, NULL, iv, -1);
816             }
817         }
818     }
819     if (decrypt)
820         rc = EVP_DecryptFinal_ex(ctx, buf, &outl);
821     else
822         rc = EVP_EncryptFinal_ex(ctx, buf, &outl);
823
824     if (rc == 0)
825         BIO_printf(bio_err, "Error finalizing cipher loop\n");
826     return count;
827 }
828
829 /*
830  * CCM does not support streaming. For the purpose of performance measurement,
831  * each message is encrypted using the same (key,iv)-pair. Do not use this
832  * code in your application.
833  */
834 static int EVP_Update_loop_ccm(void *args)
835 {
836     loopargs_t *tempargs = *(loopargs_t **) args;
837     unsigned char *buf = tempargs->buf;
838     EVP_CIPHER_CTX *ctx = tempargs->ctx;
839     int outl, count, realcount = 0, final;
840     unsigned char tag[12];
841
842     if (decrypt) {
843         for (count = 0; COND(c[D_EVP][testnum]); count++) {
844             if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_SET_TAG, sizeof(tag),
845                                       tag) > 0
846                 /* reset iv */
847                 && EVP_DecryptInit_ex(ctx, NULL, NULL, NULL, iv) > 0
848                 /* counter is reset on every update */
849                 && EVP_DecryptUpdate(ctx, buf, &outl, buf, lengths[testnum]) > 0)
850                 realcount++;
851         }
852     } else {
853         for (count = 0; COND(c[D_EVP][testnum]); count++) {
854             /* restore iv length field */
855             if (EVP_EncryptUpdate(ctx, NULL, &outl, NULL, lengths[testnum]) > 0
856                 /* counter is reset on every update */
857                 && EVP_EncryptUpdate(ctx, buf, &outl, buf, lengths[testnum]) > 0)
858                 realcount++;
859         }
860     }
861     if (decrypt)
862         final = EVP_DecryptFinal_ex(ctx, buf, &outl);
863     else
864         final = EVP_EncryptFinal_ex(ctx, buf, &outl);
865
866     if (final == 0)
867         BIO_printf(bio_err, "Error finalizing ccm loop\n");
868     return realcount;
869 }
870
871 /*
872  * To make AEAD benchmarking more relevant perform TLS-like operations,
873  * 13-byte AAD followed by payload. But don't use TLS-formatted AAD, as
874  * payload length is not actually limited by 16KB...
875  */
876 static int EVP_Update_loop_aead(void *args)
877 {
878     loopargs_t *tempargs = *(loopargs_t **) args;
879     unsigned char *buf = tempargs->buf;
880     EVP_CIPHER_CTX *ctx = tempargs->ctx;
881     int outl, count, realcount = 0;
882     unsigned char aad[13] = { 0xcc };
883     unsigned char faketag[16] = { 0xcc };
884
885     if (decrypt) {
886         for (count = 0; COND(c[D_EVP][testnum]); count++) {
887             if (EVP_DecryptInit_ex(ctx, NULL, NULL, NULL, iv) > 0
888                 && EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_SET_TAG,
889                                     sizeof(faketag), faketag) > 0
890                 && EVP_DecryptUpdate(ctx, NULL, &outl, aad, sizeof(aad)) > 0
891                 && EVP_DecryptUpdate(ctx, buf, &outl, buf, lengths[testnum]) > 0
892                 && EVP_DecryptFinal_ex(ctx, buf + outl, &outl) >0)
893                 realcount++;
894         }
895     } else {
896         for (count = 0; COND(c[D_EVP][testnum]); count++) {
897             if (EVP_EncryptInit_ex(ctx, NULL, NULL, NULL, iv) > 0
898                 && EVP_EncryptUpdate(ctx, NULL, &outl, aad, sizeof(aad)) > 0
899                 && EVP_EncryptUpdate(ctx, buf, &outl, buf, lengths[testnum]) > 0
900                 && EVP_EncryptFinal_ex(ctx, buf + outl, &outl) > 0)
901                 realcount++;
902         }
903     }
904     return realcount;
905 }
906
907 static int RSA_sign_loop(void *args)
908 {
909     loopargs_t *tempargs = *(loopargs_t **) args;
910     unsigned char *buf = tempargs->buf;
911     unsigned char *buf2 = tempargs->buf2;
912     size_t *rsa_num = &tempargs->sigsize;
913     EVP_PKEY_CTX **rsa_sign_ctx = tempargs->rsa_sign_ctx;
914     int ret, count;
915
916     for (count = 0; COND(rsa_c[testnum][0]); count++) {
917         *rsa_num = tempargs->buflen;
918         ret = EVP_PKEY_sign(rsa_sign_ctx[testnum], buf2, rsa_num, buf, 36);
919         if (ret <= 0) {
920             BIO_printf(bio_err, "RSA sign failure\n");
921             ERR_print_errors(bio_err);
922             count = -1;
923             break;
924         }
925     }
926     return count;
927 }
928
929 static int RSA_verify_loop(void *args)
930 {
931     loopargs_t *tempargs = *(loopargs_t **) args;
932     unsigned char *buf = tempargs->buf;
933     unsigned char *buf2 = tempargs->buf2;
934     size_t rsa_num = tempargs->sigsize;
935     EVP_PKEY_CTX **rsa_verify_ctx = tempargs->rsa_verify_ctx;
936     int ret, count;
937
938     for (count = 0; COND(rsa_c[testnum][1]); count++) {
939         ret = EVP_PKEY_verify(rsa_verify_ctx[testnum], buf2, rsa_num, buf, 36);
940         if (ret <= 0) {
941             BIO_printf(bio_err, "RSA verify failure\n");
942             ERR_print_errors(bio_err);
943             count = -1;
944             break;
945         }
946     }
947     return count;
948 }
949
950 static int RSA_encrypt_loop(void *args)
951 {
952     loopargs_t *tempargs = *(loopargs_t **) args;
953     unsigned char *buf = tempargs->buf;
954     unsigned char *buf2 = tempargs->buf2;
955     size_t *rsa_num = &tempargs->encsize;
956     EVP_PKEY_CTX **rsa_encrypt_ctx = tempargs->rsa_encrypt_ctx;
957     int ret, count;
958
959     for (count = 0; COND(rsa_c[testnum][2]); count++) {
960         *rsa_num = tempargs->buflen;
961         ret = EVP_PKEY_encrypt(rsa_encrypt_ctx[testnum], buf2, rsa_num, buf, 36);
962         if (ret <= 0) {
963             BIO_printf(bio_err, "RSA encrypt failure\n");
964             ERR_print_errors(bio_err);
965             count = -1;
966             break;
967         }
968     }
969     return count;
970 }
971
972 static int RSA_decrypt_loop(void *args)
973 {
974     loopargs_t *tempargs = *(loopargs_t **) args;
975     unsigned char *buf = tempargs->buf;
976     unsigned char *buf2 = tempargs->buf2;
977     size_t rsa_num;
978     EVP_PKEY_CTX **rsa_decrypt_ctx = tempargs->rsa_decrypt_ctx;
979     int ret, count;
980
981     for (count = 0; COND(rsa_c[testnum][3]); count++) {
982         rsa_num = tempargs->buflen;
983         ret = EVP_PKEY_decrypt(rsa_decrypt_ctx[testnum], buf, &rsa_num, buf2, tempargs->encsize);
984         if (ret <= 0) {
985             BIO_printf(bio_err, "RSA decrypt failure\n");
986             ERR_print_errors(bio_err);
987             count = -1;
988             break;
989         }
990     }
991     return count;
992 }
993
994 #ifndef OPENSSL_NO_DH
995
996 static int FFDH_derive_key_loop(void *args)
997 {
998     loopargs_t *tempargs = *(loopargs_t **) args;
999     EVP_PKEY_CTX *ffdh_ctx = tempargs->ffdh_ctx[testnum];
1000     unsigned char *derived_secret = tempargs->secret_ff_a;
1001     int count;
1002
1003     for (count = 0; COND(ffdh_c[testnum][0]); count++) {
1004         /* outlen can be overwritten with a too small value (no padding used) */
1005         size_t outlen = MAX_FFDH_SIZE;
1006
1007         EVP_PKEY_derive(ffdh_ctx, derived_secret, &outlen);
1008     }
1009     return count;
1010 }
1011 #endif /* OPENSSL_NO_DH */
1012
1013 static int DSA_sign_loop(void *args)
1014 {
1015     loopargs_t *tempargs = *(loopargs_t **) args;
1016     unsigned char *buf = tempargs->buf;
1017     unsigned char *buf2 = tempargs->buf2;
1018     size_t *dsa_num = &tempargs->sigsize;
1019     EVP_PKEY_CTX **dsa_sign_ctx = tempargs->dsa_sign_ctx;
1020     int ret, count;
1021
1022     for (count = 0; COND(dsa_c[testnum][0]); count++) {
1023         *dsa_num = tempargs->buflen;
1024         ret = EVP_PKEY_sign(dsa_sign_ctx[testnum], buf2, dsa_num, buf, 20);
1025         if (ret <= 0) {
1026             BIO_printf(bio_err, "DSA sign failure\n");
1027             ERR_print_errors(bio_err);
1028             count = -1;
1029             break;
1030         }
1031     }
1032     return count;
1033 }
1034
1035 static int DSA_verify_loop(void *args)
1036 {
1037     loopargs_t *tempargs = *(loopargs_t **) args;
1038     unsigned char *buf = tempargs->buf;
1039     unsigned char *buf2 = tempargs->buf2;
1040     size_t dsa_num = tempargs->sigsize;
1041     EVP_PKEY_CTX **dsa_verify_ctx = tempargs->dsa_verify_ctx;
1042     int ret, count;
1043
1044     for (count = 0; COND(dsa_c[testnum][1]); count++) {
1045         ret = EVP_PKEY_verify(dsa_verify_ctx[testnum], buf2, dsa_num, buf, 20);
1046         if (ret <= 0) {
1047             BIO_printf(bio_err, "DSA verify failure\n");
1048             ERR_print_errors(bio_err);
1049             count = -1;
1050             break;
1051         }
1052     }
1053     return count;
1054 }
1055
1056 static int ECDSA_sign_loop(void *args)
1057 {
1058     loopargs_t *tempargs = *(loopargs_t **) args;
1059     unsigned char *buf = tempargs->buf;
1060     unsigned char *buf2 = tempargs->buf2;
1061     size_t *ecdsa_num = &tempargs->sigsize;
1062     EVP_PKEY_CTX **ecdsa_sign_ctx = tempargs->ecdsa_sign_ctx;
1063     int ret, count;
1064
1065     for (count = 0; COND(ecdsa_c[testnum][0]); count++) {
1066         *ecdsa_num = tempargs->buflen;
1067         ret = EVP_PKEY_sign(ecdsa_sign_ctx[testnum], buf2, ecdsa_num, buf, 20);
1068         if (ret <= 0) {
1069             BIO_printf(bio_err, "ECDSA sign failure\n");
1070             ERR_print_errors(bio_err);
1071             count = -1;
1072             break;
1073         }
1074     }
1075     return count;
1076 }
1077
1078 static int ECDSA_verify_loop(void *args)
1079 {
1080     loopargs_t *tempargs = *(loopargs_t **) args;
1081     unsigned char *buf = tempargs->buf;
1082     unsigned char *buf2 = tempargs->buf2;
1083     size_t ecdsa_num = tempargs->sigsize;
1084     EVP_PKEY_CTX **ecdsa_verify_ctx = tempargs->ecdsa_verify_ctx;
1085     int ret, count;
1086
1087     for (count = 0; COND(ecdsa_c[testnum][1]); count++) {
1088         ret = EVP_PKEY_verify(ecdsa_verify_ctx[testnum], buf2, ecdsa_num,
1089                               buf, 20);
1090         if (ret <= 0) {
1091             BIO_printf(bio_err, "ECDSA verify failure\n");
1092             ERR_print_errors(bio_err);
1093             count = -1;
1094             break;
1095         }
1096     }
1097     return count;
1098 }
1099
1100 /* ******************************************************************** */
1101
1102 static int ECDH_EVP_derive_key_loop(void *args)
1103 {
1104     loopargs_t *tempargs = *(loopargs_t **) args;
1105     EVP_PKEY_CTX *ctx = tempargs->ecdh_ctx[testnum];
1106     unsigned char *derived_secret = tempargs->secret_a;
1107     int count;
1108     size_t *outlen = &(tempargs->outlen[testnum]);
1109
1110     for (count = 0; COND(ecdh_c[testnum][0]); count++)
1111         EVP_PKEY_derive(ctx, derived_secret, outlen);
1112
1113     return count;
1114 }
1115
1116 #ifndef OPENSSL_NO_ECX
1117 static int EdDSA_sign_loop(void *args)
1118 {
1119     loopargs_t *tempargs = *(loopargs_t **) args;
1120     unsigned char *buf = tempargs->buf;
1121     EVP_MD_CTX **edctx = tempargs->eddsa_ctx;
1122     unsigned char *eddsasig = tempargs->buf2;
1123     size_t *eddsasigsize = &tempargs->sigsize;
1124     int ret, count;
1125
1126     for (count = 0; COND(eddsa_c[testnum][0]); count++) {
1127         ret = EVP_DigestSignInit(edctx[testnum], NULL, NULL, NULL, NULL);
1128         if (ret == 0) {
1129             BIO_printf(bio_err, "EdDSA sign init failure\n");
1130             ERR_print_errors(bio_err);
1131             count = -1;
1132             break;
1133         }
1134         ret = EVP_DigestSign(edctx[testnum], eddsasig, eddsasigsize, buf, 20);
1135         if (ret == 0) {
1136             BIO_printf(bio_err, "EdDSA sign failure\n");
1137             ERR_print_errors(bio_err);
1138             count = -1;
1139             break;
1140         }
1141     }
1142     return count;
1143 }
1144
1145 static int EdDSA_verify_loop(void *args)
1146 {
1147     loopargs_t *tempargs = *(loopargs_t **) args;
1148     unsigned char *buf = tempargs->buf;
1149     EVP_MD_CTX **edctx = tempargs->eddsa_ctx2;
1150     unsigned char *eddsasig = tempargs->buf2;
1151     size_t eddsasigsize = tempargs->sigsize;
1152     int ret, count;
1153
1154     for (count = 0; COND(eddsa_c[testnum][1]); count++) {
1155         ret = EVP_DigestVerifyInit(edctx[testnum], NULL, NULL, NULL, NULL);
1156         if (ret == 0) {
1157             BIO_printf(bio_err, "EdDSA verify init failure\n");
1158             ERR_print_errors(bio_err);
1159             count = -1;
1160             break;
1161         }
1162         ret = EVP_DigestVerify(edctx[testnum], eddsasig, eddsasigsize, buf, 20);
1163         if (ret != 1) {
1164             BIO_printf(bio_err, "EdDSA verify failure\n");
1165             ERR_print_errors(bio_err);
1166             count = -1;
1167             break;
1168         }
1169     }
1170     return count;
1171 }
1172 #endif /* OPENSSL_NO_ECX */
1173
1174 #ifndef OPENSSL_NO_SM2
1175 static int SM2_sign_loop(void *args)
1176 {
1177     loopargs_t *tempargs = *(loopargs_t **) args;
1178     unsigned char *buf = tempargs->buf;
1179     EVP_MD_CTX **sm2ctx = tempargs->sm2_ctx;
1180     unsigned char *sm2sig = tempargs->buf2;
1181     size_t sm2sigsize;
1182     int ret, count;
1183     EVP_PKEY **sm2_pkey = tempargs->sm2_pkey;
1184     const size_t max_size = EVP_PKEY_get_size(sm2_pkey[testnum]);
1185
1186     for (count = 0; COND(sm2_c[testnum][0]); count++) {
1187         sm2sigsize = max_size;
1188
1189         if (!EVP_DigestSignInit(sm2ctx[testnum], NULL, EVP_sm3(),
1190                                 NULL, sm2_pkey[testnum])) {
1191             BIO_printf(bio_err, "SM2 init sign failure\n");
1192             ERR_print_errors(bio_err);
1193             count = -1;
1194             break;
1195         }
1196         ret = EVP_DigestSign(sm2ctx[testnum], sm2sig, &sm2sigsize,
1197                              buf, 20);
1198         if (ret == 0) {
1199             BIO_printf(bio_err, "SM2 sign failure\n");
1200             ERR_print_errors(bio_err);
1201             count = -1;
1202             break;
1203         }
1204         /* update the latest returned size and always use the fixed buffer size */
1205         tempargs->sigsize = sm2sigsize;
1206     }
1207
1208     return count;
1209 }
1210
1211 static int SM2_verify_loop(void *args)
1212 {
1213     loopargs_t *tempargs = *(loopargs_t **) args;
1214     unsigned char *buf = tempargs->buf;
1215     EVP_MD_CTX **sm2ctx = tempargs->sm2_vfy_ctx;
1216     unsigned char *sm2sig = tempargs->buf2;
1217     size_t sm2sigsize = tempargs->sigsize;
1218     int ret, count;
1219     EVP_PKEY **sm2_pkey = tempargs->sm2_pkey;
1220
1221     for (count = 0; COND(sm2_c[testnum][1]); count++) {
1222         if (!EVP_DigestVerifyInit(sm2ctx[testnum], NULL, EVP_sm3(),
1223                                   NULL, sm2_pkey[testnum])) {
1224             BIO_printf(bio_err, "SM2 verify init failure\n");
1225             ERR_print_errors(bio_err);
1226             count = -1;
1227             break;
1228         }
1229         ret = EVP_DigestVerify(sm2ctx[testnum], sm2sig, sm2sigsize,
1230                                buf, 20);
1231         if (ret != 1) {
1232             BIO_printf(bio_err, "SM2 verify failure\n");
1233             ERR_print_errors(bio_err);
1234             count = -1;
1235             break;
1236         }
1237     }
1238     return count;
1239 }
1240 #endif                         /* OPENSSL_NO_SM2 */
1241
1242 static int KEM_keygen_loop(void *args)
1243 {
1244     loopargs_t *tempargs = *(loopargs_t **) args;
1245     EVP_PKEY_CTX *ctx = tempargs->kem_gen_ctx[testnum];
1246     EVP_PKEY *pkey = NULL;
1247     int count;
1248
1249     for (count = 0; COND(kems_c[testnum][0]); count++) {
1250         if (EVP_PKEY_keygen(ctx, &pkey) <= 0)
1251             return -1;
1252         /*
1253          * runtime defined to quite some degree by randomness,
1254          * so performance overhead of _free doesn't impact
1255          * results significantly. In any case this test is
1256          * meant to permit relative algorithm performance
1257          * comparison.
1258          */
1259         EVP_PKEY_free(pkey);
1260         pkey = NULL;
1261     }
1262     return count;
1263 }
1264
1265 static int KEM_encaps_loop(void *args)
1266 {
1267     loopargs_t *tempargs = *(loopargs_t **) args;
1268     EVP_PKEY_CTX *ctx = tempargs->kem_encaps_ctx[testnum];
1269     size_t out_len = tempargs->kem_out_len[testnum];
1270     size_t secret_len = tempargs->kem_secret_len[testnum];
1271     unsigned char *out = tempargs->kem_out[testnum];
1272     unsigned char *secret = tempargs->kem_send_secret[testnum];
1273     int count;
1274
1275     for (count = 0; COND(kems_c[testnum][1]); count++) {
1276         if (EVP_PKEY_encapsulate(ctx, out, &out_len, secret, &secret_len) <= 0)
1277             return -1;
1278     }
1279     return count;
1280 }
1281
1282 static int KEM_decaps_loop(void *args)
1283 {
1284     loopargs_t *tempargs = *(loopargs_t **) args;
1285     EVP_PKEY_CTX *ctx = tempargs->kem_decaps_ctx[testnum];
1286     size_t out_len = tempargs->kem_out_len[testnum];
1287     size_t secret_len = tempargs->kem_secret_len[testnum];
1288     unsigned char *out = tempargs->kem_out[testnum];
1289     unsigned char *secret = tempargs->kem_send_secret[testnum];
1290     int count;
1291
1292     for (count = 0; COND(kems_c[testnum][2]); count++) {
1293         if (EVP_PKEY_decapsulate(ctx, secret, &secret_len, out, out_len) <= 0)
1294             return -1;
1295     }
1296     return count;
1297 }
1298
1299 static int SIG_keygen_loop(void *args)
1300 {
1301     loopargs_t *tempargs = *(loopargs_t **) args;
1302     EVP_PKEY_CTX *ctx = tempargs->sig_gen_ctx[testnum];
1303     EVP_PKEY *pkey = NULL;
1304     int count;
1305
1306     for (count = 0; COND(kems_c[testnum][0]); count++) {
1307         EVP_PKEY_keygen(ctx, &pkey);
1308         /* TBD: How much does free influence runtime? */
1309         EVP_PKEY_free(pkey);
1310         pkey = NULL;
1311     }
1312     return count;
1313 }
1314
1315 static int SIG_sign_loop(void *args)
1316 {
1317     loopargs_t *tempargs = *(loopargs_t **) args;
1318     EVP_PKEY_CTX *ctx = tempargs->sig_sign_ctx[testnum];
1319     /* be sure to not change stored sig: */
1320     unsigned char *sig = app_malloc(tempargs->sig_max_sig_len[testnum],
1321                                     "sig sign loop");
1322     unsigned char md[SHA256_DIGEST_LENGTH] = { 0 };
1323     size_t md_len = SHA256_DIGEST_LENGTH;
1324     int count;
1325
1326     for (count = 0; COND(kems_c[testnum][1]); count++) {
1327         size_t sig_len = tempargs->sig_max_sig_len[testnum];
1328         int ret = EVP_PKEY_sign(ctx, sig, &sig_len, md, md_len);
1329
1330         if (ret <= 0) {
1331             BIO_printf(bio_err, "SIG sign failure at count %d\n", count);
1332             ERR_print_errors(bio_err);
1333             count = -1;
1334             break;
1335         }
1336     }
1337     OPENSSL_free(sig);
1338     return count;
1339 }
1340
1341 static int SIG_verify_loop(void *args)
1342 {
1343     loopargs_t *tempargs = *(loopargs_t **) args;
1344     EVP_PKEY_CTX *ctx = tempargs->sig_verify_ctx[testnum];
1345     size_t sig_len = tempargs->sig_act_sig_len[testnum];
1346     unsigned char *sig = tempargs->sig_sig[testnum];
1347     unsigned char md[SHA256_DIGEST_LENGTH] = { 0 };
1348     size_t md_len = SHA256_DIGEST_LENGTH;
1349     int count;
1350
1351     for (count = 0; COND(kems_c[testnum][2]); count++) {
1352         int ret = EVP_PKEY_verify(ctx, sig, sig_len, md, md_len);
1353
1354         if (ret <= 0) {
1355             BIO_printf(bio_err, "SIG verify failure at count %d\n", count);
1356             ERR_print_errors(bio_err);
1357             count = -1;
1358             break;
1359         }
1360
1361     }
1362     return count;
1363 }
1364
1365 static int run_benchmark(int async_jobs,
1366                          int (*loop_function) (void *), loopargs_t *loopargs)
1367 {
1368     int job_op_count = 0;
1369     int total_op_count = 0;
1370     int num_inprogress = 0;
1371     int error = 0, i = 0, ret = 0;
1372     OSSL_ASYNC_FD job_fd = 0;
1373     size_t num_job_fds = 0;
1374
1375     if (async_jobs == 0) {
1376         return loop_function((void *)&loopargs);
1377     }
1378
1379     for (i = 0; i < async_jobs && !error; i++) {
1380         loopargs_t *looparg_item = loopargs + i;
1381
1382         /* Copy pointer content (looparg_t item address) into async context */
1383         ret = ASYNC_start_job(&loopargs[i].inprogress_job, loopargs[i].wait_ctx,
1384                               &job_op_count, loop_function,
1385                               (void *)&looparg_item, sizeof(looparg_item));
1386         switch (ret) {
1387         case ASYNC_PAUSE:
1388             ++num_inprogress;
1389             break;
1390         case ASYNC_FINISH:
1391             if (job_op_count == -1) {
1392                 error = 1;
1393             } else {
1394                 total_op_count += job_op_count;
1395             }
1396             break;
1397         case ASYNC_NO_JOBS:
1398         case ASYNC_ERR:
1399             BIO_printf(bio_err, "Failure in the job\n");
1400             ERR_print_errors(bio_err);
1401             error = 1;
1402             break;
1403         }
1404     }
1405
1406     while (num_inprogress > 0) {
1407 #if defined(OPENSSL_SYS_WINDOWS)
1408         DWORD avail = 0;
1409 #elif defined(OPENSSL_SYS_UNIX)
1410         int select_result = 0;
1411         OSSL_ASYNC_FD max_fd = 0;
1412         fd_set waitfdset;
1413
1414         FD_ZERO(&waitfdset);
1415
1416         for (i = 0; i < async_jobs && num_inprogress > 0; i++) {
1417             if (loopargs[i].inprogress_job == NULL)
1418                 continue;
1419
1420             if (!ASYNC_WAIT_CTX_get_all_fds
1421                 (loopargs[i].wait_ctx, NULL, &num_job_fds)
1422                 || num_job_fds > 1) {
1423                 BIO_printf(bio_err, "Too many fds in ASYNC_WAIT_CTX\n");
1424                 ERR_print_errors(bio_err);
1425                 error = 1;
1426                 break;
1427             }
1428             ASYNC_WAIT_CTX_get_all_fds(loopargs[i].wait_ctx, &job_fd,
1429                                        &num_job_fds);
1430             FD_SET(job_fd, &waitfdset);
1431             if (job_fd > max_fd)
1432                 max_fd = job_fd;
1433         }
1434
1435         if (max_fd >= (OSSL_ASYNC_FD)FD_SETSIZE) {
1436             BIO_printf(bio_err,
1437                        "Error: max_fd (%d) must be smaller than FD_SETSIZE (%d). "
1438                        "Decrease the value of async_jobs\n",
1439                        max_fd, FD_SETSIZE);
1440             ERR_print_errors(bio_err);
1441             error = 1;
1442             break;
1443         }
1444
1445         select_result = select(max_fd + 1, &waitfdset, NULL, NULL, NULL);
1446         if (select_result == -1 && errno == EINTR)
1447             continue;
1448
1449         if (select_result == -1) {
1450             BIO_printf(bio_err, "Failure in the select\n");
1451             ERR_print_errors(bio_err);
1452             error = 1;
1453             break;
1454         }
1455
1456         if (select_result == 0)
1457             continue;
1458 #endif
1459
1460         for (i = 0; i < async_jobs; i++) {
1461             if (loopargs[i].inprogress_job == NULL)
1462                 continue;
1463
1464             if (!ASYNC_WAIT_CTX_get_all_fds
1465                 (loopargs[i].wait_ctx, NULL, &num_job_fds)
1466                 || num_job_fds > 1) {
1467                 BIO_printf(bio_err, "Too many fds in ASYNC_WAIT_CTX\n");
1468                 ERR_print_errors(bio_err);
1469                 error = 1;
1470                 break;
1471             }
1472             ASYNC_WAIT_CTX_get_all_fds(loopargs[i].wait_ctx, &job_fd,
1473                                        &num_job_fds);
1474
1475 #if defined(OPENSSL_SYS_UNIX)
1476             if (num_job_fds == 1 && !FD_ISSET(job_fd, &waitfdset))
1477                 continue;
1478 #elif defined(OPENSSL_SYS_WINDOWS)
1479             if (num_job_fds == 1
1480                 && !PeekNamedPipe(job_fd, NULL, 0, NULL, &avail, NULL)
1481                 && avail > 0)
1482                 continue;
1483 #endif
1484
1485             ret = ASYNC_start_job(&loopargs[i].inprogress_job,
1486                                   loopargs[i].wait_ctx, &job_op_count,
1487                                   loop_function, (void *)(loopargs + i),
1488                                   sizeof(loopargs_t));
1489             switch (ret) {
1490             case ASYNC_PAUSE:
1491                 break;
1492             case ASYNC_FINISH:
1493                 if (job_op_count == -1) {
1494                     error = 1;
1495                 } else {
1496                     total_op_count += job_op_count;
1497                 }
1498                 --num_inprogress;
1499                 loopargs[i].inprogress_job = NULL;
1500                 break;
1501             case ASYNC_NO_JOBS:
1502             case ASYNC_ERR:
1503                 --num_inprogress;
1504                 loopargs[i].inprogress_job = NULL;
1505                 BIO_printf(bio_err, "Failure in the job\n");
1506                 ERR_print_errors(bio_err);
1507                 error = 1;
1508                 break;
1509             }
1510         }
1511     }
1512
1513     return error ? -1 : total_op_count;
1514 }
1515
1516 typedef struct ec_curve_st {
1517     const char *name;
1518     unsigned int nid;
1519     unsigned int bits;
1520     size_t sigsize; /* only used for EdDSA curves */
1521 } EC_CURVE;
1522
1523 static EVP_PKEY *get_ecdsa(const EC_CURVE *curve)
1524 {
1525     EVP_PKEY_CTX *kctx = NULL;
1526     EVP_PKEY *key = NULL;
1527
1528     /* Ensure that the error queue is empty */
1529     if (ERR_peek_error()) {
1530         BIO_printf(bio_err,
1531                    "WARNING: the error queue contains previous unhandled errors.\n");
1532         ERR_print_errors(bio_err);
1533     }
1534
1535     /*
1536      * Let's try to create a ctx directly from the NID: this works for
1537      * curves like Curve25519 that are not implemented through the low
1538      * level EC interface.
1539      * If this fails we try creating a EVP_PKEY_EC generic param ctx,
1540      * then we set the curve by NID before deriving the actual keygen
1541      * ctx for that specific curve.
1542      */
1543     kctx = EVP_PKEY_CTX_new_id(curve->nid, NULL);
1544     if (kctx == NULL) {
1545         EVP_PKEY_CTX *pctx = NULL;
1546         EVP_PKEY *params = NULL;
1547         /*
1548          * If we reach this code EVP_PKEY_CTX_new_id() failed and a
1549          * "int_ctx_new:unsupported algorithm" error was added to the
1550          * error queue.
1551          * We remove it from the error queue as we are handling it.
1552          */
1553         unsigned long error = ERR_peek_error();
1554
1555         if (error == ERR_peek_last_error() /* oldest and latest errors match */
1556             /* check that the error origin matches */
1557             && ERR_GET_LIB(error) == ERR_LIB_EVP
1558             && (ERR_GET_REASON(error) == EVP_R_UNSUPPORTED_ALGORITHM
1559                 || ERR_GET_REASON(error) == ERR_R_UNSUPPORTED))
1560             ERR_get_error(); /* pop error from queue */
1561         if (ERR_peek_error()) {
1562             BIO_printf(bio_err,
1563                        "Unhandled error in the error queue during EC key setup.\n");
1564             ERR_print_errors(bio_err);
1565             return NULL;
1566         }
1567
1568         /* Create the context for parameter generation */
1569         if ((pctx = EVP_PKEY_CTX_new_from_name(NULL, "EC", NULL)) == NULL
1570             || EVP_PKEY_paramgen_init(pctx) <= 0
1571             || EVP_PKEY_CTX_set_ec_paramgen_curve_nid(pctx,
1572                                                       curve->nid) <= 0
1573             || EVP_PKEY_paramgen(pctx, &params) <= 0) {
1574             BIO_printf(bio_err, "EC params init failure.\n");
1575             ERR_print_errors(bio_err);
1576             EVP_PKEY_CTX_free(pctx);
1577             return NULL;
1578         }
1579         EVP_PKEY_CTX_free(pctx);
1580
1581         /* Create the context for the key generation */
1582         kctx = EVP_PKEY_CTX_new(params, NULL);
1583         EVP_PKEY_free(params);
1584     }
1585     if (kctx == NULL
1586         || EVP_PKEY_keygen_init(kctx) <= 0
1587         || EVP_PKEY_keygen(kctx, &key) <= 0) {
1588         BIO_printf(bio_err, "EC key generation failure.\n");
1589         ERR_print_errors(bio_err);
1590         key = NULL;
1591     }
1592     EVP_PKEY_CTX_free(kctx);
1593     return key;
1594 }
1595
1596 #define stop_it(do_it, test_num)\
1597     memset(do_it + test_num, 0, OSSL_NELEM(do_it) - test_num);
1598
1599 /* Checks to see if algorithms are fetchable */
1600 #define IS_FETCHABLE(type, TYPE)                                \
1601     static int is_ ## type ## _fetchable(const TYPE *alg)       \
1602     {                                                           \
1603         TYPE *impl;                                             \
1604         const char *propq = app_get0_propq();                   \
1605         OSSL_LIB_CTX *libctx = app_get0_libctx();               \
1606         const char *name = TYPE ## _get0_name(alg);             \
1607                                                                 \
1608         ERR_set_mark();                                         \
1609         impl = TYPE ## _fetch(libctx, name, propq);             \
1610         ERR_pop_to_mark();                                      \
1611         if (impl == NULL)                                       \
1612             return 0;                                           \
1613         TYPE ## _free(impl);                                    \
1614         return 1;                                               \
1615     }
1616
1617 IS_FETCHABLE(signature, EVP_SIGNATURE)
1618 IS_FETCHABLE(kem, EVP_KEM)
1619
1620 DEFINE_STACK_OF(EVP_KEM)
1621
1622 static int kems_cmp(const EVP_KEM * const *a,
1623                     const EVP_KEM * const *b)
1624 {
1625     return strcmp(OSSL_PROVIDER_get0_name(EVP_KEM_get0_provider(*a)),
1626                   OSSL_PROVIDER_get0_name(EVP_KEM_get0_provider(*b)));
1627 }
1628
1629 static void collect_kem(EVP_KEM *kem, void *stack)
1630 {
1631     STACK_OF(EVP_KEM) *kem_stack = stack;
1632
1633     if (is_kem_fetchable(kem)
1634             && sk_EVP_KEM_push(kem_stack, kem) > 0) {
1635         EVP_KEM_up_ref(kem);
1636     }
1637 }
1638
1639 static int kem_locate(const char *algo, unsigned int *idx)
1640 {
1641     unsigned int i;
1642
1643     for (i = 0; i < kems_algs_len; i++) {
1644         if (strcmp(kems_algname[i], algo) == 0) {
1645             *idx = i;
1646             return 1;
1647         }
1648     }
1649     return 0;
1650 }
1651
1652 DEFINE_STACK_OF(EVP_SIGNATURE)
1653
1654 static int signatures_cmp(const EVP_SIGNATURE * const *a,
1655                           const EVP_SIGNATURE * const *b)
1656 {
1657     return strcmp(OSSL_PROVIDER_get0_name(EVP_SIGNATURE_get0_provider(*a)),
1658                   OSSL_PROVIDER_get0_name(EVP_SIGNATURE_get0_provider(*b)));
1659 }
1660
1661 static void collect_signatures(EVP_SIGNATURE *sig, void *stack)
1662 {
1663     STACK_OF(EVP_SIGNATURE) *sig_stack = stack;
1664
1665     if (is_signature_fetchable(sig)
1666             && sk_EVP_SIGNATURE_push(sig_stack, sig) > 0)
1667         EVP_SIGNATURE_up_ref(sig);
1668 }
1669
1670 static int sig_locate(const char *algo, unsigned int *idx)
1671 {
1672     unsigned int i;
1673
1674     for (i = 0; i < sigs_algs_len; i++) {
1675         if (strcmp(sigs_algname[i], algo) == 0) {
1676             *idx = i;
1677             return 1;
1678         }
1679     }
1680     return 0;
1681 }
1682
1683 static int get_max(const uint8_t doit[], size_t algs_len) {
1684     size_t i = 0;
1685     int maxcnt = 0;
1686
1687     for (i = 0; i < algs_len; i++)
1688         if (maxcnt < doit[i]) maxcnt = doit[i];
1689     return maxcnt;
1690 }
1691
1692 int speed_main(int argc, char **argv)
1693 {
1694     CONF *conf = NULL;
1695     ENGINE *e = NULL;
1696     loopargs_t *loopargs = NULL;
1697     const char *prog;
1698     const char *engine_id = NULL;
1699     EVP_CIPHER *evp_cipher = NULL;
1700     EVP_MAC *mac = NULL;
1701     double d = 0.0;
1702     OPTION_CHOICE o;
1703     int async_init = 0, multiblock = 0, pr_header = 0;
1704     uint8_t doit[ALGOR_NUM] = { 0 };
1705     int ret = 1, misalign = 0, lengths_single = 0, aead = 0;
1706     STACK_OF(EVP_KEM) *kem_stack = NULL;
1707     STACK_OF(EVP_SIGNATURE) *sig_stack = NULL;
1708     long count = 0;
1709     unsigned int size_num = SIZE_NUM;
1710     unsigned int i, k, loopargs_len = 0, async_jobs = 0;
1711     unsigned int idx;
1712     int keylen;
1713     int buflen;
1714     size_t declen;
1715     BIGNUM *bn = NULL;
1716     EVP_PKEY_CTX *genctx = NULL;
1717 #ifndef NO_FORK
1718     int multi = 0;
1719 #endif
1720     long op_count = 1;
1721     openssl_speed_sec_t seconds = { SECONDS, RSA_SECONDS, DSA_SECONDS,
1722                                     ECDSA_SECONDS, ECDH_SECONDS,
1723                                     EdDSA_SECONDS, SM2_SECONDS,
1724                                     FFDH_SECONDS, KEM_SECONDS,
1725                                     SIG_SECONDS };
1726
1727     static const unsigned char key32[32] = {
1728         0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0,
1729         0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12,
1730         0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, 0x34,
1731         0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, 0x34, 0x56
1732     };
1733     static const unsigned char deskey[] = {
1734         0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, /* key1 */
1735         0x34, 0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, /* key2 */
1736         0x56, 0x78, 0x9a, 0xbc, 0xde, 0xf0, 0x12, 0x34  /* key3 */
1737     };
1738     static const struct {
1739         const unsigned char *data;
1740         unsigned int length;
1741         unsigned int bits;
1742     } rsa_keys[] = {
1743         {   test512,   sizeof(test512),   512 },
1744         {  test1024,  sizeof(test1024),  1024 },
1745         {  test2048,  sizeof(test2048),  2048 },
1746         {  test3072,  sizeof(test3072),  3072 },
1747         {  test4096,  sizeof(test4096),  4096 },
1748         {  test7680,  sizeof(test7680),  7680 },
1749         { test15360, sizeof(test15360), 15360 }
1750     };
1751     uint8_t rsa_doit[RSA_NUM] = { 0 };
1752     int primes = RSA_DEFAULT_PRIME_NUM;
1753 #ifndef OPENSSL_NO_DH
1754     typedef struct ffdh_params_st {
1755         const char *name;
1756         unsigned int nid;
1757         unsigned int bits;
1758     } FFDH_PARAMS;
1759
1760     static const FFDH_PARAMS ffdh_params[FFDH_NUM] = {
1761         {"ffdh2048", NID_ffdhe2048, 2048},
1762         {"ffdh3072", NID_ffdhe3072, 3072},
1763         {"ffdh4096", NID_ffdhe4096, 4096},
1764         {"ffdh6144", NID_ffdhe6144, 6144},
1765         {"ffdh8192", NID_ffdhe8192, 8192}
1766     };
1767     uint8_t ffdh_doit[FFDH_NUM] = { 0 };
1768
1769 #endif /* OPENSSL_NO_DH */
1770     static const unsigned int dsa_bits[DSA_NUM] = { 1024, 2048 };
1771     uint8_t dsa_doit[DSA_NUM] = { 0 };
1772     /*
1773      * We only test over the following curves as they are representative, To
1774      * add tests over more curves, simply add the curve NID and curve name to
1775      * the following arrays and increase the |ecdh_choices| and |ecdsa_choices|
1776      * lists accordingly.
1777      */
1778     static const EC_CURVE ec_curves[EC_NUM] = {
1779         /* Prime Curves */
1780         {"secp160r1", NID_secp160r1, 160},
1781         {"nistp192", NID_X9_62_prime192v1, 192},
1782         {"nistp224", NID_secp224r1, 224},
1783         {"nistp256", NID_X9_62_prime256v1, 256},
1784         {"nistp384", NID_secp384r1, 384},
1785         {"nistp521", NID_secp521r1, 521},
1786 #ifndef OPENSSL_NO_EC2M
1787         /* Binary Curves */
1788         {"nistk163", NID_sect163k1, 163},
1789         {"nistk233", NID_sect233k1, 233},
1790         {"nistk283", NID_sect283k1, 283},
1791         {"nistk409", NID_sect409k1, 409},
1792         {"nistk571", NID_sect571k1, 571},
1793         {"nistb163", NID_sect163r2, 163},
1794         {"nistb233", NID_sect233r1, 233},
1795         {"nistb283", NID_sect283r1, 283},
1796         {"nistb409", NID_sect409r1, 409},
1797         {"nistb571", NID_sect571r1, 571},
1798 #endif
1799         {"brainpoolP256r1", NID_brainpoolP256r1, 256},
1800         {"brainpoolP256t1", NID_brainpoolP256t1, 256},
1801         {"brainpoolP384r1", NID_brainpoolP384r1, 384},
1802         {"brainpoolP384t1", NID_brainpoolP384t1, 384},
1803         {"brainpoolP512r1", NID_brainpoolP512r1, 512},
1804         {"brainpoolP512t1", NID_brainpoolP512t1, 512},
1805 #ifndef OPENSSL_NO_ECX
1806         /* Other and ECDH only ones */
1807         {"X25519", NID_X25519, 253},
1808         {"X448", NID_X448, 448}
1809 #endif
1810     };
1811 #ifndef OPENSSL_NO_ECX
1812     static const EC_CURVE ed_curves[EdDSA_NUM] = {
1813         /* EdDSA */
1814         {"Ed25519", NID_ED25519, 253, 64},
1815         {"Ed448", NID_ED448, 456, 114}
1816     };
1817 #endif /* OPENSSL_NO_ECX */
1818 #ifndef OPENSSL_NO_SM2
1819     static const EC_CURVE sm2_curves[SM2_NUM] = {
1820         /* SM2 */
1821         {"CurveSM2", NID_sm2, 256}
1822     };
1823     uint8_t sm2_doit[SM2_NUM] = { 0 };
1824 #endif
1825     uint8_t ecdsa_doit[ECDSA_NUM] = { 0 };
1826     uint8_t ecdh_doit[EC_NUM] = { 0 };
1827 #ifndef OPENSSL_NO_ECX
1828     uint8_t eddsa_doit[EdDSA_NUM] = { 0 };
1829 #endif /* OPENSSL_NO_ECX */
1830
1831     uint8_t kems_doit[MAX_KEM_NUM] = { 0 };
1832     uint8_t sigs_doit[MAX_SIG_NUM] = { 0 };
1833
1834     uint8_t do_kems = 0;
1835     uint8_t do_sigs = 0;
1836
1837     /* checks declared curves against choices list. */
1838 #ifndef OPENSSL_NO_ECX
1839     OPENSSL_assert(ed_curves[EdDSA_NUM - 1].nid == NID_ED448);
1840     OPENSSL_assert(strcmp(eddsa_choices[EdDSA_NUM - 1].name, "ed448") == 0);
1841
1842     OPENSSL_assert(ec_curves[EC_NUM - 1].nid == NID_X448);
1843     OPENSSL_assert(strcmp(ecdh_choices[EC_NUM - 1].name, "ecdhx448") == 0);
1844
1845     OPENSSL_assert(ec_curves[ECDSA_NUM - 1].nid == NID_brainpoolP512t1);
1846     OPENSSL_assert(strcmp(ecdsa_choices[ECDSA_NUM - 1].name, "ecdsabrp512t1") == 0);
1847 #endif /* OPENSSL_NO_ECX */
1848
1849 #ifndef OPENSSL_NO_SM2
1850     OPENSSL_assert(sm2_curves[SM2_NUM - 1].nid == NID_sm2);
1851     OPENSSL_assert(strcmp(sm2_choices[SM2_NUM - 1].name, "curveSM2") == 0);
1852 #endif
1853
1854     prog = opt_init(argc, argv, speed_options);
1855     while ((o = opt_next()) != OPT_EOF) {
1856         switch (o) {
1857         case OPT_EOF:
1858         case OPT_ERR:
1859  opterr:
1860             BIO_printf(bio_err, "%s: Use -help for summary.\n", prog);
1861             goto end;
1862         case OPT_HELP:
1863             opt_help(speed_options);
1864             ret = 0;
1865             goto end;
1866         case OPT_ELAPSED:
1867             usertime = 0;
1868             break;
1869         case OPT_EVP:
1870             if (doit[D_EVP]) {
1871                 BIO_printf(bio_err, "%s: -evp option cannot be used more than once\n", prog);
1872                 goto opterr;
1873             }
1874             ERR_set_mark();
1875             if (!opt_cipher_silent(opt_arg(), &evp_cipher)) {
1876                 if (have_md(opt_arg()))
1877                     evp_md_name = opt_arg();
1878             }
1879             if (evp_cipher == NULL && evp_md_name == NULL) {
1880                 ERR_clear_last_mark();
1881                 BIO_printf(bio_err,
1882                            "%s: %s is an unknown cipher or digest\n",
1883                            prog, opt_arg());
1884                 goto end;
1885             }
1886             ERR_pop_to_mark();
1887             doit[D_EVP] = 1;
1888             break;
1889         case OPT_HMAC:
1890             if (!have_md(opt_arg())) {
1891                 BIO_printf(bio_err, "%s: %s is an unknown digest\n",
1892                            prog, opt_arg());
1893                 goto end;
1894             }
1895             evp_mac_mdname = opt_arg();
1896             doit[D_HMAC] = 1;
1897             break;
1898         case OPT_CMAC:
1899             if (!have_cipher(opt_arg())) {
1900                 BIO_printf(bio_err, "%s: %s is an unknown cipher\n",
1901                            prog, opt_arg());
1902                 goto end;
1903             }
1904             evp_mac_ciphername = opt_arg();
1905             doit[D_EVP_CMAC] = 1;
1906             break;
1907         case OPT_DECRYPT:
1908             decrypt = 1;
1909             break;
1910         case OPT_ENGINE:
1911             /*
1912              * In a forked execution, an engine might need to be
1913              * initialised by each child process, not by the parent.
1914              * So store the name here and run setup_engine() later on.
1915              */
1916             engine_id = opt_arg();
1917             break;
1918         case OPT_MULTI:
1919 #ifndef NO_FORK
1920             multi = opt_int_arg();
1921             if ((size_t)multi >= SIZE_MAX / sizeof(int)) {
1922                 BIO_printf(bio_err, "%s: multi argument too large\n", prog);
1923                 return 0;
1924             }
1925 #endif
1926             break;
1927         case OPT_ASYNCJOBS:
1928 #ifndef OPENSSL_NO_ASYNC
1929             async_jobs = opt_int_arg();
1930             if (!ASYNC_is_capable()) {
1931                 BIO_printf(bio_err,
1932                            "%s: async_jobs specified but async not supported\n",
1933                            prog);
1934                 goto opterr;
1935             }
1936             if (async_jobs > 99999) {
1937                 BIO_printf(bio_err, "%s: too many async_jobs\n", prog);
1938                 goto opterr;
1939             }
1940 #endif
1941             break;
1942         case OPT_MISALIGN:
1943             misalign = opt_int_arg();
1944             if (misalign > MISALIGN) {
1945                 BIO_printf(bio_err,
1946                            "%s: Maximum offset is %d\n", prog, MISALIGN);
1947                 goto opterr;
1948             }
1949             break;
1950         case OPT_MR:
1951             mr = 1;
1952             break;
1953         case OPT_MB:
1954             multiblock = 1;
1955 #ifdef OPENSSL_NO_MULTIBLOCK
1956             BIO_printf(bio_err,
1957                        "%s: -mb specified but multi-block support is disabled\n",
1958                        prog);
1959             goto end;
1960 #endif
1961             break;
1962         case OPT_R_CASES:
1963             if (!opt_rand(o))
1964                 goto end;
1965             break;
1966         case OPT_PROV_CASES:
1967             if (!opt_provider(o))
1968                 goto end;
1969             break;
1970         case OPT_CONFIG:
1971             conf = app_load_config_modules(opt_arg());
1972             if (conf == NULL)
1973                 goto end;
1974             break;
1975         case OPT_PRIMES:
1976             primes = opt_int_arg();
1977             break;
1978         case OPT_SECONDS:
1979             seconds.sym = seconds.rsa = seconds.dsa = seconds.ecdsa
1980                         = seconds.ecdh = seconds.eddsa
1981                         = seconds.sm2 = seconds.ffdh
1982                         = seconds.kem = seconds.sig = opt_int_arg();
1983             break;
1984         case OPT_BYTES:
1985             lengths_single = opt_int_arg();
1986             lengths = &lengths_single;
1987             size_num = 1;
1988             break;
1989         case OPT_AEAD:
1990             aead = 1;
1991             break;
1992         case OPT_KEM:
1993             do_kems = 1;
1994             break;
1995         case OPT_SIG:
1996             do_sigs = 1;
1997             break;
1998         case OPT_MLOCK:
1999             domlock = 1;
2000 #if !defined(_WIN32) && !defined(OPENSSL_SYS_LINUX)
2001             BIO_printf(bio_err,
2002                        "%s: -mlock not supported on this platform\n",
2003                        prog);
2004             goto end;
2005 #endif
2006             break;
2007         }
2008     }
2009
2010     /* find all KEMs currently available */
2011     kem_stack = sk_EVP_KEM_new(kems_cmp);
2012     EVP_KEM_do_all_provided(app_get0_libctx(), collect_kem, kem_stack);
2013
2014     kems_algs_len = 0;
2015
2016     for (idx = 0; idx < (unsigned int)sk_EVP_KEM_num(kem_stack); idx++) {
2017         EVP_KEM *kem = sk_EVP_KEM_value(kem_stack, idx);
2018
2019         if (strcmp(EVP_KEM_get0_name(kem), "RSA") == 0) {
2020             if (kems_algs_len + OSSL_NELEM(rsa_choices) >= MAX_KEM_NUM) {
2021                 BIO_printf(bio_err,
2022                            "Too many KEMs registered. Change MAX_KEM_NUM.\n");
2023                 goto end;
2024             }
2025             for (i = 0; i < OSSL_NELEM(rsa_choices); i++) {
2026                 kems_doit[kems_algs_len] = 1;
2027                 kems_algname[kems_algs_len++] = OPENSSL_strdup(rsa_choices[i].name);
2028             }
2029         } else if (strcmp(EVP_KEM_get0_name(kem), "EC") == 0) {
2030             if (kems_algs_len + 3 >= MAX_KEM_NUM) {
2031                 BIO_printf(bio_err,
2032                            "Too many KEMs registered. Change MAX_KEM_NUM.\n");
2033                 goto end;
2034             }
2035             kems_doit[kems_algs_len] = 1;
2036             kems_algname[kems_algs_len++] = OPENSSL_strdup("ECP-256");
2037             kems_doit[kems_algs_len] = 1;
2038             kems_algname[kems_algs_len++] = OPENSSL_strdup("ECP-384");
2039             kems_doit[kems_algs_len] = 1;
2040             kems_algname[kems_algs_len++] = OPENSSL_strdup("ECP-521");
2041         } else {
2042             if (kems_algs_len + 1 >= MAX_KEM_NUM) {
2043                 BIO_printf(bio_err,
2044                            "Too many KEMs registered. Change MAX_KEM_NUM.\n");
2045                 goto end;
2046             }
2047             kems_doit[kems_algs_len] = 1;
2048             kems_algname[kems_algs_len++] = OPENSSL_strdup(EVP_KEM_get0_name(kem));
2049         }
2050     }
2051     sk_EVP_KEM_pop_free(kem_stack, EVP_KEM_free);
2052     kem_stack = NULL;
2053
2054     /* find all SIGNATUREs currently available */
2055     sig_stack = sk_EVP_SIGNATURE_new(signatures_cmp);
2056     EVP_SIGNATURE_do_all_provided(app_get0_libctx(), collect_signatures, sig_stack);
2057
2058     sigs_algs_len = 0;
2059
2060     for (idx = 0; idx < (unsigned int)sk_EVP_SIGNATURE_num(sig_stack); idx++) {
2061         EVP_SIGNATURE *s = sk_EVP_SIGNATURE_value(sig_stack, idx);
2062         const char *sig_name = EVP_SIGNATURE_get0_name(s);
2063
2064         if (strcmp(sig_name, "RSA") == 0) {
2065             if (sigs_algs_len + OSSL_NELEM(rsa_choices) >= MAX_SIG_NUM) {
2066                 BIO_printf(bio_err,
2067                            "Too many signatures registered. Change MAX_SIG_NUM.\n");
2068                 goto end;
2069             }
2070             for (i = 0; i < OSSL_NELEM(rsa_choices); i++) {
2071                 sigs_doit[sigs_algs_len] = 1;
2072                 sigs_algname[sigs_algs_len++] = OPENSSL_strdup(rsa_choices[i].name);
2073             }
2074         }
2075         else if (strcmp(sig_name, "DSA") == 0) {
2076             if (sigs_algs_len + DSA_NUM >= MAX_SIG_NUM) {
2077                 BIO_printf(bio_err,
2078                            "Too many signatures registered. Change MAX_SIG_NUM.\n");
2079                 goto end;
2080             }
2081             for (i = 0; i < DSA_NUM; i++) {
2082                 sigs_doit[sigs_algs_len] = 1;
2083                 sigs_algname[sigs_algs_len++] = OPENSSL_strdup(dsa_choices[i].name);
2084             }
2085         }
2086         /* skipping these algs as tested elsewhere - and b/o setup is a pain */
2087         else if (strcmp(sig_name, "ED25519") &&
2088                  strcmp(sig_name, "ED448") &&
2089                  strcmp(sig_name, "ECDSA") &&
2090                  strcmp(sig_name, "HMAC") &&
2091                  strcmp(sig_name, "SIPHASH") &&
2092                  strcmp(sig_name, "POLY1305") &&
2093                  strcmp(sig_name, "CMAC") &&
2094                  strcmp(sig_name, "SM2")) { /* skip alg */
2095             if (sigs_algs_len + 1 >= MAX_SIG_NUM) {
2096                 BIO_printf(bio_err,
2097                            "Too many signatures registered. Change MAX_SIG_NUM.\n");
2098                 goto end;
2099             }
2100             /* activate this provider algorithm */
2101             sigs_doit[sigs_algs_len] = 1;
2102             sigs_algname[sigs_algs_len++] = OPENSSL_strdup(sig_name);
2103         }
2104     }
2105     sk_EVP_SIGNATURE_pop_free(sig_stack, EVP_SIGNATURE_free);
2106     sig_stack = NULL;
2107
2108     /* Remaining arguments are algorithms. */
2109     argc = opt_num_rest();
2110     argv = opt_rest();
2111
2112     if (!app_RAND_load())
2113         goto end;
2114
2115     for (; *argv; argv++) {
2116         const char *algo = *argv;
2117         int algo_found = 0;
2118
2119         if (opt_found(algo, doit_choices, &i)) {
2120             doit[i] = 1;
2121             algo_found = 1;
2122         }
2123         if (strcmp(algo, "des") == 0) {
2124             doit[D_CBC_DES] = doit[D_EDE3_DES] = 1;
2125             algo_found = 1;
2126         }
2127         if (strcmp(algo, "sha") == 0) {
2128             doit[D_SHA1] = doit[D_SHA256] = doit[D_SHA512] = 1;
2129             algo_found = 1;
2130         }
2131 #ifndef OPENSSL_NO_DEPRECATED_3_0
2132         if (strcmp(algo, "openssl") == 0) /* just for compatibility */
2133             algo_found = 1;
2134 #endif
2135         if (HAS_PREFIX(algo, "rsa")) {
2136             if (algo[sizeof("rsa") - 1] == '\0') {
2137                 memset(rsa_doit, 1, sizeof(rsa_doit));
2138                 algo_found = 1;
2139             }
2140             if (opt_found(algo, rsa_choices, &i)) {
2141                 rsa_doit[i] = 1;
2142                 algo_found = 1;
2143             }
2144         }
2145 #ifndef OPENSSL_NO_DH
2146         if (HAS_PREFIX(algo, "ffdh")) {
2147             if (algo[sizeof("ffdh") - 1] == '\0') {
2148                 memset(ffdh_doit, 1, sizeof(ffdh_doit));
2149                 algo_found = 1;
2150             }
2151             if (opt_found(algo, ffdh_choices, &i)) {
2152                 ffdh_doit[i] = 2;
2153                 algo_found = 1;
2154             }
2155         }
2156 #endif
2157         if (HAS_PREFIX(algo, "dsa")) {
2158             if (algo[sizeof("dsa") - 1] == '\0') {
2159                 memset(dsa_doit, 1, sizeof(dsa_doit));
2160                 algo_found = 1;
2161             }
2162             if (opt_found(algo, dsa_choices, &i)) {
2163                 dsa_doit[i] = 2;
2164                 algo_found = 1;
2165             }
2166         }
2167         if (strcmp(algo, "aes") == 0) {
2168             doit[D_CBC_128_AES] = doit[D_CBC_192_AES] = doit[D_CBC_256_AES] = 1;
2169             algo_found = 1;
2170         }
2171         if (strcmp(algo, "camellia") == 0) {
2172             doit[D_CBC_128_CML] = doit[D_CBC_192_CML] = doit[D_CBC_256_CML] = 1;
2173             algo_found = 1;
2174         }
2175         if (HAS_PREFIX(algo, "ecdsa")) {
2176             if (algo[sizeof("ecdsa") - 1] == '\0') {
2177                 memset(ecdsa_doit, 1, sizeof(ecdsa_doit));
2178                 algo_found = 1;
2179             }
2180             if (opt_found(algo, ecdsa_choices, &i)) {
2181                 ecdsa_doit[i] = 2;
2182                 algo_found = 1;
2183             }
2184         }
2185         if (HAS_PREFIX(algo, "ecdh")) {
2186             if (algo[sizeof("ecdh") - 1] == '\0') {
2187                 memset(ecdh_doit, 1, sizeof(ecdh_doit));
2188                 algo_found = 1;
2189             }
2190             if (opt_found(algo, ecdh_choices, &i)) {
2191                 ecdh_doit[i] = 2;
2192                 algo_found = 1;
2193             }
2194         }
2195 #ifndef OPENSSL_NO_ECX
2196         if (strcmp(algo, "eddsa") == 0) {
2197             memset(eddsa_doit, 1, sizeof(eddsa_doit));
2198             algo_found = 1;
2199         }
2200         if (opt_found(algo, eddsa_choices, &i)) {
2201             eddsa_doit[i] = 2;
2202             algo_found = 1;
2203         }
2204 #endif /* OPENSSL_NO_ECX */
2205 #ifndef OPENSSL_NO_SM2
2206         if (strcmp(algo, "sm2") == 0) {
2207             memset(sm2_doit, 1, sizeof(sm2_doit));
2208             algo_found = 1;
2209         }
2210         if (opt_found(algo, sm2_choices, &i)) {
2211             sm2_doit[i] = 2;
2212             algo_found = 1;
2213         }
2214 #endif
2215         if (kem_locate(algo, &idx)) {
2216             kems_doit[idx]++;
2217             do_kems = 1;
2218             algo_found = 1;
2219         }
2220         if (sig_locate(algo, &idx)) {
2221             sigs_doit[idx]++;
2222             do_sigs = 1;
2223             algo_found = 1;
2224         }
2225
2226         if (!algo_found) {
2227             BIO_printf(bio_err, "%s: Unknown algorithm %s\n", prog, algo);
2228             goto end;
2229         }
2230     }
2231
2232     /* Sanity checks */
2233     if (aead) {
2234         if (evp_cipher == NULL) {
2235             BIO_printf(bio_err, "-aead can be used only with an AEAD cipher\n");
2236             goto end;
2237         } else if (!(EVP_CIPHER_get_flags(evp_cipher) &
2238                      EVP_CIPH_FLAG_AEAD_CIPHER)) {
2239             BIO_printf(bio_err, "%s is not an AEAD cipher\n",
2240                        EVP_CIPHER_get0_name(evp_cipher));
2241             goto end;
2242         }
2243     }
2244     if (kems_algs_len > 0) {
2245         int maxcnt = get_max(kems_doit, kems_algs_len);
2246
2247         if (maxcnt > 1) {
2248             /* some algs explicitly selected */
2249             for (i = 0; i < kems_algs_len; i++) {
2250                 /* disable the rest */
2251                 kems_doit[i]--;
2252             }
2253         }
2254     }
2255     if (sigs_algs_len > 0) {
2256         int maxcnt = get_max(sigs_doit, sigs_algs_len);
2257
2258         if (maxcnt > 1) {
2259             /* some algs explicitly selected */
2260             for (i = 0; i < sigs_algs_len; i++) {
2261                 /* disable the rest */
2262                 sigs_doit[i]--;
2263             }
2264         }
2265     }
2266     if (multiblock) {
2267         if (evp_cipher == NULL) {
2268             BIO_printf(bio_err, "-mb can be used only with a multi-block"
2269                                 " capable cipher\n");
2270             goto end;
2271         } else if (!(EVP_CIPHER_get_flags(evp_cipher) &
2272                      EVP_CIPH_FLAG_TLS1_1_MULTIBLOCK)) {
2273             BIO_printf(bio_err, "%s is not a multi-block capable\n",
2274                        EVP_CIPHER_get0_name(evp_cipher));
2275             goto end;
2276         } else if (async_jobs > 0) {
2277             BIO_printf(bio_err, "Async mode is not supported with -mb");
2278             goto end;
2279         }
2280     }
2281
2282     /* Initialize the job pool if async mode is enabled */
2283     if (async_jobs > 0) {
2284         async_init = ASYNC_init_thread(async_jobs, async_jobs);
2285         if (!async_init) {
2286             BIO_printf(bio_err, "Error creating the ASYNC job pool\n");
2287             goto end;
2288         }
2289     }
2290
2291     loopargs_len = (async_jobs == 0 ? 1 : async_jobs);
2292     loopargs =
2293         app_malloc(loopargs_len * sizeof(loopargs_t), "array of loopargs");
2294     memset(loopargs, 0, loopargs_len * sizeof(loopargs_t));
2295
2296     buflen = lengths[size_num - 1];
2297     if (buflen < 36)    /* size of random vector in RSA benchmark */
2298         buflen = 36;
2299     if (INT_MAX - (MAX_MISALIGNMENT + 1) < buflen) {
2300         BIO_printf(bio_err, "Error: buffer size too large\n");
2301         goto end;
2302     }
2303     buflen += MAX_MISALIGNMENT + 1;
2304     for (i = 0; i < loopargs_len; i++) {
2305         if (async_jobs > 0) {
2306             loopargs[i].wait_ctx = ASYNC_WAIT_CTX_new();
2307             if (loopargs[i].wait_ctx == NULL) {
2308                 BIO_printf(bio_err, "Error creating the ASYNC_WAIT_CTX\n");
2309                 goto end;
2310             }
2311         }
2312
2313         loopargs[i].buf_malloc = app_malloc(buflen, "input buffer");
2314         loopargs[i].buf2_malloc = app_malloc(buflen, "input buffer");
2315
2316         /* Align the start of buffers on a 64 byte boundary */
2317         loopargs[i].buf = loopargs[i].buf_malloc + misalign;
2318         loopargs[i].buf2 = loopargs[i].buf2_malloc + misalign;
2319         loopargs[i].buflen = buflen - misalign;
2320         loopargs[i].sigsize = buflen - misalign;
2321         loopargs[i].secret_a = app_malloc(MAX_ECDH_SIZE, "ECDH secret a");
2322         loopargs[i].secret_b = app_malloc(MAX_ECDH_SIZE, "ECDH secret b");
2323 #ifndef OPENSSL_NO_DH
2324         loopargs[i].secret_ff_a = app_malloc(MAX_FFDH_SIZE, "FFDH secret a");
2325         loopargs[i].secret_ff_b = app_malloc(MAX_FFDH_SIZE, "FFDH secret b");
2326 #endif
2327     }
2328
2329 #ifndef NO_FORK
2330     if (multi && do_multi(multi, size_num))
2331         goto show_res;
2332 #endif
2333
2334     for (i = 0; i < loopargs_len; ++i) {
2335         if (domlock) {
2336 #if defined(_WIN32)
2337             (void)VirtualLock(loopargs[i].buf_malloc, buflen);
2338             (void)VirtualLock(loopargs[i].buf2_malloc, buflen);
2339 #elif defined(OPENSSL_SYS_LINUX)
2340             (void)mlock(loopargs[i].buf_malloc, buflen);
2341             (void)mlock(loopargs[i].buf_malloc, buflen);
2342 #endif
2343         }
2344         memset(loopargs[i].buf_malloc, 0, buflen);
2345         memset(loopargs[i].buf2_malloc, 0, buflen);
2346     }
2347
2348     /* Initialize the engine after the fork */
2349     e = setup_engine(engine_id, 0);
2350
2351     /* No parameters; turn on everything. */
2352     if (argc == 0 && !doit[D_EVP] && !doit[D_HMAC]
2353         && !doit[D_EVP_CMAC] && !do_kems && !do_sigs) {
2354         memset(doit, 1, sizeof(doit));
2355         doit[D_EVP] = doit[D_EVP_CMAC] = 0;
2356         ERR_set_mark();
2357         for (i = D_MD2; i <= D_WHIRLPOOL; i++) {
2358             if (!have_md(names[i]))
2359                 doit[i] = 0;
2360         }
2361         for (i = D_CBC_DES; i <= D_CBC_256_CML; i++) {
2362             if (!have_cipher(names[i]))
2363                 doit[i] = 0;
2364         }
2365         if ((mac = EVP_MAC_fetch(app_get0_libctx(), "GMAC",
2366                                  app_get0_propq())) != NULL) {
2367             EVP_MAC_free(mac);
2368             mac = NULL;
2369         } else {
2370             doit[D_GHASH] = 0;
2371         }
2372         if ((mac = EVP_MAC_fetch(app_get0_libctx(), "HMAC",
2373                                  app_get0_propq())) != NULL) {
2374             EVP_MAC_free(mac);
2375             mac = NULL;
2376         } else {
2377             doit[D_HMAC] = 0;
2378         }
2379         ERR_pop_to_mark();
2380         memset(rsa_doit, 1, sizeof(rsa_doit));
2381 #ifndef OPENSSL_NO_DH
2382         memset(ffdh_doit, 1, sizeof(ffdh_doit));
2383 #endif
2384         memset(dsa_doit, 1, sizeof(dsa_doit));
2385 #ifndef OPENSSL_NO_ECX
2386         memset(ecdsa_doit, 1, sizeof(ecdsa_doit));
2387         memset(ecdh_doit, 1, sizeof(ecdh_doit));
2388         memset(eddsa_doit, 1, sizeof(eddsa_doit));
2389 #endif /* OPENSSL_NO_ECX */
2390 #ifndef OPENSSL_NO_SM2
2391         memset(sm2_doit, 1, sizeof(sm2_doit));
2392 #endif
2393         memset(kems_doit, 1, sizeof(kems_doit));
2394         do_kems = 1;
2395         memset(sigs_doit, 1, sizeof(sigs_doit));
2396         do_sigs = 1;
2397     }
2398     for (i = 0; i < ALGOR_NUM; i++)
2399         if (doit[i])
2400             pr_header++;
2401
2402     if (usertime == 0 && !mr)
2403         BIO_printf(bio_err,
2404                    "You have chosen to measure elapsed time "
2405                    "instead of user CPU time.\n");
2406
2407 #if SIGALRM > 0
2408     signal(SIGALRM, alarmed);
2409 #endif
2410
2411     if (doit[D_MD2]) {
2412         for (testnum = 0; testnum < size_num; testnum++) {
2413             print_message(names[D_MD2], lengths[testnum], seconds.sym);
2414             Time_F(START);
2415             count = run_benchmark(async_jobs, EVP_Digest_MD2_loop, loopargs);
2416             d = Time_F(STOP);
2417             print_result(D_MD2, testnum, count, d);
2418             if (count < 0)
2419                 break;
2420         }
2421     }
2422
2423     if (doit[D_MDC2]) {
2424         for (testnum = 0; testnum < size_num; testnum++) {
2425             print_message(names[D_MDC2], lengths[testnum], seconds.sym);
2426             Time_F(START);
2427             count = run_benchmark(async_jobs, EVP_Digest_MDC2_loop, loopargs);
2428             d = Time_F(STOP);
2429             print_result(D_MDC2, testnum, count, d);
2430             if (count < 0)
2431                 break;
2432         }
2433     }
2434
2435     if (doit[D_MD4]) {
2436         for (testnum = 0; testnum < size_num; testnum++) {
2437             print_message(names[D_MD4], lengths[testnum], seconds.sym);
2438             Time_F(START);
2439             count = run_benchmark(async_jobs, EVP_Digest_MD4_loop, loopargs);
2440             d = Time_F(STOP);
2441             print_result(D_MD4, testnum, count, d);
2442             if (count < 0)
2443                 break;
2444         }
2445     }
2446
2447     if (doit[D_MD5]) {
2448         for (testnum = 0; testnum < size_num; testnum++) {
2449             print_message(names[D_MD5], lengths[testnum], seconds.sym);
2450             Time_F(START);
2451             count = run_benchmark(async_jobs, MD5_loop, loopargs);
2452             d = Time_F(STOP);
2453             print_result(D_MD5, testnum, count, d);
2454             if (count < 0)
2455                 break;
2456         }
2457     }
2458
2459     if (doit[D_SHA1]) {
2460         for (testnum = 0; testnum < size_num; testnum++) {
2461             print_message(names[D_SHA1], lengths[testnum], seconds.sym);
2462             Time_F(START);
2463             count = run_benchmark(async_jobs, SHA1_loop, loopargs);
2464             d = Time_F(STOP);
2465             print_result(D_SHA1, testnum, count, d);
2466             if (count < 0)
2467                 break;
2468         }
2469     }
2470
2471     if (doit[D_SHA256]) {
2472         for (testnum = 0; testnum < size_num; testnum++) {
2473             print_message(names[D_SHA256], lengths[testnum], seconds.sym);
2474             Time_F(START);
2475             count = run_benchmark(async_jobs, SHA256_loop, loopargs);
2476             d = Time_F(STOP);
2477             print_result(D_SHA256, testnum, count, d);
2478             if (count < 0)
2479                 break;
2480         }
2481     }
2482
2483     if (doit[D_SHA512]) {
2484         for (testnum = 0; testnum < size_num; testnum++) {
2485             print_message(names[D_SHA512], lengths[testnum], seconds.sym);
2486             Time_F(START);
2487             count = run_benchmark(async_jobs, SHA512_loop, loopargs);
2488             d = Time_F(STOP);
2489             print_result(D_SHA512, testnum, count, d);
2490             if (count < 0)
2491                 break;
2492         }
2493     }
2494
2495     if (doit[D_WHIRLPOOL]) {
2496         for (testnum = 0; testnum < size_num; testnum++) {
2497             print_message(names[D_WHIRLPOOL], lengths[testnum], seconds.sym);
2498             Time_F(START);
2499             count = run_benchmark(async_jobs, WHIRLPOOL_loop, loopargs);
2500             d = Time_F(STOP);
2501             print_result(D_WHIRLPOOL, testnum, count, d);
2502             if (count < 0)
2503                 break;
2504         }
2505     }
2506
2507     if (doit[D_RMD160]) {
2508         for (testnum = 0; testnum < size_num; testnum++) {
2509             print_message(names[D_RMD160], lengths[testnum], seconds.sym);
2510             Time_F(START);
2511             count = run_benchmark(async_jobs, EVP_Digest_RMD160_loop, loopargs);
2512             d = Time_F(STOP);
2513             print_result(D_RMD160, testnum, count, d);
2514             if (count < 0)
2515                 break;
2516         }
2517     }
2518
2519     if (doit[D_HMAC]) {
2520         static const char hmac_key[] = "This is a key...";
2521         int len = strlen(hmac_key);
2522         OSSL_PARAM params[3];
2523
2524         mac = EVP_MAC_fetch(app_get0_libctx(), "HMAC", app_get0_propq());
2525         if (mac == NULL || evp_mac_mdname == NULL)
2526             goto end;
2527
2528         evp_hmac_name = app_malloc(sizeof("hmac()") + strlen(evp_mac_mdname),
2529                                    "HMAC name");
2530         sprintf(evp_hmac_name, "hmac(%s)", evp_mac_mdname);
2531         names[D_HMAC] = evp_hmac_name;
2532
2533         params[0] =
2534             OSSL_PARAM_construct_utf8_string(OSSL_MAC_PARAM_DIGEST,
2535                                              evp_mac_mdname, 0);
2536         params[1] =
2537             OSSL_PARAM_construct_octet_string(OSSL_MAC_PARAM_KEY,
2538                                               (char *)hmac_key, len);
2539         params[2] = OSSL_PARAM_construct_end();
2540
2541         for (i = 0; i < loopargs_len; i++) {
2542             loopargs[i].mctx = EVP_MAC_CTX_new(mac);
2543             if (loopargs[i].mctx == NULL)
2544                 goto end;
2545
2546             if (!EVP_MAC_CTX_set_params(loopargs[i].mctx, params))
2547                 goto skip_hmac; /* Digest not found */
2548         }
2549         for (testnum = 0; testnum < size_num; testnum++) {
2550             print_message(names[D_HMAC], lengths[testnum], seconds.sym);
2551             Time_F(START);
2552             count = run_benchmark(async_jobs, HMAC_loop, loopargs);
2553             d = Time_F(STOP);
2554             print_result(D_HMAC, testnum, count, d);
2555             if (count < 0)
2556                 break;
2557         }
2558         for (i = 0; i < loopargs_len; i++)
2559             EVP_MAC_CTX_free(loopargs[i].mctx);
2560         EVP_MAC_free(mac);
2561         mac = NULL;
2562     }
2563 skip_hmac:
2564     if (doit[D_CBC_DES]) {
2565         int st = 1;
2566
2567         for (i = 0; st && i < loopargs_len; i++) {
2568             loopargs[i].ctx = init_evp_cipher_ctx("des-cbc", deskey,
2569                                                   sizeof(deskey) / 3);
2570             st = loopargs[i].ctx != NULL;
2571         }
2572         algindex = D_CBC_DES;
2573         for (testnum = 0; st && testnum < size_num; testnum++) {
2574             print_message(names[D_CBC_DES], lengths[testnum], seconds.sym);
2575             Time_F(START);
2576             count = run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2577             d = Time_F(STOP);
2578             print_result(D_CBC_DES, testnum, count, d);
2579         }
2580         for (i = 0; i < loopargs_len; i++)
2581             EVP_CIPHER_CTX_free(loopargs[i].ctx);
2582     }
2583
2584     if (doit[D_EDE3_DES]) {
2585         int st = 1;
2586
2587         for (i = 0; st && i < loopargs_len; i++) {
2588             loopargs[i].ctx = init_evp_cipher_ctx("des-ede3-cbc", deskey,
2589                                                   sizeof(deskey));
2590             st = loopargs[i].ctx != NULL;
2591         }
2592         algindex = D_EDE3_DES;
2593         for (testnum = 0; st && testnum < size_num; testnum++) {
2594             print_message(names[D_EDE3_DES], lengths[testnum], seconds.sym);
2595             Time_F(START);
2596             count =
2597                 run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2598             d = Time_F(STOP);
2599             print_result(D_EDE3_DES, testnum, count, d);
2600         }
2601         for (i = 0; i < loopargs_len; i++)
2602             EVP_CIPHER_CTX_free(loopargs[i].ctx);
2603     }
2604
2605     for (k = 0; k < 3; k++) {
2606         algindex = D_CBC_128_AES + k;
2607         if (doit[algindex]) {
2608             int st = 1;
2609
2610             keylen = 16 + k * 8;
2611             for (i = 0; st && i < loopargs_len; i++) {
2612                 loopargs[i].ctx = init_evp_cipher_ctx(names[algindex],
2613                                                       key32, keylen);
2614                 st = loopargs[i].ctx != NULL;
2615             }
2616
2617             for (testnum = 0; st && testnum < size_num; testnum++) {
2618                 print_message(names[algindex], lengths[testnum], seconds.sym);
2619                 Time_F(START);
2620                 count =
2621                     run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2622                 d = Time_F(STOP);
2623                 print_result(algindex, testnum, count, d);
2624             }
2625             for (i = 0; i < loopargs_len; i++)
2626                 EVP_CIPHER_CTX_free(loopargs[i].ctx);
2627         }
2628     }
2629
2630     for (k = 0; k < 3; k++) {
2631         algindex = D_CBC_128_CML + k;
2632         if (doit[algindex]) {
2633             int st = 1;
2634
2635             keylen = 16 + k * 8;
2636             for (i = 0; st && i < loopargs_len; i++) {
2637                 loopargs[i].ctx = init_evp_cipher_ctx(names[algindex],
2638                                                       key32, keylen);
2639                 st = loopargs[i].ctx != NULL;
2640             }
2641
2642             for (testnum = 0; st && testnum < size_num; testnum++) {
2643                 print_message(names[algindex], lengths[testnum], seconds.sym);
2644                 Time_F(START);
2645                 count =
2646                     run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2647                 d = Time_F(STOP);
2648                 print_result(algindex, testnum, count, d);
2649             }
2650             for (i = 0; i < loopargs_len; i++)
2651                 EVP_CIPHER_CTX_free(loopargs[i].ctx);
2652         }
2653     }
2654
2655     for (algindex = D_RC4; algindex <= D_CBC_CAST; algindex++) {
2656         if (doit[algindex]) {
2657             int st = 1;
2658
2659             keylen = 16;
2660             for (i = 0; st && i < loopargs_len; i++) {
2661                 loopargs[i].ctx = init_evp_cipher_ctx(names[algindex],
2662                                                       key32, keylen);
2663                 st = loopargs[i].ctx != NULL;
2664             }
2665
2666             for (testnum = 0; st && testnum < size_num; testnum++) {
2667                 print_message(names[algindex], lengths[testnum], seconds.sym);
2668                 Time_F(START);
2669                 count =
2670                     run_benchmark(async_jobs, EVP_Cipher_loop, loopargs);
2671                 d = Time_F(STOP);
2672                 print_result(algindex, testnum, count, d);
2673             }
2674             for (i = 0; i < loopargs_len; i++)
2675                 EVP_CIPHER_CTX_free(loopargs[i].ctx);
2676         }
2677     }
2678     if (doit[D_GHASH]) {
2679         static const char gmac_iv[] = "0123456789ab";
2680         OSSL_PARAM params[3];
2681
2682         mac = EVP_MAC_fetch(app_get0_libctx(), "GMAC", app_get0_propq());
2683         if (mac == NULL)
2684             goto end;
2685
2686         params[0] = OSSL_PARAM_construct_utf8_string(OSSL_ALG_PARAM_CIPHER,
2687                                                      "aes-128-gcm", 0);
2688         params[1] = OSSL_PARAM_construct_octet_string(OSSL_MAC_PARAM_IV,
2689                                                       (char *)gmac_iv,
2690                                                       sizeof(gmac_iv) - 1);
2691         params[2] = OSSL_PARAM_construct_end();
2692
2693         for (i = 0; i < loopargs_len; i++) {
2694             loopargs[i].mctx = EVP_MAC_CTX_new(mac);
2695             if (loopargs[i].mctx == NULL)
2696                 goto end;
2697
2698             if (!EVP_MAC_init(loopargs[i].mctx, key32, 16, params))
2699                 goto end;
2700         }
2701         for (testnum = 0; testnum < size_num; testnum++) {
2702             print_message(names[D_GHASH], lengths[testnum], seconds.sym);
2703             Time_F(START);
2704             count = run_benchmark(async_jobs, GHASH_loop, loopargs);
2705             d = Time_F(STOP);
2706             print_result(D_GHASH, testnum, count, d);
2707             if (count < 0)
2708                 break;
2709         }
2710         for (i = 0; i < loopargs_len; i++)
2711             EVP_MAC_CTX_free(loopargs[i].mctx);
2712         EVP_MAC_free(mac);
2713         mac = NULL;
2714     }
2715
2716     if (doit[D_RAND]) {
2717         for (testnum = 0; testnum < size_num; testnum++) {
2718             print_message(names[D_RAND], lengths[testnum], seconds.sym);
2719             Time_F(START);
2720             count = run_benchmark(async_jobs, RAND_bytes_loop, loopargs);
2721             d = Time_F(STOP);
2722             print_result(D_RAND, testnum, count, d);
2723         }
2724     }
2725
2726     if (doit[D_EVP]) {
2727         if (evp_cipher != NULL) {
2728             int (*loopfunc) (void *) = EVP_Update_loop;
2729
2730             if (multiblock && (EVP_CIPHER_get_flags(evp_cipher) &
2731                                EVP_CIPH_FLAG_TLS1_1_MULTIBLOCK)) {
2732                 multiblock_speed(evp_cipher, lengths_single, &seconds);
2733                 ret = 0;
2734                 goto end;
2735             }
2736
2737             names[D_EVP] = EVP_CIPHER_get0_name(evp_cipher);
2738
2739             if (EVP_CIPHER_get_mode(evp_cipher) == EVP_CIPH_CCM_MODE) {
2740                 loopfunc = EVP_Update_loop_ccm;
2741             } else if (aead && (EVP_CIPHER_get_flags(evp_cipher) &
2742                                 EVP_CIPH_FLAG_AEAD_CIPHER)) {
2743                 loopfunc = EVP_Update_loop_aead;
2744                 if (lengths == lengths_list) {
2745                     lengths = aead_lengths_list;
2746                     size_num = OSSL_NELEM(aead_lengths_list);
2747                 }
2748             }
2749
2750             for (testnum = 0; testnum < size_num; testnum++) {
2751                 print_message(names[D_EVP], lengths[testnum], seconds.sym);
2752
2753                 for (k = 0; k < loopargs_len; k++) {
2754                     loopargs[k].ctx = EVP_CIPHER_CTX_new();
2755                     if (loopargs[k].ctx == NULL) {
2756                         BIO_printf(bio_err, "\nEVP_CIPHER_CTX_new failure\n");
2757                         exit(1);
2758                     }
2759                     if (!EVP_CipherInit_ex(loopargs[k].ctx, evp_cipher, NULL,
2760                                            NULL, iv, decrypt ? 0 : 1)) {
2761                         BIO_printf(bio_err, "\nEVP_CipherInit_ex failure\n");
2762                         ERR_print_errors(bio_err);
2763                         exit(1);
2764                     }
2765
2766                     EVP_CIPHER_CTX_set_padding(loopargs[k].ctx, 0);
2767
2768                     keylen = EVP_CIPHER_CTX_get_key_length(loopargs[k].ctx);
2769                     loopargs[k].key = app_malloc(keylen, "evp_cipher key");
2770                     EVP_CIPHER_CTX_rand_key(loopargs[k].ctx, loopargs[k].key);
2771                     if (!EVP_CipherInit_ex(loopargs[k].ctx, NULL, NULL,
2772                                            loopargs[k].key, NULL, -1)) {
2773                         BIO_printf(bio_err, "\nEVP_CipherInit_ex failure\n");
2774                         ERR_print_errors(bio_err);
2775                         exit(1);
2776                     }
2777                     OPENSSL_clear_free(loopargs[k].key, keylen);
2778
2779                     /* GCM-SIV/SIV mode only allows for a single Update operation */
2780                     if (EVP_CIPHER_get_mode(evp_cipher) == EVP_CIPH_SIV_MODE
2781                             || EVP_CIPHER_get_mode(evp_cipher) == EVP_CIPH_GCM_SIV_MODE)
2782                         (void)EVP_CIPHER_CTX_ctrl(loopargs[k].ctx,
2783                                                   EVP_CTRL_SET_SPEED, 1, NULL);
2784                 }
2785
2786                 Time_F(START);
2787                 count = run_benchmark(async_jobs, loopfunc, loopargs);
2788                 d = Time_F(STOP);
2789                 for (k = 0; k < loopargs_len; k++)
2790                     EVP_CIPHER_CTX_free(loopargs[k].ctx);
2791                 print_result(D_EVP, testnum, count, d);
2792             }
2793         } else if (evp_md_name != NULL) {
2794             names[D_EVP] = evp_md_name;
2795
2796             for (testnum = 0; testnum < size_num; testnum++) {
2797                 print_message(names[D_EVP], lengths[testnum], seconds.sym);
2798                 Time_F(START);
2799                 count = run_benchmark(async_jobs, EVP_Digest_md_loop, loopargs);
2800                 d = Time_F(STOP);
2801                 print_result(D_EVP, testnum, count, d);
2802                 if (count < 0)
2803                     break;
2804             }
2805         }
2806     }
2807
2808     if (doit[D_EVP_CMAC]) {
2809         OSSL_PARAM params[3];
2810         EVP_CIPHER *cipher = NULL;
2811
2812         mac = EVP_MAC_fetch(app_get0_libctx(), "CMAC", app_get0_propq());
2813         if (mac == NULL || evp_mac_ciphername == NULL)
2814             goto end;
2815         if (!opt_cipher(evp_mac_ciphername, &cipher))
2816             goto end;
2817
2818         keylen = EVP_CIPHER_get_key_length(cipher);
2819         EVP_CIPHER_free(cipher);
2820         if (keylen <= 0 || keylen > (int)sizeof(key32)) {
2821             BIO_printf(bio_err, "\nRequested CMAC cipher with unsupported key length.\n");
2822             goto end;
2823         }
2824         evp_cmac_name = app_malloc(sizeof("cmac()")
2825                                    + strlen(evp_mac_ciphername), "CMAC name");
2826         sprintf(evp_cmac_name, "cmac(%s)", evp_mac_ciphername);
2827         names[D_EVP_CMAC] = evp_cmac_name;
2828
2829         params[0] = OSSL_PARAM_construct_utf8_string(OSSL_ALG_PARAM_CIPHER,
2830                                                      evp_mac_ciphername, 0);
2831         params[1] = OSSL_PARAM_construct_octet_string(OSSL_MAC_PARAM_KEY,
2832                                                       (char *)key32, keylen);
2833         params[2] = OSSL_PARAM_construct_end();
2834
2835         for (i = 0; i < loopargs_len; i++) {
2836             loopargs[i].mctx = EVP_MAC_CTX_new(mac);
2837             if (loopargs[i].mctx == NULL)
2838                 goto end;
2839
2840             if (!EVP_MAC_CTX_set_params(loopargs[i].mctx, params))
2841                 goto end;
2842         }
2843
2844         for (testnum = 0; testnum < size_num; testnum++) {
2845             print_message(names[D_EVP_CMAC], lengths[testnum], seconds.sym);
2846             Time_F(START);
2847             count = run_benchmark(async_jobs, CMAC_loop, loopargs);
2848             d = Time_F(STOP);
2849             print_result(D_EVP_CMAC, testnum, count, d);
2850             if (count < 0)
2851                 break;
2852         }
2853         for (i = 0; i < loopargs_len; i++)
2854             EVP_MAC_CTX_free(loopargs[i].mctx);
2855         EVP_MAC_free(mac);
2856         mac = NULL;
2857     }
2858
2859     for (i = 0; i < loopargs_len; i++)
2860         if (RAND_bytes(loopargs[i].buf, 36) <= 0)
2861             goto end;
2862
2863     for (testnum = 0; testnum < RSA_NUM; testnum++) {
2864         EVP_PKEY *rsa_key = NULL;
2865         int st = 0;
2866
2867         if (!rsa_doit[testnum])
2868             continue;
2869
2870         if (primes > RSA_DEFAULT_PRIME_NUM) {
2871             /* we haven't set keys yet,  generate multi-prime RSA keys */
2872             bn = BN_new();
2873             st = bn != NULL
2874                 && BN_set_word(bn, RSA_F4)
2875                 && init_gen_str(&genctx, "RSA", NULL, 0, NULL, NULL)
2876                 && EVP_PKEY_CTX_set_rsa_keygen_bits(genctx, rsa_keys[testnum].bits) > 0
2877                 && EVP_PKEY_CTX_set1_rsa_keygen_pubexp(genctx, bn) > 0
2878                 && EVP_PKEY_CTX_set_rsa_keygen_primes(genctx, primes) > 0
2879                 && EVP_PKEY_keygen(genctx, &rsa_key);
2880             BN_free(bn);
2881             bn = NULL;
2882             EVP_PKEY_CTX_free(genctx);
2883             genctx = NULL;
2884         } else {
2885             const unsigned char *p = rsa_keys[testnum].data;
2886
2887             st = (rsa_key = d2i_PrivateKey(EVP_PKEY_RSA, NULL, &p,
2888                                            rsa_keys[testnum].length)) != NULL;
2889         }
2890
2891         for (i = 0; st && i < loopargs_len; i++) {
2892             loopargs[i].rsa_sign_ctx[testnum] = EVP_PKEY_CTX_new(rsa_key, NULL);
2893             loopargs[i].sigsize = loopargs[i].buflen;
2894             if (loopargs[i].rsa_sign_ctx[testnum] == NULL
2895                 || EVP_PKEY_sign_init(loopargs[i].rsa_sign_ctx[testnum]) <= 0
2896                 || EVP_PKEY_sign(loopargs[i].rsa_sign_ctx[testnum],
2897                                  loopargs[i].buf2,
2898                                  &loopargs[i].sigsize,
2899                                  loopargs[i].buf, 36) <= 0)
2900                 st = 0;
2901         }
2902         if (!st) {
2903             BIO_printf(bio_err,
2904                        "RSA sign setup failure.  No RSA sign will be done.\n");
2905             ERR_print_errors(bio_err);
2906             op_count = 1;
2907         } else {
2908             pkey_print_message("private", "rsa sign",
2909                                rsa_keys[testnum].bits, seconds.rsa);
2910             /* RSA_blinding_on(rsa_key[testnum],NULL); */
2911             Time_F(START);
2912             count = run_benchmark(async_jobs, RSA_sign_loop, loopargs);
2913             d = Time_F(STOP);
2914             BIO_printf(bio_err,
2915                        mr ? "+R1:%ld:%d:%.2f\n"
2916                        : "%ld %u bits private RSA sign ops in %.2fs\n",
2917                        count, rsa_keys[testnum].bits, d);
2918             rsa_results[testnum][0] = (double)count / d;
2919             op_count = count;
2920         }
2921
2922         for (i = 0; st && i < loopargs_len; i++) {
2923             loopargs[i].rsa_verify_ctx[testnum] = EVP_PKEY_CTX_new(rsa_key,
2924                                                                    NULL);
2925             if (loopargs[i].rsa_verify_ctx[testnum] == NULL
2926                 || EVP_PKEY_verify_init(loopargs[i].rsa_verify_ctx[testnum]) <= 0
2927                 || EVP_PKEY_verify(loopargs[i].rsa_verify_ctx[testnum],
2928                                    loopargs[i].buf2,
2929                                    loopargs[i].sigsize,
2930                                    loopargs[i].buf, 36) <= 0)
2931                 st = 0;
2932         }
2933         if (!st) {
2934             BIO_printf(bio_err,
2935                        "RSA verify setup failure.  No RSA verify will be done.\n");
2936             ERR_print_errors(bio_err);
2937             rsa_doit[testnum] = 0;
2938         } else {
2939             pkey_print_message("public", "rsa verify",
2940                                rsa_keys[testnum].bits, seconds.rsa);
2941             Time_F(START);
2942             count = run_benchmark(async_jobs, RSA_verify_loop, loopargs);
2943             d = Time_F(STOP);
2944             BIO_printf(bio_err,
2945                        mr ? "+R2:%ld:%d:%.2f\n"
2946                        : "%ld %u bits public RSA verify ops in %.2fs\n",
2947                        count, rsa_keys[testnum].bits, d);
2948             rsa_results[testnum][1] = (double)count / d;
2949         }
2950
2951         for (i = 0; st && i < loopargs_len; i++) {
2952             loopargs[i].rsa_encrypt_ctx[testnum] = EVP_PKEY_CTX_new(rsa_key, NULL);
2953             loopargs[i].encsize = loopargs[i].buflen;
2954             if (loopargs[i].rsa_encrypt_ctx[testnum] == NULL
2955                 || EVP_PKEY_encrypt_init(loopargs[i].rsa_encrypt_ctx[testnum]) <= 0
2956                 || EVP_PKEY_encrypt(loopargs[i].rsa_encrypt_ctx[testnum],
2957                                     loopargs[i].buf2,
2958                                     &loopargs[i].encsize,
2959                                     loopargs[i].buf, 36) <= 0)
2960                 st = 0;
2961         }
2962         if (!st) {
2963             BIO_printf(bio_err,
2964                        "RSA encrypt setup failure.  No RSA encrypt will be done.\n");
2965             ERR_print_errors(bio_err);
2966             op_count = 1;
2967         } else {
2968             pkey_print_message("private", "rsa encrypt",
2969                                rsa_keys[testnum].bits, seconds.rsa);
2970             /* RSA_blinding_on(rsa_key[testnum],NULL); */
2971             Time_F(START);
2972             count = run_benchmark(async_jobs, RSA_encrypt_loop, loopargs);
2973             d = Time_F(STOP);
2974             BIO_printf(bio_err,
2975                        mr ? "+R3:%ld:%d:%.2f\n"
2976                        : "%ld %u bits public RSA encrypt ops in %.2fs\n",
2977                        count, rsa_keys[testnum].bits, d);
2978             rsa_results[testnum][2] = (double)count / d;
2979             op_count = count;
2980         }
2981
2982         for (i = 0; st && i < loopargs_len; i++) {
2983             loopargs[i].rsa_decrypt_ctx[testnum] = EVP_PKEY_CTX_new(rsa_key, NULL);
2984             declen = loopargs[i].buflen;
2985             if (loopargs[i].rsa_decrypt_ctx[testnum] == NULL
2986                 || EVP_PKEY_decrypt_init(loopargs[i].rsa_decrypt_ctx[testnum]) <= 0
2987                 || EVP_PKEY_decrypt(loopargs[i].rsa_decrypt_ctx[testnum],
2988                                     loopargs[i].buf,
2989                                     &declen,
2990                                     loopargs[i].buf2,
2991                                     loopargs[i].encsize) <= 0)
2992                 st = 0;
2993         }
2994         if (!st) {
2995             BIO_printf(bio_err,
2996                        "RSA decrypt setup failure.  No RSA decrypt will be done.\n");
2997             ERR_print_errors(bio_err);
2998             op_count = 1;
2999         } else {
3000             pkey_print_message("private", "rsa decrypt",
3001                                rsa_keys[testnum].bits, seconds.rsa);
3002             /* RSA_blinding_on(rsa_key[testnum],NULL); */
3003             Time_F(START);
3004             count = run_benchmark(async_jobs, RSA_decrypt_loop, loopargs);
3005             d = Time_F(STOP);
3006             BIO_printf(bio_err,
3007                        mr ? "+R4:%ld:%d:%.2f\n"
3008                        : "%ld %u bits private RSA decrypt ops in %.2fs\n",
3009                        count, rsa_keys[testnum].bits, d);
3010             rsa_results[testnum][3] = (double)count / d;
3011             op_count = count;
3012         }
3013
3014         if (op_count <= 1) {
3015             /* if longer than 10s, don't do any more */
3016             stop_it(rsa_doit, testnum);
3017         }
3018         EVP_PKEY_free(rsa_key);
3019     }
3020
3021     for (testnum = 0; testnum < DSA_NUM; testnum++) {
3022         EVP_PKEY *dsa_key = NULL;
3023         int st;
3024
3025         if (!dsa_doit[testnum])
3026             continue;
3027
3028         st = (dsa_key = get_dsa(dsa_bits[testnum])) != NULL;
3029
3030         for (i = 0; st && i < loopargs_len; i++) {
3031             loopargs[i].dsa_sign_ctx[testnum] = EVP_PKEY_CTX_new(dsa_key,
3032                                                                  NULL);
3033             loopargs[i].sigsize = loopargs[i].buflen;
3034             if (loopargs[i].dsa_sign_ctx[testnum] == NULL
3035                 || EVP_PKEY_sign_init(loopargs[i].dsa_sign_ctx[testnum]) <= 0
3036
3037                 || EVP_PKEY_sign(loopargs[i].dsa_sign_ctx[testnum],
3038                                  loopargs[i].buf2,
3039                                  &loopargs[i].sigsize,
3040                                  loopargs[i].buf, 20) <= 0)
3041                 st = 0;
3042         }
3043         if (!st) {
3044             BIO_printf(bio_err,
3045                        "DSA sign setup failure.  No DSA sign will be done.\n");
3046             ERR_print_errors(bio_err);
3047             op_count = 1;
3048         } else {
3049             pkey_print_message("sign", "dsa",
3050                                dsa_bits[testnum], seconds.dsa);
3051             Time_F(START);
3052             count = run_benchmark(async_jobs, DSA_sign_loop, loopargs);
3053             d = Time_F(STOP);
3054             BIO_printf(bio_err,
3055                        mr ? "+R5:%ld:%u:%.2f\n"
3056                        : "%ld %u bits DSA sign ops in %.2fs\n",
3057                        count, dsa_bits[testnum], d);
3058             dsa_results[testnum][0] = (double)count / d;
3059             op_count = count;
3060         }
3061
3062         for (i = 0; st && i < loopargs_len; i++) {
3063             loopargs[i].dsa_verify_ctx[testnum] = EVP_PKEY_CTX_new(dsa_key,
3064                                                                    NULL);
3065             if (loopargs[i].dsa_verify_ctx[testnum] == NULL
3066                 || EVP_PKEY_verify_init(loopargs[i].dsa_verify_ctx[testnum]) <= 0
3067                 || EVP_PKEY_verify(loopargs[i].dsa_verify_ctx[testnum],
3068                                    loopargs[i].buf2,
3069                                    loopargs[i].sigsize,
3070                                    loopargs[i].buf, 36) <= 0)
3071                 st = 0;
3072         }
3073         if (!st) {
3074             BIO_printf(bio_err,
3075                        "DSA verify setup failure.  No DSA verify will be done.\n");
3076             ERR_print_errors(bio_err);
3077             dsa_doit[testnum] = 0;
3078         } else {
3079             pkey_print_message("verify", "dsa",
3080                                dsa_bits[testnum], seconds.dsa);
3081             Time_F(START);
3082             count = run_benchmark(async_jobs, DSA_verify_loop, loopargs);
3083             d = Time_F(STOP);
3084             BIO_printf(bio_err,
3085                        mr ? "+R6:%ld:%u:%.2f\n"
3086                        : "%ld %u bits DSA verify ops in %.2fs\n",
3087                        count, dsa_bits[testnum], d);
3088             dsa_results[testnum][1] = (double)count / d;
3089         }
3090
3091         if (op_count <= 1) {
3092             /* if longer than 10s, don't do any more */
3093             stop_it(dsa_doit, testnum);
3094         }
3095         EVP_PKEY_free(dsa_key);
3096     }
3097
3098     for (testnum = 0; testnum < ECDSA_NUM; testnum++) {
3099         EVP_PKEY *ecdsa_key = NULL;
3100         int st;
3101
3102         if (!ecdsa_doit[testnum])
3103             continue;
3104
3105         st = (ecdsa_key = get_ecdsa(&ec_curves[testnum])) != NULL;
3106
3107         for (i = 0; st && i < loopargs_len; i++) {
3108             loopargs[i].ecdsa_sign_ctx[testnum] = EVP_PKEY_CTX_new(ecdsa_key,
3109                                                                    NULL);
3110             loopargs[i].sigsize = loopargs[i].buflen;
3111             if (loopargs[i].ecdsa_sign_ctx[testnum] == NULL
3112                 || EVP_PKEY_sign_init(loopargs[i].ecdsa_sign_ctx[testnum]) <= 0
3113
3114                 || EVP_PKEY_sign(loopargs[i].ecdsa_sign_ctx[testnum],
3115                                  loopargs[i].buf2,
3116                                  &loopargs[i].sigsize,
3117                                  loopargs[i].buf, 20) <= 0)
3118                 st = 0;
3119         }
3120         if (!st) {
3121             BIO_printf(bio_err,
3122                        "ECDSA sign setup failure.  No ECDSA sign will be done.\n");
3123             ERR_print_errors(bio_err);
3124             op_count = 1;
3125         } else {
3126             pkey_print_message("sign", "ecdsa",
3127                                ec_curves[testnum].bits, seconds.ecdsa);
3128             Time_F(START);
3129             count = run_benchmark(async_jobs, ECDSA_sign_loop, loopargs);
3130             d = Time_F(STOP);
3131             BIO_printf(bio_err,
3132                        mr ? "+R7:%ld:%u:%.2f\n"
3133                        : "%ld %u bits ECDSA sign ops in %.2fs\n",
3134                        count, ec_curves[testnum].bits, d);
3135             ecdsa_results[testnum][0] = (double)count / d;
3136             op_count = count;
3137         }
3138
3139         for (i = 0; st && i < loopargs_len; i++) {
3140             loopargs[i].ecdsa_verify_ctx[testnum] = EVP_PKEY_CTX_new(ecdsa_key,
3141                                                                      NULL);
3142             if (loopargs[i].ecdsa_verify_ctx[testnum] == NULL
3143                 || EVP_PKEY_verify_init(loopargs[i].ecdsa_verify_ctx[testnum]) <= 0
3144                 || EVP_PKEY_verify(loopargs[i].ecdsa_verify_ctx[testnum],
3145                                    loopargs[i].buf2,
3146                                    loopargs[i].sigsize,
3147                                    loopargs[i].buf, 20) <= 0)
3148                 st = 0;
3149         }
3150         if (!st) {
3151             BIO_printf(bio_err,
3152                        "ECDSA verify setup failure.  No ECDSA verify will be done.\n");
3153             ERR_print_errors(bio_err);
3154             ecdsa_doit[testnum] = 0;
3155         } else {
3156             pkey_print_message("verify", "ecdsa",
3157                                ec_curves[testnum].bits, seconds.ecdsa);
3158             Time_F(START);
3159             count = run_benchmark(async_jobs, ECDSA_verify_loop, loopargs);
3160             d = Time_F(STOP);
3161             BIO_printf(bio_err,
3162                        mr ? "+R8:%ld:%u:%.2f\n"
3163                        : "%ld %u bits ECDSA verify ops in %.2fs\n",
3164                        count, ec_curves[testnum].bits, d);
3165             ecdsa_results[testnum][1] = (double)count / d;
3166         }
3167
3168         if (op_count <= 1) {
3169             /* if longer than 10s, don't do any more */
3170             stop_it(ecdsa_doit, testnum);
3171         }
3172     }
3173
3174     for (testnum = 0; testnum < EC_NUM; testnum++) {
3175         int ecdh_checks = 1;
3176
3177         if (!ecdh_doit[testnum])
3178             continue;
3179
3180         for (i = 0; i < loopargs_len; i++) {
3181             EVP_PKEY_CTX *test_ctx = NULL;
3182             EVP_PKEY_CTX *ctx = NULL;
3183             EVP_PKEY *key_A = NULL;
3184             EVP_PKEY *key_B = NULL;
3185             size_t outlen;
3186             size_t test_outlen;
3187
3188             if ((key_A = get_ecdsa(&ec_curves[testnum])) == NULL /* generate secret key A */
3189                 || (key_B = get_ecdsa(&ec_curves[testnum])) == NULL /* generate secret key B */
3190                 || (ctx = EVP_PKEY_CTX_new(key_A, NULL)) == NULL /* derivation ctx from skeyA */
3191                 || EVP_PKEY_derive_init(ctx) <= 0 /* init derivation ctx */
3192                 || EVP_PKEY_derive_set_peer(ctx, key_B) <= 0 /* set peer pubkey in ctx */
3193                 || EVP_PKEY_derive(ctx, NULL, &outlen) <= 0 /* determine max length */
3194                 || outlen == 0 /* ensure outlen is a valid size */
3195                 || outlen > MAX_ECDH_SIZE /* avoid buffer overflow */) {
3196                 ecdh_checks = 0;
3197                 BIO_printf(bio_err, "ECDH key generation failure.\n");
3198                 ERR_print_errors(bio_err);
3199                 op_count = 1;
3200                 break;
3201             }
3202
3203             /*
3204              * Here we perform a test run, comparing the output of a*B and b*A;
3205              * we try this here and assume that further EVP_PKEY_derive calls
3206              * never fail, so we can skip checks in the actually benchmarked
3207              * code, for maximum performance.
3208              */
3209             if ((test_ctx = EVP_PKEY_CTX_new(key_B, NULL)) == NULL /* test ctx from skeyB */
3210                 || EVP_PKEY_derive_init(test_ctx) <= 0 /* init derivation test_ctx */
3211                 || EVP_PKEY_derive_set_peer(test_ctx, key_A) <= 0 /* set peer pubkey in test_ctx */
3212                 || EVP_PKEY_derive(test_ctx, NULL, &test_outlen) <= 0 /* determine max length */
3213                 || EVP_PKEY_derive(ctx, loopargs[i].secret_a, &outlen) <= 0 /* compute a*B */
3214                 || EVP_PKEY_derive(test_ctx, loopargs[i].secret_b, &test_outlen) <= 0 /* compute b*A */
3215                 || test_outlen != outlen /* compare output length */) {
3216                 ecdh_checks = 0;
3217                 BIO_printf(bio_err, "ECDH computation failure.\n");
3218                 ERR_print_errors(bio_err);
3219                 op_count = 1;
3220                 break;
3221             }
3222
3223             /* Compare the computation results: CRYPTO_memcmp() returns 0 if equal */
3224             if (CRYPTO_memcmp(loopargs[i].secret_a,
3225                               loopargs[i].secret_b, outlen)) {
3226                 ecdh_checks = 0;
3227                 BIO_printf(bio_err, "ECDH computations don't match.\n");
3228                 ERR_print_errors(bio_err);
3229                 op_count = 1;
3230                 break;
3231             }
3232
3233             loopargs[i].ecdh_ctx[testnum] = ctx;
3234             loopargs[i].outlen[testnum] = outlen;
3235
3236             EVP_PKEY_free(key_A);
3237             EVP_PKEY_free(key_B);
3238             EVP_PKEY_CTX_free(test_ctx);
3239             test_ctx = NULL;
3240         }
3241         if (ecdh_checks != 0) {
3242             pkey_print_message("", "ecdh",
3243                                ec_curves[testnum].bits, seconds.ecdh);
3244             Time_F(START);
3245             count =
3246                 run_benchmark(async_jobs, ECDH_EVP_derive_key_loop, loopargs);
3247             d = Time_F(STOP);
3248             BIO_printf(bio_err,
3249                        mr ? "+R9:%ld:%d:%.2f\n" :
3250                        "%ld %u-bits ECDH ops in %.2fs\n", count,
3251                        ec_curves[testnum].bits, d);
3252             ecdh_results[testnum][0] = (double)count / d;
3253             op_count = count;
3254         }
3255
3256         if (op_count <= 1) {
3257             /* if longer than 10s, don't do any more */
3258             stop_it(ecdh_doit, testnum);
3259         }
3260     }
3261
3262 #ifndef OPENSSL_NO_ECX
3263     for (testnum = 0; testnum < EdDSA_NUM; testnum++) {
3264         int st = 1;
3265         EVP_PKEY *ed_pkey = NULL;
3266         EVP_PKEY_CTX *ed_pctx = NULL;
3267
3268         if (!eddsa_doit[testnum])
3269             continue;           /* Ignore Curve */
3270         for (i = 0; i < loopargs_len; i++) {
3271             loopargs[i].eddsa_ctx[testnum] = EVP_MD_CTX_new();
3272             if (loopargs[i].eddsa_ctx[testnum] == NULL) {
3273                 st = 0;
3274                 break;
3275             }
3276             loopargs[i].eddsa_ctx2[testnum] = EVP_MD_CTX_new();
3277             if (loopargs[i].eddsa_ctx2[testnum] == NULL) {
3278                 st = 0;
3279                 break;
3280             }
3281
3282             if ((ed_pctx = EVP_PKEY_CTX_new_id(ed_curves[testnum].nid,
3283                                                NULL)) == NULL
3284                 || EVP_PKEY_keygen_init(ed_pctx) <= 0
3285                 || EVP_PKEY_keygen(ed_pctx, &ed_pkey) <= 0) {
3286                 st = 0;
3287                 EVP_PKEY_CTX_free(ed_pctx);
3288                 break;
3289             }
3290             EVP_PKEY_CTX_free(ed_pctx);
3291
3292             if (!EVP_DigestSignInit(loopargs[i].eddsa_ctx[testnum], NULL, NULL,
3293                                     NULL, ed_pkey)) {
3294                 st = 0;
3295                 EVP_PKEY_free(ed_pkey);
3296                 break;
3297             }
3298             if (!EVP_DigestVerifyInit(loopargs[i].eddsa_ctx2[testnum], NULL,
3299                                       NULL, NULL, ed_pkey)) {
3300                 st = 0;
3301                 EVP_PKEY_free(ed_pkey);
3302                 break;
3303             }
3304
3305             EVP_PKEY_free(ed_pkey);
3306             ed_pkey = NULL;
3307         }
3308         if (st == 0) {
3309             BIO_printf(bio_err, "EdDSA failure.\n");
3310             ERR_print_errors(bio_err);
3311             op_count = 1;
3312         } else {
3313             for (i = 0; i < loopargs_len; i++) {
3314                 /* Perform EdDSA signature test */
3315                 loopargs[i].sigsize = ed_curves[testnum].sigsize;
3316                 st = EVP_DigestSign(loopargs[i].eddsa_ctx[testnum],
3317                                     loopargs[i].buf2, &loopargs[i].sigsize,
3318                                     loopargs[i].buf, 20);
3319                 if (st == 0)
3320                     break;
3321             }
3322             if (st == 0) {
3323                 BIO_printf(bio_err,
3324                            "EdDSA sign failure.  No EdDSA sign will be done.\n");
3325                 ERR_print_errors(bio_err);
3326                 op_count = 1;
3327             } else {
3328                 pkey_print_message("sign", ed_curves[testnum].name,
3329                                    ed_curves[testnum].bits, seconds.eddsa);
3330                 Time_F(START);
3331                 count = run_benchmark(async_jobs, EdDSA_sign_loop, loopargs);
3332                 d = Time_F(STOP);
3333
3334                 BIO_printf(bio_err,
3335                            mr ? "+R10:%ld:%u:%s:%.2f\n" :
3336                            "%ld %u bits %s sign ops in %.2fs \n",
3337                            count, ed_curves[testnum].bits,
3338                            ed_curves[testnum].name, d);
3339                 eddsa_results[testnum][0] = (double)count / d;
3340                 op_count = count;
3341             }
3342             /* Perform EdDSA verification test */
3343             for (i = 0; i < loopargs_len; i++) {
3344                 st = EVP_DigestVerify(loopargs[i].eddsa_ctx2[testnum],
3345                                       loopargs[i].buf2, loopargs[i].sigsize,
3346                                       loopargs[i].buf, 20);
3347                 if (st != 1)
3348                     break;
3349             }
3350             if (st != 1) {
3351                 BIO_printf(bio_err,
3352                            "EdDSA verify failure.  No EdDSA verify will be done.\n");
3353                 ERR_print_errors(bio_err);
3354                 eddsa_doit[testnum] = 0;
3355             } else {
3356                 pkey_print_message("verify", ed_curves[testnum].name,
3357                                    ed_curves[testnum].bits, seconds.eddsa);
3358                 Time_F(START);
3359                 count = run_benchmark(async_jobs, EdDSA_verify_loop, loopargs);
3360                 d = Time_F(STOP);
3361                 BIO_printf(bio_err,
3362                            mr ? "+R11:%ld:%u:%s:%.2f\n"
3363                            : "%ld %u bits %s verify ops in %.2fs\n",
3364                            count, ed_curves[testnum].bits,
3365                            ed_curves[testnum].name, d);
3366                 eddsa_results[testnum][1] = (double)count / d;
3367             }
3368
3369             if (op_count <= 1) {
3370                 /* if longer than 10s, don't do any more */
3371                 stop_it(eddsa_doit, testnum);
3372             }
3373         }
3374     }
3375 #endif /* OPENSSL_NO_ECX */
3376
3377 #ifndef OPENSSL_NO_SM2
3378     for (testnum = 0; testnum < SM2_NUM; testnum++) {
3379         int st = 1;
3380         EVP_PKEY *sm2_pkey = NULL;
3381
3382         if (!sm2_doit[testnum])
3383             continue;           /* Ignore Curve */
3384         /* Init signing and verification */
3385         for (i = 0; i < loopargs_len; i++) {
3386             EVP_PKEY_CTX *sm2_pctx = NULL;
3387             EVP_PKEY_CTX *sm2_vfy_pctx = NULL;
3388             EVP_PKEY_CTX *pctx = NULL;
3389             st = 0;
3390
3391             loopargs[i].sm2_ctx[testnum] = EVP_MD_CTX_new();
3392             loopargs[i].sm2_vfy_ctx[testnum] = EVP_MD_CTX_new();
3393             if (loopargs[i].sm2_ctx[testnum] == NULL
3394                     || loopargs[i].sm2_vfy_ctx[testnum] == NULL)
3395                 break;
3396
3397             sm2_pkey = NULL;
3398
3399             st = !((pctx = EVP_PKEY_CTX_new_id(EVP_PKEY_SM2, NULL)) == NULL
3400                 || EVP_PKEY_keygen_init(pctx) <= 0
3401                 || EVP_PKEY_CTX_set_ec_paramgen_curve_nid(pctx,
3402                     sm2_curves[testnum].nid) <= 0
3403                 || EVP_PKEY_keygen(pctx, &sm2_pkey) <= 0);
3404             EVP_PKEY_CTX_free(pctx);
3405             if (st == 0)
3406                 break;
3407
3408             st = 0; /* set back to zero */
3409             /* attach it sooner to rely on main final cleanup */
3410             loopargs[i].sm2_pkey[testnum] = sm2_pkey;
3411             loopargs[i].sigsize = EVP_PKEY_get_size(sm2_pkey);
3412
3413             sm2_pctx = EVP_PKEY_CTX_new(sm2_pkey, NULL);
3414             sm2_vfy_pctx = EVP_PKEY_CTX_new(sm2_pkey, NULL);
3415             if (sm2_pctx == NULL || sm2_vfy_pctx == NULL) {
3416                 EVP_PKEY_CTX_free(sm2_vfy_pctx);
3417                 break;
3418             }
3419
3420             /* attach them directly to respective ctx */
3421             EVP_MD_CTX_set_pkey_ctx(loopargs[i].sm2_ctx[testnum], sm2_pctx);
3422             EVP_MD_CTX_set_pkey_ctx(loopargs[i].sm2_vfy_ctx[testnum], sm2_vfy_pctx);
3423
3424             /*
3425              * No need to allow user to set an explicit ID here, just use
3426              * the one defined in the 'draft-yang-tls-tl13-sm-suites' I-D.
3427              */
3428             if (EVP_PKEY_CTX_set1_id(sm2_pctx, SM2_ID, SM2_ID_LEN) != 1
3429                 || EVP_PKEY_CTX_set1_id(sm2_vfy_pctx, SM2_ID, SM2_ID_LEN) != 1)
3430                 break;
3431
3432             if (!EVP_DigestSignInit(loopargs[i].sm2_ctx[testnum], NULL,
3433                                     EVP_sm3(), NULL, sm2_pkey))
3434                 break;
3435             if (!EVP_DigestVerifyInit(loopargs[i].sm2_vfy_ctx[testnum], NULL,
3436                                       EVP_sm3(), NULL, sm2_pkey))
3437                 break;
3438             st = 1;         /* mark loop as succeeded */
3439         }
3440         if (st == 0) {
3441             BIO_printf(bio_err, "SM2 init failure.\n");
3442             ERR_print_errors(bio_err);
3443             op_count = 1;
3444         } else {
3445             for (i = 0; i < loopargs_len; i++) {
3446                 /* Perform SM2 signature test */
3447                 st = EVP_DigestSign(loopargs[i].sm2_ctx[testnum],
3448                                     loopargs[i].buf2, &loopargs[i].sigsize,
3449                                     loopargs[i].buf, 20);
3450                 if (st == 0)
3451                     break;
3452             }
3453             if (st == 0) {
3454                 BIO_printf(bio_err,
3455                            "SM2 sign failure.  No SM2 sign will be done.\n");
3456                 ERR_print_errors(bio_err);
3457                 op_count = 1;
3458             } else {
3459                 pkey_print_message("sign", sm2_curves[testnum].name,
3460                                    sm2_curves[testnum].bits, seconds.sm2);
3461                 Time_F(START);
3462                 count = run_benchmark(async_jobs, SM2_sign_loop, loopargs);
3463                 d = Time_F(STOP);
3464
3465                 BIO_printf(bio_err,
3466                            mr ? "+R12:%ld:%u:%s:%.2f\n" :
3467                            "%ld %u bits %s sign ops in %.2fs \n",
3468                            count, sm2_curves[testnum].bits,
3469                            sm2_curves[testnum].name, d);
3470                 sm2_results[testnum][0] = (double)count / d;
3471                 op_count = count;
3472             }
3473
3474             /* Perform SM2 verification test */
3475             for (i = 0; i < loopargs_len; i++) {
3476                 st = EVP_DigestVerify(loopargs[i].sm2_vfy_ctx[testnum],
3477                                       loopargs[i].buf2, loopargs[i].sigsize,
3478                                       loopargs[i].buf, 20);
3479                 if (st != 1)
3480                     break;
3481             }
3482             if (st != 1) {
3483                 BIO_printf(bio_err,
3484                            "SM2 verify failure.  No SM2 verify will be done.\n");
3485                 ERR_print_errors(bio_err);
3486                 sm2_doit[testnum] = 0;
3487             } else {
3488                 pkey_print_message("verify", sm2_curves[testnum].name,
3489                                    sm2_curves[testnum].bits, seconds.sm2);
3490                 Time_F(START);
3491                 count = run_benchmark(async_jobs, SM2_verify_loop, loopargs);
3492                 d = Time_F(STOP);
3493                 BIO_printf(bio_err,
3494                            mr ? "+R13:%ld:%u:%s:%.2f\n"
3495                            : "%ld %u bits %s verify ops in %.2fs\n",
3496                            count, sm2_curves[testnum].bits,
3497                            sm2_curves[testnum].name, d);
3498                 sm2_results[testnum][1] = (double)count / d;
3499             }
3500
3501             if (op_count <= 1) {
3502                 /* if longer than 10s, don't do any more */
3503                 for (testnum++; testnum < SM2_NUM; testnum++)
3504                     sm2_doit[testnum] = 0;
3505             }
3506         }
3507     }
3508 #endif                         /* OPENSSL_NO_SM2 */
3509
3510 #ifndef OPENSSL_NO_DH
3511     for (testnum = 0; testnum < FFDH_NUM; testnum++) {
3512         int ffdh_checks = 1;
3513
3514         if (!ffdh_doit[testnum])
3515             continue;
3516
3517         for (i = 0; i < loopargs_len; i++) {
3518             EVP_PKEY *pkey_A = NULL;
3519             EVP_PKEY *pkey_B = NULL;
3520             EVP_PKEY_CTX *ffdh_ctx = NULL;
3521             EVP_PKEY_CTX *test_ctx = NULL;
3522             size_t secret_size;
3523             size_t test_out;
3524
3525             /* Ensure that the error queue is empty */
3526             if (ERR_peek_error()) {
3527                 BIO_printf(bio_err,
3528                            "WARNING: the error queue contains previous unhandled errors.\n");
3529                 ERR_print_errors(bio_err);
3530             }
3531
3532             pkey_A = EVP_PKEY_new();
3533             if (!pkey_A) {
3534                 BIO_printf(bio_err, "Error while initialising EVP_PKEY (out of memory?).\n");
3535                 ERR_print_errors(bio_err);
3536                 op_count = 1;
3537                 ffdh_checks = 0;
3538                 break;
3539             }
3540             pkey_B = EVP_PKEY_new();
3541             if (!pkey_B) {
3542                 BIO_printf(bio_err, "Error while initialising EVP_PKEY (out of memory?).\n");
3543                 ERR_print_errors(bio_err);
3544                 op_count = 1;
3545                 ffdh_checks = 0;
3546                 break;
3547             }
3548
3549             ffdh_ctx = EVP_PKEY_CTX_new_id(EVP_PKEY_DH, NULL);
3550             if (!ffdh_ctx) {
3551                 BIO_printf(bio_err, "Error while allocating EVP_PKEY_CTX.\n");
3552                 ERR_print_errors(bio_err);
3553                 op_count = 1;
3554                 ffdh_checks = 0;
3555                 break;
3556             }
3557
3558             if (EVP_PKEY_keygen_init(ffdh_ctx) <= 0) {
3559                 BIO_printf(bio_err, "Error while initialising EVP_PKEY_CTX.\n");
3560                 ERR_print_errors(bio_err);
3561                 op_count = 1;
3562                 ffdh_checks = 0;
3563                 break;
3564             }
3565             if (EVP_PKEY_CTX_set_dh_nid(ffdh_ctx, ffdh_params[testnum].nid) <= 0) {
3566                 BIO_printf(bio_err, "Error setting DH key size for keygen.\n");
3567                 ERR_print_errors(bio_err);
3568                 op_count = 1;
3569                 ffdh_checks = 0;
3570                 break;
3571             }
3572
3573             if (EVP_PKEY_keygen(ffdh_ctx, &pkey_A) <= 0 ||
3574                 EVP_PKEY_keygen(ffdh_ctx, &pkey_B) <= 0) {
3575                 BIO_printf(bio_err, "FFDH key generation failure.\n");
3576                 ERR_print_errors(bio_err);
3577                 op_count = 1;
3578                 ffdh_checks = 0;
3579                 break;
3580             }
3581
3582             EVP_PKEY_CTX_free(ffdh_ctx);
3583
3584             /*
3585              * check if the derivation works correctly both ways so that
3586              * we know if future derive calls will fail, and we can skip
3587              * error checking in benchmarked code
3588              */
3589             ffdh_ctx = EVP_PKEY_CTX_new(pkey_A, NULL);
3590             if (ffdh_ctx == NULL) {
3591                 BIO_printf(bio_err, "Error while allocating EVP_PKEY_CTX.\n");
3592                 ERR_print_errors(bio_err);
3593                 op_count = 1;
3594                 ffdh_checks = 0;
3595                 break;
3596             }
3597             if (EVP_PKEY_derive_init(ffdh_ctx) <= 0) {
3598                 BIO_printf(bio_err, "FFDH derivation context init failure.\n");
3599                 ERR_print_errors(bio_err);
3600                 op_count = 1;
3601                 ffdh_checks = 0;
3602                 break;
3603             }
3604             if (EVP_PKEY_derive_set_peer(ffdh_ctx, pkey_B) <= 0) {
3605                 BIO_printf(bio_err, "Assigning peer key for derivation failed.\n");
3606                 ERR_print_errors(bio_err);
3607                 op_count = 1;
3608                 ffdh_checks = 0;
3609                 break;
3610             }
3611             if (EVP_PKEY_derive(ffdh_ctx, NULL, &secret_size) <= 0) {
3612                 BIO_printf(bio_err, "Checking size of shared secret failed.\n");
3613                 ERR_print_errors(bio_err);
3614                 op_count = 1;
3615                 ffdh_checks = 0;
3616                 break;
3617             }
3618             if (secret_size > MAX_FFDH_SIZE) {
3619                 BIO_printf(bio_err, "Assertion failure: shared secret too large.\n");
3620                 op_count = 1;
3621                 ffdh_checks = 0;
3622                 break;
3623             }
3624             if (EVP_PKEY_derive(ffdh_ctx,
3625                                 loopargs[i].secret_ff_a,
3626                                 &secret_size) <= 0) {
3627                 BIO_printf(bio_err, "Shared secret derive failure.\n");
3628                 ERR_print_errors(bio_err);
3629                 op_count = 1;
3630                 ffdh_checks = 0;
3631                 break;
3632             }
3633             /* Now check from side B */
3634             test_ctx = EVP_PKEY_CTX_new(pkey_B, NULL);
3635             if (!test_ctx) {
3636                 BIO_printf(bio_err, "Error while allocating EVP_PKEY_CTX.\n");
3637                 ERR_print_errors(bio_err);
3638                 op_count = 1;
3639                 ffdh_checks = 0;
3640                 break;
3641             }
3642             if (EVP_PKEY_derive_init(test_ctx) <= 0 ||
3643                 EVP_PKEY_derive_set_peer(test_ctx, pkey_A) <= 0 ||
3644                 EVP_PKEY_derive(test_ctx, NULL, &test_out) <= 0 ||
3645                 EVP_PKEY_derive(test_ctx, loopargs[i].secret_ff_b, &test_out) <= 0 ||
3646                 test_out != secret_size) {
3647                 BIO_printf(bio_err, "FFDH computation failure.\n");
3648                 op_count = 1;
3649                 ffdh_checks = 0;
3650                 break;
3651             }
3652
3653             /* compare the computed secrets */
3654             if (CRYPTO_memcmp(loopargs[i].secret_ff_a,
3655                               loopargs[i].secret_ff_b, secret_size)) {
3656                 BIO_printf(bio_err, "FFDH computations don't match.\n");
3657                 ERR_print_errors(bio_err);
3658                 op_count = 1;
3659                 ffdh_checks = 0;
3660                 break;
3661             }
3662
3663             loopargs[i].ffdh_ctx[testnum] = ffdh_ctx;
3664
3665             EVP_PKEY_free(pkey_A);
3666             pkey_A = NULL;
3667             EVP_PKEY_free(pkey_B);
3668             pkey_B = NULL;
3669             EVP_PKEY_CTX_free(test_ctx);
3670             test_ctx = NULL;
3671         }
3672         if (ffdh_checks != 0) {
3673             pkey_print_message("", "ffdh",
3674                                ffdh_params[testnum].bits, seconds.ffdh);
3675             Time_F(START);
3676             count =
3677                 run_benchmark(async_jobs, FFDH_derive_key_loop, loopargs);
3678             d = Time_F(STOP);
3679             BIO_printf(bio_err,
3680                        mr ? "+R14:%ld:%d:%.2f\n" :
3681                        "%ld %u-bits FFDH ops in %.2fs\n", count,
3682                        ffdh_params[testnum].bits, d);
3683             ffdh_results[testnum][0] = (double)count / d;
3684             op_count = count;
3685         }
3686         if (op_count <= 1) {
3687             /* if longer than 10s, don't do any more */
3688             stop_it(ffdh_doit, testnum);
3689         }
3690     }
3691 #endif  /* OPENSSL_NO_DH */
3692
3693     for (testnum = 0; testnum < kems_algs_len; testnum++) {
3694         int kem_checks = 1;
3695         const char *kem_name = kems_algname[testnum];
3696
3697         if (!kems_doit[testnum] || !do_kems)
3698             continue;
3699
3700         for (i = 0; i < loopargs_len; i++) {
3701             EVP_PKEY *pkey = NULL;
3702             EVP_PKEY_CTX *kem_gen_ctx = NULL;
3703             EVP_PKEY_CTX *kem_encaps_ctx = NULL;
3704             EVP_PKEY_CTX *kem_decaps_ctx = NULL;
3705             size_t send_secret_len, out_len;
3706             size_t rcv_secret_len;
3707             unsigned char *out = NULL, *send_secret = NULL, *rcv_secret;
3708             unsigned int bits;
3709             char *name;
3710             char sfx[MAX_ALGNAME_SUFFIX];
3711             OSSL_PARAM params[] = { OSSL_PARAM_END, OSSL_PARAM_END };
3712             int use_params = 0;
3713             enum kem_type_t { KEM_RSA = 1, KEM_EC, KEM_X25519, KEM_X448 } kem_type;
3714
3715             /* no string after rsa<bitcnt> permitted: */
3716             if (strlen(kem_name) < MAX_ALGNAME_SUFFIX + 4 /* rsa+digit */
3717                 && sscanf(kem_name, "rsa%u%s", &bits, sfx) == 1)
3718                 kem_type = KEM_RSA;
3719             else if (strncmp(kem_name, "EC", 2) == 0)
3720                 kem_type = KEM_EC;
3721             else if (strcmp(kem_name, "X25519") == 0)
3722                 kem_type = KEM_X25519;
3723             else if (strcmp(kem_name, "X448") == 0)
3724                 kem_type = KEM_X448;
3725             else kem_type = 0;
3726
3727             if (ERR_peek_error()) {
3728                 BIO_printf(bio_err,
3729                            "WARNING: the error queue contains previous unhandled errors.\n");
3730                 ERR_print_errors(bio_err);
3731             }
3732
3733             if (kem_type == KEM_RSA) {
3734                 params[0] = OSSL_PARAM_construct_uint(OSSL_PKEY_PARAM_RSA_BITS,
3735                                                       &bits);
3736                 use_params = 1;
3737             } else if (kem_type == KEM_EC) {
3738                 name = (char *)(kem_name + 2);
3739                 params[0] = OSSL_PARAM_construct_utf8_string(OSSL_PKEY_PARAM_GROUP_NAME,
3740                                                   name, 0);
3741                 use_params = 1;
3742             }
3743
3744             kem_gen_ctx = EVP_PKEY_CTX_new_from_name(app_get0_libctx(),
3745                                                (kem_type == KEM_RSA) ? "RSA":
3746                                                 (kem_type == KEM_EC) ? "EC":
3747                                                  kem_name,
3748                                                app_get0_propq());
3749
3750             if ((!kem_gen_ctx || EVP_PKEY_keygen_init(kem_gen_ctx) <= 0)
3751                 || (use_params
3752                     && EVP_PKEY_CTX_set_params(kem_gen_ctx, params) <= 0)) {
3753                 BIO_printf(bio_err, "Error initializing keygen ctx for %s.\n",
3754                            kem_name);
3755                 goto kem_err_break;
3756             }
3757             if (EVP_PKEY_keygen(kem_gen_ctx, &pkey) <= 0) {
3758                 BIO_printf(bio_err, "Error while generating KEM EVP_PKEY.\n");
3759                 goto kem_err_break;
3760             }
3761             /* Now prepare encaps data structs */
3762             kem_encaps_ctx = EVP_PKEY_CTX_new_from_pkey(app_get0_libctx(),
3763                                                         pkey,
3764                                                         app_get0_propq());
3765             if (kem_encaps_ctx == NULL
3766                 || EVP_PKEY_encapsulate_init(kem_encaps_ctx, NULL) <= 0
3767                 || (kem_type == KEM_RSA
3768                     && EVP_PKEY_CTX_set_kem_op(kem_encaps_ctx, "RSASVE") <= 0)
3769                 || ((kem_type == KEM_EC
3770                     || kem_type == KEM_X25519
3771                     || kem_type == KEM_X448)
3772                    && EVP_PKEY_CTX_set_kem_op(kem_encaps_ctx, "DHKEM") <= 0)
3773                 || EVP_PKEY_encapsulate(kem_encaps_ctx, NULL, &out_len,
3774                                       NULL, &send_secret_len) <= 0) {
3775                 BIO_printf(bio_err,
3776                            "Error while initializing encaps data structs for %s.\n",
3777                            kem_name);
3778                 goto kem_err_break;
3779             }
3780             out = app_malloc(out_len, "encaps result");
3781             send_secret = app_malloc(send_secret_len, "encaps secret");
3782             if (out == NULL || send_secret == NULL) {
3783                 BIO_printf(bio_err, "MemAlloc error in encaps for %s.\n", kem_name);
3784                 goto kem_err_break;
3785             }
3786             if (EVP_PKEY_encapsulate(kem_encaps_ctx, out, &out_len,
3787                                      send_secret, &send_secret_len) <= 0) {
3788                 BIO_printf(bio_err, "Encaps error for %s.\n", kem_name);
3789                 goto kem_err_break;
3790             }
3791             /* Now prepare decaps data structs */
3792             kem_decaps_ctx = EVP_PKEY_CTX_new_from_pkey(app_get0_libctx(),
3793                                                         pkey,
3794                                                         app_get0_propq());
3795             if (kem_decaps_ctx == NULL
3796                 || EVP_PKEY_decapsulate_init(kem_decaps_ctx, NULL) <= 0
3797                 || (kem_type == KEM_RSA
3798                   && EVP_PKEY_CTX_set_kem_op(kem_decaps_ctx, "RSASVE") <= 0)
3799                 || ((kem_type == KEM_EC
3800                      || kem_type == KEM_X25519
3801                      || kem_type == KEM_X448)
3802                   && EVP_PKEY_CTX_set_kem_op(kem_decaps_ctx, "DHKEM") <= 0)
3803                 || EVP_PKEY_decapsulate(kem_decaps_ctx, NULL, &rcv_secret_len,
3804                                         out, out_len) <= 0) {
3805                 BIO_printf(bio_err,
3806                            "Error while initializing decaps data structs for %s.\n",
3807                            kem_name);
3808                 goto kem_err_break;
3809             }
3810             rcv_secret = app_malloc(rcv_secret_len, "KEM decaps secret");
3811             if (rcv_secret == NULL) {
3812                 BIO_printf(bio_err, "MemAlloc failure in decaps for %s.\n",
3813                            kem_name);
3814                 goto kem_err_break;
3815             }
3816             if (EVP_PKEY_decapsulate(kem_decaps_ctx, rcv_secret,
3817                                      &rcv_secret_len, out, out_len) <= 0
3818                 || rcv_secret_len != send_secret_len
3819                 || memcmp(send_secret, rcv_secret, send_secret_len)) {
3820                 BIO_printf(bio_err, "Decaps error for %s.\n", kem_name);
3821                 goto kem_err_break;
3822             }
3823             loopargs[i].kem_gen_ctx[testnum] = kem_gen_ctx;
3824             loopargs[i].kem_encaps_ctx[testnum] = kem_encaps_ctx;
3825             loopargs[i].kem_decaps_ctx[testnum] = kem_decaps_ctx;
3826             loopargs[i].kem_out_len[testnum] = out_len;
3827             loopargs[i].kem_secret_len[testnum] = send_secret_len;
3828             loopargs[i].kem_out[testnum] = out;
3829             loopargs[i].kem_send_secret[testnum] = send_secret;
3830             loopargs[i].kem_rcv_secret[testnum] = rcv_secret;
3831             EVP_PKEY_free(pkey);
3832             pkey = NULL;
3833             break;
3834
3835         kem_err_break:
3836             ERR_print_errors(bio_err);
3837             EVP_PKEY_free(pkey);
3838             op_count = 1;
3839             kem_checks = 0;
3840             break;
3841         }
3842         if (kem_checks != 0) {
3843             kskey_print_message(kem_name, "keygen", seconds.kem);
3844             Time_F(START);
3845             count =
3846                 run_benchmark(async_jobs, KEM_keygen_loop, loopargs);
3847             d = Time_F(STOP);
3848             BIO_printf(bio_err,
3849                        mr ? "+R15:%ld:%s:%.2f\n" :
3850                        "%ld %s KEM keygen ops in %.2fs\n", count,
3851                        kem_name, d);
3852             kems_results[testnum][0] = (double)count / d;
3853             op_count = count;
3854             kskey_print_message(kem_name, "encaps", seconds.kem);
3855             Time_F(START);
3856             count =
3857                 run_benchmark(async_jobs, KEM_encaps_loop, loopargs);
3858             d = Time_F(STOP);
3859             BIO_printf(bio_err,
3860                        mr ? "+R16:%ld:%s:%.2f\n" :
3861                        "%ld %s KEM encaps ops in %.2fs\n", count,
3862                        kem_name, d);
3863             kems_results[testnum][1] = (double)count / d;
3864             op_count = count;
3865             kskey_print_message(kem_name, "decaps", seconds.kem);
3866             Time_F(START);
3867             count =
3868                 run_benchmark(async_jobs, KEM_decaps_loop, loopargs);
3869             d = Time_F(STOP);
3870             BIO_printf(bio_err,
3871                        mr ? "+R17:%ld:%s:%.2f\n" :
3872                        "%ld %s KEM decaps ops in %.2fs\n", count,
3873                        kem_name, d);
3874             kems_results[testnum][2] = (double)count / d;
3875             op_count = count;
3876         }
3877         if (op_count <= 1) {
3878             /* if longer than 10s, don't do any more */
3879             stop_it(kems_doit, testnum);
3880         }
3881     }
3882
3883     for (testnum = 0; testnum < sigs_algs_len; testnum++) {
3884         int sig_checks = 1;
3885         const char *sig_name = sigs_algname[testnum];
3886
3887         if (!sigs_doit[testnum] || !do_sigs)
3888             continue;
3889
3890         for (i = 0; i < loopargs_len; i++) {
3891             EVP_PKEY *pkey = NULL;
3892             EVP_PKEY_CTX *ctx_params = NULL;
3893             EVP_PKEY* pkey_params = NULL;
3894             EVP_PKEY_CTX *sig_gen_ctx = NULL;
3895             EVP_PKEY_CTX *sig_sign_ctx = NULL;
3896             EVP_PKEY_CTX *sig_verify_ctx = NULL;
3897             unsigned char md[SHA256_DIGEST_LENGTH];
3898             unsigned char *sig;
3899             char sfx[MAX_ALGNAME_SUFFIX];
3900             size_t md_len = SHA256_DIGEST_LENGTH;
3901             size_t max_sig_len, sig_len;
3902             unsigned int bits;
3903             OSSL_PARAM params[] = { OSSL_PARAM_END, OSSL_PARAM_END };
3904             int use_params = 0;
3905
3906             /* only sign little data to avoid measuring digest performance */
3907             memset(md, 0, SHA256_DIGEST_LENGTH);
3908
3909             if (ERR_peek_error()) {
3910                 BIO_printf(bio_err,
3911                            "WARNING: the error queue contains previous unhandled errors.\n");
3912                 ERR_print_errors(bio_err);
3913             }
3914
3915             /* no string after rsa<bitcnt> permitted: */
3916             if (strlen(sig_name) < MAX_ALGNAME_SUFFIX + 4 /* rsa+digit */
3917                 && sscanf(sig_name, "rsa%u%s", &bits, sfx) == 1) {
3918                 params[0] = OSSL_PARAM_construct_uint(OSSL_PKEY_PARAM_RSA_BITS,
3919                                                       &bits);
3920                 use_params = 1;
3921             }
3922
3923             if (strncmp(sig_name, "dsa", 3) == 0) {
3924                 ctx_params = EVP_PKEY_CTX_new_id(EVP_PKEY_DSA, NULL);
3925                 if (ctx_params == NULL
3926                     || EVP_PKEY_paramgen_init(ctx_params) <= 0
3927                     || EVP_PKEY_CTX_set_dsa_paramgen_bits(ctx_params,
3928                                                         atoi(sig_name + 3)) <= 0
3929                     || EVP_PKEY_paramgen(ctx_params, &pkey_params) <= 0
3930                     || (sig_gen_ctx = EVP_PKEY_CTX_new(pkey_params, NULL)) == NULL
3931                     || EVP_PKEY_keygen_init(sig_gen_ctx) <= 0) {
3932                     BIO_printf(bio_err,
3933                                "Error initializing classic keygen ctx for %s.\n",
3934                                sig_name);
3935                     goto sig_err_break;
3936                 }
3937             }
3938
3939             if (sig_gen_ctx == NULL)
3940                 sig_gen_ctx = EVP_PKEY_CTX_new_from_name(app_get0_libctx(),
3941                                       use_params == 1 ? "RSA" : sig_name,
3942                                       app_get0_propq());
3943
3944             if (!sig_gen_ctx || EVP_PKEY_keygen_init(sig_gen_ctx) <= 0
3945                 || (use_params &&
3946                     EVP_PKEY_CTX_set_params(sig_gen_ctx, params) <= 0)) {
3947                 BIO_printf(bio_err, "Error initializing keygen ctx for %s.\n",
3948                            sig_name);
3949                 goto sig_err_break;
3950             }
3951             if (EVP_PKEY_keygen(sig_gen_ctx, &pkey) <= 0) {
3952                 BIO_printf(bio_err,
3953                            "Error while generating signature EVP_PKEY for %s.\n",
3954                            sig_name);
3955                 goto sig_err_break;
3956             }
3957             /* Now prepare signature data structs */
3958             sig_sign_ctx = EVP_PKEY_CTX_new_from_pkey(app_get0_libctx(),
3959                                                       pkey,
3960                                                       app_get0_propq());
3961             if (sig_sign_ctx == NULL
3962                 || EVP_PKEY_sign_init(sig_sign_ctx) <= 0
3963                 || (use_params == 1
3964                     && (EVP_PKEY_CTX_set_rsa_padding(sig_sign_ctx,
3965                                                      RSA_PKCS1_PADDING) <= 0))
3966                 || EVP_PKEY_sign(sig_sign_ctx, NULL, &max_sig_len,
3967                                  md, md_len) <= 0) {
3968                     BIO_printf(bio_err,
3969                                "Error while initializing signing data structs for %s.\n",
3970                                sig_name);
3971                     goto sig_err_break;
3972             }
3973             sig = app_malloc(sig_len = max_sig_len, "signature buffer");
3974             if (sig == NULL) {
3975                 BIO_printf(bio_err, "MemAlloc error in sign for %s.\n", sig_name);
3976                 goto sig_err_break;
3977             }
3978             if (EVP_PKEY_sign(sig_sign_ctx, sig, &sig_len, md, md_len) <= 0) {
3979                 BIO_printf(bio_err, "Signing error for %s.\n", sig_name);
3980                 goto sig_err_break;
3981             }
3982             /* Now prepare verify data structs */
3983             memset(md, 0, SHA256_DIGEST_LENGTH);
3984             sig_verify_ctx = EVP_PKEY_CTX_new_from_pkey(app_get0_libctx(),
3985                                                         pkey,
3986                                                         app_get0_propq());
3987             if (sig_verify_ctx == NULL
3988                 || EVP_PKEY_verify_init(sig_verify_ctx) <= 0
3989                 || (use_params == 1
3990                   && (EVP_PKEY_CTX_set_rsa_padding(sig_verify_ctx,
3991                                                    RSA_PKCS1_PADDING) <= 0))) {
3992                 BIO_printf(bio_err,
3993                            "Error while initializing verify data structs for %s.\n",
3994                            sig_name);
3995                 goto sig_err_break;
3996             }
3997             if (EVP_PKEY_verify(sig_verify_ctx, sig, sig_len, md, md_len) <= 0) {
3998                 BIO_printf(bio_err, "Verify error for %s.\n", sig_name);
3999                 goto sig_err_break;
4000             }
4001             if (EVP_PKEY_verify(sig_verify_ctx, sig, sig_len, md, md_len) <= 0) {
4002                 BIO_printf(bio_err, "Verify 2 error for %s.\n", sig_name);
4003                 goto sig_err_break;
4004             }
4005             loopargs[i].sig_gen_ctx[testnum] = sig_gen_ctx;
4006             loopargs[i].sig_sign_ctx[testnum] = sig_sign_ctx;
4007             loopargs[i].sig_verify_ctx[testnum] = sig_verify_ctx;
4008             loopargs[i].sig_max_sig_len[testnum] = max_sig_len;
4009             loopargs[i].sig_act_sig_len[testnum] = sig_len;
4010             loopargs[i].sig_sig[testnum] = sig;
4011             EVP_PKEY_free(pkey);
4012             pkey = NULL;
4013             break;
4014
4015         sig_err_break:
4016             ERR_print_errors(bio_err);
4017             EVP_PKEY_free(pkey);
4018             op_count = 1;
4019             sig_checks = 0;
4020             break;
4021         }
4022
4023         if (sig_checks != 0) {
4024             kskey_print_message(sig_name, "keygen", seconds.sig);
4025             Time_F(START);
4026             count = run_benchmark(async_jobs, SIG_keygen_loop, loopargs);
4027             d = Time_F(STOP);
4028             BIO_printf(bio_err,
4029                        mr ? "+R18:%ld:%s:%.2f\n" :
4030                        "%ld %s signature keygen ops in %.2fs\n", count,
4031                        sig_name, d);
4032             sigs_results[testnum][0] = (double)count / d;
4033             op_count = count;
4034             kskey_print_message(sig_name, "signs", seconds.sig);
4035             Time_F(START);
4036             count =
4037                 run_benchmark(async_jobs, SIG_sign_loop, loopargs);
4038             d = Time_F(STOP);
4039             BIO_printf(bio_err,
4040                        mr ? "+R19:%ld:%s:%.2f\n" :
4041                        "%ld %s signature sign ops in %.2fs\n", count,
4042                        sig_name, d);
4043             sigs_results[testnum][1] = (double)count / d;
4044             op_count = count;
4045
4046             kskey_print_message(sig_name, "verify", seconds.sig);
4047             Time_F(START);
4048             count =
4049                 run_benchmark(async_jobs, SIG_verify_loop, loopargs);
4050             d = Time_F(STOP);
4051             BIO_printf(bio_err,
4052                        mr ? "+R20:%ld:%s:%.2f\n" :
4053                        "%ld %s signature verify ops in %.2fs\n", count,
4054                        sig_name, d);
4055             sigs_results[testnum][2] = (double)count / d;
4056             op_count = count;
4057         }
4058         if (op_count <= 1)
4059             stop_it(sigs_doit, testnum);
4060     }
4061
4062 #ifndef NO_FORK
4063  show_res:
4064 #endif
4065     if (!mr) {
4066         printf("version: %s\n", OpenSSL_version(OPENSSL_FULL_VERSION_STRING));
4067         printf("%s\n", OpenSSL_version(OPENSSL_BUILT_ON));
4068         printf("options: %s\n", BN_options());
4069         printf("%s\n", OpenSSL_version(OPENSSL_CFLAGS));
4070         printf("%s\n", OpenSSL_version(OPENSSL_CPU_INFO));
4071     }
4072
4073     if (pr_header) {
4074         if (mr) {
4075             printf("+H");
4076         } else {
4077             printf("The 'numbers' are in 1000s of bytes per second processed.\n");
4078             printf("type        ");
4079         }
4080         for (testnum = 0; testnum < size_num; testnum++)
4081             printf(mr ? ":%d" : "%7d bytes", lengths[testnum]);
4082         printf("\n");
4083     }
4084
4085     for (k = 0; k < ALGOR_NUM; k++) {
4086         const char *alg_name = names[k];
4087
4088         if (!doit[k])
4089             continue;
4090
4091         if (k == D_EVP) {
4092             if (evp_cipher == NULL)
4093                 alg_name = evp_md_name;
4094             else if ((alg_name = EVP_CIPHER_get0_name(evp_cipher)) == NULL)
4095                 app_bail_out("failed to get name of cipher '%s'\n", evp_cipher);
4096         }
4097
4098         if (mr)
4099             printf("+F:%u:%s", k, alg_name);
4100         else
4101             printf("%-13s", alg_name);
4102         for (testnum = 0; testnum < size_num; testnum++) {
4103             if (results[k][testnum] > 10000 && !mr)
4104                 printf(" %11.2fk", results[k][testnum] / 1e3);
4105             else
4106                 printf(mr ? ":%.2f" : " %11.2f ", results[k][testnum]);
4107         }
4108         printf("\n");
4109     }
4110     testnum = 1;
4111     for (k = 0; k < RSA_NUM; k++) {
4112         if (!rsa_doit[k])
4113             continue;
4114         if (testnum && !mr) {
4115             printf("%19ssign    verify    encrypt   decrypt   sign/s verify/s  encr./s  decr./s\n", " ");
4116             testnum = 0;
4117         }
4118         if (mr)
4119             printf("+F2:%u:%u:%f:%f:%f:%f\n",
4120                    k, rsa_keys[k].bits, rsa_results[k][0], rsa_results[k][1],
4121                    rsa_results[k][2], rsa_results[k][3]);
4122         else
4123             printf("rsa %5u bits %8.6fs %8.6fs %8.6fs %8.6fs %8.1f %8.1f %8.1f %8.1f\n",
4124                    rsa_keys[k].bits, 1.0 / rsa_results[k][0],
4125                    1.0 / rsa_results[k][1], 1.0 / rsa_results[k][2],
4126                    1.0 / rsa_results[k][3],
4127                    rsa_results[k][0], rsa_results[k][1],
4128                    rsa_results[k][2], rsa_results[k][3]);
4129     }
4130     testnum = 1;
4131     for (k = 0; k < DSA_NUM; k++) {
4132         if (!dsa_doit[k])
4133             continue;
4134         if (testnum && !mr) {
4135             printf("%18ssign    verify    sign/s verify/s\n", " ");
4136             testnum = 0;
4137         }
4138         if (mr)
4139             printf("+F3:%u:%u:%f:%f\n",
4140                    k, dsa_bits[k], dsa_results[k][0], dsa_results[k][1]);
4141         else
4142             printf("dsa %4u bits %8.6fs %8.6fs %8.1f %8.1f\n",
4143                    dsa_bits[k], 1.0 / dsa_results[k][0], 1.0 / dsa_results[k][1],
4144                    dsa_results[k][0], dsa_results[k][1]);
4145     }
4146     testnum = 1;
4147     for (k = 0; k < OSSL_NELEM(ecdsa_doit); k++) {
4148         if (!ecdsa_doit[k])
4149             continue;
4150         if (testnum && !mr) {
4151             printf("%30ssign    verify    sign/s verify/s\n", " ");
4152             testnum = 0;
4153         }
4154
4155         if (mr)
4156             printf("+F4:%u:%u:%f:%f\n",
4157                    k, ec_curves[k].bits,
4158                    ecdsa_results[k][0], ecdsa_results[k][1]);
4159         else
4160             printf("%4u bits ecdsa (%s) %8.4fs %8.4fs %8.1f %8.1f\n",
4161                    ec_curves[k].bits, ec_curves[k].name,
4162                    1.0 / ecdsa_results[k][0], 1.0 / ecdsa_results[k][1],
4163                    ecdsa_results[k][0], ecdsa_results[k][1]);
4164     }
4165
4166     testnum = 1;
4167     for (k = 0; k < EC_NUM; k++) {
4168         if (!ecdh_doit[k])
4169             continue;
4170         if (testnum && !mr) {
4171             printf("%30sop      op/s\n", " ");
4172             testnum = 0;
4173         }
4174         if (mr)
4175             printf("+F5:%u:%u:%f:%f\n",
4176                    k, ec_curves[k].bits,
4177                    ecdh_results[k][0], 1.0 / ecdh_results[k][0]);
4178
4179         else
4180             printf("%4u bits ecdh (%s) %8.4fs %8.1f\n",
4181                    ec_curves[k].bits, ec_curves[k].name,
4182                    1.0 / ecdh_results[k][0], ecdh_results[k][0]);
4183     }
4184
4185 #ifndef OPENSSL_NO_ECX
4186     testnum = 1;
4187     for (k = 0; k < OSSL_NELEM(eddsa_doit); k++) {
4188         if (!eddsa_doit[k])
4189             continue;
4190         if (testnum && !mr) {
4191             printf("%30ssign    verify    sign/s verify/s\n", " ");
4192             testnum = 0;
4193         }
4194
4195         if (mr)
4196             printf("+F6:%u:%u:%s:%f:%f\n",
4197                    k, ed_curves[k].bits, ed_curves[k].name,
4198                    eddsa_results[k][0], eddsa_results[k][1]);
4199         else
4200             printf("%4u bits EdDSA (%s) %8.4fs %8.4fs %8.1f %8.1f\n",
4201                    ed_curves[k].bits, ed_curves[k].name,
4202                    1.0 / eddsa_results[k][0], 1.0 / eddsa_results[k][1],
4203                    eddsa_results[k][0], eddsa_results[k][1]);
4204     }
4205 #endif /* OPENSSL_NO_ECX */
4206
4207 #ifndef OPENSSL_NO_SM2
4208     testnum = 1;
4209     for (k = 0; k < OSSL_NELEM(sm2_doit); k++) {
4210         if (!sm2_doit[k])
4211             continue;
4212         if (testnum && !mr) {
4213             printf("%30ssign    verify    sign/s verify/s\n", " ");
4214             testnum = 0;
4215         }
4216
4217         if (mr)
4218             printf("+F7:%u:%u:%s:%f:%f\n",
4219                    k, sm2_curves[k].bits, sm2_curves[k].name,
4220                    sm2_results[k][0], sm2_results[k][1]);
4221         else
4222             printf("%4u bits SM2 (%s) %8.4fs %8.4fs %8.1f %8.1f\n",
4223                    sm2_curves[k].bits, sm2_curves[k].name,
4224                    1.0 / sm2_results[k][0], 1.0 / sm2_results[k][1],
4225                    sm2_results[k][0], sm2_results[k][1]);
4226     }
4227 #endif
4228 #ifndef OPENSSL_NO_DH
4229     testnum = 1;
4230     for (k = 0; k < FFDH_NUM; k++) {
4231         if (!ffdh_doit[k])
4232             continue;
4233         if (testnum && !mr) {
4234             printf("%23sop     op/s\n", " ");
4235             testnum = 0;
4236         }
4237         if (mr)
4238             printf("+F8:%u:%u:%f:%f\n",
4239                    k, ffdh_params[k].bits,
4240                    ffdh_results[k][0], 1.0 / ffdh_results[k][0]);
4241
4242         else
4243             printf("%4u bits ffdh %8.4fs %8.1f\n",
4244                    ffdh_params[k].bits,
4245                    1.0 / ffdh_results[k][0], ffdh_results[k][0]);
4246     }
4247 #endif /* OPENSSL_NO_DH */
4248
4249     testnum = 1;
4250     for (k = 0; k < kems_algs_len; k++) {
4251         const char *kem_name = kems_algname[k];
4252
4253         if (!kems_doit[k] || !do_kems)
4254             continue;
4255         if (testnum && !mr) {
4256             printf("%31skeygen    encaps    decaps keygens/s  encaps/s  decaps/s\n", " ");
4257             testnum = 0;
4258         }
4259         if (mr)
4260             printf("+F9:%u:%f:%f:%f\n",
4261                    k, kems_results[k][0], kems_results[k][1],
4262                    kems_results[k][2]);
4263         else
4264             printf("%27s %8.6fs %8.6fs %8.6fs %9.1f %9.1f %9.1f\n", kem_name,
4265                    1.0 / kems_results[k][0],
4266                    1.0 / kems_results[k][1], 1.0 / kems_results[k][2],
4267                    kems_results[k][0], kems_results[k][1], kems_results[k][2]);
4268     }
4269     ret = 0;
4270
4271     testnum = 1;
4272     for (k = 0; k < sigs_algs_len; k++) {
4273         const char *sig_name = sigs_algname[k];
4274
4275         if (!sigs_doit[k] || !do_sigs)
4276             continue;
4277         if (testnum && !mr) {
4278             printf("%31skeygen     signs    verify keygens/s    sign/s  verify/s\n", " ");
4279             testnum = 0;
4280         }
4281         if (mr)
4282             printf("+F10:%u:%f:%f:%f\n",
4283                    k, sigs_results[k][0], sigs_results[k][1],
4284                    sigs_results[k][2]);
4285         else
4286             printf("%27s %8.6fs %8.6fs %8.6fs %9.1f %9.1f %9.1f\n", sig_name,
4287                    1.0 / sigs_results[k][0], 1.0 / sigs_results[k][1],
4288                    1.0 / sigs_results[k][2], sigs_results[k][0],
4289                    sigs_results[k][1], sigs_results[k][2]);
4290     }
4291     ret = 0;
4292
4293  end:
4294     ERR_print_errors(bio_err);
4295     for (i = 0; i < loopargs_len; i++) {
4296         OPENSSL_free(loopargs[i].buf_malloc);
4297         OPENSSL_free(loopargs[i].buf2_malloc);
4298
4299         BN_free(bn);
4300         EVP_PKEY_CTX_free(genctx);
4301         for (k = 0; k < RSA_NUM; k++) {
4302             EVP_PKEY_CTX_free(loopargs[i].rsa_sign_ctx[k]);
4303             EVP_PKEY_CTX_free(loopargs[i].rsa_verify_ctx[k]);
4304             EVP_PKEY_CTX_free(loopargs[i].rsa_encrypt_ctx[k]);
4305             EVP_PKEY_CTX_free(loopargs[i].rsa_decrypt_ctx[k]);
4306         }
4307 #ifndef OPENSSL_NO_DH
4308         OPENSSL_free(loopargs[i].secret_ff_a);
4309         OPENSSL_free(loopargs[i].secret_ff_b);
4310         for (k = 0; k < FFDH_NUM; k++)
4311             EVP_PKEY_CTX_free(loopargs[i].ffdh_ctx[k]);
4312 #endif
4313         for (k = 0; k < DSA_NUM; k++) {
4314             EVP_PKEY_CTX_free(loopargs[i].dsa_sign_ctx[k]);
4315             EVP_PKEY_CTX_free(loopargs[i].dsa_verify_ctx[k]);
4316         }
4317         for (k = 0; k < ECDSA_NUM; k++) {
4318             EVP_PKEY_CTX_free(loopargs[i].ecdsa_sign_ctx[k]);
4319             EVP_PKEY_CTX_free(loopargs[i].ecdsa_verify_ctx[k]);
4320         }
4321         for (k = 0; k < EC_NUM; k++)
4322             EVP_PKEY_CTX_free(loopargs[i].ecdh_ctx[k]);
4323 #ifndef OPENSSL_NO_ECX
4324         for (k = 0; k < EdDSA_NUM; k++) {
4325             EVP_MD_CTX_free(loopargs[i].eddsa_ctx[k]);
4326             EVP_MD_CTX_free(loopargs[i].eddsa_ctx2[k]);
4327         }
4328 #endif /* OPENSSL_NO_ECX */
4329 #ifndef OPENSSL_NO_SM2
4330         for (k = 0; k < SM2_NUM; k++) {
4331             EVP_PKEY_CTX *pctx = NULL;
4332
4333             /* free signing ctx */
4334             if (loopargs[i].sm2_ctx[k] != NULL
4335                 && (pctx = EVP_MD_CTX_get_pkey_ctx(loopargs[i].sm2_ctx[k])) != NULL)
4336                 EVP_PKEY_CTX_free(pctx);
4337             EVP_MD_CTX_free(loopargs[i].sm2_ctx[k]);
4338             /* free verification ctx */
4339             if (loopargs[i].sm2_vfy_ctx[k] != NULL
4340                 && (pctx = EVP_MD_CTX_get_pkey_ctx(loopargs[i].sm2_vfy_ctx[k])) != NULL)
4341                 EVP_PKEY_CTX_free(pctx);
4342             EVP_MD_CTX_free(loopargs[i].sm2_vfy_ctx[k]);
4343             /* free pkey */
4344             EVP_PKEY_free(loopargs[i].sm2_pkey[k]);
4345         }
4346 #endif
4347         for (k = 0; k < kems_algs_len; k++) {
4348             EVP_PKEY_CTX_free(loopargs[i].kem_gen_ctx[k]);
4349             EVP_PKEY_CTX_free(loopargs[i].kem_encaps_ctx[k]);
4350             EVP_PKEY_CTX_free(loopargs[i].kem_decaps_ctx[k]);
4351             OPENSSL_free(loopargs[i].kem_out[k]);
4352             OPENSSL_free(loopargs[i].kem_send_secret[k]);
4353             OPENSSL_free(loopargs[i].kem_rcv_secret[k]);
4354         }
4355         for (k = 0; k < sigs_algs_len; k++) {
4356             EVP_PKEY_CTX_free(loopargs[i].sig_gen_ctx[k]);
4357             EVP_PKEY_CTX_free(loopargs[i].sig_sign_ctx[k]);
4358             EVP_PKEY_CTX_free(loopargs[i].sig_verify_ctx[k]);
4359             OPENSSL_free(loopargs[i].sig_sig[k]);
4360         }
4361         OPENSSL_free(loopargs[i].secret_a);
4362         OPENSSL_free(loopargs[i].secret_b);
4363     }
4364     OPENSSL_free(evp_hmac_name);
4365     OPENSSL_free(evp_cmac_name);
4366     for (k = 0; k < kems_algs_len; k++)
4367         OPENSSL_free(kems_algname[k]);
4368     if (kem_stack != NULL)
4369         sk_EVP_KEM_pop_free(kem_stack, EVP_KEM_free);
4370     for (k = 0; k < sigs_algs_len; k++)
4371         OPENSSL_free(sigs_algname[k]);
4372     if (sig_stack != NULL)
4373         sk_EVP_SIGNATURE_pop_free(sig_stack, EVP_SIGNATURE_free);
4374
4375     if (async_jobs > 0) {
4376         for (i = 0; i < loopargs_len; i++)
4377             ASYNC_WAIT_CTX_free(loopargs[i].wait_ctx);
4378     }
4379
4380     if (async_init) {
4381         ASYNC_cleanup_thread();
4382     }
4383     OPENSSL_free(loopargs);
4384     release_engine(e);
4385     EVP_CIPHER_free(evp_cipher);
4386     EVP_MAC_free(mac);
4387     NCONF_free(conf);
4388     return ret;
4389 }
4390
4391 static void print_message(const char *s, int length, int tm)
4392 {
4393     BIO_printf(bio_err,
4394                mr ? "+DT:%s:%d:%d\n"
4395                : "Doing %s ops for %ds on %d size blocks: ", s, tm, length);
4396     (void)BIO_flush(bio_err);
4397     run = 1;
4398     alarm(tm);
4399 }
4400
4401 static void pkey_print_message(const char *str, const char *str2, unsigned int bits,
4402                                int tm)
4403 {
4404     BIO_printf(bio_err,
4405                mr ? "+DTP:%d:%s:%s:%d\n"
4406                : "Doing %u bits %s %s ops for %ds: ", bits, str, str2, tm);
4407     (void)BIO_flush(bio_err);
4408     run = 1;
4409     alarm(tm);
4410 }
4411
4412 static void kskey_print_message(const char *str, const char *str2, int tm)
4413 {
4414     BIO_printf(bio_err,
4415                mr ? "+DTP:%s:%s:%d\n"
4416                : "Doing %s %s ops for %ds: ", str, str2, tm);
4417     (void)BIO_flush(bio_err);
4418     run = 1;
4419     alarm(tm);
4420 }
4421
4422 static void print_result(int alg, int run_no, int count, double time_used)
4423 {
4424     if (count == -1) {
4425         BIO_printf(bio_err, "%s error!\n", names[alg]);
4426         ERR_print_errors(bio_err);
4427         return;
4428     }
4429     BIO_printf(bio_err,
4430                mr ? "+R:%d:%s:%f\n"
4431                : "%d %s ops in %.2fs\n", count, names[alg], time_used);
4432     results[alg][run_no] = ((double)count) / time_used * lengths[run_no];
4433 }
4434
4435 #ifndef NO_FORK
4436 static char *sstrsep(char **string, const char *delim)
4437 {
4438     char isdelim[256];
4439     char *token = *string;
4440
4441     memset(isdelim, 0, sizeof(isdelim));
4442     isdelim[0] = 1;
4443
4444     while (*delim) {
4445         isdelim[(unsigned char)(*delim)] = 1;
4446         delim++;
4447     }
4448
4449     while (!isdelim[(unsigned char)(**string)])
4450         (*string)++;
4451
4452     if (**string) {
4453         **string = 0;
4454         (*string)++;
4455     }
4456
4457     return token;
4458 }
4459
4460 static int strtoint(const char *str, const int min_val, const int upper_val,
4461                     int *res)
4462 {
4463     char *end = NULL;
4464     long int val = 0;
4465
4466     errno = 0;
4467     val = strtol(str, &end, 10);
4468     if (errno == 0 && end != str && *end == 0
4469         && min_val <= val && val < upper_val) {
4470         *res = (int)val;
4471         return 1;
4472     } else {
4473         return 0;
4474     }
4475 }
4476
4477 static int do_multi(int multi, int size_num)
4478 {
4479     int n;
4480     int fd[2];
4481     int *fds;
4482     int status;
4483     static char sep[] = ":";
4484
4485     fds = app_malloc(sizeof(*fds) * multi, "fd buffer for do_multi");
4486     for (n = 0; n < multi; ++n) {
4487         if (pipe(fd) == -1) {
4488             BIO_printf(bio_err, "pipe failure\n");
4489             exit(1);
4490         }
4491         fflush(stdout);
4492         (void)BIO_flush(bio_err);
4493         if (fork()) {
4494             close(fd[1]);
4495             fds[n] = fd[0];
4496         } else {
4497             close(fd[0]);
4498             close(1);
4499             if (dup(fd[1]) == -1) {
4500                 BIO_printf(bio_err, "dup failed\n");
4501                 exit(1);
4502             }
4503             close(fd[1]);
4504             mr = 1;
4505             usertime = 0;
4506             OPENSSL_free(fds);
4507             return 0;
4508         }
4509         printf("Forked child %d\n", n);
4510     }
4511
4512     /* for now, assume the pipe is long enough to take all the output */
4513     for (n = 0; n < multi; ++n) {
4514         FILE *f;
4515         char buf[1024];
4516         char *p;
4517         char *tk;
4518         int k;
4519         double d;
4520
4521         if ((f = fdopen(fds[n], "r")) == NULL) {
4522             BIO_printf(bio_err, "fdopen failure with 0x%x\n",
4523                        errno);
4524             OPENSSL_free(fds);
4525             return 1;
4526         }
4527         while (fgets(buf, sizeof(buf), f)) {
4528             p = strchr(buf, '\n');
4529             if (p)
4530                 *p = '\0';
4531             if (buf[0] != '+') {
4532                 BIO_printf(bio_err,
4533                            "Don't understand line '%s' from child %d\n", buf,
4534                            n);
4535                 continue;
4536             }
4537             printf("Got: %s from %d\n", buf, n);
4538             p = buf;
4539             if (CHECK_AND_SKIP_PREFIX(p, "+F:")) {
4540                 int alg;
4541                 int j;
4542
4543                 if (strtoint(sstrsep(&p, sep), 0, ALGOR_NUM, &alg)) {
4544                     sstrsep(&p, sep);
4545                     for (j = 0; j < size_num; ++j)
4546                         results[alg][j] += atof(sstrsep(&p, sep));
4547                 }
4548             } else if (CHECK_AND_SKIP_PREFIX(p, "+F2:")) {
4549                 tk = sstrsep(&p, sep);
4550                 if (strtoint(tk, 0, OSSL_NELEM(rsa_results), &k)) {
4551                     sstrsep(&p, sep);
4552
4553                     d = atof(sstrsep(&p, sep));
4554                     rsa_results[k][0] += d;
4555
4556                     d = atof(sstrsep(&p, sep));
4557                     rsa_results[k][1] += d;
4558
4559                     d = atof(sstrsep(&p, sep));
4560                     rsa_results[k][2] += d;
4561
4562                     d = atof(sstrsep(&p, sep));
4563                     rsa_results[k][3] += d;
4564                 }
4565             } else if (CHECK_AND_SKIP_PREFIX(p, "+F3:")) {
4566                 tk = sstrsep(&p, sep);
4567                 if (strtoint(tk, 0, OSSL_NELEM(dsa_results), &k)) {
4568                     sstrsep(&p, sep);
4569
4570                     d = atof(sstrsep(&p, sep));
4571                     dsa_results[k][0] += d;
4572
4573                     d = atof(sstrsep(&p, sep));
4574                     dsa_results[k][1] += d;
4575                 }
4576             } else if (CHECK_AND_SKIP_PREFIX(p, "+F4:")) {
4577                 tk = sstrsep(&p, sep);
4578                 if (strtoint(tk, 0, OSSL_NELEM(ecdsa_results), &k)) {
4579                     sstrsep(&p, sep);
4580
4581                     d = atof(sstrsep(&p, sep));
4582                     ecdsa_results[k][0] += d;
4583
4584                     d = atof(sstrsep(&p, sep));
4585                     ecdsa_results[k][1] += d;
4586                 }
4587             } else if (CHECK_AND_SKIP_PREFIX(p, "+F5:")) {
4588                 tk = sstrsep(&p, sep);
4589                 if (strtoint(tk, 0, OSSL_NELEM(ecdh_results), &k)) {
4590                     sstrsep(&p, sep);
4591
4592                     d = atof(sstrsep(&p, sep));
4593                     ecdh_results[k][0] += d;
4594                 }
4595 # ifndef OPENSSL_NO_ECX
4596             } else if (CHECK_AND_SKIP_PREFIX(p, "+F6:")) {
4597                 tk = sstrsep(&p, sep);
4598                 if (strtoint(tk, 0, OSSL_NELEM(eddsa_results), &k)) {
4599                     sstrsep(&p, sep);
4600                     sstrsep(&p, sep);
4601
4602                     d = atof(sstrsep(&p, sep));
4603                     eddsa_results[k][0] += d;
4604
4605                     d = atof(sstrsep(&p, sep));
4606                     eddsa_results[k][1] += d;
4607                 }
4608 # endif /* OPENSSL_NO_ECX */
4609 # ifndef OPENSSL_NO_SM2
4610             } else if (CHECK_AND_SKIP_PREFIX(p, "+F7:")) {
4611                 tk = sstrsep(&p, sep);
4612                 if (strtoint(tk, 0, OSSL_NELEM(sm2_results), &k)) {
4613                     sstrsep(&p, sep);
4614                     sstrsep(&p, sep);
4615
4616                     d = atof(sstrsep(&p, sep));
4617                     sm2_results[k][0] += d;
4618
4619                     d = atof(sstrsep(&p, sep));
4620                     sm2_results[k][1] += d;
4621                 }
4622 # endif /* OPENSSL_NO_SM2 */
4623 # ifndef OPENSSL_NO_DH
4624             } else if (CHECK_AND_SKIP_PREFIX(p, "+F8:")) {
4625                 tk = sstrsep(&p, sep);
4626                 if (strtoint(tk, 0, OSSL_NELEM(ffdh_results), &k)) {
4627                     sstrsep(&p, sep);
4628
4629                     d = atof(sstrsep(&p, sep));
4630                     ffdh_results[k][0] += d;
4631                 }
4632 # endif /* OPENSSL_NO_DH */
4633             } else if (CHECK_AND_SKIP_PREFIX(p, "+F9:")) {
4634                 tk = sstrsep(&p, sep);
4635                 if (strtoint(tk, 0, OSSL_NELEM(kems_results), &k)) {
4636                     d = atof(sstrsep(&p, sep));
4637                     kems_results[k][0] += d;
4638
4639                     d = atof(sstrsep(&p, sep));
4640                     kems_results[k][1] += d;
4641
4642                     d = atof(sstrsep(&p, sep));
4643                     kems_results[k][2] += d;
4644                 }
4645             } else if (CHECK_AND_SKIP_PREFIX(p, "+F10:")) {
4646                 tk = sstrsep(&p, sep);
4647                 if (strtoint(tk, 0, OSSL_NELEM(sigs_results), &k)) {
4648                     d = atof(sstrsep(&p, sep));
4649                     sigs_results[k][0] += d;
4650
4651                     d = atof(sstrsep(&p, sep));
4652                     sigs_results[k][1] += d;
4653
4654                     d = atof(sstrsep(&p, sep));
4655                     sigs_results[k][2] += d;
4656                 }
4657             } else if (!HAS_PREFIX(buf, "+H:")) {
4658                 BIO_printf(bio_err, "Unknown type '%s' from child %d\n", buf,
4659                            n);
4660             }
4661         }
4662
4663         fclose(f);
4664     }
4665     OPENSSL_free(fds);
4666     for (n = 0; n < multi; ++n) {
4667         while (wait(&status) == -1)
4668             if (errno != EINTR) {
4669                 BIO_printf(bio_err, "Waitng for child failed with 0x%x\n",
4670                            errno);
4671                 return 1;
4672             }
4673         if (WIFEXITED(status) && WEXITSTATUS(status)) {
4674             BIO_printf(bio_err, "Child exited with %d\n", WEXITSTATUS(status));
4675         } else if (WIFSIGNALED(status)) {
4676             BIO_printf(bio_err, "Child terminated by signal %d\n",
4677                        WTERMSIG(status));
4678         }
4679     }
4680     return 1;
4681 }
4682 #endif
4683
4684 static void multiblock_speed(const EVP_CIPHER *evp_cipher, int lengths_single,
4685                              const openssl_speed_sec_t *seconds)
4686 {
4687     static const int mblengths_list[] =
4688         { 8 * 1024, 2 * 8 * 1024, 4 * 8 * 1024, 8 * 8 * 1024, 8 * 16 * 1024 };
4689     const int *mblengths = mblengths_list;
4690     int j, count, keylen, num = OSSL_NELEM(mblengths_list), ciph_success = 1;
4691     const char *alg_name;
4692     unsigned char *inp = NULL, *out = NULL, *key, no_key[32], no_iv[16];
4693     EVP_CIPHER_CTX *ctx = NULL;
4694     double d = 0.0;
4695
4696     if (lengths_single) {
4697         mblengths = &lengths_single;
4698         num = 1;
4699     }
4700
4701     inp = app_malloc(mblengths[num - 1], "multiblock input buffer");
4702     out = app_malloc(mblengths[num - 1] + 1024, "multiblock output buffer");
4703     if ((ctx = EVP_CIPHER_CTX_new()) == NULL)
4704         app_bail_out("failed to allocate cipher context\n");
4705     if (!EVP_EncryptInit_ex(ctx, evp_cipher, NULL, NULL, no_iv))
4706         app_bail_out("failed to initialise cipher context\n");
4707
4708     if ((keylen = EVP_CIPHER_CTX_get_key_length(ctx)) < 0) {
4709         BIO_printf(bio_err, "Impossible negative key length: %d\n", keylen);
4710         goto err;
4711     }
4712     key = app_malloc(keylen, "evp_cipher key");
4713     if (EVP_CIPHER_CTX_rand_key(ctx, key) <= 0)
4714         app_bail_out("failed to generate random cipher key\n");
4715     if (!EVP_EncryptInit_ex(ctx, NULL, NULL, key, NULL))
4716         app_bail_out("failed to set cipher key\n");
4717     OPENSSL_clear_free(key, keylen);
4718
4719     if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_SET_MAC_KEY,
4720                              sizeof(no_key), no_key) <= 0)
4721         app_bail_out("failed to set AEAD key\n");
4722     if ((alg_name = EVP_CIPHER_get0_name(evp_cipher)) == NULL)
4723         app_bail_out("failed to get cipher name\n");
4724
4725     for (j = 0; j < num; j++) {
4726         print_message(alg_name, mblengths[j], seconds->sym);
4727         Time_F(START);
4728         for (count = 0; run && count < INT_MAX; count++) {
4729             unsigned char aad[EVP_AEAD_TLS1_AAD_LEN];
4730             EVP_CTRL_TLS1_1_MULTIBLOCK_PARAM mb_param;
4731             size_t len = mblengths[j];
4732             int packlen;
4733
4734             memset(aad, 0, 8);  /* avoid uninitialized values */
4735             aad[8] = 23;        /* SSL3_RT_APPLICATION_DATA */
4736             aad[9] = 3;         /* version */
4737             aad[10] = 2;
4738             aad[11] = 0;        /* length */
4739             aad[12] = 0;
4740             mb_param.out = NULL;
4741             mb_param.inp = aad;
4742             mb_param.len = len;
4743             mb_param.interleave = 8;
4744
4745             packlen = EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_TLS1_1_MULTIBLOCK_AAD,
4746                                           sizeof(mb_param), &mb_param);
4747
4748             if (packlen > 0) {
4749                 mb_param.out = out;
4750                 mb_param.inp = inp;
4751                 mb_param.len = len;
4752                 (void)EVP_CIPHER_CTX_ctrl(ctx,
4753                                           EVP_CTRL_TLS1_1_MULTIBLOCK_ENCRYPT,
4754                                           sizeof(mb_param), &mb_param);
4755             } else {
4756                 int pad;
4757
4758                 if (RAND_bytes(inp, 16) <= 0)
4759                     app_bail_out("error setting random bytes\n");
4760                 len += 16;
4761                 aad[11] = (unsigned char)(len >> 8);
4762                 aad[12] = (unsigned char)(len);
4763                 pad = EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_TLS1_AAD,
4764                                           EVP_AEAD_TLS1_AAD_LEN, aad);
4765                 ciph_success = EVP_Cipher(ctx, out, inp, len + pad);
4766             }
4767         }
4768         d = Time_F(STOP);
4769         BIO_printf(bio_err, mr ? "+R:%d:%s:%f\n"
4770                    : "%d %s ops in %.2fs\n", count, "evp", d);
4771         if ((ciph_success <= 0) && (mr == 0))
4772             BIO_printf(bio_err, "Error performing cipher op\n");
4773         results[D_EVP][j] = ((double)count) / d * mblengths[j];
4774     }
4775
4776     if (mr) {
4777         fprintf(stdout, "+H");
4778         for (j = 0; j < num; j++)
4779             fprintf(stdout, ":%d", mblengths[j]);
4780         fprintf(stdout, "\n");
4781         fprintf(stdout, "+F:%d:%s", D_EVP, alg_name);
4782         for (j = 0; j < num; j++)
4783             fprintf(stdout, ":%.2f", results[D_EVP][j]);
4784         fprintf(stdout, "\n");
4785     } else {
4786         fprintf(stdout,
4787                 "The 'numbers' are in 1000s of bytes per second processed.\n");
4788         fprintf(stdout, "type                    ");
4789         for (j = 0; j < num; j++)
4790             fprintf(stdout, "%7d bytes", mblengths[j]);
4791         fprintf(stdout, "\n");
4792         fprintf(stdout, "%-24s", alg_name);
4793
4794         for (j = 0; j < num; j++) {
4795             if (results[D_EVP][j] > 10000)
4796                 fprintf(stdout, " %11.2fk", results[D_EVP][j] / 1e3);
4797             else
4798                 fprintf(stdout, " %11.2f ", results[D_EVP][j]);
4799         }
4800         fprintf(stdout, "\n");
4801     }
4802
4803  err:
4804     OPENSSL_free(inp);
4805     OPENSSL_free(out);
4806     EVP_CIPHER_CTX_free(ctx);
4807 }