Secure Boot
Status: Pre-RFC
The following overview gives a brief, high-level explanation of OpenTitan’s secure boot process. The basic guarantee of secure boot is that no unauthorized code will be executed before the boot process reaches the device owner’s code. All executed code must be cryptographically signed by either the owner of the OpenTitan device or the (trusted) entity that originally set up the device at manufacturing time (the “Silicon Creator”).
Additionally, the secure boot procedure restricts certain stages to the Silicon Creator, so that even the current device owner can’t change them. Therefore, if the device changes owners, the new owner only has to trust the Silicon Creator, not the previous owner(s).
The diagram below summarizes the specific steps involved in the secure boot process:
ROM
The first stage of secure boot is called “ROM”.
ROM is a region of read-only memory that cannot be updated at all after an OpenTitan device is manufactured.
For that reason, the ROM is kept as simple as possible; it does some minimal setup, authenticates the next stage (ROM_EXT
), and jumps there.
The ROM contains non-updateable public keys, which it uses to authenticate the ROM_EXT
signature.
These public keys correspond to what OpenTitan calls the “Silicon Creator”: the entity who was initially involved in the manufacturing of the device.
It’s important to distinguish between the unchanging Silicon Creator and the changeable “Silicon Owner”, the entity that owns the device at a given time.
On startup, hardware settings use a feature called “enhanced Physical Memory Protection” (ePMP) to ensure that only the ROM code itself is executable. For details about how the ROM configures ePMP, see Memory Protection Module. Flash and MMIO memory regions are unlocked for read/write (for signature verification and configuring peripherals) but are not executable at this stage.
On boot, the ROM code does the following:
- Initialize any additional ePMP settings beyond what is set by hardware at startup, plus initialize the C runtime and hardware peripherals (e.g. pinmux, UART).
- Load the “manifest” for
ROM_EXT
, which includes the start and end address ofROM_EXT
code, a cryptographic signature, a public key modulus, and “selector bits” for hardware information.- The manifest’s modulus field identifies which of the stored Silicon Creator keys should be used for signature verification. If there is no matching stored key, or the matching key is not suitable for the device’s lifecycle state, then the boot fails.
- There are two slots for
ROM_EXT
implementations. ROM will choose a primary boot slot and a secondary one forROM_EXT
. If the signature verification for the primary slot fails, then ROM will attempt to boot from the secondary slot. - ROM determines the primary boot slot by choosing the
ROM_EXT
implementation with the higher security version. In case the security version is equal for both implementations, ROM will pick the one with the higher major/minor version tuple.
- Read usage constraints from hardware according to the selector bits from the manifest.
- The selector bits can choose all or part of the device ID, and/or information about the state of the device. Because the selected constraints are included in the digest, this means the signer of a
ROM_EXT
image can restrict their signature to only certain devices/states.
- The selector bits can choose all or part of the device ID, and/or information about the state of the device. Because the selected constraints are included in the digest, this means the signer of a
- Compute the SHA2-256 digest of the selected usage constraints concatenated with the contents of memory between the
ROM_EXT
start and end address given in the manifest. - Check the signature from the manifest against the digest and the selected Silicon Creator public key.
- Unlock flash execution, configure ePMP so that the
ROM_EXT
region is executable, and jump to the start ofROM_EXT
.
- Unlock flash execution, configure ePMP so that the
ROM_EXT
The ROM_EXT
(“ROM extension”) stage is another region of read-only memory that is controlled by the Silicon Creator.
However, unlike the ROM, it can be updated after the device is manufactured, as long as the new version is signed by the Silicon Creator.
Like the ROM, the ROM_EXT
must check the signature of the next boot stage (this time against the Silicon Owner’s keys, rather than the Silicon Creator’s).
In addition, the ROM_EXT
initializes Silicon Creator and then Silicon Owner keys using the key manager and performs “boot services”, which are a small set of specific operations that require access to the Silicon Creator’s keys (for instance, providing an attestation of device state or transferring the device to a new owner).
These services must happen during boot and not afterwards, because after boot we don’t have access to the Silicon Creator keys.
The general procedure for the ROM_EXT
looks something like this:
- Load the manifest for BL0 (which has the same format as the
ROM_EXT
manifest described in the ROM procedure). - Read usage constraints from hardware according to the selector bits from the manifest.
- Compute the SHA2-256 digest of the selected usage constraints concatenated with the contents of BL0, as ROM does for
ROM_EXT
. - Check the signature from the manifest against the digest and a public code-signing key from the current Silicon Owner (RSA-3072 with the F4 exponent).
- Like the Silicon Creator, the Silicon Owner may have multiple public code-signing keys. How many keys exactly is configurable by the Owner.
- The number of retries in case verification fails might differ from ROM, and can differ between
ROM_EXT
implementations.
- Step the key manager device in order to obtain the Silicon Creator “root key”.
- The root key mixes secret values provisioned by the Silicon Creator at manufacturing time with information about the specific device, the device health state, and
ROM_EXT
. It will differ between devices and betweenROM_EXT
images. - The actual value of the root key is locked inside the key manager and hidden from software. The key manager starts with the Silicon Creator’s secret values (which are also hidden from all software) and advances its state to a new value with each additional piece of information.
- See the identities and root keys page for more details about the intermediate, identity, and root keys.
- The root key mixes secret values provisioned by the Silicon Creator at manufacturing time with information about the specific device, the device health state, and
- From the Silicon Creator root key, use the key manager interface to derive the Silicon Creator “identity” key (an ECDSA-P256 key used for attestation) and the Silicon Owner “intermediate key” (a new key manager state which can later be used to derive the Silicon Owner’s “identity” key).
- To create the intermediate key, the key manager starts with the Silicon Creator root key from the ROM stage, and software steps the key manager state by mixing in owner secrets (provisioned by the owner at the time they take ownership of the device) and certain BL0 configuration information.
- In between getting the Silicon Creator identity key and the Silicon Owner intermediate key, check if the boot purpose was “attestation”; if so, generate an attestation certificate for the software/hardware state, sign it with the Silicon Creator identity key, and write it to a special region of memory.
- Unlock flash execution, configure ePMP so that the Silicon Creator controlled regions of memory are not writable and the BL0 region is executable, and then jump to the start of BL0.
Once the code has jumped into the Silicon Owner code at BL0, secure boot in its simplest form is complete. The Silicon Owner may choose to extend the secure boot process with multiple boot stages of their own; this will differ between device owners, while the stages described here are guaranteed by the Silicon Creator and will be shared by all OpenTitan implementations. If any signature verification in the above process fails, or there is any kind of unexpected error, the device will fail to boot.
Silicon Creator Keys
The Silicon Creator has multiple public keys. This redundancy partially protects against the scenario in which one of the keys is compromised; any OpenTitan devices produced after the key is known to be compromised can mark the compromised key invalid, without requiring a full new ROM implementation. Devices produced before the key is known to be compromised are not protected by this strategy.
Additionally, each key is restricted to one of three “roles”, which determine in which device states the key can be used. The roles are:
dev
: development, only for devices in theDEV
lifecycle state.test
: manufacturing and testing, only for devices in theTEST_UNLOCK
andRMA
lifecycle states.prod
: production, intended forPROD
orPROD_END
lifecycle states but can be used in all states.
The following table summarizes which role can be used in which lifecycle state:
Key Type | LC_TEST | LC_RMA | LC_DEV | LC_PROD |
---|---|---|---|---|
test | X | X | ||
dev | X | |||
prod | X | X | X | X |
If the key indicated in the manifest has a role that doesn’t match the lifecycle state of the device, the boot fails. All of these keys are 3072-bit RSA public keys with exponent e=65537 (the “F4 exponent”).
Terminology Quick Reference
OpenTitan Logical Entities
- Silicon Creator: The owner of the public keys injected into the OpenTitan device at manufacturing time.
Signs the
ROM
andROM_EXT
boot stages. - Silicon Owner: The individual or group who has taken ownership of the OpenTitan device by adding their public keys during an ownership transfer.
Signs all boot stages after
ROM_EXT
.
The Silicon Creator and the Silicon Owner may be the same individual or group, but are not necessarily so. The Silicon Owner can change during the lifetime of the device, but the Silicon Creator cannot.
RISC-V Concepts:
- ePMP: Enhanced Physical Memory Protection unit: Ibex Physical Memory Protection. Can be configured to allow or prevent read (R), write (W) and/or execute (X) access to regions of memory.
Boot stages:
ROM
: Metal ROM, sometimes known as ROM or Boot ROM.ROM_EXT
: ROM Extension. Stored in flash and signed by the Silicon Creator.BL0
: Bootloader. Signed by the Silicon Owner.Kernel
: Post-bootloader code. Signed by the Silicon Owner.
Boot Policy
In order to provide a flexible boot mechanism the Boot Info page will store a
structure called the Boot Policy. The boot policy dictates the boot flow,
including storing boot attempts and successes for a given ROM_EXT
, allowing
the ROM code to decide when to mark a ROM_EXT
good or bad. The boot policy
also contains directions to ROM_EXT
about which slot it loads silicon owner
code from. TODO(gdk): Expand on policy.
Memory Layout
Memory on OpenTitan can be considered as split into three separate regions: ROM, Flash Info, and addressable flash. The addressable flash is further divided into two equally-sized regions called Flash Bank 0 and Flash Bank 1. The beginning addresses for Flash Bank 0 and Flash Bank 1 are the only fixed points of reference that the system is opinionated about, as they correspond to the beginning of each physical flash bank. It is expected that a Silicon Owner might arbitrarily reserve space at the end of each flash bank to use as additional storage.
Boot Services
Boot Services refers to the functionality stored inside of ROM
/ROM_EXT
that
can be controlled via specific messages passed between from Silicon Owner code
in retention SRAM. Since ROM/ROM_EXT
is responsible for the boot process and
is the only software on the device which can manipulate identities belonging to
the Silicon Owner, these services are required to perform actions such as
attestation of device identity and firmware update.
Entering Boot Services
Boot services are invoked by placing a request structure at the beginning of
retention SRAM and resetting the system with the cause BOOT_SERVICE_REQUEST
.
Commands
UNLOCK_OWNERSHIP
: As per Ownership Transfer’s Unlock Flow, relinquish ownership of the device.TRANSFER_OWNERSHIP
: Initiate processing of an ownership transfer blob.REFRESH_ATTESTATION
: See Attestation. Causes theROM_EXT
to regenerate the attestation chain as per the attestation command section.UPDATE_FIRMWARE
: Instructs the activeROM_EXT
to begin the firmware update process. This process allows for attempting to boot from a newROM_EXT
or silicon owner code with a programmable attempt count that must be satisfied before committing to the new code. This is done by updating the boot policy block. When a kernel wishes to update the other slot in the device it writes the firmware there and then issues anUPDATE_FIRMWARE
command to instruct the next boot ofROM_EXT
to attempt to load from that slot.
Manifest Requirements
This document does not prescribe an exact data structure for the ROM_EXT
manifest as seen by the ROM.
For that information, see the manifest format page.
However, these are the requirements that the manifest format is required to support:
- Hash scheme selection. The manifest must specify the hashing scheme that
covers the
ROM_EXT
slot. - Signature scheme selection. The manifest must specify the signature
scheme that covers the
ROM_EXT
slot. - Key derivation constants. As specified in the Identities and Root Keys document, the manifest header must include constants used to derive the next key generation.
- Header version. The version of the
ROM_EXT
. This version field is used as part of the measurements for key derivations, and can be used as a constraint for the boot policy. - Rollback protection. A generation marker that is used by
ROM_EXT
to determine if this version is bootable or is considered a rollback. - Entrypoint. The executable entrypoint for this
ROM_EXT
slot.