2016-10-26 10 views
2

整数配列の奇数の数を数えるARM関数(サブルーチン)を記述します。関数シグネチャは次のとおりアセンブリ内の奇数の検索

int numodd(int array[], int size) ; 

: int配列[]は整数配列の最初の要素へのポインタとしてARM関数に渡されると、 INTサイズが値によって渡され、数あります配列内の要素

C言語のソースコードは次のとおりです。

#include <stdlib.h> 
#include <stdio.h> 

extern int numodd(int array[], int size) ; 

int main(int argc, char * argv[]) 
{ 
    int numarray[] = { 2, 3, 1025, 3024, 4057, -3, -1025, -3578 } ; 
    int size = sizeof(numarray)/sizeof(int) ; 
    int result ; 

    result = numodd(numarray, size) ; 
    printf("Number of odd numbers: %d\n", result) ; 

    exit(0) ; 

} 

アセンブリコード(今のところ):

 .global numodd 
     .text 
numodd: stmfd sp!,{v1-v6,lr} 
     mov a3, #0 
elop: ldr a4, [a1], #4 
     tst a4, #1 
     beq odd 
     subs a2, a2, #1 
     bne elop 
odd: add a3, a3, #1 
     bne elop 
     mov a1, a3 
     ldmfd sp!,{v1-v6,pc} 
     .end 
+2

ご質問はありますか?このコードはあなたが期待することをしますか? See [ask]。そうでない場合は、デバッガでシングルステップ実行するのが最も良い方法です。 –

答えて

2

あなたはARMを考えた場合、私はあなただけの余分なsubsを忘れてしまったのかはわからない、またはブランチディレイスロットを持っていましたが、「偶数」の場合にはa2をデクリメントするだけです。

あなたは、代わりに条件付き実行を使用することができ、より効率的になるので、 beq oddは不要である。なお

:今後の参考のため

tst a4, #1 
    addne a3, a3, #1  @ if (a4 & 1) a3++ 
    subs a2, a2, #1 
    bne elop 
    mov a1, a3 
    ldmfd sp!,{v1-v6,pc} 
+0

@Micheal - どのARMバージョンですか? – InfinitelyManic

+1

@InfinitelyManic:これは、あなたが求めているのであれば、あらかじめ統一された構文です。私は、OPが使用していた構文(ARMv4の場合はarmasmのように見えるか、それ以上のものも可能)をたどっただけです。 – Michael

+0

ありがとうございます。それは完璧に働いた。私は次回の理解を深めるためにそれを読む必要があります。 –

0

プライムポンプへのARMv8マクロ。

// isOdd 
.macro isOdd num 
.isOdd\@: 
push2 x1, xzr 
     mov x1, \num 
     ands x0, x1, 1   // if result is True then subject bit is set 
     cset x0, ne    // ne = Z flag not set; 1 AND 1 == 1 so clears Z flag; so set x0 to 0 if even num 
pop2 x1, xzr 
.endm 
関連する問題