LowPowerLab Forum

Hardware support => Moteino => Topic started by: TomWS on January 01, 2015, 09:56:31 PM

Title: Wireless Programming Flash Memory format
Post by: TomWS on January 01, 2015, 09:56:31 PM
Felix,
I'm looking at an alternate way to get program updates to my Motes since my gateway infrastructure coupled with the VERY low duty cycle of Motes being online isn't conducive to using the existing WirelessProgramming method without SOME change.   I have a number of ideas and virtually all of them would send the Intel Hex file in a rather piecemeal (but highly structured) way. 

I've been looking at your WirelessProgramming library and I think I understand how the Flash Memory should be programmed to take advantage of your dualOptiboot loader, but I wanted to check with you to verify my interpretation.

As I see it:
And there is no other formatting requirements.  Am I correct?

Tom
Title: Re: Wireless Programming Flash Memory format
Post by: Felix on January 02, 2015, 09:00:10 AM
Quote from: TomWS on January 01, 2015, 09:56:31 PM
Felix,
I'm looking at an alternate way to get program updates to my Motes since my gateway infrastructure coupled with the VERY low duty cycle of Motes being online isn't conducive to using the existing WirelessProgramming method without SOME change.   I have a number of ideas and virtually all of them would send the Intel Hex file in a rather piecemeal (but highly structured) way. 

I've been looking at your WirelessProgramming library and I think I understand how the Flash Memory should be programmed to take advantage of your dualOptiboot loader, but I wanted to check with you to verify my interpretation.

