Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 7 additions & 2 deletions hal/cc26x2.c
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,10 @@ int uart_read_nonblock(char *c)

int RAMFUNCTION hal_flash_write(uint32_t address, const uint8_t *data, int len)
{
FlashProgram(data, address, len);
/* driverlib's FlashProgram() takes a non-const buffer but only reads
* from it. */
if (FlashProgram((uint8_t *)data, address, len) != FAPI_STATUS_SUCCESS)
return -1;
while(FlashCheckFsmForReady() != FAPI_STATUS_FSM_READY)
;
return 0;
Expand All @@ -64,7 +67,9 @@ int RAMFUNCTION hal_flash_erase(uint32_t address, int len)
{
int i = 0;
while (len > 0) {
FlashSectorErase(address + (WOLFBOOT_SECTOR_SIZE * i++));
if (FlashSectorErase(address + (WOLFBOOT_SECTOR_SIZE * i++)) !=
FAPI_STATUS_SUCCESS)
return -1;
while(FlashCheckFsmForReady() != FAPI_STATUS_FSM_READY)
;

Expand Down
40 changes: 30 additions & 10 deletions hal/stm32n6.c
Original file line number Diff line number Diff line change
Expand Up @@ -138,20 +138,28 @@ static int RAMFUNCTION octospi_cmd(uint8_t fmode, uint8_t cmd,
return -1;
}

static void RAMFUNCTION octospi_write_enable(void)
static int RAMFUNCTION octospi_write_enable(void)
{
octospi_cmd(0, WRITE_ENABLE_CMD, 0, SPI_MODE_NONE,
NULL, 0, SPI_MODE_NONE, 0);
/* A failed WREN leaves the write-enable latch clear: the device then
* silently ignores the program/erase that follows, never goes BUSY, and
* octospi_wait_ready() reports idle on its first poll. The command must
* fail the operation instead of being discarded. */
return octospi_cmd(0, WRITE_ENABLE_CMD, 0, SPI_MODE_NONE,
NULL, 0, SPI_MODE_NONE, 0);
}

static void RAMFUNCTION octospi_wait_ready(void)
static int RAMFUNCTION octospi_wait_ready(void)
{
uint8_t sr;
do {
sr = 0;
octospi_cmd(1, READ_SR_CMD, 0, SPI_MODE_NONE,
&sr, 1, SPI_MODE_SINGLE, 0);
/* A failed status-register transfer must not read as "ready":
* sr stays zero and the loop would exit as if the flash were idle. */
if (octospi_cmd(1, READ_SR_CMD, 0, SPI_MODE_NONE,
&sr, 1, SPI_MODE_SINGLE, 0) < 0)
return -1;
} while (sr & FLASH_SR_BUSY);
return 0;
}

static void RAMFUNCTION octospi_enable_mmap(void)
Expand Down Expand Up @@ -730,14 +738,20 @@ static int RAMFUNCTION nor_flash_write(uint32_t offset, const uint8_t *data,

memcpy(page_buf, data, write_sz);

octospi_write_enable();
if (octospi_write_enable() < 0) {
ret = -1;
break;
}
ret = octospi_cmd(0, PAGE_PROG_4B_CMD,
offset, SPI_MODE_SINGLE,
page_buf, write_sz, SPI_MODE_SINGLE, 0);
if (ret < 0)
break;

octospi_wait_ready();
if (octospi_wait_ready() < 0) {
ret = -1;
break;
}

offset += write_sz;
data += write_sz;
Expand All @@ -759,14 +773,20 @@ static int RAMFUNCTION nor_flash_erase(uint32_t offset, int len)
end = offset + len;

while (offset < end) {
octospi_write_enable();
if (octospi_write_enable() < 0) {
ret = -1;
break;
}
ret = octospi_cmd(0, SEC_ERASE_4B_CMD,
offset, SPI_MODE_SINGLE,
NULL, 0, SPI_MODE_NONE, 0);
if (ret < 0)
break;

octospi_wait_ready();
if (octospi_wait_ready() < 0) {
ret = -1;
break;
}
offset += FLASH_SECTOR_SIZE;
}

Expand Down
7 changes: 7 additions & 0 deletions tools/unit-tests/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ TESTS+=unit-arm-tee-psa-ipc
TESTS+=unit-dice-token-size
TESTS+=unit-dice-token-nosign
TESTS+=unit-va416x0-fram
TESTS+=unit-flash-write-cc26x2
TESTS+=unit-flash-write-mcxa
TESTS+=unit-flash-write-nrf52
TESTS+=unit-flash-write-samr21
Expand Down Expand Up @@ -749,6 +750,12 @@ unit-ata-security-passphrase-zeroize: ../../include/target.h unit-ata-security-p
gcc -o $@ unit-ata-security-passphrase-zeroize.c $(CFLAGS) \
-ffunction-sections -fdata-sections $(LDFLAGS) -Wl,--gc-sections

# unit-flash-write-cc26x2 includes hal/cc26x2.c directly, with cc26x2_ti_stub/
# standing in for the (not vendored) TI CC26x2 SDK headers it includes. This
# is also the only build coverage hal/cc26x2.c has.
unit-flash-write-cc26x2: ../../include/target.h unit-flash-write-cc26x2.c ../../hal/cc26x2.c
gcc -o $@ unit-flash-write-cc26x2.c -Icc26x2_ti_stub $(CFLAGS) $(LDFLAGS)

# unit-flash-write-mcxa includes hal/mcxa.c directly, with mcxa_fsl_stub/
# standing in for the (not vendored) NXP MCUXpresso SDK headers it includes.
unit-flash-write-mcxa: unit-flash-write-mcxa.c ../../hal/mcxa.c
Expand Down
7 changes: 7 additions & 0 deletions tools/unit-tests/cc26x2_ti_stub/oscillators.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
/* Stand-in for the CC26x2 SDK/board oscillators.h that hal/cc26x2.c includes.
* Nothing from it is used by the flash paths under test; the real header
* only declares the oscillator setup that clock_init() performs. */
#ifndef CC26X2_OSCILLATORS_STUB_H
#define CC26X2_OSCILLATORS_STUB_H

#endif /* CC26X2_OSCILLATORS_STUB_H */
73 changes: 73 additions & 0 deletions tools/unit-tests/cc26x2_ti_stub/ti-lib.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
/* Minimal stand-in for the TI CC26x2 driverlib wrappers (ti-lib.h) that
* hal/cc26x2.c includes. Only what that file references is declared here:
* the Fapi flash API used by hal_flash_write()/hal_flash_erase() (the unit
* test provides those bodies), plus the UART and PRCM/VIMS entry points used
* by uart_read()/hal_init(). The latter are not exercised by the test -- they
* only have to compile and link, so they are no-op inlines here. */
#ifndef CC26X2_TI_LIB_STUB_H
#define CC26X2_TI_LIB_STUB_H

#include <stdint.h>
#include <stdbool.h>

/* Fapi status codes (mirror driverlib/flash.h) */
#define FAPI_STATUS_SUCCESS 0x00000000UL
#define FAPI_STATUS_FSM_BUSY 0x00000001UL
#define FAPI_STATUS_FSM_READY 0x00000002UL
#define FAPI_STATUS_FSM_ERROR 0x00000003UL

/* Flash API. Definitions live in the unit test. The data pointer is
* non-const, matching driverlib/flash.h. */
uint32_t FlashProgram(uint8_t *pui8DataBuffer, uint32_t ui32Address,
uint32_t ui32Count);
uint32_t FlashSectorErase(uint32_t ui32SectorAddress);
uint32_t FlashCheckFsmForReady(void);

/* UART. Definitions live in the unit test. */
#define UART0_BASE 0x40001000UL
int32_t UARTCharGet(uint32_t ui32Base);
int32_t UARTCharGetNonBlocking(uint32_t ui32Base);

/* PRCM / VIMS constants and no-op entry points used by hal_init() */
#define VIMS_BASE 0x40034000UL
#define VIMS_MODE_ENABLED 0x00000000UL
#define PRCM_DOMAIN_PERIPH 0x00000004UL
#define PRCM_DOMAIN_SERIAL 0x00000002UL
#define PRCM_DOMAIN_POWER_ON 0x00000001UL
#define PRCM_PERIPH_GPIO 0x00000010UL
#define PRCM_PERIPH_UART0 0x00000200UL

static inline void ti_lib_vims_mode_set(uint32_t base, uint32_t mode)
{
(void)base; (void)mode;
}

static inline void ti_lib_vims_configure(uint32_t base, bool round_robin,
bool prefetch)
{
(void)base; (void)round_robin; (void)prefetch;
}

static inline void ti_lib_int_master_disable(void) { }
static inline void ti_lib_int_master_enable(void) { }

static inline void ti_lib_prcm_power_domain_on(uint32_t domain)
{
(void)domain;
}

static inline uint32_t ti_lib_prcm_power_domain_status(uint32_t domain)
{
(void)domain;
return PRCM_DOMAIN_POWER_ON;
}

static inline void ti_lib_prcm_peripheral_run_enable(uint32_t periph)
{
(void)periph;
}

static inline void ti_lib_prcm_load_set(void) { }
static inline bool ti_lib_prcm_load_get(void) { return true; }

#endif /* CC26X2_TI_LIB_STUB_H */
Loading
Loading