原来单片机main函数在这里执行

发布时间:2023-03-27  

最近看了硬汉分享的一个内容:为什么复位中断服务程序里面直接调用的main函数,难道所有程序都在复位中断里面执行的?


首先,Reset_Handler 是单片机的一个中断,其次,main 函数也确实被 Reset_Handler 中断调用了。那不是,main函数在中断里执行?


看到这个问题,你是否也曾想过这个问题,难道我们以前的认识错了?


说实话,我都没曾想过这个问题,我觉得绝大多数人都没有想过这个问题。所以,这里顺便分享一下这个问题的内容。


单片机的操作模式

这里的单片机,主要指 ARM Cortex-M 内核单片机。


要回答开篇那个问题,就要提到单片机的操作模式,这里以 Cortex‐M3 单片机为例,Cortex‐M3 支持两种模式和两个特权等级。


两种模式:

  • Handler 模式

  • Thread 模式


两个等级:

  • 特权级

  • 用户级


在 Cortex‐M3 手册中有这么一段:


其中,开篇问题的答案,我圈出来了。

官方的在线文档也提到了相关的说明:


地址:developer.arm.com/docum

示例分析

上面圈出了答案,可能你还是蒙的,这里结合 Keil MDK + STM32 的工程代码给大家简单对比分析一下。

1.进入Reset_Handler中断我们在线调试时,复位状态,进入 Reset_Handler 复位中断:


此时,就是文档中提到的:在复位后,处理器进入特权级的Thread模式。


2.进入SysTick_Handler中断当我们进入普通中断,比如这里进入 SysTick_Handler 时钟滴答中断:


此时,我们进入的是特权级的Handler模式。看到这里,想必你应该明白了。


总结

这个问题,关键点就是:

复位中断(Reset_Handler)和普通中断(SysTick_Handler)的操作模式不一样。


其他IDE,比如Keil、GCC等编译环境道理类似,这个问题主要在于内核,也就是由内核决定。


可能你从来没有关心过这个问题,当然,我们也很少遇到与之对应的问题。


这是一个不是问题的问题,不了解也没关系,你今天看到了也算进一步了解了 Cortex-M 单片机内核的一个知识点。


文章来源于:电子工程世界    原文链接
本站所有转载文章系出于传递更多信息之目的,且明确注明来源,不希望被转载的媒体或个人可与我们联系,我们将立即进行删除处理。

相关文章

    个经常会被忽略的问题是:微控制器(单片机)上电后,是如何寻找到并执行main函数的呢?很显然微控制器无法从硬件上定位main函数的入口地址,因为使用C语言作为开发语言后,变量/函数的......
    后,是如何寻找到并执行main函数的呢?很显然微控制器无法从硬件上定位main函数的入口地址,因为使用C语言作为开发语言后,变量/函数的地址便由编译器在编译时自行分配,这样一来main函数的......
    中对一个指针常量进行赋值操作,于是就在程序运行中调用fun函数的时候造成了段错误。 以上就是这段代码的错误分析,既然我们通过gdb定位到了段错误的位置,也分析出了段错误产生的原因,那么......
    初值,红色箭头指向的位置就是栈顶指针指向的位置。 代码中的局部变量,函数栈帧等等数据,全部都存放在SP开始往下的位置,因为 栈的开辟是从高地址向低地址 。 如上图所示,在main函数......
    达到稳定运行的状态。其实这个函数在固件库里面有提供,官方已经为我们写好。 __main 其实不是我们定义的(不要与C 语言中的main 函数混淆),这是一个C函数,当编译器编译时,只要遇到这个标号就会定义这个函数......
    被破坏是导致程序运行异常的重要因素。C语言对数据进行了许多专业性的处理,避免了运行中间非异步的破坏    ·提供常用的标准函数库,以供用户直接使用; ·有严格的句法检查,错误很少,可容易地在高级语言的水平上迅速地被排掉;    ·可方......
    的是栈顶地址,0X04 存放的是复位程序的地址,以此类推。从代码上看,向量表中存放的都是中断服务函数的函数名,可我们知道C 语言中的函数名就是一个地址。 DCD:分配一个或者多个以字为单位的内存,以四......
    C51使用经验(2022-12-27)
    时执行的代码并非是从main()函数的第一句语句开始的,在main()函数的第一句语句执行前要先执行一段’起始代码’。正是这段代码执行了清零的工作。C编译程序提供了这段起始代码的源程序,名为......
    不了热启动的要求。这是为什么呢?原来,用C语言编程时,开机时执 行的代码并非是从main()函数的第一语句开始的,在main()函数的第一语句执行前要先执行一段‘起始代码’。正是这段代码执行了内存清零的工作。 C......
    节为一个单位,地址 0 存放的是栈顶地址, 0X04 存放的是复位程序的地址,以此类推。从代码上看,向量表中存放的都是中断服务函数的函数名,可我们知道 C 语言中的函数名就是一个地址。 DCD:分配......

我们与500+贴片厂合作,完美满足客户的定制需求。为品牌提供定制化的推广方案、专属产品特色页,多渠道推广,SEM/SEO精准营销以及与公众号的联合推广...详细>>

利用葫芦芯平台的卓越技术服务和新产品推广能力,原厂代理能轻松打入消费物联网(IOT)、信息与通信(ICT)、汽车及新能源汽车、工业自动化及工业物联网、装备及功率电子...详细>>

充分利用其强大的电子元器件采购流量,创新性地为这些物料提供了一个全新的窗口。我们的高效数字营销技术,不仅可以助你轻松识别与连接到需求方,更能够极大地提高“闲置物料”的处理能力,通过葫芦芯平台...详细>>

我们的目标很明确:构建一个全方位的半导体产业生态系统。成为一家全球领先的半导体互联网生态公司。目前,我们已成功打造了智能汽车、智能家居、大健康医疗、机器人和材料等五大生态领域。更为重要的是...详细>>

我们深知加工与定制类服务商的价值和重要性,因此,我们倾力为您提供最顶尖的营销资源。在我们的平台上,您可以直接接触到100万的研发工程师和采购工程师,以及10万的活跃客户群体...详细>>

凭借我们强大的专业流量和尖端的互联网数字营销技术,我们承诺为原厂提供免费的产品资料推广服务。无论是最新的资讯、技术动态还是创新产品,都可以通过我们的平台迅速传达给目标客户...详细>>

我们不止于将线索转化为潜在客户。葫芦芯平台致力于形成业务闭环,从引流、宣传到最终销售,全程跟进,确保每一个potential lead都得到妥善处理,从而大幅提高转化率。不仅如此...详细>>