Skip to content

Commit 8a9fbe5

Browse files
dgarskedanielinux
authored andcommitted
Improve network core firmware update.
1 parent 6db7de6 commit 8a9fbe5

5 files changed

Lines changed: 152 additions & 100 deletions

File tree

config/examples/nrf5340_net.config

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,7 @@ RAM_CODE?=1
1717

1818
DUALBANK_SWAP?=0
1919
FLAGS_HOME=0
20-
DISABLE_BACKUP=0
20+
DISABLE_BACKUP=1
2121
EXT_FLASH?=0
2222
SPI_FLASH?=0
2323
QSPI_FLASH?=0

hal/nrf5340.c

Lines changed: 122 additions & 81 deletions
Original file line numberDiff line numberDiff line change
@@ -51,18 +51,17 @@ static int test_flash(void);
5151
#define PART_NET_ADDR 0x100000UL
5252
#endif
5353

54-
/* Shared Memory between network and application cores */
54+
/* SHM: Shared Memory between network and application cores */
5555
/* first 64KB (0x10000) is used by wolfBoot and limited in nrf5340.ld */
5656
#ifndef SHARED_MEM_ADDR
5757
#define SHARED_MEM_ADDR (0x20000000UL + (64 * 1024))
58-
#define SHARED_MEM_SIZE (256 * 1024) /* enable access to full 256KB for entire network update image */
5958
#endif
60-
/* Shared memory states */
59+
/* Shared memory states (mask, easier to check) */
6160
#define SHARED_STATUS_UNKNOWN 0
6261
#define SHARED_STATUS_READY 1
6362
#define SHARED_STATUS_UPDATE_START 2
64-
#define SHARED_STATUS_UPDATE_DONE 3
65-
#define SHARED_STATUS_DO_BOOT 4
63+
#define SHARED_STATUS_UPDATE_DONE 4
64+
#define SHARED_STATUS_DO_BOOT 8
6665

6766
#define SHAREM_MEM_MAGIC 0x5753484D /* WSHM */
6867

@@ -78,11 +77,12 @@ typedef struct {
7877
ShmInfo_t app; /* application core write location */
7978

8079
/* application places firmware here */
81-
uint8_t data[0];
80+
uint8_t data[FLASH_SIZE_NET];
8281
} SharedMem_t;
8382
static SharedMem_t* shm = (SharedMem_t*)SHARED_MEM_ADDR;
8483

8584

85+
/* UART */
8686
#ifdef DEBUG_UART
8787
#ifndef UART_SEL
8888
#define UART_SEL 0 /* select UART 0 or 1 */
@@ -280,24 +280,77 @@ void hal_net_core(int hold) /* 1=hold, 0=release */
280280
}
281281
#endif
282282

