【问题标题】:Profiling C++ threads with clock()使用 clock() 分析 C++ 线程
【发布时间】:2012-04-11 13:14:58
【问题描述】:

我正在尝试测量 gcc 线程在我的系统上的执行情况。我写了一些非常简单的测量代码,就像这样......

start = clock();
for(int i=0; i < thread_iters; i++) {
  pthread_mutex_lock(dataMutex);
  data++;
  pthread_mutex_unlock(dataMutex);
}
end = clock();

我通过 CLOCKS_PER_SEC 执行通常的减法和除法运算,以获得 100000000 次迭代的大约 2 秒的经过时间。然后我稍微更改分析代码,以便测量每个 mutex_lock/unlock 调用的单独时间。

for(int i=0; i < thread_iters; i++) {
  start1 = clock();
  pthread_mutex_lock(dataMutex);
  end1 = clock();
  lock_time+=(end1-start1);

  data++;

  start2 = clock();
  pthread_mutex_unlock(dataMutex);
  end2 = clock();
  unlock_time+=(end2-start2)
}

相同次数的迭代次数是 锁定:~27 秒 解锁:~27 秒

我明白为什么程序的总时间增加了,循环中的计时器调用次数增加了。但是系统调用的时间仍然应该少于 2 秒。有人可以帮我弄清楚我哪里出错了吗?谢谢!

【问题讨论】:

    标签: c++


    【解决方案1】:

    clock 调用还测量调用clock 并从中返回所需的时间。这会在测量中引入偏差。 IE。在clock 函数内部的某个地方,它需要一个样本。但是在运行你的代码之前,它必须从clock 的深处返回。然后,当您进行最终测量时,在那个时间样本可以被采集之前,clock 必须被调用,并且控制必须传递到该函数深处的某个地方,它实际上获得了时间。因此,您将所有这些开销作为衡量的一部分。

    您必须找出连续的clock 调用之间的时间间隔(通过对多对clock 调用进行一些采样以获得准确的平均值)。这给了你一个基线偏差:在两个时钟样本之间完全不执行任何操作需要多少时间。然后你小心地从测量中减去你的偏差。

    但致电clock 可能会干扰性能,因此您无法获得准确的答案。调用内核以获取时钟正在干扰您的 L1 缓存和指令缓存。对于像这样的细粒度测量,最好下拉到内联汇编并从 CPU 读取循环计数寄存器。

    clock 最适合在第一个示例中使用:围绕执行多次迭代的某事物进行采样,然后除以迭代次数以估计单次迭代时间。

    【讨论】:

      猜你喜欢
      • 2011-02-27
      • 2010-10-12
      • 1970-01-01
      • 1970-01-01
      • 2015-08-01
      • 2014-06-21
      相关资源
      最近更新 更多