Content originally posted in LPCWare by mroe on Mon Aug 04 18:31:10 MST 2014
Hello,
I am trying to use IAP to store a variable in NV Flash RAM that will retain its state after reboot.
I am using my own linker script and storing the variable at location 0x6000 far away from anything else.
This the memory is being properly written to when I initially debug the application, but not after reboot. After rebooting, the code crashes when I try to erase the iap sector before writing to it.
Here is the relevant portion of my iap code:
int iap_erase_sector(unsigned int sector_start, unsigned int sector_end)
{
unsigned int command[5];
unsigned int result[4];
command[0] = ERASE_SECTOR; // 52
command[1] = (unsigned int)sector_start;
command[2] = (unsigned int)sector_end;
command[3] = SystemCoreClock / 1000;
iap_entry(command, result);
return result[0];
}
int iap_prepare_sector(unsigned int sector_start, unsigned int sector_end)
{
unsigned int command[5];
unsigned int result[4];
command[0] = PREPARE_SECTOR; // 50
command[1] = (unsigned int) sector_start;
command[2] = (unsigned int) sector_end;
iap_entry(command, result);
return result[0];
}
int iap_copy_ram_to_flash(void* ram_address, void* flash_address, unsigned int count)
{
unsigned int command[5];
unsigned int result[4];
command[0] = COPY_RAM_TO_FLASH; // 51
command[1] = (unsigned int)flash_address;
command[2] = (unsigned int)ram_address;
command[3] = count;
command[4] = SystemCoreClock / 1000;
iap_entry(command, result);
return result[0];
}
int iap_write(void *ram_address, void *flash_address, unsigned int count, unsigned int sector, unsigned int sector_size)
{
int iap_status = 0; // CMD_SUCCESS
SystemCoreClockUpdate();
iap_status = iap_prepare_sector(sector, sector_size);
if (iap_status != 0) return iap_status;
// after reboot, this crashes when I try to erase the sector
iap_status = iap_erase_sector(sector, sector_size);
if (iap_status != 0) return iap_status;
iap_status = iap_prepare_sector(sector, sector_size);
if (iap_status != 0) return iap_status;
iap_status = iap_copy_ram_to_flash(ram_address, flash_address, count);
if (iap_status != 0) return iap_status;
return iap_status;
}
Here is the relevant section of my linker script:
.var (0x6000) :
{
KEEP(*(.var*))
} > MFlash32
Here is the relevant section of my calling code:
__CRP const unsigned int CRP_WORD = CRP_NO_CRP;
static unsigned char var_temp[] = {0, 1, 1, 1, 1, 1, 1, 1, 1};
__attribute__ ((section(".var"))) unsigned char var[256];
int main()
{
LPC_SYSCON->SYSAHBCLKCTRL |= (1 << 16);
if (var[0] == 0)
{
// after reboot, this crashes when I try to erase the sector
// iap_write(ram_address, flash_address, count, sector, sector_size)
iap_write(&var_temp, (void *)0x6000, 256, 6, 7);
}
while (1)
{
}
return 0;
}
Thanks in advance for your help.