我的程序是怎样跑起来的呢?
我肯定无法仅在这一篇文章中讲完,请多见谅。
我们眼中的cpu
cpu和内存是由许多晶体管组成的电子部件,通常称为IC( Integrated Circuit,集成电路)。从功能方面来看,如图所示,CPU的内部由寄存器、控制器.运算器和时钟四个部分构成,各部分之间由电流信号相互连通。寄存器可用来暂存指令、数据等处理对象,可以将其看作是内存的一种。根据种类的不同,一个CPU内部会有20~100个寄存器。控制器负责把内存上的指令、数据等读人寄存器,并根据指令的执行结果来控制整个计算机。运算器负责运算从内存读人寄存器的数据。时钟负责发出CPU开始计时的时钟信号。(不过,也有些计算机的时钟位于CPU的外部。) 注释:时钟信号英文叫作clock puzzle。 Pentium2 GHz表示时钟信号的频率为2GHz(1 GHz= 10亿次1秒)。也就是说,时钟信号的频率越高,CPU 的运行速度越快。 计算机导论这本书中会讲解cpu的组成,但是对CPU的了解如果只限于此的话,对编程是没有任何帮助的。程序员还需要理解CPU是如何运行的,特别是要弄清楚负责保存指令和数据的寄存器的机制。了解了寄存器,也就自然而然地理解了程序的运行机制。
cpu内部有啥嘞
不同类型的CPU,其内部寄存器的数量、种类以及寄存器存储的数值范围都是不同的。不过,根据功能的不同,我们可以将寄存器大致划分为八类,如表所示。可以看出,寄存器中存储的内容既可以是指令也可以是数据。其中,数据分为“用于运算的数值"和“表示内存地址的数值”两种。数据种类不同,存储该数值的寄存器也不同。CPU中每个寄存器的功能都是不同的。用于运算的数值放在累加寄存器中存储,表示内存地址的数值则放在基址寄存器和变址寄存器中存储。 注释:CPU是具有各种功能的寄存器的集合体。其中,程序计数器、累加寄存器、标志寄存器、指令寄存器和栈寄存器都只有一个,其他的寄存器一般有多个。程序计数器和标志寄存器比较特殊。
程序在咱的内存中是咋"走"的呢?
只有1行的有用程序是很少见的,机器语言的程序也是如此。在对CPU有了一个大体印象后,接下来我们看一下程序是如何按照流程来运行的。 图是程序起动时内存内容的模型。用户发出启动程序的指示后,Windows等操作系统"会把硬 盘中保存的程序复制到内存中。示例中的程序实现的是将123和456两个数值相加,并将结果输出到显示器上。 图中把指令、数据分配到了一个地址中。0100,然后程序便开始运行。CPU每执行一个指令,程序计数器的值就会自动加1。例如,CPU执行0100地址的指令后,程序计数器的值就变成了0101 (当执行的指令占据多个内存地址时,增加与指令长度相应的数值)。然后,CPU的控制器就会参照程序计数器的数值,从内存中读取命令并执行。也就是说,程序计数器决定着程序的流程。
最后在说一下条件分支和循环结构的实现呗。
程序的流程分为顺序执行、条件分支和循环三种。顺序执行是指按照地址内容的顺序执行指令。条件分支是指根据条件执行任意地址的指令。循环是指重复执行同一地址的指令。顺序执行的情况比较简单,每执行一个指令程序计数器的值就自动加1。但若程序中存在条件分支和循环,机器语言的指令就可以将程序计数器的值设定为任意地址(不是+1)。这样一来,程序便可以返回到上一个地址来重复执行同一个指令,或者跳转到任意地址。接下来,我们就以条件分支为例,来具体说明循环时程序计数器的数值设定机制也是一样的。 图中表示把内存中存储的数值(示例中是123)的绝对值输出到显示器的程序的内存状态。程序运行的开始位置是0100地址。随着程序计数器数值的增加,当到达0102地址时,如果累加寄存器的值是正数,则执行跳转指令( jump指令)跳转到0104地址。此时,由于累加寄存器的值是123,为正数,因此0103地址的指令被跳过,程序的流程直接跳转到了0104地址。也就是说,“跳转到0104地址”这个指令间接执行了“将程序计数器设定成0104地址”这个操作。
条件分支和循环中使用的跳转指令,会参照当前执行的运算结果来判断是否跳转。表1-1所列出的寄存器中,我们提到了标志寄存器。无论当前累加寄存器的运算结果是负数、零还是正数,标志寄存器都会将其保存(也负责存放溢出“和奇偶校验“ 的结果 )。
注意:溢出(overflow)是指运算的结果超出了寄存器的长度范围。 奇偶校验( parity check)是指检查运算结果的值是偶数还是奇数 CPU在进行运算时,标志寄存器的数值会根据运算结果自动设定。条件分支在跳转指令前会进行比较运算。至于是否执行跳转指令,则由CPU在参考标志寄存器的数值后进行判断。运算结果的正、零、负三种状态由标志寄存器的三个位“表示。 图1-6是32位CPU(寄存器的长度是32位)的标志寄存器的示例。标志寄存器的第-个字节位、第二个字节位和第三个字节位的值为1时,表示运算结果分别为正数、零和负数。 CPU执行比较的机制很有意思(就是非常简单),例如,假设要比较累加寄存器中存储的XXX值和通用寄存器中存储的YYY值,执行比较的指令后,CPU的运算装置就会在内部(暗中)进行xXx -YYY的减法运算。而无论减法运算的结果是正数、零还是负数,都会保存到标志寄存器中。结果为正表示XXX比YYY大,零表示.xXx和YYY相等,负表示xXX比YYY小。程序中的比较指令,就是在CPU内部做减法运算。
那咱今天就讲到这里,嘿,您猜怎么着,咱下回再见。
|