Skip to content

Commit b7220ae

Browse files
committed
wolfcrypt/src/random.c: backport changes to random.[ch] from #9595 "20251229-linuxkm-rng-wolfentropy" (450b0b4, 299ca1c, 0621615) and #9616 "20251230-persistent-drbg" (3c15be6, c1d2828, 0059f16, 1e0351a).
1 parent db29dac commit b7220ae

2 files changed

Lines changed: 184 additions & 58 deletions

File tree

wolfcrypt/src/random.c

Lines changed: 141 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,9 @@ This library contains implementation for the random number generator.
6868

6969

7070
#include <wolfssl/wolfcrypt/random.h>
71+
#ifdef WC_RNG_BANK_SUPPORT
72+
#include <wolfssl/wolfcrypt/rng_bank.h>
73+
#endif
7174
#include <wolfssl/wolfcrypt/cpuid.h>
7275

7376
#ifndef WC_NO_RNG /* if not FIPS and RNG is disabled then do not compile */
@@ -369,6 +372,12 @@ static int Hash_df(DRBG_internal* drbg, byte* out, word32 outSz, byte type,
369372
XFREE(digest, drbg->heap, DYNAMIC_TYPE_DIGEST);
370373
#endif
371374

375+
#ifdef WC_VERBOSE_RNG
376+
if (ret != 0)
377+
WOLFSSL_DEBUG_PRINTF("ERROR: %s failed with err = %d", __FUNCTION__,
378+
ret);
379+
#endif
380+
372381
return (ret == 0) ? DRBG_SUCCESS : DRBG_FAILURE;
373382
}
374383

@@ -406,6 +415,13 @@ static int Hash_DRBG_Reseed(DRBG_internal* drbg, const byte* seed, word32 seedSz
406415
#ifndef WOLFSSL_SMALL_STACK_CACHE
407416
WC_FREE_VAR_EX(newV, drbg->heap, DYNAMIC_TYPE_TMP_BUFFER);
408417
#endif
418+
419+
#ifdef WC_VERBOSE_RNG
420+
if (ret != 0)
421+
WOLFSSL_DEBUG_PRINTF("ERROR: Hash_DRBG_Reseed failed with err %d.",
422+
ret);
423+
#endif
424+
409425
return ret;
410426
}
411427

@@ -525,6 +541,19 @@ static int Hash_gen(DRBG_internal* drbg, byte* out, word32 outSz, const byte* V)
525541
WC_FREE_VAR_EX(data, drbg->heap, DYNAMIC_TYPE_TMP_BUFFER);
526542
#endif
527543

544+
#ifdef WC_VERBOSE_RNG
545+
if ((ret != DRBG_SUCCESS) && (ret != DRBG_FAILURE)) {
546+
/* Note, if we're just going to return DRBG_FAILURE to the caller, then
547+
* there's no point printing it out here because (1) the lower-level
548+
* code that was remapped to DRBG_FAILURE already got printed before the
549+
* remapping, so a DRBG_FAILURE message would just be spamming the log,
550+
* and (2) the caller will actually see the DRBG_FAILURE code, and is
551+
* free to (and probably will) log it itself.
552+
*/
553+
WOLFSSL_DEBUG_PRINTF("ERROR: Hash_gen failed with err %d.", ret);
554+
}
555+
#endif
556+
528557
return (ret == 0) ? DRBG_SUCCESS : DRBG_FAILURE;
529558
}
530559

@@ -635,6 +664,14 @@ static int Hash_DRBG_Generate(DRBG_internal* drbg, byte* out, word32 outSz)
635664
#endif
636665
}
637666

667+
#ifdef WC_VERBOSE_RNG
668+
if ((ret != DRBG_SUCCESS) && (ret != DRBG_FAILURE)) {
669+
/* see note above regarding log spam reduction */
670+
WOLFSSL_DEBUG_PRINTF("ERROR: Hash_DRBG_Generate failed with err %d.",
671+
ret);
672+
}
673+
#endif
674+
638675
return (ret == 0) ? DRBG_SUCCESS : DRBG_FAILURE;
639676
}
640677

