2013-04-29 18 views
1

我在編譯和鏈接用匯編語言編寫的庫與我的C++程序代碼時遇到了一些麻煩。在我的情況下,它是使用avr-gcc套件的AVR微控制器,但我想這個問題一般適用於GCC。GCC鏈接/符號名稱與C++和彙編文件混在一起

我可以得到的.o從C++源代碼和彙編建文件,但將它們連接提供了錯誤:

> avr-gcc -mmcu=attiny84 -lm -o obj\AvrTest.elf obj\Main.o obj\i2cmaster.o 
obj\Main.o: In function `main': 
Main.cpp:(.text+0x0): undefined reference to `i2c_init()' 

這裏的尤伯杯簡單Main.cpp代碼:

#include "i2cmaster.h" 
void main() { 
    i2c_init(); 
    while (true) { 
    } 
} 

i2cmaster.h定義功能原型如下:

extern void i2c_init(void); 

而在組合呃文件,i2cmaster.S,該功能是:

.global i2c_init 
.func i2c_init 
i2c_init: 
cbi SDA_DDR,SDA  ;release SDA 
cbi SCL_DDR,SCL  ;release SCL 
cbi SDA_OUT,SDA 
cbi SCL_OUT,SCL 
ret 
.endfunc 

的鏈接似乎是一個沒有腦子 - 但我得到的引用錯誤。我注意到了Main.cpp產生的彙編代碼出來是這樣的:

.global main 
.type main, @function 
main: 
rcall _Z8i2c_initv 
.L2: 
rjmp .L2 
.size main, .-main 

我懷疑的問題是,i2c_init變得_Z8i2c_initv通過一些名字改編過程中,我不明白,這_Z8i2c_initv可以不再與匹配i2cmaster.o目標文件中未被修復的i2c_init符號。

有沒有人瞭解編譯過程,以及如何在編譯/彙編期間抑制它,以便這些模塊可以相互交談?或者我可能做錯了什麼?

回答

4

好的,解決了。顯然,符號修改是一個C++的事情,並且i2c庫沒有設置爲正確使用C++。能夠使用以下方法修復它:

extern "C" { 
    #include "i2cmaster.h" 
}; 
void main() { 
    i2c_init(); 
    while (true) { 
    } 
} 
+1

爲什麼在編寫C++時爲您的問題C添加標籤? – 2013-04-29 05:37:30

+0

我在這個程序中沒有使用任何C++特性,所以認爲它等於C. – QuadrupleA 2013-04-29 06:36:36

+0

不是。 C不是C++的子集。 – 2013-04-29 12:21:24