

アドレス指定方式についてです。

直接アドレス指定方式  
指標アドレス指定方式  
ベースアドレス指定方式  
相対アドレス指定方式  
間接アドレス指定方式  
レジスタアドレス指定方式  
即値アドレス指定方式

この7つの違いはわかりました。  
しかし、それが具体的に何に使われているのか？  
この思想の違いが何故生まれてきたかなどの歴史的な経緯がわかりません。  
多分OSの設計思想の話だと思うのですが...


CC BY-SA 3.0
2015-06-29T14:05:31.750
11858
2015-08-28T10:02:39.170
2015-08-28T09:30:30.057
10945
10338
question
アルゴリズム assembly
アドレス指定方式についてです


鶏が先か卵が先かなところがありますが  
・コンパイラが作りやすいように CPU のアドレッシングを設計する  
・既にある CPU のアドレッシングに適合するようにコンパイラを設計する  
わけです。  
OS はあまり関係ないですね (CPU に適合するように OS を作るわけですし)

32bit を想定  
C/C++ でコード例を出し説明のための仮 CPU (x86, SH, RX 等を想定) で命令例を出すこととします

直接アドレッシング  
大域静的変数は固定アドレスに配置されます。

[code]

    int global_scoped_static_variable;
    void some_func() {
      global_scoped_static_variable=1;
    }
    
[/code]

この代入に対しては直接アドレッシング命令が生成でき  
MOV.L #1, @_global_scoped_static_variable

即値アドレッシング  
同様 `int* p=&global_scoped_static_variable` なるソースコードに対して  
MOV.L #_global_scoped_static_variable, R3

レジスタアドレッシング  
先のソースコードに引き続き `++*p;` としたなら  
INC.L @R3  
あるいは関数ポインタ経由の関数呼び出しは JSR @R3 とかがこれに該当します。

ベースアドレッシング、ベース＋インデックスアドレッシング  
配列変数を扱うときに使います。  
`int array[NNN];` に対して `array[x]=2;` があれば  
ベースアドレス＝ array  
インデックス = x  
乗算因子 = 4  
とすることで MOV.L [EBX+EAX*4], 2 とできます。

他は省略（宿題）

命令語数が少ないほうがプログラムが小さく高速になるわけで、  
そうできるようにアドレッシングモードやコンパイラが設計されてきました。  
ほぼ完成形まで来ているので「アドレッシングモード」が今後大幅に変化することはなさそうです。


CC BY-SA 3.0
2015-06-29T21:52:21.843
11862
2015-06-29T21:52:21.843
8589
11858
answer


アセンブリ言語の命令を分類したものです。  
例えばマイコンのデータシートに命令表が用意されています。そこでアドレッシング・モードを確認しながらプログラムを書きます。

命令の記述量が多くなって複雑さが増さないように、簡潔に表現できるようにしたのです。この機能がなければ機械語でプログラムを書くのとほとんど同じ規模になってしまいます。アセンブラによってCPUの機能の範囲内に展開されるので複雑な処理の記述やハードウエアに近い詳細なアーキテクチャを理解や重複したコードを記述する必要がないという利点があります。特にマイコンでは発信水晶子が一つで同一クロックで管理されているのにも関わらず実行ステート数が異なる理由はそこにあります。

OSでのアドレッシング・モードについて触れていますが、ページ管理の`Physical Addressing Mode` と `Virtual
Addressing Mode`
は物理アドレス空間と仮想アドレス空間のことです。しかもマイナーな表現です。同時に勉強している場合は混同しないように注意してください。


CC BY-SA 3.0
2015-08-28T07:07:37.237
14945
2015-08-28T07:12:43.550
2015-08-28T07:12:43.550
10945
10945
11858
answer


かつてはメモリーの決まった位置にプログラムを置いて、データや命令がある場所を示すアドレスは固定で動いていたようですね。そうすると、アドレス指定はすべて「直接指定（絶対指定）」で問題ありませんでした。プログラムを組む人は、プログラムがロードされるアドレスを知っていて、「どこに飛ぶ」といった指示を直接指定するわけですね。

しかし、メモリにいろんなプログラムがロードされたり、足りないメモリを補うためにメモリじゃないところにプログラムを置いたり、果てはプログラムが不正アクセスされないようにロード場所を意図して毎回変えたり、といった実行方法が普通になってきました。そうすると、実際のアドレスはプログラムが動くその時までわかりません。

そうなると、

  * 今の場所から＊＊だけ先のアドレス
  * スタート地点から＊＊だけずれたアドレス
  * アドレスは変数に入れといたから

みたいなアドレスの指定方法が必要になってきました……というような経緯で、いろんなアドレッシング方式が生まれてきたのだったと思います。

Wikipediaですが[位置独立コード](https://ja.wikipedia.org/wiki/%E4%BD%8D%E7%BD%AE%E7%8B%AC%E7%AB%8B%E3%82%B3%E3%83%BC%E3%83%89)や[リロケータブルバイナリ](https://ja.wikipedia.org/wiki/%E3%83%AA%E3%83%AD%E3%82%B1%E3%83%BC%E3%82%BF%E3%83%96%E3%83%AB%E3%83%90%E3%82%A4%E3%83%8A%E3%83%AA)などの説明を読んでみられてもいいかもしれません。


CC BY-SA 3.0
2015-08-28T10:02:39.170
14955
2015-08-28T10:02:39.170
10538
11858
answer