mirror of
https://github.com/Fishwaldo/bl808_coprocessor.git
synced 2025-03-15 19:31:39 +00:00
Mechanism to foward interupts between cores
This commit is contained in:
parent
27de351177
commit
0289bd83c5
3 changed files with 116 additions and 29 deletions
|
@ -17,6 +17,10 @@ typedef enum {
|
|||
IPC_MSG_RPMSG1 = IPC_IRQ_INT_SRC_BIT3,
|
||||
IPC_MSG_RPMSG2 = IPC_IRQ_INT_SRC_BIT4,
|
||||
IPC_MSG_RPMSG3 = IPC_IRQ_INT_SRC_BIT5,
|
||||
IPC_MSG_IRQFWD1 = IPC_IRQ_INT_SRC_BIT6,
|
||||
IPC_MSG_IRQFWD2 = IPC_IRQ_INT_SRC_BIT7,
|
||||
IPC_MSG_IRQFWD3 = IPC_IRQ_INT_SRC_BIT8,
|
||||
IPC_MSG_IRQFWD4 = IPC_IRQ_INT_SRC_BIT9,
|
||||
} IPC_MSG_Type;
|
||||
|
||||
#define IPC_MSG_MASK_ALL() ( IPC_MSG_PING || \
|
||||
|
@ -59,14 +63,16 @@ typedef enum {
|
|||
|
||||
void rpmsg_task(void *unused);
|
||||
|
||||
int ipc_mask_msg(IPC_MSG_Type msg);
|
||||
int ipc_unmask_msg(IPC_MSG_Type msg);
|
||||
int ipc_send_ping(GLB_CORE_ID_Type cpu);
|
||||
int ipc_send_pong(GLB_CORE_ID_Type cpu);
|
||||
int ipc_send_rpmsg(GLB_CORE_ID_Type cpu, uint32_t vector);
|
||||
int ipc_mask_rpmsg(uint32_t vector);
|
||||
int ipc_unmask_rpmsg(uint32_t vector);
|
||||
BL_Err_Type ipc_init();
|
||||
|
||||
BL_Err_Type ipc_mask_msg(IPC_MSG_Type msg);
|
||||
BL_Err_Type ipc_unmask_msg(IPC_MSG_Type msg);
|
||||
BL_Err_Type ipc_send_ping(GLB_CORE_ID_Type cpu);
|
||||
BL_Err_Type ipc_send_pong(GLB_CORE_ID_Type cpu);
|
||||
BL_Err_Type ipc_send_rpmsg(GLB_CORE_ID_Type cpu, uint32_t vector);
|
||||
BL_Err_Type ipc_mask_rpmsg(uint32_t vector);
|
||||
BL_Err_Type ipc_unmask_rpmsg(uint32_t vector);
|
||||
BL_Err_Type ipc_forward_interupt(int irq, GLB_CORE_ID_Type targetcpu, IPC_MSG_Type msg);
|
||||
bool ipc_is_core_alive(GLB_CORE_ID_Type cpu);
|
||||
|
||||
|
||||
|
|
|
@ -14,16 +14,36 @@ typedef struct
|
|||
uint64_t m0ping;
|
||||
uint64_t d0ping;
|
||||
uint64_t lpping;
|
||||
struct irq_fwd {
|
||||
GLB_CORE_ID_Type targetcpu;
|
||||
irq_callback irq_handler;
|
||||
} irq_fwd[4];
|
||||
} ipc_status_t;
|
||||
|
||||
ipc_status_t ipc_status;
|
||||
void ipc_isr_forward_default(int irq, void *param);
|
||||
|
||||
ipc_status_t ipc_status = {
|
||||
.m0ping = 0,
|
||||
.d0ping = 0,
|
||||
.lpping = 0,
|
||||
.irq_fwd = {
|
||||
{ .targetcpu = GLB_CORE_ID_INVALID,
|
||||
.irq_handler = ipc_isr_forward_default },
|
||||
{ .targetcpu = GLB_CORE_ID_INVALID,
|
||||
.irq_handler = ipc_isr_forward_default },
|
||||
{ .targetcpu = GLB_CORE_ID_INVALID,
|
||||
.irq_handler = ipc_isr_forward_default },
|
||||
{ .targetcpu = GLB_CORE_ID_INVALID,
|
||||
.irq_handler = ipc_isr_forward_default },
|
||||
}
|
||||
};
|
||||
|
||||
struct rpmsg_lite_instance *ipc_rpmsg;
|
||||
struct rpmsg_lite_endpoint *ipc_rpmsg_default_endpoint;
|
||||
rpmsg_ns_handle ipc_rpmsg_ns;
|
||||
rpmsg_queue_handle ipc_rpmsg_queue;
|
||||
|
||||
static int ipc_send_cmd(GLB_CORE_ID_Type targetcpu, uint32_t cmd);
|
||||
static BL_Err_Type ipc_send_cmd(GLB_CORE_ID_Type targetcpu, uint32_t cmd);
|
||||
|
||||
void ipc_m0_callback(uint32_t src)
|
||||
{
|
||||
|
@ -45,6 +65,13 @@ void ipc_m0_callback(uint32_t src)
|
|||
LOG_D("IPC: Got Notify for Vector %d\r\n", ffs(src) - IPC_MSG_RPMSG0 - 1);
|
||||
env_isr(ffs(src) - IPC_MSG_RPMSG0 - 1);
|
||||
break;
|
||||
case IPC_MSG_IRQFWD1:
|
||||
case IPC_MSG_IRQFWD2:
|
||||
case IPC_MSG_IRQFWD3:
|
||||
case IPC_MSG_IRQFWD4:
|
||||
LOG_D("IPCIRQForward: Got Notify for Vector %d\r\n", src);
|
||||
ipc_status.irq_fwd[ffs(src) - IPC_MSG_IRQFWD1 -1].irq_handler(ffs(src) - IPC_MSG_IRQFWD1 -1, (void *)src);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -68,6 +95,13 @@ void ipc_d0_callback(uint32_t src)
|
|||
LOG_D("IPC: Got Notify for Vector %d\r\n", ffs(src) - IPC_MSG_RPMSG0 - 1);
|
||||
env_isr(ffs(src) - IPC_MSG_RPMSG0 - 1);
|
||||
break;
|
||||
case IPC_MSG_IRQFWD1:
|
||||
case IPC_MSG_IRQFWD2:
|
||||
case IPC_MSG_IRQFWD3:
|
||||
case IPC_MSG_IRQFWD4:
|
||||
LOG_D("IPCIRQForward: Got Notify for Vector %d\r\n", src);
|
||||
ipc_status.irq_fwd[ffs(src) - IPC_MSG_IRQFWD1 -1].irq_handler(ffs(src) - IPC_MSG_IRQFWD1 -1, (void *)src);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -89,9 +123,27 @@ void ipc_lp_callback(uint32_t src)
|
|||
case IPC_MSG_RPMSG3:
|
||||
env_isr(ffs(src) - IPC_MSG_RPMSG0 - 1);
|
||||
break;
|
||||
case IPC_MSG_IRQFWD1:
|
||||
case IPC_MSG_IRQFWD2:
|
||||
case IPC_MSG_IRQFWD3:
|
||||
case IPC_MSG_IRQFWD4:
|
||||
LOG_D("IPCIRQForward: Got Notify for Vector %d\r\n", src);
|
||||
ipc_status.irq_fwd[ffs(src) - IPC_MSG_IRQFWD1 -1].irq_handler(ffs(src) - IPC_MSG_IRQFWD1 -1, (void *)src);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void ipc_isr_forward(int irq, void *param)
|
||||
{
|
||||
IPC_MSG_Type msg = (IPC_MSG_Type)param;
|
||||
LOG_D("IPC: Forwarding IRQ %d as IPC Interupt Command %d\r\n", irq, msg);
|
||||
ipc_send_cmd(GLB_CORE_ID_D0, msg);
|
||||
}
|
||||
|
||||
void ipc_isr_forward_default(int irq, void *param) {
|
||||
LOG_D("Got Unhandled IPC IRQ Forward %d\r\n", irq);
|
||||
}
|
||||
|
||||
void ipc_rpmsg_ns_callback(uint32_t new_ept, const char *new_ept_name, uint32_t flags, void *user_data)
|
||||
{
|
||||
LOG_W("RPMSG TODO NS Callback Ran!\r\n");
|
||||
|
@ -201,14 +253,14 @@ void rpmsg_task(void *unused)
|
|||
return;
|
||||
}
|
||||
|
||||
static int ipc_send_cmd(GLB_CORE_ID_Type targetcpu, uint32_t cmd)
|
||||
static BL_Err_Type ipc_send_cmd(GLB_CORE_ID_Type targetcpu, uint32_t cmd)
|
||||
{
|
||||
CHECK_PARAM(IS_GLB_CORE_ID_TYPE(targetcpu));
|
||||
GLB_CORE_ID_Type mycpu = GLB_Get_Core_Type();
|
||||
if (mycpu == targetcpu)
|
||||
{
|
||||
LOG_W("IPC: Cannot send message %d to self\r\n", cmd);
|
||||
return 0;
|
||||
return INVALID;
|
||||
}
|
||||
/* rpmsg needs to process each command before we send another,
|
||||
so we will busy spin on the IPC interupt for the core to see when its cleared
|
||||
|
@ -218,30 +270,30 @@ static int ipc_send_cmd(GLB_CORE_ID_Type targetcpu, uint32_t cmd)
|
|||
case GLB_CORE_ID_M0:
|
||||
if (IPC_IRQ_M0_Trigger_CPUx(targetcpu, cmd, IPC_TIMEOUT) != SUCCESS)
|
||||
{
|
||||
LOG_W("IPC: Failed to send message %d to %d\r\n", cmd, targetcpu);
|
||||
return 0;
|
||||
LOG_W("IPC: Failed to send IPC %d to %d\r\n", cmd, targetcpu);
|
||||
return TIMEOUT;
|
||||
}
|
||||
break;
|
||||
case GLB_CORE_ID_D0:
|
||||
if (IPC_IRQ_D0_Trigger_CPUx(targetcpu, cmd, IPC_TIMEOUT) != SUCCESS)
|
||||
{
|
||||
LOG_W("IPC: Failed to send message %d to %d\r\n", cmd, targetcpu);
|
||||
return 0;
|
||||
LOG_W("IPC: Failed to send IPC %d to %d\r\n", cmd, targetcpu);
|
||||
return TIMEOUT;
|
||||
}
|
||||
break;
|
||||
case GLB_CORE_ID_LP:
|
||||
if (IPC_IRQ_LP_Trigger_CPUx(targetcpu, cmd, IPC_TIMEOUT) != SUCCESS)
|
||||
{
|
||||
LOG_W("IPC: Failed to send message %d to %d\r\n", cmd, targetcpu);
|
||||
return 0;
|
||||
LOG_W("IPC: Failed to send IPC %d to %d\r\n", cmd, targetcpu);
|
||||
return TIMEOUT;
|
||||
}
|
||||
break;
|
||||
case GLB_CORE_ID_MAX:
|
||||
case GLB_CORE_ID_INVALID:
|
||||
LOG_W("Unknown CPU\r\n");
|
||||
return 0;
|
||||
return INVALID;
|
||||
}
|
||||
return 1;
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
bool ipc_is_core_alive(GLB_CORE_ID_Type cpu)
|
||||
|
@ -258,44 +310,59 @@ bool ipc_is_core_alive(GLB_CORE_ID_Type cpu)
|
|||
case GLB_CORE_ID_MAX:
|
||||
case GLB_CORE_ID_INVALID:
|
||||
LOG_W("Unknown CPU\r\n");
|
||||
return 0;
|
||||
return false;
|
||||
}
|
||||
return 0;
|
||||
return false;
|
||||
}
|
||||
|
||||
int ipc_send_ping(GLB_CORE_ID_Type cpu)
|
||||
BL_Err_Type ipc_send_ping(GLB_CORE_ID_Type cpu)
|
||||
{
|
||||
return ipc_send_cmd(cpu, IPC_MSG_PING);
|
||||
}
|
||||
|
||||
int ipc_send_pong(GLB_CORE_ID_Type cpu)
|
||||
BL_Err_Type ipc_send_pong(GLB_CORE_ID_Type cpu)
|
||||
{
|
||||
return ipc_send_cmd(cpu, IPC_MSG_PONG);
|
||||
}
|
||||
|
||||
int ipc_send_rpmsg(GLB_CORE_ID_Type cpu, uint32_t cmd)
|
||||
BL_Err_Type ipc_send_rpmsg(GLB_CORE_ID_Type cpu, uint32_t cmd)
|
||||
{
|
||||
return ipc_send_cmd(cpu, (IPC_MSG_RPMSG0 + cmd));
|
||||
}
|
||||
|
||||
int ipc_mask_msg(IPC_MSG_Type msg)
|
||||
BL_Err_Type ipc_mask_msg(IPC_MSG_Type msg)
|
||||
{
|
||||
/* XXX TODO - we need a Unmask Function in the SDK to go with this */
|
||||
return 1;
|
||||
}
|
||||
|
||||
int ipc_unmask_msg(IPC_MSG_Type msg)
|
||||
BL_Err_Type ipc_unmask_msg(IPC_MSG_Type msg)
|
||||
{
|
||||
/* XXX TODO - Need to write our own Unmask Function */
|
||||
return 1;
|
||||
}
|
||||
|
||||
int ipc_mask_rpmsg(uint32_t vector)
|
||||
BL_Err_Type ipc_mask_rpmsg(uint32_t vector)
|
||||
{
|
||||
return ipc_mask_msg(IPC_MSG_RPMSG0 + vector);
|
||||
}
|
||||
|
||||
int ipc_unmask_rpmsg(uint32_t vector)
|
||||
BL_Err_Type ipc_unmask_rpmsg(uint32_t vector)
|
||||
{
|
||||
return ipc_unmask_msg(IPC_MSG_RPMSG0 + vector);
|
||||
}
|
||||
|
||||
BL_Err_Type ipc_forward_interupt(int irq, GLB_CORE_ID_Type targetcpu, IPC_MSG_Type msg)
|
||||
{
|
||||
if (bflb_irq_attach(irq, ipc_isr_forward, (void *)msg) != 0) {
|
||||
LOG_W("IPCFWD: Failed to attach IRQ %d\r\n", irq);
|
||||
}
|
||||
ipc_status.irq_fwd[(msg - IPC_MSG_IRQFWD1)].targetcpu = targetcpu;
|
||||
bflb_irq_enable(irq);
|
||||
LOG_I("IPCFWD: Forwarding IRQ %d to %d as message %d in slot %d\r\n", irq, targetcpu, msg, (msg - IPC_MSG_IRQFWD1));
|
||||
return SUCCESS;
|
||||
}
|
||||
|
||||
BL_Err_Type ipc_init() {
|
||||
return SUCCESS;
|
||||
}
|
|
@ -53,14 +53,28 @@ int main(void)
|
|||
LOG_I("Console Started\r\n");
|
||||
//pt_table_set_flash_operation(bflb_flash_erase, bflb_flash_write, bflb_flash_read);
|
||||
//pt_table_dump();
|
||||
|
||||
LOG_I("Init IPC\r\n");
|
||||
if (ipc_init() != SUCCESS) {
|
||||
LOG_W("Failed to Initialize IPC\r\n");
|
||||
}
|
||||
|
||||
LOG_I("About to Start RPMSG Task\r\n");
|
||||
if (xTaskCreate(rpmsg_task, "RPMSG_TASK", 2048, NULL, tskIDLE_PRIORITY + 1U, &rpmsg_task_handle) != pdPASS)
|
||||
{
|
||||
printf("\r\nFailed to create rpmsg task\r\n");
|
||||
return -1;
|
||||
}
|
||||
LOG_I("Forward SDH Interupt to D0\r\n");
|
||||
if (ipc_forward_interupt(SDH_IRQn, GLB_CORE_ID_D0, IPC_MSG_IRQFWD1) != SUCCESS) {
|
||||
LOG_W("Failed to Forward SDH Interupt\r\n");
|
||||
}
|
||||
#ifdef Zagitta_test
|
||||
bflb_irq_set_pending(SDH_IRQn);
|
||||
ipc_isr_forward(SDH_IRQn, IPC_MSG_IRQFWD1);
|
||||
#endif
|
||||
|
||||
LOG_I("Starting Scheduler\r\n");
|
||||
printf("main: mcause %x " PRINTF_BINARY_PATTERN_INT32 " \r\n", __get_MCAUSE(), PRINTF_BYTE_TO_BINARY_INT32(__get_MCAUSE()));
|
||||
|
||||
vTaskStartScheduler();
|
||||
/* we should never get here */
|
||||
|
|
Loading…
Add table
Reference in a new issue