File 0673-crypto-Make-get_curve_cnt-less-racy.patch of Package erlang
From e1625b615f61932da9f9da88717fcde83f348105 Mon Sep 17 00:00:00 2001
From: Sverker Eriksson <sverker@erlang.org>
Date: Mon, 27 Sep 2021 21:11:00 +0200
Subject: [PATCH 2/2] crypto: Make get_curve_cnt() less racy
As algo_curve_cnt and algo_curve_cnt_initialized are read
without any lock we are not guaranteed consistency. We may read
algo_curve_cnt_initialized as 1 and then algo_curve_cnt as 0.
Instead mark uninitialized with negative value and skip the separate
_initialized variable.
It's still not 100% kosher to read algo_curve_cnt without
synchronization but will work in practice.
---
lib/crypto/c_src/algorithms.c | 33 +++++++++++++++------------------
1 file changed, 15 insertions(+), 18 deletions(-)
diff --git a/lib/crypto/c_src/algorithms.c b/lib/crypto/c_src/algorithms.c
index 5baa5b3c08..2c73b2005c 100644
--- a/lib/crypto/c_src/algorithms.c
+++ b/lib/crypto/c_src/algorithms.c
@@ -205,44 +205,36 @@ ERL_NIF_TERM curve_algorithms(ErlNifEnv* env, int argc, const ERL_NIF_TERM argv[
return enif_make_list_from_array(env, algo_curve[fips_mode], algo_curve_cnt);
}
-#if defined(HAVE_EC)
int init_curves(ErlNifEnv* env, int fips);
+#if defined(HAVE_EC)
int valid_curve(int nid);
#endif
int get_curve_cnt(ErlNifEnv* env, int fips) {
- static unsigned int algo_curve_cnt, algo_curve_cnt_initialized;
- static unsigned int algo_curve_fips_cnt, algo_curve_fips_cnt_initialized;
+ static int algo_curve_cnt = -1;
+ static int algo_curve_fips_cnt = -1;
int cnt = 0;
- if (0 == fips && 1 == algo_curve_cnt_initialized) {
+ if (0 == fips && algo_curve_cnt >= 0) {
return algo_curve_cnt;
}
- if (1 == fips && 1 == algo_curve_fips_cnt_initialized) {
+ if (1 == fips && algo_curve_fips_cnt >= 0) {
return algo_curve_fips_cnt;
}
enif_mutex_lock(mtx_init_curve_types);
if (1 == fips) {
- if (1 == algo_curve_fips_cnt_initialized) {
+ if (algo_curve_fips_cnt >= 0) {
return algo_curve_fips_cnt;
}
-
-#if defined(HAVE_EC)
algo_curve_fips_cnt = init_curves(env, 1);
-#endif /* defined(HAVE_EC) */
cnt = algo_curve_fips_cnt;
- algo_curve_fips_cnt_initialized = 1;
} else {
- if (1 == algo_curve_cnt_initialized) {
+ if (algo_curve_cnt >= 0) {
return algo_curve_cnt;
}
-
-#if defined(HAVE_EC)
algo_curve_cnt = init_curves(env, 0);
-#endif /* defined(HAVE_EC) */
- cnt = algo_curve_cnt ;
- algo_curve_cnt_initialized = 1;
+ cnt = algo_curve_cnt;
}
enif_mutex_unlock(mtx_init_curve_types);
@@ -268,12 +260,12 @@ void init_curve_types(ErlNifEnv* env) {
#endif /* defined(HAVE_EC) */
- ASSERT(curve_cnt <= sizeof(algo_curve)/sizeof(ERL_NIF_TERM));
+ ASSERT(curve_cnt <= sizeof(algo_curve[0])/sizeof(ERL_NIF_TERM));
}
-#if defined(HAVE_EC)
int init_curves(ErlNifEnv* env, int fips) {
+#if defined(HAVE_EC)
int cnt = 0;
#ifdef NID_secp160k1
@@ -622,8 +614,13 @@ int init_curves(ErlNifEnv* env, int fips) {
}
return cnt;
+#else /* if not HAVE_EC */
+ return 0;
+#endif
}
+#if defined(HAVE_EC)
+
/* Check if the curve in nid is supported by the
current cryptolib and current FIPS state.
*/
--
2.31.1