2010-04-07 110 views

回答

32

當您鏈接到可執行文件的某個對象發生顯着變化時,會發生這種情況。例如,它獲得或丟失了一些profilable代碼行。

產生錯誤的最小情況是使用2個源文件。這裏有兩個例子源文件名爲main.c中......

/* main.c */ 
int do_stuff(int value); 

int main(int argc, const char *argv[]) 
{ 
    do_stuff(argc); 
    return 0; 
} 

和stuff.c

/* stuff.c */ 
#include <stdio.h> 

#if 0 
int more_stuff() 
{ 
    int i; 
    i = 0; 
    return i; 
} 
#endif 

int do_stuff(int value) 
{ 
    if (value > 1) { 
     printf("Value > 1\n"); 
    } else { 
     printf("Value <= 1\n"); 
    } 
    return 0; 
} 

他們做什麼並不重要。要建立他們,這裏是一個簡單的Makefile:

CFLAGS := -fprofile-arcs -ftest-coverage 
LDFLAGS := -fprofile-arcs -ftest-coverage 

testexe: main.o stuff.o 
    $(CC) $(LDFLAGS) -o [email protected] $^ 

建立makefile向上,以便在編譯main.c -> main.ostuff.c -> stuff.o最後stuff.o + main.o -> testexe。如果我們將這些C文件編譯並鏈接到-fprofile-arcs -ftest-coverage選項,那麼可執行文件會進行分析。運行可執行文件,你將得到2個輸出文件,main.gcdastuff.gcda。到現在爲止還挺好。

現在將行#if 0更改爲#if 1。 Makefile應該只會導致stuff.c重新編譯,並且可執行文件會重新鏈接。下次您運行測試可執行文件時,您將收到文件「合併不匹配」消息。 stuff.gcda文件不受影響,因爲它的對象文件已經用所有新的摘要信息重新創建。如果您重新編譯main.c並重新鏈接可執行文件,則錯誤消息將消失。

那麼可以做些什麼?我很想知道!目前我運行find . -name '*.gcda' | xargs rm每當我需要重新檢查覆蓋面,這是不是很理想。另一種解決方案是在使用分析「以防萬一」時重新編譯所有內容,但似乎過度殺傷。

+1

非常好,謝謝你的信息!很高興終於明白這裏發生了什麼。優秀的解釋。我有一個類似的解決方法 - 在運行之前刪除所有生成的文件。我現在明白了這是爲什麼起作用,但我認爲錯誤信息可能會有所改善。 – mikelong 2010-04-24 22:26:16