2009年11月21日土曜日

オブジェクトの空間的取扱いに関する整理(私家版)

オブジェクトを計算機の中でどういう単位というか塊で取り扱うことがあるのかなぁ、というのを、ふと、自分なりにまとめてみたくなった。ここでいうオブジェクトは、オブジェクト指向のオブジェクトではなくて、なんといったらいいのか、0と1の連なりのこと。

こうやって書いてみると、この程度のことしかまとめとして書けない自分に愕然とする。。。

こつこつやるしかないですね。。。


- オブジェクトの空間的取扱いに関する整理(私家版)
- ビット

オブジェクトはビットで表現する。

- 計算機のビットの取扱い

ビットは表現力が低いので、複数ビットを単位と
した塊を定義して、それを計算機は処理対象とす
ることが多い。

- 処理単位:ニブル

割愛。

- 処理単位:バイト

処理単位のひとつ。現在は8ビットであることが多
い。記憶領域の番地もバイト単位で指定すること
が多い(これをバイトアドレッシングと言う)。

- 処理単位:オクテット

バイトはアーキテクチャ毎に異なるため、8ビット
を曖昧さなく表す用語として、通信の世界で使わ
れはじめた。

- 複数バイトの取扱い

複数バイトになると、それを記憶領域上にどういう
順序で配置するかという選択が発生する(エンディ
アン)。

- 処理単位:ワード

ワードは文脈依存であり、いくつかの定義がある。
文脈は、CPUアーキテクチャ、記憶領域、OS、プロ
グラム言語などである。ここではCPUアーキテクチャ
文脈で話をする。

CPUアーキテクチャにおいてもワードの用法は揺れ
がある。例えば、PICマイコンなどでは、ワードは
バイトと並ぶような単位であり、バイトはデータ
メモリをCPUが取り扱う単位であり(8ビット)、ワー
ドはプログラムメモリをCPUが取り扱う単位である
(14ビット)。

しかし、PCアーキテクチャにおいては、ワードは、
バイトを束ねた単位とすることが多い。ここでは
その文脈とする。

バイトの表現力にも限界がみえたため、現在の計算
機は複数バイトを単位として処理単位とすることが
多い。その単位をワードと言う。複数バイトなので、
もちろんエンディアンの選択が存在する。

ワードは、CPUの歴史に依存している場合もある。
例えば、IAでは、現在でも2バイトがワードである。
ただし、ダブルワード、クワッドワード、ダブル
クワッドワードなどの単位が存在し、命令もそれ
らの取扱いを考慮して設計されている。

複数ワードをどう配置するかというエンディアン
の選択もある。通常、バイトエンディアンと同じ
ものを選択する。

- バイトアドレッシング、ワード、レジスタ

この3者のサイズは同値にするのが基本。ただし弱い
基本。

バイトアドレッシングが64ビットということは、ア
ドレスの表現が最大64ビットの数値ということ。

レジスタは、アドレスを扱うので、効率的にするに
は64ビット以上のサイズがあった方がよい。そこで、
基本、レジスタのサイズも64ビットにする。アーキ
テクチャ独自のメリットがある場合は、64ビット
以上にすることもある。

ワードは、CPU内のデータ処理やCPU内外のデータ転
送の単位である。これは少くともアドレスをまと
めて扱うことができるべきである。ただし、ワー
ドの場合、細かなデータの記憶領域への格納につ
いての効率など、いろいろなファクタがあるので、
そのままワード=64ビットとしないこともある。す
なわち、ワードは64ビット以下というのが基本で
あり、長いものはダブルワードやロングワードな
どと定義することが多い。

- 整列ルールと境界

複数バイトを記憶領域に配置することを考える。記
憶領域側からしてみれば、どこを開始番地にして、
どれだけの長さを配置することも可能である。

しかしCPU側から見ると、なんでもOKじゃなくて、
ルールがあった方が、いろいろと効率がよいこと
が多い。

なのでアーキテクチャの選択として、複数バイト
の連なりをどうメモリ上に置くべきかがルールと
して決まっていることがある。

よくあるのが、2バイトのデータは2バイト境界にな
ど、偶数バイトで境界を定めるものである。この場
合、3バイトのデータが複数ある場合、4バイト境界
毎に配置するため、1バイトずつの無駄がでる。

- 仮想記憶 (仮想アドレス)

複数プログラムが独立して動くことをハードウエ
アでサポートするために、記憶領域のアドレスは
仮想化されていることが多い。(仮想アドレスのニー
ズはこれだけではないが)

この仮想記憶のベースとなる機構はCPUにて実
装されることが多い。一般に、OSがそのCPUの機能
を利用しつつ、ハードディスクなどの二次記憶
の機構と統合して、記憶階層の機構を実現してい
ることが多い。この機構をページングシステムと
呼ぶ。

