我有一个基本的问题是关于大会。

为什么我们懒得做算术运算只有在寄存器,如果他们可以工作上的存储器呢?

例如以下两个原因(基本)同样价值计算为一个回答:

1段

.data
    var dd 00000400h

.code

    Start:
        add var,0000000Bh
        mov eax,var
        ;breakpoint: var = 00000B04
    End Start


2段

.code

    Start:
        mov eax,00000400h
        add eax,0000000bh
        ;breakpoint: eax = 0000040B
    End Start



从我所看到的大多数文本和教程做算术运算主要是在寄存器。它是就更快的工作寄存器?

编辑:那是快:)

一些伟大的答复;最好的答案是选择的基础上第一个好的答案。

有帮助吗?

解决方案

寄存器是要快得多,并且还操作,你可以在存储器直接执行远远更多的限制。

其他提示

如果你看看计算机体系结构,你会发现一系列的记忆力水平。那些接近CPU是速度快,(每一个位)价格昂贵,因此小,而在另一端,你有大,速度慢和廉价的存储设备。在现代计算机中,这些通常是这样的:

 CPU registers (slightly complicated, but in the order of 1KB per a core - there
                are different types of registers. You might have 16 64 bit
                general purpose registers plus a bunch of registers for special
                purposes)
 L1 cache (64KB per core)
 L2 cache (256KB per core)
 L3 cache (8MB)
 Main memory (8GB)
 HDD (1TB)
 The internet (big)

随着时间的推移,越来越多的级别的高速缓存增加了 - 我能记得什么时候的CPU没有任何板载缓存,而我现在还年轻!这些天来,硬盘驱动器附带了板载缓存,以及互联网在任意数量的地方缓存:在内存,在硬盘上,也许对缓存代理服务器

有是减少的带宽并在增加的显着(量值的常数量级)的延迟在每一步远离CPU。例如,HDD可能能够在100MB与要读取的5毫秒的延迟(这些数字可能不完全正确)/ s,而你的主内存可以读取6.4GB / s的9ns六个订单的延迟(大小!)。延迟是一个非常重要的因素,因为你不想让CPU的等待不再比它(这是与深管线架构尤其如此,但是这是另一天的讨论)。

的想法是,你会经常被一遍又一遍地重复使用相同的数据,所以是有意义的把它放在一个小的快速缓存进行下一步操作。这被称为的时间局部性即可。局部性的另一个重要的原则是的空间局部性下,这表示,彼此接近该存储器位置可能会在大约相同的时间被读取。正是出于这个原因,从RAM读取会导致读取RAM的更大的块并付诸于CPU的缓存。如果不是因为当地的这些原则,然后在内存中的任何位置将具有在任何时间被读取同样可能的机会,所以就没有办法预测什么接下来将访问和高速缓存的所有级别世界上不会提高速度。你还不如只使用一个硬盘驱动器,但我敢肯定,你知道是什么感觉有电脑来进行分页时嘎然而止(这基本上是使用硬盘作为扩展到RAM)。在概念上,可能已经没有记忆,除了硬盘驱动器(以及许多小型设备有一个单一的内存),但是这会缓慢地痛苦相比,我们所熟悉的。

具有寄存器(只有一小数量的寄存器)的另一个优点是,它可以让你有的更短的说明即可。如果您有包含两个(或更多)64位地址的指令,你将有一些长期指导!

寄存器进行访问的办法比RAM的内存更快,因为你没有进入“缓慢”的内存总线!

x86,像几乎每一个其他的"正常"的CPU你可能会学大会,是一个 "注册机".还有其他的方式来设计的东西,你可以的程序(例如图灵机的移动沿着逻辑"带"在存储器),但登记的机器已经被证明是基本上唯一的路要走高的性能。

由于x86的目的是使用寄存器,你真的不能避免他们完全,甚至如果你想要和不关心的业绩。

目前x86处理器可读写/更多注册的每个时钟周期于存储的地点。

