我目前正在研究计算5阶乘的简单SPARC汇编代码。我想知道为什么我使用的全局寄存器通过函数调用不一致。Sparc程序集 - 整个函数调用中的全局寄存器不一致
随着使用的局部寄存器和输入/输出参数traditionnal版本(进入%O0),我没有问题,代码工作正常,
,但是当我想用另一个版本与全球寄存器,我有这个一致性问题。
下面的代码:
.data
.LLC0: .asciz "fact(5) = %d\n"
.text
.global main
main:
save %sp, -96, %sp
set 5, %g1 ! value 5 into %g1 register
sethi %hi(.LLC0), %g2
or %g2, %lo(.LLC0), %o0
mov %g1, %o1
call printf
nop
mov %g1, %o0 ! set %g1 into parameter for fact function
call fact
nop
mov %o0, %g4
sethi %hi(.LLC0), %g3
or %g3, %lo(.LLC0), %o0
mov %g4, %o1
call printf
nop
ret
fact:
addcc %g1, -1, %g1 ! current index of the procedure -
! supposed to be decremented at each call -
be term ! PROBLEM : %g1 always set to 0 before decrement
nop
sethi %hi(.LLC0), %g2
or %g2, %lo(.LLC0), %o0
mov %g1, %o1
call printf ! printf the value of %g1 :
! still equal to -1 at execution
nop
call fact
nop
mov %o0, %g2
umul %g2, %g1, %g2
mov %g2, %i0
ret
term: set 1, %o0
ret
我的问题是,为fact
功能,全局寄存器%g1
设置为0
在每次呼叫,使%g1
打印在执行总是-1
给人。
从这个link,我认为全球寄存器呈持续整个函数调用,即它们的范围是全球性的,并通过在代码中的任何功能的共享。
例如,在这里,我把set 5, %g1
放在主要部分,通常我应该得到4
作为fact
函数的打印值。
如果任何人都可以看到什么是错的?
感谢
UPDATE:
调用printf使用%O0和01%,而不是%G1。我仍然有全局寄存器的范围(%G5-G7)的问题。下面是使用它们的例子是这样的:
.data
.LLC0: .asciz "fact(5) = %d\n"
.text
.global main
main:
save %sp, -120, %sp
set 5, %g5
sethi %hi(.LLC0), %g2
or %g2, %lo(.LLC0), %o0
mov %g5, %o1
call printf
nop
mov %g5, %o0
call fact
nop
mov %o0, %g7
sethi %hi(.LLC0), %g3
or %g3, %lo(.LLC0), %o0
mov %g7, %o1
call printf
nop
ret
restore
fact:
addcc %g5, -1, %g5
be term
nop
sethi %hi(.LLC0), %g2
or %g2, %lo(.LLC0), %o0
mov %g5, %o1
call printf
nop
call fact
nop
mov %o0, %g6
smul %g6, %g5, %g6
mov %g6, %o0
ret
term: set 1, %o0
ret
在这段代码中,我打印的global %g5 register
值在每次递归调用,输出为:
fact(5) = 5
fact(5) = 838860799
fact(5) = 838860798
fact(5) = 838860797
fact(5) = 838860796
fact(5) = 838860795
fact(5) = 838860794
fact(5) = 838860793
fact(5) = 838860792
fact(5) = 838860791
fact(5) = 838860790
...
好像从事实的第一个电话主要使初始值为%g5
(初始化为5
)
我的错误在哪里?
感谢