SiWx917 Generic Flash APIs#
This section explains how to configure and use flash APIs for the generic flash programmer.
The related software modules are found at SiWx917_SoC_Flash_Loader\Source_Code\Si917_Flashloader\Src. (This source code is provided in Software section.)
There are two main files:
FlashDev.c
FlashPrg.c
These two files are SEGGER template files. One can port these files to their system to make a flash programmer of their own.
The flash APIs provide complete low-level access to the flash memory and help to modify the flash memory contents. The APIs support flash memory erase, program, and read operations.
The code blocks (shown in the table below) play a major role in the flash programmer.
Code Block | Description |
---|---|
FlashOS.h | Contains all defines and prototypes of public functions |
FlashDev.c | Flash device Description |
FlashPrg.c | Implementation of RAM Code |
Initialization#
The initialization is done in the FlashDev.c file. The SEGGER template is used.
Though this is dummy, it is included for device description.
File : FlashDev.c
Purpose : Flash device Description Template
*/
#include "FlashOS.h"
struct FlashDevice_t const FlashDevice __attribute__ ((section ("DevDscr"))) = {
FLASH_DRV_VERS, // Algo version. Must be == 0x0101
{ "Si917_Generic_Flash" }, // Flash device name
ONCHIP, // Flash device type. Must be == 1
0x08000000, // Flash base address
0x00800000, // Total flash device erase size in Bytes
4096, // Page Size (Will be passed as <NumBytes> to ProgramPage().
A multiple of this is passed as <NumBytes> to SEGGER_OPEN_Program() to
program more than 1 page in 1 RAMCode call, speeding up programming).
0, // Reserved, should be 0
0xFF, // Flash erased value
50000000, // Program page timeout in ms
50000000, // Erase sector timeout in ms
{
{ 0x00001000, 0x00000000 },
{ 0xFFFFFFFF, 0xFFFFFFFF } // Indicates the end of the flash sector layout. Must be present.
}
};
Program the Device#
In FlashPrg.c, implementation of the RAM code template is done. The file contains SEGGER template APIs.
Among all the APIs, the ProgramPage() and EraseChip() play a major role in programming the common flash SiWx917 device.
ProgramPage API#
The code block shown below explains the ProgramPage API.
* ProgramPage
*
* Function description: Programs one flash page.
* Parameters
* DestAddr - Address to start programming on
* NumBytes - Number of bytes to program. Guaranteed to be == <FlashDevice.PageSize>
* pSrcBuff - Pointer to data to be programmed
* Return value
* == 0 O.K.
* == 1 Error
*/
#define TA_RESET_ADDR 0x22000004
int ProgramPage(U32 DestAddr, U32 NumBytes, U8 *pSrcBuff)
{
int32_t status = 1;
static int32_t x = 0, size;
uint32_t Imageheader[HEADER_LENGTH];
*(uint32_t *)(TA_RESET_ADDR) = 0x0; //put TA in reset
#ifdef DEBUG_OFL
*(volatile uint32_t *)0x24048624 |= (1<<5);
#endif
memset(Imageheader,'\0', HEADER_LENGTH);
if (x == 0)
{
memcpy(Imageheader, pSrcBuff, HEADER_LENGTH);
if (!board_ready) {
if((uint32_t)(Imageheader[0] & IMAGE_TYPE_MASK) == (uint32_t)TA_IMAGE)
{
status = rsi_device_init(BURN_NWP_FW);
} else
{
status = rsi_device_init(RSI_UPGRADE_IMAGE_I_FW);
}
if (status != RSI_SUCCESS) {
return status;
}
}
size = Imageheader[2];
size = (size) / CHUNK_SIZE;
status = rsi_bl_upgrade_firmware(pSrcBuff, NumBytes, 1);
size--;
x = 1;
#ifdef DEBUG_OFL
*(volatile uint32_t *)0x24048624 &= ~(1<<5);
#endif
return status;
}
if (size == 0) {
status = rsi_bl_upgrade_firmware(pSrcBuff, NumBytes, 2);
x = 0;
} else {
status = rsi_bl_upgrade_firmware(pSrcBuff, NumBytes, 0);
size--;
}
#ifdef DEBUG_OFL
*(volatile uint32_t *)0x24048624 &= ~(1<<5);
#endif
return status;
}
Function Description#
Mandatory function. Must be present to make OFL(Open Flash Loader) detected as valid.
Programs flash. The block passed to this function is always a multiple of what is indicated as page size by FlashDevice.PageSize.
This function can rely on only being called with destination addresses and NumBytes that are aligned to FlashDevice.PageSize.
In this function, we call the boot loader APIs, to load the M4 and TA firmware for the common flash radio board.
API: rsi_device_init#
Source File: rsi_device_init_apis_flm.c
Prototype:
int32_t rsi_device_init(uint8_t select_option);
Description
This API power cycles the module and sets the boot up option for module features. This API also initializes the module SPI.
Parameter
Parameter | Description |
---|---|
select_option | RSI_LOAD_IMAGE_I_FW: To load Firmware image RSI_LOAD_IMAGE_I_ACTIVE_LOW_FW: To load active low Firmware image. Active low firmware will generate active low interrupts to indicate that packets are pending on the module, instead of the default active high. RSI_UPGRADE_IMAGE_I_FW: To upgrade firmware file ERASE_COMMON_FLASH: To Erase the Common flash region. |
Return Values
Value | Description |
---|---|
0 | Successful execution of the command |
Non Zero Value | -1: Failure |
Example
if (!board_ready)
{
status = rsi_device_init(RSI_UPGRADE_IMAGE_I_FW);
if (status != RSI_SUCCESS) {
return status;
}
API: rsi_bl_select_option#
Source File: rsi_device_init_flm.c
Prototype:
int16_t rsi_bl_select_option(uint8_t cmd);
Description
This API is used to send firmware load requests to TA or update default configurations.
Parameter
Parameter | Description |
---|---|
cmd | Type of configuration to be loaded |
Return Values
Value | Description |
---|---|
0 | Success |
<0 | Failure |
Example
uint8_t cmd = LOAD_NWP_FW;
status = rsi_bl_select_option(cmd);
API: rsi_bl_upgrade_firmware#
Source File: rsi_device_init_flm.c
Prototype:
int16_t rsi_bl_upgrade_firmware(uint8_t *firmware_image, uint32_t fw_image_size, uint8_t flags);
Description
This API upgrades the firmware in the module device from the host. The firmware file is given in chunks to this API.
Each chunk must be a multiple of 4096 bytes unless it is the last chunk.
For the first chunk, set RSI_FW_START_OF_FILE in flags.
For the last chunk set RSI_FW_END_OF_FILE in flags.
Parameters
Parameter | Description |
---|---|
firmware_image | This is a pointer to firmware image buffer |
flags |
1 - RSI_FW_START_OF_FILE 2 - RSI_FW_END_OF_FILE Set flags to 1 - If it is the first chunk 2 - If it is last chunk 0 - For all other chunks |
fw_image_size | This is the size of firmware image |
Return Values
Value | Description |
---|---|
0 | Successful execution of the command |
Non Zero Value | -1: Failure |
Example
rsi_bl_upgrade_firmware(fw_image, FW_IMG_SIZE, 1);
API: rsi_bootloader_instructions#
Source File: rsi_device_init_flm.c
Prototype:
int16_t rsi_bootloader_instructions(uint8_t type, uint16_t *data);
Description
This API is used to send boot instructions to TA.
Parameters
Parameter | Description |
---|---|
type | Type of the instruction to perform |
data | Pointer to data which is to be read/write |
Return Values
Value | Description |
---|---|
0 | Success |
Non Zero Value | Failure |
Example
status = rsi_bootloader_instructions(RSI_REG_READ, data);
EraseChip APIs#
The below code block explains the EraseChip operation.
/* EraseChip
*
* Function description: Erases the entire flash.
*
* Return value
* == 0 O.K.
* == 1 Error
*/
#if SUPPORT_ERASE_CHIP
int EraseChip(void) {
int status =RSI_SUCCESS;
//Send the common flash erase command to the TA
status = rsi_device_init(ERASE_COMMON_FLASH);
if(status==RSI_SUCCESS)
return RSI_OK;
else
return 0;
}
#endif
Function description#
This function is used to Erases the entire flash for the common flash radio board.
API: rsi_device_init#
Source File: rsi_device_init_apis_flm.c
Prototype:
int32_t rsi_device_init(uint8_t select_option);
Description
This API power cycles the module and sets the boot up option for module features. This API also initializes the module SPI.
Parameter
Parameter | Description |
---|---|
select_option | ERASE_COMMON_FLASH: To Erase the Common flash region. |
Return Values
Value | Description |
---|---|
0 | Successful execution of the command |
Non Zero Value | -1: Failure |
Example
status = **rsi_device_init(ERASE_COMMON_FLASH);**
if(status==RSI_SUCCESS)
return RSI_OK;