個人資料
歸檔
正文

OS-RTOS

(2022-03-20 22:31:32) 下一個

1. Kernel

1.1 編譯安裝5.9.6 on Ubuntu

https://phoenixnap.com/kb/build-linux-kernel 需要的改動:

1.UEFI BIOS, secure boot要禁止,不然報linux kernel: invalid signature, you need to load the kernel first’,可也自己生成signature:https://help.univention.com/t/problem-booting-server-shows-invalid-signature-you-need-to-load-the-kernel-first/13557 
2.改.config兩行,去掉找不到的debian license,去debug以減小尺寸,改後為:
CONFIG_SYSTEM_TRUSTED_KEYS=""
CONFIG_DEBUG_INFO_BTF=n
3.生成的initrd.img需要strip剪裁,不然啟動時裝入kernel後停在initrd.img處,辦法是
https://unix.stackexchange.com/questions/270390/how-to-reduce-the-size-of-the-initrd-when-compiling-your-kernel 
cd /lib/modules/
find . -name *.ko -exec strip --strip-unneeded {} +
cd
sudo make install

1.2 編譯安裝5.13.1 on Ubuntu

sudo apt update && sudo apt upgrade
sudo reboot
sudo apt install build-essential libncurses5-dev fakeroot xz-utils libelf-dev flex bison libssl-dev dwarves zstd 
cd ~/Downloads
wget https://cdn.kernel.org/pub/linux/kernel/v5.x/linux-5.13.1.tar.xz
tar xf linux-5.13.1.tar.xz
cd linux-5.13
sudo find /boot/ ( -iname "*config*" -a -iname "*`uname -r`*" ) -exec cp -i -t ./ {} ;
mv *`uname -r`* .config
ls /boot | grep config
sudo gedit .config &
==comment out: #CONFIG_SYSTEM_TRUSTED_KEYS, #CONFIG_SYSTEM_REVOCATION_KEYS, 
==enable: CONFIG_PCIEPORTBUS=y, CONFIG_PCIEAER=y, CONFIG_PCIEAER_INJECT=y, CONFIG_PCIE_ECRC=y, 
sudo make menuconfig
sudo make -j 8
sudo make bzImage -j 8
sudo make modules_install
sudo make install
cd /lib/modules/5.13.1
sudo find . -name *.ko -exec strip --strip-unneeded {} +
sudo update-initramfs -c -k 5.13.1
sudo update-grub
sudo reboot
uname -mrs

若見"cannot represent change to vmlinux-gdb.py",直接刪除該文件再編譯。最新的5.15.35也同樣編譯安裝。

1.3 remove kernel

https://phoenixnap.com/kb/ubuntu-remove-old-kernels 

2 .Zhphyr RTOS
Zhphyr文檔:https://docs.zephyrproject.org/2.7.0/zephyr.pdf?  https://docs.zephyrproject.org/latest/   
Zephyr on ESP32: https://www.zephyrproject.org/zephyr-rtos-on-esp32/ 
2.0 west:https://docs.zephyrproject.org/latest/boards/xtensa/esp32/doc/index.html  需要運行west init才能運行
west espressif update
2.1 install Zephyr
https://docs.zephyrproject.org/latest/getting_started/index.html?upgrade  stc:  https://askubuntu.com/questions/1090223/how-to-upgrade-dtc-version-in-ubuntu-18-04   

https://docs.zephyrproject.org/latest/getting_started/index.html 裝Zephyr,編譯前要加裝 pip3 install pyelftools 不然出錯:

cd ~/zephyrproject/zephyr
west build -p auto -b arduino_nano samples/basic/blinky 

起步還可以讀:https://www.zephyrproject.org/blinking-an-led-with-zephyr-rtos-creating-an-application/ 

2.2 install ESP32 tool chain

https://docs.espressif.com/projects/esp-idf/en/latest/esp32/get-started/linux-macos-setup.html#get-started-prerequisites? 
在Connect your device一節,Linux下可用dmesh | grep /dev/ttyUSB*確定插入的串口號。

