装配中的等式的错误答案

时间:2016-06-24 23:41:57

标签: assembly floating-point equation pi

我正在尝试用汇率点在汇编中实现一个等式,它给了我错误的答案。

我把它放在一个caculater中它给了我433.0127018 ...并且我的代码我得到了0.0193269641235答案甚至没有接近正确但我无法找出它为什么给错了aswer。

式:

initX=sin((degree+ (i∗dStep)) ∗pi/180) ∗ scale

变量:

degree      dd  0
dStep       dq  120.0   
scale       dq  500.0
pi          dq  3.14159265358979    
oneEighty   dq  180.0
initX       dq  0.0
tmp         dq  0.0
tmptmpdegree    dq  0.0

代码:

;  initX=sin((degree+(i*dstep))*pi/180)*scale

movsxd  r10,dword[degree]
cvtsi2sd    xmm0,r10
movsd   qword[tmpdegree],xmm0
movsd   xmm1,qword[pi]
divss   xmm1,dword[oneEighty]
movsd   qword[tmp],xmm1

movsd   xmm0,qword[tmpdegree]
addsd   xmm0,qword[dStep]
mulsd   xmm0,qword[tmp]
call    sin
mulsd   xmm0,qword[scale]
movsd   qword[initX],xmm0

1 个答案:

答案 0 :(得分:2)

divss is single-precision,你在双精度数据上使用它。您甚至写了dword [oneEighty],即使您在该标签上放置了dq浮点数。

因此,您将double的尾数的低32位视为float

就像Jester所说,调试器会告诉你xmm1中的值没有改变到你在该指令之后所期望的值。

有关详情,请参阅代码维基。

更好的方法是在汇编时将两个常数组合在一起,只存储pi/180.0,这样你根本不需要分割。请记住,是编译器。如果您希望您的代码不会吮吸,您必须找到自己简化代码的方法。

此外,这是毫无意义的:

movsd   qword[tmp], xmm1
...
mulsd   xmm0, qword[tmp]

这些说明之间没有任何内容会破坏xmm1,所以你应该将值保留在xmm1中。

tmpdegree相同。当你准备好时,你应该cvtsi2sd xmm0, [degree]

您还应该将degree作为arg放在注册表中,而不是全局。而且你的常量与变量混合在一起。将常量放在.rodata部分。