这让我感到困惑的原因是,所有地址都包含1和0的序列。那么,CPU如何区分00000100
(整数)与00000100
(CPU指令)?
首先,不同的命令具有不同的值(操作码)。这就是CPU知道what要做的事情。
最后,问题仍然存在:什么是命令,什么是数据?
现代PC正在使用von Neumann-体系结构(https://en.wikipedia.org/wiki/John_von_Neumann)”,其中数据和操作码存储在同一存储空间中。 (在这两个数据类型之间有一些架构是分开的,例如哈佛架构)]
详细解释所有内容将完全超出stackoverflow的范围,很可能每个帖子的字符数不足。
用尽可能少的单词回答问题(实际上,每个人都在这个级别上工作都会因为解释中的快捷方式而杀死我:]
因此,假设应该执行加法,并且内存中有3个地址,应用程序将进行存储(在5+7
的情况下(我在指令中使用了“动词”)]
Adress | Stored Value
1 | ADD
2 | 5
3 | 7
最后,CPU接收到指令1 2 3
,这意味着ADD 5 7
(这些东西是顺序敏感的![命令] [v1] [v2])...现在情况变得越来越复杂。
CPU会将这些值(实际上不是值,只是值的地址)移到其寄存器中,然后进行处理。选择的确切寄存器取决于数据类型,数据大小和操作码。
[对于命令#1 #2 #3
,CPU将首先读取这些存储器地址,然后知道需要ADD 5 7
。
基于ADD
的操作码,CPU将知道:
#2
放入r1#3
放入r2注对此进行了简化。实际上,CPU需要有关其处理value还是address的确切说明。在组装中,可以通过使用
CPU无法对存储在存储器中的值执行计算,因此将值从存储器移至寄存器以及从寄存器移至存储器非常忙。
即如果有
eax = 0x2
和在内存中
0x2 = 110011
和说明
MOV ebx, [eax]
这意味着:将当前存储在eax
中的当前存储在地址中的值移动到寄存器ebx
中。所以最后
ebx = 110011
(每次CPU进行一次计算时都会发生这种情况。内存->寄存器->内存)
最后,请求的应用程序可以读取其预定义的内存地址#2,得出地址2568,然后知道计算结果存储在地址2568中。读取地址将得出12
(5 + 7)值>
这只是发生的事情的一个很小的例子。有关此内容的详细介绍,请参考http://www.cs.virginia.edu/~evans/cs216/guides/x86.html
一个人不能真正把握2个值的简单
加法的数据移动量和计算量。执行CPU的操作(在纸上)将花费您几分钟来计算“ 5 + 7”,因为没有“ 5”也没有“ 7”-一切都隐藏在内存中的地址后面,指向某些位,根据地址0x1所指示的内容,得出不同的值...简写形式:CPU不知道那里存储了什么,但是指令告诉CPU如何解释它。
CPU(除了NX位之类的安全性东西之外)对数据还是代码视而不见。
这是因为ISA必须考虑有效的指令集以及如何对数据进行编码:内存地址/寄存器/文字。
简而言之,操作系统会告诉它下一条指令在哪里。在x64的情况下,有一个称为rip(指令指针)的特殊寄存器,该寄存器保存要执行的下一条指令的地址。它将自动读取该地址处的数据,对其进行解码和执行,并自动将rip增加指令的字节数。