1 // SPDX-License-Identifier: BSD-2-Clause 2 /* 3 * Copyright 2022-2023 NXP 4 */ 5 6 #include <assert.h> 7 #include <compiler.h> 8 #include <config.h> 9 #include <console.h> 10 #include <keep.h> 11 #include <kernel/boot.h> 12 #include <kernel/linker.h> 13 #include <kernel/misc.h> 14 #include <kernel/panic.h> 15 #include <kernel/thread.h> 16 #include <mm/core_memprot.h> 17 #include <mm/core_mmu.h> 18 #include <mm/tee_mm.h> 19 #include <mm/tee_pager.h> 20 #include <platform_config.h> 21 #include <riscv.h> 22 #include <sbi.h> 23 #include <stdio.h> 24 #include <trace.h> 25 #include <util.h> 26 27 #define PADDR_INVALID ULONG_MAX 28 29 paddr_t start_addr; 30 unsigned long boot_args[4]; 31 32 uint32_t sem_cpu_sync[CFG_TEE_CORE_NB_CORE]; 33 34 void init_sec_mon(unsigned long nsec_entry __maybe_unused) 35 { 36 assert(nsec_entry == PADDR_INVALID); 37 /* Do nothing as we don't have a secure monitor */ 38 } 39 40 #ifdef CFG_RISCV_S_MODE 41 static void start_secondary_cores(void) 42 { 43 size_t i = 0; 44 size_t pos = get_core_pos(); 45 46 for (i = 0; i < CFG_TEE_CORE_NB_CORE; i++) 47 if (i != pos && IS_ENABLED(CFG_RISCV_SBI) && 48 sbi_boot_hart(i, start_addr, i)) 49 EMSG("Error starting secondary hart %zu", i); 50 } 51 #endif 52 53 static void init_runtime(void) 54 { 55 malloc_add_pool(__heap1_start, __heap1_end - __heap1_start); 56 57 IMSG_RAW("\n"); 58 } 59 60 void init_tee_runtime(void) 61 { 62 core_mmu_init_ta_ram(); 63 call_preinitcalls(); 64 call_initcalls(); 65 } 66 67 static void init_primary(unsigned long nsec_entry) 68 { 69 thread_init_core_local_stacks(); 70 71 /* 72 * Mask asynchronous exceptions before switch to the thread vector 73 * as the thread handler requires those to be masked while 74 * executing with the temporary stack. The thread subsystem also 75 * asserts that the foreign interrupts are blocked when using most of 76 * its functions. 77 */ 78 thread_set_exceptions(THREAD_EXCP_ALL); 79 80 init_runtime(); 81 thread_init_boot_thread(); 82 thread_init_primary(); 83 thread_init_per_cpu(); 84 init_sec_mon(nsec_entry); 85 } 86 87 /* May be overridden in plat-$(PLATFORM)/main.c */ 88 __weak void plat_primary_init_early(void) 89 { 90 } 91 92 /* May be overridden in plat-$(PLATFORM)/main.c */ 93 __weak void main_init_plic(void) 94 { 95 } 96 97 /* May be overridden in plat-$(PLATFORM)/main.c */ 98 __weak void main_secondary_init_plic(void) 99 { 100 } 101 102 void boot_init_primary_early(unsigned long pageable_part __unused, 103 unsigned long nsec_entry __unused) 104 { 105 unsigned long e = PADDR_INVALID; 106 107 init_primary(e); 108 } 109 110 void boot_init_primary_late(unsigned long fdt __unused, 111 unsigned long tos_fw_config __unused) 112 { 113 IMSG("OP-TEE version: %s", core_v_str); 114 if (IS_ENABLED(CFG_WARN_INSECURE)) { 115 IMSG("WARNING: This OP-TEE configuration might be insecure!"); 116 IMSG("WARNING: Please check https://optee.readthedocs.io/en/latest/architecture/porting_guidelines.html"); 117 } 118 IMSG("Primary CPU initializing"); 119 main_init_plic(); 120 init_tee_runtime(); 121 call_finalcalls(); 122 IMSG("Primary CPU initialized"); 123 124 #ifdef CFG_RISCV_S_MODE 125 start_secondary_cores(); 126 #endif 127 } 128 129 static void init_secondary_helper(unsigned long nsec_entry) 130 { 131 size_t pos = get_core_pos(); 132 133 IMSG("Secondary CPU %zu initializing", pos); 134 135 /* 136 * Mask asynchronous exceptions before switch to the thread vector 137 * as the thread handler requires those to be masked while 138 * executing with the temporary stack. The thread subsystem also 139 * asserts that the foreign interrupts are blocked when using most of 140 * its functions. 141 */ 142 thread_set_exceptions(THREAD_EXCP_ALL); 143 144 thread_init_per_cpu(); 145 init_sec_mon(nsec_entry); 146 main_secondary_init_plic(); 147 148 IMSG("Secondary CPU %zu initialized", pos); 149 } 150 151 void boot_init_secondary(unsigned long nsec_entry __unused) 152 { 153 init_secondary_helper(PADDR_INVALID); 154 } 155