.NET Framework入門

3.Common Language Runtime(1)

― CLRの内部構造とプログラム実行の流れ ―


デジタルアドバンテージ 遠藤孝信
2000/12/14

p.1 p.2 p.3 p.4 p.5 p.6 p.7 p.8 p.9

本記事は改訂されました。改訂版の「.NETとは何か? ― 基礎解説:.NET初心者のための.NET入門【2011年版】」をご覧ください。

 今述べたとおり、.NET Framework上でアプリケーションやコンポーネントを動作させるための実行エンジンとなるのがCLR(Common Language Runtime)である。

 ランタイム(runtime)といえば、私たちに馴染みの深いものの1つとしてVisual Basicランタイム(以下VBランタイム)があるだろう。これは、Visual Basicで記述されたプログラムを実行するときに必要となるDLLファイルであった。初期のVisual Basicでは、「P-コード」と呼ばれる中間コードを生成してEXEファイルに格納しておき、実行時にこのP-コードがVBランタイムによって解釈され動作するようになっていた(これに対し現行のVisual Basicでは、プロセッサのネイティブ・コードをEXEファイルとして生成できるようになった)。

 実行ファイルがプロセッサのネイティブ・コードでなく、中間コードであるという点で、CLRのしくみはVBランタイムに似ている。ただしVBランタイムは、Visual Basicで記述されたプログラムを実行するためだけのものであったのに対し、CLRは、その名が表しているように、複数の言語処理系にまたがる「共通の言語ランタイム」である。.NET Frameworkでは、従来のC++やVisual Basicに加え、マイクロソフトが開発した新言語処理系のC#(シー・シャープ)、さらにCOBOLやPerlなど、現在明らかになっているだけでも、十種類以上の言語がサポートされる予定である(これらCLRでサポートされる言語処理系については、すぐ次で詳しく述べる)。これら各言語処理系で記述されたコードは、各言語コンパイラによってコンパイルされるが、それによって出力されるコードはすべてCLRで解釈可能な中間言語となる。この中間言語は「MSIL(Microsoft Intermediate Language)」あるいは単に「IL」と呼ばれる。ただし中間コードではあるものの、コンパイルされた実行ファイルの拡張子は従来どおりEXEファイルとなり、CLRの存在を意識することなく、従来どおりに実行することができる。

 CLRの内部構成を図示すると次のようになる。

CLRの内部構成

ガーベジ・コレクションを行う「ガーベジ・コレクタ」や型チェック、セキュリティ管理など、C/C++言語などによる従来のプログラミングで大きな負担になっていたソフトウェアの基本機能がこのCLR内部で提供されることとなった。上位アプリケーションは、もはやヒープ・メモリ管理やセキュリティ管理などを意識する必要はない。

 ここで詳細は述べないが、ガーベジ・コレクションを行ってくれる「ガーベジ・コレクタ」を始め、型チェックやセキュリティ管理など、多くのアプリケーションに共通して必要なものでありながら、C/C++言語などでの従来のプログラミングでは、各アプリケーションが必要に応じて独自に実装しなければならなかった基本機能の多くが、このCLR内部で提供されることとなった。上位アプリケーションは、もはやメモリ・リークやセキュリティ管理などを意識する必要はない。実際、プログラムを開発するという意味では、上に示したCLRの内部構成を知る必要もない。

CLRによるプログラムの実行

 CLR上でのソース・コードのコンパイルから、生成されたMSILコードの実行までの流れを図示すると次のようになる。

CLRでのプログラム実行

