2016-11-17 4 views
-1

NASMアセンブリ言語の文字列argv [1]の長さを数えようとしています。私は正しい道にいると思う。私はargv [1]のアドレスをeaxに登録するように移動しましたが、今はバイト単位で移動してヌル文字列ターミネータと比較したいと思います。アセンブリー(NASM)の文字列を繰り返し処理する

私はコードを実行するたびにヌル比較でsegfaultsを実行します。メモリのインデックスを正しく取得できませんか?

*免責事項:これは大きな宿題の一部です。いくつかのヒントとGDBの助けを借りた後

segment .bss 

N: resd 1     ;counter for size of argv[1] 

segment .text 
    global asm_main 

asm_main: 
    enter 0,0    ;setup 
    pusha     ;save all registers 

    mov eax, dword [ebp+8] ;argc to eax 

    mov ebx, dword [ebp+12] ; address of argv to ebx 
    mov eax, dword [ebx+4] ; address of argv[1] to eax 

    mov [N], dword 0  ; N = 0 

    .loop: 

    add eax, [N]   ; advance index by N 
    cmp eax, dword 0  ; check for end of string 
    je .endloop   ; break out of the loop if we're done 


    add [N], dword 1  ; N++  

    jmp .loop    ; loop back for next char 

    .endloop: 

popa 
mov eax, 0 
leave 
ret 
+1

実際にどの命令がセグメンテーションされますか? 'add eax、[N]'は固定アドレスから読み込みますので、最初にsegfaultしなければsegfaultしないでください。デバッガを使用してシングルステップを実行し、障害が発生したときにregs/memの内容を確認します。 –

+1

ここで最も明白な問題は、文字列を読むことが決してないことです。ポインタを増分してゼロと比較するだけです。 (そして、 '[N]'が直線的に増加するので、あなたは幾何級数的にeaxを増やします。) –

+0

これはcmp行で消滅します。あなたが正しいです、上記の行は、文字そのものではなく、アドレス(うまくいけば、文字のアドレス)と期待値を比較します。私はcmp [eax]、dword 0を持つべきですか? – Eric

答えて

3

、ループは次のようになります。

mov [N], dword 0  ; N = 0 

    .loop: 

    cmp [eax], byte 0  ; check for end of string 
    je .endloop  

    add eax, dword 1  ; advance index by 1 byte 
    add [N], dword 1  ; N++  

    jmp .loop    

    .endloop: 

指数は愚かだったインクリメントするNを使用しました。私は1だけインクリメントする必要がありました。

+2

別途カウンターは必要ありません。ループの後で、 'sub eax、start_of_string'を実行することができます。 (あなたがそれを避けることができれば、ループカウンタを決してメモリに保持しないでください。本当に遅いです。あなたのコードは、Nをレジスタに入れたままにした場合(あるいは完全に避けた場合)よりもほとんどのインテルCPUでほぼ正確に6倍遅くなります。インテル®SnBファミリのCPUではストア/リロードの往復をループで実行される依存関係チェインに、ストア転送のレイテンシは5サイクルになります)。 –

+2

あなたが使用するデータのサイズを知っていることを感謝しますが、JFYI: 'add eax、dword 1'はサイズ指定子を必要としません。片側の' eax'は命令の32bサイズの文脈を強制します。したがって、このような場合は、 'add eax、1'で十分です。 'add [N]、dword 1'の下にあるものは正しいです。サイズ指定子が少なくとも片側に必要です。あまりにも曖昧であれば、' N'でも 'byte'や' word'でも意味があります。バイト/単語だけになります。そして、+ 1を行うために、x86は専用のオペコード 'inc'と' dec'を持っており、 '1、'の型付けを保存します。なぜ私は本当にそれらの2つが好きか分からない。 :) – Ped7g

関連する問題