ZHCU861A March 2021 – August 2022 TM4C1230C3PM , TM4C1230D5PM , TM4C1230E6PM , TM4C1230H6PM , TM4C1231C3PM , TM4C1231D5PM , TM4C1231D5PZ , TM4C1231E6PM , TM4C1231E6PZ , TM4C1231H6PGE , TM4C1231H6PM , TM4C1231H6PZ , TM4C1232C3PM , TM4C1232D5PM , TM4C1232E6PM , TM4C1232H6PM , TM4C1233C3PM , TM4C1233D5PM , TM4C1233D5PZ , TM4C1233E6PM , TM4C1233E6PZ , TM4C1233H6PGE , TM4C1233H6PM , TM4C1233H6PZ , TM4C1236D5PM , TM4C1236E6PM , TM4C1236H6PM , TM4C1237D5PM , TM4C1237D5PZ , TM4C1237E6PM , TM4C1237E6PZ , TM4C1237H6PGE , TM4C1237H6PM , TM4C1237H6PZ , TM4C123AE6PM , TM4C123AH6PM , TM4C123BE6PM , TM4C123BE6PZ , TM4C123BH6PGE , TM4C123BH6PM , TM4C123BH6PZ , TM4C123BH6ZRB , TM4C123FE6PM , TM4C123FH6PM , TM4C123GE6PM , TM4C123GE6PZ , TM4C123GH6PGE , TM4C123GH6PM , TM4C123GH6PZ , TM4C123GH6ZRB , TM4C123GH6ZXR , TM4C1290NCPDT , TM4C1290NCZAD , TM4C1292NCPDT , TM4C1292NCZAD , TM4C1294KCPDT , TM4C1294NCPDT , TM4C1294NCZAD , TM4C1297NCZAD , TM4C1299KCZAD , TM4C1299NCZAD , TM4C129CNCPDT , TM4C129CNCZAD , TM4C129DNCPDT , TM4C129DNCZAD , TM4C129EKCPDT , TM4C129ENCPDT , TM4C129ENCZAD , TM4C129LNCZAD , TM4C129XKCZAD , TM4C129XNCZAD
在本节中,将使用适用于 EK-TM4C123GXL LaunchPad 开发套件的 TivaWare boot_serial 示例作为引导加载程序固件,并将使用 hello 示例作为应用程序代码。
boot_serial 示例仅包含 bl_config.h 文件,因为闪存引导加载程序本身是 TivaWare boot_loader 文件夹的一部分。对引导加载程序的任何修改可通过 bl_config 文件完成,可在文件中选择串行接口并进行修改,包括选择要使用的模块和引脚(不同于锁定至特定引脚的 ROM 引导加载程序)。另一项重要功能是能够设置起始地址。起始地址定义为 APP_START_ADDRESS,它用于确定由引导加载程序加载的应用程序在闪存中的起始地址。需要将引导加载程序置于从 0x0000.0000 地址开始的闪存中,因此需要起始地址。APP_START_ADDRESS 的大小是根据引导加载程序代码的长短定义的。它用于在引导加载流程结束时跳至应用程序代码的起始位置,并开始执行它。
#define APP_START_ADDRESS 0x2800
TM4C123x 器件和 TM4C129x 器件的 APP_START_ADDRESS 有所不同,因为不同系列的闪存结构存在差异。通常,确定起始地址时有两个主要考虑因素。第一个是矢量表必须与 1024 字节页的边界对齐。第二个因素是在对应用程序代码进行编程时,不能擦除引导加载程序,因为闪存是按扇区擦除的。
对于 TM4C123x 器件,闪存扇区的大小为 1kB,但对于 TM4C129x 器件,大小为 16kB。为了避免引导加载程序和应用程序位于同一扇区中,最简单的解决方案是从引导加载程序结束后的第一个扇区边界开始存储应用程序。这还可以满足矢量表与 1024 字节页边界对齐的要求。对于使用随附的 TivaWare 闪存引导加载程序的 TM4C123x 器件,起始地址设置为 0x2800,这是不存在任何引导加载程序代码的第一个扇区。对于 TM4C129x 器件,起始地址设置为 0x4000,因为扇区大小为 16kB。
定义起始地址后,下一步是编译将要引导加载的应用程序代码,因此起始地址将体现在生成的二进制文件中。可以通过修改 CCS 工程的链接器命令文件来实现此操作。打开 hello 工程或将其导入 CCS 后,找到 hello_ccs.cmd 文件并双击,即可在 CCS 链接器命令文件编辑器中打开该文件。本文件中有两个重要的代码部分,即 #define 语句设置的地址基址和系统存储器映射。
#define APP_BASE 0x00000000
#define RAM_BASE 0x20000000
/* 系统存储器映射 */
MEMORY
{
/* 应用程序存储在内部闪存中并通过其执行 */
FLASH (RX) : origin = APP_BASE, length = 0x00040000
SRAM (RWX) : origin = RAM_BASE, length = 0x00008000
}
为了准备与引导加载程序搭配使用的 hello,请首先更新 APP_BASE 存储器地址,体现 bl_config 中的 APP_START_ADDRESS。引导加载程序会占用从 0x0000.0000 到 APP_BASE 的存储空间,因此必须更新系统存储器映射中的 length 字段,以体现应用程序可用的闪存空间。length 字段是总器件闪存减去引导加载程序所需的空间。在本例中,0x0004.0000 – 0x0000.2800 等于 0x0003.D800。一种能最大限度地减小误差的简单方法是直接从定义的 length 值中减去 APP_BASE。
#define APP_BASE 0x00002800
#define RAM_BASE 0x20000000
/* 系统存储器映射 */
MEMORY
{
/* 应用程序存储在内部闪存中并通过其执行 */
FLASH (RX) : origin = APP_BASE, length = 0x00040000 - APP_BASE
SRAM (RWX) : origin = RAM_BASE, length = 0x00008000
}
完成这些更改后,保存更新的 .cmd 文件,然后重新编译工程,在 Debug 文件夹中生成更新的 .out 和 .bin 文件。现在,hello 工程已准备就绪,可通过 boot_serial 引导加载程序加载。
使用 Code Composer Studio 的最后一步是使用 boot_serial 工程对目标器件进行编程。由于引导加载程序没有 main 函数,IDE 将不提供在编程后运行固件的选项,这意味着引导加载程序已成功编程。