xmm指令在哪里" divsd"存储剩余部分

时间:2018-01-19 01:16:05

标签: assembly x86 sse

声明中:

divsd xmm0,xmm1

剩下的存储在哪里? xmm寄存器是否有余数寄存器,如整数寄存器?我应该在x87指令中使用FPREM吗?

据我所知,英特尔手册在这个问题上没有提及,很多研究都没有提供有用的答案。

1 个答案:

答案 0 :(得分:1)

DIVSD处理单个浮点,因此不会返回余数。相反,它会为该类型的浮点数计算尽可能多的小数。

来自英特尔文档:

# DIVSD (128-bit Legacy SSE version)
DEST[63:0] ← DEST[63:0] / SRC[63:0]
DEST[MAX_VL-1:64] (Unmodified)

请注意,这与FDIV指令相同。

当然,您可以使用通常的方法计算余数,方法是将结果转换为整数,再乘以,然后从原始数字中减去。

像这样的东西(UNTESTED!AT& T语法)

; inputs: xmm1 divisor, xmm2 dividend
MOVQ xmm3, xmm2         ; xmm3 ← xmm2
DIVPS xmm2, xmm1        ; xmm2 ← xmm2 ÷ xmm1
CVTPS2DQ xmm3, xmm2     ; xmm3 ← integers of xmm2
MULPS xmm3, xmm1        ; xmm3 ← xmm3 × xmm1
MOVQ xmm4, xmm2         ; xmm4 ← xmm2
SUBPS xmm4, xmm3        ; xmm3 ← xmm3 - xmm2
; xmm2 = xmm2 ÷ xmm1
; xmm4 = remainder (mathematically: frac(xmm2) × xmm1)

使用FPREM时可能遇到的问题是您无法使用浮点单元和MMX寄存器混合代码。他们最终都使用相同的寄存器,但不同。

有一些关于该问题的文档。如果你不使用MMX寄存器,你可以没事。

  

来源:Vol。 1 11-31 - 使用流式SIMD扩展2进行编程(SSE2)

     

11.6.7 SSE / SSE2指令与x87 FPU和MMX指令的交互

     

XMM寄存器和x87 FPU和MMX寄存器代表单独的执行环境,在同一代码模块中执行SSE,SSE2,MMX和x87 FPU指令时或在混合包含这些指令的代码模块时具有某些分支: / p>      

•那些只在XMM寄存器上运行的SSE和SSE2指令(例如压缩和标量浮点指令和128位SIMD整数指令)在同一条指令流中使用64位整数或x87 FPU指令而没有任何指令限制。例如,应用程序可以执行

     

XMM寄存器中的大部分浮点计算,使用压缩和标量浮点指令,同时使用x87 FPU执行三角函数和其他超越计算。同样,应用程序可以无限制地一起执行打包的64位和128位SIMD整数操作。

     

•在MMX寄存器上运行的那些SSE和SSE2指令(例如CVTPS2PI,CVTTPS2PI,CVTPI2PS,CVTPD2PI,CVTTPD2PI,CVTPI2PD,MOVDQ2Q,MOVQ2DQ,PADDQ和PSUBQ指令)也可以在与指令流相同的指令流中执行。但是,这里的64位SIMD整数或x87 FPU指令受限于同时使用MMX技术和x87 FPU指令,其中包括:

     

- 从x87 FPU到MMX技术指令或在MMX寄存器上运行的SSE或SSE2指令的转换之前应先保存x87 FPU的状态。

     

- 从MMX技术指令或从MMX寄存器操作的SSE或SSE2指令到x87 FPU指令的转换之前,应先执行EMMS指令。

由于您有很多XMM / YMM / ZMM寄存器,因此在SSE / AVX中执行此类操作通常是值得的。另一方面,FPU使用的堆栈在装配时更难处理。