仮想記憶を実現する道具立てとして、仮想ア
ドレス、ページ、ページフレーム、ページテーブ
ルなどがある。ちなみにページングとは、ページ
をページフレームに割り付ける(物理記憶上にデー
タがある状態にする)こと。

- ページとページフレーム

仮想記憶を実現するために、仮想アドレスを複数バ
イトの単位で分割して取り扱う。この単位をページ
と言う。同じ単位で、実際に装備している物理記憶
領域も分割して取り扱う。これをページフレーム
と言う。

ページとページフレームを紐づけるのが、ページ
テーブルである。

例えば、IA-32では、現状4KBと4MBのページを取り
扱うことができる。

- ページングシステムとファイルシステム

ページングシステムがどのように二次記憶を使う
かは2通りの手法がある。

1つは、二次記憶の取扱いについてファイルシステ
ムに相乗りする手法である。

もう1つは、二次記憶の取扱いについて、ファイル
システムとは別の独自の取扱いをする手法である。

現在は前者が多い。ここでは前者を取り扱う。

- ページングの仕組み

ページングはいろいろなアルゴリズムや手法があり、
OSの設計によっていろいろである。

Linuxは、デマンドページングとコピーオンライト
(COW)である。(PCアーキテクチャのOSでは、現在
はみんなこれかもしれない)

- デマンドページング

デマンドページングではないということは、あ
るプログラムを動かすとき、始めに全てのオブ
ジェクトをページングするということ。デマン
ドページングは、始めは何もページングしてお
らず、メモリアクセスされるにつれてページン
グが進んでいくという方式。

- コピーオンライト

子プロセスを生成するときに、子プロは生成当
初、親プロのページフレームをCOWマーク付きで
参照する方式。すなわち複数のプロセスのペー
ジによって、単一のページフレームが共有され
ている。自分がCOWページに書き込みをするとき
に始めてコピーされる。

ページングで重要なトピックは、ページフレーム
の共有ということだ。共有できれば、物理記憶領
域の消費を抑えられ、空間的にも効率がよいし、
実行速度的にも効率がよい。

- ページングとオブジェクト

共有の鍵となるのは、書き込み(write)の有無だ。
そこで、ページへのオブジェクトの配置としては、
オブジェクトの中で、読み出しだけの部分はROペー
ジとして取り扱えるとよい。また書き込みがあるか
もしれない部分もまとめてCOWページとして取り扱
えるとよいだろう。

- 共有ライブラリと位置独立コード(PIC)

同じライブラリを使ったプログラムが複数動いてい
るとする。すると、それぞれの仮想記憶に別々に
ほとんど同じライブラリのオブジェクトが配置さ
れていることになる。これは空間効率が悪い。

だが、ROページにはできない。それぞれの仮想アド
レス空間におけるライブラリの再配置先は異なり
うるからだ。

そこで、位置独立コード(Position Independent
Code)という手法をとる。オブジェクトの構造を整
理して、再配置情報はCOWページへ、それ以外は、
ROページへいけるようにするというもの。すると
この後者の部分はアドレス位置独立のコードと言
える。

- セグメントシステム

仮想記憶とページングシステムについては一旦忘れ
る。

組み込み機器などえ、CPUのアドレス空間が小さく、
それに比して物理記憶領域の量が多い場合がある。
例えば、アドレス空間が16ビット(64KBアドレス可
能) で、物理記憶領域が1MBであるなど。こういう
状況にて、プログラムが64KB以上の記憶領域を使
うための仕組みとして、セグメントシステムがあ
る。

具体的には、アドレスの指定に16ビット値を2つ使
う。ひとつの値を左に4ビットシフトしたものを物
理記憶領域のアドレスの起点とし、もうひとつの
値をそこからのオフセットとする。これによって、
物理記憶領域のすべてをアドレスできるようにな
る。

ここで、ひとつの起点からオフセットにて指定で
きる領域のサイズは依然として16ビット(64KB)で
ある。この領域をセグメントと呼ぶ。起点のアド
レスをセグメントアドレスやセレクタと呼ぶ。

IA-32の32ビットプロテクトモードでは、レジスタ
のサイズは十分であるが、セグメントシステムが使
われている。

セレクタ(16ビット):オフセット(32ビット)

の組でアドレスを行なう。オフセットが32ビットな
ので、これだけで4GBを扱うことが可能である。こ
の領域のことも引き続きセグメントと呼ぶ。さて、
セグメントが4GBだとすると、セレクタを何につかっ
ているかという疑問がある。セレクタはセグメント
ディスクリプタという情報の指定に使われている。
セグメントディスクリプタは、主に

アクセス権(8ビット)
ベースアドレス(32ビット)
リミット(20ビット)

で構成され、リミットは1B単位または4KB単位で解
釈される。4KB解釈のとき最大で4GBになる。

32ビットプロテクトモードでは、セグメントシステ
ムとページングシステムの併用が可能である。


こつこつ。

0 件のコメント: