Image Layout

本节主要介绍 Flash 布局Image 格式

Flash 布局

RTL8752H 的 Flash 布局 如下,由 Reserved,OEM Header(即 Config File 的存储空间),OTA Bank0,OTA Bank1,FTL,OTA TMP,User Data1 和 User Data2 组成。访问 Flash 的起始地址为 0x00800000。

../../../_images/Flash_Layout.png

Flash 布局

Flash 空间分布和功能说明

内存段

起始地址

大小(字节)

功能

是否支持 DFU 升级

OEM Header

0x00801000

0x1000

配置信息存储区域,包括蓝牙地址和用户可修改的 Flash 布局等内容

OTA Bank0

可变(由 OEM Header 决定)

可变(由 OEM Header 决定)

OTA Bank0 主要用于存储设备的固件和运行时数据

具体功能请参考 OTA Bank Flash 布局

OTA Bank1

可变(由 OEM Header 决定)

可变(由 OEM Header 决定)

对于支持 Bank 切换的 DFU 方案

  • 如果 OTA Bank0 是运行区,那么 OTA Bank1 将作为备份区

  • 反之,如果 OTA Bank1 是运行区,OTA Bank0 将作为备份区

FTL

可变(由 OEM Header 决定)

可变(由 OEM Header 决定)

该区域空间支持以逻辑地址访问 Flash

OTA TMP

可变(由 OEM Header 决定)

可变(由 OEM Header 决定)

使用不支持 Bank 切换的 DFU 方式下,作为 OTA 备份区使用

大小必须不小于 OTA Bank0 最大的 image 大小

User Data1

可变(由 OEM Header 决定)

可变(由 OEM Header 决定)

Flash 剩余未划分区域,用户可以自由使用

User Data2

可变(由 OEM Header 决定)

可变(由 OEM Header 决定)

Flash 剩余未划分区域,用户可以自由使用

OTA Bank 内部的布局和说明如下:

../../../_images/Layout_of_OTA_Bank.png

OTA Bank 布局

OTA Bank Flash 布局

内存段

起始地址

大小(字节)

功能

是否支持 DFU 升级

OTA Header

由 OEM Header 决定

4KB

存储 OTA Header 的版本信息,Bank 中存在 image 的起始地址和大小

