【问题标题】:Why calls of main is more than once in gprofile profile?为什么在 gprofile 配置文件中不止一次调用 main?
【发布时间】:2013-12-16 10:50:34
【问题描述】:

这是我从个人资料数据中得到的。我不明白为什么 main 调用不止一次?

   %   cumulative   self              self     total           
  time   seconds   seconds    calls  Ts/call  Ts/call  name    
  0.00      0.00     0.00       96     0.00     0.00  fun
  0.00      0.00     0.00       33     0.00     0.00  __x86.get_pc_thunk.bx
  0.00      0.00     0.00       27     0.00     0.00  main

更奇怪的是,我的代码是这样的

 void foo() {
  foo1();
  if ( a condition) foo2();
}

%   cumulative   self              self     total    
 time   seconds   seconds    calls  us/call  us/call  name    
 54.55      0.06     0.06     6115     9.81     9.81  foo1
 18.18      0.08     0.02   252520     0.08     0.08  cmp_by_weight
  9.09      0.09     0.01   865699     0.01     0.01  foo2

为什么 foo2() 的调用次数比 foo1() 的调用次数多?

我在编译时使用了 -pg 选项。然后使用 gprof -a exe gmon.out 从 gmon.out 生成配置文件。

Calls:是函数被调用的总次数。如果函数从未被调用,或者无法确定调用次数(可能是因为函数未在启用分析的情况下编译),则调用字段为空。

【问题讨论】:

  • 很奇怪。 exe 和 gmon 文件之间可能存在一些 incostintencies。尝试删除这两个文件并重新构建。
  • @egur 我已经这样做了,但是得到了相同的结果。
  • 你能发布完整的src代码吗?你的程序是 fork() 吗?
  • @tristan 完整的代码有点长。但我保证它是一个单线程程序并且没有fork()。

标签: c gprof


【解决方案1】:

谁知道? -pg 导致 gcc 在每个例程 B 的序言中插入代码。该代码查看堆栈以试图找出调用者 A 是谁。然后它增加 A 调用 B 的次数。

您可以看到这个过程很容易混淆。 它通过查找相当于链接器映射(当然是散列)的地址来定位例程。 如果该映射与实际代码之间存在任何类型的不匹配,则结果将比通常情况下更没有意义。

看,如果您想了解如何让代码运行得更快,here's the method I use

如果您只是出于某种原因尝试运行分析器,有很多选择,包括oprofileZoom 等。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-04-23
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多