From 26b42684422c057516efa2620e05eecff84f7f2b Mon Sep 17 00:00:00 2001 From: Dmitry Misharov Date: Mon, 3 Aug 2026 15:35:19 +0200 Subject: [PATCH] Avoid false sharing: accumulate iteration counts locally, store once at thread end Assisted-by: Claude:claude-opus-5 --- source/evp_cipher.c | 9 +++++++-- source/evp_fetch.c | 5 ++++- source/evp_hash.c | 9 +++++++-- source/evp_mac.c | 18 ++++++++++++++---- source/evp_setpeer.c | 8 ++++---- source/handshake.c | 15 ++++++++++++--- source/newrawkey.c | 7 ++++--- source/pkeyread.c | 7 ++++--- source/providerdoall.c | 7 ++++--- source/randbytes.c | 7 ++++--- source/rsasign.c | 6 +++--- source/sslnew.c | 7 ++++--- source/writeread.c | 4 +++- source/x509storeissuer.c | 6 +++--- 14 files changed, 77 insertions(+), 38 deletions(-) diff --git a/source/evp_cipher.c b/source/evp_cipher.c index 741917dc..90b02fca 100644 --- a/source/evp_cipher.c +++ b/source/evp_cipher.c @@ -83,6 +83,7 @@ static int cipher_isolated() static void do_cipher_isolated(size_t num) { OSSL_TIME time; + size_t count = 0; do { if (!cipher_isolated()) { @@ -90,15 +91,18 @@ static void do_cipher_isolated(size_t num) return; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = count; } static void do_cipher_shared(size_t num) { OSSL_TIME time; EVP_CIPHER_CTX *ctx = EVP_CIPHER_CTX_new(); + size_t count = 0; if (ctx == NULL || !EVP_CipherInit_ex2(ctx, evp_cipher, key, iv, 1, NULL)) { err = 1; @@ -111,11 +115,12 @@ static void do_cipher_shared(size_t num) goto err; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); err: + counts[num] = count; EVP_CIPHER_CTX_free(ctx); } diff --git a/source/evp_fetch.c b/source/evp_fetch.c index 3ec64083..a5cf778b 100644 --- a/source/evp_fetch.c +++ b/source/evp_fetch.c @@ -163,6 +163,7 @@ void do_fetch(size_t num) { OSSL_TIME time; size_t i, j; + size_t count = 0; const char *fetch_alg = NULL; int array_size = ARRAY_SIZE(fetch_entries); @@ -282,9 +283,11 @@ void do_fetch(size_t num) err = 1; return; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = count; } static void diff --git a/source/evp_hash.c b/source/evp_hash.c index 9b29bae8..e754b9bd 100644 --- a/source/evp_hash.c +++ b/source/evp_hash.c @@ -191,6 +191,7 @@ static int hash_evp_sha512() static void do_hash_isolated(size_t num) { OSSL_TIME time; + size_t count = 0; do { if (!hash_func_isolated()) { @@ -198,9 +199,11 @@ static void do_hash_isolated(size_t num) return; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = count; } /* @@ -226,6 +229,7 @@ static void do_hash_evp_shared(size_t num) { OSSL_TIME time; EVP_MD_CTX *mctx = EVP_MD_CTX_new(); + size_t count = 0; if (mctx == NULL || !EVP_DigestInit_ex(mctx, evp_md, NULL)) { err = 1; @@ -238,11 +242,12 @@ static void do_hash_evp_shared(size_t num) goto err; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); err: + counts[num] = count; EVP_MD_CTX_free(mctx); } diff --git a/source/evp_mac.c b/source/evp_mac.c index 1838b075..e88464cc 100644 --- a/source/evp_mac.c +++ b/source/evp_mac.c @@ -93,6 +93,7 @@ static int evp_isolated() static void do_evp_isolated(size_t num) { OSSL_TIME time; + size_t count = 0; do { if (!evp_isolated()) { @@ -100,15 +101,18 @@ static void do_evp_isolated(size_t num) return; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = count; } static void do_evp_shared(size_t num) { OSSL_TIME time; EVP_MAC *mac = NULL; + size_t count = 0; EVP_MAC_CTX *ctx = NULL; OSSL_PARAM params[] = { OSSL_PARAM_construct_utf8_string("digest", "SHA256", 0), @@ -129,11 +133,12 @@ static void do_evp_shared(size_t num) goto err; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); err: + counts[num] = count; EVP_MAC_CTX_free(ctx); EVP_MAC_free(mac); } @@ -173,6 +178,7 @@ static int hmac_isolated() static void do_deprecated_isolated(size_t num) { OSSL_TIME time; + size_t count = 0; do { if (!hmac_isolated()) { @@ -180,15 +186,18 @@ static void do_deprecated_isolated(size_t num) return; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = count; } static void do_deprecated_shared(size_t num) { OSSL_TIME time; HMAC_CTX *ctx = HMAC_CTX_new(); + size_t count = 0; if (ctx == NULL || !HMAC_Init_ex(ctx, key, KEY_SIZE, EVP_sha256(), NULL)) @@ -199,10 +208,11 @@ static void do_deprecated_shared(size_t num) || !HMAC_Init_ex(ctx, NULL, 0, NULL, NULL)) goto err; - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + counts[num] = count; return; err: diff --git a/source/evp_setpeer.c b/source/evp_setpeer.c index f0292e9c..a41927f1 100644 --- a/source/evp_setpeer.c +++ b/source/evp_setpeer.c @@ -39,6 +39,7 @@ OSSL_TIME max_time; void do_setpeer(size_t num) { OSSL_TIME time; + size_t count = 0; EVP_PKEY_CTX *pkey_ctx = NULL; @@ -56,17 +57,16 @@ void do_setpeer(size_t num) return; } - counts[num] = 0; - do { if (EVP_PKEY_derive_set_peer(pkey_ctx, pkey) <= 0) { err = 1; break; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + counts[num] = count; EVP_PKEY_CTX_free(pkey_ctx); } @@ -183,7 +183,7 @@ int main(int argc, char *argv[]) return EXIT_FAILURE; } - counts = OPENSSL_malloc(sizeof(OSSL_TIME) * threadcount); + counts = OPENSSL_malloc(sizeof(size_t) * threadcount); if (counts == NULL) { printf("Failed to create counts array\n"); return EXIT_FAILURE; diff --git a/source/handshake.c b/source/handshake.c index f87c6ca3..464d59e2 100644 --- a/source/handshake.c +++ b/source/handshake.c @@ -69,6 +69,7 @@ static void do_handshake(size_t num) SSL *clientssl = NULL, *serverssl = NULL; int ret = 1; OSSL_TIME time; + size_t count = 0; SSL_CTX *lsctx = NULL; SSL_CTX *lcctx = NULL; @@ -102,10 +103,12 @@ static void do_handshake(size_t num) SSL_CTX_free(lcctx); lsctx = lcctx = NULL; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + counts[num] = count; + if (!ret) err = 1; } @@ -117,6 +120,7 @@ static void do_handshake_ossl_lib_ctx_per_thread(size_t num) SSL *clientssl = NULL, *serverssl = NULL; int ret = 1; OSSL_TIME time; + size_t count = 0; OSSL_LIB_CTX *libctx = NULL; SSL_CTX *lsctx = NULL; SSL_CTX *lcctx = NULL; @@ -156,10 +160,12 @@ static void do_handshake_ossl_lib_ctx_per_thread(size_t num) SSL_CTX_free(lcctx); lsctx = lcctx = NULL; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + counts[num] = count; + SSL_CTX_free(lsctx); SSL_CTX_free(lcctx); @@ -174,6 +180,7 @@ static void do_handshake_ctx_pool(size_t num) SSL *clientssl = NULL, *serverssl = NULL; int ret = 1; OSSL_TIME time; + size_t count = 0; SSL_CTX *lsctx = NULL; SSL_CTX *lcctx = NULL; struct ctxs *ctx = NULL; @@ -226,11 +233,13 @@ static void do_handshake_ctx_pool(size_t num) SSL_CTX_free(lcctx); lsctx = lcctx = NULL; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + counts[num] = count; + if (share_ctx == 1 && test_case == TC_OSSL_LIB_CTX_POOL) { SSL_CTX_free(lsctx); SSL_CTX_free(lcctx); diff --git a/source/newrawkey.c b/source/newrawkey.c index 850e5c22..db6d49fc 100644 --- a/source/newrawkey.c +++ b/source/newrawkey.c @@ -337,6 +337,7 @@ void do_newrawkey(size_t num) { EVP_PKEY *pkey; OSSL_TIME time; + size_t count = 0; const unsigned char *key_data = key_x25519; size_t key_len = sizeof(key_x25519); @@ -362,8 +363,6 @@ void do_newrawkey(size_t num) break; } - counts[num] = 0; - do { #if OPENSSL_VERSION_NUMBER >= 0x30000000L pkey = EVP_PKEY_new_raw_public_key_ex(NULL, alg_name, NULL, key_data, @@ -379,9 +378,11 @@ void do_newrawkey(size_t num) err = 1; else EVP_PKEY_free(pkey); - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = count; } int main(int argc, char *argv[]) diff --git a/source/pkeyread.c b/source/pkeyread.c index 262734de..d339178c 100644 --- a/source/pkeyread.c +++ b/source/pkeyread.c @@ -128,6 +128,7 @@ static void do_derread(size_t num) size_t keydata_sz; EVP_PKEY *pkey = NULL; OSSL_TIME time; + size_t count = 0; if (sample_id >= SAMPLE_ALL) { fprintf(stderr, "%s no sample key set for test\n", __func__); @@ -135,8 +136,6 @@ static void do_derread(size_t num) return; } - counts[num] = 0; - do { keydata = (const unsigned char *)sample_keys[sample_id][FORMAT_DER]; keydata_sz = sample_key_sizes[sample_id][FORMAT_DER]; @@ -151,9 +150,11 @@ static void do_derread(size_t num) error: EVP_PKEY_free(pkey); pkey = NULL; - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = count; } static int sample_name_to_id(const char *sample_name) diff --git a/source/providerdoall.c b/source/providerdoall.c index dbdbb0d4..503fd4c7 100644 --- a/source/providerdoall.c +++ b/source/providerdoall.c @@ -44,8 +44,7 @@ static void do_providerdoall(size_t num) { int count; OSSL_TIME time; - - counts[num] = 0; + size_t iters = 0; do { count = 0; @@ -53,9 +52,11 @@ static void do_providerdoall(size_t num) err = 1; break; } - counts[num]++; + iters++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = iters; } int main(int argc, char *argv[]) diff --git a/source/randbytes.c b/source/randbytes.c index 7d14fcf6..a339c687 100644 --- a/source/randbytes.c +++ b/source/randbytes.c @@ -36,15 +36,16 @@ void do_randbytes(size_t num) { unsigned char buf[32]; OSSL_TIME time; - - counts[num] = 0; + size_t count = 0; do { if (!RAND_bytes(buf, sizeof(buf))) err = 1; - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = count; } int main(int argc, char *argv[]) diff --git a/source/rsasign.c b/source/rsasign.c index b7775015..af1a3e28 100644 --- a/source/rsasign.c +++ b/source/rsasign.c @@ -54,8 +54,7 @@ void do_rsasign(size_t num) EVP_PKEY_CTX *ctx = EVP_PKEY_CTX_new(rsakey, NULL); size_t siglen = sizeof(sig); OSSL_TIME time; - - counts[num] = 0; + size_t count = 0; do { if (EVP_PKEY_sign_init(ctx) <= 0 @@ -64,10 +63,11 @@ void do_rsasign(size_t num) err = 1; break; } - counts[num]++; + count++; time = ossl_time_now(); } while(time.t < max_time.t); + counts[num] = count; EVP_PKEY_CTX_free(ctx); } diff --git a/source/sslnew.c b/source/sslnew.c index 4efa89a0..64c38b03 100644 --- a/source/sslnew.c +++ b/source/sslnew.c @@ -37,8 +37,7 @@ void do_sslnew(size_t num) SSL *s; BIO *rbio, *wbio; OSSL_TIME time; - - counts[num] = 0; + size_t count = 0; do { s = SSL_new(ctx); @@ -55,9 +54,11 @@ void do_sslnew(size_t num) } SSL_free(s); - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + + counts[num] = count; } int main(int argc, char *argv[]) diff --git a/source/writeread.c b/source/writeread.c index 6a845a39..18bc304a 100644 --- a/source/writeread.c +++ b/source/writeread.c @@ -44,6 +44,7 @@ static void do_writeread(size_t num) int ret = 1; OSSL_TIME time; char *sbuf, *cbuf; + size_t count = 0; /* Prepare client and server buffers. */ sbuf = OPENSSL_malloc(buf_size); @@ -92,10 +93,11 @@ static void do_writeread(size_t num) err = 1; return; } - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); + counts[num] = count; perflib_shutdown_ssl_connection(serverssl, clientssl); if (share_ctx == 0) { SSL_CTX_free(lsctx); diff --git a/source/x509storeissuer.c b/source/x509storeissuer.c index bd927d0b..1853d871 100644 --- a/source/x509storeissuer.c +++ b/source/x509storeissuer.c @@ -38,6 +38,7 @@ static void do_x509storeissuer(size_t num) X509_STORE_CTX *ctx = X509_STORE_CTX_new(); X509 *issuer = NULL; OSSL_TIME time; + size_t count = 0; if (ctx == NULL || !X509_STORE_CTX_init(ctx, store, x509, NULL)) { printf("Failed to initialise X509_STORE_CTX\n"); @@ -45,8 +46,6 @@ static void do_x509storeissuer(size_t num) goto err; } - counts[num] = 0; - do { /* * We actually expect this to fail. We've not configured any @@ -60,11 +59,12 @@ static void do_x509storeissuer(size_t num) goto err; } issuer = NULL; - counts[num]++; + count++; time = ossl_time_now(); } while (time.t < max_time.t); err: + counts[num] = count; X509_STORE_CTX_free(ctx); }