UCOS移植到MSP430过程与心得体会《3》
[复制链接]
static void OS_InitRdyList (void) { INT16U i; INT8U *prdytbl;
OSRdyGrp = 0x00;
ready list */ prdytbl = &OSRdyTbl[0]; for (i = 0; i < OS_RDY_TBL_SIZE; i++) { *prdytbl++ = 0x00; }
OSPrioCur = 0; OSPrioHighRdy = 0;
OSTCBHighRdy = (OS_TCB *)0; OSTCBCur = (OS_TCB *)0; }
static void OS_InitTCBList (void) { INT8U i; OS_TCB *ptcb1; OS_TCB *ptcb2; OSTCBList = (OS_TCB *)0; /* TCB Initialization */ for (i = 0; i < (OS_LOWEST_PRIO + 1); i++){ /*Clear the priority table OSTCBPrioTbl = (OS_TCB *)0; } ptcb1 = &OSTCBTbl[0]; ptcb2 = &OSTCBTbl[1]; for (i = 0; i < (OS_MAX_TASKS + OS_N_SYS_TASKS - 1); i++) { /* Init. list of free TCBs */ ptcb1->OSTCBNext = ptcb2; ptcb1++; ptcb2++; } ptcb1->OSTCBNext = (OS_TCB *)0; /* Last OS_TCB */ OSTCBFreeList = &OSTCBTbl[0]; }
static void OS_InitEventList (void) { #if (OS_EVENT_EN > 0) && (OS_MAX_EVENTS > 0) #if (OS_MAX_EVENTS > 1) INT16U i; OS_EVENT *pevent1; OS_EVENT *pevent2;
pevent1 = &OSEventTbl[0]; pevent2 = &OSEventTbl[1]; for (i = 0; i < (OS_MAX_EVENTS - 1); i++) { /* Init. list of free EVENT control blocks */ pevent1->OSEventType = OS_EVENT_TYPE_UNUSED; pevent1->OSEventPtr = pevent2; pevent1++; pevent2++; } pevent1->OSEventType = OS_EVENT_TYPE_UNUSED; pevent1->OSEventPtr = (OS_EVENT *)0; OSEventFreeList = &OSEventTbl[0]; #else OSEventFreeList = &OSEventTbl[0]; /* Only have ONE event control block */ OSEventFreeList->OSEventType = OS_EVENT_TYPE_UNUSED; OSEventFreeList->OSEventPtr = (OS_EVENT *)0; #endif #endif }
//调用任务选出最优先级最高的任务.
void OSStart (void) { INT8U y; INT8U x;
if (OSRunning == FALSE) { y = OSUnMapTbl[OSRdyGrp]; /* Find highest priority's task priority number */ x = OSUnMapTbl[OSRdyTbl[y]]; OSPrioHighRdy = (INT8U)((y << 3) + x); OSPrioCur = OSPrioHighRdy; OSTCBHighRdy = OSTCBPrioTbl[OSPrioHighRdy]; /* Point to highest priority task ready to run */ OSTCBCur = OSTCBHighRdy; OSStartHighRdy(); /* Execute target specific code to start task */ } } <调用OSStartHighRdy()对选出来将优先级最高的任务的堆栈出栈>
OSStartHighRdy call #OSTaskSwHook
mov.b #1, &OSRunning ; kernel running
mov.w SP, &OSISRStkPtr ; save interrupt stack
mov.w &OSTCBHighRdy, R13 ; load highest ready task stack mov.w @R13, SP
POPALL ; pop all registers
reti
//task的优先级为5 ,进入运行. void task(void *pdata) { WDTCTL=WDT_MDLY_8; IE1|=0X01; P4DIR=0xFF; while(1) { if(FlagLED==false) { //P4OUT=0x80; FlagLED=true; } if(FlagLED==true) { LED=(LED==0x80)?(0x01):(LED<<1); P4OUT=LED; FlagLED=false; } OSTimeDly(10); } }
在上面断要考虑以下几个怀况: WDTCTL=WDT_MDLY_8; IE1|=0X01; OSTimeDly(10); 三个同时工作对任务的作用: 表面意思来看.WDTCTL=WDT_MDLY_8; IE1|=0x01; 是看门狗廷时8ms 主详细看下面执行过程.
void OSTimeDly (INT16U ticks) { #if OS_CRITICAL_METHOD == 3 /* Allocate storage for CPU status register */ OS_CPU_SR cpu_sr; #endif
if (ticks > 0) { /* 0 means no delay! */ OS_ENTER_CRITICAL(); if ((OSRdyTbl[OSTCBCur->OSTCBY] &= ~OSTCBCur->OSTCBBitX) == 0) { /* Delay current task */ OSRdyGrp &= ~OSTCBCur->OSTCBBitY; } OSTCBCur->OSTCBDly = ticks; /* Load ticks in TCB */ OS_EXIT_CRITICAL(); OS_Sched(); /* Find next task to run! */ } }
< OS_ENTER_CRITICAL();>里的内容.----何存内容. OSCPUSaveSR / MOV.W SR,R12 DINT RET
< OS_EXIT_CRITICAL();> //返回 OSCPURestoreSR MOV.W R12,SR RET
//以下说明在整个执行过程中, OSTimeDly()调用了OS_Sched() //及OS_TASK_SW();对任务进行切换. void OS_Sched (void) { #if OS_CRITICAL_METHOD == 3 /* Allocate storage for CPU status register */ OS_CPU_SR cpu_sr; #endif INT8U y; OS_ENTER_CRITICAL(); if ((OSIntNesting == 0) && (OSLockNesting == 0)) { /* Sched. only if all ISRs done & not locked */ y = OSUnMapTbl[OSRdyGrp]; /* Get pointer to HPT ready to run */ OSPrioHighRdy = (INT8U)((y << 3) + OSUnMapTbl[OSRdyTbl[y]]); if (OSPrioHighRdy != OSPrioCur) { /* No Ctx Sw if current task is highest rdy */ OSTCBHighRdy = OSTCBPrioTbl[OSPrioHighRdy]; OSCtxSwCtr++; /* Increment context switch counter */ OS_TASK_SW(); /* Perform a context switch */ } } OS_EXIT_CRITICAL(); }
|