ウィンドウズはどう動いているか

まず、ウィンドウズプログラムはどのように動くのでしょうか?
それを説明するためにまず、ウィンドウズ自体がどのように動いているのか考えてみます。

原始的なコンピュータの時代にはプログラムはゼロから立ち上がりました。
始めに人間がメモリにプログラムを打ち込まなければ電源を入れてもコンピュータは暴走するばかりでなにも意味のある事はできませんでした。
実行するべきプログラムがある場所にはでたらめの値が入っているので、そのでたらめな値をプログラムだと思って暴走する訳ですね。
当時は、電源が入ったらどうするか、という部分からプログラムを作のがプログラマでした。
このプログラムを立ち上げプログラムと呼びましょう。

現在でもワンチップコンピュータ(冷蔵庫や洗濯機に組み込まれているもの)はこのエリアをプログラムに使います。

現在のパソコンにはこの立ち上げプログラムはあるのでしょうか?
じつはあるのです、というか無ければ立ち上がらないわけですね。
今はこの立ち上げ時に動くプログラムを作る人はほとんどいません。
趣味で作るひとは世界中でも数えるほどでしょう。
この立ち上げプログラムは、現在では「BIOS」(バイオス)と呼ばれてパソコンのマザーボードに刺さっているROMの中にあります。
ROMというのは記憶用のICチップで書き直すことができません。
このプログラムを作のは、マザーボードのメーカーか、「BIOS」のメーカーの技術者です。

ここはかつてプログラマに解放されていた0番地から始まる部分です。
いまはプログラマがその部分を触ることはできません。
ROMなので変更することも困難です。
その部分はマザーボードが立ち上がったときに周辺機器やメモリーのチェックを行い、システムのプログラムを実行エリアに読み込んでそのシステムを実行します。

BIOSが置いてある次のエリアにはMS/DOSがあります。
しかしWINDOWS95以降ではほとんどウィンドウズに吸収されているのでまあBIOSの上にWindowsがあるといっても間違いでは無いでしょう。
アプリケーションはその後です。
実際にはCPUは物理メモリのアドレスを自由に変えることができるので、必ずしもこの順番とは言えませんが、機能的にはこのように働いていると思って下さい。

ウィンドウズマシンの場合は、ハードディスクからウィンドウズをメモリに読み込んだあと、ウィンドウズに制御を移します。

「BIOS」の働きはもう一つ、周辺機器の制御です。
たとえばウィンドウズがプリンタを使おうとするとき、BIOSにプリンタとのやり取りを依頼するのです。
最近のマザーボードにはCPUのクロックの変更などもBIOSでできるものがあります。
歴史的に見るとCPUがメインでその上でウィンドウズというソフトが動いていると言えますが逆にユーザが使うのはウィンドウズだから、ウィンドウズがメインと考えるとウィンドウズが 自分を動かすためにCPUを使っているとも考えられますね。

さてBIOSがウィンドウズを立ち上げると、ウィンドウズは待機状態になります。
ユーザが何かのプログラムをダブルクリックして立ち上げます。
通常のアプリケーションの場合はそのアプリ用のウィンドウが出てきます。
たとえばエディタは、編集用のウィンドウを出して待機になります。
表計算ならなにも入力されていない表を出して待機状態になります。

通常でないアプリケーション(たとえばゲーム)は、ウィンドウを出してそのままぐりぐりするすると動きつづけることもあります。
待機している場合はCPUはアプリのコードを実行している訳ではありません。
ただ、メモリの中にアプリをロードして実行可能な状態になっているだけです。
ゲームの場合はデモプログラムが連続で動いていて、ロゴが出たり、メニューが出たりします。

通常プログラムはCPUがあるアドレスの番地に書いてある命令を読み込んで実行します。
それから次のアドレス、それから次のあどれす、と進んでいくわけです。
ウィンドウズはあるアプリが実行されると、そのアプリの初期化ルーチンを呼び出します。
呼び出された初期化ルーチンは、初期化処理つまりウィンドウを出したり、白紙の表を出したりしたあとで、リターンします。
リターンすると、CPUはウィンドウズの命令に戻ってウィンドウズのプログラムの実行を再開します。

その時点ではアプリケーション用のコードは実行していないのです。
ゲームの場合は、物にもよりますが、素直にウィンドウズにリターンしません。
定期的に自分のコードを呼び出すようにしたり、ときどきあいている時間だけウィンドウズのコードを実行したりするようにします。
すると、CPUをほとんどゲームが使うことができます。

通常のアプリケーションとゲームプログラムを比較すると、同じようにプログラムが難しいと言ってもその難しさに違いがあります。

両方ともウィンドウズに対する知識が必要ですが、必要とする知識もその範囲がずれているのです。
もっともビジネスアプリでもスタンドアローンのアプリケーションとネットワークアプリケーションではやはり同じように必要な知識もスキルもずれがあるので、それは当然とも言えます。

さてそこでまず通常のアプリケーションを考えてみます。
ウィンドウにボタンがひとつあるプログラムを考えてみましょう。
起動すると、ウィンドウズはそのプログラムをメモリに読み込みます。
次に初期化ルーチンを呼びます。
あとはほったらかしです。
そのとき、メモリ上にあるプログラムは以下のようになっています。

番地         名前    動作

0012456   initialize   変数を初期化してウィンドウを開く。

0013400   on_click   ボタンを押した時の動作

メモリ上のプログラムはそれぞれ初期化部分とか、ボタンを押したときの動作とかが固まりになってあります。
ボタンが押されると、ウィンドウズはプログラムにボタンが押されたぞ、というメッセージをプログラムに渡します。
渡されたプログラムは、ボタンを押したばあいにやることを実行します。

では、メッセージを渡すというのはどういうことでしょうか?
これはプログラムが持っているメッセージを保存する場所(キューと言う)にメッセージを書き込むことです。

プログラムはキューに入っているメッセージを順番に解釈して必要な処理をします。
ウィンドウズはたくさんのプログラムが同時に動いています。
混乱しそうですが、こういう方法をとってCPUを順番に使えば滞りなく処理ができるわけで、とても賢い方法です。

実際にやるとどうなるか、ここでVC++を立ち上げてやってみましょう。

ここでウィンドウの形に付いての説明をしておきましょう。
このVC++のようにアプリケーションが一つの大きなウィンドウをもち、そのなかに小さなほかのウィンドウを持っていることをMDI(マルチドキュメントインターフェース)といいます。
中に小さなウィンドウを持たないものはSDI(シングルドキュメントインターフェース)それから、灰色のウィンドウでファイルの消去の確認の場合などに出る「YES」「NO」「OK]などの選択を迫るウィンドウは「ダイアログ」といいます。
これらはVC++での開発では良く使う単語なので覚えておきます。