使用英特尔最后分支记录的开销是多少?

时间:2013-02-03 08:07:47

标签: x86 intel branch-prediction

Last Branch Record是指寄存器对(MSR)的集合,用于存储与最近执行的分支相关的源和目标地址。如果您感兴趣,http://css.csail.mit.edu/6.858/2012/readings/ia32/ia32-3b.pdf文档会提供更多信息。

  • a)有人可以知道LBR会减慢程序执行程序的速度 - CPU和IO密集型吗?
  • b)当LBR跟踪开启时,是否会关闭分支预测?

2 个答案:

答案 0 :(得分:10)

论文Intel Code Execution Trace Resources(由Arium工作人员,Craig Pedersen和Jeff Acampora撰写,2012年4月29日)列出了三种分支追踪变体:

  • DebugCtlMSR中的最后一个分支记录(LBR)标志以及相应的LastBranchToIP和LastBranchFromIP MSR以及LastExceptionToIP和LastExceptionFromIP MSR。

  • 分支跟踪存储(BTS),使用缓存为RAM或系统DRAM。

  • 架构事件跟踪(AET)从XDP端口捕获并存储 外部连接的目标探针。

如第2页所述, LBR 在MSR中保存信息,"不会妨碍任何实时性能,"但仅适用于非常短的代码("有效的跟踪显示非常浅,通常只能显示数百条指令。")。仅保存有关4-16个分支的信息。

BTS 允许捕获多对分支"从"和"到" s,并将它们存储在缓存中(Cache-as-RAM, CAR)或系统DRAM。在CAR的情况下,跟踪深度/长度受高速缓存大小(和一些常数)的限制;具有DRAM走线长度几乎是无限的。由于额外的内存存储,本文估计BTS的开销从20%到100%。 Linux上的BTS易于使用建议的perf branch record(尚未在香草中)或btrax projectperf branch演示提供了一些关于BTS组织的提示:有BTS缓冲区,其中包含"来自","到"字段和"预测标志"。因此,使用BTS时不会关闭分支预测。此外,当BTS缓冲区填满最大大小时,会产生中断。内核中的BTS处理模块(perf_events子系统或btrax内核模块)应该在发生此类中断时将数据从BTS缓冲区复制到其他位置。

因此,在BTS模式下,有两个开销来源:缓存/存储器存储和来自BTS缓冲区溢出的中断。

AET 使用外部代理来保存调试和跟踪数据。此代理通过扩展调试端口(XDP)连接,并与目标探测器(ITP)连接。 AET和#34的开销会对系统性能产生重大影响,这可能会高出几个数量级。根据这篇论文,因为AET可以生成/捕获更多类型的事件。但收集的数据存储在调试平台外部。

论文"摘要"说: 

  

LBR 没有开销,但非常浅(4-16个分支位置,具体取决于   在CPU上)。跟踪数据在重置后立即可用。

     

BTS 更深入,但对CPU性能和要求有影响   板载RAM。初始化CAR后即可获得跟踪数据。

     

AET 需要特殊的ITP硬件,并非所有CPU都可用   架构。它具有将跟踪数据存储在板外的优点。

答案 1 :(得分:1)

这是一个古老的问题(也有一个古老的答案),但它确实出现在今天的搜索中。

在 2021 年,您希望用于硬件跟踪的是英特尔® 处理器跟踪 (IPT)。
请记住,问题显然是关于 Intel/AMD 台式机 CPU。 AFAIK 有针对 ARM CPU 的类似解决方案,此处未介绍。

我已经使用自定义驱动程序在 Windows 中使用了 LBR 和 IPT 设置,而后者是迄今为止开销最少的。以两位数或更少百分比的方式进行流程跟踪。

也在 anwear 说:

<块引用>

LBR 没有开销,..

技术上是正确的,但说不切实际,因为开销是在实际读取存储寄存器时出现的。通常,您会将其设置为在每个分支记录上中断。因此,我们讨论的是通过陷阱/单步标志激活线程的每个分支(调用、jmp、jcc、int 等)指令处理中断/异常/陷阱的开销。

IPT 的最大缺点是它仅在 Intel CPU 上可用,而 LBR 功能也被 AMD CPU 支持。

另外不幸的是 AFAIK(我上次检查过)任何商业 VM 软件尚不支持 IPT 功能。这意味着您很可能只能在直接硬件上进行 IPT 会话。除非您真的想在 VM 中进行跟踪,否则这没什么大不了的。就此而言,LBR 可能具有相同的限制。

某些 Linux 具有对 IPT 的本机内核支持。 Windows 的一个很好的起点是 Alex Ionescu 的 WinIPT 项目:
https://ionescu007.github.io/winipt/