20

私はドライバー開発にまったく慣れておらず、キーボードまたはマウスデバイスを有効または無効にする単純なフィルタードライバーを作成しようとしています。動作させることができれば、マウスが接続されているときにラップトップのタッチパッドを無効にするために使用したいと考えています。おそらくこれを行うソフトウェアが既に存在することはわかっていますが、デバイスドライバーに本当に興味があり、これを自分で行う方法を学びます。

私は、上位フィルター ドライバーとしてインストールされた、WDK に同梱されているkbfiltrmoufiltrの例を使用しています。kbfiltr の例では、ユーザーモード プログラムによって列挙および接続できる pdo が作成されます。これにより、KbFilter_EvtIoDeviceControlForRawPdoによって処理される PDO に IOCTL を送信できます。ただし、 KbFilter_EvtIoInternalDeviceControlを呼び出すなど、フィルター ドライバーに関連することを試してみると、次のようなことができます。

VOID
KbFilter_EvtIoInternalDeviceControl(
    IN WDFQUEUE      Queue,
    IN WDFREQUEST    Request,
    IN size_t        OutputBufferLength,
    IN size_t        InputBufferLength,
    IN ULONG         IoControlCode
    )
    ...
    hDevice = WdfIoQueueGetDevice(Queue);
    devExt = FilterGetData(hDevice);

    switch (IoControlCode) {      
    ...
      case IOCTL_INTERNAL_KEYBOARD_DISCONNECT:
       //
       // Clear the connection parameters in the device extension.
       //
       devExt->UpperConnectData.ClassService = NULL;
       break;
    ...
    }

BSOD が発生します。上記のコードではありません。バニラの例では、null への設定がコメント アウトされています。Kbfilter を呼び出すだけで BSOD が発生します。デバイス拡張機能を PDO で直接設定しようとしましたが、これも BSOD の原因になります。これはおそらく、kbfiltr ではなく PDO devExt であるためでしょうか?

(関連: BSOD からスタック トレースを取得する良い方法は何ですか? テスト環境として Virtual PC を使用し、XPSP3 の未チェックのビルドを使用しています)

IOCTL_INTERNAL_KEYBOARD_DISCONNECT をドライバー スタックに直接送信することはできません (入力デバイスは一度に 1 つの接続のみを受け入れることを理解していますか?) したがって、生の PDO が必要です。実際には 2 つの IOCTL (有効化と無効化) を送信するだけで済み、これらは既に定義されているため、キーボードの切断と接続を使用するだけでよいと考えました。

これらの仮定のいずれかについて間違っている場合は、お知らせください。私は本当に初心者であることを知っていますが、PDO を介したこの種の通信に関する多くのドキュメントは見つかりませんでした。

4

2 に答える 2

17

わかりました、私は最終的にこれを解決し、ドライバーは機能しています。

KMDF フィルター ドライバーの実装:

WinDbg の セットアップに役立つ COM ポート アプローチを提案してくれた Sergius に感謝します。この素晴らしいブログ投稿では、すばやくセットアップする方法について説明しています。基本的には、VPC で COM ポートを名前付きパイプとしてセットアップし、仮想化 OS でカーネル デバッグ モードを有効にして、起動中に接続します。その後、ドライバーのロード時にすべての DbgPrint メッセージを取得し、さらに多くのことを行うことができますが、起動プロセス中のトレース メッセージだけが私にとって大きな助けになりました。

私の主な問題は、KbFiltr で内部 IOCTL を再利用しようとしたことだと思います。内部 IOCTL と他の IOCTL の違いを理解していなかったので、これは私の設計上の悪い考えでした。また、この KB 記事「フィルター ドライバーに IOCTL を送信する方法」は、同じ制御デバイス構造を使用した例ですが、WDM です。

とにかく、週末を通して KbFiltr の例と戦った後、私はついにあきらめて、WDF Toaster/filterの例 を使い始めました。これは、より必要最小限の KMDF フィルター ドライバーであり、KbFiltr と MouFiltr を使用して多くの空白を埋める必要がありました。Toaster フィルター ドライバーの操作は KbFiltr に似ていますが、PDO の代わりにコントロール デバイスを作成します。また、制御デバイスの dos デバイス名を設定するため、その手順を実行するために Pinvoke を実行しなくても、ユーザーモードから制御デバイスと通信できます。コントロール デバイスを使用すると、コレクションを反復処理するだけで、フィルター ドライバーが読み込まれているすべてのデバイスを制御できます。コレクションへのアクセスを同期するために、待機ロックが使用されます。

また、INF ファイルを変更して (Toaster クラスの代わりに Mouse クラスを使用するように)、ドライバー コードを変更することなく、そのままテスト マシンに適用することもできました。機能しているものから始める方がはるかに簡単です。このページには、サンプルを適応させるために変更する必要があるものの包括的なリストが記載されています。

于 2009-09-24T12:37:01.707 に答える