C程序汇编运行模式简析
SJTUBEAR 原创作品转载请注明出处 /《Linux内核分析》MOOC课程http://mooc.study.163.com/course/USTC-1000029000
1. 汇编
在修习LINUX内核这门课的初始阶段,首先需要掌握的就是汇编以及汇编程序对于堆栈的操作。
下面我们就来分析一下一个简单地C程序是如何被汇编程序所表达的!
2. 得到汇编代码
首先,我们写一个简单地C程序,命名为exp1.c:
#include <stdio.h> int g(int x)
{
return x+;
} int f(x)
{
return g(x);
} int main()
{
return f()+;
}
程序非常的简单,我们此时再通过编译指令将其编译为汇编程序:
gcc –S –o main.s main.c -m32
这样我们就得到了这个简单C程序的汇编代码:
.file "exp1.c"
.text
.globl g
.type g, @function
g:
.LFB0:
.cfi_startproc
pushl %ebp
.cfi_def_cfa_offset
.cfi_offset , -
movl %esp, %ebp
.cfi_def_cfa_register
movl (%ebp), %eax
addl $, %eax
popl %ebp
.cfi_def_cfa ,
.cfi_restore
ret
.cfi_endproc
.LFE0:
.size g, .-g
.globl f
.type f, @function
f:
.LFB1:
.cfi_startproc
pushl %ebp
.cfi_def_cfa_offset
.cfi_offset , -
movl %esp, %ebp
.cfi_def_cfa_register
subl $, %esp
movl (%ebp), %eax
movl %eax, (%esp)
call g
leave
.cfi_restore
.cfi_def_cfa ,
ret
.cfi_endproc
.LFE1:
.size f, .-f
.globl main
.type main, @function
main:
.LFB2:
.cfi_startproc
pushl %ebp
.cfi_def_cfa_offset
.cfi_offset , -
movl %esp, %ebp
.cfi_def_cfa_register
subl $, %esp
movl $, (%esp)
call f
addl $, %eax
leave
.cfi_restore
.cfi_def_cfa ,
ret
.cfi_endproc
.LFE2:
.size main, .-main
.ident "GCC: (Ubuntu/Linaro 4.6.3-1ubuntu5) 4.6.3"
.section .note.GNU-stack,"",@progbits
3.汇编代码分析
汇编出的代码,多了很多辅助信息,为了能够更好地看清主干,我们删减一下:
g:
pushl %ebp //保存现场,将父函数的栈底寄存器存入当前程序栈中
movl %esp, %ebp //构建当前函数堆栈
movl (%ebp), %eax //从父函数堆栈中取得参数,存入ax寄存器
addl $, %eax //完成+3操作
popl %ebp //恢复原父函数堆栈
ret //pop出原EIP地址,恢复执行
f:
pushl %ebp //保存现场,将父函数的栈底寄存器存入当前程序栈中
movl %esp, %ebp //构建当前函数堆栈
subl $, %esp //栈顶加一,用以储存变量传递给g函数
movl (%ebp), %eax //取得参数
movl %eax, (%esp) //将参数传入变量位置
call g //调用g
leave //清楚局部变量空间
ret //返回
main:
pushl %ebp
movl %esp, %ebp
subl $, %esp //空出局部变量空间
movl $, (%esp) //为变量赋值
call f //调用f
addl $, %eax //完成+1操作
leave //清理局部变量
ret //返回
我们对f函数进行详细的分析:
1. 首先进行enter指令:
此时,ebp当前所指向的位置存入栈顶,并且将ebp重定向指向esp:
2.栈顶加一并存入变量值:
3.调用g
4.从g返回后,返回值储存在AX寄存器中,不用操作,调用leave,清理变量
5.最后ret,同时EIP被读出恢复到原位置继续执行,返回值在AX中传递给调用函数
3.个人的一点感悟:
程序的调用就是这样嵌套的执行下去,每个函数都有自己的堆栈用以储存当前变量以及环境值,并通过将父函数的EBP放入栈底用以恢复环境。
同时EIP存入父栈栈顶,便于恢复到原节点处继续执行。
这样,就可以有规律的一直嵌套下去。
如果使用递归函数,就是一个码堆栈的过程,知道最顶部的堆栈返回,函数就像多米诺骨牌一样收回所有的堆栈。
这也是递归函数占用空间比较多的原因之一。如果没有很好地退出机制,有可能内存溢出。
C程序汇编运行模式简析的更多相关文章
- Hadoop_20_MapReduce程序的运行模式
1.MapReduce程序的运行模式 1. Windows中运行MapReduce程序 (1)mapreduce程序是被提交给LocalJobRunner在本地以单进程的形式运行 (2)而处理的数据及 ...
- DirectShow程序运行过程简析
这段时间一直在学习陆其明老师的<DirectShow开发指南>一书,书中对DirectShow的很多细节讲解清晰,但是却容易让人缺少对全局的把握.在学习过程中,整理了关于DirectSho ...
- Qt- 图形界面应用程序的运行模式
main() 定义主窗口 ————>fd = DefineMainWindow() 创建主窗口————>win = CreateMainWindow() 创建主窗口中的元素-----> ...
- Hadoop-MR[会用]MR程序的运行模式
1.简介 现在很少用到使用MR计算框架来实现功能,通常的做法是使用hive等工具辅助完成.但是对于其底层MR的原理还是有必要做一些了解. 2.MR客户端程序实现套路 这一小节总结归纳编写mr客户端程序 ...
- RAP开发入门-运行过程简析(三)
今天通过标准的RAP程序来简单分析下RAP的启动过程 1.新建一个标准的rap plugin-in 项目: 得到的项目结构大概如下: run confi..->..add bundle(配置好b ...
- iOS7程序后台运行
介绍 这次 iOS7 对程序后台运行进行了加强,但是仅仅是加强而已,要想像 Android 程序那样自由当然就别想了,苹果这么做主要还是出于电池使用时间考虑,但是这次的加强对大部分程序基本够用. 在介 ...
- Flink源码阅读(一)——Flink on Yarn的Per-job模式源码简析
一.前言 个人感觉学习Flink其实最不应该错过的博文是Flink社区的博文系列,里面的文章是不会让人失望的.强烈安利:https://ververica.cn/developers-resource ...
- Eclipse Debug模式的开启与关闭问题简析_java - JAVA
文章来源:嗨学网 敏而好学论坛www.piaodoo.com 欢迎大家相互学习 默认情况下,eclipse中右键debug,当运行到设置的断点时会自动跳到debug模式下.但由于我的eclipse环境 ...
- 3 weekend110的job提交的逻辑及YARN框架的技术机制 + MR程序的几种提交运行模式
途径1: 途径2: 途径3: 成功! 由此,可以好好比较下,途径1和途径2 和途径3 的区别. 现在,来玩玩weekend110的joba提交的逻辑之源码跟踪 原来如此,weekend110的job提 ...
随机推荐
- Linux 文件系统分区基础
文件系统就是管理设备,组织文件的一些结构和算法. /boot分区,它包含了操作系统的内核和在启动系统过程中所要用到的文件, 建这个分 区是有必要的,因为目前大多数的PC机要受到BIOS的限制,况且如果 ...
- [django]手动数据库备份
基本原理是按钮点击后,系统查询出数据表中信息,然后在网页中导出相关表格! 若有自动数据库备份的兄弟,指点一下! 模板代码: <a href="{% url 'work_backup' ...
- 初识WebService
一.什么是Web服务 Web服务是一种可以用来解决跨网络应用集成问题的开发模式,目的是保证不同平台的应用服务可以互操作 二.Web服务的三个核心 Soap: SOAP(Simple Object Ac ...
- 《Google软件测试之道》基础
<Google软件测试之道>,一直听朋友讲起这本书,出于琐事太多,一直没机会拜读,最近部门架构觉得我们IT部门的技术太low,就给我们挑选了一些书籍,让我们多看看... 个人的一种学习习惯 ...
- jquery.mobiscroll仿Iphone ActionSheet省市区联动
1 <!DOCTYPE html> 2 <html lang="en"> 3 <head> 4 <meta charset="u ...
- 搭建一套自己实用的.net架构(3)【ORM-Dapper+DapperExtensions】
现在成熟的ORM比比皆是,这里只介绍Dapper的使用(最起码我在使用它,已经运用到项目中,小伙伴们反馈还可以). 优点: 1.开源.轻量.小巧.上手容易. 2.支持的数据库还蛮多的, Mysql,S ...
- [LeetCode] Merge k Sorted Lists 合并k个有序链表
Merge k sorted linked lists and return it as one sorted list. Analyze and describe its complexity. 这 ...
- csv表格处理(上)-- JS 与 PHP 协作导入导出
CSV简介 在开发后台管理系统的时候,几乎无可避免的会遇到需要导入导出Excel表格的需求.csv也是表格的一种,其中文名为“逗号分隔符文件”.在Excel中打开如下图左边所示,在记事本打开如下图右边 ...
- jsp的九大内置对象
九大内置对象 jsp servlet 对象名 类型 使用范围 request HttpServletRequest 请求 浏览器--->服务器 response HttpServletRes ...
- ReactJS尝鲜:实现tab页切换和菜单栏切换和手风琴切换效果,进度条效果
前沿 对于React, 去年就有耳闻, 挺不想学的, 前端那么多东西, 学了一个框架又有新框架要学