zoukankan      html  css  js  c++  java
  • 浅析NRF51822合并文件之app_valid_setting_apply

    【原创出品§转载请注明出处】

    出处:http://www.cnblogs.com/libra13179/p/5787084.html

    我们打开app_valid_setting_apply.hex如下

    :020000040003F7
    :10FC00000100000000000000FE000000FFFFFFFFF9
    :00000001FF

    分析如下

    对数据帧结构

    冒号
    本行数据长度
    本行数据的起始地址
    数据类型
    数据
    校验码
    (红色)
    (紫色)
    (绿色)
    (蓝色)
    (黑色)
    (橙色)
     
    1byte
    2byte
    1byte
    N byte
    1byte

    补充

    数据类型

    '00' Data Rrecord:用来记录数据,HEX文件的大部分记录都是数据记录

    '01' End of File Record:用来标识文件结束,放在文件的最后,标识HEX文件的结尾

    '02' Extended Segment Address Record:用来标识扩展段地址的记录

    '03' Start Segment Address Record:开始段地址记录

    '04' Extended Linear Address Record:用来标识扩展线性地址的记录

    '05' Start Linear Address Record:开始线性地址记录

    好了现在正式开始

    :020000040003F7
    :10FC00000100000000000000FE000000FFFFFFFFF9
    :00000001FF
    
    :020000040008F2
    :10 0004 00 FF00A0E314209FE5001092E5011092E5 A3
    :00000001FF       
    对上面的HEX文件进行分析:
    第1条记录的长度为02,LOAD OFFSET为0000,RECTYPE为04,说明该记录为扩展段地址记录。数据为0003,校验和为F7
    从这个记录的长度和数据,我们可以计算出一个基地址,这个地址为(
    0x0003 << 16)。后面的数据记录都以这个地址为基地址。 第2条记录的长度为1016),LOAD OFFSET为FC00,RECTYPE为00,说明该记录为数据记录。数据为0100000000000000FE000000FFFFFFFF,共16个BYTE。这个记录的校验和为F9
    此时的基地址为0X30000,加上OFFSET,这个记录里的16BYTE的数据的起始地址就是0x30000 + 0xFC00 = 0x3FC00. 第3条记录的长度为00,LOAD OFFSET为0000,TYPE= 01,校验和为FF。说明这个是一个END OF FILE RECORD,标识文件的结尾。

    问题来了这个0x3FC00是什么鬼??

    在dfu_types.H文件中

    #ifdef NRF51
    #ifdef SIGNING
    #define BOOTLOADER_REGION_START         0x00039C00                                                    /**< This field should correspond to start address of the bootloader, found in UICR.RESERVED, 0x10001014, register. This value is used for sanity check, so the bootloader will fail immediately if this value differs from runtime value. The value is used to determine max application size for updating. */
    #define BOOTLOADER_SETTINGS_ADDRESS     0x0003D800                                                    /**< The field specifies the page location of the bootloader settings address. */
    #else
    #define BOOTLOADER_REGION_START         0x0003C000                                                      /**< This field should correspond to start address of the bootloader, found in UICR.RESERVED, 0x10001014, register. This value is used for sanity check, so the bootloader will fail immediately if this value differs from runtime value. The value is used to determine max application size for updating. */
    #define BOOTLOADER_SETTINGS_ADDRESS     0x0003FC00                                                      /**< The field specifies the page location of the bootloader settings address. */
    #endif
    
    #define CODE_PAGE_SIZE                  0x0400                                                          /**< Size of a flash codepage. Used for size of the reserved flash space in the bootloader region. Will be runtime checked against NRF_UICR->CODEPAGESIZE to ensure the region is correct. */
    #elif NRF52
    #define BOOTLOADER_REGION_START         0x0007B000                                                      /**< This field should correspond to start address of the bootloader, found in UICR.RESERVED, 0x10001014, register. This value is used for sanity check, so the bootloader will fail immediately if this value differs from runtime value. The value is used to determine max application size for updating. */
    #define BOOTLOADER_SETTINGS_ADDRESS     0x0007F000                                                      /**< The field specifies the page location of the bootloader settings address. */
    #define CODE_PAGE_SIZE                  0x1000                                                          /**< Size of a flash codepage. Used for size of the reserved flash space in the bootloader region. Will be runtime checked against NRF_UICR->CODEPAGESIZE to ensure the region is correct. */
    #else
    #error No target defined
    #endif


    我们继续跟踪

    #if defined ( __CC_ARM )
    uint8_t  m_boot_settings[CODE_PAGE_SIZE] __attribute__((at(BOOTLOADER_SETTINGS_ADDRESS))) __attribute__((used));              /**< This variable reserves a codepage for bootloader specific settings, to ensure the compiler doesn't locate any code or variables at his location. */
    uint32_t m_uicr_bootloader_start_address __attribute__((at(NRF_UICR_BOOT_START_ADDRESS))) = BOOTLOADER_REGION_START;            /**< This variable ensures that the linker script will write the bootloader start address to the UICR register. This value will be written in the HEX file and thus written to UICR when the bootloader is flashed into the chip. */
    #elif defined ( __GNUC__ )
    __attribute__ ((section(".bootloaderSettings"))) uint8_t m_boot_settings[CODE_PAGE_SIZE];                                       /**< This variable reserves a codepage for bootloader specific settings, to ensure the compiler doesn't locate any code or variables at his location. */
    __attribute__ ((section(".uicrBootStartAddress"))) volatile uint32_t m_uicr_bootloader_start_address = BOOTLOADER_REGION_START; /**< This variable ensures that the linker script will write the bootloader start address to the UICR register. This value will be written in the HEX file and thus written to UICR when the bootloader is flashed into the chip. */
    #elif defined ( __ICCARM__ )
    __no_init uint8_t m_boot_settings[CODE_PAGE_SIZE] @ 0x0003FC00;                                                                 /**< This variable reserves a codepage for bootloader specific settings, to ensure the compiler doesn't locate any code or variables at his location. */
    __root    const uint32_t m_uicr_bootloader_start_address @ 0x10001014 = BOOTLOADER_REGION_START;                                /**< This variable ensures that the linker script will write the bootloader start address to the UICR register. This value will be written in the HEX file and thus written to UICR when the bootloader is flashed into the chip. */
    #endif

    我们看到这个

    void bootloader_util_settings_get(const bootloader_settings_t ** pp_bootloader_settings)
    {
        // Read only pointer to bootloader settings in flash. 
        bootloader_settings_t const * const p_bootloader_settings =
            (bootloader_settings_t *)&m_boot_settings[0];        
    
        *pp_bootloader_settings = p_bootloader_settings;
    }

    看到这个我们将0100000000000000FE000000FFFFFFFF的具体含义了

    /**@brief Structure holding bootloader settings for application and bank data.
     */
    typedef struct
    {
        bootloader_bank_code_t bank_0;          /**< Variable to store if bank 0 contains a valid application. */
        uint16_t               bank_0_crc;      /**< If bank is valid, this field will contain a valid CRC of the total image. */
        bootloader_bank_code_t bank_1;          /**< Variable to store if bank 1 has been erased/prepared for new image. Bank 1 is only used in Banked Update scenario. */
        uint32_t               bank_0_size;     /**< Size of active image in bank0 if present, otherwise 0. */
        uint32_t               sd_image_size;   /**< Size of SoftDevice image in bank0 if bank_0 code is BANK_VALID_SD. */
        uint32_t               bl_image_size;   /**< Size of Bootloader image in bank0 if bank_0 code is BANK_VALID_SD. */
        uint32_t               app_image_size;  /**< Size of Application image in bank0 if bank_0 code is BANK_VALID_SD. */
        uint32_t               sd_image_start;  /**< Location in flash where SoftDevice image is stored for SoftDevice update. */
    } bootloader_settings_t;
  • 相关阅读:
    hibernate中对象的3种状态:瞬时态(Transient)、 持久态(Persistent)、脱管态(Detached)
    object references an unsaved transient instance
    前端JS利用canvas的drawImage()对图片进行压缩
    js获取上传图片的尺寸大小
    多线程经典问题1——主线程子线程交替问题
    hdu 1689 Alien’s Necklace (bfs层次图剪枝)
    新炬数据库大师—暑期公益体验课
    怎样高速地安装Ubuntu SDK
    Spring boot 整合spring Data JPA+Spring Security+Thymeleaf框架(上)
    iOS 合并.a文件,制作通用静态库
  • 原文地址:https://www.cnblogs.com/libra13179/p/5787084.html
Copyright © 2011-2022 走看看