我期待在上升沿信號輸入後發出非常短的脈衝。使用nop彙編精確延遲Arduino?
這裏最難的部分是我想控制(以高分辨率)在我的脈搏之前的延遲時間,以及我的脈搏持續時間。我可以很容易地控制這一點,只需將自己編碼爲一個硬編碼延遲,但我不確定如何以某種任意延遲執行此操作,並且具有相同的準確性。
經過很多頭痛追逐定時器,然後最終意識到我最終受到中斷例程進入/退出時間的限制,現在我正在試圖通過nops來控制我的延遲。
我曾以爲這個C開關語句是我想要的東西(編譯,希望它會成爲有效的,只是改變程序計數器到正確的位置之後),但它產生了一些非常奇怪的行爲...
switch(delayTime){ case 10: __asm__ __volatile__("nop"); case 9: __asm__ __volatile__("nop"); case 8: __asm__ __volatile__("nop"); case 7: __asm__ __volatile__("nop"); case 6: __asm__ __volatile__("nop"); case 5: __asm__ __volatile__("nop"); case 4: __asm__ __volatile__("nop"); case 3: __asm__ __volatile__("nop"); case 2: __asm__ __volatile__("nop"); case 1: __asm__ __volatile__("nop"); } PORTD = 0x10; ...
理想情況下,我想主要是通過一些代碼,將彙編成這樣運行:(這是C語言和彙編的一些奇怪的僞代碼,仍然不知道如何組裝做它的某些)
0x005 Reg1 = 0xFF-val1 %(where somehow 0xFF is known?/found out?) 0x006 Reg2 =0x1FF-val2 0x007 IJMP Reg1 0x008 NOP 0x009 NOP 0x00A NOP ... 0x0FF MOV 0x40, PORTD % assign the value 0x40 to the static variable "PORTD" 0x100 IJMP Reg2 0x101 NOP 0x102 NOP 0x103 NOP 0x104 NOP ... 0x1FF MOV 0x00, PORTD % assign the value 0x00 to the static variable "PORTD"
我只是總體不確定如何在運行時/運行期間找到代碼的內存位置,這樣該程序的「0xFF」和「0x1FF」方面並不是那麼糟糕(它看起來像是超級危險的只是,獲得代碼的彙編,然後硬編碼...我寧願不這樣做)。另外,雖然很容易只用200多個nops來洪泛,但如何讓IJMP cmd按照我想要的方式行事? (我真的不知道,如果這是我想要的命令)..
我想一般我正在尋找一些彙編命令(我似乎無法找到),讓我「添加N到程序計數器「,我可以確保該命令在彙編中運行,至少有N + 1個彙編命令在其之前,硬編碼。
作爲一個附註,所有這些都在一箇中斷程序,所以我不覺得玩電腦很糟糕...另外,我知道是有點不好的阻止多達500個操作,但對於手頭的任務來說,時間比它有多重要更重要作爲一個例程塊。
AVR Libc中的延遲例程有什麼問題? – 2014-10-08 04:57:24
爲了獲得我想要的精度,我想我需要使用類似「__builtin_avr_delay_cycles」的東西。然而,這個函數需要一個常量(它是一個似乎在編譯時構建的宏),而我正在尋找一些函數我可以在運行時調用一個變量。據我所知,只要將PC移到內存中以獲得確切的nops數是最可靠的解決方案,但是它可能會遺漏AVR libc中的某些內容。 (我只能看到每次迭代需要3,4個週期的方法),這對於我想要的16 MHz時鐘而言是不夠的時間分辨率。 – BlueCoconut 2014-10-08 05:16:25