2012-04-22 11 views
0

2つのソースファイルがあります.1つはアセンブリで、もう1つはcです。アセンブリには、cソース内の静的文字列への参照が含まれています。私はcソースから呼び出されたアセンブリ内の関数を定義し、ヒッチがなくても正常に動作します。しかし、アセンブリからprintfを呼び出して、引数としてCソースファイルの文字列を渡そうとすると、出力が文字化けするか、まったく出力されません。アセンブリソースが引数を正しく渡すことができません

nasmを使用してelf32-i386にアセンブリをコンパイルし、gccを使用してcファイルをコンパイルします。私はデバッグ情報の有無にかかわらず試してみましたが、幸いにも同じ結果が得られました。

main.s:

SECTION .text 

global s_func 
extern c_str 
extern printf 

s_func: 
    sub esp, 4 
    mov dword [esp], c_str 
    call printf 
    add esp, 4 
    ret 

はmain.cの:

#include <stdio.h> 
const char* c_str = "Sup."; 
extern void s_func(void); 

int main(void) 
{ 
    printf(c_str); //prints as expected 
    s_func(); //weird stuff 
} 

のMakefile:

main : main.o main.s.o 
    gcc main.o main.s.o -o main 

main.o : 
    gcc -g -c main.c -o main.o 
main.s.o : 
    nasm -f elf main.s -o main.s.o 

ここではその一部だ。ここ

は、単純なソースファイルがありますあなたがこれらを集めたら、私を得る2つのファイルがオブジェクトにリンクされていれば、printfの呼び出しがどちらのソースでも同じであることがわかります。コードセグメントは同じで、c_strには両方のアセンブリリストに同じアドレスが含まれています。 main.cの中

コール:main.sで

printf(c_str); //prints as expected 
80483ed: a1 14 a0 04 08   mov 0x804a014,%eax 
80483f2: 89 04 24    mov %eax,(%esp) 
80483f5: e8 06 ff ff ff   call 8048300 <[email protected]> 

コール

08048410 <s_func>: 
8048410: 83 ec 04    sub $0x4,%esp 
8048413: b8 14 a0 04 08   mov $0x804a014,%eax 
8048418: 89 04 24    mov %eax,(%esp) 
804841b: e8 e0 fe ff ff   call 8048300 <[email protected]> 
8048420: 83 c4 04    add $0x4,%esp 
8048423: c3      ret  

は、たぶん私はいくつかのレジスタを保存することとしていますか?私はs_func上で通常のスタックフレームをセットアップしましたが、それはまだ失敗します。

+1

値の代わりにc_strのアドレスをプッシュしているようです。デバッガのコードをステップ実行します。 –

+0

c_strは、そうでなければならないポインタです。それはまったく同じです。 $記号は意味がありますか? – chaz

+0

main.sのコードがソースコードと一致しません。元のコードはeaxをロードしませんでした。何かが足りない。多分あなたは間違ったコードを見ているでしょう。 –

答えて

0

オブジェクトファイルをリンクする際に問題があると思います(アセンブリでの印刷のため)。

私は最良の方法は、Cライブラリのprintfを使用する関数を含むGASアセンブリを作成し、次に "as"コマンドを使ってファイルをアセンブルすることだと思います。

次に、gccコンパイラを使用してcコードをコンパイルし、GASで作成したオブジェクトファイルを次のコマンドを使用して1行にリンクします。

GAS作成したオブジェクトファイルがmain_s.oであれば、

gcc main_c.c main_s.o -o main 

だから、gccが最初main_c.cのオブジェクトフォーマットを作成するには、その後main_c.oとmain_s.oの両方をリンクし、それがcurrectリンクエルフを与えますファイル。

+0

いいえいいえ私はそれを考え出しました、とにかくありがとう^^ – chaz

+0

はい、私はそれを得ました。問題ない.. – Mohanraj

関連する問題