前言
在开发mcu代码的时候经常会有些疑惑,变量是怎么在编译之后进入单片机的ram区的呢,特别是在使用keil开发的时候。后来在接触gcc编译器和自研的mcu后,终于明白了这个问题。实际上变量编译后被放在了bin文件中代码的后面(data存放在bin中,bss在bin里存放了长度信息)。程序运行时会主动将该区域的数据依次加载到ram区域中。
原理
写完代码编译后,会把code中的data区的变量放在代码的后面,bss区的变量仅存放长度在bin中,当然这个规则也是由链接文件来决定的。示例图如下
在程序运行后正式进入C环境前,code中会存在一段汇编代码。主要作用就是把data区域内存依次复制到ram中,复制结束后。把后面和bss区描述长度一致区域的内存全置为0。
通过这也能够看出为什么bss区域的值会被设置为0,因为内存中是没有类型的说法。如果不全置0,无论其它哪个值都没法确认实际类型的值。(例如设置为1的话,不同的类型就会对应不同的值。int是0x1111,short是0x11)
但是在keil中我们没有看到这样的代码。keil的汇编代码如下:
Reset_Handler PROC
EXPORT Reset_Handler [WEAK