1 /* 2 * SPDX-License-Identifier: BSD-3-Clause 3 * SPDX-FileCopyrightText: Copyright The TrustedFirmware-M Contributors 4 * 5 */ 6 7 /* FIXME: This shouldn't be required when TFM_PLAT_SPECIFIC_MULTI_CORE_COMM is 8 * enabled. 9 */ 10 11 #include "tfm_ns_mailbox.h" 12 #include "platform_multicore.h" 13 #include "region.h" 14 15 #include "pico/multicore.h" 16 #include "hardware/irq.h" 17 #include "hardware/structs/scb.h" 18 #include "hardware/structs/sio.h" 19 20 #include "tfm_hal_device_header.h" 21 #include "uart_stdout.h" 22 #include "Driver_Common.h" 23 tfm_ns_platform_init(void)24int32_t tfm_ns_platform_init(void) 25 { 26 if(sio_hw->cpuid == 0) { 27 __enable_irq(); 28 } else { 29 /* Core1 */ 30 __enable_irq(); 31 stdio_init(); 32 } 33 34 return ARM_DRIVER_OK; 35 } 36 37 /* Platform specific inter-processor communication interrupt handler. */ SIO_IRQ_FIFO_NS_IRQHandler(void)38void SIO_IRQ_FIFO_NS_IRQHandler(void) 39 { 40 uint32_t msg; 41 if(multicore_fifo_rvalid()) 42 { 43 msg = multicore_fifo_pop_blocking(); 44 if (msg == NOTIFY_FROM_CORE0) { 45 /* Handle all the pending replies */ 46 tfm_ns_mailbox_wake_reply_owner_isr(); 47 } 48 } 49 } 50 tfm_ns_mailbox_hal_init(struct ns_mailbox_queue_t * queue)51int32_t tfm_ns_mailbox_hal_init(struct ns_mailbox_queue_t *queue) 52 { 53 uint32_t stage; 54 55 if(sio_hw->cpuid == 0) { 56 return MAILBOX_SUCCESS; 57 } 58 59 if (!queue) { 60 return MAILBOX_INVAL_PARAMS; 61 } 62 63 NVIC_SetVector(SIO_IRQ_FIFO_NS_IRQn, (uint32_t) SIO_IRQ_FIFO_NS_IRQHandler); 64 65 /* 66 * Wait until SPE mailbox library is ready to receive NSPE mailbox queue 67 * address. 68 */ 69 while (1) { 70 stage = multicore_fifo_pop_blocking(); 71 if (stage == NS_MAILBOX_INIT) { 72 break; 73 } 74 } 75 76 /* Send out the address */ 77 struct mailbox_init_t ns_init; 78 ns_init.status = &queue->status; 79 ns_init.slot_count = NUM_MAILBOX_QUEUE_SLOT; 80 ns_init.slots = &queue->slots[0]; 81 multicore_fifo_push_blocking((uint32_t) &ns_init); 82 83 /* Wait until SPE mailbox service is ready */ 84 while (1) { 85 stage = multicore_fifo_pop_blocking(); 86 if (stage == S_MAILBOX_READY) { 87 break; 88 } 89 } 90 91 NVIC_EnableIRQ(SIO_IRQ_FIFO_NS_IRQn); 92 93 return MAILBOX_SUCCESS; 94 } 95 tfm_ns_mailbox_hal_notify_peer(void)96int32_t tfm_ns_mailbox_hal_notify_peer(void) 97 { 98 multicore_fifo_push_blocking(NOTIFY_FROM_CORE1); 99 return 0; 100 } 101 tfm_ns_mailbox_hal_enter_critical(void)102void tfm_ns_mailbox_hal_enter_critical(void) 103 { 104 /* Reading a spinlock register attempts to claim it, returning nonzero 105 * if the claim was successful and 0 if unsuccessful */ 106 while(!*MAILBOX_SPINLOCK); 107 return; 108 } 109 tfm_ns_mailbox_hal_exit_critical(void)110void tfm_ns_mailbox_hal_exit_critical(void) 111 { 112 /* Writing to a spinlock register releases it */ 113 *MAILBOX_SPINLOCK = 0x1u; 114 return; 115 } 116 tfm_ns_mailbox_hal_enter_critical_isr(void)117void tfm_ns_mailbox_hal_enter_critical_isr(void) 118 { 119 /* Reading a spinlock register attempts to claim it, returning nonzero 120 * if the claim was successful and 0 if unsuccessful */ 121 while(!*MAILBOX_SPINLOCK); 122 return; 123 } 124 tfm_ns_mailbox_hal_exit_critical_isr(void)125void tfm_ns_mailbox_hal_exit_critical_isr(void) 126 { 127 /* Writing to a spinlock register releases it */ 128 *MAILBOX_SPINLOCK = 0x1u; 129 return; 130 } 131 132 extern void runtime_init(void); 133 extern int main(void); 134 extern uint32_t __StackOneTop; 135 extern uint32_t __Vectors_Start__; 136 core1_ns_entry(void)137void __attribute__((section(".core1_ns_entry"), used, naked)) core1_ns_entry(void) 138 { 139 scb_hw->vtor = (uintptr_t) &__Vectors_Start__; 140 __set_MSP((uint32_t)(&__StackOneTop)); 141 __set_PSP((uint32_t)(&__StackOneTop)); 142 runtime_init(); 143 main(); 144 } 145 146 #include "stdio.h" tfm_platform_ns_wait_for_s_cpu_ready(void)147int32_t tfm_platform_ns_wait_for_s_cpu_ready(void) 148 { 149 if(sio_hw->cpuid == 1) { 150 /* Core1 */ 151 multicore_fifo_push_blocking(CORE1_NS_READY); 152 } 153 return 0; 154 } 155