ドライバー検証ツールは、1 つ以上のドライバーを検証するたびに、次のチェックを実行します。 これらのチェックをアクティブ化または非アクティブ化することはできません。 Windows 10 バージョン 1709 以降では、これらの自動チェックは関連する 標準フラグに移動されました。 その結果、標準フラグでドライバー検証ツールを有効にしているユーザーには、適用されるチェックの減少は表示されません。
IRQL とメモリ ルーチンの監視
ドライバー検証ツールは、次の禁止されたアクションについて、選択したドライバーを監視します。
KeLowerIrql を呼び出して IRQL を発生させる
KeRaiseIrql を呼び出して IRQL を下げる
サイズ 0 のメモリ割り当てを要求する
IRQL > APC_LEVEL でページ プールを割り当てまたは解放する
IRQL > DISPATCH_LEVELで非ページ プールを割り当てるまたは解放する
以前の割り当てから返されなかったアドレスを解放しようとしています
既に解放されているアドレスを解放しようとしています
IRQL > APC_LEVELで高速ミューテックスを取得または解放する
IRQL がDISPATCH_LEVELと等しくないスピン ロックを取得または解放する
スピン ロックをダブルリリースします。
割り当て要求 MUST_SUCCEED をマークします。 このような要求は許可されません。
ドライバー検証ツールがアクティブでない場合、これらの違反によって、すべてのケースで即時のシステム クラッシュが発生しない可能性があります。 ドライバー検証ツールは、ドライバーの動作を監視し、これらの違反のいずれかが発生した場合0xC4バグ チェックを発行します。 バグ チェック パラメーターの一覧については、バグ チェック 0xC4 (DRIVER_VERIFIER_DETECTED_VIOLATION) を参照してください。
スタック切り替えの監視
ドライバー検証ツールは、検証中のドライバーによるスタックの使用状況を監視します。 ドライバーがスタックを切り替え、新しいスタックがスレッド スタックでも DPC スタックでもない場合は、バグ チェックが発行されます。 (これは、最初のパラメーターが 0x90 と等しいバグ チェック 0xC4になります)。 KB デバッガー コマンドによって表示されるスタックには、通常、この操作を実行したドライバーが表示されます。
ドライバーのアンロード時のチェック
検証中のドライバーがアンロードされた後、ドライバー検証ツールは、ドライバーがクリーンアップされたことを確認するためにいくつかのチェックを実行します。
特に、ドライバー検証ツールは次を探します。
削除されていないタイマー
保留中の遅延プロシージャ 呼び出し (DPC)
未削除のルックアサイド リスト
未削除のワーカー スレッド
未削除のキュー
その他の同様のリソース
このような問題は、ドライバーのアンロード後しばらくしてシステムバグチェックが発行される可能性があり、これらのバグチェックの原因を特定するのが難しい場合があります。 ドライバー検証ツールがアクティブな場合、このような違反により、ドライバーがアンロードされた直後にバグ チェック0xC7が発行されます。 バグ チェック パラメーターの一覧については、バグ チェック 0xC7 (TIMER_OR_DPC_INVALID) を参照してください。
メモリ記述子リスト (MDL) の使用状況の監視
Windows Vista では、ドライバー検証ツールは、次の禁止されたアクションの選択したドライバーも監視します。
適切なフラグがない MDL で MmProbeAndLockPages または MmProbeAndLockProcessPages を呼び出します。 たとえば、MmBuildMdlForNonPagedPool を使用して作成された MDL に対して MmProbeAndLockPages を呼び出すのが正しくありません。
適切なフラグがない MDL で MmMapLockedPages を呼び出す。 たとえば、既にシステム アドレスにマップされている MDL またはロックされていない MDL に対して MmMapLockedPages を呼び出すのが正しくありません。
部分的な MDL(つまり、IoBuildPartialMdl を使用して作成された MDL) で MmUnlockPages または MmUnmapLockedPages を呼び出す。
システム アドレスにマップされていない MDL で MmUnmapLockedPages を呼び出します。
ドライバー検証ツールがアクティブでない場合、これらの違反により、システムがすべてのケースですぐに応答を停止しない可能性があります。 ドライバー検証ツールは、ドライバーの動作を監視し、これらの違反のいずれかが発生した場合0xC4バグ チェックを発行します。 バグ チェック パラメーターの一覧については、バグ チェック 0xC4 (DRIVER_VERIFIER_DETECTED_VIOLATION) を参照してください。
NonPagedPoolSession メモリからの同期オブジェクトの割り当て
Windows 7 以降、ドライバー検証ツールはセッション メモリからの同期オブジェクトをチェックします。
同期オブジェクトは、ページ化できないものである必要があります。 また、グローバルなシステム全体の仮想アドレス空間に住んでいる必要があります。
グラフィックス ドライバーは、 EngAllocMem などの API を呼び出すことによってセッション メモリを割り当てることができます。 グローバル アドレス空間とは異なり、セッション アドレス空間はターミナル サーバー セッションごとに仮想化されます。 これは、2 つの異なるセッションのコンテキストで使用されるのと同じ仮想アドレスが、2 つの異なるオブジェクトを参照することを意味します。 Windows カーネルは、任意のターミナル サーバー セッションから同期オブジェクトにアクセスできる必要があります。 別のセッションからセッション メモリ アドレスを参照しようとすると、システムのクラッシュや別のセッションのデータのサイレント破損など、予期しない結果が発生します。
Windows 7 以降では、検証済みドライバーが KeInitializeEvent や KeInitializeMutex などの API を呼び出して同期オブジェクトを初期化すると、ドライバー検証ツールは、オブジェクトのアドレスがセッション仮想アドレス空間内にあるかどうかを確認します。 ドライバー検証ツールは、この種の正しくないアドレスを検出した場合、0xDFのパラメーター 1 の値を持つ バグ チェック 0xC4: DRIVER_VERIFIER_DETECTED_VIOLATIONを発行します。
オブジェクト参照カウンターの 0 から 1 への変更
Windows 7 以降、ドライバー検証ツールは、正しくないオブジェクト参照の追加クラスをチェックします。
Windows カーネル オブジェクト マネージャーが File オブジェクトや Thread オブジェクトなどのオブジェクトを作成すると、新しいオブジェクトの参照カウンターは 1 に設定されます。 参照カウンターは、 ObReferenceObjectByPointer や ObReferenceObjectByHandle などの API の呼び出しによってインクリメントされます。 参照カウンターは、同じオブジェクトに対するすべての ObDereferenceObject 呼び出しによってデクリメントされます。
参照カウンターが 0 の値に達すると、オブジェクトは解放の対象になります。 オブジェクト マネージャーは、すぐに解放するか、後で解放する可能性があります。 ObReferenceObjectByPointer または ObDereferenceObject を呼び出し、参照カウンターを 0 から 1 に変更すると、既に解放されているオブジェクトの参照カウンターがインクリメントされます。 他のユーザーのメモリ割り当てが破損する可能性があるため、これは常に正しくありません。
システムシャットダウンブロックまたは遅延
Windows 7 以降、ドライバー検証ツールは、起動後 20 分後にシステムのシャットダウンが完了しない場合にカーネル デバッガーに中断を発行します。 ドライバー検証ツールは、Windows カーネルがレジストリ、プラグ アンド プレイ、I/O マネージャー サブシステムなどのさまざまなサブシステムのシャットダウンを開始する時刻として、システムのシャットダウンの開始を割り当てます。
カーネルデバッガーがシステムにアタッチされていない場合、ドライバー検証ツールはバグチェック 0xC4: DRIVER_VERIFIER_DETECTED_VIOLATIONを発行し、ブレークポイントの代わりに、パラメーター1の値0x115となります。
多くの場合、20 分未満で終了できないシステムシャットダウンは、そのシステムで実行されているドライバーの 1 つが誤動作していることを示します。 カーネル デバッガーから !analyze -v を実行すると、シャットダウンを担当するシステム ワーカー スレッドのスタック トレースが表示されます。 そのスタック トレースを調べて、テスト対象のドライバーのいずれかでシャットダウン スレッドがブロックされているかどうかを確認する必要があります。
システムが重いストレステストにさらされているため、すべてのドライバーが正しく機能していても、シャットダウンできない場合があります。 ユーザーは、このドライバー検証ツールのブレークポイントの後に実行を続行し、システムが最終的にシャットダウンするかどうかを確認できます。