裝ESPRESSIF: https://docs.espressif.com/projects/esp-idf/en/v4.2/esp32/get-started/index.html#get-started-get-prerequisites 在configure之前要加裝:
sudo apt install python-pip;pip install click 
另一錯誤多半是缺省用了Python2,去掉改用Python3的辦法是:
sudo apt purge -y python2.7-minimal
sudo ln -s /usr/bin/python3 /usr/bin/python
sudo apt install -y python3-pip
sudo ln -s /usr/bin/pip3 /usr/bin/pip
python --version

錯誤在menuconfig失敗,找不到不到支持bidict>=0.21.0的模塊,最後將Ubuntu升級到20.04按此文裝成功:https://docs.espressif.com/projects/esp-idf/en/latest/esp32/get-started/linux-macos-setup.html#get-started-prerequisites 編譯用idf.py

2.3 不匹配

至此,Zephyr和ESP32各自的工具都就緒,可是Zephyr編譯ESP32不是用ESP32的工具鏈,因此我按https://www.zephyrproject.org/zephyr-rtos-on-esp32/  裝後,編譯時才發現Zephyr version: 3.0.99是,cmake需3.20,west需0.7.1,dtc需1.5.0,似乎是官網要求的:https://docs.zephyrproject.org/latest/getting_started/index.html

換句話無論按哪個指南做,其中部分軟件更新後,都可導致失敗。按官網發現sdk是0.14而非0.12,又是個耗時的過程。最後編譯錯誤出在

1)-- Found west (found suitable version "0.12.0", minimum required is "0.7.1")
2)-- Found dtc: /usr/bin/dtc (found suitable version "1.5.0", minimum required is "1.4.6")
3)CMake Error at /home/jodai/zephyrproject/zephyr/cmake/toolchain/espressif/generic.cmake:52 (message):
  Unable to find toolchain in
  /home/jodai/.espressif/tools/xtensa-esp32-elf/esp-2020r3-8.4.0/xtensa-esp32-elf
錯誤3最重要,看Cmake可知它產生的工具鏈是: ~/.espressif/tools/xtensa-esp32-elf/esp-2020r3-8.4.0/xtensa-esp32-elf而實際的是:~/.espressif/tools/zephyr/xtensa-esp32-elf/xtensa-esp32-elf,換句話工具鏈要由github下指定版本。

2.3 nRF52840-MDK
支持 Bluetooth 5、Bluetooth Mesh、Thread、IEEE 802.15.4、ANT 等無線協議,帶有片上 Arm CryptoCell 加密子係統,集成了多功能調試器 Arm Mbed DAPLink,提供“拖放式”下載固件、USB CDC 虛擬串口、CMSIS-DAP 仿真等功能。板載Microchip 兩端口 USB 2.0 高速集線器,隻需一個 USB 接口即可同時使用 DAPLink 和 nRF52840 的 USB 設備控製器;有64Mbit 超低功耗 QSPI FLASH、可編程按鍵、RGB LED、晶片天線及外部天線連接器等硬件資源。

nRF52840-MDK 支持Zephyr框架,跨平台開發,可以玩轉多種開源軟件框架(如:nRF5 SDK, Mesh, OpenThread, ZigBee 3.0, Mbed OS 5, Zephyr, Mynewt, iBeacon, Eddystone, Web Bluetooth 等等),提供豐富的在線文檔及示例,幫助加速物聯網應用開發。https://bbs.huaweicloud.com/blogs/163505 

中肯提醒:如果您是 MCU 世界的新手且功耗不是大問題,請選擇 ESP32。 Nordic 的東西(比如這個板子)更適合實際的生產綁定產品開發和原型設計,更加健壯和靈活,但根據我的經驗,IDE 並不直觀,支持庫也不那麽廣泛。 我隻向有經驗的用戶或快速學習者推薦這個產品。 如果您知道自己在做什麽,這是一個很棒的產品,並且比官方的 Nordic nRF 開發板小得多,後者是無用的巨大。直觀的 arduino IDE 更好地支持相同外形尺寸的 esp32 板,並具有廣泛的支持庫、示例代碼示例和龐大的社區來提供幫助。

