完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
本帖最后由 eehome 于 2013-1-5 09:57 编辑
void OSInit (void) { INT16U i; /*****/ /*****/ OStime = 0L; /* Clear the 32-bit system clock */ OSIntNesting = 0; /**中断嵌套层数计数,>0时候禁止任务调度***/ /* Clear the interrupt nesting counter */ OSLockNesting = 0; /**锁定嵌套计数器,>0时候禁止任务调度***/ /* Clear the scheduling lock counter */ OSTaskCtr = 0; /* 任务计数器Clear the number of tasks */ OSRunning = FALSE; /* 指出多任务是否开始Indicate that multitasking not started */ OSIdleCtr = 0L; /* 空闲任务计数器,Clear the 32-bit idle counter */ OSCtxSwCtr = 0; /* 统计计数器=任务切换的次数,Clear the context switch counter */ OSRdyGrp = 0; /*任务就绪组,任何时候只有一个bit位是置1的,和优先级有关 Clear the ready list */ for (i = 0; i < OS_RDY_TBL_SIZE; i++) { OSRdyTbl = 0; /**每个任务的就绪任务表**/ } OSPrioCur = 0; /***存放应用任务的优先级***/ OSPrioHighRdy = 0; OSTCBHighRdy = (OS_TCB *)0; /* TCB Initialization */ OSTCBCur = (OS_TCB *)0; OSTCBList = (OS_TCB *)0; for (i = 0; i < (OS_LOWEST_PRIO + 1); i++) { /**初始化任务优先级表(清零)*//* Clear the priority table */ OSTCBPrioTbl = (OS_TCB *)0; /**全部的控制模块清成空闲状态**/ } /**任务链表数组--**/ for (i = 0; i < (OS_MAX_TASKS + OS_N_SYS_TASKS - 1); i++) { /* Init. list of free TCBs */ OSTCBTbl.OSTCBNext = &OSTCBTbl[i + 1]; /**将任务链表的TCB地址记录**/ } OSTCBTbl[OS_MAX_TASKS + OS_N_SYS_TASKS - 1].OSTCBNext = (OS_TCB *)0; /* Last OS_TCB */ OSTCBFreeList = &OSTCBTbl[0];/*空任务块控制指针:初始化时候指向的是第一个任务*/ /*第一个任务是系统任务--空闲任务,还有一个统计任务(OS_N_SYS_TASKS=2时)**/ /**事件链表数组***/ for (i = 0; i < (OS_MAX_EVENTS - 1); i++) { /* Init. list of free EVENT control blocks */ OSEventTbl.OSEventPtr = (OS_EVENT *)&OSEventTbl[i + 1]; } OSEventTbl[OS_MAX_EVENTS - 1].OSEventPtr = (OS_EVENT *)0;/**最后的事件表**/ OSEventFreeList = &OSEventTbl[0]; #if OS_STK_GROWTH == 1 /***由高地址向低地址方向***/ OSTaskCreate(OSTaskIdle, (void *)0, &OSTaskIdleStk[OS_TASK_IDLE_STK_SIZE - 1], OS_IDLE_PRIO); #else /****栈的方向由低地址到高地址***/ OSTaskCreate(OSTaskIdle, (void *)0, &OSTaskIdleStk[0], OS_IDLE_PRIO); // mand by jk 2007-8-16 // OSTaskCreate(OSTaskIdle, (void *)0, &OSTaskIdleStk[OS_TASK_IDLE_STK_SIZE - 1], OS_IDLE_PRIO); #endif } /*消息通信函数:OSSemPend(A)期待A事件的发生,如果事件A还没有发生,那么就被挂起(pending)等待,并且下一个优先级获得CPU的控制权,进行下一个任务。相应的OSSemPost();就是通知给OSSemPend()事件发生了,那么如果在下一个任务中执行了OSSemPost(A),则上面的任务就知道了事件A的发生,那么系统将CPU控制权交给了原来的优先级更高的任务运行。相应的函数有OSFlagPend(),OSSemPend(),OSMutexPend(),OSMboxPend(),OSQPend()都是peng挂起等待某个事件的产生,否则进入到等待状态。*/ void OSSemPend (OS_EVENT *pevent, INT16U timeout, INT8U *err)reentrant INT8U OSSemPost (OS_EVENT *pevent)reentrant /*--例子:*/ void TaskA() { OSSemPend(Event,5,err); //A任务等待系统里面Event事件的发生 } void TaskB() { OSSemPost(Event); //B事件告示了Event事件的发生 } /***以下为内核中最重要的几个函数***/ INT8U OSTaskCreate( void (*task)(void *pd)reentrant,//任务函数 void *dataptr, //任务中需要使用的数据参数:万能指针类型 OS_STK *ptos, //任务栈顶指针:指向一开始申请的堆栈数组 INT8U prio ) reentrant // 定义任务的优先级 { void *psp; //堆栈任务指针 INT8U err; if(prio>OS_LOWEST_PRIO) { //确保优先级在合法使用区域内 return (OS_PRIO_INVALID) }//优先级错误则返回一个不合法的优先级错误代码 OS_ENTER_CRITICAL();//进入临界区域--关中断 if(OSTCBPrioTbl[prio]==(OS_TCB *)0) ///**是否有清空当前任务块的优先级链表**/ { OSTCBPrioTbl[prio]==(OS_TCB *)1; //提升系统性能,先开中断,离开临界区 OS_EXIT_CRITICAL(); //初始化任务堆栈,包含了任务执行首地址,数据,堆栈顶 /**初始化堆栈:在建立的堆栈区域存放相应的内容**/ psp=(void *)OSTaskStkInit(task,dataptr,ptos,0); //初始化TCB任务控制模块函数: err=OSTCBInit(prio,psp,(void *)0,0,0,(void *)0,0); if (err == OS_NO_ERR) { /**没有error:说明建立的任务控制模块一切正常**/ OS_ENTER_CRITICAL(); OSTaskCtr++; /**增加任务数**/ OSTaskCreateHook(OSTCBPrioTbl[prio]); /*当OSTaskCreateHook( )被调用时,它会收到指向已建立任务的任务控制块的指针,这样就可调用里面所有成员*/ OS_EXIT_CRITICAL(); if (OSRunning) { OSSched(); /****/ } } else { OS_ENTER_CRITICAL(); OSTCBPrioTbl[prio] = (OS_TCB *)0; OS_EXIT_CRITICAL(); } return (err); } else { OS_EXIT_CRITICAL(); return (OS_PRIO_EXIST); } } /*********************************************************************************************************** 关于OSTaskCreate()函数内部调用的一些说明: 函数OSTCBInit(INT8U prio,OS_STK *ptos,OS_STK *pbos,INT16U id,INT16U stk_size,void *pext,INT16U opt)reentrant 分别为 优先级 栈顶指针 栈末尾 任务号 栈大小 用户使用堆栈区 任务扩展在OSTaskCreateExt()用 ***********************************************************************************************************/ /**初始化最新创建的任务控制模块** 优先级、堆栈的起始地址、堆栈的结束地址、任务编号、任务堆栈大小.... ****/ static OS_TCB *ptcb11; INT8U OSTCBInit (INT8U prio, OS_STK *ptos, OS_STK *pbos, INT16U id, INT16U stk_size, void *pext, INT16U opt)reentrant { OS_ENTER_CRITICAL(); ptcb11 = OSTCBFreeList; /**首先赋值给空闲TCB指针**/ /* Get a free TCB from the free TCB list */ if (ptcb11 != (OS_TCB *)0) { /**检查TCB是否为空**/ OSTCBFreeList = ptcb11->OSTCBNext; /* Update pointer to free TCB list */ OS_EXIT_CRITICAL(); ptcb11->OSTCBStkPtr = ptos; /* Load Stack pointer in TCB */ ptcb11->OSTCBPrio = (INT8U)prio; /* Load task priority into TCB */ ptcb11->OSTCBStat = OS_STAT_RDY; /* Task is ready to run */ ptcb11->OSTCBDly = 0; /* Task is not delayed */ #if OS_TASK_CREATE_EXT_EN ptcb11->OSTCBExtPtr = pext; /* Store pointer to TCB extension */ ptcb11->OSTCBStkSize = stk_size; /* Store stack size */ ptcb11->OSTCBStkBottom = pbos; /* Store pointer to bottom of stack */ ptcb11->OSTCBOpt = opt; /* Store task options */ ptcb11->OSTCBId = id; /* Store task ID */ #else pext = pext; /* Prevent compiler warning if not used */ stk_size = stk_size; pbos = pbos; opt = opt; id = id; #endif #if OS_TASK_DEL_EN ptcb11->OSTCBDelReq = OS_NO_ERR; #endif /**任务表的计算:当知优先级时就可以优先定义**/ ptcb11->OSTCBY = prio >> 3; /* Pre-compute X, Y, BitX and BitY */ ptcb11->OSTCBBitY = OSMapTbl[ptcb11->OSTCBY]; ptcb11->OSTCBX = prio & 0x07; ptcb11->OSTCBBitX = OSMapTbl[ptcb11->OSTCBX]; #if OS_MBOX_EN || (OS_Q_EN && (OS_MAX_QS >= 2)) || OS_Sem_EN ptcb11->OSTCBEventPtr = (OS_EVENT *)0; /* Task is not pending on an event */ #endif #if OS_MBOX_EN || (OS_Q_EN && (OS_MAX_QS >= 2)) ptcb11->OSTCBMsg = (void *)0; /* No message received */ #endif OS_ENTER_CRITICAL(); /***加入TCB链表:前后插入法***/ OSTCBPrioTbl[prio] = ptcb11; ptcb11->OSTCBNext = OSTCBList; /* Link into TCB chain */ ptcb11->OSTCBPrev = (OS_TCB *)0; if (OSTCBList != (OS_TCB *)0) { OSTCBList->OSTCBPrev = ptcb11; } /**任务模块控制链表建立**/ OSTCBList = ptcb11; /**任务成员变量:方便任务上下文切换**/ OSRdyGrp |= ptcb11->OSTCBBitY; /* Make task ready to run */ OSRdyTbl[ptcb11->OSTCBY] |= ptcb11->OSTCBBitX; OS_EXIT_CRITICAL(); return (OS_NO_ERR); } else { OS_EXIT_CRITICAL(); return (OS_NO_MORE_TCB); } } |
|
相关推荐
|
|
值得学习~~谢谢楼主
|
|
|
|
|
|
1039 浏览 0 评论
AI模型部署边缘设备的奇妙之旅:如何在边缘端部署OpenCV
3425 浏览 0 评论
tms320280021 adc采样波形,为什么adc采样频率上来波形就不好了?
1465 浏览 0 评论
2146 浏览 0 评论
1640 浏览 0 评论
75366 浏览 21 评论
小黑屋| 手机版| Archiver| 电子发烧友 ( 湘ICP备2023018690号 )
GMT+8, 2024-12-28 21:38 , Processed in 1.037228 second(s), Total 79, Slave 61 queries .
Powered by 电子发烧友网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
电子发烧友观察
版权所有 © 湖南华秋数字科技有限公司
电子发烧友 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号