与现代传感器的接口:轮询ADC驱动程序
與現代傳感器的接口:輪詢ADC驅動程序
Interfacing with modern sensors: Polled ADC drivers
我們研究了在現代嵌入式應用程序中,開發人員應該如何創建一個接口,將底層驅動程序實現細節與應用程序代碼分離。這個接口提供了一個體系結構抽象,通過減少對硬件的依賴,提高了應用程序代碼的可伸縮性和可移植性。
現在我們將開始研究幾種不同的方法,開發人員可以根據我們在3個微控制器驅動程序設計技術中討論的技術來實現ADC驅動程序。在本文中,我們將更詳細地研究如何使用輪詢技術,并討論阻塞和非阻塞驅動程序之間的區別。
阻止還是不阻止,這是個問題
當為微控制器開發任何驅動程序時,開發人員必須決定他們的驅動程序是阻塞的還是非阻塞的。阻塞驅動程序基本上會暫停代碼的執行,直到驅動程序完成其任務為止。例如,printf映射到UART的典型實現是阻塞的。
當你打電話時:
printf(“你好,世界!”);
開發人員知道,無論該語句后面的哪一行代碼都不會執行,直到整個“Hello World!“聲明已經在通用異步收發器上打印出來了?!澳愫?#xff0c;世界!“包含12個字節,96位,但語句阻塞的時間取決于UART波特率。對于配置為1Mbps的UART,您將期望大約96微秒。對于配置為9600bps的UART,您將期望大約10000微秒!這是一個很大的區別,這取決于硬件的配置,它可以顯著地影響程序的執行,UART驅動程序被配置為阻塞驅動程序。
非阻塞驅動程序是在驅動程序完成其任務時不會暫停程序執行的驅動程序。例如,上一個例子中的printf和UART驅動程序可以被配置成不阻塞,而是允許應用程序在每個字節被發送出UART時繼續執行。這可以在適當的情況下實現更有效的應用,但需要額外的設置,例如使用中斷、DMA或至少一個傳輸緩沖區。
如何設計驅動程序取決于應用程序和硬件。例如,如果UART被配置為1Mbps,那么從效率的角度來看,編寫非阻塞驅動程序可能不會獲得太多好處,實際上可能會導致更多的問題,而不是通過增加程序復雜性來解決問題。然而,如果應用程序調用9600bps,其中應用程序代碼被阻塞10毫秒,那么擁有一個非阻塞驅動程序可以顯著提高程序效率,并且額外的時間復雜度問題的風險更小,也更易于管理。
嵌入式ADC驅動程序概述
需要注意的是,在一個博客中,我無法完成編寫完整ADC驅動程序所需的所有步驟。我可以很容易地寫一篇20頁的論文,或者開一個完整的網絡研討會,它可能還不能涵蓋所有的細節,但我們至少可以看看一些核心部分。
低級驅動程序在初始化時接收配置模塊,并根據配置設置硬件。低級驅動程序提供了一個公共硬件抽象層(HAL),應用程序代碼可以使用它。ADC-HAL調用應該是通用的,以便高級應用程序可以以任何必要的方式配置硬件,并且可以重用和擴展。例如,我過去使用的一些ADC HAL調用包括:
·
AdcError_t Adc_Init(const AdcConfig_t * Config);
·
AdcError_t Adc_StartConversion(void);
·
bool Adc_ConversionComplete(void);
·
void Adc_RegisterWrite(uint32_t const Address, uint32_t const Value);
·
uint32_t Adc_RegisterRead(uint32_t Address);
·
void Adc_CallbackRegister(AdcCallback_t const Function, TYPE
(*CallbackFunction)(type));
前三個API提供初始化ADC硬件、啟動轉換并檢查轉換狀態的功能。最后三個函數的設計是為了允許低層硬件的可伸縮性。例如,如果HAL不提供應用程序所需的選項(例如轉換單個ADC信道),則可以使用ADC_RegisterRead和ADC_RegisterWrite函數擴展HAL。這提供了基于應用程序需求的靈活性,而不需要創建一個壓倒性的API。
編寫一個簡單的阻塞ADC驅動程序
我們可以編寫一個非常簡單的ADC驅動程序,它位于硬件層之上。例如,我們可以創建一個名為Adc_Sample的簡單函數,該函數啟動Adc硬件,然后將所有結果存儲在緩沖區中,然后應用程序可以訪問該緩沖區。存儲模擬值計數值的緩沖區不一定只需要存儲一個值,而是可以存儲多個值,這些值以后可以根據應用程序的需要進行平均或過濾。采樣函數的阻塞版本可能如下所示:
正如您在這段代碼中看到的,while循環會阻止執行,直到ADC硬件完成轉換,然后將值存儲在應用程序緩沖區中。
編寫一個簡單的無阻塞ADC驅動程序
將阻塞驅動程序轉換為非阻塞代碼非常簡單,但是需要對更高級別的應用程序代碼進行更改。例如,現在,如果應用程序要對傳感器進行采樣,開發人員會調用:
Adc_Sample();
在非阻塞版本中,開發人員必須檢查Adc_Sample的返回值,以查看示例是否已完成并可以使用。這使示例可以在后臺運行,應用程序代碼在驅動程序代碼的以下更新后繼續運行:
結論
正如我們在這篇文章中看到的,有多種方法來編寫ADC,并且實現可以是阻塞的,也可以是非阻塞的,這取決于我們的需要。阻塞驅動程序往往比非阻塞驅動程序更簡單、更不完整,但它們可能效率低下。非阻塞驅動程序允許其他代碼在驅動程序工作時運行,但是應用程序代碼仍然需要檢查狀態,這在輪詢實現中本身效率低下。
總結
以上是生活随笔為你收集整理的与现代传感器的接口:轮询ADC驱动程序的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 如何保证Qt状态机的最佳性能
- 下一篇: 现代传感器的接口:中断驱动的ADC驱动程