Zephyr用了類似Linux的menuconfig,Intel曾在開始時很熱心,現在是NXP。缺點是比較複雜,樣本多是板子廠家提供通用性一般,感覺工具出問題比較麻煩不如make直接給出原因。arduino IDE就太簡潔直觀了。所用版本備忘:

$ cmake --version
cmake version 3.23.0
$ python3 --version
Python 3.8.10
$ dtc --version
Version: DTC 1.5.0
$ west --version
West version: v0.12.0
~/zephyrproject/zephyr$ west build -p auto -b esp32 samples/basic/blinky
https://github.com/espressif/crosstool-NG/releases

3. FreeRTOS

https://github.com/freertos?  https://zhuanlan.zhihu.com/p/145699420  https://blog.csdn.net/Chuangke_Andy/article/details/115397230 官網的18f452代碼不能編譯:1)所有源碼是同一目錄上載到官網變成多級目錄 2)XIDE加include路徑無效 3)核心已經修改不配套 4)原編譯器用PICC與XC8不兼容,XC8聲稱的#asm也不能用,asm()可用。新片PIC18F26/46/56Q43為28/40/44/48pin,PIC18F26Q43-I/SP $2.08,PIC18F45Q43T-I/PT $1.7, PIC18F4550T-I/PT $7.91:
18F4550T-I/PT  TQFP44,10x10 2.0-5.5V 32K 2KB-DRAM 256B-EEPROM 48MHz I/O-35 UART/I2C/SPI 10bx13chAD no-DAC  USB2.0
18F45Q43T-I/PT TQFP48,7x7   1.8-5.5V 32K 2KB-DRAM  1KB-EEPROM 64MHz I/O-36 +I2S+PWM     12bx35chAD 8bx1ch no-USB
18F45K50-I/P   DIP40        2.3-5.5V $2.08 32K 2KB-DRAM 256B-EEPROM 48MHz I/O-35 UART/I2C/SPI 10bx13chAD 5bx1ch USB2.0

https://github.com/tahaemara/MicroRTOS-for-PIC-18F-Family PIC18F4550用mikroc PRO for PIC編譯。https://www.youtube.com/watch?v=hYynOanPZWU 使用T0時鍾延遲和軟件堆棧。uP初始化棧指針STKPTR為0,TOSU:TOSH:TOSL存有當前棧指針STKPTR的內容24bit,操作棧時需禁止GIE。STKOVF/STKUNF為上溢/下溢標誌。上溢時若STVREN置位將中斷,否則棧頂0x7F內容被重寫;但是人工設置STVREN不會中斷。STKUNF同理。新品F45K50:1) Have lesser flash write cycles
2) Needs no crystal for USB. built in oscillator works up to 16 MHz.
3) Oscillator configuration, config bits are slightly different.
4) Has a 5-bit DAC and CTMU peripheral for capacitive sensing.
5) might not supported by free mcc18 compilers
6) not supported by PICkit2 (non-official device file supports this)
7) LPT1OSC config bit not available on the K part.

https://github.com/FreeRTOS/FreeRTOS/releases 

以前就說過,Pic因為時間長芯片程序會丟,現有用Pic的產品需重編程,否則不要用。ESP32價廉物美可覆蓋多數嵌入式,但是基於ARM的板子也很多。我用Arduino IDE試了ESP32版本的FreeRTOS-因為CPU是雙核,很好用很容易,如果sample code夾雜了其它CPU的.h文件需要改造。

3.1 FreeRTOS的學習筆記

