打印
[资源共享]

多任务系统中的堆栈使用

[复制链接]
1117|6
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
在使用μC/OS的多任务应用程序中,main()启动后首先使用系统C栈,在OS启动后使用任务栈。
基于μC/OS-II或μC/OS-III编写应用代码时,用户必须为每个任务声明一个堆栈,用于任务运行现场及保存任务上下文(CPU寄存器)。在多任务处理开始之前执行的C代码将使用C栈。只有当应用程序的第一个任务开始运行时,栈才会从C栈中转移到任务栈。
不同的微控制器栈的实现也不同,许多32位处理器支持多个栈。例如,ARM Cortex-M内核有两个栈指针,分别指向主栈和进程栈。在基于μC/OS-III的应用中,多任务开始前使用主堆栈,其空间为链接命令文件中定义的堆栈区域。当应用程序调用OSStart()函数启动多任务时,进程堆栈指针被设置为第一个任务堆栈的栈顶地址,并修改控制寄存器,使任务开始运行时使用该堆栈。同时,主堆栈指针被用来指向μC/OS-III的中断堆栈OSCfg_ISRStk[]。后续多任务系统运行过程中,此堆栈将专门用于中断和异常处理程序。多任务启动后,C堆栈会丢失,导致嵌入式应用中可用的RAM量减少,在资源有限的应用中,可以重用C堆栈空间,用于任务堆栈,具体实现可以参考文章:技术小课堂| µC/OS-III的应用中CSTACK重用
由于main()对C堆栈的依赖,必须确保为这个堆栈留出足够的空间。如上所述,µC/OS-III用户还必须知道OSCfg_ISRStk[]栈的大小。OSCfg_ISRStk[]是一个数组,类似于任务堆栈,其大小由内核配置常量OS_CFG_ISR_STK_SIZE决定。另一方面,C堆栈的大小通常直接提供给链接器,因此在不同开发环境中对该堆栈进行更改的方法是不一样的。
在Segger Embedded Studio中,Cortex-M的应用中main()使用的堆栈通常被命名为stack,可以通过工程options菜单进行堆栈配置,无需直接更改链接器文件。
如果基于μC/OS-III官方示例工程开发,通常不需要修改C栈的大小。这些工程已为main()的执行分配了足够的空间。不过,中断堆栈大小的定义OS_CFG_ISR_STK_SIZE可能需要进行一些调整。对于使用独立中断堆栈的应用,如果不在中断处理程序增加复杂的函数调用,示例的默认大小即可满足需求。
基于μC/OS构建的系统在main()运行过程中依赖C堆栈,一旦调用OSStart()后,系统就切换到任务堆栈,以便开始多任务处理。



使用特权

评论回复
沙发
tpgf| | 2023-2-6 11:13 | 只看该作者
我觉得最费劲的就是指针会产生误操作

使用特权

评论回复
板凳
木木guainv| | 2023-2-6 11:23 | 只看该作者
在多任务操作系统中创建任务时,都需要指定该任务的堆栈大小

使用特权

评论回复
地板
磨砂| | 2023-2-6 12:02 | 只看该作者
任务状态简单分为运行态,就绪态,阻塞态

使用特权

评论回复
5
晓伍| | 2023-2-6 12:16 | 只看该作者
磨砂 发表于 2023-2-6 12:02
任务状态简单分为运行态,就绪态,阻塞态

运行态:万事俱备,不欠东风(获得CPU控制权);
就绪态:万事俱备,只欠东风(缺少CPU控制权);
阻塞态:万事不俱备(等事件或信号),还欠东风(缺少CPU控制权);
每个任务基本上都会游离于这三种状态。

使用特权

评论回复
6
八层楼| | 2023-2-6 13:12 | 只看该作者
任务控制块的stack_alloc_ptr,就是堆栈的栈指针,用于关联任务堆栈

使用特权

评论回复
7
观海| | 2023-2-6 13:21 | 只看该作者
当任务在运行时,一般都会调用各式各样的函数,而函数的局部变量,参数,返回值是存在于函数栈帧里的,每个函数都拥有独立的栈帧,各个栈帧使用的空间就是任务堆栈的空间

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

2038

主题

7364

帖子

10

粉丝