我刚刚开始钻研ARM Cortex-M微控制器的世界,我已经决定不使用现有的开发板或易于使用的集成开发环境,而是直接接触这些东西的裸机,所以我已经将自己的STM32F103焊接到了原型板上,现在正在尝试使用Launchpad的arm-embedded工具链。经过一段时间的努力阅读了关于链接器脚本之类的手册之后,我现在已经编写了自己的链接器脚本和启动代码,它们基本上什么也不做,只是将.data部分从只读存储器复制到内存,清零.bss,然后从ST的标准外设库中调用SystemInit()来执行基本的uC初始化,最后调用main()。
现在,从我找到的一些关于Cortex M-3开发的教程中,我看到他们使用链接器的-nostartfiles标志,但现在我想知道:在这种情况下,我必须自己初始化newlib吗?或者我应该使用默认的从GCC/newlib开始的文件,并删除-nostartfiles?但是在这种情况下,我仍然需要做一些初始化工作,比如将.data复制到内存并设置向量表,这需要一个定制的链接器脚本。那么我该在哪里做呢?
我甚至不想开始考虑C++!
那么,初始化这种基于Cortex-M3的微控制器及其libc (不包括外围设备)的推荐方式是什么?
提前感谢!
发布于 2018-03-20 16:40:20
据我所知,你不应该为一个纯C应用程序调用任何stdlib函数。但对于C++应用程序,你应该这样做,因为有静态初始化器、RTTI的vtable等需要初始化。newlib本身包含来自stdlib的函数,如mem*、*printf等,据我所知,这些函数适用于只读存储器较小的单片机。
但是通常没有什么可以主动初始化的。如果一个std-function确实有一个全局数据,它希望声明它并将其存储在一些变量中,这些变量存储在.data部分中。例如,__errno就是这方面的候选者。但是你不能确定你的newlib实现做了什么,因为这是由开发人员决定的,他们如何在库中设计内部工作流。
请看下面的代码片段。这是一个用C编写的启动例程(重置处理程序)。ST将它们的启动文件作为汇编文件(*.s)提供,但也可以用C编写。恩智浦则使用.c启动文件生成其项目。
如果您的应用程序只是一个C应用程序,则可以省略C++注释下面的函数调用。_data和_idata的符号由链接器生成(在链接器脚本中定义)。
__set_PSP((uint32_t)&_vStackTop); // set stack pointer
SCB->VTOR = (uint32_t)&VectorTable; // set the pointer to the vector table
pDest = &_data;
pSrc = &_idata;
// fill .data section
for ( ; pDest < &_edata; )
{
*pDest = *pSrc;
++pSrc;
++pDest;
}
// fill .bss section
for (pDest = &_bss; pDest < &_ebss; ++pDest)
{
*pDest = 0;
}
//
// Call C++ library initialization, if your app is an C++ app
//
__libc_init_array();
main(); // enter main
for(;;) // you shouldn't land here at anytime
{
}https://stackoverflow.com/questions/19890826
复制相似问题