https://freertos.org/Documentation/161204_Mastering_the_FreeRTOS_Real_Time_Kernel-A_Hands-On_Tutorial_Guide.pdf 
FreeRTOS 
 └─Source 
       ├─tasks.c               FreeRTOS source file - always required
       ├─list.c                   FreeRTOS source file - always required
       ├─queue.c              FreeRTOS source file - nearly always required
       ├─timers.c              FreeRTOS source file - optional
       ├─event_groups.c  FreeRTOS source file - optional
       └─Portable

            ├─[compiler]/[architecture]         All C/asm files
            └─MemMang
                   └─heap_?.c                         heap_?.c, ?=1-5, heap files               

目前v10,由v9開始無需heap manager,有5個heap?.c可選:1適用於任務創建後無需刪除,沒有回收的環境;3類似傳統malloc/free但有線程安全性且忽略
TOTAL_HEAP_SIZE;4是2的增強,會把釋放的相連的緩衝池合並;5用於緩衝池不連續的環境需要配置。函數是pvPortMalloc() 和vPortFree(),也有統計函數xPortGetFreeHeapSize()(unit in bytes)和configTOTAL_HEAP_SIZE定義堆的大小單位是棧寬,如64bit則為64bit。FreeRTOS中,函數前綴v返回void,x返回變量,pv返回void指針,pd是常量。注意ESP32的RAM類型多,官網另有heap說明。注意在原版Vanilla FreeRTOS中uxTaskGetStackHighWaterMark返回Dword長度而在ESP-IDF中返回Byte長度,是堆棧空餘最小值。https://www.youtube.com/watch?v=Qske3yZRW5I#t=10m38s? 

配置文件是FreeRTOS/Source/include/FreeRTOSConfig.h,缺省配置的tick是10ms(可改為1ms)是所有延遲的最小單位,延遲時間用pdMS_TO_TICKS()轉為tick,延遲函數是vTaskDelay()和vTaskDelayUntil(),後者是定周期的任務執行。如果不用係統延遲函數,較低優先級的任務將被堵塞。FreeRTOS配置configUSE_PREEMPTION和configUSE_TIME_SLICING可為搶占式或合作(輪轉)式,通常兩者都置1。任務是一個死循環的函數或進程,其堆棧和變量均在其heap中,由主程序中的vTaskStartScheduler係統調度將其在條件滿足時投入運行,這些條件包括端口或定時中斷、各種信號量等。任務相關函數有:xTaskCreate、xTaskCreateStatic、vTaskPrioritySet、uxTaskPriorityGet、vTaskDelete()。任務狀態有:running、ready、blocked、suspended四種狀態。任務優先級通常是0-31。最低為0是係統idle任務專用,idle任務實現一些係統統計功能,可用vApplicationIdleHook添加用戶任務,如將係統置於低功耗,此時configUSE_IDLE_HOOK需為1。

Queue隊列是一個FIFO先進先出的數據區,但數據的拷貝也可以取消或重寫,任何任務均可訪問。通常用於任務間通信,也可用於任務與中斷服務程序的通信。在任務等待隊列數據時會進入blocked態。可能會有多個任務因等待數據而進入blocked;一旦數據到來,隻有最高優先級或等待最久的任務會被激活。 同樣,可能會有多個寫任務因隊列滿處於blocked,待可寫入時隻有一個被激活,但寫入操作可指定最大等待時延。Queue由 xQueueCreateStatic() 或 xQueueCreateStatic()創建並返回handle;由xQueueSendToBack()和xQueueSendToFront()寫入,或xQueueSendToFrontFromISR()和xQueueSendToBackFromISR();讀是xQueueReceive()。Queue的內容可以是任何數據結構。
TCP TCP/IP stack包的例子:從網絡接收的數據通過結構IPStackEvent_t的發送到TCP/IP任務,結構中的eEventType設置為eNetworkRxEvent,而pvData 指向包含接收數據的緩衝區;根據eEventType來處理各類事件/數據。
如果必須用多個Queue來處理數據,可以把它們放入Queue Set隊列集中,而無需逐個判斷是否有數據待處理,並可捆綁Semaphores信號燈。這是通過將configUSE_QUEUE_SETS置1和xQueueCreateSet、xQueueAddToSet來實現的。然後用xQueueSelectFromSet先取得有數據的Queue Handle或SemaphoreHandle_t handle,比較其名後用xQueueReceive或xSemaphoreTake做相應處理。

