@ -27,6 +27,11 @@
@@ -27,6 +27,11 @@
# include <AP_Common/ExpandingString.h>
# include "sdcard.h"
# include "shared_dma.h"
# include <AP_Common/ExpandingString.h>
# if HAL_ENABLE_SAVE_PERSISTENT_PARAMS
# include <AP_InertialSensor/AP_InertialSensor.h>
# endif
# if HAL_WITH_IO_MCU
# include <AP_BoardConfig/AP_BoardConfig.h>
@ -209,8 +214,32 @@ Util::FlashBootloader Util::flash_bootloader()
@@ -209,8 +214,32 @@ Util::FlashBootloader Util::flash_bootloader()
// make sure size is multiple of 32
fw_size = ( fw_size + 31U ) & ~ 31U ;
bool uptodate = true ;
const uint32_t addr = hal . flash - > getpageaddr ( 0 ) ;
if ( ! memcmp ( fw , ( const void * ) addr , fw_size ) ) {
if ( memcmp ( fw , ( const void * ) addr , fw_size ) ! = 0 ) {
uptodate = false ;
}
# if HAL_ENABLE_SAVE_PERSISTENT_PARAMS
// see if we should store persistent parameters along with the
// bootloader. We only do this on boards using a single sector for
// the bootloader. The persistent parameters are stored as text at
// the end of the sector
const int32_t space_available = hal . flash - > getpagesize ( 0 ) - int32_t ( fw_size ) ;
ExpandingString persistent_params { } , old_persistent_params { } ;
if ( get_persistent_params ( persistent_params ) & &
space_available > = persistent_params . get_length ( ) & &
( ! load_persistent_params ( old_persistent_params ) | |
strcmp ( persistent_params . get_string ( ) ,
old_persistent_params . get_string ( ) ) ! = 0 ) ) {
// persistent parameters have changed, we will update
// bootloader to allow storage of the params
uptodate = false ;
}
# endif
if ( uptodate ) {
Debug ( " Bootloader up-to-date \n " ) ;
AP_ROMFS : : free ( fw ) ;
return FlashBootloader : : NO_CHANGE ;
@ -249,6 +278,12 @@ Util::FlashBootloader Util::flash_bootloader()
@@ -249,6 +278,12 @@ Util::FlashBootloader Util::flash_bootloader()
continue ;
}
Debug ( " Flash OK \n " ) ;
# if HAL_ENABLE_SAVE_PERSISTENT_PARAMS
if ( persistent_params . get_length ( ) ) {
const uint32_t ofs = hal . flash - > getpagesize ( 0 ) - persistent_params . get_length ( ) ;
hal . flash - > write ( addr + ofs , persistent_params . get_string ( ) , persistent_params . get_length ( ) ) ;
}
# endif
hal . flash - > keep_unlocked ( false ) ;
AP_ROMFS : : free ( fw ) ;
return FlashBootloader : : OK ;
@ -342,3 +377,80 @@ void Util::dma_info(ExpandingString &str)
@@ -342,3 +377,80 @@ void Util::dma_info(ExpandingString &str)
ChibiOS : : Shared_DMA : : dma_info ( str ) ;
}
# endif
# if HAL_ENABLE_SAVE_PERSISTENT_PARAMS
static const char * persistent_header = " {{PERSISTENT_START_V1}} \n " ;
/*
create a set of persistent parameters in string form
*/
bool Util : : get_persistent_params ( ExpandingString & str ) const
{
str . printf ( " %s " , persistent_header ) ;
# if HAL_INS_TEMPERATURE_CAL_ENABLE
const auto * ins = AP_InertialSensor : : get_singleton ( ) ;
if ( ins ) {
ins - > get_persistent_params ( str ) ;
}
# endif
if ( str . has_failed_allocation ( ) | | str . get_length ( ) < = strlen ( persistent_header ) ) {
// no data
return false ;
}
// ensure that the length is a multiple of 32 to meet flash alignment requirements
while ( ! str . has_failed_allocation ( ) & & str . get_length ( ) % 32 ! = 0 ) {
str . append ( " \n " , 1 ) ;
}
return ! str . has_failed_allocation ( ) ;
}
/*
load a set of persistent parameters in string form from the bootloader sector
*/
bool Util : : load_persistent_params ( ExpandingString & str ) const
{
const uint32_t addr = hal . flash - > getpageaddr ( 0 ) ;
const uint32_t size = hal . flash - > getpagesize ( 0 ) ;
const char * s = ( const char * ) memmem ( ( void * ) addr , size ,
persistent_header ,
strlen ( persistent_header ) ) ;
if ( s ) {
str . append ( s , ( addr + size ) - uint32_t ( s ) ) ;
return ! str . has_failed_allocation ( ) ;
}
return false ;
}
/*
apply persistent parameters from the bootloader sector to AP_Param
*/
void Util : : apply_persistent_params ( void ) const
{
ExpandingString str { } ;
if ( ! load_persistent_params ( str ) ) {
return ;
}
char * s = str . get_writeable_string ( ) ;
char * saveptr ;
s + = strlen ( persistent_header ) ;
uint32_t count = 0 ;
for ( char * p = strtok_r ( s , " \n " , & saveptr ) ;
p ; p = strtok_r ( nullptr , " \n " , & saveptr ) ) {
char * eq = strchr ( p , int ( ' = ' ) ) ;
if ( eq ) {
* eq = 0 ;
if ( AP_Param : : set_default_by_name ( p , atof ( eq + 1 ) ) ) {
count + + ;
}
}
}
if ( count ) {
AP_Param : : invalidate_count ( ) ;
GCS_SEND_TEXT ( MAV_SEVERITY_INFO , " Loaded %u persistent parameters " ,
unsigned ( count ) ) ;
}
}
# endif // HAL_ENABLE_SAVE_PERSISTENT_PARAMS