例如,英特尔Skylake可以做两载荷和一个商店,从/向其32kiB8-路联合L1D缓存每个周期(最好的情况下),但是可以 阅读以上10寄存器中的每个时钟,并编写3个或4(加EFLAGS).

建立一个L1D缓与尽可能多的读写港口 登记册的文件 将过于昂贵,(在极/积和电力使用),特别是如果你想保持它作为大,因为它是。这可能只是身体不可能建立的东西,可以使用的记忆方式x86使用注册相同的性能。

此外,编写了登记,然后读取它再次具有本质上的零延迟,因为CPU检测到这一并转发的结果直接输出的一个执行单元输入的另一个绕过回写阶段。(见 https://en.wikipedia.org/wiki/Classic_RISC_pipeline#Solution_A._Bypassing).

这些结果转发之间的连接执行的执行单元是所谓的"旁路网络"或"转发网络",它很容易的CPU要做到这一登记册的设计比如果一切都得以进入存储器,并回。CPU只有检查的3至5位注册号码,而不是一个32位或64位地址,以检测的情况下输出的一个指令是需要马上输入另一个操作。(与那些登记的数字很难编码的成机器码,使他们可用的时候了。)

正如其他人已经提到的,3或4个位址注册使机码格式更为紧凑于如果每一个指令有绝对的地址。


也参看 https://en.wikipedia.org/wiki/Memory_hierarchy:你可以认为登记册作为一个小的快 固定的尺寸 存储空间的独立自主存储器,其中只有直接的绝对解决的支持。(你不能"指标"一个注册:给予一个整数 N 在一个登记册,你不能得到的内容 N第登记册的一个insn.)

寄存器也是私人的,以一个单一的CPU核心,因此超出了执行可以做什么,它想要与他们。与存储,这有担心什么了事情就变得看到其他的CPU核心。

有一个固定数量的注册的一部分什么可以做的Cpu 登记册重新命名 为了执行。具有的注册号码可提供适当的指示是解码也使得这个比较容易:有没有读或写信给一个未知的登记。

看看 为什么mulss采取的仅仅3周期在哈斯韦尔,不同于昂纳的指示表? 对于一个解释的登记册重新命名,以及一个具体例子(后来的编辑问题/后部分我的回答显示出加速从展开与多个蓄隐藏FMA延迟,尽管它重复使用相同的建筑登记册重复).


商店缓冲存储转发并基本上给你"的存储器重新命名".一个存放/重新加载到存储位置独立的先前储存和装载到那个位置从核心。

重复功能的电话一堆参呼吁《公约》和/或返回值的参考,情况相同的字节的堆存储器可以被重新使用多次。

该秒存放/重新加载可以执行,即使第一储存是仍在等待它的投入。(我已经测试了这个Skylake,但是。如果我曾经公布了结果在一个答案任何地方。)

我们使用的寄存器,因为他们是快。通常情况下,他们在CPU的速度运行。结果 寄存器和CPU的缓存与不同的技术/面料和结果作出 它们是昂贵的。在另一方面RAM便宜,并且100倍慢。

一般来说寄存器算术更快,非常优选。但也有一些情况下直接存储器运算是非常有用的。 如果你想要做的是增加了一些在内存中(而不是其他至少几百万条指令),那么一个直接存储器运算指令通常是略快于负载/添加/店。

此外,如果你正在做的一系列复杂的操作,你通常需要大量的寄存器来跟踪你在哪里,并在您的阵列结束。在旧的架构,你可以注册的真的很快因此增加的内存两位在一起,没有任何快速移动的当前寄存器的选择是非常有用的冒了出来。

是的,这是非常非常快许多使用寄存器。即使只考虑来自处理器的物理距离来注册相比PROC到存储器,可以节省通过不发送电子到目前为止,这意味着可以以较高的时钟速率运行大量的时间。

是 - 也可以典型地推/易于弹出寄存器用于调用程序,处理中断等

这只是指令集将不会允许你做这样复杂的操作:

add [0x40001234],[0x40002234]

您必须去通过寄存器。

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top