1// SPDX-License-Identifier: GPL-2.0+
2/*
3 * Copyright (C) 2016 Google, Inc
4 * Written by Simon Glass <sjg@chromium.org>
5 */
6
7#include <common.h>
8#include <errno.h>
9#include <fpga.h>
10#include <gzip.h>
11#include <image.h>
12#include <log.h>
13#include <memalign.h>
14#include <mapmem.h>
15#include <spl.h>
16#include <sysinfo.h>
17#include <asm/global_data.h>
18#include <asm/io.h>
19#include <linux/libfdt.h>
20#include <linux/printk.h>
21
22DECLARE_GLOBAL_DATA_PTR;
23
24struct spl_fit_info {
25	const void *fit;	/* Pointer to a valid FIT blob */
26	size_t ext_data_offset;	/* Offset to FIT external data (end of FIT) */
27	int images_node;	/* FDT offset to "/images" node */
28	int conf_node;		/* FDT offset to selected configuration node */
29};
30
31__weak ulong board_spl_fit_size_align(ulong size)
32{
33	return size;
34}
35
36static int find_node_from_desc(const void *fit, int node, const char *str)
37{
38	int child;
39
40	if (node < 0)
41		return -EINVAL;
42
43	/* iterate the FIT nodes and find a matching description */
44	for (child = fdt_first_subnode(fit, node); child >= 0;
45	     child = fdt_next_subnode(fit, child)) {
46		int len;
47		const char *desc = fdt_getprop(fit, child, FIT_DESC_PROP, &len);
48
49		if (!desc)
50			continue;
51
52		if (!strcmp(desc, str))
53			return child;
54	}
55
56	return -ENOENT;
57}
58
59/**
60 * spl_fit_get_image_name(): By using the matching configuration subnode,
61 * retrieve the name of an image, specified by a property name and an index
62 * into that.
63 * @fit:	Pointer to the FDT blob.
64 * @images:	Offset of the /images subnode.
65 * @type:	Name of the property within the configuration subnode.
66 * @index:	Index into the list of strings in this property.
67 * @outname:	Name of the image
68 *
69 * Return:	0 on success, or a negative error number
70 */
71static int spl_fit_get_image_name(const struct spl_fit_info *ctx,
72				  const char *type, int index,
73				  const char **outname)
74{
75	struct udevice *sysinfo;
76	const char *name, *str;
77	__maybe_unused int node;
78	int len, i;
79	bool found = true;
80
81	name = fdt_getprop(ctx->fit, ctx->conf_node, type, &len);
82	if (!name) {
83		debug("cannot find property '%s': %d\n", type, len);
84		return -EINVAL;
85	}
86
87	str = name;
88	for (i = 0; i < index; i++) {
89		str = strchr(str, '\0') + 1;
90		if (!str || (str - name >= len)) {
91			found = false;
92			break;
93		}
94	}
95
96	if (!found && CONFIG_IS_ENABLED(SYSINFO) && !sysinfo_get(&sysinfo)) {
97		int rc;
98		/*
99		 * no string in the property for this index. Check if the
100		 * sysinfo-level code can supply one.
101		 */
102		rc = sysinfo_detect(sysinfo);
103		if (rc)
104			return rc;
105
106		rc = sysinfo_get_fit_loadable(sysinfo, index - i - 1, type,
107					      &str);
108		if (rc && rc != -ENOENT)
109			return rc;
110
111		if (!rc) {
112			/*
113			 * The sysinfo provided a name for a loadable.
114			 * Try to match it against the description properties
115			 * first. If no matching node is found, use it as a
116			 * node name.
117			 */
118			int node;
119			int images = fdt_path_offset(ctx->fit, FIT_IMAGES_PATH);
120
121			node = find_node_from_desc(ctx->fit, images, str);
122			if (node > 0)
123				str = fdt_get_name(ctx->fit, node, NULL);
124
125			found = true;
126		}
127	}
128
129	if (!found) {
130		debug("no string for index %d\n", index);
131		return -E2BIG;
132	}
133
134	*outname = str;
135	return 0;
136}
137
138/**
139 * spl_fit_get_image_node(): By using the matching configuration subnode,
140 * retrieve the name of an image, specified by a property name and an index
141 * into that.
142 * @fit:	Pointer to the FDT blob.
143 * @images:	Offset of the /images subnode.
144 * @type:	Name of the property within the configuration subnode.
145 * @index:	Index into the list of strings in this property.
146 *
147 * Return:	the node offset of the respective image node or a negative
148 *		error number.
149 */
150static int spl_fit_get_image_node(const struct spl_fit_info *ctx,
151				  const char *type, int index)
152{
153	const char *str;
154	int err;
155	int node;
156
157	err = spl_fit_get_image_name(ctx, type, index, &str);
158	if (err)
159		return err;
160
161	debug("%s: '%s'\n", type, str);
162
163	node = fdt_subnode_offset(ctx->fit, ctx->images_node, str);
164	if (node < 0) {
165		pr_err("cannot find image node '%s': %d\n", str, node);
166		return -EINVAL;
167	}
168
169	return node;
170}
171
172static int get_aligned_image_offset(struct spl_load_info *info, int offset)
173{
174	return ALIGN_DOWN(offset, spl_get_bl_len(info));
175}
176
177static int get_aligned_image_overhead(struct spl_load_info *info, int offset)
178{
179	return offset & (spl_get_bl_len(info) - 1);
180}
181
182static int get_aligned_image_size(struct spl_load_info *info, int data_size,
183				  int offset)
184{
185	data_size = data_size + get_aligned_image_overhead(info, offset);
186
187	return ALIGN(data_size, spl_get_bl_len(info));
188}
189
190/**
191 * load_simple_fit(): load the image described in a certain FIT node
192 * @info:	points to information about the device to load data from
193 * @sector:	the start sector of the FIT image on the device
194 * @ctx:	points to the FIT context structure
195 * @node:	offset of the DT node describing the image to load (relative
196 *		to @fit)
197 * @image_info:	will be filled with information about the loaded image
198 *		If the FIT node does not contain a "load" (address) property,
199 *		the image gets loaded to the address pointed to by the
200 *		load_addr member in this struct, if load_addr is not 0
201 *
202 * Return:	0 on success or a negative error number.
203 */
204static int load_simple_fit(struct spl_load_info *info, ulong fit_offset,
205			   const struct spl_fit_info *ctx, int node,
206			   struct spl_image_info *image_info)
207{
208	int offset;
209	size_t length;
210	int len;
211	ulong size;
212	ulong load_addr;
213	void *load_ptr;
214	void *src;
215	ulong overhead;
216	uint8_t image_comp = -1, type = -1;
217	const void *data;
218	const void *fit = ctx->fit;
219	bool external_data = false;
220
221	if (IS_ENABLED(CONFIG_SPL_FPGA) ||
222	    (IS_ENABLED(CONFIG_SPL_OS_BOOT) && spl_decompression_enabled())) {
223		if (fit_image_get_type(fit, node, &type))
224			puts("Cannot get image type.\n");
225		else
226			debug("%s ", genimg_get_type_name(type));
227	}
228
229	if (spl_decompression_enabled()) {
230		fit_image_get_comp(fit, node, &image_comp);
231		debug("%s ", genimg_get_comp_name(image_comp));
232	}
233
234	if (fit_image_get_load(fit, node, &load_addr)) {
235		if (!image_info->load_addr) {
236			printf("Can't load %s: No load address and no buffer\n",
237			       fit_get_name(fit, node, NULL));
238			return -ENOBUFS;
239		}
240		load_addr = image_info->load_addr;
241	}
242
243	if (!fit_image_get_data_position(fit, node, &offset)) {
244		external_data = true;
245	} else if (!fit_image_get_data_offset(fit, node, &offset)) {
246		offset += ctx->ext_data_offset;
247		external_data = true;
248	}
249
250	if (external_data) {
251		void *src_ptr;
252
253		/* External data */
254		if (fit_image_get_data_size(fit, node, &len))
255			return -ENOENT;
256
257		/* Dont bother to copy 0 byte data, but warn, though */
258		if (!len) {
259			log_warning("%s: Skip load '%s': image size is 0!\n",
260				    __func__, fit_get_name(fit, node, NULL));
261			return 0;
262		}
263
264		if (spl_decompression_enabled() &&
265		    (image_comp == IH_COMP_GZIP || image_comp == IH_COMP_LZMA))
266			src_ptr = map_sysmem(ALIGN(CONFIG_SYS_LOAD_ADDR, ARCH_DMA_MINALIGN), len);
267		else
268			src_ptr = map_sysmem(ALIGN(load_addr, ARCH_DMA_MINALIGN), len);
269		length = len;
270
271		overhead = get_aligned_image_overhead(info, offset);
272		size = get_aligned_image_size(info, length, offset);
273
274		if (info->read(info,
275			       fit_offset +
276			       get_aligned_image_offset(info, offset), size,
277			       src_ptr) < length)
278			return -EIO;
279
280		debug("External data: dst=%p, offset=%x, size=%lx\n",
281		      src_ptr, offset, (unsigned long)length);
282		src = src_ptr + overhead;
283	} else {
284		/* Embedded data */
285		if (fit_image_get_data(fit, node, &data, &length)) {
286			puts("Cannot get image data/size\n");
287			return -ENOENT;
288		}
289		debug("Embedded data: dst=%lx, size=%lx\n", load_addr,
290		      (unsigned long)length);
291		src = (void *)data;	/* cast away const */
292	}
293
294	if (CONFIG_IS_ENABLED(FIT_SIGNATURE)) {
295		printf("## Checking hash(es) for Image %s ... ",
296		       fit_get_name(fit, node, NULL));
297		if (!fit_image_verify_with_data(fit, node, gd_fdt_blob(), src,
298						length))
299			return -EPERM;
300		puts("OK\n");
301	}
302
303	if (CONFIG_IS_ENABLED(FIT_IMAGE_POST_PROCESS))
304		board_fit_image_post_process(fit, node, &src, &length);
305
306	load_ptr = map_sysmem(load_addr, length);
307	if (IS_ENABLED(CONFIG_SPL_GZIP) && image_comp == IH_COMP_GZIP) {
308		size = length;
309		if (gunzip(load_ptr, CONFIG_SYS_BOOTM_LEN, src, &size)) {
310			puts("Uncompressing error\n");
311			return -EIO;
312		}
313		length = size;
314	} else if (IS_ENABLED(CONFIG_SPL_LZMA) && image_comp == IH_COMP_LZMA) {
315		size = CONFIG_SYS_BOOTM_LEN;
316		ulong loadEnd;
317
318		if (image_decomp(IH_COMP_LZMA, CONFIG_SYS_LOAD_ADDR, 0, 0,
319				 load_ptr, src, length, size, &loadEnd)) {
320			puts("Uncompressing error\n");
321			return -EIO;
322		}
323		length = loadEnd - CONFIG_SYS_LOAD_ADDR;
324	} else {
325		memcpy(load_ptr, src, length);
326	}
327
328	if (image_info) {
329		ulong entry_point;
330
331		image_info->load_addr = load_addr;
332		image_info->size = length;
333
334		if (!fit_image_get_entry(fit, node, &entry_point))
335			image_info->entry_point = entry_point;
336		else
337			image_info->entry_point = FDT_ERROR;
338	}
339
340	return 0;
341}
342
343static bool os_takes_devicetree(uint8_t os)
344{
345	switch (os) {
346	case IH_OS_U_BOOT:
347		return true;
348	case IH_OS_LINUX:
349		return IS_ENABLED(CONFIG_SPL_OS_BOOT) ||
350		       IS_ENABLED(CONFIG_SPL_OPENSBI);
351	default:
352		return false;
353	}
354}
355
356__weak int board_spl_fit_append_fdt_skip(const char *name)
357{
358	return 0;	/* Do not skip */
359}
360
361static int spl_fit_append_fdt(struct spl_image_info *spl_image,
362			      struct spl_load_info *info, ulong offset,
363			      const struct spl_fit_info *ctx)
364{
365	struct spl_image_info image_info;
366	int node, ret = 0, index = 0;
367
368	/*
369	 * Use the address following the image as target address for the
370	 * device tree.
371	 */
372	image_info.load_addr = spl_image->load_addr + spl_image->size;
373
374	/* Figure out which device tree the board wants to use */
375	node = spl_fit_get_image_node(ctx, FIT_FDT_PROP, index++);
376	if (node < 0) {
377		size_t size;
378
379		debug("%s: cannot find FDT node\n", __func__);
380
381		/*
382		 * U-Boot did not find a device tree inside the FIT image. Use
383		 * the U-Boot device tree instead.
384		 */
385		if (!gd->fdt_blob)
386			return node;
387
388		/*
389		 * Make the load-address of the FDT available for the SPL
390		 * framework
391		 */
392		size = fdt_totalsize(gd->fdt_blob);
393		spl_image->fdt_addr = map_sysmem(image_info.load_addr, size);
394		memcpy(spl_image->fdt_addr, gd->fdt_blob, size);
395	} else {
396		ret = load_simple_fit(info, offset, ctx, node, &image_info);
397		if (ret < 0)
398			return ret;
399
400		spl_image->fdt_addr = phys_to_virt(image_info.load_addr);
401	}
402
403	if (CONFIG_IS_ENABLED(FIT_IMAGE_TINY))
404		return 0;
405
406#if CONFIG_IS_ENABLED(LOAD_FIT_APPLY_OVERLAY)
407		void *tmpbuffer = NULL;
408
409		for (; ; index++) {
410			const char *str;
411
412			ret = spl_fit_get_image_name(ctx, FIT_FDT_PROP, index, &str);
413			if (ret == -E2BIG) {
414				debug("%s: No additional FDT node\n", __func__);
415				ret = 0;
416				break;
417			} else if (ret < 0) {
418				continue;
419			}
420
421			ret = board_spl_fit_append_fdt_skip(str);
422			if (ret)
423				continue;
424
425			node = fdt_subnode_offset(ctx->fit, ctx->images_node, str);
426			if (node < 0) {
427				debug("%s: unable to find FDT node %d\n",
428				      __func__, index);
429				continue;
430			}
431
432			if (!tmpbuffer) {
433				/*
434				 * allocate memory to store the DT overlay
435				 * before it is applied. It may not be used
436				 * depending on how the overlay is stored, so
437				 * don't fail yet if the allocation failed.
438				 */
439				size_t size = CONFIG_SPL_LOAD_FIT_APPLY_OVERLAY_BUF_SZ;
440
441				tmpbuffer = malloc_cache_aligned(size);
442				if (!tmpbuffer)
443					debug("%s: unable to allocate space for overlays\n",
444					      __func__);
445			}
446			image_info.load_addr = (ulong)tmpbuffer;
447			ret = load_simple_fit(info, offset, ctx, node,
448					      &image_info);
449			if (ret < 0)
450				break;
451
452			/* Make room in FDT for changes from the overlay */
453			ret = fdt_increase_size(spl_image->fdt_addr,
454						image_info.size);
455			if (ret < 0)
456				break;
457
458			ret = fdt_overlay_apply_verbose(spl_image->fdt_addr,
459							(void *)image_info.load_addr);
460			if (ret) {
461				pr_err("failed to apply DT overlay %s\n",
462				       fit_get_name(ctx->fit, node, NULL));
463				break;
464			}
465
466			debug("%s: DT overlay %s applied\n", __func__,
467			      fit_get_name(ctx->fit, node, NULL));
468		}
469		free(tmpbuffer);
470		if (ret)
471			return ret;
472#endif
473	/* Try to make space, so we can inject details on the loadables */
474	ret = fdt_shrink_to_minimum(spl_image->fdt_addr, 8192);
475	if (ret < 0)
476		return ret;
477
478	return ret;
479}
480
481static int spl_fit_record_loadable(const struct spl_fit_info *ctx, int index,
482				   void *blob, struct spl_image_info *image)
483{
484	int ret = 0;
485	const char *name;
486	int node;
487
488	if (CONFIG_IS_ENABLED(FIT_IMAGE_TINY))
489		return 0;
490
491	ret = spl_fit_get_image_name(ctx, "loadables", index, &name);
492	if (ret < 0)
493		return ret;
494
495	node = spl_fit_get_image_node(ctx, "loadables", index);
496
497	ret = fdt_record_loadable(blob, index, name, image->load_addr,
498			image->size, image->entry_point,
499			fdt_getprop(ctx->fit, node, FIT_TYPE_PROP, NULL),
500			fdt_getprop(ctx->fit, node, FIT_OS_PROP, NULL),
501			fdt_getprop(ctx->fit, node, FIT_ARCH_PROP, NULL));
502
503	return ret;
504}
505
506static int spl_fit_image_is_fpga(const void *fit, int node)
507{
508	const char *type;
509
510	if (!IS_ENABLED(CONFIG_SPL_FPGA))
511		return 0;
512
513	type = fdt_getprop(fit, node, FIT_TYPE_PROP, NULL);
514	if (!type)
515		return 0;
516
517	return !strcmp(type, "fpga");
518}
519
520static int spl_fit_image_get_os(const void *fit, int noffset, uint8_t *os)
521{
522	if (!CONFIG_IS_ENABLED(FIT_IMAGE_TINY) || CONFIG_IS_ENABLED(OS_BOOT))
523		return fit_image_get_os(fit, noffset, os);
524
525	const char *name = fdt_getprop(fit, noffset, FIT_OS_PROP, NULL);
526	if (!name)
527		return -ENOENT;
528
529	/*
530	 * We don't care what the type of the image actually is,
531	 * only whether or not it is U-Boot. This saves some
532	 * space by omitting the large table of OS types.
533	 */
534	if (!strcmp(name, "u-boot"))
535		*os = IH_OS_U_BOOT;
536	else
537		*os = IH_OS_INVALID;
538
539	return 0;
540}
541
542/*
543 * The purpose of the FIT load buffer is to provide a memory location that is
544 * independent of the load address of any FIT component.
545 */
546static void *spl_get_fit_load_buffer(size_t size)
547{
548	void *buf;
549
550	buf = malloc_cache_aligned(size);
551	if (!buf) {
552		pr_err("Could not get FIT buffer of %lu bytes\n", (ulong)size);
553
554		if (IS_ENABLED(CONFIG_SPL_SYS_MALLOC))
555			pr_err("\tcheck CONFIG_SPL_SYS_MALLOC_SIZE\n");
556		else
557			pr_err("\tcheck CONFIG_SPL_SYS_MALLOC_F_LEN\n");
558
559		buf = spl_get_load_buffer(0, size);
560	}
561	return buf;
562}
563
564__weak void *board_spl_fit_buffer_addr(ulong fit_size, int sectors, int bl_len)
565{
566	return spl_get_fit_load_buffer(sectors * bl_len);
567}
568
569/*
570 * Weak default function to allow customizing SPL fit loading for load-only
571 * use cases by allowing to skip the parsing/processing of the FIT contents
572 * (so that this can be done separately in a more customized fashion)
573 */
574__weak bool spl_load_simple_fit_skip_processing(void)
575{
576	return false;
577}
578
579/*
580 * Weak default function to allow fixes after fit header
581 * is loaded.
582 */
583__weak void *spl_load_simple_fit_fix_load(const void *fit)
584{
585	return (void *)fit;
586}
587
588static void warn_deprecated(const char *msg)
589{
590	printf("DEPRECATED: %s\n", msg);
591	printf("\tSee doc/uImage.FIT/source_file_format.txt\n");
592}
593
594static int spl_fit_upload_fpga(struct spl_fit_info *ctx, int node,
595			       struct spl_image_info *fpga_image)
596{
597	const char *compatible;
598	int ret;
599	int devnum = 0;
600	int flags = 0;
601
602	debug("FPGA bitstream at: %x, size: %x\n",
603	      (u32)fpga_image->load_addr, fpga_image->size);
604
605	compatible = fdt_getprop(ctx->fit, node, "compatible", NULL);
606	if (!compatible) {
607		warn_deprecated("'fpga' image without 'compatible' property");
608	} else {
609		if (CONFIG_IS_ENABLED(FPGA_LOAD_SECURE))
610			flags = fpga_compatible2flag(devnum, compatible);
611		if (strcmp(compatible, "u-boot,fpga-legacy"))
612			debug("Ignoring compatible = %s property\n",
613			      compatible);
614	}
615
616	ret = fpga_load(devnum, (void *)fpga_image->load_addr,
617			fpga_image->size, BIT_FULL, flags);
618	if (ret) {
619		printf("%s: Cannot load the image to the FPGA\n", __func__);
620		return ret;
621	}
622
623	puts("FPGA image loaded from FIT\n");
624
625	return 0;
626}
627
628static int spl_fit_load_fpga(struct spl_fit_info *ctx,
629			     struct spl_load_info *info, ulong offset)
630{
631	int node, ret;
632
633	struct spl_image_info fpga_image = {
634		.load_addr = 0,
635	};
636
637	node = spl_fit_get_image_node(ctx, "fpga", 0);
638	if (node < 0)
639		return node;
640
641	warn_deprecated("'fpga' property in config node. Use 'loadables'");
642
643	/* Load the image and set up the fpga_image structure */
644	ret = load_simple_fit(info, offset, ctx, node, &fpga_image);
645	if (ret) {
646		printf("%s: Cannot load the FPGA: %i\n", __func__, ret);
647		return ret;
648	}
649
650	return spl_fit_upload_fpga(ctx, node, &fpga_image);
651}
652
653static int spl_simple_fit_read(struct spl_fit_info *ctx,
654			       struct spl_load_info *info, ulong offset,
655			       const void *fit_header)
656{
657	unsigned long count, size;
658	void *buf;
659
660	/*
661	 * For FIT with external data, figure out where the external images
662	 * start. This is the base for the data-offset properties in each
663	 * image.
664	 */
665	size = ALIGN(fdt_totalsize(fit_header), 4);
666	size = board_spl_fit_size_align(size);
667	ctx->ext_data_offset = ALIGN(size, 4);
668
669	/*
670	 * So far we only have one block of data from the FIT. Read the entire
671	 * thing, including that first block.
672	 *
673	 * For FIT with data embedded, data is loaded as part of FIT image.
674	 * For FIT with external data, data is not loaded in this step.
675	 */
676	size = get_aligned_image_size(info, size, 0);
677	buf = board_spl_fit_buffer_addr(size, size, 1);
678
679	count = info->read(info, offset, size, buf);
680	ctx->fit = buf;
681	debug("fit read offset %lx, size=%lu, dst=%p, count=%lu\n",
682	      offset, size, buf, count);
683
684	return (count == 0) ? -EIO : 0;
685}
686
687static int spl_simple_fit_parse(struct spl_fit_info *ctx)
688{
689	/* Find the correct subnode under "/configurations" */
690	ctx->conf_node = fit_find_config_node(ctx->fit);
691	if (ctx->conf_node < 0)
692		return -EINVAL;
693
694	if (IS_ENABLED(CONFIG_SPL_FIT_SIGNATURE)) {
695		printf("## Checking hash(es) for config %s ... ",
696		       fit_get_name(ctx->fit, ctx->conf_node, NULL));
697		if (fit_config_verify(ctx->fit, ctx->conf_node))
698			return -EPERM;
699		puts("OK\n");
700	}
701
702	/* find the node holding the images information */
703	ctx->images_node = fdt_path_offset(ctx->fit, FIT_IMAGES_PATH);
704	if (ctx->images_node < 0) {
705		debug("%s: Cannot find /images node: %d\n", __func__,
706		      ctx->images_node);
707		return -EINVAL;
708	}
709
710	return 0;
711}
712
713int spl_load_simple_fit(struct spl_image_info *spl_image,
714			struct spl_load_info *info, ulong offset, void *fit)
715{
716	struct spl_image_info image_info;
717	struct spl_fit_info ctx;
718	int node = -1;
719	int ret;
720	int index = 0;
721	int firmware_node;
722
723	ret = spl_simple_fit_read(&ctx, info, offset, fit);
724	if (ret < 0)
725		return ret;
726
727	/* skip further processing if requested to enable load-only use cases */
728	if (spl_load_simple_fit_skip_processing())
729		return 0;
730
731	ctx.fit = spl_load_simple_fit_fix_load(ctx.fit);
732
733	ret = spl_simple_fit_parse(&ctx);
734	if (ret < 0)
735		return ret;
736
737	if (IS_ENABLED(CONFIG_SPL_FPGA))
738		spl_fit_load_fpga(&ctx, info, offset);
739
740	/*
741	 * Find the U-Boot image using the following search order:
742	 *   - start at 'firmware' (e.g. an ARM Trusted Firmware)
743	 *   - fall back 'kernel' (e.g. a Falcon-mode OS boot
744	 *   - fall back to using the first 'loadables' entry
745	 */
746	if (node < 0)
747		node = spl_fit_get_image_node(&ctx, FIT_FIRMWARE_PROP, 0);
748
749	if (node < 0 && IS_ENABLED(CONFIG_SPL_OS_BOOT))
750		node = spl_fit_get_image_node(&ctx, FIT_KERNEL_PROP, 0);
751
752	if (node < 0) {
753		debug("could not find firmware image, trying loadables...\n");
754		node = spl_fit_get_image_node(&ctx, "loadables", 0);
755		/*
756		 * If we pick the U-Boot image from "loadables", start at
757		 * the second image when later loading additional images.
758		 */
759		index = 1;
760	}
761	if (node < 0) {
762		debug("%s: Cannot find u-boot image node: %d\n",
763		      __func__, node);
764		return -1;
765	}
766
767	/* Load the image and set up the spl_image structure */
768	ret = load_simple_fit(info, offset, &ctx, node, spl_image);
769	if (ret)
770		return ret;
771
772	/*
773	 * For backward compatibility, we treat the first node that is
774	 * as a U-Boot image, if no OS-type has been declared.
775	 */
776	if (!spl_fit_image_get_os(ctx.fit, node, &spl_image->os))
777		debug("Image OS is %s\n", genimg_get_os_name(spl_image->os));
778	else if (!IS_ENABLED(CONFIG_SPL_OS_BOOT))
779		spl_image->os = IH_OS_U_BOOT;
780
781	/*
782	 * Booting a next-stage U-Boot may require us to append the FDT.
783	 * We allow this to fail, as the U-Boot image might embed its FDT.
784	 */
785	if (os_takes_devicetree(spl_image->os)) {
786		ret = spl_fit_append_fdt(spl_image, info, offset, &ctx);
787		if (ret < 0 && spl_image->os != IH_OS_U_BOOT)
788			return ret;
789	}
790
791	firmware_node = node;
792	/* Now check if there are more images for us to load */
793	for (; ; index++) {
794		uint8_t os_type = IH_OS_INVALID;
795
796		node = spl_fit_get_image_node(&ctx, "loadables", index);
797		if (node < 0)
798			break;
799
800		/*
801		 * if the firmware is also a loadable, skip it because
802		 * it already has been loaded. This is typically the case with
803		 * u-boot.img generated by mkimage.
804		 */
805		if (firmware_node == node)
806			continue;
807
808		image_info.load_addr = 0;
809		ret = load_simple_fit(info, offset, &ctx, node, &image_info);
810		if (ret < 0) {
811			printf("%s: can't load image loadables index %d (ret = %d)\n",
812			       __func__, index, ret);
813			return ret;
814		}
815
816		if (spl_fit_image_is_fpga(ctx.fit, node))
817			spl_fit_upload_fpga(&ctx, node, &image_info);
818
819		if (!spl_fit_image_get_os(ctx.fit, node, &os_type))
820			debug("Loadable is %s\n", genimg_get_os_name(os_type));
821
822		if (os_takes_devicetree(os_type)) {
823			spl_fit_append_fdt(&image_info, info, offset, &ctx);
824			spl_image->fdt_addr = image_info.fdt_addr;
825		}
826
827		/*
828		 * If the "firmware" image did not provide an entry point,
829		 * use the first valid entry point from the loadables.
830		 */
831		if (spl_image->entry_point == FDT_ERROR &&
832		    image_info.entry_point != FDT_ERROR)
833			spl_image->entry_point = image_info.entry_point;
834
835		/* Record our loadables into the FDT */
836		if (spl_image->fdt_addr)
837			spl_fit_record_loadable(&ctx, index,
838						spl_image->fdt_addr,
839						&image_info);
840	}
841
842	/*
843	 * If a platform does not provide CONFIG_SYS_UBOOT_START, U-Boot's
844	 * Makefile will set it to 0 and it will end up as the entry point
845	 * here. What it actually means is: use the load address.
846	 */
847	if (spl_image->entry_point == FDT_ERROR || spl_image->entry_point == 0)
848		spl_image->entry_point = spl_image->load_addr;
849
850	spl_image->flags |= SPL_FIT_FOUND;
851
852	return 0;
853}
854
855/* Parse and load full fitImage in SPL */
856int spl_load_fit_image(struct spl_image_info *spl_image,
857		       const struct legacy_img_hdr *header)
858{
859	struct bootm_headers images;
860	const char *fit_uname_config = NULL;
861	uintptr_t fdt_hack;
862	const char *uname;
863	ulong fw_data = 0, dt_data = 0, img_data = 0;
864	ulong fw_len = 0, dt_len = 0, img_len = 0;
865	int idx, conf_noffset;
866	int ret;
867
868#ifdef CONFIG_SPL_FIT_SIGNATURE
869	images.verify = 1;
870#endif
871	ret = fit_image_load(&images, virt_to_phys((void *)header),
872			     NULL, &fit_uname_config,
873			     IH_ARCH_DEFAULT, IH_TYPE_STANDALONE, -1,
874			     FIT_LOAD_OPTIONAL, &fw_data, &fw_len);
875	if (ret >= 0) {
876		printf("DEPRECATED: 'standalone = ' property.");
877		printf("Please use either 'firmware =' or 'kernel ='\n");
878	} else {
879		ret = fit_image_load(&images, virt_to_phys((void *)header),
880				     NULL, &fit_uname_config, IH_ARCH_DEFAULT,
881				     IH_TYPE_FIRMWARE, -1, FIT_LOAD_OPTIONAL,
882				     &fw_data, &fw_len);
883	}
884
885	if (ret < 0) {
886		ret = fit_image_load(&images, virt_to_phys((void *)header),
887				     NULL, &fit_uname_config, IH_ARCH_DEFAULT,
888				     IH_TYPE_KERNEL, -1, FIT_LOAD_OPTIONAL,
889				     &fw_data, &fw_len);
890	}
891
892	if (ret < 0)
893		return ret;
894
895	spl_image->size = fw_len;
896	spl_image->load_addr = fw_data;
897	if (fit_image_get_entry(header, ret, &spl_image->entry_point))
898		spl_image->entry_point = fw_data;
899	if (fit_image_get_os(header, ret, &spl_image->os))
900		spl_image->os = IH_OS_INVALID;
901	spl_image->name = genimg_get_os_name(spl_image->os);
902
903	debug(SPL_TPL_PROMPT "payload image: %32s load addr: 0x%lx size: %d\n",
904	      spl_image->name, spl_image->load_addr, spl_image->size);
905
906#ifdef CONFIG_SPL_FIT_SIGNATURE
907	images.verify = 1;
908#endif
909	ret = fit_image_load(&images, virt_to_phys((void *)header), NULL,
910			     &fit_uname_config, IH_ARCH_DEFAULT, IH_TYPE_FLATDT,
911			     -1, FIT_LOAD_OPTIONAL, &dt_data, &dt_len);
912	if (ret >= 0) {
913		spl_image->fdt_addr = (void *)dt_data;
914
915		if (spl_image->os == IH_OS_U_BOOT) {
916			/* HACK: U-Boot expects FDT at a specific address */
917			fdt_hack = spl_image->load_addr + spl_image->size;
918			fdt_hack = (fdt_hack + 3) & ~3;
919			debug("Relocating FDT to %p\n", spl_image->fdt_addr);
920			memcpy((void *)fdt_hack, spl_image->fdt_addr, dt_len);
921		}
922	}
923
924	conf_noffset = fit_conf_get_node((const void *)header,
925					 fit_uname_config);
926	if (conf_noffset < 0)
927		return 0;
928
929	for (idx = 0;
930	     uname = fdt_stringlist_get((const void *)header, conf_noffset,
931					FIT_LOADABLE_PROP, idx,
932				NULL), uname;
933	     idx++) {
934#ifdef CONFIG_SPL_FIT_SIGNATURE
935		images.verify = 1;
936#endif
937		ret = fit_image_load(&images, (ulong)header,
938				     &uname, &fit_uname_config,
939				     IH_ARCH_DEFAULT, IH_TYPE_LOADABLE, -1,
940				     FIT_LOAD_OPTIONAL_NON_ZERO,
941				     &img_data, &img_len);
942		if (ret < 0)
943			return ret;
944	}
945
946	return 0;
947}
948