xref: /rk3399_ARM-atf/plat/arm/board/fvp/fvp_common.c (revision 77648689ad2627911a3aa6fd69463e8043889532)
1 /*
2  * Copyright (c) 2013-2020, ARM Limited and Contributors. All rights reserved.
3  *
4  * SPDX-License-Identifier: BSD-3-Clause
5  */
6 
7 #include <assert.h>
8 
9 #include <common/debug.h>
10 #include <drivers/arm/cci.h>
11 #include <drivers/arm/ccn.h>
12 #include <drivers/arm/gicv2.h>
13 #include <drivers/arm/sp804_delay_timer.h>
14 #include <drivers/generic_delay_timer.h>
15 #include <lib/mmio.h>
16 #include <lib/smccc.h>
17 #include <lib/xlat_tables/xlat_tables_compat.h>
18 #include <platform_def.h>
19 #include <services/arm_arch_svc.h>
20 #if SPM_MM
21 #include <services/spm_mm_partition.h>
22 #endif
23 
24 #include <plat/arm/common/arm_config.h>
25 #include <plat/arm/common/plat_arm.h>
26 #include <plat/common/platform.h>
27 
28 #include "fvp_private.h"
29 
30 /* Defines for GIC Driver build time selection */
31 #define FVP_GICV2		1
32 #define FVP_GICV3		2
33 
34 /*******************************************************************************
35  * arm_config holds the characteristics of the differences between the three FVP
36  * platforms (Base, A53_A57 & Foundation). It will be populated during cold boot
37  * at each boot stage by the primary before enabling the MMU (to allow
38  * interconnect configuration) & used thereafter. Each BL will have its own copy
39  * to allow independent operation.
40  ******************************************************************************/
41 arm_config_t arm_config;
42 
43 #define MAP_DEVICE0	MAP_REGION_FLAT(DEVICE0_BASE,			\
44 					DEVICE0_SIZE,			\
45 					MT_DEVICE | MT_RW | MT_SECURE)
46 
47 #define MAP_DEVICE1	MAP_REGION_FLAT(DEVICE1_BASE,			\
48 					DEVICE1_SIZE,			\
49 					MT_DEVICE | MT_RW | MT_SECURE)
50 
51 /*
52  * Need to be mapped with write permissions in order to set a new non-volatile
53  * counter value.
54  */
55 #define MAP_DEVICE2	MAP_REGION_FLAT(DEVICE2_BASE,			\
56 					DEVICE2_SIZE,			\
57 					MT_DEVICE | MT_RW | MT_SECURE)
58 
59 /*
60  * Table of memory regions for various BL stages to map using the MMU.
61  * This doesn't include Trusted SRAM as setup_page_tables() already takes care
62  * of mapping it.
63  *
64  * The flash needs to be mapped as writable in order to erase the FIP's Table of
65  * Contents in case of unrecoverable error (see plat_error_handler()).
66  */
67 #ifdef IMAGE_BL1
68 const mmap_region_t plat_arm_mmap[] = {
69 	ARM_MAP_SHARED_RAM,
70 	V2M_MAP_FLASH0_RW,
71 	V2M_MAP_IOFPGA,
72 	MAP_DEVICE0,
73 	MAP_DEVICE1,
74 #if TRUSTED_BOARD_BOOT
75 	/* To access the Root of Trust Public Key registers. */
76 	MAP_DEVICE2,
77 	/* Map DRAM to authenticate NS_BL2U image. */
78 	ARM_MAP_NS_DRAM1,
79 #endif
80 	{0}
81 };
82 #endif
83 #ifdef IMAGE_BL2
84 const mmap_region_t plat_arm_mmap[] = {
85 	ARM_MAP_SHARED_RAM,
86 	V2M_MAP_FLASH0_RW,
87 	V2M_MAP_IOFPGA,
88 	MAP_DEVICE0,
89 	MAP_DEVICE1,
90 	ARM_MAP_NS_DRAM1,
91 #ifdef __aarch64__
92 	ARM_MAP_DRAM2,
93 #endif
94 #if defined(SPD_spmd)
95 	ARM_MAP_TRUSTED_DRAM,
96 #endif
97 #ifdef SPD_tspd
98 	ARM_MAP_TSP_SEC_MEM,
99 #endif
100 #if TRUSTED_BOARD_BOOT
101 	/* To access the Root of Trust Public Key registers. */
102 	MAP_DEVICE2,
103 #if !BL2_AT_EL3
104 	ARM_MAP_BL1_RW,
105 #endif
106 #endif /* TRUSTED_BOARD_BOOT */
107 #if SPM_MM
108 	ARM_SP_IMAGE_MMAP,
109 #endif
110 #if ARM_BL31_IN_DRAM
111 	ARM_MAP_BL31_SEC_DRAM,
112 #endif
113 #ifdef SPD_opteed
114 	ARM_MAP_OPTEE_CORE_MEM,
115 	ARM_OPTEE_PAGEABLE_LOAD_MEM,
116 #endif
117 	{0}
118 };
119 #endif
120 #ifdef IMAGE_BL2U
121 const mmap_region_t plat_arm_mmap[] = {
122 	MAP_DEVICE0,
123 	V2M_MAP_IOFPGA,
124 	{0}
125 };
126 #endif
127 #ifdef IMAGE_BL31
128 const mmap_region_t plat_arm_mmap[] = {
129 	ARM_MAP_SHARED_RAM,
130 #if USE_DEBUGFS
131 	/* Required by devfip, can be removed if devfip is not used */
132 	V2M_MAP_FLASH0_RW,
133 #endif /* USE_DEBUGFS */
134 	ARM_MAP_EL3_TZC_DRAM,
135 	V2M_MAP_IOFPGA,
136 	MAP_DEVICE0,
137 	MAP_DEVICE1,
138 	ARM_V2M_MAP_MEM_PROTECT,
139 #if SPM_MM
140 	ARM_SPM_BUF_EL3_MMAP,
141 #endif
142 	/* Required by fconf APIs to read HW_CONFIG dtb loaded into DRAM */
143 	ARM_DTB_DRAM_NS,
144 	{0}
145 };
146 
147 #if defined(IMAGE_BL31) && SPM_MM
148 const mmap_region_t plat_arm_secure_partition_mmap[] = {
149 	V2M_MAP_IOFPGA_EL0, /* for the UART */
150 	MAP_REGION_FLAT(DEVICE0_BASE,				\
151 			DEVICE0_SIZE,				\
152 			MT_DEVICE | MT_RO | MT_SECURE | MT_USER),
153 	ARM_SP_IMAGE_MMAP,
154 	ARM_SP_IMAGE_NS_BUF_MMAP,
155 	ARM_SP_IMAGE_RW_MMAP,
156 	ARM_SPM_BUF_EL0_MMAP,
157 	{0}
158 };
159 #endif
160 #endif
161 #ifdef IMAGE_BL32
162 const mmap_region_t plat_arm_mmap[] = {
163 #ifndef __aarch64__
164 	ARM_MAP_SHARED_RAM,
165 	ARM_V2M_MAP_MEM_PROTECT,
166 #endif
167 	V2M_MAP_IOFPGA,
168 	MAP_DEVICE0,
169 	MAP_DEVICE1,
170 	/* Required by fconf APIs to read HW_CONFIG dtb loaded into DRAM */
171 	ARM_DTB_DRAM_NS,
172 	{0}
173 };
174 #endif
175 
176 ARM_CASSERT_MMAP
177 
178 #if FVP_INTERCONNECT_DRIVER != FVP_CCN
179 static const int fvp_cci400_map[] = {
180 	PLAT_FVP_CCI400_CLUS0_SL_PORT,
181 	PLAT_FVP_CCI400_CLUS1_SL_PORT,
182 };
183 
184 static const int fvp_cci5xx_map[] = {
185 	PLAT_FVP_CCI5XX_CLUS0_SL_PORT,
186 	PLAT_FVP_CCI5XX_CLUS1_SL_PORT,
187 };
188 
189 static unsigned int get_interconnect_master(void)
190 {
191 	unsigned int master;
192 	u_register_t mpidr;
193 
194 	mpidr = read_mpidr_el1();
195 	master = ((arm_config.flags & ARM_CONFIG_FVP_SHIFTED_AFF) != 0U) ?
196 		MPIDR_AFFLVL2_VAL(mpidr) : MPIDR_AFFLVL1_VAL(mpidr);
197 
198 	assert(master < FVP_CLUSTER_COUNT);
199 	return master;
200 }
201 #endif
202 
203 #if defined(IMAGE_BL31) && SPM_MM
204 /*
205  * Boot information passed to a secure partition during initialisation. Linear
206  * indices in MP information will be filled at runtime.
207  */
208 static spm_mm_mp_info_t sp_mp_info[] = {
209 	[0] = {0x80000000, 0},
210 	[1] = {0x80000001, 0},
211 	[2] = {0x80000002, 0},
212 	[3] = {0x80000003, 0},
213 	[4] = {0x80000100, 0},
214 	[5] = {0x80000101, 0},
215 	[6] = {0x80000102, 0},
216 	[7] = {0x80000103, 0},
217 };
218 
219 const spm_mm_boot_info_t plat_arm_secure_partition_boot_info = {
220 	.h.type              = PARAM_SP_IMAGE_BOOT_INFO,
221 	.h.version           = VERSION_1,
222 	.h.size              = sizeof(spm_mm_boot_info_t),
223 	.h.attr              = 0,
224 	.sp_mem_base         = ARM_SP_IMAGE_BASE,
225 	.sp_mem_limit        = ARM_SP_IMAGE_LIMIT,
226 	.sp_image_base       = ARM_SP_IMAGE_BASE,
227 	.sp_stack_base       = PLAT_SP_IMAGE_STACK_BASE,
228 	.sp_heap_base        = ARM_SP_IMAGE_HEAP_BASE,
229 	.sp_ns_comm_buf_base = PLAT_SP_IMAGE_NS_BUF_BASE,
230 	.sp_shared_buf_base  = PLAT_SPM_BUF_BASE,
231 	.sp_image_size       = ARM_SP_IMAGE_SIZE,
232 	.sp_pcpu_stack_size  = PLAT_SP_IMAGE_STACK_PCPU_SIZE,
233 	.sp_heap_size        = ARM_SP_IMAGE_HEAP_SIZE,
234 	.sp_ns_comm_buf_size = PLAT_SP_IMAGE_NS_BUF_SIZE,
235 	.sp_shared_buf_size  = PLAT_SPM_BUF_SIZE,
236 	.num_sp_mem_regions  = ARM_SP_IMAGE_NUM_MEM_REGIONS,
237 	.num_cpus            = PLATFORM_CORE_COUNT,
238 	.mp_info             = &sp_mp_info[0],
239 };
240 
241 const struct mmap_region *plat_get_secure_partition_mmap(void *cookie)
242 {
243 	return plat_arm_secure_partition_mmap;
244 }
245 
246 const struct spm_mm_boot_info *plat_get_secure_partition_boot_info(
247 		void *cookie)
248 {
249 	return &plat_arm_secure_partition_boot_info;
250 }
251 #endif
252 
253 /*******************************************************************************
254  * A single boot loader stack is expected to work on both the Foundation FVP
255  * models and the two flavours of the Base FVP models (AEMv8 & Cortex). The
256  * SYS_ID register provides a mechanism for detecting the differences between
257  * these platforms. This information is stored in a per-BL array to allow the
258  * code to take the correct path.Per BL platform configuration.
259  ******************************************************************************/
260 void __init fvp_config_setup(void)
261 {
262 	unsigned int rev, hbi, bld, arch, sys_id;
263 
264 	sys_id = mmio_read_32(V2M_SYSREGS_BASE + V2M_SYS_ID);
265 	rev = (sys_id >> V2M_SYS_ID_REV_SHIFT) & V2M_SYS_ID_REV_MASK;
266 	hbi = (sys_id >> V2M_SYS_ID_HBI_SHIFT) & V2M_SYS_ID_HBI_MASK;
267 	bld = (sys_id >> V2M_SYS_ID_BLD_SHIFT) & V2M_SYS_ID_BLD_MASK;
268 	arch = (sys_id >> V2M_SYS_ID_ARCH_SHIFT) & V2M_SYS_ID_ARCH_MASK;
269 
270 	if (arch != ARCH_MODEL) {
271 		ERROR("This firmware is for FVP models\n");
272 		panic();
273 	}
274 
275 	/*
276 	 * The build field in the SYS_ID tells which variant of the GIC
277 	 * memory is implemented by the model.
278 	 */
279 	switch (bld) {
280 	case BLD_GIC_VE_MMAP:
281 		ERROR("Legacy Versatile Express memory map for GIC peripheral"
282 				" is not supported\n");
283 		panic();
284 		break;
285 	case BLD_GIC_A53A57_MMAP:
286 		break;
287 	default:
288 		ERROR("Unsupported board build %x\n", bld);
289 		panic();
290 	}
291 
292 	/*
293 	 * The hbi field in the SYS_ID is 0x020 for the Base FVP & 0x010
294 	 * for the Foundation FVP.
295 	 */
296 	switch (hbi) {
297 	case HBI_FOUNDATION_FVP:
298 		arm_config.flags = 0;
299 
300 		/*
301 		 * Check for supported revisions of Foundation FVP
302 		 * Allow future revisions to run but emit warning diagnostic
303 		 */
304 		switch (rev) {
305 		case REV_FOUNDATION_FVP_V2_0:
306 		case REV_FOUNDATION_FVP_V2_1:
307 		case REV_FOUNDATION_FVP_v9_1:
308 		case REV_FOUNDATION_FVP_v9_6:
309 			break;
310 		default:
311 			WARN("Unrecognized Foundation FVP revision %x\n", rev);
312 			break;
313 		}
314 		break;
315 	case HBI_BASE_FVP:
316 		arm_config.flags |= (ARM_CONFIG_BASE_MMAP | ARM_CONFIG_HAS_TZC);
317 
318 		/*
319 		 * Check for supported revisions
320 		 * Allow future revisions to run but emit warning diagnostic
321 		 */
322 		switch (rev) {
323 		case REV_BASE_FVP_V0:
324 			arm_config.flags |= ARM_CONFIG_FVP_HAS_CCI400;
325 			break;
326 		case REV_BASE_FVP_REVC:
327 			arm_config.flags |= (ARM_CONFIG_FVP_HAS_SMMUV3 |
328 					ARM_CONFIG_FVP_HAS_CCI5XX);
329 			break;
330 		default:
331 			WARN("Unrecognized Base FVP revision %x\n", rev);
332 			break;
333 		}
334 		break;
335 	default:
336 		ERROR("Unsupported board HBI number 0x%x\n", hbi);
337 		panic();
338 	}
339 
340 	/*
341 	 * We assume that the presence of MT bit, and therefore shifted
342 	 * affinities, is uniform across the platform: either all CPUs, or no
343 	 * CPUs implement it.
344 	 */
345 	if ((read_mpidr_el1() & MPIDR_MT_MASK) != 0U)
346 		arm_config.flags |= ARM_CONFIG_FVP_SHIFTED_AFF;
347 }
348 
349 
350 void __init fvp_interconnect_init(void)
351 {
352 #if FVP_INTERCONNECT_DRIVER == FVP_CCN
353 	if (ccn_get_part0_id(PLAT_ARM_CCN_BASE) != CCN_502_PART0_ID) {
354 		ERROR("Unrecognized CCN variant detected. Only CCN-502 is supported");
355 		panic();
356 	}
357 
358 	plat_arm_interconnect_init();
359 #else
360 	uintptr_t cci_base = 0U;
361 	const int *cci_map = NULL;
362 	unsigned int map_size = 0U;
363 
364 	/* Initialize the right interconnect */
365 	if ((arm_config.flags & ARM_CONFIG_FVP_HAS_CCI5XX) != 0U) {
366 		cci_base = PLAT_FVP_CCI5XX_BASE;
367 		cci_map = fvp_cci5xx_map;
368 		map_size = ARRAY_SIZE(fvp_cci5xx_map);
369 	} else if ((arm_config.flags & ARM_CONFIG_FVP_HAS_CCI400) != 0U) {
370 		cci_base = PLAT_FVP_CCI400_BASE;
371 		cci_map = fvp_cci400_map;
372 		map_size = ARRAY_SIZE(fvp_cci400_map);
373 	} else {
374 		return;
375 	}
376 
377 	assert(cci_base != 0U);
378 	assert(cci_map != NULL);
379 	cci_init(cci_base, cci_map, map_size);
380 #endif
381 }
382 
383 void fvp_interconnect_enable(void)
384 {
385 #if FVP_INTERCONNECT_DRIVER == FVP_CCN
386 	plat_arm_interconnect_enter_coherency();
387 #else
388 	unsigned int master;
389 
390 	if ((arm_config.flags & (ARM_CONFIG_FVP_HAS_CCI400 |
391 				 ARM_CONFIG_FVP_HAS_CCI5XX)) != 0U) {
392 		master = get_interconnect_master();
393 		cci_enable_snoop_dvm_reqs(master);
394 	}
395 #endif
396 }
397 
398 void fvp_interconnect_disable(void)
399 {
400 #if FVP_INTERCONNECT_DRIVER == FVP_CCN
401 	plat_arm_interconnect_exit_coherency();
402 #else
403 	unsigned int master;
404 
405 	if ((arm_config.flags & (ARM_CONFIG_FVP_HAS_CCI400 |
406 				 ARM_CONFIG_FVP_HAS_CCI5XX)) != 0U) {
407 		master = get_interconnect_master();
408 		cci_disable_snoop_dvm_reqs(master);
409 	}
410 #endif
411 }
412 
413 #if TRUSTED_BOARD_BOOT
414 int plat_get_mbedtls_heap(void **heap_addr, size_t *heap_size)
415 {
416 	assert(heap_addr != NULL);
417 	assert(heap_size != NULL);
418 
419 	return arm_get_mbedtls_heap(heap_addr, heap_size);
420 }
421 #endif
422 
423 void fvp_timer_init(void)
424 {
425 #if USE_SP804_TIMER
426 	/* Enable the clock override for SP804 timer 0, which means that no
427 	 * clock dividers are applied and the raw (35MHz) clock will be used.
428 	 */
429 	mmio_write_32(V2M_SP810_BASE, FVP_SP810_CTRL_TIM0_OV);
430 
431 	/* Initialize delay timer driver using SP804 dual timer 0 */
432 	sp804_timer_init(V2M_SP804_TIMER0_BASE,
433 			SP804_TIMER_CLKMULT, SP804_TIMER_CLKDIV);
434 #else
435 	generic_delay_timer_init();
436 
437 	/* Enable System level generic timer */
438 	mmio_write_32(ARM_SYS_CNTCTL_BASE + CNTCR_OFF,
439 			CNTCR_FCREQ(0U) | CNTCR_EN);
440 #endif /* USE_SP804_TIMER */
441 }
442 
443 /*****************************************************************************
444  * plat_is_smccc_feature_available() - This function checks whether SMCCC
445  *                                     feature is availabile for platform.
446  * @fid: SMCCC function id
447  *
448  * Return SMC_ARCH_CALL_SUCCESS if SMCCC feature is available and
449  * SMC_ARCH_CALL_NOT_SUPPORTED otherwise.
450  *****************************************************************************/
451 int32_t plat_is_smccc_feature_available(u_register_t fid)
452 {
453 	switch (fid) {
454 	case SMCCC_ARCH_SOC_ID:
455 		return SMC_ARCH_CALL_SUCCESS;
456 	default:
457 		return SMC_ARCH_CALL_NOT_SUPPORTED;
458 	}
459 }
460 
461 /* Get SOC version */
462 int32_t plat_get_soc_version(void)
463 {
464 	return (int32_t)
465 		((ARM_SOC_IDENTIFICATION_CODE << ARM_SOC_IDENTIFICATION_SHIFT)
466 		 | (ARM_SOC_CONTINUATION_CODE << ARM_SOC_CONTINUATION_SHIFT)
467 		 | FVP_SOC_ID);
468 }
469 
470 /* Get SOC revision */
471 int32_t plat_get_soc_revision(void)
472 {
473 	unsigned int sys_id;
474 
475 	sys_id = mmio_read_32(V2M_SYSREGS_BASE + V2M_SYS_ID);
476 	return (int32_t)((sys_id >> V2M_SYS_ID_REV_SHIFT) &
477 			V2M_SYS_ID_REV_MASK);
478 }
479