[PATCH] sunxi: eMMC: support TOC0 on boot partitions

Samuel Holland samuel at sholland.org
Sat Jan 14 21:34:38 CET 2023


Hi Andre,

On 1/4/23 19:58, Andre Przywara wrote:
> To determine whether we have been booted from an eMMC boot partition, we
> replay some of the checks that the BROM must have done to successfully
> load the SPL. This involves a checksum check, which currently relies on
> the SPL being wrapped in an "eGON" header.
> 
> If a board has secure boot enabled, the BROM will only accept the "TOC0"
> format, which is internally very different, but uses the same
> checksumming algorithm. Actually the only difference for calculating the
> checksum is that the size of the SPL is stored at a different offset.
> 
> Do a header check to determine whether we deal with an eGON or TOC0
> format, then set the SPL size accordingly. The rest of the code is
> unchanged.
> 
> This fixes booting from an eMMC boot partition on devices with secure
> boot enabled, like the Remix Mini PC.
> 
> Signed-off-by: Andre Przywara <andre.przywara at arm.com>
> ---
>  arch/arm/mach-sunxi/board.c | 11 +++++++++--
>  1 file changed, 9 insertions(+), 2 deletions(-)
> 
> diff --git a/arch/arm/mach-sunxi/board.c b/arch/arm/mach-sunxi/board.c
> index 0c4b6dd1ca3..a90c88210cd 100644
> --- a/arch/arm/mach-sunxi/board.c
> +++ b/arch/arm/mach-sunxi/board.c
> @@ -365,6 +365,7 @@ static bool sunxi_valid_emmc_boot(struct mmc *mmc)
>  	struct blk_desc *bd = mmc_get_blk_desc(mmc);
>  	u32 *buffer = (void *)(uintptr_t)CONFIG_TEXT_BASE;
>  	struct boot_file_head *egon_head = (void *)buffer;
> +	struct toc0_main_info *toc0_info = (void *)buffer;
>  	int bootpart = EXT_CSD_EXTRACT_BOOT_PART(mmc->part_config);
>  	uint32_t spl_size, emmc_checksum, chksum = 0;
>  	ulong count;
> @@ -391,11 +392,17 @@ static bool sunxi_valid_emmc_boot(struct mmc *mmc)
>  
>  	/* Read the first block to do some sanity checks on the eGON header. */
>  	count = blk_dread(bd, 0, 1, buffer);
> -	if (count != 1 || !sunxi_egon_valid(egon_head))
> +	if (count != 1)
> +		return false;
> +
> +	if (sunxi_egon_valid(egon_head))
> +		spl_size = buffer[4];
> +	else if (sunxi_toc0_valid(toc0_info))
> +		spl_size = buffer[7];

Please dereference the appropriate structure member here instead of
indexing the buffer.

Regards,
Samuel

> +	else
>  		return false;
>  
>  	/* Read the rest of the SPL now we know it's halfway sane. */
> -	spl_size = buffer[4];
>  	count = blk_dread(bd, 1, DIV_ROUND_UP(spl_size, bd->blksz) - 1,
>  			  buffer + bd->blksz / 4);
>  



More information about the U-Boot mailing list