2011-06-21 163 views
4

我使用Linux和我有以下文件:未定義的引用函數

main.c, main.h 
fileA.c, fileA.h 
fileB.cpp, fileB.h 

F1()fileB.h聲明和fileB.cpp定義的功能。我需要使用的功能fileA.c,所以我聲明瞭功能

extern void F1(); 

fileA.c

然而,在編譯過程中,我得到了錯誤

fileA.c: (.text+0x2b7): undefined reference to `F1' 

有什麼不對?

謝謝。

ETA:多虧了我已經收到了答案,我現在有以下幾點:

在fileA.h,我有

#include fileB.h 
#include main.h 

#ifdef __cplusplus 
extern "C" 
#endif 
void F1(); 

在fileA.c,我有

#include fileA.h 

在fileB.h,我有

extern "C" void F1(); 

在fileB.cpp,我有

#include "fileB.h" 

extern "C" void F1() 
{ } 

不過,我現在有錯誤

fileB.h: error: expected identifier or '(' before string constant 

回答

15

如果你真的編譯fileA.c爲C,而不是C++,那麼你需要確保該功能具有適當的C兼容鏈接。

您可以使用extern關鍵字的特例來做到這一點。雙方在聲明和定義:

extern "C" void F1(); 
extern "C" void F1() {} 

否則的C連接器將尋找那才真的有一些錯位的C++名稱存在的功能,並且不支持的調用約定。 :)

不幸的是,雖然這是你必須做的C++,the syntax isn't valid in C。您必須使extern僅對C++代碼可見。

因此,一些預處理魔術:

#ifdef __cplusplus 
extern "C" 
#endif 
void F1(); 

不完全是漂亮,但它是你付出的共享兩種語言的代碼之間的頭的價格。

+0

所以現在我有extern「C」void F1();和extern「C」void F1(){}分別在我的fileB.h和fileB.cpp中,還有extern「C」void F1();在fileA.c中。但是在編譯期間,我得到了錯誤「fileB.h:error:expected identifier」或「(」在字符串常量之前「,」fileA.c:錯誤:預期的標識符或「(」在字符串常量之前「,還有」fileA.c :warning:隱式聲明函數「F1」。「 – Rayne

+0

@Rayne:糟糕,因爲C代碼[不會接受它](http://www.ideone.com/EB3Iz)。 –

+0

@Rayne:看看我的編輯。 –

-1

fileA.c需要還包括fileA.h我相信。

+0

它已包含在內。 – Rayne

+0

包含失敗在編譯時提供聲明錯誤,而不是在鏈接時定義錯誤。 –

4

也許,使用

extern "C" void F1(); 
5

爲了能夠從C源代碼中調用C++函數你neeed給予相應linkage specification

指定聯動規範的格式爲

extern "type_of_Linkage" <function_name> 

所以你的情況,你應該用:

extern "C" void F1(); 
2

fileA.c不能包含fileB.h(通過fileA.h),因爲C編譯器不知道extern「C」是什麼意思,所以它會抱怨它在字符串之前看到一個標識符。不要試圖將fileB.h包含在fileA.c或fileA.h中。其不需要