mail box在此是長度為1的Queue。Queue通常為另一個任務或中斷服務程序提供數據,後者則取出數據;mailbox不同的是它的寫xQueueOverwrite是覆蓋性的;數據可為任何任務或中斷服務程序通過xQueuePeek來讀但並不取出,用戶代碼可用返回pdTRUE來表明新數據,否則pdFALSE。

軟件計時器用於以固定頻率周期或在未來設定時刻執行程序,籍由其ATimerCallback回調函數實現。這是可選的,需要configUSE_TIMERS置1並包括FreeRTOS/Source/timers.c。回調函數不能被blocked,因此不能調用API、vTaskDelay或xTicksToWait不為0的xQueueReceive。Software Timer由xTimerCreateStatic或xTimerCreate創建,相關函數有xTimerStart/Stop/Reset/ChangePeriod等。它可以是One shot或Auto-reload,有Dormant休眠和Running運行兩種狀態,Timer service或稱RTOS daemon任務自動運行並由configTIMER_TASK_PRIORITY和configTIMER_TASK_STACK_DEPTH配置,API通過timer command queue給它下達命令,隊列長度是configTIMER_QUEUE_LENGTH。每個Timer可通過vTimerSetTimerID()設置ID,由pvTimerGetTimerID()直接讀取,不通過命令隊列。xTimerChangePeriod可以改變定時,例如在CheckTasksAreRunningWithoutError返回錯誤後。

中斷服務調用的API函數(*fromISR)導致更高優先級任務應當被換入時,FreeRTOS設計為在中斷內不做自動切換,但可通過portYIELD_FROM_ISR()或portEND_SWITCHING_ISR()來切換,兩者功能相同,都是taskYIELD()的可在中斷內使用的的版本,有的隻移植其一。調用的參數是pxHigherPriorityTaskWoken,它應初始化為pdFALSE,在發生上述情況下被RTOS置為pdTRUE。如果初始化為NULL則禁止其功能。極少數移植隻允許portYIELD_FROM_ISR()在終端服務程序的最後使用。
Deferred Interrupt Processing是指盡可能的把中斷服務的功能放在服務程序之外的任務中,以減小中斷開銷和使用更多的API功能,該任務的優先級通常高於其它任務,用xSemaphoreCreateBinary創建且調用xSemaphoreTake()使自己掛起。在中斷服務程序中調用xSemaphoreGiveFromISR()給該任務、開中斷後調用portYIELD_FROM_ISR(),將直接切換到該任務。這種semaphore的用法與常規不同-不給還,更像是長度為1的Queue。vPortGenerateSimulatedInterrupt()可用於中斷仿真。
centralized deferred interrupt processing是指用xTimerPendFunctionCallFromISR()延遲中斷處理給RTOS Daemon守護程序,避免每個中斷都要一個外處理任務;該函數的中斷不安全版是xTimerPendFunctionCall。許多API函數有中斷安全版(fromISR),例如Queue讀寫函數。
嵌套的中斷需要配置,注意Cortex-M的中斷是數字越小優先級越高,可以用Assert使得FreeRTOS檢測。


