看看GNU编译器都生成了什么样的汇编代码

平时工作中有接触到汇编,一时兴起,就想看看GNU的编译器生成的汇编代码是什么样的。

1. 生成汇编代码

我写了一个非常简单的C语言代码,如下

然后,执行“gcc -S simple_program.s simple_program.c”生成汇编代码(simple_program.s)。

如下是注释了的汇编代码,编译器生成的汇编代码是没有注释的。

2. 汇编的知识,再说几点

在汇编代码中,我增加了不少注释。有些问题,我觉得光靠注释是说不清楚的,这里简明交待两点。

2.1 汇编程序中的segment问题

在汇编程序中,不同的数据是放在不同的段中的。

代码是放在代码段中的,就是.text段中。

数据是放在数据段中的,数据段有.data段和.bss段之分。赋了初值的全局变量放在.data段中,没有赋初值的全局变量放在.bss段中。

2.2汇编程序中的函数调用问题

汇编代码是由GNU编译器自动生成的。虽然是自动的,肯定有一个约定成俗的规范在起作用,要么岂不乱套了。

函数调用的规范,或许你从汇编代码中已经看出了一点端倪。

先说一下函数参数。函数参数是通过栈空间来传递的。

在调用函数之前,先将函数参数入栈,进栈的顺序依次为,函数参数n,函数参数n-1, ........函数参数1。

在汇编程序执行call function_name后,汇编程序会自行将函数的返回地址,也就是call function_name的下一行的指令地址压入栈中。

在汇编函数中,为了保证返回地址不被意外的更改,将EBP压入栈中,专门用EBP保存ESP的值。

这样,在汇编函数中,函数参数1就保存在ESP+8的位置处,函数参数2保存在ESP+12的位置处,依次类推。ESP+0保存的是EBP的值,ESP+4保存的是函数的返回地址。

汇编函数的返回值入在寄存器EAX中。

局部变量也是通过栈来实现的。

文章写得简略。若有不明之处。还请见谅。

版权声明:本文为博主原创文章,未经博主允许不得转载。

时间: 2024-08-04 00:58:16

看看GNU编译器都生成了什么样的汇编代码的相关文章

Java编译器如何生成重载和覆盖方法代码

%E5%AE%9E%E9%AA%8C10%EF%BC%9AProblem%20C%3A%20STL%E2%80%94%E2%80%94%E5%91%B5%E5%91%B5%E5%9E%8B%E8%87%AA%E5%8A%A8%E6%9C%BA ?f??[OLkkJBbM?????????? http://auto.315che.com/woerwoc30/qa23674212.htm?i7 http://auto.315che.com/jinbeit50/qa23968953.htm?o0 ht

LLVM和GCC的区别(LLVM提供了模块化的编译模块,非常有利于重用,以前的编译器都没有做到这一点)

最近在Mac OS X Mountain Lion下用Xcode进行开发,发现在编译选项里有如下所示的这两种编译器:一个是Apple LLVM compiler 4.2,另外一个是LLVM GCC 4.2. 近几年一直听人说LLVM比GCC好,但是我一直没有时间研究这二者的差别.由此问题出发,我又给自己抛出了很多疑问: cc, c89, c99是什么?有何区别? gcc, g++, cpp, gpp又是什么? LLVM与GCC区别大吗? Apple LLVM compiler 4.2和LLVM

条款6:如果不想使用编译器自动生成的函数,就应该明确的拒绝。

有些情况自己是不希望生成拷贝构造函数以及拷贝赋值运算符的,这种时候不能只是自己不去编写这些函数,因为这样编译器会自动的去生成这些函数.保险一点的做法是将拷贝构造函数以及拷贝赋值运算符都声明为private的.这样既阻止了编译器生成默认的版本,而且又阻止了别人去调用它. 注意上面的这条“将成员函数声明为private而故意的不去实现它”是一种常用手段,即使是标准程序库中有的部分也是这样做的. class HomeForSale//很明显,销售的两个方子一般内容都是不相同的,所以拷贝构造函数以及 {

Effective C++ 之 Item 6 : 若不想使用编译器自动生成的函数,就该明确拒绝

Effective C++ chapter 2. 构造 / 析构 / 赋值运算 (Constructors, Destructors, and Assignment Operators) Item 6. 若不想使用编译器自动生成的函数,就该明确拒绝 (Explicitly disallow the use of compiler-generated functions you do not want) 地产中介商卖的是房子,一个中介软件系统自然而然想必有个 class 用来描述待售房屋: cla

C++构造函数和编译器自动生成代码的陷阱

最近在项目中debug各种access violation的,其中这个问题比较有代表性,并且能够被规范的代码标准解决. 问题可以总结为以下的代码: 1 class TestString 2 { 3 public: 4 TestString(const char* input) : m_value(input) {} 5 TestString(const TestString& input) : m_value(input.m_value) {} 6 operator const char*()

【Effective c++】条款6:若不想使用编译器自动生成的函数就应该明确拒绝

地产中介卖的是房子,其使用的中介软件系统应该有个类用来描述卖掉的房子 class HomeFoeSale { ......} 但是任何房子都是独一无二的,不应该存在两个房子拥有同样的属性,因此以下操作不应该正确! HomeForSale h; HomeForSale h1(h); //调用复制构造函数 HomeForSale h2 = h; //调用赋值操作符 阻止这两个操作(复制.赋值)可以不声明它们,but自己不声明,编译器会自动生成,并且访问权限还是public.没办法只好声明出来,但是如

Effetive C++_笔记_条款06_若不想使用编译器自动生成的函数,就该明确拒绝

(整理自Effctive C++,转载请注明.整理者:华科小涛@http://www.cnblogs.com/hust-ghtao/) 通常如果你不希望class支持某一特定机能,只要不声明对应函数就是了.但这个策略对copy构造函数和copy assignment操作符却不起作用,你如果不声明它们,而某些人尝试调用它,编译器会为你声明它们. 这把你逼到了一个困境.如果你不声明copy构造函数和copy assignment操作符,编译器可能为你产出一份,于是你的clas支持copying.如果

C++进阶--不让编译器自动生成类函数

//############################################################################ /* * 不让编译器自动生成类函数 * * * * 并不是所有的类都需要编译器自动生成类函数 * * 例: 一个"OpenFile" 类表示一个被打开的文件.构造函数至少需要一个文件名作为参数 * 所有不需要默认构造函数 */ 那么如何让编译不自动生成函数 /* * 对于C++ 11: */ class dog { public:

Effective C++ Item 6 若不想使用编译器自动生成的函数,就该明确拒绝

本文为senlie原创,转载请保留此地址:http://blog.csdn.net/zhengsenlie 为驳回编译器自动提供的机能,可将相应的成员函数声明为private并且不予实现.使用像Uncopyable这样的base class也是一种方法 classUncopyable{ protected: //允许derived对象构造和析构 Uncopyable(){} ~Uncopyable(){} private: Uncopyable(constUncopyable&); //但阻止c