(消息)在通話過程中斷關閉,以防止重入(@ MUL3232)
我不想定時器禁用,因爲我需要精確度。
這是一個錯誤的擔心。
代碼只是保護自己免受良好設計可避免發生的異常情況的影響。
當運行定時器中斷服務程序(ISR),另一定時中斷的再entrantcy通常只發生在兩種情況:
定時器ISR頻率太高。這意味着處理1個定時器所需的時間很短,另外還有一個時間是在這個完成之前發生的。這不是一個好設計。爲了解決這個問題,確保定時器頻率不是很高。
延遲。處理某些需要很長時間的其他ISR時發生定時器ISR,從而阻止該定時器ISR調用。在執行此ISR時,又發生了另一個定時器中斷。爲了解決這個問題,確保所有ISR一起不要超過計時器週期。
有了良好的設計,則第2個定時器中斷將不會發生,並暫時禁用時間做乘法不會阻止一個定時器中斷髮生。
或者簡化代碼
aDfilter * 8
需要一個@MUL3232
呼叫意味着弱優化或不必要地使用簽署數學。通過使用無符號數學使編譯器更容易編碼。
// some_signed_32_bit_type aDfilter
uint32_t aDfilter;
// and if that is not enough change code
// aDfilter = aDfilter * 8 + aD * 2;
aDfilter = (aDfilter << 3) + aD * 2;
潛在的性能提升。根據整體設計,delay_us(40);
應該能夠被消除。如果只使用1個通道,則可以採用以下方式 - 取決於各種要求。
#int_RTCC
void RTCC_isr(void) {
// delay_us(40); // not needed is timer period >> 40us
unsigned int16 aD = read_adc();
set_adc_channel(0); // select channel now (also at initialization)
aDfilter = aDfilter * 8 + aD * 2;
}
潛在的bug。如果read_adc()
處於設置最高有效位的模式(例如,10位轉換向左移位6)並且編譯器具有16位整數/無符號,則aD*2
溢出。在那種情況下使用:
uint32_t aDfilter;
...
aDfilter = aDfilter*8 + (uint32_t)read_adc()*2;
什麼是警告?可能你需要做如下計算:'aDfilter =(float)aDfilter * 0.8f +(float)aD * 0.2f;'順便說一句,你想通過禁止中斷來防止重入?沒有意義或者你需要不同的單詞,如*防止遞歸*? – tilz0R
Sory,正確的是:aDfilter = aDfilter * 8 + aD * 2 不需要浮動。 問題是我正在使用乘法內外中斷。有沒有辦法做到這一點? –
基本上所有的問題都源於此:PIC不是PC。 – Lundin