Fix size-constrained ESP32 release builds

This commit is contained in:
mikecarper
2026-08-12 11:50:25 -07:00
parent c96bdd6eeb
commit a9d6398f33
2 changed files with 58 additions and 9 deletions
+32 -9
View File
@@ -8,6 +8,7 @@
#include <freertos/FreeRTOS.h>
#include <freertos/semphr.h>
#include <mbedtls/platform_util.h>
#include <stdlib.h>
#include "IdentityGeneration.h"
@@ -22,7 +23,12 @@ enum TrueRandomState : uint8_t {
TRUE_RANDOM_DISCARDED
};
uint8_t true_random_pool[TRUE_RANDOM_POOL_SIZE];
// Keep the short-lived startup pool on the heap. Classic ESP32 has a much
// smaller link-time DRAM window than its runtime heap, and retaining this
// buffer in .bss can prevent otherwise valid FULL bridge images from linking.
// The allocation happens during Arduino's early init hook and is securely
// erased and released as soon as the persisted/new identity is ready.
uint8_t* true_random_pool = NULL;
size_t true_random_offset = 0;
TrueRandomState true_random_state = TRUE_RANDOM_UNINITIALIZED;
@@ -49,11 +55,12 @@ bool tryMixESP32TrueRandom(uint8_t* dest, size_t size) {
SemaphoreHandle_t mutex = getTrueRandomMutex();
if (mutex == NULL || xSemaphoreTake(mutex, portMAX_DELAY) != pdTRUE) return false;
const bool valid_offset = true_random_offset <= sizeof(true_random_pool);
const bool valid_offset = true_random_offset <= TRUE_RANDOM_POOL_SIZE;
const size_t available = valid_offset
? sizeof(true_random_pool) - true_random_offset
? TRUE_RANDOM_POOL_SIZE - true_random_offset
: 0;
if (true_random_state != TRUE_RANDOM_READY || size > available) {
if (true_random_state != TRUE_RANDOM_READY || true_random_pool == NULL
|| size > available) {
xSemaphoreGive(mutex);
return false;
}
@@ -81,10 +88,18 @@ void initializeESP32TrueRandom() {
return;
}
true_random_pool = static_cast<uint8_t*>(malloc(TRUE_RANDOM_POOL_SIZE));
if (true_random_pool == NULL) {
true_random_state = TRUE_RANDOM_DISCARDED;
xSemaphoreGive(mutex);
esp_restart();
return;
}
// ESP-IDF guarantees true RNG output while this SAR ADC entropy source is
// enabled. Arduino's init hook below runs before variant and board setup.
bootloader_random_enable();
esp_fill_random(true_random_pool, sizeof(true_random_pool));
esp_fill_random(true_random_pool, TRUE_RANDOM_POOL_SIZE);
bootloader_random_disable();
true_random_offset = 0;
@@ -105,14 +120,22 @@ void mixESP32TrueRandom(uint8_t* dest, size_t size) {
void discardESP32TrueRandom() {
SemaphoreHandle_t mutex = getTrueRandomMutex();
if (mutex == NULL || xSemaphoreTake(mutex, portMAX_DELAY) != pdTRUE) {
mbedtls_platform_zeroize(true_random_pool, sizeof(true_random_pool));
true_random_offset = sizeof(true_random_pool);
if (true_random_pool != NULL) {
mbedtls_platform_zeroize(true_random_pool, TRUE_RANDOM_POOL_SIZE);
free(true_random_pool);
true_random_pool = NULL;
}
true_random_offset = TRUE_RANDOM_POOL_SIZE;
true_random_state = TRUE_RANDOM_DISCARDED;
return;
}
mbedtls_platform_zeroize(true_random_pool, sizeof(true_random_pool));
true_random_offset = sizeof(true_random_pool);
if (true_random_pool != NULL) {
mbedtls_platform_zeroize(true_random_pool, TRUE_RANDOM_POOL_SIZE);
free(true_random_pool);
true_random_pool = NULL;
}
true_random_offset = TRUE_RANDOM_POOL_SIZE;
true_random_state = TRUE_RANDOM_DISCARDED;
xSemaphoreGive(mutex);
}