英特尔x86_64的组装,如何落地双从XMM寄存器为int? [英] Intel x86_64 assembly, how to floor double from xmm register to int?
问题描述
我怎样才能做到这一点?这将是最好的,如果结果将是E * X寄存器。
How can I do that? It would be best if result will be in e*x register.
推荐答案
您已经问过,你可以通过看C编译器是如何做的接听几个琐碎的问题。从那里,你可以看一下它使用的指令,并决定要实际使用哪些。 (有大约在libm中数不胜数不同的舍入的功能,所以在第一时间挑选合适的人并不容易)。
You've asked several trivial questions which you could answer by just looking at how a C compiler does it. From there, you can look up the instructions it used, and decide which ones you want to actually use. (There are about a zillion different rounding functions in libm, so picking the right one in the first place isn't always easy).
使用 -O3 -ffast-数学
内联得到最简单的libm函数(因为它不具有潜在的设置错误号
上NAN或垃圾一样的)。
Using -O3 -ffast-math
gets most simple libm functions inlined (since it doesn't have to potentially set errno
on NaN, or crap like that).
反正编译的输入和输出,从<一href=\"http://gcc.godbolt.org/#compilers:!((compiler:clang380,options:'-xc+-std%3Dgnu11+-O3+-Wall+-Wextra+-fverbose-asm+-march%3Dhaswell+-mno-avx+-ffast-math',source:'%23include+%3Cmath.h%3E%0A%0Aint+floor_double(double+x)+%7B+return+(int)+floor(x)%3B+%7D%0A%0Aint+truncate_double(double+x)+%7B+return+(int)+(x)%3B+%7D')),filterAsm:(commentOnly:!t,directives:!t,intel:!t,labels:!t),version:3\"相对=nofollow>在Godbolt编译器资源管理器GCC 5.3:
Anyway, compiler input and output, from gcc 5.3 on the Godbolt Compiler Explorer:
#include <math.h>
int floor_double(double x) { return (int) floor(x); }
roundsd xmm0, xmm0, 9
cvttsd2si eax, xmm0
ret
int truncate_double(double x) { return (int)x; }
cvttsd2si eax, xmm0
ret
查看 86 标签维基英特尔指令集的参考手册PDF。还有一个非官方的HTML版本从PDF 产生的。
See the x86 tag wiki for links to Intel's instruction set reference manual pdf. There's also an unofficial HTML version generated from the PDF.
cvttsd2si
截断向零如 TRUNC()
,而不是朝着负无穷大的舍入像的 地板()
功能。
cvttsd2si
truncates towards zero, like trunc()
, instead of rounding towards -Infinity like the floor()
function.
这就是为什么地板()
编译为SSE4.1 roundsd
时的指令集是可用的。 (否则它与舍入模式摆弄,你可以通过删除或更改对godbolt的 -march
选项见)。
That's why floor()
compiles to SSE4.1 roundsd
when that instruction set is available. (Otherwise it has to fiddle with the rounding mode, as you can see by removing or changing the -march
option on godbolt).
有也挤满的转换指令的版本,如 CVTTPD2DQ` 做2立刻。 (或4 AVX)。
There are also packed versions of the conversion instructions, like CVTTPD2DQ` to do 2 at once. (Or 4 with AVX).
这篇关于英特尔x86_64的组装,如何落地双从XMM寄存器为int?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!