diff options
Diffstat (limited to 'PGU/CHAP4/power.s')
| -rw-r--r-- | PGU/CHAP4/power.s | 94 |
1 files changed, 94 insertions, 0 deletions
diff --git a/PGU/CHAP4/power.s b/PGU/CHAP4/power.s new file mode 100644 index 0000000..124586e --- /dev/null +++ b/PGU/CHAP4/power.s @@ -0,0 +1,94 @@ +# Power Program +# +# Computes the value of a number raised to a power +# using functions. +# + +# Everything in the main program is stored in registers +# no need for data section +.section .data + +.section .text + +.globl _start + +_start: + + pushq $3 # Second argument (power) + pushq $2 # First argument (base) + call power # Call the function power + + # Cleanup stack removing the arguments from it + addq $16, %rsp + + # Save the answer in the stack before calling power again + push %rax + + pushq $2 # Second argument (Power) + pushq $5 # First argument (Base) + call power + + addq $16, %rsp # Cleanup stack + + # Second answer is already in %rax, get the first + # back from stack to %rdi + popq %rdi + + # Just add them + addq %rax, %rdi + + #Sum is already in %rdi, just call exit() with %rdi as argument + movq $60, %rax + syscall + + + +################## +# Power Function # +################## + +# - First Arg - Base power +# - Second Arg - The power to raise it to +# +# NOTE: So far, power must be 1 or greater +# +# Variables +# +# - %rbx - holds the base number +# - %rcx - holds the power (also acts as a counter) +# - -8(%rbp) holds the current result + +.type power, @function + +power: + pushq %rbp # Save old Base Pointer + movq %rsp, %rbp # make stack pointer the base pointer + subq $8, %rsp # Add space in stack for local storage + + movq 16(%rbp), %r8 # Retrieve Base number from stack to %rbx + movq 24(%rbp), %r9 # Retrieve second argument from stack to %rcx + + movq %r8, -8(%rbp) # Store current result (the operand by itself) + +power_loop_start: + cmpq $1, %r9 # If power is 1, we are done + je end_power + + movq -8(%rbp), %rax # Move current into %rax + imulq %r8, %rax # Multiply current result by base number + + movq %rax, -8(%rbp) # Save current result + + decq %r9 # Decrease the power (using as a counter) + jmp power_loop_start + +end_power: + movq -8(%rbp), %rax # Retrieve end result into %rax + # Return value goes into %rax + movq %rbp, %rsp # Restore stack pointer + popq %rbp # Restore base pointer + ret + + + + |
