首页 / 行业
解析使用RT-Thread Studio指定特殊函数加载到RAM的方法
2021-11-18 10:06:00
用ITCM给ART-Pi(STM32H7)代码加速 , 这篇文章就提到了,将特殊的函数(如,算法相关)加载到速度更快的 ITCM,但是这篇文章中使用 GCC 编译器的时候,无法保证在断电复位后 RAM 段的代码不消失,所以本文来研究这个问题。
众所周知,RAM 是掉电丢失数据的,为了做到产品中也能使用这种操作,就需要将代码编译到 ROM 中,然后启动的时候,从 ROM 拷贝到 RAM 当中,知道了原理,具体如何操作呢?
二、RT-Thread Studio 指定特殊函数到RAM的办法
为了实现这种操作,需要知道可执行程序的生成过程,预处理- 》编译 -》汇编-》 链接,可以从这几个地方去着手解决这个问题。RTT Studio 使用的是 GCC 的编译器,所以修改相应的 GCC 文件就可以了。
1. 修改链接文件
为了实现这个目的,所以需要在链接文件中增加对应的 .section.
描述 ITCM 的属性
1MEMORY2{3ROM(rx):ORIGIN=0x90000000,LENGTH=8192k4RAM(rw):ORIGIN=0x24000000,LENGTH=512k5RxDecripSection(rw):ORIGIN=0x30040000,LENGTH=32k6TxDecripSection(rw):ORIGIN=0x30040060,LENGTH=32k7RxArraySection(rw):ORIGIN=0x30040200,LENGTH=32k8ITCM(rx):ORIGIN=0x00000000,LENGTH=64k9}
ITCM (rx):名字是 ITCM,r: Read-only sections. , x : Sections containing executable code.
ORIGIN =0x00000000: 起始地址
LENGTH =64k:总长度
构造 section
1SECTIONS 2{ 3.text: 4{ 5.=ALIGN(4); 6_stext=.; 7KEEP(*(.isr_vector))/*Startupcode*/ 8.=ALIGN(4); 9*(.text.*)10*(.rodata)/*read-onlydata(constants)*/11*(.rodata*)12*(.glue_7)13*(.glue_7t)14*(.gnu.linkonce.t*)1516/*sectioninformationforfinshshell*/17.=ALIGN(4);18__fsymtab_start=.;19KEEP(*(FSymTab))20__fsymtab_end=.;2122.=ALIGN(4);23__vsymtab_start=.;24KEEP(*(VSymTab))25__vsymtab_end=.;2627/*sectioninformationforutest*/28.=ALIGN(4);29__rt_utest_tc_tab_start=.;30KEEP(*(UtestTcTab))31__rt_utest_tc_tab_end=.;3233/*sectioninformationforatserver*/34.=ALIGN(4);35__rtatcmdtab_start=.;36KEEP(*(RtAtCmdTab))37__rtatcmdtab_end=.;38.=ALIGN(4);3940/*sectioninformationformodules*/41.=ALIGN(4);42__rtmsymtab_start=.;43KEEP(*(RTMSymTab))44__rtmsymtab_end=.;4546/*sectioninformationforinitial.*/47.=ALIGN(4);48__rt_init_start=.;49KEEP(*(SORT(.rti_fn*)))50__rt_init_end=.;5152.=ALIGN(4);5354PROVIDE(__ctors_start__=.);55KEEP(*(SORT(.init_array.*)))56KEEP(*(.init_array))57PROVIDE(__ctors_end__=.);5859.=ALIGN(4);6061_etext=.;62}>ROM6364.ITCM:65{66.=ALIGN(4);67__itcm_start=.;68*(.ITCM)69.=ALIGN(4);70__itcm_end=.;71}>ITCMAT>ROM72__itcm_rom_start=LOADADDR(.ITCM);73__itcm_size=SIZEOF(.ITCM);
这里链接文件的修改的作用是,将__attribute__((section(".ITCM"))) int main(void)
这种指定函数到特殊区域的ITCM
段的函数,编译后放到 ROM 里面,程序运行的时候从 RAM 取这个函数,这样可以在系统上电之后可以从 ROM 中把数据复制到 RAM 当中,这样就解决了上一篇文章的问题。这里定义了 2 个全局变量方便后续在汇编当中把函数从 ROM 拷贝到 RAM。
2. 修改启动汇编
startup_stm32h750xx.s
这里只做了,已初始化值的数据,从 ROM 拷贝到 RAM 的操作,所以需要增加一些代码来实现把函数从 ROM 拷贝到 RAM
修改部分:
1Reset_Handler:/*程序复位后的启动地址*/ 2ldrsp,=_estack/*设置SP*/ 3 4ldrr0,=__itcm_rom_start/*加载放在了ROM当中,需要加载到ITCM中数据的起始地址到R0*/ 5ldrr1,=__itcm_start/*加载ITCM第一个函数的起始放置位置到R1*/ 6ldrr2,=__itcm_size/*加载ITCM的大小到R2*/ 7addr2,r1,r2/*R1加R2的值放到R2*/ 8 91:10cmpr2,r1/*比较R1与R2*/11beq2f/*如果上面的比较之后是相等的则跳转到标签2*/12ldrr3,[r0],#4/*将 R0寄存器里面存放的地址处的代码,写入到 R3 寄存器里面。然后 R0+ 4 */13strr3,[r1],#4/*将R3中的数据写入以R1为地址的存储器中,然后R1+4*/14b1b/*调回到标签1,循环拷贝*/152:/*以下是未修改之前的GCC启动汇编代码*/1617/*CopythedatasegmentinitializersfromflashtoSRAM*/18movsr1,#019bLoopCopyDataInit
这里使用了数字标签,所以跳转时候标签后缀为b或f,b==back ,f == forward。
这里的拷贝方法就是,知道程序下载之后放在了 ROM 的位置,然后从这个位置拷贝到 RAM 中去。
3. 将函数指定链接位置
1__attribute__((section(".ITCM")))2intmain(void)3{4rt_uint32_tcount=0;56rt_pin_mode(LED_PIN,PIN_MODE_OUTPUT);7}
三, 总结
1、用ITCM给ART-Pi(STM32H7)代码加速提到的方法,MDK 可以实现启动的时候将 ROM 中的函数搬运到 RAM 当中的操作,使用 RTT Studio 也可以实现
2、在 GCC 的链接文件可以描述一个文件的 section 的中数据的存放地址和加载地址不一致。
3、在 RT-Thread Studio 中实现这个操作,确实比 MDK 会复杂很多,对于研究底层的人而言,在 MDK 中很难看到这些细节,喜欢自定义操作的人而言,GCC 就更加的灵活了。
最新内容
手机 |
相关内容
写flash芯片时为什么需要先擦除?
写flash芯片时为什么需要先擦除?,擦除,芯片,充电,初始状态,存储单元,数据,Flash芯片是一种非易失性存储器技术,用于存储数据并实现固半导体主控技术:驱动自动驾驶革命的
半导体主控技术:驱动自动驾驶革命的引擎,自动驾驶,交通,自动驾驶系统,数据,车辆,自动,随着科技的不断进步,自动驾驶技术已经成为现实Arbe 4D成像雷达以高分辨率雷达技
Arbe 4D成像雷达以高分辨率雷达技术和先进处理技术消除“幽灵刹车”问题,刹车,成像,分辨率,系统,目标,数据,Arbe 4D成像雷达是一种清华大学研发光电融合芯片,算力超商
清华大学研发光电融合芯片,算力超商用芯片三千余倍,芯片,研发,商用,测试,计算,科学研究,近日,清华大学发布了一项重要科研成果,他们成工业物联网数据采集:从Modbus到MQTT
工业物联网数据采集:从Modbus到MQTT,数据采集,物联网,模式,网关,协议,数据,工业物联网(Industrial Internet of Things,IIoT)的核心任务消除“间隙”:力敏传感器如何推动新
消除“间隙”:力敏传感器如何推动新颖的HMI设计,传感器,智能手机,交互,交互方式,操作,用户,随着科技的不断发展,人机交互界面(HMI)的设射频前端芯片GC1103在智能家居无线
射频前端芯片GC1103在智能家居无线通信IoT模块中应用,模块,芯片,无线通信,智能家居,支持,数据交换,射频前端芯片GC1103是一种低功耗变频器过载保护和过流保护有什么区
变频器过载保护和过流保护有什么区别?,变频器,频率,超过,损害,方法,负载,BCP55变频器过载保护和过流保护是两种不同的保护机制,用于保