2012-01-26 14 views
0

自分で解決できないリンカーエラー(未定義参照)があります。 ARM用にGCC Sourcery G ++ Lite 4.5.2を使用しています。cファイルのアセンブリ要素の参照が未定義

私は多くの未定義の参照を持っており、ほとんどすべてアセンブリファイルを参照しています。ここでは一例:

私はcpu.sxという名前のアセンブリファイルで定義された "_CPU_MmuConfigGet" があります。

.global _CPU_MmuConfigGet 
CPU_MmuConfigGet: 
mrc p15,0,r0,c1,c0,0   
mov pc,lr 

mmu.cという名前の交流ファイルでは、CPU_MmuConfigGetが呼び出されます。

最後に
#include "cpu.h" 
U32 MMU_ConfigGet(void) { 
    return CPU_MmuConfigGet(); 
} 

ヘッダファイルcpu.hにCPU_MmuConfigGetが宣言されます。

extern U32 CPU_MmuConfigGet(void); 

テーマツリーファイルsは以下のフォルダに置かれています。

Base/Common/src/mmu.c  
Base/Common/inc/cpu.h  
Base/Common/src/cpu.sx  

私は、ネット上の赤い異なるポストから、私は(試みたが、私の問題を解決していなかった)CPU_MmuConfigGetにアンダーラインを追加しなければならないことがわかりました。私はまたいくつかのフォーラムで、リンクするとオブジェクトファイルの順序は重要だが、他のフォーラムでは、オブジェクトの順序は重要ではない(私はここで混乱している)。私はmmu.cのアセンブリバージョンを見るために-Sパラメータを試しましたが、それは私のエラーについての手がかりを見つけるのを助けませんでした...

ここに私が使用したコンパイラコマンドですこのヘルプ)...間違っているものを見つける:

arm-none-eabi-gcc -c -g3 -gdwarf-2 -H -o"mmu.o" -Wall -Wa,-adhlns="mmu.o.lst" 
-fmessage-length=0 -MMD -MP -MF"mmu.d" -MT"mmu.d" -fpic -march=armv4t -mcpu=arm7tdmi -mlittle-endian 
-I"../../OS/ngos/hw/cdb89712" -I"../../OS/ngos" -I"../../OS/ngos/include" -I"../../OS/ngos/rtos/ucosii" 
-I"C:/Program Files/CodeSourcery/Sourcery G++ Lite/lib/gcc/arm-none-eabi/4.5.2/include" -I"./" 
-I"src/" -I"../../Common/inc" -I"../../OS/uCOS-II/SOURCE" -I"../../OS/ngos/drivers/arm" 
-I"../../OS/ngos/include/ngos" -I"../../OS/ngip/include" -I"../../OS/ngip/include/ngip" 
-I"../../Dvcscomponent/Inc" -I"../../Inc" "../../Common/src/mmu.c" 
. ../../Common/inc/base.h 
. ../../Common/inc/hw7312.h 
. ../../Common/inc/serial.h 
.. ../../Common/inc/base.h 
.. ../../Common/inc/hw7312.h 
. ../../Common/inc/base.h 
. ../../Common/inc/cpu.h 
.. ../../Common/inc/base.h 
.. ../../Common/inc/hw7312.h 
. ../../Common/inc/mmu.h 

今組立コマンド:エラーと

arm-none-eabi-gcc -g3 -gdwarf-2 -x assembler-with-cpp -Wa,-adhlns="cpu.o.lst" -Wall -c 
-fmessage-length=0 -MMD -MP -MF"cpu.d" -MT"cpu.d" -fpic -o"cpu.o" -march=armv4t -mcpu=arm7tdmi -mlittle-endian 
-I"../../OS/ngos/hw/cdb89712" -I"../../Common" -I"../../OS/ngos/drivers/arm" 
"../../Common/src/cpu.sx" 

が最後にリンクするコマンド:

arm-none-eabi-gcc -fpic -mcpu=arm7tdmi -T".\linker.ld" -Wl,-Map,BootLoad.map -g3 -gdwarf-2 -o "BootLoad.elf" 
InitMain.o tsk_main.o ecp.o memalloc.o tsk_ecp.o firmdesc.o crc.o flash.o eth.o firmflash.o 
firmdest.o bcfg.o bootdownload.o cinit.o serial.o cpu.o mmu.o ngucos.o cdbini.o cs712sio.o 
cs712eth.o ../../OS/ngos/lib/rtstub/arm/gcc/libngosd4m32l.a ../../OS/ngip/lib/rtstub/arm/gcc/libngipd4m32l.a 
mmu.o: In function `MMU_ConfigGet': 
C:\Working\SF2100-0074-BootLoaderMezz\Base\NexGen\BootLoader/../../Common/src/mmu.c:28: undefined reference to `CPU_MmuConfigGet' 

私は誰かが何か提案をしている、私はそれらを聞くことを嬉しく思います!

ありがとうございます!

+0

先頭のアンダースコアを使用してアセンブリソースにシンボルを定義します。これは、先例のアンダースコアを使用するAppleの愚かな慣習です。それ以外のGNU環境では使用されません。 –

+0

この発言をお寄せいただきありがとうございます。先頭のアンダースコアの有無に関わらず、私はまだリンクエラーが発生していることに気付きました。私は先頭のアンダースコアの言葉を入れて、 "先行するアンダースコアを追加してみてください"のような答えを避けて、私がすでにこれを試したことを説明しなければならない... –

+0

提案はありません?まだここにはまった。 extern U32 CPU_MmuConfigGet(void)asm( "CPU_MmuConfigGet");外部呼び出しを変更するなど、他のいくつかのことを試してみてください。ファイルを手作業で(メイクファイルなしで)コンパイルする、ファイルの場所を変更する...など何も見つかりませんでした! –

答えて

1

最後に、cpu.sxのリスティングを参考にして、ファイルの一部が「見つからない」ことに驚きました。ファイルに別のアセンブリファイルがインクルードされていることがわかりました。この組み込みファイルは...

.end 

ディレクティブによって終了されました。

私はこの指令を削除し、プロジェクトをコンパイルしました。

0

問題は、ソースにはいくつかの場所で先頭のアンダースコアがあるが、他の場所ではないことが明らかです。 には、そのツールチェインを使用する必要がありますが、好きな場合は可能ですが、一貫している必要がありますが、が必要です。

さらに小さなアセンブラファイルをすべて削除し、Cファイルにアセンブラを挿入する必要がありますか?

など。

int CPU_MmuConfigGet() 
{ 
    int config; 
    asm ("mrc p15,0,%0,c1,c0,0" : "=r" (config)); 
    return config; 
} 

この小さな機能は、すべてのことリンカナンセンスを隠し、あなたのプロジェクトツリーをクリーンアップして、あなたのメイクファイル、およびコンパイラはそれができるならば、他の機能にそれをインライン化しても自由です。

コンパイラマニュアルには、挿入をアセンブルするための入力と出力を指定する完全な詳細があります。彼らは最初はちょっと混乱しますが、長期的にはそれに見合う価値があります。

もちろん、アセンブラファイルがまだ必要な場所 - crt0.sなどがあります。

+0

この特定のケースでは、インラインアセンブリを使用するのは複雑でしたが、これは同様の問題を抱えている他の人にとっては良い提案です... –