使用汇编语言在 Arduino Uno 中创建延迟而不使用计时器 [英] Create Delay in Arduino Uno using Assembly language without using timer
问题描述
我刚刚开始学习微控制器,我无法理解如何在不使用计时器的情况下在代码中引入延迟.我的主板有一个 16MHZ 的时钟.假设我想在检查按钮是否被按下之前引入 5ms 延迟.我如何确定需要执行多少条指令才能获得 5 毫秒的延迟,以及我将如何对其进行编程?有没有标准化的方法来做到这一点?这看起来是一件很标准的事情,但我无法理解它是如何完成的.
I just started learning about micro controllers and I was not able to understand how we could introduce delays in the code without using timers. My board has a clock of 16MHZ. Let's say I want to introduce 5ms delay before I check if a button is pressed. How would I identify how many instructions I need to execute to get 5 ms delay and how would I program it? Is there a standardized way of doing this? It looks like a very standard thing but I am not able to understand how it is done.
我正在 Atmega 328 Arduino uno 上使用汇编语言进行编程.
I am programming using Assembly language on Atmega 328 Arduino uno.
推荐答案
一般先算出需要烧掉多少个时钟周期,然后再写一个循环.查阅您的数据表以确定您的循环需要多少个循环并计算您需要多少次迭代.
Generally you figure out how many clock cycles you need to burn, then write a loop. Consult your datasheet to determine how many cycles your loop takes and calculate how many iterations you need.
ldi r16, x ; 1 cycle
loop: nop ; 1 cycle
dec r16 ; 1 cycle
brne loop1 ; 2 cycles when jumping, 1 otherwise
根据x
的值,这个循环需要x * 4
个周期.对于 16MHz 板,1ms 是 16000 个周期,所以 5ms 将是 80000 个周期.这超出了这个 8 位循环所能管理的范围,因此我们需要制作一个 16 位计数器.
Depending on the value of x
, this loop will take x * 4
cycles. With a 16MHz board 1ms is 16000 cycles, so 5ms would be 80000 cycles. That's more than this 8 bit loop can manage so we need to make a 16 bit counter.
ldi r16, x ; 1 cycle
ldi r17, y ; 1 cycle
loop: nop ; 1 cycle
dec r16 ; 1 cycle
brne skip ; 2 cycles when jumping, 1 otherwise
dec r17 ; 1 cycle
skip: brne loop ; 2 cycles when jumping, 1 otherwise
好的,我们的循环体现在每次迭代需要 6 个周期.请注意,无论 r16
是否包装,它都是 6 个周期.设置需要 2 个周期,但最终的 x=low(13333)=21
和 y=high(13333)=52
并添加一个 nop
.
Okay so our loop body now takes 6 cycles per iteration. Notice that it's 6 cycles no matter if r16
is wrapping or not. The setup takes 2 cycles but the final brne
gives us 1 cycle back so we got 1 cycle overhead. That means we need 79999 cycles which is 13333 iterations and one more cycle to waste. Thus x=low(13333)=21
and y=high(13333)=52
and add a nop
.
这是大体的想法,我希望我没有算错任何东西.如果您打算为此创建一个函数,请考虑调用和返回的开销.此外,您还可以对其进行参数化.
That's the general idea, I hope I have not miscalculated anything. If you intend to make a function of this, factor in the overhead of the call and return. Also, you can make it parametrized.
这篇关于使用汇编语言在 Arduino Uno 中创建延迟而不使用计时器的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!