IronSide SE services
The following are the services provided by IronSide SE:
IronSide SE CPUCONF service
The IronSide SE CPUCONF service enables the application core to trigger the boot of another CPU at a specified address.
Specifically, IronSide SE sets INITSVTOR of the CPUCONF instance of the processor being booted with the address provided to the IronSide call, and then writes 0x1 to CPUSTART of the CPUCONF instance of the processor being booted to start the target CPU. When CPUWAIT is enabled in the IronSide service call, the target CPU is stalled by writing 0x1 to CPUWAIT of the CPUCONF instance of the processor being booted.
This feature is intended for debugging purposes.
Note
TASKS_ERASECACHE of the CPUCONF instance of the processor being booted is not yet supported.
INITNSVTOR of the CPUCONF instance of the processor being booted will not be supported.
For details about the CPUCONF peripheral, refer to the nRF54H20 SoC datasheet.
IronSide SE update service
IronSide SE provides an update service that allows local domains to trigger the update process of IronSide SE itself.
The update service requires a release of IronSide SE or the IronSide SE Recovery image to be programmed within a valid memory range that is accessible by the application core.
The image must be stored in MRAM11 and cannot reside in MRAM10.
See Limitations and nrf_ironside/update.h for details.
After the application has invoked the service, IronSide SE will update on the next system reset. The update can be verified by checking the listed versions in the boot report on startup.
Note
Updating through the service is limited to a single image at a time. Updating both IronSide SE and IronSide SE Recovery images requires performing two rounds of the update service procedure, in which the IronSide SE Recovery image is updated first.
See the update application sample for an example on calling the service at runtime.
IronSide SE counter service
The IronSide SE counter service provides secure monotonic counters for rollback protection, version tracking, and other security-critical applications that require strictly increasing values.
The header file for this service is sdk-zephyr/soc/nordic/ironside/include/nrf_ironside/counter.h.
It provides four independent 32-bit monotonic counters (IRONSIDE_COUNTER_0 through IRONSIDE_COUNTER_3).
Each counter can only be set to a value greater than or equal to its current value, which ensures that counter values never decrease.
The counters have the following properties:
Property |
Description |
|---|---|
Monotonic |
Counter values can only increase or stay the same; they cannot decrease. |
Persistent |
Counter values are stored in secure storage and survive reboots. |
Per-boot locking |
Counters can be locked for the current boot session to prevent further modifications. |
Automatic initialization |
Counters are initialized to 0 during the first boot with an unlocked UICR. |
Operations
The Counter service provides three primary operations applicable to the counters: set, get, and lock.
Set
The ironside_counter_set() function sets a counter to a specified value.
The new value must be greater than or equal to the current counter value.
The function takes the following parameters:
counter_id- Counter identifier (IRONSIDE_COUNTER_0throughIRONSIDE_COUNTER_3).value- New counter value. It must be greater than or equal to the current value.
The function returns the following values:
0on success.-IRONSIDE_COUNTER_ERROR_INVALID_IDif the counter ID is invalid.-IRONSIDE_COUNTER_ERROR_TOO_LOWif the specified value is lower than the current value.-IRONSIDE_COUNTER_ERROR_LOCKEDif the counter is locked for this boot session.-IRONSIDE_COUNTER_ERROR_STORAGE_FAILUREif the storage operation failed.
Get
The ironside_counter_get() function retrieves the current value of a counter.
The function takes the following parameters:
counter_id- Counter identifier (IRONSIDE_COUNTER_0throughIRONSIDE_COUNTER_3).value- Pointer to store the retrieved counter value.
The function returns the following values:
0on success.-IRONSIDE_COUNTER_ERROR_INVALID_IDif the counter ID is invalid.-IRONSIDE_COUNTER_ERROR_STORAGE_FAILUREif the storage operation failed or the counter is not initialized.
Lock
The ironside_counter_lock() function locks a counter for the current boot session, which prevents any further modifications until the next reboot.
Lock states are non-persistent and are cleared on reboot.
The function takes the following parameter:
counter_id- Counter identifier (IRONSIDE_COUNTER_0throughIRONSIDE_COUNTER_3).
The function returns the following values:
0on success.-IRONSIDE_COUNTER_ERROR_INVALID_IDif the counter ID is invalid.
Usage
The Counter service is typically used for the following purposes:
Firmware version tracking - Store the current firmware version and prevent rollback to older versions.
Anti-rollback protection - Ensure that security-critical updates cannot be reverted.
Nonce generation - Generate unique, strictly increasing values for cryptographic operations.
The following example demonstrates how to use the Counter service to track firmware versions and prevent rollback:
#include <nrf_ironside/counter.h>
/* Read the current firmware version counter */
uint32_t current_version;
int err = ironside_counter_get(IRONSIDE_COUNTER_0, ¤t_version);
if (err != 0) {
/* Handle error */
}
/* Update to the new firmware version */
uint32_t new_version = 42;
err = ironside_counter_set(IRONSIDE_COUNTER_0, new_version);
if (err == -IRONSIDE_COUNTER_ERROR_TOO_LOW) {
/* Firmware rollback detected - reject update */
}
/* Lock the counter to prevent tampering during this boot session */
ironside_counter_lock(IRONSIDE_COUNTER_0);