CPU如何执行程序

简介: 1. CPU = 运算单元 + 数据单元 + 控制单元2. CPU 只能识别「二进制」的指令3. 总线像连接 CPU 和内存这两个设备的高速公路4. 执行高级语言的两种方式:1. 解释执行 2. 编译执行5. 汇编语言和机器语言是一一对应的6. 内存中的每个存储空间都有其对应的独一无二的地址7. CPU时钟周期:取出指令、分析指令、执行指令这三个过程


kill the boy,let the man born --《权利的游戏》

一语中的

  1. CPU = 运算单元 + 数据单元 + 控制单元
  2. CPU 只能识别「二进制」的指令
  3. 总线像连接 CPU 和内存这两个设备的高速公路
  4. 执行高级语言的两种方式:1. 解释执行 2. 编译执行
  5. 汇编语言和机器语言是一一对应的
  6. 内存中的每个存储空间都有其对应的独一无二的地址
  7. CPU时钟周期:取出指令、分析指令、执行指令这三个过程

文章概要

  • 计算机工作模式
  • CPU和内存如何配合工作的
  • 机器语言/汇编语言/高级语言
  • CPU如何执行程序

计算机工作模式

对于计算机来讲,最核心的就是「CPU」(Central Processing Unit,中央处理器)

CPU 和其他设备连接,要靠一种叫作「总线」(Bus)的东西,其实就是主板上密密麻麻的集成电路,这些东西组成了 CPU 和其他设备的高速通道。

在这些设备中,最重要的是「内存」(Memory)。因为单靠 CPU 是没办法完成计算任务的,很多复杂的计算任务都需要将中间结果保存下来,然后基于中间结果进行进一步的计算。CPU 本身没办法保存这么多中间结果,这就要依赖内存了。

总线上还有一些其他设备,例如显卡会连接显示器、磁盘控制器会连接硬盘、USB 控制器会连接键盘和鼠标等等。


CPU和内存如何配合工作的

CPU:包括三个部分,运算单元、数据单元和控制单元。

  • 运算单元只管算,例如做加法、做位移等等。
  • 数据单元包括 CPU 内部的缓存通用寄存器组,「空间很小」,但是速度飞快,可以「暂时」存放数据和运算结果
  • 控制单元是一个统一的「指挥中心」,它可以获得下一条指令,然后执行这条指令。 这个指令会指导运算单元取出数据单元中的某几个数据,计算出个结果,然后放在数据单元的某个地方。

每个程序都有一个「项目执行计划书」,里面是一行行程序执行的指令。每个进程都有一个程序放在硬盘上,是「二进制」的,再里面就是一行行的指令,会操作一些数据。

进程一旦运行,比如图中两个进程 A 和 B,会有「独立」的内存空间,互相隔离,程序会分别加载到进程 A 和进程 B 的内存空间里面,形成各自的代码段

程序运行的过程中要操作的数据和产生的计算结果,都会放在数据段里面。

CPU 的控制单元里面,有一个「指令指针寄存器」(IP 寄存器),它里面存放的是下一条指令在内存中的地址。控制单元会「不停」地将代码段的指令拿进来,先放入指令寄存器。


机器语言/汇编语言/高级语言

机器语言

把 CPU 看成是一个非常小的运算机器,为了能够完成复杂的任务,为 CPU 提供了一大堆指令来实现各种功能,这一大堆指令称为指令集(Instructions)。也就是「机器语言」。

CPU 只能识别二进制的指令

汇编语言

但是,二进制代码难以阅读和记忆,又将二进制指令集转换为人类可以识别和记忆的符号 -- 「汇编指令集」

1000100111011000  机器指令
mov ax,bx         汇编指令
复制代码

CPU 不能直接识别汇编语言,还需要一个「汇编编译器」,其作用是将汇编代码编程成机器代码。

「汇编语言的弊端」

  • 不同的 CPU 有着不同的指令集
  • 需要了解和处理器架构相关的硬件知识

高级语言

所以, 诸如 C、C++、Java、C#、Python、JavaScript 等高级语言应用而生。

和汇编语言一样,CPU也不能直接识别由高级语言所编写的代码。

根据对高级语言转换的过程中是否生成「机器代码」,把执行高级语言分为

  1. 解释执行
  2. 编译执行

解释执行

先将源代码通过解析器编译成中间代码,之后「直接」使用解释器解释执行中间代码,然后「直接输出结果」。

并不把整个程序 变成目标码,而是按顺序,读一句,解释一句,执行一句,所以,没给完整程序,它就可以执行了。

例如,浏览器处理网页,网页程序,每下来一句,就可以解释执行一句,不用等整个网页下来后再处理。

编译执行

先将源代码通过「解析器」编译成中间代码,编译器再将中间代码编译成「机器代码」(编译成的机器代码以二进制文件形式存储), 执行这段程序的时候直接执行二进制文件。

必须给出完整程序,编译器通过几次扫描,翻译,编排,链接,变成exe文件执行。


CPU如何执行程序

我们通过针对一段C代码,进行编译执行,来看看CPU是如何执行程序的。(像JS这种解释执行,有另外一套逻辑和实现方式,后期会有介绍)

// test.c
int main (void)
{
   int x =1;
   int y = 2;
   int z = x + y;
   return z;
}
复制代码