資源管理任務在訪問不可重入且非線程安全的共享資源時,需要獨占訪問權直至資源到一致狀態。用於例如對非原子的讀-修改-寫代碼用Mutex以免被打斷,或在打印字符行時不會被插入其它字符串,兩者均可用宏調用taskENTER_CRITICAL()和taskEXIT_CRITICAL()來包圍,稱為基本臨界區。在中斷中臨界區可用uxSavedIntruptStatus = taskENTER_CRITICAL_FROM_ISR();和taskEXIT_CRITICAL_FROM_ISR(uxSavedIntrStatus);來包圍。另一對可以使用的函數是vTaskSuspendAll和xTaskResumeAll。
binary semaphore通常用於事件同步或延遲的中斷處理,counting semaphore通常用於事件或資源計數。常規的它是0~N之間的變量;但在FreeRTOS中是長度為N內容不論的Queue。它由configUSE_COUNTING_SEMAPHORES置1使能,用xSemaphoreCreateCounting創建,多次調用xSemaphoreGiveFromISR可以設置大於1的值。
mutual exclusion(Mutex)
互斥鎖與之類似,常用於任務中來獨占被多個任務共享的資源。Mutex可理解為token,獲得它的任務獨享資源,用後必須交回;而binary semaphore多用於事件同步,獲得後不必交回多被丟棄。由configUSE_MUTEXES使能,xSemaphoreCreateMutex創建,仍用xSemaphoreTake和xSemaphoreGive來獲得和交回。低優先級的任務能因獲得Mutex而導致高優先級的任務被blocked,直至Mutex被釋放,這被稱為Priority inversion優先級反轉。由於低優先級的任務不被換出,相當於它具有了與高優先級任務同樣的優先級,又稱Mutex有Priority Inheritance優先級繼承的特點;而binary semaphore沒有這個特點。如果是同一優先級,剛獲得Mutex的任務B要等下次調度;但前一任務A可能再次獲得Mutex並繼續運行,導致任務B不能即時運行,這需要適當的編碼以平衡任務的運行時間,或及時調用taskYIELD。
如果兩個任務互相用Mutex獨占了對方所需資源,兩者都因等待而無法運行,這被稱為Dead lock死鎖,需要在編碼時避免或給Mutex等待限時,或者將資源置於Gatekeeper任務管理之下,需要的任務都通過它來獲得資源。使用時configUSE_TICK_HOOK置1,然後定義vApplicationTickHook(),它在每個tick被執行,因此必須簡短。
Dead Lock死鎖也可在單個任務中因多次獲取Mutex而忘了釋放而產生,這時可用Recursive Mutex,同一任務可N次獲得該Mutex,但是在N次釋放前別的任務不可獲得該Mutex。相關函數名在Mutex前有前綴Recursive。


事件組允許任務在阻塞狀態下等待多個組合事件;可在事件發生時unblock等待該事件(組)的所有任務,可以由多個任務共享。EventBits_t缺省為32bit,低24bit分別對應一個事件。以FreeRTOS+TCP TCP/IP stack包為例,它包括在FreeRTOS_Socket_t結構中,含有TCP socket的accept/bind/read/close及Abort事件,由FreeRTOS+TCP API使用。
相關函數為xEventGroupCreate、xEventGroupSetBits(FromISR)、xEventGroupWaitBits,最後這個函數允許所在任務按事件組blocked和unblocked。事件組也可用於任務同步,例如接受到TCP包的任務委托其它幾個任務處理,在都處理完後相關事件都被置位,該包就可close。


Task Notifications任務通知:指任務間直接通信,不通過例如queue、semaphore等對象中轉。將configUSE_TASK_NOTIFICATIONS置1後,每個任務都有“Notification State”和uint32的“Notification Value”。注意:發送任務不能阻塞以待發送完成。接收任務隻允許是一個且不能是中斷服務程序,可選指定時延的堵塞式等待它的通知狀態變為Pending,在讀取通知值後狀態被置為Not-Pending。有兩套函數:簡化的發送xTaskNotifyGive()/xTaskNotifyGiveFromISR(),發送後通知值自動加1,配用堵塞等待的ulTaskNotifyTake()接收,可以取代以前的binary semaphore用於延遲的中斷服務;增強的xTaskNotify()/xTaskNotifyFromISR() /xTaskNotifyWait(),多了對通知值的讀寫,可提供類似mail box或事件組覆蓋寫入的功能。xTaskNotifyWait()以可選的超時等待調用任務接收通知。如果接收任務在等待通知到達時已在等待通知的blocked態,則接收RTOS任務將被unblock並清除通知。
書中偽碼例154:由Mutex互斥的xUART_Send()被共享來發送數據,先用xSemaphoreTake()清空,繼而調用底層發送,再用xSemaphoreTake()使自己處於堵塞態。UART硬件在最後一字符被發送後中斷,在中斷服務中用xSemaphoreGiveFromISR()使得xUART_Send()解除堵塞,隨即portYIELD_FROM_ISR()切換運行。

