Windows 7解剖 – 1:「カーネルAPIの修正」について

カーネルAPI

昨年10月の発売以来、マイクロソフト社のWindows 7の販売本数は9,000万本に達しており、Windows販売史上最速という記録を更新しているといわれています。今回は、Windows 7で新たに強化された内部構造に関し、2回に渡って取り上げる予定です。まず第1回目は、多くの人が興味を示している、新軽量カーネル「MinWin」について紹介したいと思います。

多くの人が新軽量カーネル「MinWin」に大きな関心を寄せている一方で、大半の人が「MinWin」を正しく理解していません。中には、「MinWin」と「Server Core」を混同している人も少なくありません。では、「MinWin」とは、正確に何を指すのでしょうか?

正常にインストールできたXPMでは、「Enhanced Mode」、「Basic Mode」、「Virtual Applications Mode」の3種類のモードが使用可能です。Windows XPのデスクトップをそのまま表示して使う「Enhanced Mode」と「Basic Mode」は、通常のVirtual PCを使う場合と、見た目は全く変わらず、Virtual PCとWindows XP仮想マシンが表示されます。

過去、マイクロソフト社がWindows Server 2008で実現したものの1つに、「Server Core」(旧名称:「Server Foundation」)がありました。これは、ADやDNS、DHCPサーバー、インターネットインフォメーションサービス(IIS)といった一般的なサーバー機能の動作に必要なコンポーネントを集めた、Windows OSのサブセット製品でした。一方「MinWin」は、上位層のコンポーネントに依存しない、独立型の小規模なOSです。一般的には、Windows 7に付属して出荷される、最小構成の独立型Windowsコンポーネントセットとしてよく知られています。

マイクロソフト社のあるWindows開発者は、「MinWin」を「アーキテクチャの階層に沿ったコードの修正」と説明しています。実際、初の「MinWin」ベースのOSと言われるWindows Vista以降(Windows Vistaではすでに複数のコンポーネント化と修正が行われています)は、OSのどのコンポーネントにも、他のコンポーネントとの依存関係を表す「階層番号」が割り振られており、OSのコアに近いコンポーネントほど、小さな番号が割り当てられています。「コード修正」はコアのアーキテクチャチームが行い、この修正によって、下位層のコンポーネントが上位層のコンポーネントに依存する、という依存関係の問題を解決しました。次に、Windows 7における「階層化」と「コード修正」の方法を、例を使って説明しましょう。

ApiSet Stub DLLs:
api-ms-win-core-console-l1-1-0.dll
api-ms-win-core-datetime-l1-1-0.dll
api-ms-win-core-debug-l1-1-0.dll
api-ms-win-core-delayload-l1-1-0.dll
api-ms-win-core-errorhandling-l1-1-0.dll
api-ms-win-core-fibers-l1-1-0.dll
api-ms-win-core-file-l1-1-0.dll
api-ms-win-core-handle-l1-1-0.dll
api-ms-win-core-heap-l1-1-0.dll
api-ms-win-core-interlocked-l1-1-0.dll
api-ms-win-core-io-l1-1-0.dll
api-ms-win-core-libraryloader-l1-1-0.dll
api-ms-win-core-localization-l1-1-0.dll
api-ms-win-core-localregistry-l1-1-0.dll
api-ms-win-core-memory-l1-1-0.dll
api-ms-win-core-misc-l1-1-0.dll
api-ms-win-core-namedpipe-l1-1-0.dll
api-ms-win-core-processenvironment-l1-1-0.dll
api-ms-win-core-processthreads-l1-1-0.dll
api-ms-win-core-profile-l1-1-0.dll
api-ms-win-core-rtlsupport-l1-1-0.dll
api-ms-win-core-string-l1-1-0.dll
api-ms-win-core-synch-l1-1-0.dll
api-ms-win-core-sysinfo-l1-1-0.dll
api-ms-win-core-threadpool-l1-1-0.dll
api-ms-win-core-util-l1-1-0.dll
api-ms-win-core-xstate-l1-1-0.dll
api-ms-win-security-base-l1-1-0.dll
api-ms-win-security-lsalookup-l1-1-0.dll
api-ms-win-security-sddl-l1-1-0.dll
api-ms-win-service-core-l1-1-0.dll
api-ms-win-service-management-l1-1-0.dll
api-ms-win-service-management-l2-1-0.dll
api-ms-win-service-winsvc-l1-1-0.dll

これを見ると、「Kernel32!OpenProcess」が実際には大した働きをせず、単に、スタブDLLの1つ(api-ms-win-core-synch-l1-1-0.dll)からインポートされる「OpenProcess_0」へジャンプしているだけ、ということがわかります。

IDA ProとDependency Walkerを使えば、この依存関係はひと目でわかります。しかし、「api-ms-win-core-synch-l1-1-0!OpenProcess」を逆アセンブルしたコードをより詳しく見てみると、驚いたことにこの関数は実際には空で、単に0を返してくるにすぎません。しかもエクスポートした関数のうち、引数が3のものはすべて、同じ関数スタブ(下図参照)を共有していることが分かるでしょう。では、「Kernel32!OpenProcess」は結局のところ空関数なのに、なぜうまく機能するのでしょうか?

その秘密は、このDLLのロードプロセスにあります。デバッガWindbgの出力結果から、「Kernel32!OpenProcess」は実行中に「api-ms-win-core-synch-l1-1-0!OpenProcess」にジャンプしないことがわかります。さらに、「OpenProcess」のインポートテーブル・エントリーは、実際には「Kernelbase!OpenProcess」のアドレスで埋められていて、「api-ms-win-*.dll」はいずれもプロセスアドレス空間(!pebの出力を参照)にロードされないことがわかりました。

実際に動作するコードは、「Kernel32!OpenProcess」から「Kernelbase!OpenProcess」(下図参照)に移動し、そこでさらに「Ntdll!ZwOpenProcess」を実行しています。ちなみに、「アーキテクチャの階層に沿ったコードの修正」では、「OpenProcess」だけでなくほとんどのWin32 APIがその対象となりました。

次回では、Windows 7の新機能である、仮想化とリモート・アプリケーションを組み合わせた「Windows XP Mode(XPM)」について取り上げたいと思います。

関連記事

※本ページの内容はMcAfee Blogの抄訳です。
原文:Windows 7 – Kernel API Refactoring

[レポート]クラウド環境の現状レポートと今後 ~クラウドの安全性の状況と実用的ガイダンス

 マカフィーでは、1,400人のIT担当者に年次アンケートを実施し、クラウド採用状況やセキュリティについて調査しました。
 調査の結果、クラウドの採用とリスク管理への投資を増やしている組織がある一方で、クラウドの採用に慎重なアプローチをしている組織が多いことがわかりました。
 本調査では、クラウドサービスの利用状況を分類し、短期投資の確認、変化速度の予測、重要なプライバシーおよびセキュリティ上の障害物への対応方法の概要を示しています。

 本レポートでは、クラウドの現状把握と今後の方向性、クラウド対応の課題やポイントを理解することができます。

<掲載内容>
■ 主要調査結果
■ 調査結果から言える方向性
■ 課題への対応
■ 変化への対応力
■ 考慮すべき点:安全なクラウドの採用で事業を加速