thestanley 发表于 2008-1-10 16:39:57

UCOS任务切换的问题

移植完ucOSII 后,一共建立了2个任务(不包括系统的空闲任务),优先级为6,7(以下简称任务6,7),启动后任务6正常切换至7,7有1000ticks延时,然后正常跳入任务7,但是再次切换时,就直接跳至main(),百思不得其解,望大家不吝赐教。

任务创建:
点击此处下载ourdev_200239.txt(文件大小:4K)

thestanley 发表于 2008-1-10 16:42:07

ucOSii 版本为2.85
其它移植文件为ucos官方网站提供的下载

ATMEGA_007 发表于 2008-1-10 16:59:24

没看见你对空闲任务和统计任务的的堆栈进行调整..

因为这2个任务是系统建立的,原来的uCOSII的堆栈不分数据栈和程序返回栈的,你现在分开了就要调整,任务建立的时候也要给出差值,不知道是不是这个原因

ATMEGA_007 发表于 2008-1-10 17:01:10

void main(void)
{
    #if (OS_TASK_NAME_SIZE > 14) && (OS_TASK_STAT_EN > 0)
    INT8Uerr;
    #endif
   
    OSTaskStkSize   = OS_TASK_IDLE_STK_SIZE;
    OSTaskStkSizeHard = OS_TASK_IDLE_STK_SIZE_HARD;
    OSInit();
    //调整空闲任务堆栈尺寸
    OSTCBPrioTbl->OSTCBStkSize   = OSTaskStkSize - OSTaskStkSizeHard;
    OSTCBPrioTbl->OSTCBStkBottom = &OSTaskIdleStk;
    //调整统计任务堆栈尺寸
    #if OS_TASK_STAT_EN > 0
    OSTCBPrioTbl->OSTCBStkSize   = OSTaskStkSize - OSTaskStkSizeHard;
    OSTCBPrioTbl->OSTCBStkBottom = &OSTaskStatStk;
    #endif
    //设置空闲任务名称
    #if OS_TASK_NAME_SIZE > 14
    OSTaskNameSet(OS_IDLE_PRIO, "uC/OS-II Idle", &err);
    #endif
    //设置统计任务名称
    #if (OS_TASK_NAME_SIZE > 14) && (OS_TASK_STAT_EN > 0)
    OSTaskNameSet(OS_STAT_PRIO, "uC/OS-II Stat", &err);
    #endif
   
    //用任务建立任务
    OSTaskStkSize   = OS_TASK_START_STK_SIZE;
    OSTaskStkSizeHard = OS_TASK_START_STK_SIZE_HARD;
    OSTaskCreateExt(OSTaskStart,                                          //void (*task)(void *pd) 任务首地址
                  (void *)0,                                          //void *pdata            数据指针
                  &OSTaskStartStk,          //OS_STK *ptos         指向任务堆栈栈顶的指针
                  OS_TASK_START_PRIO,                                 //INT8U prio             任务优先级
                  OS_TASK_START_ID,                                     //INT16U id            任务的ID号
                  &OSTaskStartStk,         //OS_STK *pbos         指向任务堆栈栈底的指针
                  OS_TASK_START_STK_SIZE - OS_TASK_START_STK_SIZE_HARD, //INT32U stk_size      堆栈容量
                  (void *)0,                                          //void *pnext            数据指针
                  OS_TASK_OPT_STK_CHK | OS_TASK_OPT_STK_CLR);         //INT16U opt             设定OSTaskCreateExt的选项

    OSTaskNameSet(OS_TASK_START_PRIO, "Task-Start", &err);

    OSStart();
}

hjssnoopy168 发表于 2008-1-10 18:37:17

正在学习中。。。

thestanley 发表于 2008-1-11 08:53:22

