我目前正在尝试了解 x86_64(特别是我的 Intel(R) Core(TM) i3-8145U CPU @ 2.10GHz 处理器)上某些循环的性能属性。具体来说,在循环体内部添加一个额外的读取内存指令几乎可以使性能翻倍,而细节并不是特别重要。
我一直在使用一个测试程序,它由两个主要部分组成:一个测试循环和一个被测函数。测试循环运行被测函数 2 32次,一次将每个有符号的 32 位整数作为参数(按从INT_MIN到 的顺序INT_MAX)。被测函数(名为body)是一个小函数,用于检查是否使用预期参数调用它,否则将错误记录在全局变量中。测试程序涉及的内存量足够小,所有东西都可能适合 L1 缓存。
为了消除可能由编译器行为引起的任何速度差异,我用汇编语言编写了两个有问题的函数(我clang用作汇编程序),并被迫从固定地址(这种测试循环的性能通常受与对齐或缓存相关的影响所支配,因此使用固定地址将消除任何与更改无关的对齐效果或缓存效果)。
这是反汇编的测试循环(它需要函数的地址在 中循环%rdi):
401300: 53 push %rbx
401301: 55 push %rbp
401302: 51 push %rcx
401303: 48 89 fd mov %rdi,%rbp
401306: bb 00 00 00 80 mov $0x80000000,%ebx
loop:
40130b: 89 df mov %ebx,%edi
40130d: ff d5 callq *%rbp
40130f: 83 c3 01 add $0x1,%ebx
401312: 71 f7 jno 40130b <loop> …Run Code Online (Sandbox Code Playgroud)