将64位整数加载到双精度SSE2寄存器的最佳方法是什么?

Eri*_*nge 14 double assembly sse int64 sse2

xmm在32位模式下,在SSE2寄存器中加载64位整数值的最佳/最快方法是什么?

在64位模式下,cvtsi2sd可以使用,但在32位模式下,它仅支持32位整数.

到目前为止,我还没有发现更多:

  • 使用fild,fstp以堆叠然后movsdxmm寄存器
  • 加载高32位部分,乘以2 ^ 32,加上低32位

第一个解决方案很慢,第二个解决方案可能会引入精度损失(编辑:无论如何它都很慢,因为低32位必须转换为无符号...)

有更好的方法吗?

Ste*_*non 9

你的第二个选择可以起作用,虽然它有点笨拙.我假设您的64位数字最初是在edx:eax中.

cvtsi2sd xmm0, edx              // high part * 2**-32
mulsd    xmm0, [2**32 from mem] // high part
movsd    xmm2, [2**52 from mem]
movd     xmm1, eax
orpd     xmm1, xmm2             // (double)(2*52 + low part as unsigned)
subsd    xmm1, xmm2             // (double)(low part as unsigned)
addsd    xmm0, xmm1             // (double)(high part + low part as unsigned)
Run Code Online (Sandbox Code Playgroud)

除了可能的最后一个操作之外的所有操作都是精确的,因此这是正确舍入的.应该注意的是,-0.0当输入是0并且mxcsr被设置为舍入到无穷大时,该转换产生.如果它在运行时库中用于旨在提供IEEE-754一致性的编译器,则需要解决这个问题,但对于大多数用法来说不是问题.