SAMD20 app boot code

Go To Last Post
2 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Hi Everyone,

 

Just checking to see if this is possible. I have an application that runs on a SAMD20J17 (128K). The application has NVM routines that allow me receive (via UART) image data and buffers it at 0x10000, then checksums it. Depending on the purpose of the image, it will be placed at 0x1E000 if it is a new boot-loader, or the app will call the boot-loader to move the image over-top my application.

 

So receiving a bootloader image or application image and putting it at 0x10000 works. Copying the bootloader image from 0x10000 to 0x1e000 works. The only portion I am trying to make work is copying the application from 0x10000 to 0x00000 which isn't working yet. It just hangs.

 

 

My question is, if I want an independent boot-loader at 0x1E000 (as a separate project) I have the following code:

 

//bootloader.c

#define BOOTLOADER_SECTION __attribute__ ((section (".BOOT")))

#pragma GCC optimize ("O1") // optimize this file for performance

BOOTLOADER_SECTION void BLmain(void);

// Includes
void configure_nvm(void);
#include "asf.h"
//#include "reset.h"
#include "axxbootload.h"
#include "nvm2.h"

// Main boot-loader starts here - test code to see what address it compiles to
// .BOOT=0x1E000
BOOTLOADER_SECTION void BLmain(void)
{
    static uint16_t bi;
    static uint8_t nvm_buff[NVMCTRL_PAGE_SIZE];

    enum status_code nvm_error_code;
    struct nvm2_config config_nvm;

    nvm2_get_config_defaults(&config_nvm);
    config_nvm.manual_page_write = false;
    nvm2_set_config(&config_nvm);

    //system_interrupt_enter_critical_section();
    // Copy 768 blocks of 64B = 49,152B. Hard-coded for safety. Assume all code will be less than 49,152B
    bi = 0;

    while (bi < 768)
    {
        do
        {
            nvm_error_code = nvm2_read_buffer(IMAGE_LOCATION + (bi * NVMCTRL_PAGE_SIZE), nvm_buff, NVMCTRL_PAGE_SIZE);
        }
        while (nvm_error_code == STATUS_BUSY);

        do
        {
            nvm_error_code = nvm2_erase_row(bi * NVMCTRL_PAGE_SIZE);
        }
        while (nvm_error_code == STATUS_BUSY);            
            
        do
        {
            nvm_error_code = nvm2_write_buffer(bi * NVMCTRL_PAGE_SIZE, nvm_buff, NVMCTRL_PAGE_SIZE);
        }
        while (nvm_error_code == STATUS_BUSY);
        bi++;
    }

    system_reset();
}

 

I edited a copy of nvm2.h to indicate all functions are addressed in the BOOTLOADER_SECTION which is 0x1e000 and up.

 

 

Thanks

Attachment(s): 

Last Edited: Tue. Jun 4, 2019 - 05:54 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

NVM, I got this working. phew!