i.MX RT1050 简单上手
600MHz的CM7能做什么?
i.MX RT1050 简单上手
1. 前言
i.MX RT1050大概是能买到的比较便宜的Cortex-M7 MCU了,本文介绍从裸Linux环境开始配置完整工作环境。
2. 硬件准备
- i.MX RT1050开发板
- JTAG/SWD调试器
- 足够多的USB线和杜邦线
3. 软件准备
- ARM GCC(任意版本,>= 7)
- CMake
- OpenOCD(越新越好)
- 文本编辑器(任意)
4. OpenOCD调试环境准备
- 在任意位置保存如下target配置
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
# NXP i.MX RT1050 family (Arm Cortex-M7 @ 600 MHz)
#
if { [info exists CHIPNAME] } {
set _CHIPNAME $CHIPNAME
} else {
set _CHIPNAME imxrt1050
}
source [find target/swj-dp.tcl]
if { [info exists CPU_SWD_TAPID] } {
set _CPU_SWD_TAPID $CPU_SWD_TAPID
} else {
set _CPU_SWD_TAPID 0x0bd11477
}
if { [using_jtag] } {
set _CPU_TAPID 0
} else {
set _CPU_TAPID $_CPU_SWD_TAPID
}
swj_newdap $_CHIPNAME cpu -irlen 4 -expected-id $_CPU_TAPID
set _TARGETNAME $_CHIPNAME
dap create $_TARGETNAME.dap -chain-position $_TARGETNAME.cpu
target create $_TARGETNAME cortex_m -dap $_TARGETNAME.dap
if { ![using_hla] } {
cortex_m reset_config sysresetreq
}
gdb_breakpoint_override hard # 调试XIP Flash应用时,见说明
adapter_khz 1000
- 根据你的JTAG Adapter,选择合适的配置文件
- 运行OpenOCD,直到看到类似的消息代表识别成功
- OpenOCD会自动选择断点模式,Flash区域应使用硬件断点,否则无法命中。由于i.MX RT1050 无片上Flash,Config中并未加入Flash bank的定义,而是强制全局使用硬件断点以避免这种情况。RT1050的Cortex-M7拥有8个硬件断点,这对于大多数调试情况都足够了。个人使用时也可以加入自己板子定义的Flash区域,但目前(2018.12现在)OpenOCD并不支持RT1050的Flash读写,所以仅能用来自动配置断点类型。
1
openocd -f ~/Documents/Conf/OpenOCD/interface/ft232-swd.cfg -f ~/Documents/Conf/OpenOCD/target/imxrt1050.cfg
1
2
3
4
5
6
7
8
9
10
11
12
13
14
Open On-Chip Debugger 0.10.0+dev-00523-g2a3b709aa (2018-08-30-22:25)
Licensed under GNU GPL v2
For bug reports, read
http://openocd.org/doc/doxygen/bugs.html
Info : FTDI SWD mode enabled
adapter speed: 2000 kHz
cortex_m reset_config sysresetreq
adapter speed: 1000 kHz
Info : Listening on port 6666 for tcl connections
Info : Listening on port 4444 for telnet connections
Info : clock speed 1000 kHz
Info : SWD DPIDR 0x0bd11477
Info : imxrt1050: hardware has 8 breakpoints, 4 watchpoints
Info : Listening on port 3333 for gdb connections
5. 示例工程准备
- 从 https://mcuxpresso.nxp.com/en/dashboard 添加并下载i.MX RT1050的SDK,根据芯片型号选择对应的SDK。(测试中Rev.1 和Rev.2可以互换但不建议使用)
- 从NXP网站下载 Config Tool。
- 解压deb,选择合适的位置放置Config Tool,运行
/path/to/config_tool/bin/tool并选择解压到SDK的位置,从示例创建新工程,类型选择ARM GCC。
6. 编译示例工程
- 在工程目录中运行
ARMGCC_DIR=/path/to/arm_gcc ./build_debug.sh即可编译出ELF - 在工程目录中运行
ARMGCC_DIR=/path/to/arm_gcc ./build_flexspi_nor_debug.sh - 由于第二步中我们选择了flexspi_nor配置,该程序将被链接进FlexSPI NOR Flash区域(
0x60000000);第一步中的ELF则被链接进SRAM区域。
7. 调试
- 运行GDB连接OpenOCD并加载elf,载入ELF到设备SRAM并跳转入口点即可开始调试(注:事先需要halt CPU)
- 以下步骤中continue位置不建议使用,应使用
jump *entry_point跳转程序入口点开始执行。 - 本例中程序入口点位于
0x468,即jump *0x468。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
130 imi415@imi415 ..dwares/Kinetis_Projects/freertos_hello % arm-none-eabi-gdb -ex "target remote localhost:3333" debug/freertos_hello.elf :(
GNU gdb (GDB) 8.1.1
Copyright (C) 2018 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law. Type "show copying"
and "show warranty" for details.
This GDB was configured as "--host=x86_64-pc-linux-gnu --target=arm-none-eabi".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
<http://www.gnu.org/software/gdb/documentation/>.
For help, type "help".
Type "apropos word" to search for commands related to "word"...
Reading symbols from debug/freertos_hello.elf...done.
Remote debugging using localhost:3333
0x600044d6 in ?? ()
(gdb) load
Loading section .interrupts, size 0x400 lma 0x0
Loading section .text, size 0x5c08 lma 0x400
Loading section .ARM, size 0x8 lma 0x6008
Loading section .init_array, size 0x4 lma 0x6010
Loading section .fini_array, size 0x4 lma 0x6014
Loading section .data, size 0x6c lma 0x6018
Start address 0x468, load size 24708
Transfer rate: 69 KB/sec, 3529 bytes/write.
(gdb) b main
Breakpoint 1 at 0x4afa: file /home/imi415/Documents/Hardwares/Kinetis_Projects/freertos_hello/source/freertos_hello.c, line 68.
(gdb) c
Continuing.
Breakpoint 1, main () at /home/imi415/Documents/Hardwares/Kinetis_Projects/freertos_hello/source/freertos_hello.c:68
68 BOARD_ConfigMPU();
(gdb)
8. 下载程序到FlexSPI NOR Flash 并启用XIP
- 根据开发板制造商的参数修改
xip目录下文件,配置XIP Header。 - NOR Flash XIP Header类似下方
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
#include "fire_imxrt1050_flexspi_nor_config.h"
/*******************************************************************************
* Code
******************************************************************************/
#if defined(XIP_BOOT_HEADER_ENABLE) && (XIP_BOOT_HEADER_ENABLE == 1)
#if defined(__CC_ARM) || defined(__GNUC__)
__attribute__((section(".boot_hdr.conf")))
#elif defined(__ICCARM__)
#pragma location = ".boot_hdr.conf"
#endif
const flexspi_nor_config_t spiflash_config = {
.memConfig =
{
.tag = FLEXSPI_CFG_BLK_TAG, /*标志:FCFB*/
.version = FLEXSPI_CFG_BLK_VERSION, /*版本:V1.4.0*/
.readSampleClkSrc = kFlexSPIReadSampleClk_LoopbackInternally, /*内部环回*/
.csHoldTime = 3u, /*保持时间*/
.csSetupTime = 3u, /*建立时间*/
.columnAddressWidth = 0u, /*列地址宽度*/
.deviceModeCfgEnable = 1u, /*设备模式配置使能*/
.deviceModeType = 1u, /*Quad 使能命令*/
.deviceModeSeq.seqNum = 1u, /*LUT序列号*/
.deviceModeSeq.seqId = 4u, /*LUT序列索引*/
.deviceModeArg = 0x000200, /*设置 QE=1(S9)*/
.deviceType = kFlexSpiDeviceType_SerialNOR, /*设备类型为nor flash*/
.sflashPadType = kSerialFlash_4Pads, /*设备数据总线为4*/
.serialClkFreq = kFlexSpiSerialClk_133MHz, /*flash 时钟*/
.sflashA1Size = 32u * 1024u * 1024u, /*flash 大小32MBytes*/
//.dataValidTime = {16u, 16u},
.lookupTable =
{
/*快速读命令(四线)*/
[0] = FLEXSPI_LUT_SEQ(CMD_SDR, FLEXSPI_1PAD, 0xEB, RADDR_SDR, FLEXSPI_4PAD, 0x18),
[1] = FLEXSPI_LUT_SEQ(DUMMY_SDR, FLEXSPI_4PAD, 0x06, READ_SDR, FLEXSPI_4PAD, 0x04),
/*读状态命令*/
[1 * 4] = FLEXSPI_LUT_SEQ(CMD_SDR, FLEXSPI_1PAD, 0x05, READ_SDR, FLEXSPI_1PAD, 0x04),
/*写使能命令*/
[3 * 4] = FLEXSPI_LUT_SEQ(CMD_SDR, FLEXSPI_1PAD, 0x06, STOP, FLEXSPI_1PAD, 0),
/*擦除扇区命令*/
[5 * 4] = FLEXSPI_LUT_SEQ(CMD_SDR, FLEXSPI_1PAD, 0x20, RADDR_SDR, FLEXSPI_1PAD, 0x04),
/*页编程命令(四线)*/
[9 * 4] = FLEXSPI_LUT_SEQ(CMD_SDR, FLEXSPI_1PAD, 0x32, RADDR_SDR, FLEXSPI_1PAD, 0x18),
[9 * 4 + 1] = FLEXSPI_LUT_SEQ(WRITE_SDR, FLEXSPI_4PAD, 0x04, STOP, FLEXSPI_1PAD, 0),
/*整片擦除*/
[11 * 4] = FLEXSPI_LUT_SEQ(CMD_SDR, FLEXSPI_1PAD, 0xc7, STOP, FLEXSPI_1PAD, 0),
},
},
.pageSize = 256u, /*页大小为256字节*/
.sectorSize = 4u * 1024u, /*扇区大小为4k字节*/
};
#endif /* XIP_BOOT_HEADER_ENABLE */
- 从NXP下载Flashloader并解压
- 通过GDB将
Flashloader/flashloader.elf下载到内存并执行(步骤同RAM调试步骤,需要跳转程序入口点开始执行。) -
将ELF转换为
srec或ihxarm-none-eabi-objcopy -O srec freertos_hello.elf freertos_hello.srec
- 连接USB OTG1,会有一个新USB HID设备连接到主机
- 运行下列命令初始化NOR Flash并写入程序
1
2
3
sudo ./blhost -u -V fill-memory 0x2000 0x04 0xc0000006
sudo ./blhost -u -V -t 30000 configure-memory 0x09 0x2000
sudo ./blhost -u -V -t 30000 flash-image ~/freertos_hello.srec erase
根据Flash类型调整第一条命令的值。
- Flash 识别状态可以通过如下命令查看。
1
sudo ./blhost -u -V list-memory
9. 总结
环境是第一步,代码尚未成功,同志仍需努力:)
This post is licensed under CC BY 4.0 by the author.

