You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
P0: release builds can reach the development trust anchor, and nothing structural stops them #120
The release path can reach the development trust anchor, and after #116 that anchor works — its private half is printed in RFC 8032. Nothing structural stops it being compiled into the firmware release.yml publishes, and today it is.
Verified
EBLDR_PRODUCTION_KEY appears nowhere except inside core/keystore.c: there is no CMake option for it and no build sets it. Every firmware job in .github/workflows/release.yml (stm32f4, stm32h7, nrf52, rpi4, riscv64_virt, esp32, esp32c3, x86_64_efi) configures with only -DEBLDR_BOARD=… -DCMAKE_BUILD_TYPE=Release, so every published artifact compiles the #ifndef EBLDR_PRODUCTION_KEY branch.
No board under boards/ implements otp_read or otp_write (grep -rl otp_read boards/ is empty), so eos_keystore_init() finds no OTP on every one of them, fills slot 0 from default_dev_key, and sets ks->source = EOS_KEY_SOURCE_COMPILED. Blast radius: all eight release boards.
The sole guard is a compile-time #warning, which fails nothing and is invisible in a release log.
The #ifdef EBLDR_PRODUCTION_KEY branch does not build: it declares extern const uint8_t ebldr_production_key[] and nothing in the tree defines, generates or documents that symbol. The comment at core/keystore.c:25 describes this as settled ("Production builds set EBLDR_PRODUCTION_KEY, which replaces it").
.ai/security.md: "Test keys and development keys must be structurally incapable of signing a release artifact. Check that the release path cannot reach them." It reaches them.
Required
A real EBLDR_PRODUCTION_KEY CMake option that generates ebldr_production_key[] from a supplied public key, so the production branch compiles.
A configure-time refusal when a Release build for a real board carries no production anchor (with an explicit, named opt-out for bring-up).
release.yml passes the anchor to every firmware job, and refuses an artifact that embeds the development anchor bytes.
The keystore comment and docs/key_lifecycle.md describe what actually exists.
Found during review of #116 (P0 finding). Pre-existing; #116 did not create it but makes it live.
Activity
test(keystore): compare the anchor against the generated fixture key,…
test(keystore): compare the anchor against the generated fixture key,…
test(keystore): compare the anchor against the generated fixture key,…