是(当支持Bank切换

否(当不支持Bank切换

ROM Patch

由 OTA Header 决定

可变

ROM 中平台功能的优化和扩展代码

Secure Boot Loader

由 OTA Header 决定

可变

启动过程中对代码安全级别检查的代码

BT Stack Patch

由 OTA Header 决定

可变

蓝牙 controller 协议栈优化和扩展代码

Upperstack

由 OTA Header 决定

可变

实现 HCI 及以上蓝牙协议栈部分代码

APP

由 OTA Header 决定

可变

开发方案的运行代码

APP Data1

由 OTA Header 决定

可变

开发方案中使用的数据区

APP Data2

由 OTA Header 决定

可变

开发方案中使用的数据区

APP Data3

由 OTA Header 决定

可变

开发方案中使用的数据区

APP Data4

由 OTA Header 决定

可变

开发方案中使用的数据区

APP Data5

由 OTA Header 决定

可变

开发方案中使用的数据区

APP Config File

由 OTA Header 决定

可变

APP Config 信息

Flash 布局调整

Flash 布局设置分为以下两级:

  • High Level Flash map —— 由 OEM Header 决定

  • OTA Bank map —— 由 OTA Header 文件决定

用户可通过 MP Tool 中 Config Set 选项加载自定义的 Flash 布局文件并生成 Config File。

../../../_images/MPTool_config.png

通过 MP Tool 生成 Config File

为方便用户使用,Realtek 提供 Flash Map Generate Tool 用于生成 Flash 布局文件,说明如下:

  • flash map.ini 文件 —— 导入到 MP Tool,用于生成 Config File 和 OTA header。

  • flash_map.h 文件 —— 需要拷贝到 APP 的工程目录下,编译出正确可运行的 APP image。

../../../_images/FlashMapGenerateTool.png

Flash Map Generate Tool 配置 Flash Map

Flash 布局调整原则如下:

  1. 如果选择 支持Bank切换 的 DFU 方案,需保证 OTA Bank0 的大小等于 OTA Bank1 的大小,并且将 OTA TMP 区域的大小设置为 0。

  2. 如果选择 不支持Bank切换 的 DFU 方案,将 OTA Bank1 的大小设置为 0,OTA TMP 区域的大小不小于 OTA Bank0 中最大的 image 的大小。

  3. 为了将所有的 code 区域都上锁,防止非预期的 Flash 写入和擦除操作,尽可能地将 OTA Bank1 结束地址相对于 Flash 起始地址的偏移对齐到实际所选用的 Flash 所支持的某个保护级别对应的范围,详细请参考: 软件块保护

Flash 布局示例

基于 Flash 布局调整 的规则,本节提供 支持 Bank 切换方案不支持 Bank 切换方案 下的 Flash 布局示例。

支持 Bank 切换方案

支持 Bank 切换方案 Flash 布局示例

flash 总大小为 1MB 的示例布局

大小(字节)

起始地址

Reserved

4K

0x00800000

OEM Header

4K

0x00801000

OTA Bank0

344K

0x00802000

  • OTA Header

4K

0x00802000

  • Secure Boot Loader code

4K

0x0080A000

  • ROM Patch code

28K

0x00803000

  • BT Stack Patch code

28K

0x0080B000

  • Upperstack code

144K

0x00812000

  • APP code

132K

0x00836000

  • APP data1

0K

0x00857000

  • APP data2

0K

0x00857000

  • APP data3

0K

0x00857000

  • APP data4

0K

0x00857000

  • APP data5

0K

0x00857000

  • APP Config File

4K

0x00857000

OTA Bank1

344K

0x00858000

  • OTA Header

4K

0x00858000

  • Secure Boot Loader code

4K

0x00860000

  • ROM Patch code

28K

0x00859000

  • BT Stack Patch code

28K

0x00861000

  • Upperstack code

144K

0x00868000

  • APP code

132K

0x0088C000

  • APP data1

0K

0x008AD000

  • APP data2

0K

0x008AD000

  • APP data3

0K

0x008AD000

  • APP data4

0K

0x008AD000

  • APP data5

0K

0x008AD000

  • APP Config File

4K

0x008AD000

FTL

16K

0x008AE000

OTA TMP

0K

0x008B2000

user data1

0K

0x008B2000

user data2

0K

0x008B2000

备注

Flash 布局需要根据用户实际 image 和 data 的大小进行合理划分。

不支持 Bank 切换方案

不支持 Bank 切换方案 Flash 布局示例

flash总大小为 512KB 的示例布局

大小 (字节)

起始地址

Reserved

4K

0x00800000

OEM Header

4K

0x00801000

OTA Bank0

344K

0x00802000

  • OTA Header

4K

0x00802000

  • Secure Boot Loader code

4K

0x0080A000

  • ROM Patch code

28K

0x00803000

  • BT Stack Patch code

28K

0x0080B000

  • Upperstack code

144K

0x00812000

  • APP code

132K

0x00836000

  • APP data1

0K

0x00857000

  • APP data2

0K

0x00857000

  • APP data3

0K

0x00857000

  • APP data4

0K

0x00857000

  • APP data5

0K

0x00857000

  • APP Config File

4K

0x00857000

OTA Bank1(等于0)

0K

0x00858000

FTL

16K

0x00858000

OTA TMP

144K

0x0085C000

user data1

0K

0x00880000

user data2

0K

0x00880000

备注

此处没有分配 APP data,Flash 布局需要根据用户实际 image 和 data 的大小进行合理划分。

Image 格式

OTA Bank Flash 布局 中所有可支持升级的 image 都是由一个 1024 Bytes 大小的 image header 和不定长的 payload 部分组成。

Image header 会包含 image 类型、大小、版本号、哈希值和签名信息等,具体介绍如下:

Image header 中各字段定义

内存段

大小(字节)

功能

image_cmac

16

image 的 CMAC 值,用于在开启 secure boot 时进行认证

image_signature

384

image 的签名,用于在开启 secure boot 时进行认证

image_hash

32

image 的哈希校验,用于 image 完整性校验

image_control_header

12

image 的控制信息,具体请参考 image_control_header 格式

uuid

16

image 的 UUID

exe_base

4

image 的执行地址

load_src

4

加载到 RAM 的代码起始地址

load_len

4

加载到 RAM 的代码大小

image_base

4

image 的 flash 地址

dev_id

2

Not used

flash_layout_size_4k,

2

flash layout 大小(单位: 4KB)

magic_pattern

4

image 的 pattern 信息

dec_key

16

Not used

load_dst

4

加载到 flash 的代码起始地址

ex_info

24

image 的 heap 和 ram 信息

git_ver

16

image 的版本信息

RSA Public Key

388

用于在开启 secure boot 时进行认证

image_info

92

OTA Header 的 image_info 为 OTA Bank 内各 image 的起始地址和 size

其它 image 的 image_info 为 reserved

Image header 中 image_control_header 格式如下:

  typedef struct _IMG_CTRL_HEADER_FORMAT
  {
      uint16_t crc16;
      uint8_t ic_type;
      uint8_t secure_version;
      union
      {
          uint16_t value;
          struct
          {
              uint16_t xip: 1; // payload is executed on flash
              uint16_t enc: 1; // all the payload is encrypted
              uint16_t load_when_boot: 1; // load image when boot
              uint16_t enc_load: 1; // encrypt load part or not
              uint16_t enc_key_select: 3; // referenced to ENC_KEY_SELECT
              uint16_t not_ready: 1; //for copy image in ota
              uint16_t not_obsolete: 1; //for copy image in ota
              uint16_t integrity_check_en_in_boot: 1; // enable image integrity check in boot flow
              uint16_t compressed_not_ready: 1;
              uint16_t compressed_not_obsolete: 1;
              uint16_t rsvd: 1;
              uint16_t image_type: 3; /*for app 000b: normal image, 001b:compressed image, other for more types
              for patch in temp bank consist of 001b: patch+fsbl, 010b: patch+app, 011b: patch+fsbl+app*/
          };
      } ctrl_flag;
      uint16_t image_id;
      uint32_t payload_len;
  } T_IMG_CTRL_HEADER_FORMAT;

参数说明:

ic_type:

表示 IC type,RTL8752H IC type 值为 16。

secure_version:

表示启动安全检查 image 的版本。

image_id:

标识不同的 image 的类型枚举如下,其中 SCCD,OCCD 不能 DFU 升级。

typedef enum
{
    IMAGE_FIRST = 0x278D,
    SCCD        = 0x278D,
    OCCD        = 0x278E,
    FactoryCode = 0x278F,
    OTA         = 0x2790, /**< OTA header */
    SecureBoot  = 0x2791,
    RomPatch    = 0x2792,
    AppPatch    = 0x2793,
    AppData1    = 0x2794,
    AppData2    = 0x2795,
    AppData3    = 0x2796,
    AppData4    = 0x2797,
    AppData5    = 0x2798,
    AppConfigFile = 0x2799,
    UpperStack  = 0x279a,
    IMG_BT_STACKPATCH = 0x279b,
    IMAGE_MAX,

    IMAGE_USER_DATA2 = 0xFFFD,  /**<the image only support unsafe single bank ota*/
    IMAGE_USER_DATA = 0xFFFE,  /**<the image only support unsafe single bank ota*/
} T_IMG_ID;

参数说明:

payload_len:

单位是字节,表示 image 的大小,不包括 1024 Bytes 的 image header,image total length = payload_len + 1024。

crc16:

表示对 image 的 crc16 校验值,image 默认使用 sha256 校验,校验值存在 image_hash 中,crc16 可忽略。

ctrl_flag:

和 DFU 相关的位域只有 not_readynot_obsolete

  • not_ready: 标识 image 是否为有效。默认发布、编译或者通过工具生成的文件的 image header 中 not_ready 字段均为 0。

    • 通过蓝牙传输将 image 写入到备份区,中间可能存在断电的风险。所以在写入备份区前,需要将 not_ready 修改为 1 再写入 Flash。

    • 只有当 image 传输完成,并且 image 完整性校验成功后,修改备份区 image 中的 not_ready 为 0,标识备份区 image 有效。

    • 系统重启后,由 BootLoader 完成备份 image 的激活流程。

  • not_obsolete: 标识 image 是否废弃,默认编译的 image 中 not_obsolete 为1。

    • 当支持Bank切换时, not_obsolete 在 DFU 过程中无效。

    • 当不支持 Bank 切换时,DFU 升级完成后,启动代码判断 not_ready 为 0 且 not_obsolete 为 1,此时将 image 从 OTA TMP 区搬运到 OTA Bank0 内的对应 image 的运行区域,搬运成功后,将OTA TMP 区 image 中 not_obsolete 写为 0,防止重复搬运。