Skip to content

Draft: rockpi4b: sign FIT image

Ghost User requested to merge (removed):rockpi4b-sign-fit into master

TL;DR: doesn't work on my board, please test and report back if you can, thanks.

Sign images and configuration in u-boot.itb (U-Boot, TF-A BL31 and OP-TEE). A development key is generated using Open SSL, it is stored in the build directory as keys/dev.key (contains the private key) and keys/dev.crt (the public key). If that key is lost it doesn't really matter as long as both idbloader.img and u-boot.itb are flashed to the SD card.

NOTE

When I run this on my board I get a hash verification error on atf_2.

U-Boot TPL 2022.04 (Apr 04 2022 - 14:31:32)
Channel 0: LPDDR4, 50MHz
BW=32 Col=10 Bk=8 CS0 Row=15 CS1 Row=15 CS=2 Die BW=16 Size=2048MB
Channel 1: LPDDR4, 50MHz
BW=32 Col=10 Bk=8 CS0 Row=15 CS1 Row=15 CS=2 Die BW=16 Size=2048MB
256B stride
lpddr4_set_rate: change freq to 400000000 mhz 0, 1
lpddr4_set_rate: change freq to 800000000 mhz 1, 0
Trying to boot from BOOTROM
Returning to boot ROM...

U-Boot SPL 2022.04 (Apr 04 2022 - 14:31:32 +0000)
Trying to boot from MMC1
## Checking hash(es) for config config_1 ... sha1,rsa2048:dev+ OK
## Checking hash(es) for Image atf_1 ... sha1+ sha1,rsa2048:dev+ OK
## Checking hash(es) for Image uboot ... sha1+ sha1,rsa2048:dev+ OK
## Checking hash(es) for Image fdt_1 ... sha1+ sha1,rsa2048:dev+ OK
## Checking hash(es) for Image atf_2 ... sha1 error!
Bad hash value for 'hash-1' hash node in 'atf_2' image node
spl_load_simple_fit: can't load image loadables index 1 (ret = -1)
mmc_load_image_raw_sector: mmc block read error

I traced the issue down to a write to memory that modifies a different memory location as well (!). atf_2 is loaded at address 0xff3b0000 (file: bl31_0xff3b0000.bin, 8024 bytes in my build), but due to the alignment of the start of the binary inside u-boot.itb and then on the MMC device, a bit more than the file size has to be read (exactly 17 blocks of 512 bytes = 8704 bytes). So the MMC driver reads data into the memory range 0xff3b0000 .. 0xff3b2200 and later performs a memcpy() to align the start properly. But for some reason I can't explain, writes at the end of the buffer modify the beginning, for example 32 bytes of data written to 0xff3b2100 can be read back at 0xff3b0100! And then the hash is invalid of course.

Here is a test case:

diff --git a/drivers/mmc/mmc.c b/drivers/mmc/mmc.c
index f6ccd837aa..810d5fa6db 100644
--- a/drivers/mmc/mmc.c
+++ b/drivers/mmc/mmc.c
@@ -401,6 +401,12 @@ static int mmc_read_blocks(struct mmc *mmc, void *dst, lbaint_t start,
 	struct mmc_cmd cmd;
 	struct mmc_data data;
 
+	printf("== 0x%08x\n", *(u32 *)0xff3b0100);
+	*(u32 *)0xff3b0100 = 0;
+	printf("== 0x%08x\n", *(u32 *)0xff3b0100);
+	*(u32 *)0xff3b2100 = 0xdeadbeef;
+	printf("== 0x%08x\n", *(u32 *)0xff3b0100);
+
 	if (blkcnt > 1)
 		cmd.cmdidx = MMC_CMD_READ_MULTIPLE_BLOCK;
 	else

On my board, this does print 0xdeadbeef! As far as I can tell the code is running at EL3 with the MMU is disabled at this stage... So how can this be? 😕

Edited by Ghost User

Merge request reports