我是使用OSTaskCreate()建立的任务,应该不需要指定OSTCBStkBottom啊
另外你说的软硬件堆栈指定,我在OSTaskStkInit()似乎看到了已经做了相应的处理,代码如下:
OS_STK*OSTaskStkInit (void (*task)(void *pd), void *p_arg, OS_STK *ptos, INT16U opt)
{
    INT8U*psoft_stk;
    INT8U*phard_stk;                      /* Temp. variable used for setting up AVR hardware stack    */
    INT16Utmp;


    (void)opt;                              /* 'opt' is not used, prevent warning                     */
    psoft_stk    = (INT8U *)ptos;
    phard_stk    = (INT8U *)ptos
               - OSTaskStkSize            /* Task stack size                                          */
               + OSTaskStkSizeHard;       /* AVR return stack ("hardware stack")                      */

    tmp          = *(INT16U const *)task;   /* (1) ICC compiler handles function pointers indirectly!   */

    *phard_stk-- = (INT8U)(tmp & 0xFF);   /* Put task start address on top of "hardware stack"      */
    tmp      >>= 8;
    *phard_stk-- = (INT8U)(tmp & 0xFF);

    *psoft_stk-- = (INT8U)0x00;             /* R0    = 0x00                                             */
    *psoft_stk-- = (INT8U)0x01;             /* R1    = 0x01                                             */
    *psoft_stk-- = (INT8U)0x02;             /* R2    = 0x02                                             */
    *psoft_stk-- = (INT8U)0x03;             /* R3    = 0x03                                             */
    *psoft_stk-- = (INT8U)0x04;             /* R4    = 0x04                                             */
    *psoft_stk-- = (INT8U)0x05;             /* R5    = 0x05                                             */
    *psoft_stk-- = (INT8U)0x06;             /* R6    = 0x06                                             */
    *psoft_stk-- = (INT8U)0x07;             /* R7    = 0x07                                             */
    *psoft_stk-- = (INT8U)0x08;             /* R8    = 0x08                                             */
    *psoft_stk-- = (INT8U)0x09;             /* R9    = 0x09                                             */
    *psoft_stk-- = (INT8U)0x10;             /* R10   = 0x10                                             */
    *psoft_stk-- = (INT8U)0x11;             /* R11   = 0x11                                             */
    *psoft_stk-- = (INT8U)0x12;             /* R12   = 0x12                                             */
    *psoft_stk-- = (INT8U)0x13;             /* R13   = 0x13                                             */
    *psoft_stk-- = (INT8U)0x14;             /* R14   = 0x14                                             */
    *psoft_stk-- = (INT8U)0x15;             /* R15   = 0x15                                             */
    tmp          = (INT16U)p_arg;
    *psoft_stk-- = (INT8U)(tmp & 0xFF);   /* 'p_arg' passed in R17:R16                              */
    tmp      >>= 8;
    *psoft_stk-- = (INT8U)(tmp & 0xFF);
    *psoft_stk-- = (INT8U)0x18;             /* R18   = 0x18                                             */
    *psoft_stk-- = (INT8U)0x19;             /* R19   = 0x19                                             */
    *psoft_stk-- = (INT8U)0x20;             /* R20   = 0x20                                             */
    *psoft_stk-- = (INT8U)0x21;             /* R21   = 0x21                                             */
    *psoft_stk-- = (INT8U)0x22;             /* R22   = 0x22                                             */
    *psoft_stk-- = (INT8U)0x23;             /* R23   = 0x23                                             */
    *psoft_stk-- = (INT8U)0x24;             /* R24   = 0x24                                             */
    *psoft_stk-- = (INT8U)0x25;             /* R25   = 0x25                                             */
    *psoft_stk-- = (INT8U)0x26;             /* R26   = 0x26                                             */
    *psoft_stk-- = (INT8U)0x27;             /* R27   = 0x27                                             */
                                          /* R28   R29:R28 is the software stack which gets ...   */
                                          /* R29   ... stored in the task's OS_TCB.               */
    *psoft_stk-- = (INT8U)0x30;             /* R30   = 0x30                                             */
    *psoft_stk-- = (INT8U)0x31;             /* R31   = 0x31                                             */
    *psoft_stk-- = (INT8U)0xAA;             /* RAMPZ = 0xAA                                             */
    *psoft_stk-- = (INT8U)0x80;             /* SREG= Interrupts enabled                               */
    tmp          = (INT16U)phard_stk;
    *psoft_stk-- = (INT8U)(tmp >> 8);       /* SPH                                                      */
    *psoft_stk   = (INT8U) tmp;             /* SPL                                                      */
    return ((OS_STK *)psoft_stk);
}

不知道我理解的对不对
页: [1]
查看完整版本: UCOS任务切换的问题