As I see it:

  • the new code needs to start at the 0th byte in the Flash Memory.
  • the first field in the Flash MUST have 'FLXIMG:nn:', where 'nn' is the binary number of bytes-10 (for this header) of all data written to Flash
  • the subsequent fields are data records that get written to flash and are the following format:

    • 'FLX:ss:', where 'ss' is 1-4 ascii digits of incrementally increasing sequence number starting at 0, followed by...
    • 'iiiiiiiii', where 'iiiiiii' is the complete intel Hex record in binary form excluding the leading ':' (since you've got that in the prefix)
    • the eof line of the intel record isn't stored in the Flash.
And there is no other formatting requirements.  Am I correct?

Tom
Only the header is special and contains the FLXIMG:NN: 10 byte signature. The NN is 2 bytes (16bits, represents up to 65536 bytes following the signature). The rest is just that, hex bytes waiting to be copied to atmega's internal flash memory. The program data gets copied starting from position 0 in the atmega flash memory (the bootloader sits in the last 1k of the 32k of atmega flash). The FLXIMG image in external flash also sits starting at position 0 and occupies up to the first 2 (two) 32K sectors of the external FLASH memory chip, this is to keep things simple. This could be moved but it would require modding the bootloader to check elsewhere.
The FLX:ss: signature you're referring to is only used by the wireless packets which ensure integrity and continuity of the HEX image being transmitted. That signature is eliminated before writing each record in FLASH.

So what ends up in external FLASH for the bootloader to check is this:
FLXIMG:NN:nnnnnnnnnnnnnnnnnnnnnn
Where NN is a 16 bit number that is == the count of nn bytes following. Nothing more. Then the bootloader will copy this many bytes into atmega flash, delete the first(and second) 32k sectors in the external FLASH and restart the MCU. I hope that made sense.
Title: Re: Wireless Programming Flash Memory format
Post by: TomWS on January 02, 2015, 09:17:51 AM
Quote from: Felix on January 02, 2015, 09:00:10 AM
<...snip>
Only the header is special and contains the FLXIMG:NN: 10 byte signature. The NN is 2 bytes (16bits, represents up to 65536 bytes following the signature). The rest is just that, hex bytes waiting to be copied to atmega's internal flash memory. The program data gets copied starting from position 0 in the atmega flash memory (the bootloader sits in the last 1k of the 32k of atmega flash). The FLXIMG image in external flash also sits starting at position 0 and occupies up to the first 2 (two) 32K sectors of the external FLASH memory chip, this is to keep things simple. This could be moved but it would require modding the bootloader to check elsewhere.
The FLX:ss: signature you're referring to is only used by the wireless packets which ensure integrity and continuity of the HEX image being transmitted. That signature is eliminated before writing each record in FLASH.

So what ends up in external FLASH for the bootloader to check is this:
FLXIMG:NN:nnnnnnnnnnnnnnnnnnnnnn
Where NN is a 16 bit number that is == the count of nn bytes following. Nothing more. Then the bootloader will copy this many bytes into atmega flash, delete the first(and second) 32k sectors in the external FLASH and restart the MCU. I hope that made sense.
Thanks for the fast response, Felix!

Yes, it does make sense, but let me confirm, all the ADDRESS fields are stripped from the intel Hex records and the only thing stored in :nnnn... are NN number of code bytes with the first byte at offset 10 mapping to the 0th flash address in the AtMega328P?

I didn't look at more than a couple of HEX files.  Are they always contiguous data starting at address 0?

Also, it is my working assumption that the Bootloader won't do anything with the data in external flash until the two NN bytes contain a non-zero value.  Is this correct?     The reason I'm asking is that there is a possibility that the device might get reset before the entire block is copied and NN gets set to non-zero, the rest of the header would be in place, however.  I can work around this, if necessary, just need to know...

Thanks again,
Tom
UPDATE:  Never mind, I looked at the Optiboot.c code and saw that it's the FLXIMG:--: pattern that triggers the loader.  In fact, it looks like it doesn't check the count other than to confirm that its even...  In any case, I think I can simply load the code into external flash starting at address 10 and, when all the bytes are written, then fill out the first ten bytes with the signature and byte count.  Thanks again, this has saved me a lot of time (and nerve racking debugging)!
Title: Re: Wireless Programming Flash Memory format
Post by: Felix on January 02, 2015, 10:59:45 AM
Yes the intel HEX format is "processed" because they are big endian and need to be made little endian before the atmega can use them, everything else is stripped and only the raw hex program data is kept.
The two NN hex image length bytes (FLXIMG:NN:) are only written at the very end after the whole image has been stored in flash and ready to be bootloaded. This ensures that if there is any glitch or anything goes wrong, power cycle or reset, the data won't be corrupted. If the bootloader can't find a non zero NN bytes after the FLXIMG: signature it won't do anything.
And yes the flash image starts at 0 and is contiguous, the assumption being that the generated intel HEX file is also contiguous and won't skip any address blocks, at least i've never seen anything like that from avrgcc generated hex files.
Title: Re: Wireless Programming Flash Memory format
Post by: TomWS on January 02, 2015, 12:02:51 PM
Quote from: Felix on January 02, 2015, 10:59:45 AM
Yes the intel HEX format is "processed" because they are big endian and need to be made little endian before the atmega can use them, everything else is stripped and only the raw hex program data is kept.
The two NN hex image length bytes (FLXIMG:NN:) are only written at the very end after the whole image has been stored in flash and ready to be bootloaded. This ensures that if there is any glitch or anything goes wrong, power cycle or reset, the data won't be corrupted. If the bootloader can't find a non zero NN bytes after the FLXIMG: signature it won't do anything.
And yes the flash image starts at 0 and is contiguous, the assumption being that the generated intel HEX file is also contiguous and won't skip any address blocks, at least i've never seen anything like that from avrgcc generated hex files.
Thanks again, Felix.
Looking at the Optiboot.c code, however, tells me that the signature is all that's needed to trigger the bootloader to transfer NN bytes to storage, block erase the external flash, and reboot.  If NN is 0 then nothing is transferred, but it will all be lost with the block erase.  Not a problem for me, I'm going to wait to write the entire signature, with NN, once ALL the code has been saved in external flash.

Also, I thought about whether the intel records are contiguous or not and concluded that it doesn't matter to me.  For any intel record containing:
<len><addr><type><code><checksum>  I can use <addr>+10 to store the block in external flash and set NN to the last record's <addr>+<len>.  If there are gaps in the code blocks, they'll be left unwritten in external flash but the subsequent blocks will be properly mapped into the AtMega...

Tom