一,軟件定時(shí)器概述
軟件定時(shí)器允許設(shè)置一段時(shí)間,當(dāng)設(shè)定的時(shí)間到達(dá)之后就會(huì)執(zhí)行指定的功能函數(shù),被定時(shí)器調(diào)用的這個(gè)函數(shù)叫做定時(shí)器的回調(diào)函數(shù)。回調(diào)函數(shù)的兩次執(zhí)行間隔叫做定時(shí)器的定時(shí)周期。
二,回調(diào)函數(shù)的注意事項(xiàng)
回調(diào)函數(shù)是在定時(shí)器服務(wù)任務(wù)中執(zhí)行的,因?yàn)槎〞r(shí)器服務(wù)任務(wù)是由內(nèi)核產(chǎn)生,無法由用戶控制,所以本身的運(yùn)行周期時(shí)間是固定的。
所以調(diào)用回調(diào)函數(shù)不可以調(diào)用有阻塞的函數(shù)API,eg.vTaskDelay()、vTaskDelayUntil()等,因?yàn)楫?dāng)執(zhí)行定時(shí)器服務(wù)任務(wù)的回調(diào)函數(shù)里有這些函數(shù),CPU就會(huì)被占用,使得定時(shí)器的任務(wù)無法得到處理其他定時(shí)器的超時(shí)任務(wù)【定時(shí)器服務(wù)任務(wù)負(fù)責(zé)管理和處理所有的軟件定時(shí)器的超時(shí)事件】,當(dāng)阻塞的事件過長(zhǎng)的時(shí)候,會(huì)導(dǎo)致超時(shí)事件得不到處理,導(dǎo)致系統(tǒng)出現(xiàn)異常。
三.定時(shí)器命令隊(duì)列
定時(shí)器命令隊(duì)列是用戶應(yīng)用任務(wù)和定時(shí)器服務(wù)任務(wù)的一個(gè)媒介。
#define xTimerStart( xTimer, xTicksToWait ) xTimerGenericCommand( ( xTimer ), tmrCOMMAND_START, ( xTaskGetTickCount() ), NULL, ( xTicksToWait ) )
tmrCOMMAND_START命令表示啟動(dòng)一個(gè)定時(shí)器,并通過定時(shí)器命令隊(duì)列把相關(guān)信息傳遞給定時(shí)器服務(wù)任務(wù),由定時(shí)器服務(wù)任務(wù)統(tǒng)一管理和執(zhí)行。
定時(shí)器服務(wù)任務(wù)在接收到tmrCOMMAND_START命令后,會(huì)檢查定時(shí)器句柄是否有效,如果有效則將該定時(shí)器加入定時(shí)器鏈表,并按照xTimeToWait指定的時(shí)間長(zhǎng)度啟動(dòng)該定時(shí)器的超時(shí)計(jì)時(shí)器。同時(shí),定時(shí)器服務(wù)任務(wù)會(huì)根據(jù)該定時(shí)器的超時(shí)時(shí)間和當(dāng)前系統(tǒng)時(shí)間計(jì)算出該定時(shí)器的超時(shí)時(shí)間點(diǎn),并在該時(shí)間點(diǎn)觸發(fā)該定時(shí)器的回調(diào)函數(shù)。
四.軟件定時(shí)器的屬性
·單次定時(shí)器:當(dāng)定時(shí)器開始啟動(dòng),并且到達(dá)指定時(shí)間,回調(diào)函數(shù)只會(huì)執(zhí)行一次,且定時(shí)器不會(huì)再自動(dòng)重新啟動(dòng),但會(huì)手動(dòng)啟動(dòng)。
·周期定時(shí)器:當(dāng)定時(shí)間隔到達(dá)之后,執(zhí)行回調(diào)函數(shù),還會(huì)自動(dòng)重新啟動(dòng),可以實(shí)現(xiàn)周期性的調(diào)用函數(shù)。
?
?對(duì)于軟件定時(shí)器我的理解:
軟件定時(shí)器可以設(shè)定超時(shí)事件且不會(huì)和定時(shí)器服務(wù)任務(wù)產(chǎn)生沖突,因?yàn)镕reeRTOS內(nèi)核的定時(shí)器服務(wù)是基于軟件定時(shí)器和系統(tǒng)時(shí)基(tick)實(shí)現(xiàn)的。定時(shí)器服務(wù)任務(wù)是一個(gè)高優(yōu)先級(jí)任務(wù),它負(fù)責(zé)處理所有的軟件定時(shí)器事件。在系統(tǒng)啟動(dòng)時(shí),定時(shí)器服務(wù)任務(wù)會(huì)被創(chuàng)建并開始運(yùn)行,它以系統(tǒng)時(shí)基的時(shí)間間隔定期被調(diào)度執(zhí)行。定時(shí)器服務(wù)任務(wù)的主要作用是從定時(shí)器消息隊(duì)列中獲取定時(shí)器事件,然后根據(jù)定時(shí)器事件的類型進(jìn)行相應(yīng)的處理,例如啟動(dòng)、停止、重置、刪除定時(shí)器等。而定時(shí)器事件則由軟件定時(shí)器生成,并通過xTimerChangePeriod()、xTimerStart()等函數(shù)向定時(shí)器服務(wù)任務(wù)發(fā)送。軟件定時(shí)器提供了一種輕量級(jí)、靈活的機(jī)制,允許用戶自定義定時(shí)器的超時(shí)時(shí)間。當(dāng)軟件定時(shí)器到達(dá)超時(shí)時(shí)間時(shí),F(xiàn)reeRTOS內(nèi)核會(huì)自動(dòng)將該定時(shí)器的事件加入定時(shí)器消息隊(duì)列中,等待定時(shí)器服務(wù)任務(wù)處理。
軟件定時(shí)器開始運(yùn)行,當(dāng)設(shè)定的時(shí)間到了,會(huì)產(chǎn)生一個(gè)超時(shí)事件,將該事件放入到消息隊(duì)列中,計(jì)數(shù)器此時(shí)會(huì)開始第二輪的計(jì)時(shí),當(dāng)?shù)却某瑫r(shí)事件被執(zhí)行的時(shí)候,也就是定時(shí)器服務(wù)任務(wù)執(zhí)行的時(shí)候,計(jì)數(shù)器要暫停,等待服務(wù)任務(wù)執(zhí)行結(jié)束,才會(huì)從原本暫停的計(jì)數(shù)值開始繼續(xù)執(zhí)行,當(dāng)超時(shí)事件一直未被處理或者下一輪產(chǎn)生了新的超時(shí)事件,這個(gè)超時(shí)事件則會(huì)被舍棄。
當(dāng)定時(shí)器到達(dá)超時(shí)時(shí)間后,若同時(shí)有多個(gè)定時(shí)器到期,則定時(shí)器服務(wù)任務(wù)會(huì)按照它們的超時(shí)時(shí)間先后順序進(jìn)行處理。如果某個(gè)定時(shí)器回調(diào)函數(shù)執(zhí)行的時(shí)間過長(zhǎng)導(dǎo)致定時(shí)器服務(wù)任務(wù)未及時(shí)處理其他超時(shí)事件,則可能會(huì)影響其他定時(shí)器的響應(yīng)能力和精度。
超時(shí)事件的1個(gè)tick:1ms
#define configTICK_RATE_HZ (1000) //時(shí)鐘節(jié)拍頻率,這里設(shè)置為1000,周期就是1ms
五,函數(shù)介紹
1.xTimerStart( TimerHandle_t xTimer, TickType_t xTicksToWait );
- xTimer:要啟動(dòng)的定時(shí)器的句柄,它是在調(diào)用 xTimerCreate() 函數(shù)創(chuàng)建定時(shí)器時(shí)返回的。
- xTicksToWait:等待定時(shí)器啟動(dòng)的最長(zhǎng)時(shí)間。如果傳遞的值為 0,則該函數(shù)將立即返回,而不等待定時(shí)器啟動(dòng);如果傳遞的值為 portMAX_DELAY,則該函數(shù)將一直等待,直到定時(shí)器啟動(dòng)。
- 調(diào)用 xTimerStart() 函數(shù)之后,定時(shí)器會(huì)開始計(jì)時(shí),并且在每次計(jì)時(shí)器超時(shí)事件發(fā)生時(shí),都會(huì)調(diào)用該定時(shí)器注冊(cè)的回調(diào)函數(shù)。需要注意的是,在啟動(dòng)定時(shí)器之前,必須先通過 xTimerReset() 函數(shù)重置定時(shí)器的計(jì)數(shù)器,以確保定時(shí)器從指定的周期開始計(jì)時(shí)。
2.TimerReset( TimerHandle_t xTimer, TickType_t xTicksToWait );
- xTimer:要重置的定時(shí)器的句柄,它是在調(diào)用 xTimerCreate() 函數(shù)創(chuàng)建定時(shí)器時(shí)返回的。
- xTicksToWait:等待定時(shí)器重置的最長(zhǎng)時(shí)間。如果傳遞的值為 0,則該函數(shù)將立即返回,而不等待定時(shí)器重置;如果傳遞的值為 portMAX_DELAY,則該函數(shù)將一直等待,直到定時(shí)器重置。
3.xTimerCreate( const char * pcTimerName, TickType_t xTimerPeriod, UBaseType_t uxAutoReload, void * pvTimerID, TimerCallbackFunction_t pxCallbackFunction );文章來源:http://www.zghlxwxcb.cn/news/detail-453956.html
- pcTimerName:定時(shí)器的名稱,在調(diào)試和跟蹤時(shí)使用。通常可以將其設(shè)置為 NULL。
- xTimerPeriod:定時(shí)器超時(shí)時(shí)間,單位是 tick。用于確定定時(shí)器超時(shí)事件的發(fā)生間隔。當(dāng)定時(shí)器服務(wù)任務(wù)開始時(shí),定時(shí)器計(jì)數(shù)器會(huì)被遞減,直到達(dá)到 0,此時(shí)定時(shí)器超時(shí)事件就會(huì)發(fā)生??梢詫⒃搮?shù)設(shè)置為 pdMS_TO_TICKS() 宏的值來將毫秒轉(zhuǎn)換為 tick。
- uxAutoReload:是否需要自動(dòng)重置計(jì)數(shù)器,并從頭開始重新計(jì)時(shí),以便創(chuàng)建一個(gè)循環(huán)定時(shí)器。如果將其設(shè)置為 0,則該定時(shí)器不會(huì)自動(dòng)重置計(jì)數(shù)器,而是只會(huì)執(zhí)行一次超時(shí)事件;否則,如果將其設(shè)置為 1,則該定時(shí)器將會(huì)自動(dòng)重置計(jì)數(shù)器,并且在每個(gè)超時(shí)事件發(fā)生后,會(huì)按照設(shè)置的周期再次觸發(fā)超時(shí)事件。
- pvTimerID:一個(gè)指向任意類型數(shù)據(jù)的指針,用于指定應(yīng)該在計(jì)時(shí)器超時(shí)事件中傳遞的數(shù)據(jù)。如果不需要傳遞數(shù)據(jù),則可以將其設(shè)置為 NULL。
- pxCallbackFunction:一個(gè)指向定時(shí)器超時(shí)事件回調(diào)函數(shù)的指針。當(dāng)定時(shí)器計(jì)數(shù)器達(dá)到 0 時(shí),定時(shí)器服務(wù)任務(wù)會(huì)調(diào)用此函數(shù)。在該函數(shù)中,可以編寫相關(guān)的任務(wù)代碼來執(zhí)行所需的操作,例如發(fā)出信號(hào)量或?qū)⑷蝿?wù)加入隊(duì)列等。
4.xTimerStop( TimerHandle_t xTimer, TickType_t xTicksToWait );文章來源地址http://www.zghlxwxcb.cn/news/detail-453956.html
- xTimer:要停止的定時(shí)器的句柄,它是在調(diào)用 xTimerCreate() 函數(shù)創(chuàng)建定時(shí)器時(shí)返回的。
- xTicksToWait:等待該定時(shí)器停止的最長(zhǎng)時(shí)間。如果傳遞的值為 0,則該函數(shù)將立即返回,而不等待定時(shí)器停止;如果傳遞的值為 portMAX_DELAY,則該函數(shù)將一直等待,直到定時(shí)器停止。
到了這里,關(guān)于FreeRTOS(6)----軟件定時(shí)器的文章就介紹完了。如果您還想了解更多內(nèi)容,請(qǐng)?jiān)谟疑辖撬阉鱐OY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!