283+
static uint8_t* get_image_hdr(struct wolfBoot_image* img)
284+
{
285+
#ifdef EXT_FLASH
286+
return img->hdr_cache;
287+
#else
288+
return img->hdr;
289+
#endif
290+
}
291+
static uint16_t get_image_partition_id(struct wolfBoot_image* img)
292+
{
293+
return wolfBoot_get_blob_type(get_image_hdr(img)) & HDR_IMG_TYPE_PART_MASK;
294+
}
295+
283296
#define IMAGE_IS_NET_CORE(img) ( \
284-
(img->type & HDR_IMG_TYPE_PART_MASK) == PART_NET_ID && \
285-
img->fw_size < FLASH_SIZE_NET)
286-
static int hal_net_get_image(struct wolfBoot_image* img)
297+
(get_image_partition_id(img) == PART_NET_ID) && \
298+
(img->fw_size < (FLASH_SIZE_NET - IMAGE_HEADER_SIZE)))
299+
static int hal_net_get_image(struct wolfBoot_image* img, ShmInfo_t* info)
287300
{
301+
int ret;
302+
#ifdef TARGET_nrf5340_app
288303
/* check the update partition for a network core update */
289-
int ret = wolfBoot_open_image(img, PART_UPDATE);
290-
if (ret == 0 && IMAGE_IS_NET_CORE(img)) {
291-
return 0;
304+
ret = wolfBoot_open_image(img, PART_UPDATE);
305+
if (ret == 0 && !IMAGE_IS_NET_CORE(img)) {
306+
ret = -1;
292307
}
293308
/* if external flash is enabled, try an alternate location */
294-
#ifdef EXT_FLASH
295-
ret = wolfBoot_open_image_external(img, PART_UPDATE, PART_NET_ADDR);
296-
if (ret == 0 && IMAGE_IS_NET_CORE(img)) {
297-
return 0;
309+
#ifdef EXT_FLASH
310+
if (ret != 0) {
311+
ret = wolfBoot_open_image_external(img, PART_UPDATE,
312+
(uint8_t*)PART_NET_ADDR);
313+
if (ret == 0 && !IMAGE_IS_NET_CORE(img)) {
314+
ret = -1;
315+
}
298316
}
299-
#endif
300-
return (ret != 0) ? ret : -1;
317+
#endif
318+
#else /* TARGET_nrf5340_net */
319+
ret = wolfBoot_open_image(img, PART_BOOT);
320+
#endif /* TARGET_nrf5340_* */
321+
if (ret == 0) {
322+
info->version = wolfBoot_get_blob_version(get_image_hdr(img));
323+
info->size = img->fw_size;
324+
wolfBoot_printf("Network Image: Ver 0x%x, Size %d\n",
325+
info->version, info->size);
326+
}
327+
else {
328+
info->version = 0; /* not known */
329+
wolfBoot_printf("Network Image: Update not found\n");
330+
}
331+
return ret;
332+
}
333+
334+
static void hal_shm_status_set(ShmInfo_t* info, uint32_t status)
335+
{
336+
info->magic = SHAREM_MEM_MAGIC;
337+
info->status = status;
338+
}
339+
340+
static int hal_shm_status_wait(ShmInfo_t* info, uint32_t status,
341+
uint32_t timeout_us)
342+
{
343+
int ret = 0;
344+
uint32_t timeout = timeout_us;
345+
while ((info->magic != SHAREM_MEM_MAGIC || (info->status & status) == 0)
346+
&& --timeout > 0) {
347+
sleep_us(1);
348+
};
349+
if (timeout == 0) {
350+
wolfBoot_printf("Timeout: status 0x%x\n", status);
351+
ret = -1; /* timeout */
352+
}
353+
return ret;
301354
}
302355

303356
static void hal_net_check_version(void)
@@ -308,65 +361,49 @@ static void hal_net_check_version(void)
308361

309362
#ifdef TARGET_nrf5340_app
310363
/* check the network core version */
311-
ret = hal_net_get_image(&img);
312-
if (ret == 0) {
313-
shm->app.version = img.fw_ver;
314-
shm->app.size = img.fw_size;
315-
wolfBoot_printf("Network: Ver 0x%x, Size %d\n",
316-
shm->app.version, shm->app.size);
317-
}
318-
else {
319-
wolfBoot_printf("Failed finding net core update on ext flash 0x%x\n",
320-
PART_NET_ADDR);
321-
}
322-
shm->app.magic = SHAREM_MEM_MAGIC;
323-
shm->app.status = SHARED_STATUS_READY;
364+
hal_net_get_image(&img, &shm->app);
365+
hal_shm_status_set(&shm->app, SHARED_STATUS_READY);
324366

325367
/* release network core - issue boot command */
326368
hal_net_core(0);
327369

328370
/* wait for ready status from network core */
329-
timeout = 1000000;
330-
while (shm->net.magic != SHAREM_MEM_MAGIC &&
331-
shm->net.status != SHARED_STATUS_READY &&
332-
--timeout > 0) {
333-
/* wait */
334-
};
335-
if (timeout == 0) {
336-
wolfBoot_printf("Timeout: network core ready!\n");
337-
}
371+
ret = hal_shm_status_wait(&shm->net, SHARED_STATUS_READY, 1000000);
338372

339373
/* check if network core can continue booting or needs to wait for update */
340-
if (shm->app.version == shm->net.version) {
341-
shm->app.status = SHARED_STATUS_DO_BOOT;
342-
}
343-
#else /* net */
344-
ret = wolfBoot_open_image(&img, PART_BOOT);
345-
if (ret == 0) {
346-
shm->net.version = img.fw_ver;
347-
shm->net.size = img.fw_size;
348-
wolfBoot_printf("Network: Ver 0x%x, Size %d\n",
349-
shm->net.version, shm->net.size);
374+
if (ret != 0 || shm->app.version <= shm->net.version) {
375+
wolfBoot_printf("Network Core: Releasing for boot\n");
376+
hal_shm_status_set(&shm->app, SHARED_STATUS_DO_BOOT);
350377
}
351378
else {
352-
wolfBoot_printf("Error getting boot partition info\n");
379+
wolfBoot_printf("Network Core: Holding for update\n");
353380
}
354-
shm->net.magic = SHAREM_MEM_MAGIC;
355-
shm->net.status = SHARED_STATUS_READY;
356-
357-
wolfBoot_printf("Network version: 0x%x\n", shm->net.version);
358-
359-
/* wait for do_boot or update */
360-
timeout = 1000000;
361-
while (shm->app.magic == SHAREM_MEM_MAGIC &&
362-
shm->app.status == SHARED_STATUS_READY &&
363-
--timeout > 0) {
364-
/* wait */
365-
};
366-
if (timeout == 0) {
367-
wolfBoot_printf("Timeout: app core boot signal!\n");
381+
#else /* TARGET_nrf5340_net */
382+
hal_net_get_image(&img, &shm->net);
383+
hal_shm_status_set(&shm->net, SHARED_STATUS_READY);
384+
385+
/* wait for do_boot or update from app core */
386+
ret = hal_shm_status_wait(&shm->app,
387+
(SHARED_STATUS_UPDATE_START | SHARED_STATUS_DO_BOOT), 1000000);
388+
/* are we updating? */
389+
if (ret == 0 && shm->app.status == SHARED_STATUS_UPDATE_START) {
390+
wolfBoot_printf("Starting update: Ver %d->%d, Size %d->%d\n",
391+
shm->net.version, shm->app.version, shm->net.size, shm->net.size);
392+
/* Erase network core boot flash */
393+
wb_flash_erase(&img, 0, WOLFBOOT_PARTITION_SIZE);
394+
/* Write new firmware to internal flash */
395+
wb_flash_write(&img, 0, shm->data, shm->app.size);
396+
397+
/* Reopen image and refresh information */
398+
wolfBoot_open_image(&img, PART_BOOT);
399+
wolfBoot_printf("Network version (after update): 0x%x\n",
400+
shm->net.version);
401+
hal_net_get_image(&img, &shm->net);
402+
hal_shm_status_set(&shm->net, SHARED_STATUS_UPDATE_DONE);
403+
404+
/* continue booting */
368405
}
369-
#endif
406+
#endif /* TARGET_nrf5340_* */
370407
exit:
371408
wolfBoot_printf("Status: App %d (ver %d), Net %d (ver %d)\n",
372409
shm->app.status, shm->app.version, shm->net.status, shm->net.version);
@@ -380,28 +417,32 @@ void hal_net_check_update(void)
380417
struct wolfBoot_image img;
381418

382419
/* handle update for network core */
383-
ret = hal_net_get_image(&img);
384-
if (ret == 0 && img.fw_ver > shm->net.version) {
420+
ret = hal_net_get_image(&img, &shm->app);
421+
if (ret == 0 && shm->app.version > shm->net.version) {
422+
wolfBoot_printf("Found Network Core update: Ver %d->%d, Size %d->%d\n",
423+
shm->net.version, shm->app.version, shm->net.size, shm->net.size);
424+
385425
/* validate the update is valid */
386426
if (wolfBoot_verify_integrity(&img) == 0 &&
387427
wolfBoot_verify_authenticity(&img) == 0)
388428
{
389-
/* relocate image to ram */
390-
ret = spi_flash_read(PART_NET_ADDR, shm->data, img.fw_size);
429+
uint32_t fw_size = IMAGE_HEADER_SIZE + img.fw_size;
430+
wolfBoot_printf("Network image valid, loading into shared mem\n");
431+
/* relocate image to shared ram */
432+
#ifdef EXT_FLASH
433+
ret = ext_flash_read(PART_NET_ADDR, shm->data, fw_size);
434+
#else
435+
memcpy(shm->data, img.hdr, fw_size);
436+
#endif
391437
if (ret >= 0) {
392438
/* signal network core to do update */
393-
shm->app.status = SHARED_STATUS_UPDATE_START;
439+
hal_shm_status_set(&shm->app, SHARED_STATUS_UPDATE_START);
394440

395441
/* wait for update_done */
396-
timeout = 1000000;
397-
while (shm->net.magic == SHAREM_MEM_MAGIC &&
398-
shm->net.status < SHARED_STATUS_UPDATE_DONE &&
399-
--timeout > 0) {
400-
sleep_us(1);
401-
};
402-
if (timeout == 0) {
403-
wolfBoot_printf("Timeout: net core update done!\n");
404-
}
442+
ret = hal_shm_status_wait(&shm->net,
443+
SHARED_STATUS_UPDATE_DONE, 1000000);
444+
if (ret == 0)
445+
wolfBoot_printf("Network core firmware update sent\n");
405446
}
406447
}
407448
else {
@@ -410,7 +451,7 @@ void hal_net_check_update(void)
410451
}
411452
}
412453
/* inform network core to boot */
413-
shm->app.status = SHARED_STATUS_DO_BOOT;
454+
hal_shm_status_set(&shm->app, SHARED_STATUS_DO_BOOT);
414455
}
415456
#endif
416457

include/image.h

Lines changed: 7 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -93,12 +93,13 @@ int wolfBot_get_dts_size(void *dts_addr);
9393

9494
struct wolfBoot_image {
9595
uint8_t *hdr;
96+
#ifdef EXT_FLASH
97+
uint8_t *hdr_cache;
98+
#endif
9699
uint8_t *trailer;
97100
uint8_t *sha_hash;
98101
uint8_t *fw_base;
99102
uint32_t fw_size;
100-
uint32_t fw_ver;
101-
uint32_t type;
102103
uint32_t part;
103104
uint32_t hdr_ok;
104105
uint32_t canary_FEED4567;
@@ -512,12 +513,13 @@ static void __attribute__((noinline)) wolfBoot_image_confirm_signature_ok(
512513

513514
struct wolfBoot_image {
514515
uint8_t *hdr;
516+
#ifdef EXT_FLASH
517+
uint8_t *hdr_cache;
518+
#endif
515519
uint8_t *trailer;
516520
uint8_t *sha_hash;
517521
uint8_t *fw_base;
518522
uint32_t fw_size;
519-
uint32_t fw_ver;
520-
uint16_t type;
521523
uint8_t part;
522524
uint8_t hdr_ok : 1;
523525
uint8_t signature_ok : 1;
@@ -567,7 +569,7 @@ static void wolfBoot_image_confirm_signature_ok(struct wolfBoot_image *img)
567569
/* Defined in image.c */
568570
int wolfBoot_open_image(struct wolfBoot_image *img, uint8_t part);
569571
#ifdef EXT_FLASH
570-
int wolfBoot_open_image_external(struct wolfBoot_image* img, uint8_t part, uint32_t addr);
572+
int wolfBoot_open_image_external(struct wolfBoot_image* img, uint8_t part, uint8_t* addr);
571573
#endif
572574
int wolfBoot_open_image_address(struct wolfBoot_image* img, uint8_t* image);
573575
int wolfBoot_verify_integrity(struct wolfBoot_image *img);

src/image.c

Lines changed: 9 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -881,12 +881,15 @@ int wolfBoot_open_image_address(struct wolfBoot_image *img, uint8_t *image)
881881
#endif
882882
img->hdr_ok = 1;
883883
img->fw_base = img->hdr + IMAGE_HEADER_SIZE;
884-
img->fw_ver = wolfBoot_get_blob_version(image);
885-
img->type = wolfBoot_get_blob_type(image);
884+
#ifdef EXT_FLASH
885+
img->hdr_cache = image;
886+
#endif
886887

887888
wolfBoot_printf("%s partition: %p (sz %d, ver 0x%x, type 0x%d)\n",
888889
(img->part == PART_BOOT) ? "Boot" : "Update",
889-
img->hdr, (unsigned int)img->fw_size, img->fw_ver, img->type);
890+
img->hdr, (unsigned int)img->fw_size,
891+
wolfBoot_get_blob_version(image),
892+
wolfBoot_get_blob_type(image));
890893

891894
return 0;
892895
}
@@ -992,16 +995,15 @@ int wolfBoot_open_image(struct wolfBoot_image *img, uint8_t part)
992995

993996
#ifdef EXT_FLASH
994997
int wolfBoot_open_image_external(struct wolfBoot_image* img, uint8_t part,
995-
uint32_t addr)
998+
uint8_t* addr)
996999
{
997-
uint8_t *image;
998-
1000+
uint8_t* image;
9991001
if (img == NULL)
10001002
return -1;
10011003

10021004
memset(img, 0, sizeof(struct wolfBoot_image));
10031005
img->part = part;
1004-
img->hdr = (void*)addr;
1006+
img->hdr = addr;
10051007
img->hdr_ok = 1;
10061008
hdr_cpy_done = 0; /* reset hdr "open" flag */
10071009
image = fetch_hdr_cpy(img);

0 commit comments

Comments
 (0)