drivers: firmware: nrf_ironside: add IRONside CPUCONF service
Add an IPC service API for booting local domain cores. Signed-off-by: Sebastian Bøe <sebastian.boe@nordicsemi.no> Signed-off-by: Jonathan Nilsen <jonathan.nilsen@nordicsemi.no>
This commit is contained in:
parent
c0c4170c42
commit
14a47cbe05
4 changed files with 147 additions and 0 deletions
|
@ -4,3 +4,5 @@
|
||||||
zephyr_library()
|
zephyr_library()
|
||||||
|
|
||||||
zephyr_library_sources_ifdef(CONFIG_NRF_IRONSIDE_CALL call.c)
|
zephyr_library_sources_ifdef(CONFIG_NRF_IRONSIDE_CALL call.c)
|
||||||
|
|
||||||
|
zephyr_library_sources_ifdef(CONFIG_NRF_IRONSIDE_CPUCONF_SERVICE cpuconf.c)
|
||||||
|
|
|
@ -26,3 +26,15 @@ config NRF_IRONSIDE_CALL_INIT_PRIORITY
|
||||||
but higher than the priority of any feature that selects NRF_IRONSIDE_CALL.
|
but higher than the priority of any feature that selects NRF_IRONSIDE_CALL.
|
||||||
|
|
||||||
endif # NRF_IRONSIDE_CALL
|
endif # NRF_IRONSIDE_CALL
|
||||||
|
|
||||||
|
menu "Nordic IRONside services"
|
||||||
|
depends on SOC_NRF54H20_IRON
|
||||||
|
|
||||||
|
config NRF_IRONSIDE_CPUCONF_SERVICE
|
||||||
|
bool "IRONside CPUCONF service"
|
||||||
|
depends on SOC_NRF54H20_CPUAPP
|
||||||
|
select NRF_IRONSIDE_CALL
|
||||||
|
help
|
||||||
|
Service used to boot local domain cores.
|
||||||
|
|
||||||
|
endmenu
|
||||||
|
|
59
drivers/firmware/nrf_ironside/cpuconf.c
Normal file
59
drivers/firmware/nrf_ironside/cpuconf.c
Normal file
|
@ -0,0 +1,59 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2025 Nordic Semiconductor ASA
|
||||||
|
* SPDX-License-Identifier: Apache-2.0
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <stdint.h>
|
||||||
|
#include <stdbool.h>
|
||||||
|
|
||||||
|
#include <zephyr/sys/util.h>
|
||||||
|
#include <zephyr/kernel.h>
|
||||||
|
|
||||||
|
#include <zephyr/drivers/firmware/nrf_ironside/call.h>
|
||||||
|
#include <zephyr/drivers/firmware/nrf_ironside/cpuconf.h>
|
||||||
|
|
||||||
|
#define CPU_PARAMS_CPU_OFFSET (0)
|
||||||
|
#define CPU_PARAMS_CPU_MASK (0xF)
|
||||||
|
#define CPU_PARAMS_WAIT_BIT BIT(4)
|
||||||
|
|
||||||
|
int ironside_cpuconf(NRF_PROCESSORID_Type cpu, const void *vector_table, bool cpu_wait,
|
||||||
|
const uint8_t *msg, size_t msg_size)
|
||||||
|
{
|
||||||
|
int err;
|
||||||
|
struct ironside_call_buf *buf;
|
||||||
|
uint8_t *buf_msg;
|
||||||
|
|
||||||
|
if (msg_size > IRONSIDE_CPUCONF_SERVICE_MSG_MAX_SIZE) {
|
||||||
|
return -IRONSIDE_CPUCONF_ERROR_MESSAGE_TOO_LARGE;
|
||||||
|
}
|
||||||
|
|
||||||
|
buf = ironside_call_alloc();
|
||||||
|
|
||||||
|
buf->id = IRONSIDE_CALL_ID_CPUCONF_V0;
|
||||||
|
|
||||||
|
buf->args[IRONSIDE_CPUCONF_SERVICE_CPU_PARAMS_IDX] =
|
||||||
|
(((uint32_t)cpu << CPU_PARAMS_CPU_OFFSET) & CPU_PARAMS_CPU_MASK) |
|
||||||
|
(cpu_wait ? CPU_PARAMS_WAIT_BIT : 0);
|
||||||
|
|
||||||
|
buf->args[IRONSIDE_CPUCONF_SERVICE_VECTOR_TABLE_IDX] = (uint32_t)vector_table;
|
||||||
|
|
||||||
|
buf_msg = (uint8_t *)&buf->args[IRONSIDE_CPUCONF_SERVICE_MSG_0];
|
||||||
|
if (msg_size > 0) {
|
||||||
|
memcpy(buf_msg, msg, msg_size);
|
||||||
|
}
|
||||||
|
if (msg_size < IRONSIDE_CPUCONF_SERVICE_MSG_MAX_SIZE) {
|
||||||
|
memset(&buf_msg[msg_size], 0, IRONSIDE_CPUCONF_SERVICE_MSG_MAX_SIZE - msg_size);
|
||||||
|
}
|
||||||
|
|
||||||
|
ironside_call_dispatch(buf);
|
||||||
|
|
||||||
|
if (buf->status == IRONSIDE_CALL_STATUS_RSP_SUCCESS) {
|
||||||
|
err = buf->args[IRONSIDE_CPUCONF_SERVICE_RETCODE_IDX];
|
||||||
|
} else {
|
||||||
|
err = buf->status;
|
||||||
|
}
|
||||||
|
|
||||||
|
ironside_call_release(buf);
|
||||||
|
|
||||||
|
return err;
|
||||||
|
}
|
74
include/zephyr/drivers/firmware/nrf_ironside/cpuconf.h
Normal file
74
include/zephyr/drivers/firmware/nrf_ironside/cpuconf.h
Normal file
|
@ -0,0 +1,74 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2025 Nordic Semiconductor ASA
|
||||||
|
* SPDX-License-Identifier: Apache-2.0
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef ZEPHYR_INCLUDE_ZEPHYR_DRIVERS_FIRMWARE_NRF_IRONSIDE_CPUCONF_H_
|
||||||
|
#define ZEPHYR_INCLUDE_ZEPHYR_DRIVERS_FIRMWARE_NRF_IRONSIDE_CPUCONF_H_
|
||||||
|
|
||||||
|
#include <stdbool.h>
|
||||||
|
#include <stddef.h>
|
||||||
|
#include <zephyr/drivers/firmware/nrf_ironside/call.h>
|
||||||
|
#include <zephyr/toolchain/common.h>
|
||||||
|
#include <nrf.h>
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @name CPUCONF service error codes.
|
||||||
|
* @{
|
||||||
|
*/
|
||||||
|
|
||||||
|
/** An invalid or unsupported processor ID was specified. */
|
||||||
|
#define IRONSIDE_CPUCONF_ERROR_WRONG_CPU (1)
|
||||||
|
/** The boot message is too large to fit in the buffer. */
|
||||||
|
#define IRONSIDE_CPUCONF_ERROR_MESSAGE_TOO_LARGE (2)
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @}
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define IRONSIDE_CALL_ID_CPUCONF_V0 2
|
||||||
|
|
||||||
|
enum {
|
||||||
|
IRONSIDE_CPUCONF_SERVICE_CPU_PARAMS_IDX,
|
||||||
|
IRONSIDE_CPUCONF_SERVICE_VECTOR_TABLE_IDX,
|
||||||
|
IRONSIDE_CPUCONF_SERVICE_MSG_0,
|
||||||
|
IRONSIDE_CPUCONF_SERVICE_MSG_1,
|
||||||
|
IRONSIDE_CPUCONF_SERVICE_MSG_2,
|
||||||
|
IRONSIDE_CPUCONF_SERVICE_MSG_3,
|
||||||
|
/* The last enum value is reserved for the number of arguments */
|
||||||
|
IRONSIDE_CPUCONF_NUM_ARGS
|
||||||
|
};
|
||||||
|
|
||||||
|
/* Maximum size of the CPUCONF message parameter. */
|
||||||
|
#define IRONSIDE_CPUCONF_SERVICE_MSG_MAX_SIZE (4 * sizeof(uint32_t))
|
||||||
|
|
||||||
|
/* IDX 0 is re-used by the error return code and the 'cpu' parameter. */
|
||||||
|
#define IRONSIDE_CPUCONF_SERVICE_RETCODE_IDX 0
|
||||||
|
|
||||||
|
BUILD_ASSERT(IRONSIDE_CPUCONF_NUM_ARGS <= NRF_IRONSIDE_CALL_NUM_ARGS);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Boot a local domain CPU
|
||||||
|
*
|
||||||
|
* @param cpu The CPU to be booted
|
||||||
|
* @param vector_table Pointer to the vector table used to boot the CPU.
|
||||||
|
* @param cpu_wait When this is true, the CPU will WAIT even if the CPU has clock.
|
||||||
|
* @param msg A message that can be placed in radiocore's boot report.
|
||||||
|
* @param msg_size Size of the message in bytes.
|
||||||
|
*
|
||||||
|
* @note cpu_wait is only intended to be enabled for debug purposes
|
||||||
|
* and it is only supported that a debugger resumes the CPU.
|
||||||
|
*
|
||||||
|
* @note the call always sends IRONSIDE_CPUCONF_SERVICE_MSG_MAX_SIZE message bytes.
|
||||||
|
* If the given msg_size is less than that, the remaining bytes are set to zero.
|
||||||
|
*
|
||||||
|
* @retval 0 on success or if the CPU has already booted.
|
||||||
|
* @retval Positive non-0 error status if reported by IRONside call.
|
||||||
|
* @retval -IRONSIDE_CPUCONF_ERROR_WRONG_CPU if cpu is unrecognized
|
||||||
|
* @retval -IRONSIDE_CPUCONF_ERROR_MESSAGE_TOO_LARGE if msg_size is greater than
|
||||||
|
* IRONSIDE_CPUCONF_SERVICE_MSG_MAX_SIZE.
|
||||||
|
*/
|
||||||
|
int ironside_cpuconf(NRF_PROCESSORID_Type cpu, const void *vector_table, bool cpu_wait,
|
||||||
|
const uint8_t *msg, size_t msg_size);
|
||||||
|
|
||||||
|
#endif /* ZEPHYR_INCLUDE_ZEPHYR_DRIVERS_FIRMWARE_NRF_IRONSIDE_CPUCONF_H_ */
|
Loading…
Add table
Add a link
Reference in a new issue