1 /*
2  * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
3  *
4  * SPDX-License-Identifier: BSD-3-Clause
5  */
6 
7 #include <stdint.h>
8 
9 #include <platform_def.h>
10 
11 #include <common/debug.h>
12 #include <drivers/arm/tzc400.h>
13 #include <drivers/st/stm32mp1_clk.h>
14 #include <dt-bindings/clock/stm32mp1-clks.h>
15 #include <lib/mmio.h>
16 
17 #define TZC_REGION_NSEC_ALL_ACCESS_RDWR \
18 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_A7_ID) | \
19 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_GPU_ID) | \
20 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_LCD_ID) | \
21 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_MDMA_ID) | \
22 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_M4_ID) | \
23 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_DMA_ID) | \
24 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_USB_HOST_ID) | \
25 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_USB_OTG_ID) | \
26 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_SDMMC_ID) | \
27 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_ETH_ID) | \
28 	TZC_REGION_ACCESS_RDWR(STM32MP1_TZC_DAP_ID)
29 
30 static unsigned int region_nb;
31 
init_tzc400_begin(unsigned int region0_attr)32 static void init_tzc400_begin(unsigned int region0_attr)
33 {
34 	tzc400_init(STM32MP1_TZC_BASE);
35 	tzc400_disable_filters();
36 
37 	/* Region 0 set to cover all DRAM at 0xC000_0000 */
38 	tzc400_configure_region0(region0_attr, 0);
39 
40 	region_nb = 1U;
41 }
42 
init_tzc400_end(unsigned int action)43 static void init_tzc400_end(unsigned int action)
44 {
45 	tzc400_set_action(action);
46 	tzc400_enable_filters();
47 }
48 
tzc400_add_region(unsigned long long region_base,unsigned long long region_top,bool sec)49 static void tzc400_add_region(unsigned long long region_base,
50 			      unsigned long long region_top, bool sec)
51 {
52 	unsigned int sec_attr;
53 	unsigned int nsaid_permissions;
54 
55 	if (sec) {
56 		sec_attr = TZC_REGION_S_RDWR;
57 		nsaid_permissions = 0;
58 	} else {
59 		sec_attr = TZC_REGION_S_NONE;
60 		nsaid_permissions = TZC_REGION_NSEC_ALL_ACCESS_RDWR;
61 	}
62 
63 	tzc400_configure_region(STM32MP1_FILTER_BIT_ALL, region_nb, region_base,
64 				region_top, sec_attr, nsaid_permissions);
65 
66 	region_nb++;
67 }
68 
69 /*******************************************************************************
70  * Initialize the TrustZone Controller. Configure Region 0 with Secure RW access
71  * and allow Non-Secure masters full access.
72  ******************************************************************************/
init_tzc400(void)73 static void init_tzc400(void)
74 {
75 	unsigned long long region_base, region_top;
76 	unsigned long long ddr_base = STM32MP_DDR_BASE;
77 	unsigned long long ddr_ns_size =
78 		(unsigned long long)stm32mp_get_ddr_ns_size();
79 	unsigned long long ddr_ns_top = ddr_base + (ddr_ns_size - 1U);
80 	unsigned long long ddr_top __unused;
81 
82 	init_tzc400_begin(TZC_REGION_S_NONE);
83 
84 	/*
85 	 * Region 1 set to cover all non-secure DRAM at 0xC000_0000. Apply the
86 	 * same configuration to all filters in the TZC.
87 	 */
88 	region_base = ddr_base;
89 	region_top = ddr_ns_top;
90 	tzc400_add_region(region_base, region_top, false);
91 
92 #ifdef AARCH32_SP_OPTEE
93 	/* Region 2 set to cover all secure DRAM. */
94 	region_base = region_top + 1U;
95 	region_top += STM32MP_DDR_S_SIZE;
96 	tzc400_add_region(region_base, region_top, true);
97 
98 	ddr_top = STM32MP_DDR_BASE + dt_get_ddr_size() - 1U;
99 	if (region_top < ddr_top) {
100 		/* Region 3 set to cover non-secure memory DRAM after BL32. */
101 		region_base = region_top + 1U;
102 		region_top = ddr_top;
103 		tzc400_add_region(region_base, region_top, false);
104 	}
105 #endif
106 
107 	/*
108 	 * Raise an interrupt (secure FIQ) if a NS device tries to access
109 	 * secure memory
110 	 */
111 	init_tzc400_end(TZC_ACTION_INT);
112 }
113 
114 /*******************************************************************************
115  * Initialize the TrustZone Controller.
116  * Early initialization create only one region with full access to secure.
117  * This setting is used before and during DDR initialization.
118  ******************************************************************************/
early_init_tzc400(void)119 static void early_init_tzc400(void)
120 {
121 	stm32mp_clk_enable(TZC1);
122 	stm32mp_clk_enable(TZC2);
123 
124 	/* Region 0 set to cover all DRAM secure at 0xC000_0000 */
125 	init_tzc400_begin(TZC_REGION_S_RDWR);
126 
127 	/* Raise an exception if a NS device tries to access secure memory */
128 	init_tzc400_end(TZC_ACTION_ERR);
129 }
130 
131 /*******************************************************************************
132  * Initialize the secure environment. At this moment only the TrustZone
133  * Controller is initialized.
134  ******************************************************************************/
stm32mp1_arch_security_setup(void)135 void stm32mp1_arch_security_setup(void)
136 {
137 	early_init_tzc400();
138 }
139 
140 /*******************************************************************************
141  * Initialize the secure environment. At this moment only the TrustZone
142  * Controller is initialized.
143  ******************************************************************************/
stm32mp1_security_setup(void)144 void stm32mp1_security_setup(void)
145 {
146 	init_tzc400();
147 }
148