热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

使用rdtsc对intel进行汇编器基准测试给出了奇怪的答案,为什么?

如何解决《使用rdtsc对intel进行汇编器基准测试给出了奇怪的答案,为什么?》经验,为你挑选了1个好方法。

前一段时间,我问了一个关于堆栈溢出的问题,并展示了如何在C++中执行rdtsc操作码.我最近使用rdtsc创建了一个基准函数,如下所示:

inline unsigned long long rdtsc() {
  unsigned int lo, hi;
  asm volatile (
     "cpuid \n"
     "rdtsc" 
   : "=a"(lo), "=d"(hi) /* outputs */
   : "a"(0)             /* inputs */
   : "%ebx", "%ecx");     /* clobbers*/
  return ((unsigned long long)lo) | (((unsigned long long)hi) <<32);
}

typedef uint64_t (*FuncOneInt)(uint32_t n);
/**
     time a function that takes an integer parameter and returns a 64 bit number
     Since this is capable of timing in clock cycles, we won't have to do it a
     huge number of times and divide, we can literally count clocks.
     Don't forget that everything takes time including getting into and out of the
     function.  You may want to time an empty function.  The time to do the computation
     can be compute by taking the time of the function you want minus the empty one.
 */
void clockBench(const char* msg, uint32_t n, FuncOneInt f) {
    uint64_t t0 = rdtsc();
    uint64_t r = f(n);
    uint64_t t1 = rdtsc();
    std::cout <uint64_t empty(uint32_t n) {
    return 0;
}

uint64_t sum1Ton(uint32_t n) {
    uint64_t s = 0;
    for (int i = 1; i <= n; i++)
        s += i;
    return s;
}

代码是使用编译的

g++ -g -O2

我可以理解是否由于中断或其他条件导致了一些错误,但考虑到这些例程很短,并且选择n很小,我认为我可以看到实数.但令我惊讶的是,这是两次连续运行的输出

empty n=100 elapsed=438
Sum 1 to n=100  elapsed=887

empty n=100 elapsed=357
Sum 1 to n=100  elapsed=347

一直以来,空函数显示它比预期更多.

毕竟,进入和退出该功能只涉及一些指令.真正的工作是在循环中完成的.别担心方差很大.在第二次运行中,空函数声称需要357个时钟周期,总和需要更少,这是荒谬的.

怎么了?



1> Peter Cordes..:

一直以来,空函数显示它比预期更多.

你有cpuid定时间隔. cpuid根据Agner Fog的测试,英特尔Sandybridge系列CPU需要100至250个核心时钟周期(取决于您忽略设置的输入).(https://agner.org/optimize/).

但是你没有测量核心时钟周期,你正在测量RDTSC参考周期,这可能会明显缩短.(例如我的Skylake i7-6700k在800MHz时空闲,但参考时钟频率为4008 MHz.)请参阅获取CPU周期数?因为我尝试了一个规范的答案rdtsc.

首先预热CPU,或者pause在另一个核心上运行忙碌循环以使其保持最大值(假设它是台式机/笔记本电脑的双核或四核,其中所有核心频率都锁定在一起.)


别担心方差很大.在第二次运行中,空函数声称需要357个时钟周期,总和需要更少,这是荒谬的.

这种效果是否也一致?

也许你的CPU在打印第3行消息期间/之后达到全速,使最后一个定时区域运行得更快?(为什么这个延迟循环在没有睡眠的几次迭代后开始运行得更快?).

IDK在eax和ecx之前cpuid可以有多大的不同垃圾效果.替换它lfence以消除它并使用更低的开销方式来序列化rdtsc.


推荐阅读
  • 本文概述了JNI的原理以及常用方法。JNI提供了一种Java字节码调用C/C++的解决方案,但引用类型不能直接在Native层使用,需要进行类型转化。多维数组(包括二维数组)都是引用类型,需要使用jobjectArray类型来存取其值。此外,由于Java支持函数重载,根据函数名无法找到对应的JNI函数,因此介绍了JNI函数签名信息的解决方案。 ... [详细]
  • IhaveWindows8.1prowithanAMDprocessor.IinstalledtheAndroidSDKandEclipse.Itworksbut ... [详细]
  • 本文主要解析了Open judge C16H问题中涉及到的Magical Balls的快速幂和逆元算法,并给出了问题的解析和解决方法。详细介绍了问题的背景和规则,并给出了相应的算法解析和实现步骤。通过本文的解析,读者可以更好地理解和解决Open judge C16H问题中的Magical Balls部分。 ... [详细]
  • 前景:当UI一个查询条件为多项选择,或录入多个条件的时候,比如查询所有名称里面包含以下动态条件,需要模糊查询里面每一项时比如是这样一个数组条件:newstring[]{兴业银行, ... [详细]
  • 本文介绍了一个题目的解法,通过二分答案来解决问题,但困难在于如何进行检查。文章提供了一种逃逸方式,通过移动最慢的宿管来锁门时跑到更居中的位置,从而使所有合格的寝室都居中。文章还提到可以分开判断两边的情况,并使用前缀和的方式来求出在任意时刻能够到达宿管即将锁门的寝室的人数。最后,文章提到可以改成O(n)的直接枚举来解决问题。 ... [详细]
  • Java在运行已编译完成的类时,是通过java虚拟机来装载和执行的,java虚拟机通过操作系统命令JAVA_HOMEbinjava–option来启 ... [详细]
  • 本文详细介绍了如何使用MySQL来显示SQL语句的执行时间,并通过MySQL Query Profiler获取CPU和内存使用量以及系统锁和表锁的时间。同时介绍了效能分析的三种方法:瓶颈分析、工作负载分析和基于比率的分析。 ... [详细]
  • 本文介绍了深入浅出Linux设备驱动编程的重要性,以及两种加载和删除Linux内核模块的方法。通过一个内核模块的例子,展示了模块的编译和加载过程,并讨论了模块对内核大小的控制。深入理解Linux设备驱动编程对于开发者来说非常重要。 ... [详细]
  • 通过Anaconda安装tensorflow,并安装运行spyder编译器的完整教程
    本文提供了一个完整的教程,介绍了如何通过Anaconda安装tensorflow,并安装运行spyder编译器。文章详细介绍了安装Anaconda、创建tensorflow环境、安装GPU版本tensorflow、安装和运行Spyder编译器以及安装OpenCV等步骤。该教程适用于Windows 8操作系统,并提供了相关的网址供参考。通过本教程,读者可以轻松地安装和配置tensorflow环境,以及运行spyder编译器进行开发。 ... [详细]
  • x86 linux的进程调度,x86体系结构下Linux2.6.26的进程调度和切换
    进程调度相关数据结构task_structtask_struct是进程在内核中对应的数据结构,它标识了进程的状态等各项信息。其中有一项thread_struct结构的 ... [详细]
  • 如何解决《volatile语句的负载障碍在哪里?》经验,为你挑选了1个好方法。 ... [详细]
  • github项目地址https:github.comlinux-nvmenvme-cli下载:wgethttps:codeload.github.comlin ... [详细]
  • 这是原文链接:sendingformdata许多情况下,我们使用表单发送数据到服务器。服务器处理数据并返回响应给用户。这看起来很简单,但是 ... [详细]
  • 本文讨论了一个关于cuowu类的问题,作者在使用cuowu类时遇到了错误提示和使用AdjustmentListener的问题。文章提供了16个解决方案,并给出了两个可能导致错误的原因。 ... [详细]
  • Imtryingtofigureoutawaytogeneratetorrentfilesfromabucket,usingtheAWSSDKforGo.我正 ... [详细]
author-avatar
残破的前进
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有