If I was given Assembly code like the below, how could I determine how many clock cycles it will take to execute?
ldi r20, 250
loop: inc r20
brne loop
nop
In the datasheet, all the instructions take up 16 bits (1 instruction word).
Attempting it myself, I get 14 as the answer. Since ldi r20, 250
is called once (1 cycle), then the loop is called 6 times before overflow to zero occurs (6x2=12 cycles). And finally at the end, nop
takes 1 cycle. In total that is 14 cycles.
However, the answer is apparently 19 cycles. Would anyone be able to tell me what I have done wrong?
You've skipped including the inc
at each loop. So each loop will be brne (2) + inc (1)
. Therefore your calculation should be (r20
value in brackets):
1
1 (251)
2
1 (252)
2
1 (253)
2
1 (254)
2
1 (255)
2
1 (0)
1
1
The brne
is 1 cycle when the branch is not taken.
Its a bit more visible if you unroll that loop:
; (4 cycles)
ldi r20, 250 ; 1
inc r20 ; 1
nop ; these two represent the brne at 2 cycles because it branches
nop
; (3 cycles)
inc r20 ; 1
nop ; these two represent the brne at 2 cycles because it branches
nop
; (3 cycles)
inc r20 ; 1
nop ; these two represent the brne at 2 cycles because it branches
nop
; (3 cycles)
inc r20 ; 1
nop ; these two represent the brne at 2 cycles because it branches
nop
; (3 cycles)
inc r20 ; 1
nop ; these two represent the brne at 2 cycles because it branches
nop
; (2 cycles)
inc r20 ; 1
nop ; this represents the brne at 1 cycle, because its just overflowed and therefore ** will not branch **
; (1 cycle)
nop