如何在VS c ++中使用IA32指令'fabs'?

时间:2013-11-17 22:55:04

标签: c++ visual-studio-2012 assembly x86 x87

这是我第一次尝试使用汇编,我只是尝试使用英特尔架构指令FABS。 (参见第399页的this document)。

这应该是清除符号位。

关于汇编我知道的一点点涉及来源和目的地,但我没有看到任何关于该指令的符号的参考。

以下是我尝试使用它的一种方法(使用Visual Studio 2012,C ++):

double myabs(double x){
  __asm(fabs(x));
return x;
}

此特定尝试在“操作码”中给出错误C2400:内联汇编语法错误;找到'('


请注意,我想使用汇编指令,对其他可用的“更好”选项不感兴趣。

2 个答案:

答案 0 :(得分:2)

几个指示:首先 - 您正在使用gcc样式内联汇编,您可以使用MS样式 -

__asm{ ... }

第二 - 说明不是函数,所以括号也有错误。

最后但最重要的是 - fabs没有参数,它只是在FP堆栈的顶部工作。您需要首先明确加载您的变量。试试这个:

__asm {
    fld x
    fabs
    fstp x
}

无论如何,使用旧的x87指令可能不是一件好事,它可能效率很低 - 您应该考虑切换到SSE解决方案,请参阅 - How to absolute 2 double or 4 floats using SSE instruction set? (Up to SSE4)

答案 1 :(得分:1)

使用VC ++时,不要将汇编语言括在括号中。正确的语法更像是:

__asm fabs

或:

__asm { 
    fabs
    // possibly more instructions here
}

在您的具体情况下,您可能需要以下内容:

__asm { 
    fload x // load x onto F.P. stack
    fabs    // take absolute value
    fstp x  // store back to x and pop from F.P. stack.
}

就源和目的地而言,x86上的浮点使用堆栈。除非您另行指定,否则大多数指令(加载/存储除外)从堆栈顶部获取操作数,并将结果存放在堆栈顶部。例如,如果没有给出操作数,fabs将取浮点堆栈顶部的操作数的绝对值,并将结果存回到同一位置。