# FreeRTOS Project Overview [參考Poject ](https://github.com/jkovacic/FreeRTOS-GCC-ARM926ejs/blob/master/drivers/uart.c) ### 摘要 Main.c 中 為Project 主程式,其中能為透過user鍵盤輸入字串,透過FreeRTOS 輸出至 console 端,紀錄完整運作過程。 架構圖 ![](https://i.imgur.com/lq9XqCg.jpg) ### 前置作業 * 初始化Uart * init.c 將uart 初始化 * 必註冊ISR,必須註冊ISR,敲鍵盤時才知道要進行中斷,執行相對應的Handler * receive.c 中 建立對應的queue,Handler的任務就是將Uart的字串透過Sent至queue ### 運作流程 Uart 是跟 Console端進行溝通,因此當鍵盤敲字時,QEMU中所模擬的Uart會接收到,下圖程式碼為設定對應Uart Interrupt Register ```c= void uart_enableRxInterrupt(uint8_t nr) { /* Sanity check */ if ( nr >= BSP_NR_UARTS ) { return; } /* Set bit 4 of the IMSC register: */ HWREG_SET_BITS( pReg[nr]->UARTIMSC, INT_RXIM ); } ``` 透過Uart Data Register 去讀相對應的資料,從下圖程式碼可以明顯看出,將讀到值傳入queue,也就是Interrupt Handler在做的事情。 ```c= char uart_readChar(uint8_t nr) { /* Sanity check */ if ( nr >= BSP_NR_UARTS ) { return (char) 0; } /* Wait until the receiving FIFO is not empty */ while ( 0 != HWREG_READ_BITS( pReg[nr]->UARTFR, FR_RXFE ) ); /* * UART DR is a 32-bit register and only the least significant byte must be returned. * Casting its address to char* effectively turns the word into an array * of (four) 8-bit characters. Now, dereferencing the first character of this array affects * only the desired character itself, not the whole word. */ return *( (char*) &(pReg[nr]->UARTDR) ); } ``` 接著在Main.c中,有一個Task被創出,他的任務就是去receive queue中的值,並做前處理的動作,最後透過vPrintMsg印在consolo端。 ```c= if ( pdPASS != xTaskCreate(recvTask, "recv", 128, NULL, PRIOR_RECEIVER, NULL) ) { FreeRTOS_Error("Could not create a receiver task\r\n"); } ``` ### 延伸問題 Q1:接收鍵盤的Uart 跟 vPrintMsg 所使用的Uart 是同一個嗎? A:從code trace 中發現是同一個,但是似乎不是同時一起使用 ![](https://i.imgur.com/mgIdUOV.png) ----- ![](https://i.imgur.com/iBLp4Ay.png) ----- ![](https://i.imgur.com/Lyfh7nU.png) ----- 從上圖可以發現,觀察PrintInit 跟 recvInit 他們所傳入的參數 都被定義為 0 圖太程式碼化可以抽象一點 箭頭一樣都一樣意思卻不一樣