问题标签 [rdtsc]
For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.
c - 为什么第一个 printf 需要更长的时间?
我在玩高精度计时器,我的第一个测试是使用 rdtsc 来测量 printf。下面是我的测试 prpgram,然后是它的输出。我注意到的是,第一次运行 printf 时,第一次打印的时间总是比后续打印的时间长约 25 倍。这是为什么?
和输出:
(作为参考,这是在 OSX 上使用 gcc 编译的)
hardware - 为什么 RDTSC 是现代处理器上的虚拟化指令?
我正在研究 RDTSC 并了解它是如何为 VirtualBox 和 VMWare 等虚拟机而虚拟化的。为什么 Intel/AMD 不厌其烦地虚拟化这条指令?
我觉得它可以很容易地用一个陷阱来模拟,它并不是一个超级常见的指令(我测试过,在禁用硬件 RDTSC 虚拟化的虚拟机中,一般使用没有明显的减速)。
但是,我知道 Intel/AMD 不会费尽心思将此指令添加到虚拟化硬件中,除非能够非常快速地执行很重要。
有谁知道为什么?
c - rdtsc,循环次数过多
我已经用 gcc 编译了这段代码,并进行了 -O0 -O1 -O2 -O3 优化。我总是得到 2000-2500 个周期。谁能解释这个输出的原因?如何度过这些周期?
第一个函数“tick”是错误的。这是对的。
另一个版本的函数“tick”
这是 -O3 的汇编代码
这是CPU
linux - 使用 RDTSC 获取 cpu 周期 - 为什么 RDTSC 的值总是增加?
我想在特定点获得 CPU 周期。我当时使用这个功能:
(编者注:"=A"
x86-64 是错误的;它选择RDX或RAX。只有在 32 位模式下,它才会选择您想要的 EDX:EAX 输出。请参阅如何从 C++ 获取 x86_64 中的 CPU 周期计数?。)
问题是它总是返回一个增加的数字(在每次运行中)。就好像它指的是绝对时间。
我是否错误地使用了这些功能?
c++ - cpp linux:关于rdtsc
我在我的代码中使用以下函数:
此函数是否返回自上次启动以来的滴答数?我在哪里可以找到有关此功能的文档?
ubuntu - 从 /sys/kernel/debug/tracing 在 Ubuntu 中协调时间
我正在尝试以编程方式从 Ubuntu 10.10 机器上的多个来源收集有关程序性能的数据。对于我所有的其他来源,我已经能够使用 RDTSC x86 指令收集它们,然后使用 gettimeofday 缩放它们以转换为绝对时间的秒数。但是,当我开始尝试将这些数据源与在 /sys/kernel/debug/tracing 中执行 sched_switch 跟踪的输出进行协调时,我遇到了一个问题,因为我看到的输出是从某个未知时间开始以秒和微秒为单位的。
我已经完成的步骤:
1.我确定Linux内核内部也使用RDTSC,但添加了一些它收集的偏移量,但我似乎没有能力检索。它也是在每个核心的基础上执行此操作的,这意味着我必须尝试所有四个核心并确定最好的一个,这似乎是解决这个问题的一个糟糕的解决方案。
2. 我尝试在打开日志记录时转换 RDTSC 时间,以查看至少转换本身是否一致(即一些恒定偏移),但规模似乎在整个运行过程中并没有保持不变。
3. clock_gettime(CLOCK_MONOTONIC, ...) 似乎有一个非常相似的值,但总是偏离一个无法例外的量(大约半秒),而且似乎也不完全一致。
如果我能够将其他数据源收集时间的方式更改为所需的时间(假设它不是性能密集型的),我应该如何收集时间以便在跟踪时间和我收集的时间之间进行协调?是否有某种方法可以将输出更改为 RDTSC,这样我就可以使用它,或者是否可以进行系统调用来获得与要跟踪的输出相同的时间?提前感谢您的帮助。
python - 在 Python 中读取 rdtsc
有没有办法在 Python 中读取 x86 CPU 上的时间戳计数器?
我知道使用rdtscp
不好,使用rdtsc
更糟。但是相信我,我真的需要那个值,或者至少是那个值的近似值。
有任何想法吗?
c++ - 如何在 GCC x86 中使用 RDTSC 计算时钟周期?
使用 Visual Studio,我可以从处理器读取时钟周期计数,如下所示。我如何对 GCC 做同样的事情?
x86 - rdtsc 的返回值是_always_ mod 10 == 0 on Atom N450
在我的 E8200 机器上,这不会发生,但在我的 Atom N450 上网本(都运行 OpenSuse 11.2)上,每当我读取 CPU 的 TSC 时,返回的值为mod 10 == 0
,即它不能被 10 整除。我正在使用 RDTSC测量有趣的代码所花费的时间的价值,但为了演示的目的,我编写了这个小程序:
(我通常使用自己的例程进行转换,但为了防止读者暗示可能存在错误,我在这里仅使用 printf() 。)
使用上面的代码,输出是(例如):
可以很容易地看出,delta 在合理的范围内变化。但显着(不是说合谋;-)是最低有效十进制数字始终为0。
我已经观察到这种现象两年多了,而 Stack Overflow 并不是我公开这个问题的第一个地址。但我还没有得到一个合理的答案。我们(我和其他人)提出的想法是
- TSC 仅每 10个周期增加一次,然后增加 10,或
- TSC 在内部正确更新,但仅每 10个周期反映到外部,或
- TSC 每个周期递增 10。
然而,这些观点都没有真正的意义。我实际上应该在 E8200 上运行一个类似的程序(当前出现故障),以查看增量的数量级是否与上述输出中的数量级相同或只有十分之一。(有志愿者吗?)
谷歌搜索没有帮助,英特尔的手册也没有。
在与其他人讨论时,没有其他人经历过同样的行为。如果它与内核有关,那么至少有 3 个版本受到影响,但是……内核与它有什么关系?
我还使用了上网本,它带有一个新的主板——意味着一个新的 CPU,所以 N450 至少有两个单独的实体必须受到影响。
我还针对时钟频率变化采取了措施(无论我将时钟固定到什么频率,值都只在预期范围内变化(如图所示)),并关闭了 HT,尽管这些实际上应该有助于获得一些其他最低有效数字,而不是阻止它们。但只是为了确定。
好吧,如果有人想在他们的机器上运行程序,命令行是(假设你将源代码保存在文件中rdtsc.s
):
为了用 gcc 前端构建它,即
您必须添加(或替换_start:
标签)main:
标签并使其成为全局标签。
[更新(2012-09-15 ~21:15 UTC):实际上我之前也可以这样做:我只是让它在 a 之前和之后取 TSC sleep(1)
,这给出了一个略大于 1,666,000,000 的增量,这表明第三个上面列表中的点是错误的。但我仍然不知道为什么我没有得到完整的精度。/更新]
c++ - rdtscp、rdtsc 之间的区别:内存和 cpuid / rdtsc?
假设我们正在尝试使用 tsc 进行性能监控,并且我们希望防止指令重新排序。
这些是我们的选择:
1: rdtscp
是一个序列化调用。它可以防止围绕对 rdtscp 的调用进行重新排序。
但是,rdtscp
仅在较新的 CPU 上可用。所以在这种情况下,我们必须使用rdtsc
. 但是rdtsc
是非序列化的,因此单独使用它不会阻止 CPU 对其进行重新排序。
所以我们可以使用这两个选项中的任何一个来防止重新排序:
2:这是对cpuid
then的调用rdtsc
。cpuid
是一个序列化调用。
3:rdtsc
这是对clobber列表中的with的调用memory
,它可以防止重新排序
我对第 3 个选项的理解如下:
进行调用__volatile__
可防止优化器删除 asm 或将其移动到可能需要 asm 结果(或更改输入)的任何指令中。但是,它仍然可以移动它以进行不相关的操作。所以__volatile__
还不够。
告诉编译器内存正在被破坏:: "memory")
. clobber 意味着 GCC 不能对"memory"
整个 asm 中的内存内容保持不变做出任何假设,因此不会围绕它重新排序。
所以我的问题是:
- 1:我的理解
__volatile__
和"memory"
正确吗? - 2:后两个调用做同样的事情吗?
- 3:使用
"memory"
看起来比使用另一个序列化指令简单得多。为什么有人会使用第三个选项而不是第二个选项?