CPU 并不能直接执行这段 C 代码,需要对其进行编译,将其转换为二进制的机器码, CPU 才能按照顺序执行编译后的机器码。

通过 GCC 编译器将 C 代码编译成二进制文件。gcc -O0 -o code_prog test.c。 (在Mac环境下,可以通过brew来进行gcc的下载) 随后, 文件夹中生成名为 code_prog 的「可执行程序」。

通过objdump将编译出来的 code_prog 程序进行反汇编。objdump -d code_prog

  • 左边就是编译生成的机器码,每一行其实都是一个指令,该指令可以让 CPU 执行指定的任务
  • 中间的部分是汇编代码, 汇编代码采用助记符(memonic)来编写程序,原本是二进制表示的指令,在汇编代码中可以使用单词来表示。「汇编语言和机器语言是一一对应的」

编译后的程序是由一堆二进制代码组成的(二进制代码是由一条条指令构成的)

准备工作

在程序执行之前,程序需要被「装进内存」。CPU 可以通过指定内存地址,从内存中读取数据,或者往内存中写入数据。(内存是一个临时存储数据的设备, 因为断电之后,内存中的数据都会消失)

「内存中的每个存储空间都有其对应的独一无二的地址」。

在内存中,每个存放字节的空间都有其唯一的地址,而且地址是按照顺序排放的

代码被编译成可执行文件, 而可执行文件中包含了二进制的机器码。 当二进制代码被加载进了内存后,内存中的每条「二进制代码」便都有了自己对应的地址。

CPU时钟周期

CPU时钟周期:取出指令、分析指令、执行指令这三个过程

CPU取指令

CPU 中有一个 PC 寄存器,它保存了将要执行的指令地址。 当二进制代码被装载进了内存之后, 系统会将二进制代码中的第一条指令的地址写入到 PC 寄存器中。 到了下一个时钟周期时,CPU 便会根据 PC 寄存器中的地址,从内存中取出指令。

CPU分析指令

PC 寄存器中的指令取出来之后,将下一条指令的地址更新到 PC 寄存器中,并分析取出的指令。

CPU执行指令

取出的指令分两部分

  1. 一部分是做什么操作,例如是加法还是位移;
  2. 一部分是操作哪些数据。

要执行这条指令,就要把第一部分交给运算单元,第二部分交给数据单元。

数据单元根据数据的地址,从数据段里读到数据寄存器里,就可以参与运算了。运算单元做完运算,产生的结果会暂存在数据单元的数据寄存器里。最终,会有指令将数据写回内存中的数据段。

如此往复的对内存中的指令,进行取出、分析、执行。直到PC寄存器到达指令的最后。


参考资料:

  1. 趣谈Linux操作系统
  2. Google V8


相关文章
|
数据采集 安全 Windows
解决关于Windows Defender Antivirus Service自启造成运行python程序时,Windows的cpu和内存占用过高问题
启用“关闭Windwos defender”服务解决阿里云Windows服务器的卡顿问题,并列举了网上一些错误的解决方法。
11459 3
解决关于Windows Defender Antivirus Service自启造成运行python程序时,Windows的cpu和内存占用过高问题
|
4月前
|
C++
C++ 根据程序运行的时间和cpu频率来计算在另外的cpu上运行所花的时间
C++ 根据程序运行的时间和cpu频率来计算在另外的cpu上运行所花的时间
48 0
|
6月前
|
缓存 C语言 计算机视觉
程序与技术分享:CPU0处理器的架构及应用
程序与技术分享:CPU0处理器的架构及应用
|
5月前
|
缓存 弹性计算 数据库
阿里云2核4G服务器支持多少人在线?程序效率、并发数、内存CPU性能、公网带宽多因素
2核4G云服务器支持的在线人数取决于多种因素:应用效率、并发数、内存、CPU、带宽、数据库性能、缓存策略、CDN和OSS使用,以及用户行为和系统优化。阿里云的ECS u1实例2核4G配置,适合轻量级应用,实际并发量需结合具体业务测试。
89 0
阿里云2核4G服务器支持多少人在线?程序效率、并发数、内存CPU性能、公网带宽多因素
|
Java Go 开发工具
如何排查Go 程序 CPU 占用过高问题
如何排查Go 程序 CPU 占用过高问题
1769 0
如何排查Go 程序 CPU 占用过高问题
|
C++ 索引 Windows
调试实战——程序CPU占用率飙升,你知道如何快速定位吗?
程序CPU占用率飙升,你知道如何快速定位吗?
|
缓存 算法 Linux
程序绑定 CPU 核心
程序绑定 CPU 核心
477 0
|
数据可视化 Java Windows
windows系统启动java程序限制cpu核心数
windows系统启动java程序限制cpu核心数
634 0
windows系统启动java程序限制cpu核心数
|
存储 消息中间件 Kafka
【操作系统入门到成神系列 一】CPU 是如何执行程序的?
【操作系统入门到成神系列 一】CPU 是如何执行程序的?
【操作系统入门到成神系列 一】CPU 是如何执行程序的?
|
Java 程序员 编译器
CPU中的程序是怎么运行起来的
CPU中的程序是怎么运行起来的
197 0
CPU中的程序是怎么运行起来的