例155:semaphore帶來的存儲和執行開銷、及初始化在上例中是不必要的。本例中semaphore由TaskHandle_t類型的xTaskToNotify取代,後者由API和中斷共享。如果CPU位長不低於任務通知值,寫入是原子操作,否則寫入需臨界域保護。用於接收的類似實現見例156。例157則用xTaskNotifyWait()以便傳送ADC值,很實用的方法。本章最後說明了雲端收發的流程

關於調試:並非所有編譯器都提供Assert,為此可在配置中定義等效的configASSERT(),出錯時後續的代碼不會運行。例如自定義函數vAssertCalled()然後定義:
    #define configASSERT( x ) if( ( x ) == 0 ) vAssertCalled( __FILE__, __LINE__ )
FreeRTOS提供Malloc failed hook、Stack overflow hook、Task Run-Time Statistics、Run-Time Statistics Clock,配置後與uxTaskGetSystemState()聯用。另有Helper函數和Trace Hook Macros,許多IDE也提供debug plugin。FreeRTOS+Trace是Percepio提供的運行時診斷和優化工具,包括互聯的20種圖表。
最常見開發問題是incorrect interrupt priority assignment, stack overflow, inappropriate use of printf().
1)中斷優先級:硬件中斷的優先級應高於任務。不能超出configMAX_SYSCALL_INTERRUPT_PRIORITY,不能不定義,ARM Cortex把最低數字認為最高優先級。例如某CPU中斷和配置最高中斷都是5,但可被優先級4中斷,則API中斷優先級的值不應低於5。ARM Cortex的硬件和庫實現都各有不同。優先級可分為pre-emption priority和sub-priority兩部分,請隻使用前一部分。有時候configMAX_SYSCALL_INTERRUPT_PRIORITY被稱為configMAX_API_CALL_INTERRUPT_PRIORITY。
2)堆棧溢出:uxTaskGetStackHighWaterMark()返回某任務棧的最小剩餘空間。配置configCHECK_FOR_STACK_OVERFLOW為1(返回棧的曆史)或2(返回最近20此)並使用下列函數原型來勾取棧溢出的處理函數:void vApplicationStackOverflowHook( TaskHandle_t *pxTask, signed char *pcTaskName );
3)亂用printf()/sprintf():除非特殊設計。這兩函數通常不具有線程安全性,可能會用malloc()或用堆棧,會加大程序尺寸和開銷。開源的printf-stdarg.c可用來替代庫函數,並可將輸出重定向到端口。
其它注意事項:在中斷服務中或調度器被掛起-例如在臨界區域內-使用一般API函數可能崩盤。在調度器運行前的中斷可能崩盤。在調度器工作前使用API可能導致中斷被禁止。

