我想写一个小的低级程序.对于它的某些部分,我将需要使用汇编语言,但其余代码将使用C/C++编写.
那么,如果我使用GCC将C/C++与汇编代码混合在一起,我是否需要使用AT&T语法,还是可以使用Intel语法?或者你如何以其他方式混合使用C/C++和asm(intel语法)?
我意识到也许我没有选择,必须使用AT&T语法,但我想确定..
如果结果没有选择,我可以在哪里找到有关AT&T语法的完整/官方文档?
谢谢!
我想检查boost::variant在我的代码中应用的程序集输出,以便查看哪些中间调用被优化掉了.
当我编译以下示例(使用GCC 5.3 g++ -O3 -std=c++14 -S)时,似乎编译器优化了所有内容并直接返回100:
(...)
main:
.LFB9320:
.cfi_startproc
movl $100, %eax
ret
.cfi_endproc
(...)
Run Code Online (Sandbox Code Playgroud)
#include <boost/variant.hpp>
struct Foo
{
int get() { return 100; }
};
struct Bar
{
int get() { return 999; }
};
using Variant = boost::variant<Foo, Bar>;
int run(Variant v)
{
return boost::apply_visitor([](auto& x){return x.get();}, v);
}
int main()
{
Foo f;
return run(f);
}
Run Code Online (Sandbox Code Playgroud)
但是,完整的程序集输出包含的内容远远超过上面的摘录,对我而言,它看起来永远不会被调用.有没有办法告诉GCC/clang删除所有"噪音"并输出程序运行时实际调用的内容?
完整装配输出:
.file "main1.cpp"
.section .rodata.str1.8,"aMS",@progbits,1
.align 8
.LC0:
.string "/opt/boost/include/boost/variant/detail/forced_return.hpp"
.section .rodata.str1.1,"aMS",@progbits,1
.LC1: …Run Code Online (Sandbox Code Playgroud) 16(%esp)真的违反直觉[esp+16]吗?是不是更合乎逻辑:
eax = 5
mov eax, 5
Run Code Online (Sandbox Code Playgroud)
at at&t是:
mov 5, eax
5 = a (? wait what ?)
Run Code Online (Sandbox Code Playgroud)
注意:我不是想乱跑.我只是不明白他们所做的设计选择,我试图了解他们为什么做了他们所做的.
为什么这段代码没有设置temp为1?我该怎么做呢?
int temp;
__asm__(
".intel_syntax;"
"mov %0, eax;"
"mov eax, %1;"
".att_syntax;"
: : "r"(1), "r"(temp) : "eax");
printf("%d\n", temp);
Run Code Online (Sandbox Code Playgroud) 在x86或amd64上使用汇编指令时,程序员可以使用"Intel"(即nasm编译器)或"AT&T"(即gas编译器)汇编语法."Intel"语法在Windows上更受欢迎,但"AT&T"在UNIX(类似)系统上更受欢迎.
但是英特尔和AMD手册,以及芯片创建者创建的手册都使用"英特尔"语法.
我想知道,"AT&T"语法设计背后的原始想法是什么?浮动处理器创建者使用的符号有什么好处?