mirror of https://github.com/wolfSSL/wolfBoot.git
Fixed delta updates from external devices (+ test)
parent
aaf780fae9
commit
f26dd61e23
|
@ -67,7 +67,7 @@ int wb_diff_init(WB_DIFF_CTX *ctx, uint8_t *src_a, uint32_t len_a, uint8_t *src_
|
|||
int wb_diff(WB_DIFF_CTX *ctx, uint8_t *patch, uint32_t len);
|
||||
int wb_patch_init(WB_PATCH_CTX *bm, uint8_t *src, uint32_t ssz, uint8_t *patch, uint32_t psz);
|
||||
int wb_patch(WB_PATCH_CTX *ctx, uint8_t *dst, uint32_t len);
|
||||
int wolfBoot_get_delta_info(uint8_t part, int inverse, uint32_t *img_offset, uint16_t *img_size);
|
||||
int wolfBoot_get_delta_info(uint8_t part, int inverse, uint32_t **img_offset, uint16_t **img_size);
|
||||
|
||||
#endif
|
||||
|
||||
|
|
|
@ -467,7 +467,7 @@ static inline uint16_t im2ns(uint16_t val)
|
|||
}
|
||||
|
||||
#ifdef DELTA_UPDATES
|
||||
int wolfBoot_get_delta_info(uint8_t part, int inverse, uint32_t *img_offset, uint16_t *img_size)
|
||||
int wolfBoot_get_delta_info(uint8_t part, int inverse, uint32_t **img_offset, uint16_t **img_size)
|
||||
{
|
||||
uint32_t *version_field = NULL;
|
||||
uint32_t *magic = NULL;
|
||||
|
@ -500,17 +500,17 @@ int wolfBoot_get_delta_info(uint8_t part, int inverse, uint32_t *img_offset, uin
|
|||
return -1;
|
||||
if (inverse) {
|
||||
if (wolfBoot_find_header((uint8_t *)(image + IMAGE_HEADER_OFFSET),
|
||||
HDR_IMG_DELTA_INVERSE, (void *)img_offset) != sizeof(uint32_t)) {
|
||||
HDR_IMG_DELTA_INVERSE, (uint8_t **) img_offset) != sizeof(uint32_t)) {
|
||||
return -1;
|
||||
}
|
||||
if (wolfBoot_find_header((uint8_t *)(image + IMAGE_HEADER_OFFSET),
|
||||
HDR_IMG_DELTA_INVERSE_SIZE, (void *)img_size) != sizeof(uint16_t)) {
|
||||
HDR_IMG_DELTA_INVERSE_SIZE, (uint8_t **) img_size) != sizeof(uint16_t)) {
|
||||
return -1;
|
||||
}
|
||||
} else {
|
||||
*img_offset = 0x0000000;
|
||||
if (wolfBoot_find_header((uint8_t *)(image + IMAGE_HEADER_OFFSET),
|
||||
HDR_IMG_DELTA_SIZE, (void *)img_size) != sizeof(uint16_t)) {
|
||||
HDR_IMG_DELTA_SIZE, (uint8_t **)img_size) != sizeof(uint16_t)) {
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -167,8 +167,8 @@ static int wolfBoot_delta_update(struct wolfBoot_image *boot,
|
|||
uint8_t delta_blk[DELTA_BLOCK_SIZE];
|
||||
uint32_t offset = 0;
|
||||
uint16_t ptr_len;
|
||||
uint32_t img_offset;
|
||||
uint16_t img_size;
|
||||
uint32_t *img_offset;
|
||||
uint16_t *img_size;
|
||||
uint32_t total_size;
|
||||
WB_PATCH_CTX ctx;
|
||||
|
||||
|
@ -177,9 +177,6 @@ static int wolfBoot_delta_update(struct wolfBoot_image *boot,
|
|||
if ((update->fw_size + IMAGE_HEADER_SIZE) > total_size)
|
||||
total_size = update->fw_size + IMAGE_HEADER_SIZE;
|
||||
|
||||
if (total_size <= IMAGE_HEADER_SIZE)
|
||||
return -1;
|
||||
|
||||
hal_flash_unlock();
|
||||
#ifdef EXT_FLASH
|
||||
ext_flash_unlock();
|
||||
|
@ -198,16 +195,16 @@ static int wolfBoot_delta_update(struct wolfBoot_image *boot,
|
|||
delta_base_v = wolfBoot_get_diffbase_version(PART_UPDATE);
|
||||
if ((cur_v == upd_v) && (delta_base_v < cur_v)) {
|
||||
ret = wb_patch_init(&ctx, boot->hdr, boot->fw_size + IMAGE_HEADER_SIZE,
|
||||
update->hdr + img_offset, img_size);
|
||||
update->hdr + *img_offset, *img_size);
|
||||
} else {
|
||||
ret = -1;
|
||||
}
|
||||
} else {
|
||||
ret = wb_patch_init(&ctx, boot->hdr, boot->fw_size + IMAGE_HEADER_SIZE,
|
||||
update->hdr + IMAGE_HEADER_SIZE, img_size);
|
||||
update->hdr + IMAGE_HEADER_SIZE, *img_size);
|
||||
}
|
||||
if (ret < 0)
|
||||
return ret;
|
||||
goto out;
|
||||
|
||||
while((sector * WOLFBOOT_SECTOR_SIZE) < (int)total_size) {
|
||||
if ((wolfBoot_get_update_sector_flag(sector, &flag) != 0) || (flag == SECT_FLAG_NEW)) {
|
||||
|
@ -245,13 +242,14 @@ static int wolfBoot_delta_update(struct wolfBoot_image *boot,
|
|||
if (((sector + 1) * WOLFBOOT_SECTOR_SIZE) < WOLFBOOT_PARTITION_SIZE)
|
||||
wolfBoot_set_update_sector_flag(sector, flag);
|
||||
}
|
||||
#if 0
|
||||
if (sector == 0) {
|
||||
/* New total image size after first sector is patched */
|
||||
volatile uint32_t update_size;
|
||||
hal_flash_lock();
|
||||
update_size =
|
||||
wolfBoot_image_size((uint8_t *)WOLFBOOT_PARTITION_BOOT_ADDRESS)
|
||||
+ IMAGE_HEADER_SIZE;
|
||||
hal_flash_unlock();
|
||||
if (update_size > total_size)
|
||||
total_size = update_size;
|
||||
if (total_size <= IMAGE_HEADER_SIZE) {
|
||||
|
@ -264,7 +262,6 @@ static int wolfBoot_delta_update(struct wolfBoot_image *boot,
|
|||
}
|
||||
|
||||
}
|
||||
#endif
|
||||
sector++;
|
||||
}
|
||||
ret = 0;
|
||||
|
@ -273,10 +270,13 @@ static int wolfBoot_delta_update(struct wolfBoot_image *boot,
|
|||
sector * WOLFBOOT_SECTOR_SIZE, WOLFBOOT_SECTOR_SIZE);
|
||||
sector++;
|
||||
}
|
||||
//wb_flash_erase(swap, 0, WOLFBOOT_SECTOR_SIZE);
|
||||
st = IMG_STATE_TESTING;
|
||||
wolfBoot_set_partition_state(PART_BOOT, st);
|
||||
/* On success, reset all flags on update partition */
|
||||
wb_flash_erase(update, WOLFBOOT_PARTITION_SIZE - WOLFBOOT_SECTOR_SIZE,
|
||||
WOLFBOOT_SECTOR_SIZE);
|
||||
out:
|
||||
wb_flash_erase(swap, 0, WOLFBOOT_SECTOR_SIZE);
|
||||
#ifdef EXT_FLASH
|
||||
ext_flash_lock();
|
||||
#endif
|
||||
|
@ -324,11 +324,6 @@ static int RAMFUNCTION wolfBoot_update(int fallback_allowed)
|
|||
|
||||
update_type = wolfBoot_get_image_type(PART_UPDATE);
|
||||
|
||||
#ifdef DELTA_UPDATES
|
||||
if ((update_type & 0x00F0) == HDR_IMG_TYPE_DIFF) {
|
||||
return wolfBoot_delta_update(&boot, &update, &swap, fallback_allowed);
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Check the first sector to detect interrupted update */
|
||||
if ((wolfBoot_get_update_sector_flag(0, &flag) < 0) || (flag == SECT_FLAG_NEW))
|
||||
|
@ -346,11 +341,19 @@ static int RAMFUNCTION wolfBoot_update(int fallback_allowed)
|
|||
#endif
|
||||
}
|
||||
|
||||
|
||||
#ifdef DELTA_UPDATES
|
||||
if ((update_type & 0x00F0) == HDR_IMG_TYPE_DIFF) {
|
||||
return wolfBoot_delta_update(&boot, &update, &swap, fallback_allowed);
|
||||
}
|
||||
#endif
|
||||
|
||||
hal_flash_unlock();
|
||||
#ifdef EXT_FLASH
|
||||
ext_flash_unlock();
|
||||
#endif
|
||||
|
||||
|
||||
/* Read encryption key/IV before starting the update */
|
||||
#ifdef EXT_ENCRYPTED
|
||||
wolfBoot_get_encrypt_key(key, nonce);
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
test-delta-update:SIGN_ARGS?=--ecc256
|
||||
test-delta-update:SIGN_DELTA_ARGS?=--ecc256 --encrypt /tmp/enc_key.der
|
||||
test-delta-update:USBTTY?=/dev/ttyACM0
|
||||
test-delta-update:TIMEOUT?=60
|
||||
test-delta-update:EXPVER=tools/test-expect-version/test-expect-version /dev/ttyACM0
|
||||
|
||||
test-delta-update-ext:SIGN_ARGS?=--ecc256
|
||||
|
@ -26,23 +25,18 @@ test-delta-update: factory.bin test-app/image.bin tools/uart-flash-server/ufserv
|
|||
@st-flash write test-app/image_v7_signed_diff.bin 0x0802C000
|
||||
@sleep 2
|
||||
@st-flash reset
|
||||
@sleep 20
|
||||
@echo Expecting version '7'
|
||||
@(test `$(EXPVER)` -eq 7)
|
||||
@sleep 2
|
||||
@st-flash reset
|
||||
@echo Expecting version '7'
|
||||
@(test `$(EXPVER)` -eq 7)
|
||||
@sleep 2
|
||||
@st-flash reset
|
||||
@echo Expecting version '1'
|
||||
@(test `$(EXPVER)` -eq 1)
|
||||
@st-flash reset
|
||||
@st-flash erase || st-flash erase
|
||||
@st-flash write factory.bin 0x08000000
|
||||
@echo Expecting version '1'
|
||||
@(test `$(EXPVER)` -eq 1)
|
||||
@sleep 1
|
||||
@st-flash reset
|
||||
@st-flash write test-app/image_v2_signed_diff.bin 0x0802C000
|
||||
@st-flash reset
|
||||
@echo Expecting version '2'
|
||||
|
@ -69,13 +63,30 @@ test-delta-update-ext: factory.bin test-app/image.bin tools/uart-flash-server/uf
|
|||
@sync
|
||||
@echo Waiting $(TIMEOUT) seconds...
|
||||
@sleep $(TIMEOUT)
|
||||
@st-flash reset
|
||||
@sleep 3
|
||||
@killall ufserver
|
||||
@st-flash reset
|
||||
@sleep 3
|
||||
@st-flash read boot_full.bin 0x0800C000 0x8000
|
||||
@SIZE=`wc -c test-app/image_v7_signed.bin | cut -d" " -f 1`; \
|
||||
dd if=boot_full.bin of=boot.bin bs=1 count=$$SIZE
|
||||
@diff boot.bin test-app/image_v7_signed.bin || (echo "TEST FAILED" && exit 1)
|
||||
@rm boot.bin boot_full.bin
|
||||
@echo "TEST SUCCESSFUL"
|
||||
@sleep 1
|
||||
@echo
|
||||
@echo
|
||||
@st-flash reset
|
||||
@(tools/uart-flash-server/ufserver test-app/image_v7_signed_diff.bin $(USBTTY))&
|
||||
@echo TEST INVERSE
|
||||
@sleep $(TIMEOUT)
|
||||
@st-flash reset
|
||||
@killall ufserver
|
||||
@st-flash reset
|
||||
@st-flash read boot_full.bin 0x0800C000 0x8000
|
||||
@SIZE=`wc -c test-app/image_v1_signed.bin | cut -d" " -f 1`; \
|
||||
dd if=boot_full.bin of=boot.bin bs=1 count=$$SIZE
|
||||
@diff boot.bin test-app/image_v1_signed.bin || (echo "TEST INVERSE FAILED" && exit 1)
|
||||
@rm boot.bin boot_full.bin
|
||||
@echo "TEST SUCCESSFUL"
|
||||
|
||||
|
||||
|
|
|
@ -55,6 +55,10 @@
|
|||
#define SWAP_SIZE 0x1000
|
||||
#define UART_BITRATE 115200
|
||||
|
||||
/* Change the following to 1 to debug flash access */
|
||||
#define LOG_FLASH_ADDRESS 0
|
||||
|
||||
|
||||
const char msgSha[] = "Verifying SHA digest...";
|
||||
const char msgReadUpdate[] = "Fetching update blocks ";
|
||||
const char msgReadSwap[] = "Reading SWAP blocks ";
|
||||
|
@ -280,7 +284,9 @@ static void uart_flash_erase(uint8_t *base, int ud)
|
|||
} else {
|
||||
printmsg(msgEraseSwap);
|
||||
}
|
||||
#if LOG_FLASH_ADDRESS
|
||||
printf("Erase @%x\n", address);
|
||||
#endif
|
||||
for (i = 0; i < len; i++) {
|
||||
base[address + i] = 0xFF;
|
||||
}
|
||||
|
@ -307,7 +313,9 @@ static void uart_flash_read(uint8_t *base, int ud)
|
|||
} else {
|
||||
printmsg(msgReadSwap);
|
||||
}
|
||||
#if LOG_FLASH_ADDRESS
|
||||
printf("Read @%x\n", address);
|
||||
#endif
|
||||
if (address + len > (FIRMWARE_PARTITION_SIZE + SWAP_SIZE))
|
||||
return;
|
||||
for (i = 0; i < len; i++) {
|
||||
|
@ -330,7 +338,9 @@ static void uart_flash_write(uint8_t *base, int ud)
|
|||
} else {
|
||||
printmsg(msgWriteSwap);
|
||||
}
|
||||
#if LOG_FLASH_ADDRESS
|
||||
printf("Write @%x\n", address);
|
||||
#endif
|
||||
if (address + len > (FIRMWARE_PARTITION_SIZE + SWAP_SIZE))
|
||||
return;
|
||||
for (i = 0; i < len; i++) {
|
||||
|
@ -373,7 +383,7 @@ static void serve_update(uint8_t *base, const char *uart_dev)
|
|||
}
|
||||
|
||||
v = buf[4] + (buf[3] << 8) + (buf[2] << 16) + (buf[1] << 24);
|
||||
printf("Bootloader version from test app: %u\n", v);
|
||||
printf("Boot partition version from test app: %u\n", v);
|
||||
continue;
|
||||
}
|
||||
if (buf[0] == CMD_HDR_VER) {
|
||||
|
|
Loading…
Reference in New Issue