3

在 x86 中将单个内存单元设置为零的最快方法是什么?通常我这样做的方式是这样的:

C745D800000000  MOV [ebp-28], 0

正如你所看到的,它有一个非常粗的编码,因为它使用了所有 4 个字节作为常量。使用普通寄存器,我可以使用MVZE更紧凑的寄存器,但MVZE不适用于内存。

我在想也许可以清除一个寄存器,然后MOV将寄存器值存储到内存中。然后,它将是两条指令,但总共只有 5 个字节,而不是上面的一个 7 字节指令。遵循“如果它更短,它通常更快”的规则,这可能是可取的。

4

2 回答 2

5

不幸的是,您在这里写的是“直接”将存储单元归零的唯一方法。当然,异或寄存器然后将其移动到某个内存位置也可以,但我不知道这是否会更快。

如果您碰巧有一个值为零的寄存器并且您确定它,那么一定要使用它。否则,坚持使用mov [ebp-28], 0. 请记住,mem, imm已知操作数是最慢的操作数之一:如果您分析您的代码并发现这是一个瓶颈,请尝试在您的函数(或其他)开始时将寄存器初始化为零,然后在整个过程中使用它代码,作为一种预定义的常量。

于 2013-03-15T22:27:13.493 回答
2

如果您希望您的数据不在缓存中,并且您不希望很快再次访问它,那么这MASKMOVDQU可能是最快的方法。这允许您写入一个或多个字节,而不会影响周围的字节,也无需等待请求所有权请求将关联的缓存线带入内存。

本质上,写入是直接发送到内存的,而不是相反。由于 CPU 在高速缓存行大小的块中与内存交互,因此在幕后发生的事情是包含写入的高速缓存行被向下发送,以及指示哪些字节实际被更新的掩码。无论是在内存控制器、L3 高速缓存还是内存本身,要写入的字节都会与应该单独保留的字节合并。

于 2019-02-02T22:23:21.353 回答