2019-2020-1 20199310《Linux内核原理与分析》第二周作业
1.问题描述
众所周知,计算机是20世纪最伟大的发明之一,计算机是如何工作的呢?本文主要通过计算机的组成结构和工作原理,以及汇编代码工作过程来进行详细叙述。
2.解决过程
2.1 冯·诺依曼体系结构
一般来讲,现代计算机结构依据冯·诺依曼结构体系,该结构也成普林斯顿结构,是一种将程序指令存储器和数据存储器合并在一起的存储器结构。主要由运算器、控制器、存储器、输入设备和输出设备五大部件构成,其中运算器,控制器和部分寄存器合并也称为CPU,整个体系采用二进制逻辑运算,即0/1编码。结构示意图如下所示:

引用链接:计算机系统
2.2 计算机工作原理
计算机运行的基础是CPU,CPU中主要包括算数逻辑单元ALU,程序计数器PC,指令寄存器IR,数据寄存器DR,地址寄存器AR等。CPU内部结构如下图所示:

几乎所有的冯·诺依曼型计算机的CPU执行指令都可以进行5个阶段:取指,译码,访存,执行和写回。
2.2.1 取指
取指令阶段,是将指令从主存中取出到指令寄存器IR的过程,同时程序寄存器PC中的值会指向当前执行指令的下一条指令地址。
2.2.2 译码
取出指令后,指令译码器根据指令的格式,对取出的指令进行拆分和解析,获取不同的操作方法。
2.2.3 访存
根据指令内容,可能会再次根据指令中地址访问主存,读取操作数,用于操作运算。
2.2.4 执行
在取指和取数结束后,根据指令的操作码,会进行一系列不同的操作。
2.2.5 写回
指令执行结束后,会把数据以写回的存储到内部寄存器中或外部存储空间中。
指令执行过程如下图所示:

引用链接:计算机组成原理
2.3 汇编代码的简易工作过程
汇编语言(assembly language)是一种用于电子计算机、微处理器、微控制器或其他可编程器件的低级语言,亦称为符号语言。在汇编语言中,用助记符代替机器指令的操作码,用地址符号或标号代替指令或操作数的地址。在不同的设备中,汇编语言对应着不同的机器语言指令集,通过汇编过程转换成机器指令。
引用链接:汇编语言
接下来将通过汇编一个简单的C语言程序并分析其汇编指令执行过程。
2.3.1 C语言程序
使用vim编辑器编辑mian.c程序,内容如下代码:
int g(int x)
{
return x + 5;
}
int f(int x)
{
return g(x);
}
int main(void)
{
return f(10) + 2;
}
在实验楼环境中,通过gcc命令编译和执行main.c程序,命令执行代码如下:
#编译C语言代码文件
gcc main.c
#执行a.out可执行文件
./a.out
#输出程序返回值
echo $?
运行程序结果如下图所示:

2.3.2 汇编文件
通过gcc命令将c语言程序文件转化为一个汇编文件main.s,并vim编辑器处理和读取汇编代码,具体操作如下:
#将c语言程序编译为main.s汇编文件
gcc –S –o main.s main.c -m32
#用vi方式打开汇编文件
vi main.s
#在命令模式下取除"."开头的辅助信息
g/\.s*/d
汇编语言显示如下:

2.4 汇编代码的工作栈分析
栈(stack)又名堆栈,它是一种运算受限的线性表。限定仅在表尾进行插入和删除操作的线性表。这一端被称为栈顶,相对地,把另一端称为栈底。向一个栈插入新元素又称作进栈、入栈或压栈,它是把新元素放到栈顶元素的上面,使之成为新的栈顶元素;从一个栈删除元素又称作出栈或退栈,它是把栈顶元素删除掉,使其相邻的元素成为新的栈顶元素,栈的最大特点是先进后出。
引用链接:栈
在汇编语言执行过程中,指令和数据等会寄存在以栈未主要形式的寄存器里。32位的8086CPU中,主要由两个指针寄存器ESP和EBP,以及一个常用的数据寄存器EAX。
其中ESP堆栈指针寄存器,用于存放指向系统栈最上面一个栈帧的栈顶,EBP基指针寄存器,用于存放指向系统栈最上面一个栈帧的栈底。通俗地讲在函数调用前,EBP的值会传入栈,ESP存储栈顶地址,然后ESP会把值传给EBP;在函数调用结束后,EBP会把值传回ESP,ESP又指向栈顶地址。本例中建设堆栈空间单元号向下增长,地址向下减小,一个存储单元未4个字节32位,初始状态下,EBP和ESP指针均指向标号为0的初始位置(2000),如下图所示:

下面来分析一下上一小节中main.s各行汇编语言执行过程中,堆栈空间的变化情况:
2.4.1 main函数执行过程
程序先执行18-22行,然后调用f函数。
pushl %ebp
此代码执行后,ESP寄存器将会指向单元号1,然后EBP寄存器的值(地址2000)会存储到堆栈标号1的位置。

