xref: /rk3399_ARM-atf/plat/socionext/uniphier/uniphier_io_storage.c (revision 61f72a34250d063da67f4fc2b0eb8c3fda3376be)
1 /*
2  * Copyright (c) 2017, ARM Limited and Contributors. All rights reserved.
3  *
4  * SPDX-License-Identifier: BSD-3-Clause
5  */
6 
7 #include <assert.h>
8 #include <errno.h>
9 #include <firmware_image_package.h>
10 #include <io/io_block.h>
11 #include <io/io_driver.h>
12 #include <io/io_fip.h>
13 #include <io/io_memmap.h>
14 #include <platform_def.h>
15 #include <types.h>
16 #include <utils_def.h>
17 #include <xlat_tables_v2.h>
18 
19 #include "uniphier.h"
20 
21 #define UNIPHIER_ROM_REGION_BASE	0x00000000ULL
22 #define UNIPHIER_ROM_REGION_SIZE	0x10000000ULL
23 
24 #define UNIPHIER_OCM_REGION_BASE	0x30000000ULL
25 #define UNIPHIER_OCM_REGION_SIZE	0x00040000ULL
26 
27 static const io_dev_connector_t *uniphier_fip_dev_con;
28 static uintptr_t uniphier_fip_dev_handle;
29 
30 static const io_dev_connector_t *uniphier_backend_dev_con;
31 static uintptr_t uniphier_backend_dev_handle;
32 
33 static io_block_spec_t uniphier_fip_spec = {
34 	/* .offset will be set by the io_setup func */
35 	.length = 0x00200000,
36 };
37 
38 static const io_uuid_spec_t uniphier_bl2_spec = {
39 	.uuid = UUID_TRUSTED_BOOT_FIRMWARE_BL2,
40 };
41 
42 static const io_uuid_spec_t uniphier_scp_spec = {
43 	.uuid = UUID_SCP_FIRMWARE_SCP_BL2,
44 };
45 
46 static const io_uuid_spec_t uniphier_bl31_spec = {
47 	.uuid = UUID_EL3_RUNTIME_FIRMWARE_BL31,
48 };
49 
50 static const io_uuid_spec_t uniphier_bl32_spec = {
51 	.uuid = UUID_SECURE_PAYLOAD_BL32,
52 };
53 
54 static const io_uuid_spec_t uniphier_bl33_spec = {
55 	.uuid = UUID_NON_TRUSTED_FIRMWARE_BL33,
56 };
57 
58 #if TRUSTED_BOARD_BOOT
59 static const io_uuid_spec_t uniphier_tb_fw_cert_spec = {
60 	.uuid = UUID_TRUSTED_BOOT_FW_CERT,
61 };
62 
63 static const io_uuid_spec_t uniphier_trusted_key_cert_spec = {
64 	.uuid = UUID_TRUSTED_KEY_CERT,
65 };
66 
67 static const io_uuid_spec_t uniphier_scp_fw_key_cert_spec = {
68 	.uuid = UUID_SCP_FW_KEY_CERT,
69 };
70 
71 static const io_uuid_spec_t uniphier_soc_fw_key_cert_spec = {
72 	.uuid = UUID_SOC_FW_KEY_CERT,
73 };
74 
75 static const io_uuid_spec_t uniphier_tos_fw_key_cert_spec = {
76 	.uuid = UUID_TRUSTED_OS_FW_KEY_CERT,
77 };
78 
79 static const io_uuid_spec_t uniphier_nt_fw_key_cert_spec = {
80 	.uuid = UUID_NON_TRUSTED_FW_KEY_CERT,
81 };
82 
83 static const io_uuid_spec_t uniphier_scp_fw_cert_spec = {
84 	.uuid = UUID_SCP_FW_CONTENT_CERT,
85 };
86 
87 static const io_uuid_spec_t uniphier_soc_fw_cert_spec = {
88 	.uuid = UUID_SOC_FW_CONTENT_CERT,
89 };
90 
91 static const io_uuid_spec_t uniphier_tos_fw_cert_spec = {
92 	.uuid = UUID_TRUSTED_OS_FW_CONTENT_CERT,
93 };
94 
95 static const io_uuid_spec_t uniphier_nt_fw_cert_spec = {
96 	.uuid = UUID_NON_TRUSTED_FW_CONTENT_CERT,
97 };
98 #endif /* TRUSTED_BOARD_BOOT */
99 
100 struct uniphier_io_policy {
101 	uintptr_t *dev_handle;
102 	uintptr_t image_spec;
103 	uintptr_t init_params;
104 };
105 
106 static const struct uniphier_io_policy uniphier_io_policies[] = {
107 	[FIP_IMAGE_ID] = {
108 		.dev_handle = &uniphier_backend_dev_handle,
109 		.image_spec = (uintptr_t)&uniphier_fip_spec,
110 	},
111 	[BL2_IMAGE_ID] = {
112 		.dev_handle = &uniphier_fip_dev_handle,
113 		.image_spec = (uintptr_t)&uniphier_bl2_spec,
114 		.init_params = FIP_IMAGE_ID,
115 	},
116 	[SCP_BL2_IMAGE_ID] = {
117 		.dev_handle = &uniphier_fip_dev_handle,
118 		.image_spec = (uintptr_t)&uniphier_scp_spec,
119 		.init_params = FIP_IMAGE_ID,
120 	},
121 	[BL31_IMAGE_ID] = {
122 		.dev_handle = &uniphier_fip_dev_handle,
123 		.image_spec = (uintptr_t)&uniphier_bl31_spec,
124 		.init_params = FIP_IMAGE_ID,
125 	},
126 	[BL32_IMAGE_ID] = {
127 		.dev_handle = &uniphier_fip_dev_handle,
128 		.image_spec = (uintptr_t)&uniphier_bl32_spec,
129 		.init_params = FIP_IMAGE_ID,
130 	},
131 	[BL33_IMAGE_ID] = {
132 		.dev_handle = &uniphier_fip_dev_handle,
133 		.image_spec = (uintptr_t)&uniphier_bl33_spec,
134 		.init_params = FIP_IMAGE_ID,
135 	},
136 #if TRUSTED_BOARD_BOOT
137 	[TRUSTED_BOOT_FW_CERT_ID] = {
138 		.dev_handle = &uniphier_fip_dev_handle,
139 		.image_spec = (uintptr_t)&uniphier_tb_fw_cert_spec,
140 		.init_params = FIP_IMAGE_ID,
141 	},
142 	[TRUSTED_KEY_CERT_ID] = {
143 		.dev_handle = &uniphier_fip_dev_handle,
144 		.image_spec = (uintptr_t)&uniphier_trusted_key_cert_spec,
145 		.init_params = FIP_IMAGE_ID,
146 	},
147 	[SCP_FW_KEY_CERT_ID] = {
148 		.dev_handle = &uniphier_fip_dev_handle,
149 		.image_spec = (uintptr_t)&uniphier_scp_fw_key_cert_spec,
150 		.init_params = FIP_IMAGE_ID,
151 	},
152 	[SOC_FW_KEY_CERT_ID] = {
153 		.dev_handle = &uniphier_fip_dev_handle,
154 		.image_spec = (uintptr_t)&uniphier_soc_fw_key_cert_spec,
155 		.init_params = FIP_IMAGE_ID,
156 	},
157 	[TRUSTED_OS_FW_KEY_CERT_ID] = {
158 		.dev_handle = &uniphier_fip_dev_handle,
159 		.image_spec = (uintptr_t)&uniphier_tos_fw_key_cert_spec,
160 		.init_params = FIP_IMAGE_ID,
161 	},
162 	[NON_TRUSTED_FW_KEY_CERT_ID] = {
163 		.dev_handle = &uniphier_fip_dev_handle,
164 		.image_spec = (uintptr_t)&uniphier_nt_fw_key_cert_spec,
165 		.init_params = FIP_IMAGE_ID,
166 	},
167 	[SCP_FW_CONTENT_CERT_ID] = {
168 		.dev_handle = &uniphier_fip_dev_handle,
169 		.image_spec = (uintptr_t)&uniphier_scp_fw_cert_spec,
170 		.init_params = FIP_IMAGE_ID,
171 	},
172 	[SOC_FW_CONTENT_CERT_ID] = {
173 		.dev_handle = &uniphier_fip_dev_handle,
174 		.image_spec = (uintptr_t)&uniphier_soc_fw_cert_spec,
175 		.init_params = FIP_IMAGE_ID,
176 	},
177 	[TRUSTED_OS_FW_CONTENT_CERT_ID] = {
178 		.dev_handle = &uniphier_fip_dev_handle,
179 		.image_spec = (uintptr_t)&uniphier_tos_fw_cert_spec,
180 		.init_params = FIP_IMAGE_ID,
181 	},
182 	[NON_TRUSTED_FW_CONTENT_CERT_ID] = {
183 		.dev_handle = &uniphier_fip_dev_handle,
184 		.image_spec = (uintptr_t)&uniphier_nt_fw_cert_spec,
185 		.init_params = FIP_IMAGE_ID,
186 	},
187 #endif
188 };
189 
190 static int uniphier_io_block_setup(size_t fip_offset, uintptr_t block_dev_spec)
191 {
192 	int ret;
193 
194 	uniphier_fip_spec.offset = fip_offset;
195 
196 	ret = register_io_dev_block(&uniphier_backend_dev_con);
197 	if (ret)
198 		return ret;
199 
200 	return io_dev_open(uniphier_backend_dev_con, block_dev_spec,
201 			   &uniphier_backend_dev_handle);
202 }
203 
204 static int uniphier_io_memmap_setup(size_t fip_offset)
205 {
206 	int ret;
207 
208 	uniphier_fip_spec.offset = fip_offset;
209 
210 	ret = mmap_add_dynamic_region(fip_offset, fip_offset,
211 				      uniphier_fip_spec.length,
212 				      MT_RO_DATA | MT_SECURE);
213 	if (ret)
214 		return ret;
215 
216 	ret = register_io_dev_memmap(&uniphier_backend_dev_con);
217 	if (ret)
218 		return ret;
219 
220 	return io_dev_open(uniphier_backend_dev_con, 0,
221 			   &uniphier_backend_dev_handle);
222 }
223 
224 static int uniphier_io_fip_setup(void)
225 {
226 	int ret;
227 
228 	ret = register_io_dev_fip(&uniphier_fip_dev_con);
229 	if (ret)
230 		return ret;
231 
232 	return io_dev_open(uniphier_fip_dev_con, 0, &uniphier_fip_dev_handle);
233 }
234 
235 static int uniphier_io_emmc_setup(unsigned int soc_id)
236 {
237 	uintptr_t block_dev_spec;
238 	int ret;
239 
240 	ret = uniphier_emmc_init(&block_dev_spec);
241 	if (ret)
242 		return ret;
243 
244 	return uniphier_io_block_setup(0x20000, block_dev_spec);
245 }
246 
247 static int uniphier_io_nand_setup(unsigned int soc_id)
248 {
249 	uintptr_t block_dev_spec;
250 	int ret;
251 
252 	ret = uniphier_nand_init(&block_dev_spec);
253 	if (ret)
254 		return ret;
255 
256 	return uniphier_io_block_setup(0x20000, block_dev_spec);
257 }
258 
259 static int uniphier_io_nor_setup(unsigned int soc_id)
260 {
261 	return uniphier_io_memmap_setup(0x70000);
262 }
263 
264 static int uniphier_io_usb_setup(unsigned int soc_id)
265 {
266 	uintptr_t block_dev_spec;
267 	int ret;
268 
269 	/* use ROM API for loading images from USB storage */
270 	ret = mmap_add_dynamic_region(UNIPHIER_ROM_REGION_BASE,
271 				      UNIPHIER_ROM_REGION_BASE,
272 				      UNIPHIER_ROM_REGION_SIZE,
273 				      MT_CODE | MT_SECURE);
274 	if (ret)
275 		return ret;
276 
277 	/*
278 	 * on-chip SRAM region: should be DEVICE attribute because the USB
279 	 * load functions provided by the ROM use this memory region as a work
280 	 * area, but do not cater to cache coherency.
281 	 */
282 	ret = mmap_add_dynamic_region(UNIPHIER_OCM_REGION_BASE,
283 				      UNIPHIER_OCM_REGION_BASE,
284 				      UNIPHIER_OCM_REGION_SIZE,
285 				      MT_DEVICE | MT_RW | MT_SECURE);
286 	if (ret)
287 		return ret;
288 
289 	ret = uniphier_usb_init(soc_id, &block_dev_spec);
290 	if (ret)
291 		return ret;
292 
293 	return uniphier_io_block_setup(0x20000, block_dev_spec);
294 }
295 
296 static int (* const uniphier_io_setup_table[])(unsigned int) = {
297 	[UNIPHIER_BOOT_DEVICE_EMMC] = uniphier_io_emmc_setup,
298 	[UNIPHIER_BOOT_DEVICE_NAND] = uniphier_io_nand_setup,
299 	[UNIPHIER_BOOT_DEVICE_NOR] = uniphier_io_nor_setup,
300 	[UNIPHIER_BOOT_DEVICE_USB] = uniphier_io_usb_setup,
301 };
302 
303 int uniphier_io_setup(unsigned int soc_id)
304 {
305 	int (*io_setup)(unsigned int soc_id);
306 	unsigned int boot_dev;
307 	int ret;
308 
309 	boot_dev = uniphier_get_boot_device(soc_id);
310 	if (boot_dev == UNIPHIER_BOOT_DEVICE_RSV)
311 		return -EINVAL;
312 
313 	io_setup = uniphier_io_setup_table[boot_dev];
314 	ret = io_setup(soc_id);
315 	if (ret)
316 		return ret;
317 
318 	ret = uniphier_io_fip_setup();
319 	if (ret)
320 		return ret;
321 
322 	return 0;
323 }
324 
325 int plat_get_image_source(unsigned int image_id, uintptr_t *dev_handle,
326 			  uintptr_t *image_spec)
327 {
328 	uintptr_t init_params;
329 
330 	assert(image_id < ARRAY_SIZE(uniphier_io_policies));
331 
332 	*dev_handle = *(uniphier_io_policies[image_id].dev_handle);
333 	*image_spec = uniphier_io_policies[image_id].image_spec;
334 	init_params = uniphier_io_policies[image_id].init_params;
335 
336 	return io_dev_init(*dev_handle, init_params);
337 }
338 
339 int uniphier_check_image(unsigned int image_id)
340 {
341 	uintptr_t dev_handle, image_spec, image_handle;
342 	int ret;
343 
344 	ret = plat_get_image_source(image_id, &dev_handle, &image_spec);
345 	if (ret)
346 		return ret;
347 
348 	ret = io_open(dev_handle, image_spec, &image_handle);
349 	if (ret)
350 		return ret;
351 
352 	io_close(image_handle);
353 
354 	return 0;
355 }
356