(二)任务堆栈

任务堆栈的创建                           

1、为了方便定义任务堆栈,在文件OS_CPU.H中定义了一个数据类型OS_STK:

typedef unsigned int  OS_STK; //该类型长度为16位

2、在定义任务堆栈的栈区时,只要定义一个OS_STK类型的数组即可。例如:

#define  TASK_STK_SIZE    512   //定义堆栈的长度(1024字节)

OS_STK   TaskStk[TASK_STK_SIZE];   //定义一个数组来作为任务堆栈

3、堆栈增长方向随处理器的不同而不同:

堆栈的生长方向从最本质的理解是堆栈入栈方向是从高地址向地址还是低地址向高地址。

从高地址向低地址生长一般叫做向下生长,也叫作逆向生长。

从低地址向高地址生长一般叫做向上生长,也叫作正向生长。

51单片机的堆栈生长方向为正向生长,因为执行PUSH指令时先将SP的值加1再将指定的8位数据单元的内容入栈

80x86微机的堆栈生长方向为逆向生长,因为执行PUSH指令时先将SP的值减2再将指定的16位数据单元内容入栈。高字节放高地址,低字节放低地址(小端模式)。

STM32的堆栈生长方向是逆向生长

为提高可移植性,利用OS_CFG.H文件中的常数OS_STK_CROWTH作为选择开关,用户通过定义改常数的值来选择不同的代码段,以适应不同的堆栈增长方式的需要。

#define  OS_STK_CROWTH  1   // 1:向下增长方式,0:向上增长方式

例如:

#define TASK_STK_SIZE   64
OS_STK MyTaskStk[TASK_STK_SIZE];  //任务堆栈

void main(void)
{
   .....
#if  OS_STK_CROWTH == 1  //堆栈向下增长方式
    OSTaskCreate(MyTask,                       //任务指针
                 &MytaskAgu,                   //传递给任务的参数
                 &MytaskStk[TASK_STK_SIZE-1],  //任务堆栈栈顶的指针 
                 20                            //优先级别
                 );
#else  //堆栈向上增长方式
    OSTaskCreate(MyTask,                       //任务指针                    
                 &MytaskAgu,                   //传递给任务的参数
                 &MytaskStk[0],                //任务堆栈栈顶的指针
                 20                            //优先级别
                 );
#endif
    ......
}
任务堆栈的初始化                     

当CPU在启动运行一个任务时,CPU的各寄存器总是需要预置一些初始数据。由于它们都是任务的私有数据,所以应该将它们都存放在任务堆栈。

把任务初始数据放到任务堆栈的工作叫做任务堆栈的初始化,UC/OS-II提供了任务堆栈初始化函数OSTaskStkInit()

OS_STK* OSTaskStkInit(

                                         void (*task)(void *pd),

                                         void *pdata,

                                         OS_STK *ptos,

                                          INT16U opt

                                        );

该函数由任务创建函数OSTaskCreate()来调用。

另外,因为处理器中寄存器及对堆栈的操作方式不尽相同,所以该函数需要用户在进行UC/OS-II移植时,按所使用的处理器来编写,请参考UC/OS-II移植说明


你可能感兴趣的:((二)任务堆栈)