CLR環境では、プログラムのソース・コードはコンパイラによって中間コード形式のMSILに変換され、これが実行ファイル(拡張子.EXE)として生成される。こうして生成されたMSIL形式の実行ファイルを起動すると、最初に、プログラムで使用されているクラスがクラス・ローダによってメモリにロードにされる。次にJITコンパイラによってMSILが各システム向けのネイティブ・コードに変換されて実行される。
  CLR対応のプログラム言語で記述されたソース・コード(テキスト形式)。
  ソース・コードは、各プログラム言語に対応したコンパイラによって、中間コード形式のMSILに変換される。
  コンパイラによって変換されたMSILは拡張子.EXEとして保存される。したがって少なくともファイルの拡張子を見ただけでは、それがネイティブ・コードを含む従来の実行ファイルなのか、MSIL形式のファイルなのかは見分けがつかない。
  MSILデータを含む実行ファイルを起動すると、最初にクラス・ローダが実行され、プログラム中で使用されているクラス情報がクラス・ライブラリから読み出され、メモリにロードされる。
  特定のプロセッサ・アーキテクチャに依存しない中間コード形式のMSILは、各システム向けに用意されたJIT(Just-In-Time)コンパイラによって、そのプロセッサ向けのネイティブ・コードに変換される。
  各システムのマイクロプロセッサが直接解釈して実行可能なネイティブ・コード。
  ネイティブ・コードの実行。

 コンパイラによってソース・コードからMSIL形式に変換された実行ファイルを起動すると、まずはクラス・ローダによって起動されたプログラムが読み込まれ、このプログラム中で使用されているクラス情報がクラス・ライブラリからメモリ上にロードされる。クラス情報のロードが終わると、次はJIT(Just-In-Time)コンパイラによって、中間コードであるMSILが各システム(プログラムを実行するシステム)のプロセッサ・アーキテクチャなどに対応するネイティブ・コードに変換される。必要に応じて、プログラムの実行時にネイティブ・コードに変換するコンパイラであることからこのように呼ばれるものと思われる。文献によっては、省略して「JITter」と呼んでいるものもあるようだ。

 MSILをネイティブ・コードに変換するJITコンパイラには、標準コンパイラとエコノミー・コンパイラの2種類がある。このうち前者の標準コンパイラでは、生成したネイティブ・コードの最適化が行われ、後者のエコノミー・コンパイラでは最適化が行われない。最適化を実施したネイティブ・コードのほうが、最終的な実行速度は向上するが、代わりにコンパイル時の負担が大きい。このためシステムの性能や、実行プログラムの性質などに応じて、2つのJITコンパイラを切り替えて使用することができるようになっている。

 ネイティブ・コードが実行されるときにはセキュリティチェックが行われ、素性の知れないプログラムは実行できないようになっている。プログラムの実行中には「ガーベジ・コレクション(GC)」により、参照されなくなった不要なオブジェクトは随時回収され、これによってメモリリソースは効率的に管理される。このようにCLR上でのプログラムの実行は完全にCLRによって管理される。このような管理されたプログラムコードは、.NET Frameworkでは「マネージド・コード(managed code)」と呼ばれる(文献によっては、「管理コード」と訳したものもあるようだが、これではあまりに一般用語のイメージが強いので、本稿ではあえて「マネージド・コード」と呼ぶことにした)。

 このようにCLR環境で実行されるプログラムは、CLRが提供する機能をほとんど意識することなく、その恩恵に浴することができる(前出の図「CLRの内部構成」)。これにはさまざまな機能があるが、プログラマにとって特にありがたいのは、ガーベジ・コレクション(プログラムの実行中に使用されなくなったメモリを自動的に見つけ出し、再利用できるようにするための機構)に代表されるメモリ管理機能、そしてセキュリティ機能だろう。たとえば、現時点でWindowsアプリケーション開発の主流言語の1つであるC/C++では、こうした面倒な処理を自前でやりくりしなければならない。ユーザーの操作に応じてさまざまな処理を非同期的に実行するようなWindowsアプリケーションでは、思わぬところでメモリ・リークが発生してしまったりする。また、インターネットのどこかにいるクラッカーによる侵入や、攻撃から見守るために、多くのプログラムでセキュリティ機能が必須となりつつあるが、こうした機能をプログラマが自前で備えるには限界もあるし、その積み上げによって構築されたシステムを安全に運用するなど到底不可能なことだ。やはりシステム全体で強固かつ統一的なセキュリティ・メカニズムが必要であるし、万一セキュリティ・ホールが見つかった場合でも、その場しのぎ的に対処するのではなく、それに対処することで、システム全体のセキュリティ性能が改善されるようなものでなければならない。

 またプログラムを中間コード形式で保存し、実行時にこれをネイティブ・コードに変換するという方式を採用することにより、.NET Frameworkは、PCばかりではなく、多様なプラットフォームをサポートできるようになった。

 原稿執筆時点(2000年12月)マイクロソフトの説明によれば、CLRは、将来発表されるWindows OSにおいてシステムに標準的に組み込まれる予定だ。ただし、Windows 2000/Windows Meの後継OSとして現在開発が進められているWindows WhistlerでCLRが標準サポートされるかどうかは、この原稿を執筆している2000年12月時点では不明である。既存のWindows環境としては、Windows 2000、Windows NT 4.0、Windows Me/98/95でCLRがサポートされるとしている。これらのサポート・モジュールは、CLRを利用するプログラムとセットにして提供されるか、Windowsのアップデート用モジュールとしてマイクロソフトから提供されることになるだろう。さらにPC−Windows以外の環境向けにも、スマート・デバイス(マイクロソフトは、PDAや携帯電話などの小型デバイスをひとまとめにしてこう呼んでいる)用として、「.NET Framework Compact」と呼ばれる最小限の機能を装備した.NET Frameworkが用意される。またLinuxなど、他のオペレーティング・システムへの対応も噂されているのはすでに述べたとおりである。


 INDEX
  [特集].NET Framework入門
    1.Microsoft.NETプラットフォームとWeb Service
    2..NETプラットフォームと.NET Framework
  3.Common Language Runtime(1)
   CLRの内部構造とプログラム実行の流れ
    4.Common Language Runtime(2)
   CLRによる複数言語サポート:
    VS.NETで標準サポートされる言語処理系
    5.Common Language Runtime(3)
   CLRによる複数言語サポート:
   サードパーティによってサポートが予定されている言語処理系
    6.ASP.NET(1)
    ASP.NETで何が変わるのか? まずは既存のASPと比較してみよう
    7.ASP.NET(2)
    VBライクなWebアプリケーション開発を可能にするASP.NETのサーバ・コントロール群
    8.ASP.NET(3)
    Web Service開発始めの一歩。サービス公開に必要なのはキーワード指定1つ 


Insider.NET フォーラム 新着記事
  • 第2回 簡潔なコーディングのために (2017/7/26)
     ラムダ式で記述できるメンバの増加、throw式、out変数、タプルなど、C# 7には以前よりもコードを簡潔に記述できるような機能が導入されている
  • 第1回 Visual Studio Codeデバッグの基礎知識 (2017/7/21)
     Node.jsプログラムをデバッグしながら、Visual Studio Codeに統合されているデバッグ機能の基本の「キ」をマスターしよう
  • 第1回 明瞭なコーディングのために (2017/7/19)
     C# 7で追加された新機能の中から、「数値リテラル構文の改善」と「ローカル関数」を紹介する。これらは分かりやすいコードを記述するのに使える
  • Presentation Translator (2017/7/18)
     Presentation TranslatorはPowerPoint用のアドイン。プレゼンテーション時の字幕の付加や、多言語での質疑応答、スライドの翻訳を行える
@ITメールマガジン 新着情報やスタッフのコラムがメールで届きます(無料)

注目のテーマ

Insider.NET 記事ランキング

本日 月間