40 lines
1.7 KiB
ArmAsm
40 lines
1.7 KiB
ArmAsm
.section .text
|
|
.global fib_iter
|
|
|
|
fib_iter:
|
|
push %rbp # Save old base pointer to stack.
|
|
# This also makes sure that rsp is
|
|
# 16-byte aligned.
|
|
movq %rsp, %rbp # Write new base pointer
|
|
cmpq $1, %rdi # Compare the argument to 1
|
|
je one # If n = 1 go to 'one' label.
|
|
cmpq $0, %rdi
|
|
je zero # If n = 0, go to 'zero' label.
|
|
|
|
|
|
movq $1, %rcx # Set minus_one (rcx) to 1
|
|
movq $0, %rdx # Set minus_two (rdx) to 0
|
|
movq %rcx, %rax # Set r (rax) to minus_one (rcx)
|
|
|
|
loop: addq %rdx, %rax # r (rax) = minus_one (rcx)
|
|
# + minus_two (rdx)
|
|
# rax is already set to minus_one
|
|
# due to the last line in the loop
|
|
# The first time the loop is run,
|
|
# this is handled before the loop.
|
|
movq %rcx, %rdx # minus_two (rdx) = minus_one (rcx)
|
|
movq %rax, %rcx # minus_one (rcx) = r (rax)
|
|
decq %rdi # Decrement the counter by 1.
|
|
cmpq $1, %rdi # Loop if the counter is over 1:
|
|
jle end # If counter is 1:
|
|
# End and return r (rax)
|
|
jmp loop # If counter is 0: loop.
|
|
|
|
zero: movq $0, %rax # Return 0.
|
|
jmp end
|
|
one: movq $1, %rax # Return 1.
|
|
end: leave # Return the state of the base and
|
|
# stack pointers to their
|
|
# original state.
|
|
ret # Return r (rax)
|