5

我正在尝试在 x86-64 处理器上分析代码的执行时间。我指的是这份英特尔白皮书,并且还通过其他 SO 线程讨论了在此处此处使用 RDTSCP 与 CPUID+RDTSC 的主题。

在上面提到的白皮书中,使用 CPUID+RDTSC 的方法被称为不可靠的,并且也使用统计数据证明了这一点。

CPUID+RDTSC 不可靠的原因可能是什么?

此外,同一白皮书中的图 1(最小值行为图)和图 2(方差行为图)中的图表具有“方波”模式。是什么解释了这种模式?

4

2 回答 2

4

我认为他们发现测量间隔内的 CPUID 会导致总时间的额外变化。他们在3.2 使用 RDTSCP 指令的改进CPUID中提出的修复强调了这样一个事实,即当他们使用/RDTSC启动和RDTSCP/CPUID停止时,时间间隔内没有 CPUID 。

也许他们可以在执行 CPUID 之前确保 EAX=0 或 EAX=1,以选择要读取的 CPUID 数据叶 ( http://www.sandpile.org/x86/cpuid.htm#level_0000_0000h ),以防占用 CPUID 时间取决于您进行的查询。除此之外,我不确定为什么会这样。

或者更好的是,使用lfence而不是cpuid序列化 OoO exec 而不是完整的序列化操作。


请注意,英特尔白皮书中的内联汇编很糟糕:mov如果您使用正确的输出约束(如"=a"(low), "=d"(high). 请参阅如何从 C++ 获取 x86_64 中的 CPU 周期计数?为了更好的方法。

于 2018-12-24T01:22:47.887 回答
2

CPUID+RDTSC 不可靠的另一个原因是由于 VM 侧信道攻击。

在VM内部运行CPUID指令会导致VM EXIT,这是发生的,因此VM将按照自己的意愿处理CPUID并操作CPUID指令。
执行此操作会增加额外的时间,并且使用 RDTSC 将返回“高”值,因为“整个 VM CPUID 操作”是在该时间执行的。
然后可以使用此值来检测我们是否在 VM 内部运行。

可以扩展或虚拟化 TSC 的 VM 可以防止这种行为,从而使 RDTSC 不可靠

检测 VM 退出开销

于 2019-01-04T00:52:51.097 回答