我有大約6個傳感器(GPS,IMU等),我需要不斷收集數據。出於我的目的,我需要從每個(在很短的時間範圍內)讀取一個完整的數據包。現在我正在使用中斷,但是這會導致來自某些傳感器的更多數據,而且如前所述,我需要將數據匹配起來。嵌入式系統 - 輪詢
移動到基於輪詢的系統中,我可以按設定的順序輪詢每個傳感器嗎?這樣我可以從每個「週期」的每個傳感器獲取數據。
但是,我擔心輪詢的速度,因爲這個系統需要接近實時運行。
我有大約6個傳感器(GPS,IMU等),我需要不斷收集數據。出於我的目的,我需要從每個(在很短的時間範圍內)讀取一個完整的數據包。現在我正在使用中斷,但是這會導致來自某些傳感器的更多數據,而且如前所述,我需要將數據匹配起來。嵌入式系統 - 輪詢
移動到基於輪詢的系統中,我可以按設定的順序輪詢每個傳感器嗎?這樣我可以從每個「週期」的每個傳感器獲取數據。
但是,我擔心輪詢的速度,因爲這個系統需要接近實時運行。
輪詢結合「主定時器中斷」可能是你的朋友在這裏。假設您的「最慢」傳感器可以提供20ms間隔的數據,並且可以更快地讀取其他數據。這是50更新每秒。如果這個距離足夠接近實時(可能對於IMU是近距離的),那麼你可能會這樣做:
當計時器熄滅,設置一個標誌中斷服務程序中:
volatile uint8_t timerFlag = 0;
ISR(TIMER_ISR_whatever)
{
timerFlag = 1; // nothing but a semaphore for later...
}
然後,在你的主循環行爲時timerFlag
說,它的時間:
while(1)
{
if(timerFlag == 1)
{
<read first device>
<read second device>
<you get the idea ;) >
timerflag = 0;
}
}
通過這種方式,您可以讀取每個設備並保持其讀數同步。這是解決嵌入式空間中這個問題的典型方法。現在,如果你需要的數據速度超過20ms,那麼你縮短了計時器等等。像這樣的情況下,最大的問題是「你能輪詢多快」與「你需要輪詢多快」。 「只有實驗並瞭解各種設備的特性和時間才能告訴你。但是,當所有時機「合適」時,我提出的是一個通用解決方案。
編輯,採用不同的方法
更基於中斷的例子:
volatile uint8_t device1Read = 0;
volatile uint8_t device2Read = 0;
etc...
ISR(device 1)
{
<read device>
device1Read = 1;
}
ISR(device 2)
{
<read device>
device2Read = 1;
}
etc...
// main loop
while(1)
{
if(device1Read == 1 && device2Read == 1 && etc...)
{
//< do something with your "packet" of data>
device1Read = 0;
device2Read = 0;
etc...
}
}
在這個例子中,你的所有設備可以中斷驅動,但主循環處理仍然是制約,由最慢的中斷節奏來調節。無論速度或延遲如何,均可使用每個設備的最新完整讀數。這種模式更接近您的想法嗎?
@Clifford確實。在這樣的情況下,我所做的是外圍設備採樣速率大不相同的情況,就是使用計數器「減速」timerFlag。平衡機器人的IMU可能需要50次更新/秒才能保持直立,而GPS只能輪詢50次。 – TomServo
這就是爲什麼我不喜歡投票。使用這種方法,您必須計算所有傳感器組合的數據處理延遲,並確保第一個輪詢間隔不超過20ms(作爲示例)。只要您將來添加新的傳感器,或者傳感器在數據處理或輪詢間隔方面發生變化,您的所有環路方案就會陷入癱瘓,變得完全不可維護且不可擴展。 – Alex
@亞歷克斯同意。我更喜歡在可能的情況下中斷。然而,OP的問題是關於投票的問題,事實是,有可能這樣做。 OP可能沒有興趣在這裏擴展任何東西,只是一次性的解決方案。因此,無需判斷我用可能的解決方案回答了她的問題。 – TomServo
輪詢是一個相當不錯的,容易實現的想法,以防您的傳感器可以(你期望的輸出頻率比較)提供的數據幾乎瞬間。如果數據源需要大量(甚至可變)時間來提供讀數或需要異步「啓動/收集」循環,它確實會陷入惡夢。您必須對輪詢週期進行排序以適應「最慢」數據源。
如果您知道每個數據源的平均「數據轉換率」,可以採用什麼方法來設置多個定時器(每個數據源),這些定時器在poll time - data conversion rate
處觸發,並從這些數據源中啓動測量定時器ISR。然後在poll timer + some safety margin
上觸發最後一個計時器,收集所有轉換結果。另一方面,只要你沒有任何合理的處理浪費的CPU/CPU資源,你從「快速」數據源中看到的「有太多測量結果」的明顯問題就不會對我造成太大的影響,傳感器負載。
如果您有一些浪費的週期,最後一個更簡單的方法是:簡單地將數據源從「最慢」排序到「最快」,然後按照該順序開始測量,然後等待結果以相同順序和民意調查。
嗯!?輪詢和中斷混合。我喜歡。好的方法,將牢記在心。 – Alex
所以問題是...?測試你的投票循環時間,看看它是否符合你的要求... – LPs
我個人不喜歡投票。你的傳感器沒有中斷嗎? – Alex
既不僅僅是輪詢,也不是中斷只與實時有關,你必須做你的系統工程,這會給出所有的答案。輪詢當然是最容易的,你可以確定每條事件路徑的時間,只要最慢的一條不干擾其他條件的要求,你就很好。有時候你可以只通過輪詢來做到這一點,或者只能打斷它,但可能會在中間的某個地方結束。中斷並不意味着你在那裏處理它們,有時候不好,所以沒有人回答。 –