Commit c5ae170e85 for openssl.org
commit c5ae170e855d055774000f7221f5d5afd5f4fa72
Author: Jakub Zelenka <jakub.zelenka@openssl.foundation>
Date: Thu Jun 25 17:57:37 2026 +0200
property: add cache provider-order regression test
When two providers cache the same nid and property query, the first one
to do so must own the providerless cache entry, so that a NULL-provider
lookup keeps resolving to that provider. This covers commit 9d476175d7.
Assisted-by: Claude:claude-opus-4-8
Reviewed-by: Neil Horman <nhorman@openssl.org>
Reviewed-by: Nikola Pajkovsky <nikolap@openssl.org>
MergeDate: Tue Jun 30 11:01:57 2026
(Merged from https://github.com/openssl/openssl/pull/31738)
diff --git a/test/property_test.c b/test/property_test.c
index 47422b4049..602651df25 100644
--- a/test/property_test.c
+++ b/test/property_test.c
@@ -691,6 +691,62 @@ err:
return res;
}
+/*
+ * When two providers cache the same nid and property query, the first one to
+ * do so must own the providerless ("any provider will do") cache entry, so
+ * that a NULL-provider lookup keeps resolving to that provider regardless of
+ * how many other providers subsequently cache the same nid. This matches the
+ * provider ossl_method_store_fetch would pick by implementation order.
+ */
+static int test_query_cache_provider_order(void)
+{
+ OSSL_METHOD_STORE *store = NULL;
+ int res = 0;
+ int method1 = 0, method2 = 0;
+ void *result = NULL;
+ OSSL_PROVIDER prov1 = {
+ .flag_initialized = 1,
+ .flag_activated = 1,
+ .name = "first-provider"
+ };
+ OSSL_PROVIDER prov2 = {
+ .flag_initialized = 1,
+ .flag_activated = 1,
+ .name = "second-provider"
+ };
+
+ if (!TEST_ptr(store = ossl_method_store_new(NULL)))
+ goto err;
+
+ /* prov1 caches the nid first, so it owns the providerless entry. */
+ if (!TEST_true(ossl_method_store_cache_set(store, &prov1, 1, "", &method1,
+ up_ref, down_ref))
+ || !TEST_true(ossl_method_store_cache_set(store, &prov2, 1, "",
+ &method2, up_ref, down_ref)))
+ goto err;
+
+ /* A NULL-provider ("any provider") lookup must resolve to prov1. */
+ if (!TEST_true(ossl_method_store_cache_get(store, NULL, 1, "", &result))
+ || !TEST_ptr_eq(result, &method1))
+ goto err;
+
+ /* Provider-specific lookups must still return each provider's method. */
+ result = NULL;
+ if (!TEST_true(ossl_method_store_cache_get(store, &prov1, 1, "", &result))
+ || !TEST_ptr_eq(result, &method1))
+ goto err;
+ result = NULL;
+ if (!TEST_true(ossl_method_store_cache_get(store, &prov2, 1, "", &result))
+ || !TEST_ptr_eq(result, &method2))
+ goto err;
+
+ res = 1;
+
+err:
+ ossl_method_store_free(store);
+ return res;
+}
+
static int test_fips_mode(void)
{
int ret = 0;
@@ -804,6 +860,7 @@ int setup_tests(void)
ADD_TEST(test_property);
ADD_TEST(test_query_cache_stochastic);
ADD_TEST(test_query_cache_set_duplicate);
+ ADD_TEST(test_query_cache_provider_order);
ADD_TEST(test_fips_mode);
ADD_ALL_TESTS(test_property_list_to_string, OSSL_NELEM(to_string_tests));
ADD_TEST(test_property_list_to_string_bounds);