なぜx86 大学の機械語序論という授業でx86(x86_64ではない)でアセンブラを書いています。 x86のアドレッシングモードが難しかったので復習を兼ねてまとめます。 やりたかったこと 授業でfib(10)を求めてebxに格納する課題がありました。 方針としては、aというシンボルのデータ領域を、アドレッシングモードを使って配列のように扱い、 フィボナッチ数列を計算することにしました。 わかりやすくRubyで書くとこんな方針です。

fib.rb a = 1, 1, 0, 0, 0, 0, 0, 0, 0, 0.each {|i| a[i+2] = a[i+1] + a[i]} puts a[10] アセンブラでa[i+2]やa[i+1]を参照する必要があったので、 アドレッシングモードを利用したいと思ったわけです。

x86のアドレッシングモード 授業の資料によると、x86 では、以下のアドレッシングができるそうです。 BASE+(INDEX*SCALE)+DISPLACEMENT DISPLACEMENT: アドレス、もしくはベースレジスタからのオフセットを示す。定数。 BASE: ベースレジスタ INDEX: インデックスレジスタ、配列の添え字のようなもの SCALE: 2,4,8 のいずれか。配列要素のサイズを指定する。 そして、これを次のように記述するらしいです。 DISPLACEMENT(BASE, INDEX, SCALE) 注意点 ここがポイントなのですが、 アドレッシングモードを利用するときには必ず型を守らなくてはいけません。 特に、 BASEをレジスタにするのを忘れて エラーになるケースが多いような気がします。 コンパイラはjunk errorとか適当なエラーメッセージしか出してくれないので、 何がいけないのか分からずに苦労しました。 DISPLACEMENTには定数を指定する。 BASEとINDEXにはレジスタを指定する。 DISPLACEMENTはバイト単位(long型の配列なら、添字*4を指定する)。 これらを踏まえると、%eaxにインデックス、%ecxに配列arrayの先頭アドレスを格納したとき、 array[%eax+2]を参照するためには、次のようにする必要がありました。

Read more