专题 18 Inline Assembly(在C语言中嵌套使用汇编)
1.调用形式
标准形式:
asm("movl %ecx %eax");/* moves the contents of ecx to eax */
__asm__("movb %bh(%eax)"); /*moves the byte from bh to the memory pointed by eax*/
多行:
__asm__ ("movl %eax,%ebx\n\t"
"movl $56,%esi\n\t"
"movl %ecx,$label(%edx,%ebx,$4)\n\t"
"movb %ah,(%ebx)");
扩展形式:
asm ( assemblertemplate
: output operands /* optional */
: input operands /* optional */
: list ofclobbered registers /* optional */
);
2.实例
/*将a的值赋给b*/
inta=10, b;
asm("movl %1, %%eax;
movl%%eax, %0;"
:"=r"(b) /* output */
:"r"(a) /* input */
:"%eax" /* clobbered register */
);
3.说明:
AssemblerTemplate:
Theformat islike: eithereach instructionshould beenclosed withindouble quotes,or theentire groupof instructionsshould bewithin doublequotes. Eachinstruction shouldalso endwith adelimiter. Operandscorresponding tothe Cexpressions arerepresented by%0, %1... etc.
Ifweusemorethanoneoperand,theyareseparatedbycomma.Intheassemblertemplate,eachoperandisreferencedbynumbers.Numberingisdoneasfollows.Ifthereareatotalofnoperands(bothinputandoutputinclusive),thenthefirstoutputoperandisnumbered0,continuinginincreasingorder,andthelastinputoperandisnumberedn-1.Themaximumnumberofoperandsisaswesawintheprevioussection.
寄存器与符号表示之间的关系如下表
限制符 |
说明 |
a |
对应的变量必须在EAX中 |
b |
EBX |
c |
ECX |
d |
EDX |
S |
ESI |
D |
EDI |
q |
EAX,EBX,ECX,EDX中的任何一个 |
r |
EAX,EBX,ECX,EDX,ESI,EDI中的任何一个 |
A |
EAX:EDX组合成一个64位的操作数 |
m |
操作数必须是内存中的变量 |
o |
操作数是内存变量,并且对操作数的寻址方式为基址加一个偏移量 |
V |
操作数是内存变量,但是寻址方式为基址,没有偏移量 |
g |
操作数可以是内存变量,立即数,EAX,EBX,ECX或者EDX |
I |
操作数是0~31的立即数(用于32位的移位操作) |
J |
操作数是0~63的立即数(用于64位的移位操作) |
K |
操作数必须是0xFF |
L |
操作数必须是0xFFFF |
M |
操作数是0,1,2,或3 |
N |
操作数可以是0-255中的任何一个数(用于in/out指令) |
f |
操作数是浮点寄存器 |
t |
第一个浮点寄存器 |
u |
第二个浮点寄存器 |
= |
操作数是只写的(用于输出) |
+ |
操作数是可读写的(用于输入输出) |
& |
表示在汇编代码前前,对应的操作数会输入部分修改 |
memory |
用在损坏部分中,表示内在被修改了 |
4.更多实例
//计算一个数的5倍
asm("leal (%1,%1,4), %0"
: "=r"(five_times_x)
: "r" (x)
);
//这个版本中输入和输出使用同一个寄存器
asm ("leal (%0,%0,4),%0"
: "=r"(five_times_x)
: "0" (x)
);
5. 处理跳转
条件分支和无条件分支都允许指定一个数字加上方向标志作为标签,方向标志指出处理器应该指向哪个方向查找数字型标签。第一个遇到的标签会被采用。
例子:
#include <stdio.h>int main()
{int a = 10;int b = 20;int result;asm("cmp %1, %2\n\t""jge 0f\n\t""movl %1, %0\n\t""jmp 1f\n""0:\n\t""movl %2, %0\n""1:":"=r"(result):"r"(a), "r"(b));printf("The larger value is %d\n", result);return 0;
}
f后缀表示向前跳转,b后缀表示向后跳转。
转载于:https://my.oschina.net/fuyajun1983cn/blog/263914
专题 18 Inline Assembly(在C语言中嵌套使用汇编)相关推荐
- linux c语言编程内嵌汇编,gcc编译c语言中内嵌汇编
gcc编译c语言中内嵌汇编 --AT&T and Intel 汇编语法对照 寄存器命名: AT&T: %eax Intel: eax AT&T 语法源地址在左侧,目的地址在右 ...
- C语言中内嵌汇编asm语法
这篇文章写得炒鸡详细而且很全面,易于理解,建议新手查看 C语言中内嵌汇编asm语法 下面这两篇文章作为补充来看 C语言内嵌汇编:asm volatile C语言ASM汇编内嵌语法
- GCC在C语言中内嵌汇编 asm __volatile__
在内嵌汇编中,可以将C语言表达式指定为汇编指令的操作数,而且不用去管如何将C语言表达式的值读入哪个寄存器,以及如何将计算结果写回C 变量,你只要告诉程序中C语言表达式与汇编指令操作数之间的对应关系即可 ...
- c语言中 伪指令,ARM汇编伪指令介绍(1)
ARM汇编伪指令介绍 在ARM汇编语言程序里,有一些特殊的助记符,这些助记符与指令系统的助记符不同,没有相对应的操作码,这些特殊指令助记符被称为伪指令,他们所完成的操作称为伪操作.伪指令在源程序中的作 ...
- c 语言中嵌套循环,C 嵌套循环 | 菜鸟教程
C 嵌套循环 C 语言允许在一个循环内使用另一个循环,下面演示几个实例来说明这个概念. 语法 C 语言中 嵌套 for 循环 语句的语法: for (initialization; condition ...
- Linux C中内联汇编的语法格式及使用方法
在阅读Linux内核源码或对代码做性能优化时,经常会有在C语言中嵌入一段汇编代码的需求,这种嵌入汇编在CS术语上叫做inline assembly.本文的笔记试图说明Inline Assembly的基 ...
- ARM中C和汇编混合编程及示例
在嵌入式系统开发中,目前使用的主要编程语言是C和汇编,C++已经有相应的编译器,但是现在使用还是比较少的.在稍大规模的嵌入式软件中,例如含有OS,大部分的代码都是用C编写的,主要是因为C语言的结构比较 ...
- C语言中内联函数的作用 inline
C语言中内联函数的作用 inline C语言中内联函数到底有什么作用? 试想一下,每当我们在假设就在主函数中调用另外一个函数的时候,那么这个函数就要入栈或者出栈,比如说下面的一个例子: 点击(此处)折 ...
- c语言什么是内联函数,C语言中内联函数inline的使用方法
该楼层疑似违规已被系统折叠 隐藏此楼查看此楼 来源一:比特网 来源二:东方锐智 在C++中,为了解决一些频繁调用的小涵数大量消耗栈空间或者是叫栈内存的问题,特别的引入了inline修饰符,表示为内联涵 ...
最新文章
- Windows xp下配置Apache、PHP环境及Oracle10g客户端
- Delphi资源文件的应用(转)
- PAT甲级题目翻译+答案 AcWing(哈希表)
- linux shell 判断文件是否存在
- Metal之实现视频采集与实时渲染
- 在Latex中插入Python代码
- Flask 项目实战|从零开发“StackOverflow”问答网站
- dart系列之:dart语言中的函数
- [剑指offer]面试题第[65]题[JAVA][不用加减乘除做加法][位运算]
- 跟我一起学docker(15)--监控日志和日志管理
- 基于Python3-Pygame的坦克大战小游戏
- FZU 2128 最长子串
- Exadata使用EXAchk进行健康检查
- 基于蓝牙的单片机小车
- 计算机英语课堂活动总结,英语活动总结(精选8篇)
- 零基础搭建外卖优惠券返利CPS小程序教程
- 谷歌浏览器(Chrome)输入框总是有历史输入记录,解决办法
- linux12k8s --> 03二进制安装
- 2020年 Top 6+ 最佳免费字体网站
- accept()函数说明