特集
Windows 9x or Windows 2000?

6.Windows 9xのプロセス管理メカニズム(1)

デジタルアドバンテージ
2000/08/23


 CPUの処理能力や搭載メモリ、搭載ディスク容量が限定的だった初期のPCにおいて、何とか実用になるマルチウィンドウ、マルチタスク環境を実現するために、Ver.3.xまでのWindowsでは、OSのオーバーヘッドが少ないノンプリエンプティブなマルチタスキング メカニズムを採用していた。これらWindows 3.xでのマルチタスク管理方式については、別稿の「コラム:Windows 3.xのマルチタスク システム」に詳しくまとめたので参照されたい。

プリエンプティブなマルチタスクが可能になったWindows 9x

 マルチタスク システムとしてはかなり原始的だったWindows 3.xに比較し、Windows 9xでは、スレッドをスケジューリングの単位とするプリエンプティブなマルチタスクに改良された。このプリエンプティブなマルチタスクでは、OS(つまりWindows 9xシステム)がプロセス管理の全権を掌握し、システムが全プロセスの挙動を常に監視しており、仮にメッセージ処理をいつまでも終わらないアプリケーションがあったとしても、そのアプリケーションから(メッセージ処理の途中であっても)強制的に制御権を奪い、別のアプリケーションに制御権を与えることができる。ただし詳細は後述するが、本来的にプリエンプティブにスケジューリング可能なのはWindows 9xにネイティブに対応したWin32アプリケーションのみで、Windows 9xシステムにおいても、複数のWin16アプリケーション同士はノン プリエンプティブなマルチタスクで実行されるようになっている。

Win32アプリケーションのプロセスとスレッド

 仮想メモリ システムも実装されたWindows 9xでは、実行される各アプリケーション(Win32アプリケーション)ごとに独立したメモリ空間が与えられる。すべてのアプリケーションでメモリ空間を共有していたWindows 3.xでは、プログラムの実行単位をタスク(task)と呼んでいたが、Windows 9xでのプログラムの実行単位はプロセス(process)と呼ぶ。

 Win32アプリケーションが起動されると、Windows 9xはそのアプリケーションのプロセスを生成し、これに独立したメモリ空間やI/O空間、ファイル ハンドルなどを割り当てる。つまりWin32アプリケーションは、同時に実行されている他のアプリケーションを意識することなく、これらの資源(リソース)にアクセスできるということだ。もちろん、物理的なメモリやI/Oなどはシステムに1つしかないので、複数のアプリケーションが同時にこれらの資源を使うことはできないが、それらの調停はWindows 9xシステムのVMM(Virtual Machine Manager)が行ってくれる。

 このようにWindows 9x環境では、各種のシステム資源がプロセスを単位に割り当てられる。従来型のマルチタスクOS(初期のUNIXなど)では、このプロセスを単位にスケジューリングを行うものもあったが、Windows 9x(およびWindows 2000)では、それよりも小さなスレッド(thread)と呼ばれる単位でスケジューリングを行うようになっている。

プロセスとスレッド
Windows 9xおよびWindows 2000では、仮想メモリ空間などのシステム資源はプロセスを単位として割り当てられるが、CPU時間のスケジューリングは、プロセス内に生成されるスレッド(thread)と呼ばれる単位で行われる。このように、1つのプロセスには、最低でも1つのスレッドが含まれる。プロセスが生成されると、自動的に1つのスレッドが生成される。このスレッドは、特に「プライマリ スレッド(primary thread)」と呼ばれる。

 プロセスが生成されると、その内部に自動的にスレッドが1つ生成される。これはプレイマリ スレッドと呼ばれ、すべてのプロセスには少なくとも1つのスレッド(プライマリ スレッド)が存在している。その後アプリケーションは、必要に応じて複数のスレッドを生成し、それらを同時に実行させることができる。仮想メモリ空間に代表される各種のシステム資源はプロセスを単位として割り当てられるので、同一プロセス内の複数のスレッドは、これらのリソースを互いに共有することができる。具体的には、特別な手続きなしに、ごくわずかなオーバーヘッドで共有メモリを介したスレッド間通信などを行うことが可能なのだ。たとえば、Windows環境で各種のファイル操作を行うエクスプローラでは、複数のウィンドウを表示させて、それらの間でファイルのドラッグ&ドロップによるファイルのコピーなどが可能である。このときエクスプローラは、表示するウィンドウごとに異なるスレッドを起動し、そのウィンドウの処理をスレッドで行うようになっている。ここで、あるウィンドウでファイルを選択し、別のウィンドウにドロップすると、エクスプローラは、ドロップされた側のスレッドでファイルのコピー処理を行うようになっている。

Windows 9xのエクスプローラ
Win32アプリケーションであるエクスプローラでは、同時に表示されるウィンドウごとにスレッドを生成し、このスレッドによってウィンドウの処理を行うようになっている。画面は、マウスを使用してファイルのドラッグ&ドロップを行ったところ。この場合エクスプローラは、ファイルがドロップされた側のウィンドウのスレッドでファイルのコピー処理を実行する。

Windows 9xのメッセージ システム

 別稿の「コラム:Windows 3.xのマルチタスク システム」でご紹介したように、従来のWindows 3.xシステムでは、キーボード/マウス入力など、各種のイベントごとに生成されるWindowsメッセージを複数のアプリケーションで処理することでマルチタスク システムを実現していた。Windows 9xにおいても、イベントに応じてメッセージが生成され、これらがアプリケーションに送られて処理されるという点に変わりはない。しかしWindows 9xでは、マルチタスクがプリエンプティブ方式に変更されるとともに、複数のアプリケーションを効率よく同時実行するために、メッセージ システムにも改良が加えられた。Windows 9xのメッセージ システムを以下に示す。この図と、「コラム:Windows 3.xのマルチタスク システム」で示したWindows 3.xのメッセージ システムを比較していただきたい。

