你码的代码是如何在SOC芯片上跑起来的
前言
SOC是啥?System on Chip。一个芯片,但是片上有好多东西的意思。市面上的AI芯片、包括你知道的麒麟xxx,骁龙xxx等等一系列手机芯片都是SOC。对于SOC设计者来讲,显然要知道码农们码出来的一行行代码是如何在SOC上跑起来的。
来自清华大学工学博士桔里猫用科普的方式为介绍SOC代码的重要步骤,其中省略了大量细节,尽量用非专业的词汇讲清楚。当然,如果要真的研究这些东西,还需要大量阅读文档。
1.概览
一段C代码要在SOC上跑起来,一般需要6个步骤。
这是一个总图,包括了最简单的编译流程以及一个SOC可以跑的最小系统。
左面绿框里的东西是在PC机上进行的,主要就是把你写的C代码变成二进制的机器码。
右面紫框里是PCB板,红框就是一颗芯片。只有红框里的芯片显然是不可能运行的。你至少要有电源,FLASH,晶振这些。
FLASH是存储你写的程序的二进制文件的。
电源是干啥的,应当很清楚。
晶振是给芯片提供时钟(Clock)的。当然芯片内部会有PLL来接收晶振的时钟。
Reset是个按钮,重置芯片的,理解为上电后自动按一下。你手动也可以按一下。
UART是输出信息用的。毕竟你要知道你的helloworld到底跑了没有,需要把结果通过某个东西输出来。
红框里就是芯片内的东西。此处画了一个最最最简单的AI芯片SOC。此处介绍一个最最最小的SOC架构:
1)ARM-M3是个CPU,可以换成RISC-V或者其他系列的CPU,都没问题。
2)AXI是个总线。你可以理解为一种用于传输数据的模块或者总线。用于两个模块或者多个模块之间相互递数据。反正它有一堆优点。。被SOC广泛采用了。
3)SRAM是片上存储器,用来存储堆栈,速度很快。
4)NPU是个神经网络加速单元。这个东西现在市面上一堆一堆。比如寒武纪最原始就是给华为提供这个IP。(当然,后来华为把寒武纪踹了开始自己写这个NPU)
5)APB,AXI是高速总线,但总有好多外设其实不需要那么快的速度。为了防止AXI太忙,所以一般有个慢速的总线,APB。挂一些慢的东西,例如UART。
嵌入式物联网的学习之路非常漫长,不少人因为学习路线不对或者学习内容不够专业而错失高薪offer。不过别担心,我为大家整理了一份150多G的学习资源,基本上涵盖了嵌入式物联网学习的所有内容。点击下方链接,0元领取学习资源,让你的学习之路更加顺畅!记得点赞、关注、收藏、转发哦!
2.准备启动文件
此处我们先要写好一个叫startup.s的文件。这个文件直接是用汇编写的,主要完成三个工作:堆栈的初始化,定位中断向量表,调用启动函数。
- 堆栈初始化
上图是startup.s里面栈的初始化,主要就是分配一下大小,重置一下指针。
- 定义中断向量表
上图就是定义的中断向量表,其实你可以理解这个就是各个小函数的地址。要放在Flash的0位置处。例如你要运行Reset_Handler这个小程序,PC就会先先访问这个中断向量表,得知Resethandler在哪个地址,然后PC跳到相应的位置开始执行Resethandler, 里面定义了各种中断发生后CPU要做的事儿(小程序)。
- 调用ResetHandler
这个小程序就是默认的初始化操作。其实就干了两件事儿,把你写的二进制代码文件从FLASH里搬到SRAM里,然后开始运行(bl main).
3.编写业务代码
这一步你应该比较熟,就是你的c文件。一般来讲学c语言写的第一个程序就是这个。
4.编译生成机器码
第三步是把写的代码变成机器可以认识的二进制文件。一般用到的工具是GCC,包括了链接、编译等等一大堆东西。此处为了简单解释,你可以理解为把startup.s翻译成二进制,把hellowolrd.c翻译成二进制。然后把两段二进制拼起来,最终生成code.bin。里面的东西如下图所示。
生成这个code.bin以后,基本上电脑编译这一步就算完成了。下一步就是下载到开发板了。
5.烧写FLASH
第三步生成的code.bin总归是个文件。在你的PC机上,如何让它跑在SOC上呢?这需要一个媒介,就是FLASH,这是个小的存储芯片。至于怎么烧写进去,就要用这个烧写器。其实一般来讲接口都会设计的很优雅,比如用个micro usb啥的,不会让你抱着砖写FLASH的。
总之,第四步结束以后code.bin就到flash里面了。
6.烧写FLASH
第五步是要复位一下芯片系统。为什么要复位一下这个,你可能要对数字芯片有一定的了解,让芯片里的各个寄存器恢复到初始状态。大体解释一下的话,CPU里存在一个寄存器叫PC。例如PC=2,就从存储2位置处取出指令来执行。这个复位就是让PC恢复到0,开始跑。
7.CPU开始执行
emmm 到这一步,CPU开始跑程序。先跑startup.s, 再跑helloworld.c。
8.输出计算结果
等计算结束以后,要输出结果(结果也是一串二进制数)。这时候数据先从ARM写到AXI总线,然后通过AXI-APB纵线桥写到APB,然后写到UART串口。最后你用串口线就能把结果在PC机上看到。
总结
emmm 感觉上述就是如何设计一个最小SOC系统并在系统上跑一个helloworld,实际上里面涉及到的细节非常多。比如UART如何用起来的, FLASH怎么接进去的。复位信号也不是一个RESET这么简单,往往有power-on reset, system reset等等一堆。但是原理上就是上面讲的这些。
- 赞