[iot] Load fdt from oem_bootloader using dtimg format

See http://cs/android/system/libufdt/utils/README.md
for the dtimg format.

Bug: 78537598
Bug: 78630913
Bug: 78904624
Test: iMX7D boots with new oem_bootloader format.
Test: iMX8M boots with new oem_bootloader format.
Change-Id: I2cab38a0f0706586a9e4fb06b75e29c82d134032
This commit is contained in:
Braden Kell 2018-04-26 13:54:23 -07:00 committed by Ji Luo
parent ab85a073b6
commit 153021557f
2 changed files with 101 additions and 51 deletions

View File

@ -64,20 +64,17 @@ extern void trusty_os_init(void);
#endif #endif
#ifdef CONFIG_AVB_SUPPORT #ifdef CONFIG_AVB_SUPPORT
#include <dt_table.h>
#include <fsl_avb.h> #include <fsl_avb.h>
#endif #endif
#ifdef CONFIG_ANDROID_THINGS_SUPPORT #define FASTBOOT_VERSION "0.4"
#include <fs.h>
#endif
#ifdef CONFIG_FASTBOOT_LOCK #ifdef CONFIG_FASTBOOT_LOCK
#include "fastboot_lock_unlock.h" #include "fastboot_lock_unlock.h"
#endif #endif
#endif #endif
#define FASTBOOT_VERSION "0.4"
#define FASTBOOT_COMMON_VAR_NUM 13 #define FASTBOOT_COMMON_VAR_NUM 13
#define FASTBOOT_VAR_YES "yes" #define FASTBOOT_VAR_YES "yes"
#define FASTBOOT_VAR_NO "no" #define FASTBOOT_VAR_NO "no"
@ -112,10 +109,9 @@ struct fastboot_device_info fastboot_firmwareinfo;
* that expect bulk OUT requests to be divisible by maxpacket size. * that expect bulk OUT requests to be divisible by maxpacket size.
*/ */
#define AT_OEM_DTB "/kernel.dtb" #define AT_OEM_BL_PART_NAME_BASE "oem_bootloader"
#define AT_OEM_PART_NAME "oem_bootloader" #define AT_OEM_BL_PART_SIZE (sizeof(AT_OEM_BL_PART_NAME_BASE) + \
#define AT_OEM_PART_SIZE 17 sizeof("_a") - 1)
#define AT_OEM_DEV_SIZE 6
/* Offset (in u32's) of start and end fields in the zImage header. */ /* Offset (in u32's) of start and end fields in the zImage header. */
#define ZIMAGE_START_ADDR 10 #define ZIMAGE_START_ADDR 10
@ -1874,34 +1870,6 @@ bootimg_print_image_hdr(struct andr_img_hdr *hdr)
#endif #endif
} }
#ifdef CONFIG_ANDROID_THINGS_SUPPORT
static int android_things_load_fdt(const char *slot,
struct andr_img_hdr *hdrload, u32 *fdt_size) {
/* check for kernel.dtb in oem_bootloader */
char oem_bootloader[AT_OEM_PART_SIZE];
snprintf(oem_bootloader, AT_OEM_PART_SIZE, AT_OEM_PART_NAME "%s", slot);
struct fastboot_ptentry *pte = fastboot_flash_find_ptn(oem_bootloader);
if (pte == NULL) {
printf("boota: no partition found for '%s'\n", oem_bootloader);
return -1;
}
char dev_part[AT_OEM_DEV_SIZE];
snprintf(dev_part, AT_OEM_DEV_SIZE, "%x:%x", fastboot_devinfo.dev_id,
pte->partition_index);
if (fs_set_blk_dev("mmc", dev_part, FS_TYPE_EXT) != 0)
return -1;
loff_t size;
if (!fs_read(AT_OEM_DTB, hdrload->second_addr, 0, 0, &size) && size) {
*fdt_size = size;
return 0;
}
return -1;
}
#endif
static struct andr_img_hdr boothdr __aligned(ARCH_DMA_MINALIGN); static struct andr_img_hdr boothdr __aligned(ARCH_DMA_MINALIGN);
#ifdef CONFIG_IMX_TRUSTY_OS #ifdef CONFIG_IMX_TRUSTY_OS
@ -2162,21 +2130,51 @@ int do_boota(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) {
#endif #endif
#ifdef CONFIG_OF_LIBFDT #ifdef CONFIG_OF_LIBFDT
u32 fdt_size = 0; u32 fdt_size = 0;
bool fdt_loaded = false; char oemimage[AT_OEM_BL_PART_SIZE];
#ifdef CONFIG_ANDROID_THINGS_SUPPORT snprintf(oemimage, sizeof(oemimage), "%s%s",
fdt_loaded = !android_things_load_fdt(slot, hdr, &fdt_size); AT_OEM_BL_PART_NAME_BASE, slot);
#endif /* CONFIG_ANDROID_THINGS_SUPPORT */
/* load the dtb file */ struct dt_table_header *dt_img = NULL;
if (!fdt_loaded && hdr->second_addr) { size_t num_read;
/* The fdt is appended to the zImage. Use the address and size of the kernel if (fsl_avb_ops.read_from_partition(&fsl_avb_ops, oemimage, 0,
section of the boot image and the kernel size from the zImage to sizeof(*dt_img), dt_img, &num_read) !=
calculate the address and size of the fdt. */ AVB_IO_RESULT_OK &&
u32 zimage_size = ((u32 *)hdr->kernel_addr)[ZIMAGE_END_ADDR] num_read != sizeof(*dt_img)) {
- ((u32 *)hdr->kernel_addr)[ZIMAGE_START_ADDR]; printf("boota: read dt table header error\n");
fdt_size = hdr->kernel_size - zimage_size; goto dt_read_done;
memcpy((void *)(ulong)hdr->second_addr,
(void*)(ulong)hdr->kernel_addr + zimage_size, fdt_size);
} }
if (be32_to_cpu(dt_img->magic) != DT_TABLE_MAGIC) {
printf("boota: bad dt table magic %08x\n",
be32_to_cpu(dt_img->magic));
goto dt_read_done;
} else if (!be32_to_cpu(dt_img->dt_entry_count)) {
printf("boota: no dt entries\n");
goto dt_read_done;
}
struct dt_table_entry *dt_entry = NULL;
assert(be32_to_cpu(dt_img->dt_entry_size) == sizeof(*dt_entry));
if (fsl_avb_ops.read_from_partition(&fsl_avb_ops, oemimage,
be32_to_cpu(dt_img->dt_entries_offset),
be32_to_cpu(dt_img->dt_entry_size), dt_entry,
&num_read) != AVB_IO_RESULT_OK &&
num_read != sizeof(*dt_entry)) {
printf("boota: read dt entry error\n");
goto dt_read_done;
}
/* Read the fdt from oem_bootloader into hdr->second_addr. */
fdt_size = be32_to_cpu(dt_entry->dt_size);
if (fsl_avb_ops.read_from_partition(&fsl_avb_ops, oemimage,
be32_to_cpu(dt_entry->dt_offset), fdt_size,
(void *)hdr->second_addr, &num_read) !=
AVB_IO_RESULT_OK && num_read != fdt_size) {
printf("boota: read fdt error\n");
}
dt_read_done:
;
#endif /*CONFIG_OF_LIBFDT*/ #endif /*CONFIG_OF_LIBFDT*/
if (check_image_arm64) { if (check_image_arm64) {
android_image_get_kernel(hdr, 0, NULL, NULL); android_image_get_kernel(hdr, 0, NULL, NULL);

52
include/dt_table.h Normal file
View File

@ -0,0 +1,52 @@
/*
* Copyright (C) 2018 The Android Open Source Project
*
* Permission is hereby granted, free of charge, to any person
* obtaining a copy of this software and associated documentation
* files (the "Software"), to deal in the Software without
* restriction, including without limitation the rights to use, copy,
* modify, merge, publish, distribute, sublicense, and/or sell copies
* of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be
* included in all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
* BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
* ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#ifndef _DT_TABLE_H_
#define _DT_TABLE_H_
#include <linux/types.h>
/* https://android.googlesource.com/platform/system/libufdt/+/master/utils/README.md */
#define DT_TABLE_MAGIC 0xd7b7ab1e
struct dt_table_header {
__be32 magic;
__be32 total_size;
__be32 header_size;
__be32 dt_entry_size;
__be32 dt_entry_count;
__be32 dt_entries_offset;
__be32 page_size;
__be32 version;
};
struct dt_table_entry {
__be32 dt_size;
__be32 dt_offset;
__be32 id;
__be32 rev;
__be32 custom[4];
};
#endif /* _DT_TABLE_H_ */