ECDSA based Secure Boot V2 is not functional for certain input vectors on
ESP32-C5/C61/H2/P4 and on the preview targets ESP32-H4/H21. RSA based Secure
Boot V2 is the recommended scheme where the SoC supports it. This issue will be
fixed in a future hardware ECO revision; more details will be shared through the
hardware errata document.
A new hidden Kconfig option SECURE_BOOT_V2_ECDSA_INSECURE marks the affected
mass-production SoCs (ESP32-C5/C61/H2/P4). On these SoCs, when hardware Secure
Boot V2 is enabled, the ECDSA (V2) signing scheme is no longer offered by
default; it must be turned on explicitly via SECURE_BOOT_V2_FORCE_ENABLE_ECDSA
under "Allow potentially insecure options" (CONFIG_SECURE_BOOT_INSECURE). App
signing without hardware Secure Boot is not affected. Note that ESP32-C61 has no
RSA based Secure Boot V2, so it has no Secure Boot scheme enabled by default.
The preview targets ESP32-H4 and ESP32-H21 mark ECDSA Secure Boot V2 as not
supported in their SoC capabilities instead of using the option above. As
ESP32-H4 has no other Secure Boot V2 scheme, Secure Boot is disabled entirely on
it; ESP32-H21 retains RSA based Secure Boot V2.
The security documentation keeps the ECDSA Secure Boot V2 content visible and
adds a warning describing the limitation (including that ECDSA Secure Boot V2 on
ESP32-C61 is not recommended for production). CI apps that exercise ECDSA Secure
Boot V2 on the affected SoCs set CONFIG_SECURE_BOOT_V2_FORCE_ENABLE_ECDSA
accordingly.
- `bootloader_flash_execute_command_common`: whitelist the flash command
opcodes the REE actually uses; reject the rest
- `spi_flash_hal_* services`: a forged `host->driver` could hijack TEE
control flow since the HAL dispatches through it, so swap
`host->driver` to a TEE-rodata vtable around each HAL call
- Deny partition table and bootloader writes by default and permit
bootloader writes only when explicitly enabled via
`CONFIG_SPI_FLASH_DANGEROUS_WRITE_ALLOWED` option
- Protect the TEE-assigned interrupt pin configuration against REE
- Validate nested DS context pointers in start/finish_sign and bound
the result copy to the SoC max signature size
- Fix the stack usage in service dispatcher argument parsing
The bootloader subproject's full Kconfig discovery resolves CONFIG_SPIRAM=y
when the parent app has it enabled, even though esp_psram is not linked
into the bootloader (the CMake gate is
'if(NOT non_os_build) if(CONFIG_SPIRAM) idf_component_optional_requires(PRIVATE esp_psram)').
Shared sources in esp_hw_support that #include esp_psram private headers
or call esp_psram functions guarded only by '#if CONFIG_SPIRAM' then fail
to compile in the bootloader with
"fatal error: esp_private/esp_psram_extram.h: No such file or directory".
Mirror the CMake gate in source guards: every '#if CONFIG_SPIRAM' block in
a bootloader-compiled source that touches esp_psram becomes
'#if !BOOTLOADER_BUILD && CONFIG_SPIRAM'. The leaked CONFIG_SPIRAM value
in the bootloader's sdkconfig.h is then harmless because every dependent
block evaluates to false.
Sites updated:
- esp_memory_utils.c: include of esp_psram_extram.h and all
esp_psram_check_ptr_addr() call sites
- port/esp32{c5,c61,p4}/cpu_region_protect.c: include of
esp_psram_extram.h (inner SPIRAM_FETCH/RODATA/PRE_CONFIGURE blocks are
already inside outer !BOOTLOADER_BUILD guards)
Signed-off-by: Frantisek Hrbata <frantisek.hrbata@espressif.com>
The console transport read loop passed &linebuf[i] to uart_read_bytes()
before checking i < LINE_BUF_SIZE, so a line of LINE_BUF_SIZE or more
bytes without a terminator wrote one byte past the 256-byte linebuf
stack array.
Gate the read on the bounds check and reserve the final byte for the NUL
terminator (LINE_BUF_SIZE - 1), so the buffer handed to esp_console_run()
stays terminated even when an overlong line is truncated.
Closes https://github.com/espressif/esp-idf/issues/18638
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>