Windows 9xのメッセージ システム
各種のイベントごとにメッセージが生成され、それらがアプリケーションに送られることで、ウィンドウ システムの処理が実行される点は従来のWindows 3.xと変わらない。しかしWindows 9xでは、プリエンプティブなマルチタスク方式に改良されることに従い、それを効率的に運用する目的でメッセージ システムも改良された。

Win32アプリケーションでは、スレッド単位にキューが割り当てられる

 Windows 3.xのメッセージ システムでは、キーボード/マウスなどのデバイス、Windowsシステム、他のアプリケーションからのメッセージが、システムに1つしかないシステム メッセージ キューにキューイングされ、その後アプリケーションに送られるようになっていた。基本的に、メッセージは発生順にキューイングされて処理されることになるので、あるアプリケーションのメッセージ処理が停滞すると(メッセージ処理を行ってシステムに制御を返さないと)、それ以後にキューイングされているメッセージを待っているアプリケーションは処理を進められない。つまり、システム メッセージ キューがシステム全体のボトルネックとなってしまう危険があったわけだ。

 Windows 3.xでは、メッセージ処理とマルチタスク機構が完全に一致していたので、これでも問題はなかったが(メッセージ システムのボトルネックは、そのままマルチタスク システムのボトルネックとなっていた)、Windows 9xでは、プリエンプティブなマルチスレッド機能が組み込まれ、Windowsメッセージ処理とマルチタスク機構が分離された。このように改良されたWindows 9xに、Windows 3.xのメッセージ処理機構をそのまま持ち込むとどうなるか?

 スケジューリングされるが(実行されるが)、メッセージ キューに別スレッドのメッセージがつかえているため、メッセージを取り出せずに、ただ待ち続けることでタイム スライスを終了するスレッドが出てきてしまうだろう。たとえていえば、バットを渡されても、すでに別人がバッターボックスにいて、打席に立てないようなものだ(バットを渡される意味がない)。つまりこれでは、Windows 3.xでの問題がそのまま残ってしまうことになる。

 まずは、図左下にある2つのWin32アプリケーションに注目されたい。この問題を解決するために、Windows 9xのWin32アプリケーションでは、各スレッド単位にメッセージ キューを持てるようにし(必要がなければ、メッセージ キューを持たないスレッドも生成できる)、メッセージはここにキューイングされるようになった。図から分かるとおり、Windows 9xでは、キーボードやマウスなどの周辺デバイスなどからのメッセージは、システム内にある「ロー インプット キュー(raw input queue)」にいったんキューイングされ、その後直ちに、メッセージの宛先であるスレッドのキューに分配される。Windows 9xでは、ロー インプット キューをモニタしている専用のスレッドが常時実行されており、ここにメッセージがキューイングされると、このスレッドが直ちにメッセージを適切なスレッドのキューに分配するようになっている。

 Windows 3.xでは、あらゆるメッセージがシステム内で唯一のシステム メッセージ キューにキューイングされていたが、Windows 9xでは、Windowsシステムからのメッセージ(ウィンドウの切り替えやアプリケーションの終了を知らせるメッセージなど)や、他のアプリケーションから送られるメッセージについては、ロー インプット キューを経由することなく、メッセージの宛先であるスレッドのキューに直接送られるようになった。

Win16アプリケーション同士は、1つのメッセージ キューを共用する

 今度は、図の右下にあるWin16アプリケーションに注目しよう。図から分かるとおり、Windows 9xシステムでも、Win16アプリケーション同士は、1つのメッセージ キューを共用するようになっている。つまり、Win16アプリケーションから見れば、Windows 3.xと同等のメッセージ環境が提供されているわけだ。Win16アプリケーションでは、DDE(Dynamic Data Exchange)などのアプリケーション間通信のプロトコルを始め、アプリケーション自体も、ノンプリエンプティブなマルチタスクを前提として設計されているので(つまり、自分から明示的に制御を解放しないかぎり、別のアプリケーションは実行されないという前提で設計されているので)、Win16アプリケーションの互換性を維持するには、意図的にノンプリエンプティブなマルチタスク環境を作ってやらなければならないからだ。このようにWindows 9x環境においても、Win16アプリケーション同士はノンプリエンプティブにスケジューリングされるので、あるWin16アプリケーションがいつまでも制御を返さないと、他のWin16アプリケーションは動くことができない。ただしこれはWin16アプリケーションのみの制限で、Win32アプリケーションについては、Win16アプリケーションの挙動に影響を受けることなく、プリエンプティブに処理を進めることができる。


 INDEX
  [特集]Windows 9x or Windows 2000?
     1.イントロダクション
     2.Windows 9xカーネルの概要
      コラム:Windows歴史、メモリの歴史 (1)
      コラム:Windows歴史、メモリの歴史 (2)
     3.Windows 2000カーネルの概要 (1)
     4.Windows 2000カーネルの概要 (2)
     5.プロセス管理の概要
     コラム:Windows 3.xのマルチタスク システム
   6.Windows 9xのプロセス管理メカニズム (1)
     7.Windows 9xのプロセス管理メカニズム (2)
     8.Windows 2000のプロセス管理メカニズム (1)
     9.Windows 2000のプロセス管理メカニズム (2)
 
 特集


Windows Server Insider フォーラム 新着記事
@ITメールマガジン 新着情報やスタッフのコラムがメールで届きます(無料)

注目のテーマ

Windows Server Insider 記事ランキング

本日 月間