@@ -721,7 +758,6 @@ int wc_RNG_TestSeed(const byte* seed, word32 seedSz)
721758
if (ConstantCompare(seed + seedIdx,
722759
seed + seedIdx + scratchSz,
723760
(int)scratchSz) == 0) {
724-
725761
ret = DRBG_CONT_FAILURE;
726762
}
727763
seedIdx += SEED_BLOCK_SZ;
@@ -922,6 +958,11 @@ static int _InitRng(WC_RNG* rng, byte* nonce, word32 nonceSz,
922958
else {
923959
ret = seedCb(&rng->seed, seed, seedSz);
924960
if (ret != 0) {
961+
#ifdef WC_VERBOSE_RNG
962+
WOLFSSL_DEBUG_PRINTF(
963+
"ERROR: seedCb in _InitRng() failed with err = %d",
964+
ret);
965+
#endif
925966
ret = DRBG_FAILURE;
926967
}
927968
}
@@ -931,6 +972,10 @@ static int _InitRng(WC_RNG* rng, byte* nonce, word32 nonceSz,
931972
if (ret != 0) {
932973
#if defined(DEBUG_WOLFSSL)
933974
WOLFSSL_MSG_EX("Seed generation failed... %d", ret);
975+
#elif defined(WC_VERBOSE_RNG)
976+
WOLFSSL_DEBUG_PRINTF(
977+
"ERROR: wc_GenerateSeed() in _InitRng() failed with err %d",
978+
ret);
934979
#endif
935980
ret = DRBG_FAILURE;
936981
rng->status = DRBG_FAILED;
@@ -942,7 +987,14 @@ static int _InitRng(WC_RNG* rng, byte* nonce, word32 nonceSz,
942987
if (ret != 0) {
943988
WOLFSSL_MSG_EX("wc_RNG_TestSeed failed... %d", ret);
944989
}
990+
#elif defined(WC_VERBOSE_RNG)
991+
if (ret != DRBG_SUCCESS) {
992+
WOLFSSL_DEBUG_PRINTF(
993+
"ERROR: wc_RNG_TestSeed() in _InitRng() returned err %d.",
994+
ret);
995+
}
945996
#endif
997+
946998
if (ret == DRBG_SUCCESS)
947999
ret = Hash_DRBG_Instantiate((DRBG_internal *)rng->drbg,
9481000
seed + SEED_BLOCK_SZ, seedSz - SEED_BLOCK_SZ,
@@ -1112,19 +1164,35 @@ static int PollAndReSeed(WC_RNG* rng)
11121164
else {
11131165
ret = seedCb(&rng->seed, newSeed, SEED_SZ + SEED_BLOCK_SZ);
11141166
if (ret != 0) {
1167+
#ifdef WC_VERBOSE_RNG
1168+
WOLFSSL_DEBUG_PRINTF("ERROR: seedCb() in PollAndReSeed() "
1169+
"failed with err %d", ret);
1170+
#endif
11151171
ret = DRBG_FAILURE;
11161172
}
11171173
}
11181174
#else
11191175
ret = wc_GenerateSeed(&rng->seed, newSeed,
11201176
SEED_SZ + SEED_BLOCK_SZ);
1121-
#endif
1122-
if (ret != 0)
1177+
if (ret != 0) {
1178+
#ifdef WC_VERBOSE_RNG
1179+
WOLFSSL_DEBUG_PRINTF(
1180+
"ERROR: wc_GenerateSeed() in PollAndReSeed() failed with "
1181+
"err %d", ret);
1182+
#endif
11231183
ret = DRBG_FAILURE;
1184+
}
1185+
#endif
11241186
}
1125-
if (ret == DRBG_SUCCESS)
1187+
if (ret == DRBG_SUCCESS) {
11261188
ret = wc_RNG_TestSeed(newSeed, SEED_SZ + SEED_BLOCK_SZ);
1127-
1189+
#ifdef WC_VERBOSE_RNG
1190+
if (ret != DRBG_SUCCESS)
1191+
WOLFSSL_DEBUG_PRINTF(
1192+
"ERROR: wc_RNG_TestSeed() in PollAndReSeed() returned "
1193+
"err %d.", ret);
1194+
#endif
1195+
}
11281196
if (ret == DRBG_SUCCESS)
11291197
ret = Hash_DRBG_Reseed((DRBG_internal *)rng->drbg,
11301198
newSeed + SEED_BLOCK_SZ, SEED_SZ);
@@ -1146,8 +1214,12 @@ static int PollAndReSeed(WC_RNG* rng)
11461214
#endif
11471215

11481216
/* place a generated block in output */
1217+
#ifdef WC_RNG_BANK_SUPPORT
1218+
static int wc_local_RNG_GenerateBlock(WC_RNG* rng, byte* output, word32 sz)
1219+
#else
11491220
WOLFSSL_ABI
11501221
int wc_RNG_GenerateBlock(WC_RNG* rng, byte* output, word32 sz)
1222+
#endif
11511223
{
11521224
int ret;
11531225

@@ -1194,6 +1266,11 @@ int wc_RNG_GenerateBlock(WC_RNG* rng, byte* output, word32 sz)
11941266
#ifdef CUSTOM_RAND_GENERATE_BLOCK
11951267
XMEMSET(output, 0, sz);
11961268
ret = (int)CUSTOM_RAND_GENERATE_BLOCK(output, sz);
1269+
#ifdef WC_VERBOSE_RNG
1270+
if (ret != 0)
1271+
WOLFSSL_DEBUG_PRINTF(
1272+
"ERROR: CUSTOM_RAND_GENERATE_BLOCK failed with err %d.", ret);
1273+
#endif
11971274
#else
11981275

11991276
#ifdef HAVE_HASHDRBG
@@ -1243,6 +1320,42 @@ int wc_RNG_GenerateBlock(WC_RNG* rng, byte* output, word32 sz)
12431320
return ret;
12441321
}
12451322

1323+
#ifdef WC_RNG_BANK_SUPPORT
1324+
WOLFSSL_ABI
1325+
int wc_RNG_GenerateBlock(WC_RNG* rng, byte* output, word32 sz)
1326+
{
1327+
if (rng == NULL)
1328+
return BAD_FUNC_ARG;
1329+
1330+
if (rng->status == WC_DRBG_BANKREF) {
1331+
int ret;
1332+
struct wc_rng_bank_inst *bank_inst = NULL;
1333+
1334+
ret = wc_local_rng_bank_checkout_for_bankref(rng->bankref, &bank_inst);
1335+
if (ret != 0)
1336+
return ret;
1337+
if (bank_inst == NULL)
1338+
return BAD_STATE_E;
1339+
ret = wc_local_RNG_GenerateBlock(WC_RNG_BANK_INST_TO_RNG(bank_inst),
1340+
output, sz);
1341+
{
1342+
int checkin_ret = wc_rng_bank_checkin(rng->bankref, &bank_inst);
1343+
if (checkin_ret != 0) {
1344+
#ifdef WC_VERBOSE_RNG
1345+
WOLFSSL_DEBUG_PRINTF(
1346+
"ERROR: wc_RNG_GenerateBlock() wc_rng_bank_checkin() "
1347+
"failed with err %d.", checkin_ret);
1348+
#endif
1349+
if (ret == 0)
1350+
ret = checkin_ret;
1351+
}
1352+
}
1353+
return ret;
1354+
}
1355+
else
1356+
return wc_local_RNG_GenerateBlock(rng, output, sz);
1357+
}
1358+
#endif
12461359

12471360
int wc_RNG_GenerateByte(WC_RNG* rng, byte* b)
12481361
{
@@ -1257,6 +1370,11 @@ int wc_FreeRng(WC_RNG* rng)
12571370
if (rng == NULL)
12581371
return BAD_FUNC_ARG;
12591372

1373+
#ifdef WC_RNG_BANK_SUPPORT
1374+
if (rng->status == WC_DRBG_BANKREF)
1375+
return wc_BankRef_Release(rng);
1376+
#endif /* WC_RNG_BANK_SUPPORT */
1377+
12601378
#if defined(WOLFSSL_ASYNC_CRYPT)
12611379
wolfAsync_DevCtxFree(&rng->asyncDev, WOLFSSL_ASYNC_MARKER_RNG);
12621380
#endif
@@ -2994,68 +3112,51 @@ int wc_GenerateSeed(OS_Seed* os, byte* output, word32 sz)
29943112

29953113
#elif defined(WOLFSSL_LINUXKM)
29963114

2997-
/* When registering the kernel default DRBG with a native/intrinsic entropy
2998-
* source, fallback to get_random_bytes() isn't allowed because we replace
2999-
* it with our DRBG.
3000-
*/
3001-
3002-
#if defined(HAVE_ENTROPY_MEMUSE) && \
3003-
defined(LINUXKM_LKCAPI_REGISTER_HASH_DRBG_DEFAULT)
3004-
3005-
int wc_GenerateSeed(OS_Seed* os, byte* output, word32 sz)
3006-
{
3007-
(void)os;
3008-
return wc_Entropy_Get(MAX_ENTROPY_BITS, output, sz);
3009-
}
3010-
3011-
#elif (defined(HAVE_INTEL_RDSEED) || defined(HAVE_AMD_RDSEED)) && \
3012-
defined(LINUXKM_LKCAPI_REGISTER_HASH_DRBG_DEFAULT)
3013-
3014-
int wc_GenerateSeed(OS_Seed* os, byte* output, word32 sz)
3015-
{
3016-
(void)os;
3017-
return wc_GenerateSeed_IntelRD(NULL, output, sz);
3018-
}
3019-
3020-
#else /* !((HAVE_ENTROPY_MEMUSE || HAVE_*_RDSEED) && LINUXKM_LKCAPI_REGISTER_HASH_DRBG_DEFAULT) */
3115+
#ifndef LINUXKM_LKCAPI_REGISTER_HASH_DRBG_DEFAULT
3116+
#include <linux/random.h>
3117+
#endif
30213118

3022-
#include <linux/random.h>
30233119
int wc_GenerateSeed(OS_Seed* os, byte* output, word32 sz)
30243120
{
30253121
(void)os;
30263122
int ret;
30273123

30283124
#ifdef HAVE_ENTROPY_MEMUSE
30293125
ret = wc_Entropy_Get(MAX_ENTROPY_BITS, output, sz);
3030-
if (ret == 0) {
3126+
if (ret == 0)
30313127
return 0;
3032-
}
30333128
#ifdef ENTROPY_MEMUSE_FORCE_FAILURE
3034-
/* Don't fallback to /dev/urandom. */
30353129
return ret;
30363130
#endif
30373131
#endif
30383132

30393133
#if defined(HAVE_INTEL_RDSEED) || defined(HAVE_AMD_RDSEED)
30403134
if (IS_INTEL_RDSEED(intel_flags)) {
30413135
ret = wc_GenerateSeed_IntelRD(NULL, output, sz);
3042-
#ifndef FORCE_FAILURE_RDSEED
30433136
if (ret == 0)
3044-
#endif
3045-
{
3046-
return ret;
3047-
}
3137+
return 0;
3138+
#ifdef FORCE_FAILURE_RDSEED
3139+
return ret;
3140+
#endif
30483141
}
30493142
#endif /* HAVE_INTEL_RDSEED || HAVE_AMD_RDSEED */
30503143

3144+
#ifdef LINUXKM_LKCAPI_REGISTER_HASH_DRBG_DEFAULT
3145+
#if !defined(HAVE_ENTROPY_MEMUSE) && \
3146+
!defined(HAVE_INTEL_RDSEED) && \
3147+
!defined(HAVE_AMD_RDSEED)
3148+
#error LINUXKM_LKCAPI_REGISTER_HASH_DRBG_DEFAULT requires an intrinsic entropy source.
3149+
#else
3150+
return ret;
3151+
#endif
3152+
#else
30513153
(void)ret;
30523154

30533155
get_random_bytes(output, sz);
30543156
return 0;
3157+
#endif
30553158
}
30563159

3057-
#endif /* !(HAVE_*_RDSEED && LINUXKM_LKCAPI_REGISTER_HASH_DRBG_DEFAULT) */
3058-
30593160
#elif defined(WOLFSSL_BSDKM)
30603161
#include <sys/random.h>
30613162
int wc_GenerateSeed(OS_Seed* os, byte* output, word32 sz)

0 commit comments

Comments
 (0)