3.2 FreeRTOS配置文件詳解
C:Userse6400AppDataLocalArduino15packagesesp32hardwareesp321.0.6toolssdkincludefreertosfreertosFreeRTOSConfig.h 
內核配置一
參數名稱          參數說明
USE_PREEMPTION      定義調度器模式
CPU_CLOCK_HZ       定義CPU的主頻
TICK_RATE_HZ       定義係統時鍾節拍數
MAX_PRIORITIES      定義可供用戶使用的最大優先級數
MINIMAL_STACK_SIZE   定義空閑任務的棧空間大小
MAX_TASK_NAME_LEN   定義任務名最大的字符數
USE_16_BIT_TICKS    係統時鍾節拍計數使用TickType_t數據類型定義
IDLE_SHOULD_YIELD   用於使能與空閑任務同優先級的任務
內核配置二
參數名稱                   參數說明
USE_MUTEXES                 用於使能互斥鎖
USE_RECURSIVE_MUTEXES          用於使能遞歸互斥鎖
USE_COUNTING_SEMAPHORES           用於使能計數信號量
QUEUE_REGISTRY_SIZE               用於設置可以注冊的信號量和消息隊列個數
USE_APPLICATION_TASK_TAG          用於使能任務標記
ENABLE_BACKWARD_COMPATIBILITY     用於使能新版本對老版本的兼容特性
USE_PORT_OPTIMISED_TASK_SELECTION 用於優化優先級列表中藥執行的最高優先級任務的算法
USE_TICKLESS_IDLE                 用於使能tickless低功耗模式
USE_TASK_NOTIFICATIONS            使能任務間直接的消息傳遞,包括信號量、事件標誌組和消息郵箱
內存管理
參數名稱            參數說明
MEMORY_ALLOCATION   定義內存分配模式
TOTAL_HEAP_SIZE     定義動態內存分配總長度
HEAP_NUMBER         定義動態內存管理方式
任務運行信息獲取配置
參數名稱                         參數說明
GENERATE_RUN_TIME_STATS          用於使能任務運行狀態參數統計
USE_TRACE_FACILITY               使能此配置將添加額外的結構體成員和函數
USE_STATS_FORMATTING_FUNCTIONS   用戶配置宏定義 configUSE_TRACE_FACILITY 和 configUSE_STATS_FORMATTING_FUNCTIONS
   都為 1 的時候,將使能函數 vTaskList() 和 vTaskGetRunTimeStats(),如果兩者中任何一個為 0,那麽這兩個函數都將被禁能
軟件定時器
參數名稱        參數說明
USE_TIMERS      用於使能軟件定時器
中斷優先級
參數名稱                                參數說明
LIBRARY_LOWEST_INTERRUPT_PRIORITY       用於配置 FreeRTOS 用到的 SysTick 中斷和 PendSV 中斷的優先級
LIBRARY_MAX_SYSCALL_INTERRUPT_PRIORITY  定義了受 FreeRTOS 管理的最高優先級中斷
函數Include            配置
參數名稱               參數說明
vTaskPrioritySet       設置任務優先級
uxTaskPriorityGet      獲取任務優先級
vTaskDelete            任務刪除
vTaskCleanUpResources  清理任務資源
vTaskSuspend           任務掛起
vTaskDelayUntil        任務絕對延時
vTaskDelay             任務延時
xTaskGetSchedulerState 獲取調度器狀態
xTaskResumeFromISR     在中斷中恢複任務
xQueueGetMutexHolder   獲取互斥鎖持有者
pcTaskGetTaskName      獲取任務名稱
uxTaskGetStackHighWaterMark 獲取任務堆棧信息
xTaskGetCurrentTaskHandle   獲取當前任務句柄
eTaskGetState               獲取任務狀態
xEventGroupSetBitFromISR    在中斷中設置事件標誌組
xTimerPendFunctionCall      定時器掛起後回調函數
xTaskAbortDelay             終止任務延時
xTaskGetHandle              獲取任務句柄
————————————————原文鏈接:https://blog.csdn.net/Chuangke_Andy/article/details/109597607 
 
3.3 移植
 
3.4 用CubeMX移植
https://blog.csdn.net/so_cracy/article/details/80246414 配置裏把FreeRTOS勾選,若定時器衝突換一個,即可。
CubeMX - STM32Cube initialization code generator:https://blog.csdn.net/ybhuangfugui/article/details/52225736
 
[ 打印 ]
閱讀 ()評論 (0)
評論
目前還沒有任何評論
登錄後才可評論.