xref: /optee_os/core/arch/arm/plat-stm32mp2/main.c (revision fc9ea0db8ddf8150754aac716691616c7e3f404a)
1 // SPDX-License-Identifier: BSD-2-Clause
2 /*
3  * Copyright (c) 2023, STMicroelectronics
4  */
5 
6 #include <config.h>
7 #include <console.h>
8 #include <drivers/gic.h>
9 #include <drivers/stm32_rif.h>
10 #include <drivers/stm32_uart.h>
11 #include <initcall.h>
12 #include <kernel/boot.h>
13 #include <kernel/dt.h>
14 #include <kernel/interrupt.h>
15 #include <kernel/misc.h>
16 #include <kernel/spinlock.h>
17 #include <mm/core_memprot.h>
18 #include <platform_config.h>
19 #include <stm32_util.h>
20 #include <trace.h>
21 
22 register_phys_mem_pgdir(MEM_AREA_IO_NSEC, APB1_BASE, APB1_SIZE);
23 
24 register_phys_mem_pgdir(MEM_AREA_IO_SEC, APB1_BASE, APB1_SIZE);
25 register_phys_mem_pgdir(MEM_AREA_IO_SEC, APB2_BASE, APB2_SIZE);
26 register_phys_mem_pgdir(MEM_AREA_IO_SEC, APB3_BASE, APB3_SIZE);
27 register_phys_mem_pgdir(MEM_AREA_IO_SEC, APB4_BASE, APB4_SIZE);
28 register_phys_mem_pgdir(MEM_AREA_IO_SEC, AHB2_BASE, AHB2_SIZE);
29 register_phys_mem_pgdir(MEM_AREA_IO_SEC, AHB3_BASE, AHB3_SIZE);
30 register_phys_mem_pgdir(MEM_AREA_IO_SEC, AHB4_BASE, AHB4_SIZE);
31 register_phys_mem_pgdir(MEM_AREA_IO_SEC, AHB5_BASE, AHB5_SIZE);
32 register_phys_mem_pgdir(MEM_AREA_IO_SEC, SAPB_BASE, SAPB_SIZE);
33 register_phys_mem_pgdir(MEM_AREA_IO_SEC, SAHB_BASE, SAHB_SIZE);
34 
35 register_phys_mem_pgdir(MEM_AREA_IO_SEC, GIC_BASE, GIC_SIZE);
36 
37 #define _ID2STR(id)		(#id)
38 #define ID2STR(id)		_ID2STR(id)
39 
40 static TEE_Result platform_banner(void)
41 {
42 	IMSG("Platform stm32mp2: flavor %s - DT %s", ID2STR(PLATFORM_FLAVOR),
43 	     ID2STR(CFG_EMBED_DTB_SOURCE_FILE));
44 
45 	return TEE_SUCCESS;
46 }
47 
48 service_init(platform_banner);
49 
50 /*
51  * Console
52  *
53  * CFG_STM32_EARLY_CONSOLE_UART specifies the ID of the UART used for
54  * trace console. Value 0 disables the early console.
55  *
56  * We cannot use the generic serial_console support since probing
57  * the console requires the platform clock driver to be already
58  * up and ready which is done only once service_init are completed.
59  */
60 static struct stm32_uart_pdata console_data;
61 
62 void plat_console_init(void)
63 {
64 #ifdef CFG_STM32_UART
65 	/* Early console initialization before MMU setup */
66 	struct uart {
67 		paddr_t pa;
68 		bool secure;
69 	} uarts[] = {
70 		[0] = { .pa = 0 },
71 		[1] = { .pa = USART1_BASE, .secure = true, },
72 		[2] = { .pa = USART2_BASE, .secure = false, },
73 		[3] = { .pa = USART3_BASE, .secure = false, },
74 		[4] = { .pa = UART4_BASE, .secure = false, },
75 		[5] = { .pa = UART5_BASE, .secure = false, },
76 		[6] = { .pa = USART6_BASE, .secure = false, },
77 		[7] = { .pa = UART7_BASE, .secure = false, },
78 		[8] = { .pa = UART8_BASE, .secure = false, },
79 		[9] = { .pa = UART9_BASE, .secure = false, },
80 	};
81 
82 	static_assert(ARRAY_SIZE(uarts) > CFG_STM32_EARLY_CONSOLE_UART);
83 
84 	if (!uarts[CFG_STM32_EARLY_CONSOLE_UART].pa)
85 		return;
86 
87 	/* No clock yet bound to the UART console */
88 	console_data.clock = NULL;
89 	console_data.secure = uarts[CFG_STM32_EARLY_CONSOLE_UART].secure;
90 	stm32_uart_init(&console_data, uarts[CFG_STM32_EARLY_CONSOLE_UART].pa);
91 	register_serial_console(&console_data.chip);
92 
93 	IMSG("Early console on UART#%u", CFG_STM32_EARLY_CONSOLE_UART);
94 #endif
95 }
96 
97 #ifdef CFG_STM32_UART
98 static TEE_Result init_console_from_dt(void)
99 {
100 	struct stm32_uart_pdata *pd = NULL;
101 	void *fdt = NULL;
102 	int node = 0;
103 	TEE_Result res = TEE_ERROR_GENERIC;
104 
105 	fdt = get_embedded_dt();
106 	res = get_console_node_from_dt(fdt, &node, NULL, NULL);
107 	if (res == TEE_ERROR_ITEM_NOT_FOUND) {
108 		fdt = get_external_dt();
109 		res = get_console_node_from_dt(fdt, &node, NULL, NULL);
110 		if (res == TEE_ERROR_ITEM_NOT_FOUND)
111 			return TEE_SUCCESS;
112 		if (res != TEE_SUCCESS)
113 			return res;
114 	}
115 
116 	pd = stm32_uart_init_from_dt_node(fdt, node);
117 	if (!pd) {
118 		IMSG("DTB disables console");
119 		register_serial_console(NULL);
120 		return TEE_SUCCESS;
121 	}
122 
123 	/* Replace early console with the new one */
124 	console_flush();
125 	console_data = *pd;
126 	register_serial_console(&console_data.chip);
127 	IMSG("DTB enables console (%ssecure)", pd->secure ? "" : "non-");
128 	free(pd);
129 
130 	return TEE_SUCCESS;
131 }
132 
133 /* Probe console from DT once clock inits (service init level) are completed */
134 service_init_late(init_console_from_dt);
135 #endif /*STM32_UART*/
136 
137 vaddr_t stm32_rcc_base(void)
138 {
139 	static struct io_pa_va base = { .pa = RCC_BASE };
140 
141 	return io_pa_or_va_secure(&base, 1);
142 }
143 
144 void boot_primary_init_intc(void)
145 {
146 	gic_init(GIC_BASE + GICC_OFFSET, GIC_BASE + GICD_OFFSET);
147 }
148 
149 void boot_secondary_init_intc(void)
150 {
151 	gic_init_per_cpu();
152 }
153 
154 #ifdef CFG_STM32_RIF
155 void stm32_rif_access_violation_action(void)
156 {
157 }
158 #endif /* CFG_STM32_RIF */
159 
160 bool stm32mp_allow_probe_shared_device(const void *fdt, int node)
161 {
162 	static int uart_console_node = -1;
163 	static bool once;
164 
165 	if (!once) {
166 		get_console_node_from_dt((void *)fdt, &uart_console_node,
167 					 NULL, NULL);
168 		once = true;
169 	}
170 
171 	/* Allow OP-TEE console to be shared with non-secure world */
172 	if (node == uart_console_node)
173 		return true;
174 
175 	return false;
176 }
177