movl %esp, %ebp
此代码执行后,EBP寄存器将会指向单元号1。

subl $4, %esp
```。

movl $10, (%esp)
此代码执行后,立即数10会被存入ESP寄存器指向的2号存储单元。

call f
此代码执行后,ESP寄存器指向下一存储单元,EIP寄存器行号23(运行call f汇编指令的文件行号的下一行)存入3号存储空间,同时EIP寄存器指向f函数的第一条指令行号9。

### 2.4.2 f函数执行过程
pushl %ebp
movl %esp, %ebp
此代码执行后,ESP寄存器先指向下一存储单元4,然后将EBP寄存器的值存入存储单元4号,然后将EBP指向与ESP相同的地址。

subl $4, %esp
movl 8(%ebp), %eax
此代码执行后,ESP寄存器先指向下一个存储单元5,然后将EBP上移8个地址位置的存储单元2中值存入EAX寄存器,注意此处EBP寄存器指针实际未改变。

movl %eax, (%esp)
此代码执行后,将EAX寄存器中数值存入ESP寄存器所指向的位置,即存储单元5。

call g
此代码执行后,ESP寄存器指向下一存储单元,EIP寄存器行号15(运行call g汇编指令的文件行号的下一行)存入6号存储空间,同时EIP寄存器指向f函数的第一条指令行号2。

### 2.4.3 g函数执行过程
pushl %ebp
movl %esp, %ebp
此代码执行后,ESP寄存器先指向下一存储单元7,然后将EBP寄存器的值存入存储单元7号,然后将EBP指向与ESP相同的地址。

movl 8(%ebp), %eax
addl $5, %eax
此代码执行后,将EBP寄存器指向位置上移8个位置所在存储单元中的立即数10存入EAX寄存器中,再把立即数5加入寄存器EAX,得到EAX寄存器存储值15。

popl %ebp
ret
此代码执行后,EBP寄存器转回ESP寄存器指向存储单元7中的内容,即恢复函数f的函数调用堆栈基址EBP寄存器,ESP寄存器指向存贮单元6,然后将ESP指向存储单元6的内容15放到EIP寄存器中,ESP寄存器进一步向上移动4个地址指向存储单元5,EIP下一步执行第15行leave指令。

### 2.4.4 f函数返回过程
leave
此代码执行后,ESP寄存器先指向EBP相同存储单元4,然后将EBP寄存器将跳转至当前存储单元内容所指向的存储单元1,然后将ESP将再向上移动4个地址指向存储单元3。

ret
此代码执行后,ESP寄存器指向内容32将写入EIP,下一步程序跳转值第23行执行addl指令,同时ESP向上移动4个地址。

### 2.4.5 main函数返回过程
addl $2, %eax
此代码执行后,将立即数$2加入EAX寄存器,然后返回函数值。

leave
ret
此代码执行后,ESP寄存器指向EBP寄存器指向的地址,EBP寄存器根据存储单元1内容跳转至初始地址(2000),然后ESP寄存器基址也向上加4个地址来到初始地址(2000)。

# 3.总结
本文主要学习了计算机冯·诺依曼体系结构、计算机CPU工作原理以及汇编语言执行过程中堆栈的变化情况,冯·诺依曼体系结构作为当前主流的计算机体系结构,一直沿用至今。早期的冯·诺依曼体系结构是以运算器为中心的,但是由于运算器和控制器集成技术的提高和存储容量的扩大,现在主要以存储器为中心。计算机CPU工作原理涉及指令的操作,以及相关硬件数据流的输入和输出,在之前基础课程计算机组成原理有过一定学习。堆栈的变化可以通过汇编语言来解读,汇编语言位于机器语言上一层,能够较为清洗地描述计算机内部硬件之间的信息交互和数据转存过程,通过这次学习,我对其中的堆栈结构以及ESP和EBP两个指针寄存器留下了深刻的印象。学习较为抽象的知识,可以借鉴灵活的模型和图表来形象演绎,可以提高学习效率。
2019-2020-1 20199310《Linux内核原理与分析》第二周作业的更多相关文章
- 2019-2020-1 20199303<Linux内核原理与分析>第二周作业
2019-2020-1 20199303第二周作业 1.汇编与寄存器的学习 寄存器是中央处理器内的组成部份.寄存器是有限存贮容量的高速存贮部件,它们可用来暂存指令.数据和位址.在中央处理器的控制部件中 ...
- 20169219 linux内核原理与分析第二周作业
"linux内核分析"的第一讲主要讲了计算机的体系结构,和各寄存器之间对数据的处理过程. 通用寄存器 AX:累加器 BX:基地址寄存器 CX:计数寄存器 DX:数据寄存器 BP:堆 ...
- 2019-2020-1 20199314 <Linux内核原理与分析>第二周作业
1.基础学习内容 1.1 冯诺依曼体系结构 计算机由控制器.运算器.存储器.输入设备.输出设备五部分组成. 1.1.1 冯诺依曼计算机特点 (1)采用存储程序方式,指令和数据不加区别混合存储在同一个存 ...
- Linux内核原理与分析-第二周作业
写之前回看了一遍秒速五厘米:如果
- Linux内核原理与分析-第一周作业
本科期间,学校开设过linux相关的课程,当时的学习方式主要以课堂听授为主.虽然老师也提供了相关的学习教材跟参考材料,但是整体学下来感觉收获并不是太大,现在回想起来,主要还是由于自己课下没有及时动手实 ...
- 2019-2020-1 20199314 <Linux内核原理与分析>第一周作业
前言 本周对实验楼的Linux基础入门进行了学习,目前学习到实验九完成到挑战二. 学习和实验内容 快速学习了Linux系统的发展历程及其简介,学习了下的变量.用户权限管理.文件打包及压缩.常用命令的和 ...
- 2018-2019-1 20189221《Linux内核原理与分析》第一周作业
Linux内核原理与分析 - 第一周作业 实验1 Linux系统简介 Linux历史 1991 年 10 月,Linus Torvalds想在自己的电脑上运行UNIX,可是 UNIX 的商业版本非常昂 ...
- 2020-2021-1 20209307 《Linux内核原理与分析》第九周作业
这个作业属于哪个课程 <2020-2021-1Linux内核原理与分析)> 这个作业要求在哪里 <2020-2021-1Linux内核原理与分析第九周作业> 这个作业的目标 & ...
- 2019-2020-1 20199329《Linux内核原理与分析》第十三周作业
<Linux内核原理与分析>第十三周作业 一.本周内容概述 通过重现缓冲区溢出攻击来理解漏洞 二.本周学习内容 1.实验简介 注意:实验中命令在 xfce 终端中输入,前面有 $ 的内容为 ...
- 2019-2020-1 20199329《Linux内核原理与分析》第十二周作业
<Linux内核原理与分析>第十二周作业 一.本周内容概述: 通过编程理解 Set-UID 的运行机制与安全问题 完成实验楼上的<SET-UID程序漏洞实验> 二.本周学习内容 ...
随机推荐
- WEB缓存系统之varnish状态引擎
前文我们聊了下varnish的VCL配置以及语法特点,怎样去编译加载varnish的vcl配置,以及命令行管理工具varnishadm怎么去连接varnish管理接口进行管理varnish,回顾请参考 ...
- Java中使用RSA算法加密
Java中使用RSA算法加密 概述 RSA加密算法是一种非对称加密算法 RSA加密的方式 使用公钥加密的数据,利用私钥进行解密 使用私钥加密的数据,利用公钥进行解密 RSA是一对密钥.分别是公钥和私钥 ...
- 「SpringBoot」如何优雅地管理SpringBoot项目
本文主要讲述一下如何优雅地管理SpringBoot项目. 背景 课堂上,当小明形如流水地回答完沐芳老师提出来的问题时,却被至今没有对象的胖虎无情嘲讽了? 沐芳老师:小明,你平时是如何启动.停止你的Sp ...
- Activiti7新的API介绍
一.Activiti7 的组成部分 Activiti Core 作为Activiti 的核心部分,Activiti Cloud 主要是利用云服务来实现分布式业务流程开发. 二.Activiti 新的 ...
- centos默认终端bash美化、颜色设置
centos默认终端bash是一个很简单的界面,又无法通过像zsh一样直接安装主题和代码高亮插件,但是我们可以在bashrc的配置文件中通过代码实现一部分功能: 1.代码介绍: 这里推荐一篇大佬的文章 ...
- markdown怎么上传图片
将图片转为base64格式 , 在线转换地址link 语法格式 // 方式1  // 方式2 ![picture][img] [img]:base64密钥
- DHCP完整过程详解及Wireshark抓包分析
DHCP,Dynamic Host Configuration Protocol,动态主机配置协议,简单来说就是主机获取IP地址的过程,属于应用层协议. DHCP采用UDP的68(客户端)和67(服务 ...
- 怎样让scratch里的人物两腿走动
需要人物角色至少有两个“造型”,表现走路时的两个动作.以默认的“小猫”觉色为例,它有两个“造型”,可以用来表现奔跑的动作. 但是要想让小猫跑起来,需要脚本来实现,简单跑动脚本如下 scratch学习视 ...
- 15分钟从零开始搭建支持10w+用户的生产环境(一)
前言 这是一个基于中小型企业或团队的架构设计. 不考虑大厂.有充分的理由相信,大厂有绝对的实力来搭建一个相当复杂的环境. 中小型企业或团队是个什么样子? 开发团队人员配置不全,部分人员身兼开发过程上下 ...
- HAproxy 基础配置
基础配置详解 HAProxy 的配置文件haproxy.cfg由两大部分组成,分别是global和proxies部分 global:全局配置段 进程及安全配置相关的参数性能调整相关参数Debug参数 ...