代碼模板:
1 void main(void) 2 { 3 OSInit(); 4 /* 安裝uCOS-II的任務切換向量 */ 5 /* 創建用戶起始任務TaskStart */ 6 OSStart(); 7 } 8 9 void TaskStart(void * pdata) 10 { 11 /* 安裝並啟動uCOS-II的時鍾節拍 */ 12 OSStatInit(); 13 /* 創建用戶應用程序任務 */ 14 for( ; ;){ 15 16 } 17 }
嵌入式實時操作系統uCOS-II(第二版)P99頁上給我們展示了一個應用模板,這里我想強調幾點。
<1> 在使用查看CPU使用率功能之前,要將OS_TASK_STAT_EN(在OS_CFG.h)設置為1,也就是使用這個功能。此時uCOS-II在調用函數OSInit()初始化的時候,不僅要創建必備的空閑任務OS_TaskIdle(),還會創建另外一個系統任務OS_TaskStat()。
<2> 在使用上述模板的時候,要嚴格按照模板中代碼出現的先后順序進行移植編寫,不可更改順序,否則會出現一些列錯誤。比如說本來應在第13行創建一個應用程序任務,假設它的優先級比啟動任務的還要高。但是用戶卻將其提前到第12行之前,就會導致在創建這個應用程序的時候剝奪了TaskStart()的CPU占有權,導致OSStatInit()不能正常初始化。OSStatInit()在執行的時候,只允許系統有三個任務TaskStart()、OS_TaskStat()、OS_TaskIdle()。
<3> uCOS-II的系統時鍾是在TaskStart()中才正式開始跳動的,不要在main()函數中啟動系統時鍾。之所以這樣做,是因為“用戶並不希望在多任務還沒有開始時就接收到時鍾節拍中斷”。
筆者在STM32上做的實例:
int main(void) { LCD_Ili9341_PortInit(); GUI_Init(); GUI_SetFont(&GUI_Font24_ASCII); GUI_DispStringAt("uC/OS Version: V",48,1*24); GUI_DispFloat(OSVersion()*0.01,4); OSInit(); OSTaskCreate(Task1_Start, (void *)0, &task1_start_stk[TASK1_START_STKSIZE-1], TASK1_START_PRIO); OSStart(); return 0; } void Task1_Start(void *p_arg) { OS_CPU_SR cpu_sr; p_arg = p_arg; OS_ENTER_CRITICAL(); SysTick_Config(SystemCoreClock / OS_TICKS_PER_SEC); OS_EXIT_CRITICAL(); OSStatInit(); OSTaskCreate(Task2, (void *)0, &task2_stk[TASK2_STKSIZE-1], TASK2_PRIO); OSTaskCreate(Task3_GUI, (void *)0,&task3_gui_stk[TASK3_GUI_STKSIZE-1], TASK3_GUI_PRIO); OSTaskDel(OS_PRIO_SELF); } void Task3_GUI(void *p_arg) { p_arg = p_arg; GUI_SetFont(&GUI_Font13_ASCII); while(1) { GUI_DispStringAt("CPU Usage: ",216,8*24); GUI_DispDec(OSCPUUsage,2); GUI_DispString("%"); GUI_X_ExecIdle(); } }
參考資料:《 嵌入式實時操作系統uCOS-II(第二版)》