问题描述
我正在编写针对x86_64的Lisp编译器。到目前为止,大多数类型的功能都可以使用,但是我现在遇到了障碍。典型的Lisp阶乘函数给了我一个分割错误。查看代码似乎完全可以,但事实并非如此!使用GDB跟踪我的代码后,即使rax为1,递归过程似乎也继续进行。我追踪到-4。有人知道为什么会这样吗?
这是我的编译方式:
clang -O0 -mstackrealign -masm=intel test.asm
(在MacOS上使用GAS。)
(define (factorial x)
(if (= x 1) 1
(* x (factorial (- x 1)))))
(define result (factorial 5))
.global _main
.text
_main:
push 5 # push argument to factorial
call factorial
add rsp,8 # discard 1 local argument
mov [x + rip],rax
mov rdi,0
mov rax,0x2000001
syscall
factorial:
push rbp
mov rbp,rsp
push 1 # push argument to =
push [rbp + 16] # push argument to =
call equal
add rsp,16 # discard 2 local arguments
cmp rax,1 # is true?
je true_1 # true branch
jmp false_2 # false branch
true_1:
mov rax,1
jmp end_3
false_2:
push 1 # push argument to -
push [rbp + 16] # push argument to -
call minus
add rsp,16 # discard 2 local arguments
push rax # result of -
call factorial
add rsp,8 # discard 1 local argument
push rax # result of factorial
push [rbp + 16] # push argument to *
call multiply
add rsp,16 # discard 2 local arguments
jmp end_3
end_3:
mov rsp,rbp
pop rbp
ret
.data
x:
.quad 0
.macro operator mnemonic
push rbp
mov rbp,rsp
mov rax,[rbp + 24]
\mnemonic rax,[rbp + 16]
mov rsp,rbp
pop rbp
ret
.endm
minus: operator sub
multiply: operator imul
equal:
push rbp
mov rbp,rsp
mov rsi,[rbp + 16]
cmp rsi,[rbp + 24]
je equal_true
mov rax,0
jmp equal_end
equal_true:
mov rax,1
jmp equal_end
equal_end:
mov rsp,rbp
pop rbp
ret
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)