首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >"rdtsc“之前的"cpuid”

"rdtsc“之前的"cpuid”
EN

Stack Overflow用户
提问于 2010-05-27 02:29:12
回答 3查看 4.4K关注 0票数 18

有时,我会遇到用rdtsc指令读取TSC的代码,但就在前面调用cpuid

为什么调用cpuid是必要的?我意识到这可能与具有TSC值的不同内核有关,但是当您按顺序调用这两个指令时会发生什么呢?

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2010-05-27 02:32:39

这是为了防止无序处决。从现在已从网络上消失的链接(但在它消失之前碰巧被复制到这里),本文摘自John Eckerdal的一篇题为“性能监控”的文章:

,奔腾Pro和奔腾II处理器,支持无序的执行指令,可以在您编程时以另一个顺序执行。如果不加以处理,这可能是错误的来源。

为了防止这种情况,程序员必须序列化指令队列。这可以通过在RDTSC指令之前插入一个类似CPUID的序列化指令来完成。。

票数 18
EN

Stack Overflow用户

发布于 2012-06-08 06:53:33

原因有二:

  • (帕克斯辉罗)说,当CPU看到一个CPUID操作码时,它确保执行所有前面的指令,然后在执行任何后续指令之前执行CPUID。如果没有这样的指令,CPU执行管道可能会在您想要执行的指令之前执行TSC。
  • --相当大比例的机器无法同步跨核的TSC寄存器。在你想从马嘴里读到它的时候因此,在测量TSC读数之间的间隔时,除非它们位于相同的核心上,否则引入的时间间隔实际上是随机的,但可能是恒定的(见下文)--即使在启动后不久,它也可以很容易地达到几秒(是的秒)。这有效地反映了BIOS在启动其他内核之前在单个核上运行了多长时间,另外--如果您有任何令人讨厌的节电选项--增加由不同频率运行或再次关闭的核引起的漂移。因此,如果您还没有将读取TSC寄存器的线程钉在同一个内核上,那么您需要构建某种交叉核心增量表,并知道每个TSC示例的核心id (由CPUID返回),以补偿此偏移量。这也是在RDTSC旁边可以看到CPUID的另一个原因,也是使用较新的RDTSCP时,许多OSes将核心id号存储到返回的额外TSC_AUX31:0数据中的原因。( RDTSCP可从核心i7和Athlon 64 X2获得,在所有方面都是一个更好的选择-操作系统通常会为您提供所述的核心id,原子到TSC,并防止指令重新排序)。
票数 6
EN

Stack Overflow用户

发布于 2019-01-16 09:49:48

CPUID正在序列化,防止RDTSC的无序执行.

现在,您可以安全地使用LFENCE。它被记录为在Intel CPU上的指令流(但不是存储到内存中)上序列化,现在也在AMD上,在它们的谱微代码更新之后。

https://hadibrais.wordpress.com/2018/05/14/the-significance-of-the-x86-lfence-instruction/解释了更多关于LFENCE的内容。

还请参阅https://www.intel.com/content/dam/www/public/us/en/documents/white-papers/ia-32-ia-64-benchmark-code-execution-paper.pdf以获得一种使用RDTSC(或LFENCE)远离定时区域的https://www.intel.com/content/dam/www/public/us/en/documents/white-papers/ia-32-ia-64-benchmark-code-execution-paper.pdfP的方法:

代码语言:javascript
复制
LFENCE     ; (or CPUID) Don't start the timed region until everything above has executed
RDTSC           ; EDX:EAX = timestamp
mov  ebx, eax   ; low 32 bits of start time

   code under test

RDTSCP     ; built-in one way barrier stops it from running early
LFENCE     ; (or CPUID) still use a barrier after to prevent anything weird
sub  eax, ebx   ; low 32 bits of end-start

有关RDTSC的更多信息,请参见Get CPU cycle count?,如constant_tsc和nonstop_tsc。

作为奖励,RDTSCP为您提供了一个核心ID。如果您想检查核心迁移,也可以使用RDTSCP作为启动时间。但是,如果您的CPU具有constant_tsc功能,则包中的所有核心都应该同步它们的TSC,因此在现代x86上通常不需要这样做。

您可以从CPUID获得核心ID,正如@Tony的回答所指出的那样。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/2918113

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档