none
Xinputドライバ開発の情報は? RRS feed

  • 全般的な情報交換

  • お世話になります。

    以前WDF/KMDFで非USBのHIDジョイスティックのドライバを書いたのですが、最近はXinput対応アプリも多いようなので新たにXinputドライバの製作を検討しています。

    しかし探し方が悪いのか検索してもアプリケーションからのXinputのAPIの呼び出し方ばかり引っかかってしまい、肝心のXinputドライバ開発の情報が見つけられません。

    USのWDKフォーラムで近い質問("How do I write a dummy Microsoft Common Controller Class / XInput driver?"/既存コントローラをPlayer2に認識させるためのダミードライバを作りたい)がありましたが、結局ワークアラウンドの提示のみでクローズしています。

    Xinputドライバ開発の情報はどこにあるのでしょうか?


    以上宜しくお願い致します。


    • 編集済み 星 睦美 2013年12月18日 2:19 参照のためにハイパーリンクを付けました。
    • 種類を変更済み 星 睦美 2013年12月25日 4:07 今後も情報交換にご活用ください。
    2013年12月17日 9:27

すべての返信

  • 私の理解だと、Xinputドライバというのは存在しなくて、ドライバは標準USB HIDを使用する、Xinputのデバイスというものが、世の中には存在している様です。

    それで、どうやってXinputのデバイスを作成するかといえば、例えば以下の様なページが該当すると思います。

    http://msdn.microsoft.com/en-us/library/dd145260.aspx

    http://msdn.microsoft.com/en-us/library/windows/desktop/hh405052(v=vs.85).aspx

    今回の質問では、どのようなデバイスでの入力を想定しているのかがわかりませんが、何らかのXinputデバイスのふりをして動作するドライバを開発するのでしたらば、自分でXinputデバイスの機能を調べて、それをシミュレーションするHIDのドライバを作るしかないと思います。

    2013年12月19日 14:36
    モデレータ
  • 日高様

    返信有難うございます。
    自分も最初は特殊なHIDデバイスかと思い、それであれば自作のHIDジョイスティックドライバのディスクリプタを差し替えるだけかと思っていたのですが、Xbox360コントローラのドライバの構成ファイルを見るとどうも違うようで混乱しています。
    以下はXbox360コントローラのINFファイルの抜粋です。

    [Version]
    Signature="$WINDOWS NT$"
    Class=XnaComposite
    ClassGUID={D61CA365-5AF4-4486-998B-9DB4734C6CA3}
    (中略)
    [Manufacturer]
    %MSFT%=MSFT,NTx86,NTamd64,NTx86.6.0,NTamd64.6.0

    [MSFT.NTx86.6.0]
    %XUSB21.DeviceName.Wired%=CC_Install, USB\Vid_045E&Pid_028E
    %XUSB21.DeviceName%=CC_Install, USB\Vid_045E&Pid_0719
    %XUSB21.DeviceName.Wired%=CC_Install, USB\MS_COMP_XUSB10
    %XUSB21.DeviceName%=CC_Install, USB\MS_COMP_XUSB20
    %XUSB21.DeviceName.Jump%=CC_Install, USB\Vid_045E&Pid_028F
    (中略)
    [CC_Install_CoInstaller_AddReg]

    HKR,,CoInstallers32,0x00010000, "WdfCoInstaller01007.dll,WdfCoInstaller"
    (中略)
    [XUSB21_wdfsect]
    KmdfLibraryVersion = 1.1

    [CC_XUSB21_Service]
    DisplayName    = %XUSB21.ServiceName%
    ServiceType    = 1 ; SERVICE_KERNEL_DRIVER
    StartType      = 3 ; SERVICE_DEMAND_START
    ErrorControl   = 0 ; SERVICE_ERROR_IGNORE
    ServiceBinary  = %12%\xusb21.sys
    (以下略)

    冒頭にClass=XnaCompositeとあるこのようにHIDクラスではなく、XnaCompositeクラスのドライバのようです。
    またinfファイル内の記述からKMDFで書かれている事は間違いなさそうなのですが、KMDFでHIDミニポートドライバを構成する際に必要なパススルードライバ http://msdn.microsoft.com/ja-jp/library/ff540774(v=vs.85).aspx の記述がありませんでした。
    この事もHIDドライバではないのでは?と思った理由です。

    この「XnaComposite」クラス(Microsoft common controller class?)のミニポートドライバを書く必要があると思うのですが、資料がまるで見つからない状態です。
    引き続き調査中ですので、質問のステータスとしてはオープン継続としたいと思います。
    また何か情報が見つかりましたらお知らせください。

    以上宜しくお願い致します。
    2013年12月20日 15:43
  • 失礼しました。

    すでに見ているとは思いますが、以下のOSRのスレッドでもD.Holan氏がボケているので、確かに何か秘密がありそうですね。

    http://www.osronline.com/ShowThread.cfm?link=223146

    他社のがどうなっているか気になります。

    2013年12月21日 17:08
    モデレータ
  • ご提示いただいた INF ファイルを見る限り (というか Class Name もそのものずばりですが。。。)、このドライバは usbccgp のような Composite Device 用の構成になっているように見受けられます。
    ということは "XnaComposite" クラスの下にクライアント デバイス用のクラスが存在していると思われますが、デバイス マネージャ上でのデバイス接続別ツリーではどのような表示になっていますでしょうか?
    あるいは DevCon ツールまたは WinDBG で DeviceNode の関係を確認したときに、"XnaComposite" クラスに対する親/子/孫はどのようなノードになっているのでしょうか?
    (質問を質問で返してしまって申し訳ありません。)

    個人的な感想ですが。。。
    既に「お手本」になるドライバが手元に存在するのであれば、関連ドキュメントを探すよりも、このドライバの動きを自分で確認する方が、解決の近道になると思います。
    具体的には、"XnaComposite" クラスに Upper Filter としてアタッチさせるクラス フィルタ ドライバを用意し、"XnaComposite" クラス ドライバに入ってくるすべてのリクエストとその応答を調べれば、XInput 機能をサポートするために何が必要なのか、そのヒントが見えてくると思います。
    (ただしフィルタ ドライバを用いたこの手の調査は、かなりの「忍耐」を必要としますが。。。)

    クラス フィルタ ドライバを用いた調査に関しては、下記サイトが参考になると思います。
    ------------------------------------------------------------
    ClasFiltサンプルINFファイル
    http://blogs.msdn.com/b/jpwdkblog/archive/2010/02/28/clasfilt-inf-install.aspx
    ------------------------------------------------------------

    以上、参考になりましたら幸いに存じます。

    2013年12月22日 6:27
  • 日高様

    >D.Holan氏がボケているので

    OSRも見てました。ドライバ製作者からすると神のような人ですが、ゲーミングサブシステムに関しては守備範囲外なのかもしれませんね。

    2013年12月23日 10:50
  • お馬鹿様

    確かに複合デバイスですね。
    Xbox360のコントローラにはヘッドセット用のジャックがあるので機能はジョイスティック+オーディオデバイスっぽいです。
    実機が手元にあれば詳細を調べられるのですが、まだドライバが作成可能か調査中の段階で実機はまだ購入していません。
    (調査のみで買うには高額で)
    ただ画像検索等で調べた限りではデバイスマネージャーに[Windows クラス用の Microsoft 共通コントローラー]というクラスが新たにでき、その下に[Xbox 360 Controller for Windows]が表示されるようです。

    >既に「お手本」になるドライバが手元に存在するのであれば、関連ドキュメントを探すよりも、このドライバの動きを自分で確認する方が、解決の近道になると思います。

    公式に公開されている情報がなさそうな現状ではそれしかなさそうですが、仰るとおりハードルが高いですね…
    リクエストの解析だけでちょっと手間が割りに合わないというのが正直なところです。作りたいのはただのジョイスティックなので。
    またリバースエンジニアリングの是非の話も出そうです。

    興味のある分野なのですが、このXnaCompositeクラスの公式情報が存在しないようなので今回は諦めるしかなさそうです。
    回答有難うございました。
    2013年12月23日 11:02
  • どーでもいいことなので大変恐縮なのですが、すっごく気になっているので、最後に一点だけ教えていただけますでしょうか?
    (また質問で返してしまって大変申し訳ないのですが。。。)

    本スレッドで提示されている OSR のスレッドに関して、Comfy Guy さん、Atomu Hidaka- さん共に Doron Holan さんのリプライが「ボケている」との認識で一致しているようですが、どこら辺が「ボケている」のでしょうか?

    私の足りない語学力と技術力では、「ボケている」部分が全然わからいのです。。。
    (私には Doron Holan さんのリプライが、"XnaComposite" クラスの構造も理解した上での適切なアドバイスに映るのです。)

    2013年12月24日 1:57
  • 日高さんの言わんとしているところはボケているいうより「はぐらかしてる?」という意味かと解釈しましたがどうでしょう。

    OSRで質問している方もXinput(XUSB)ドライバを実装しようとして静的にドライバをロードし、それに対するリクエストを調べようとしています。
    それに対してのHolanさんの回答はドライバのスタックは正しいか、そしてフィルタドライバを挟めばどうか?という一般的な回答をしていますね。(要はお馬鹿様の提案と同じ調査の為のアプローチ)

    ただHolanさんの立場を考えたとき、そういう調査方法の提案ではなく、そのものズバリの回答(それこそ該当クラスの詳細情報のありかとか実装の為の他のアプローチ)が出てきてもおかしくないとも思ったりもします。
    質問者の意図は読み違いようもないので。

    で、私としてはかのHolanさんもこのあたりは守備範囲外(本当に知らない)か、もしくはこのあたりの情報は要NDAなので一般的な回答に留めたのかなと裏読みしてました。
    流石に「おじいちゃんボケちゃって」とは思ってません。;-)
    2013年12月24日 6:13
  • ご回答いただき、ありがとうござます。
    (Comfy Guy さんの質問スレッドで私が逆に質問してしまい、大変申し訳ありまあせんでした。)

    ただ。。。私にはやはり Doron Holan さんが「はぐらかしている」とも思えないのです。
    あえて言うなら、「話が噛み合っていないので、質問の背景を明確にしようとしたけど、結局噛み合いそうにないので、途中で返信をやめた。。。」という感じがしました。
    (なので、「ボケている」のは Daniel Newton さんの方では。。。と思うのです。)

    一応私がなぜそのように感じたのかを、以下に記載しておきます。

    ----------
    あの OSR のスレッドで Daniel Newton さんは、「WinUSB を利用して作成したドライバを Xinput ドライバの PDO にアタッチさせたてみたけど、Read / Write の URB パケットが来ない!」ということを問題視されていると私は理解しました。
    が、Xinput ドライバは Client Device 用ドライバのはず(?)ですから、このドライバが生成する Device Object は FDO だと思うのです。
    また、ジョイスティックに限らずキーボード/マウス用の HID ドライバもそうだと思うのですが、それらドライバが USB などの接続バスを意識するのもおかしい気がします。
    HID デバイスにおける接続バス毎のハンドリングは hidclass ドライバよりも下位のレイヤで対応すべき話であり、そのために hidusb ドライバが存在している。。。というのが私の理解です。
    このような理由から「WinUSB を利用して作成したドライバを Xinput ドライバの PDO にアタッチさせたてみた」という内容は異質に感じました。
    なので Doron Holan さんも、「xid と WinUSB が同じ(デバイス)スタックにあるの?」と疑問に感じたんだと思うのです。
    また HID USB デバイスに限らす、一般的な USB デバイスでもそうですが、Client Device への Read / Write リクエストが URB パケットに変換されるのは、usbhub ドライバに渡される手前です。
    HID USB デバイスの場合、hidusb から usbhub に処理が渡される間に URB への変換が行われるはずなので、その上位レイヤで Read / Write の URB パケットが扱われることは無いと思うのです。
    Doron Holan さんが「xnacc と PDO の間にフィルタかまして、URB のトラフィックを調べたの?」と確認しているのも、このような理由からでは。。。
    ----------

    上記のような理由から、私には Doron Holan さんの返信は非常に正当な内容であると私には感じました。
    (もっとも、私は xid や xnacc のドライバを調べたことがないので、私の認識が根本的に間違っているのかもしれませんが。。。)

    2013年12月24日 10:07
  • お馬鹿様

    件のスレッドはNewtonさんの書き込みを真に受けてこういう理解でした。

    My current approach has been to leverage the "Xinput Driver for Microsoft
    Common Controller" by statically enumerating a PDO that looks like a
    suitable USB device.
    調査用に「USBデバイスに見せかけたなんちゃってPDO」を作成し、それに対してXinputDriverロードさせる事にした。
    ※普通ならUSB機器を接続→USBバスドライバがPDOを作成しますが、どうにかして偽PDOを列挙させた?

    I can load winusb onto this PDO and read/write to it
    この「なんちゃってPDO」に対して試しにWinUSBドライバをロードし、ローカルIOターゲットに対してReadWriteのリクエストはできた。

    but MS's Xinput driver will read descriptors, set configurtration etc but
    then will not send any read/write URBs.
    しかし(WinUSBではなく)XinputドライバをなんちゃってPDOの上にロードした時、Xinputドライバは下層のローカルIOターゲットに対してディスクリプタの読み取りやコンフィグレーションといったUSBリクエストは行うが、その後はあらゆるリクエストを投げてこない。

    ---------------------------------------------------------------------------
    つまりNewtonさんの主張では、実際のXbox360コントローラに見せかけたなんちゃってPDOを作成し、ドライバスタックの最下層でXinputDriverがローカルIOターゲットに投げるUSBリクエストをモニタしようとしていたとの理解です。
    これなら位置的にURBもモニタできそうです。(そんなことが本当に出来るかどうかは当方は知らないのですが)
    まぁ真意や実際のところは確かめようもありません。
    2013年12月24日 14:41
  • ちょっと見ない間にこんな議論になっていたとは…

    私の「ボケた」の指摘はフィルタ問答の後で、Holan氏が(私の推測では何か知っているはずなのに)それ以上の回答を止めたことです。Comfy Guy さんと全く同じ読みです。そもそもの質問が「Is there any documentation about implementing the XUSB class interface」だった訳ですから「はぐらかした」と感じました。

    ちなみに彼はおじいちゃんではありません。

    2013年12月24日 18:05
    モデレータ
  • ご返信いただき、ありがとうござます。

    -----------------------------------

    Comfy Guy さん:
    確かに一番最後に "I created the pdo so yes" と言っているので、私も当初 Daniel Newton さんは 「PDO を提供するドライバを作成した」と思ったのですが、それだと以下のような疑問がわいてしまい、もっと訳が分からなくなってしまうのです。

    ☆ hidclass のようなクラス ドライバを作成すれば、確かに PDO を提供することは可能だと思いましたが、
       そのクラスが提供する機能の詳細が分からない状態でクラス ドライバを作れるのか?
      (この場合、XnaComposite クラスと同等のドライバを作成したのかな。。。と思ったのですが、
        XnaComposite クラスの仕様がわからない状態で、そんなことできるのか?)

    ☆ そもそも Daniel Newton さんは Xinput Driver の挙動を調査したかったんだと思うのですが、
       だったらなぜ Xinput Driver の FDO にアタッチさせるフィルタ ドライバにしなかったのか?
      (あるいは XnaComposite クラスに対するクラス フィルタ ドライバではだめなの?)

    ☆ クラス ドライバを作成したと仮定した場合、クライアント デバイス (ローカル I/ Oターゲット)
       に対する Read / Write リクエスト (IRP) をクラス ドライバでキャッチすることは可能なのか?
      (ローカル I/ Oターゲットへの Read / Write リクエストは FDO に対して発行されると思いますが、
        そのリクエストを下位のクラス ドライバでキャッチできるとは思えない。)

    etc.

    Daniel Newton さんが URB パケットのトラフィックをモニタしたかったであろうことは私にも理解できたのですが、それだったらなぜ FDO や PDO にアタッチさせるフィルタ ドライバにしなかったのか、なぜわざわざ難しい(と思われる) PDO を提供するドライバにしたのか、その理由が全く分からないのです。
    また、Daniel Newton さんが作ったドライバを組み込んだデバイス スタック構成で、本当に正しく動作していたのか、私には質問内容自体が疑問だらけなのです。
    (それは私が xid や xnacc のドライバを調べたことがないことに起因しているのかもしれませんが。。。)

    -----------------------------------

    Atomu Hidaka- さん:
    Doron Holan さんが「何か知っているのにはぐらかした」と感じたとのことですが、それは「Daniel Newton さんの質問は妥当である」との前提が無ければそう感じないと私は思ったのです。
    ということは、Atomu Hidaka- さんはあの質問内容を理解されていると思いますので、それを教えて頂きたいと思った次第です。
    もし Comfy Guy さんと同じ見解であるならば、「USBデバイスに見せかけたなんちゃってPDO」をどうやって作成するのか、あるいは Comfy Guy さんと異なるのであれば、どのように理解されたのか、それを教えていただければ幸いに存じます。
    (それがわかれば、このモヤモヤがかなりスッキリできると思います。)

    -----------------------------------

    2013年12月25日 3:26
  • お馬鹿様

    >hidclass のようなクラス ドライバを作成すれば、確かに PDO を提供することは可能だと思いましたが、

    逆にこの辺の表現がわからないのですが…
    通常のUSB-HIDデバイスの場合もPDOを作るのはHIDClassDriverではなくてUSBのBusDriverですよね?
    USB-HIDのスタックは以下の順に積まれる理解なのですが誤りがあれば教えて下さい。

    1、USB-BusDriverは機器が接続されたのを検知し、ハードウェアIDやUSBディスクリプタを取得してPDOを作成。
    2、OSはPDOのハードウェアIDを見てドライバを探す。
      →大抵の場合OSが持ってるHID-Miniドライバをロードする。
    3、ロードされたHID-MiniドライバがHidRegisterMinidriver()を発行して上位のHID-ClassDriverに自身を登録。

    なのでスタックとしては下から「USB-BusDriverが作ったPDO」→「HID-MiniDriver」→「HIDClassDriver」との理解でしたが。
    で、IOリクエストは逆に上位HID-ClassDriverからHID-MiniDriverを経由してUSBローカルIOターゲットへ流れる、と。

    ちなみに当方が以前書いたHIDジョイスティックドライバは「非」USB機器で、USBドライバの開発経験は学習用に書いた程度です。

    2013年12月25日 6:48
  • > 逆にこの辺の表現がわからないのですが…
    > 通常のUSB-HIDデバイスの場合もPDOを作るのはHIDClassDriverではなくてUSBのBusDriverですよね?
    > USB-HIDのスタックは以下の順に積まれる理解なのですが誤りがあれば教えて下さい。

    各デバイス ノードのスタックが積まれていく順番は、私も Comfy Guy さんと同じ認識です。
    ただ PDO に対する認識が異なっているようです。
    私の言う PDO とは、「各デバイス ノードで基底となるデバイス オブジェクト」という意味で使っています。
    一般的に PDO というとバス ドライバが作るデバイス オブジェクトととらわれがちですが、クラス ドライバが提供するデバイス ノードで基底となるデバイス オブジェクトも PDO であるというのが私の認識です。

    言葉で説明するよりも図解の方がわかりやすいと思いますので、可能であれば WDK 7600.16385.1 に同梱されている Help Document の下記トピックをご参照ください。
    (一世代前の WDK ですが。。。最新の WDK Help Document では、なぜかこれらの図解部分が削除されているようです。)

    --------------------------------------------------
    <WDK 7600.16385.1 Help Document>
       Human Input Devices
        + Design Guide

           + Interactive Input Device Architecture
              + Driver Stacks for HIDClass Devices
                 + Device Stacks for USB Keyboard, Mouse, and Joystick Devices
                 + Driver Stacks for HIDClass Game Port Devices
                 + Driver Stacks for a Generic HIDClass Device
              + Driver Stacks for Non-HIDClass Devices
                 + Device Stacks for Non-HIDClass Keyboard, Mouse, and Joystick Devices
                 + Driver Stacks for Non-HIDClass Game Port Devices
           + HIDClass Devices
              + Device Stacks for HIDClass Devices
                 + Device Stacks for USB Keyboard, Mouse, and Joystick Devices  ☆ ← 特にこれ
                 + Device Stacks for Game Port Devices
                 + Device Stacks for Generic HIDClass Devices
    --------------------------------------------------

    あるいは、WinDBG でも同じことが確認できると思います。
    以下に。WinDBG で採取したログを添付しておきます。

    ------------------------------------------------------
    0: kd> !drvobj \driver\mouclass
    Driver object (863d3700) is for:
     \Driver\mouclass
    Driver Extension List: (id , addr)

    Device Object list:
    86ae6c40  86601030 
    ------------------------------------------------------
    0: kd> !devstack 0x86601030
      !DevObj   !DrvObj            !DevExt   ObjectName
    > 86601030  \Driver\mouclass   866010e8  PointerClass0
      863d3380  \Driver\TermDD     863d3438 
      850eca80  \Driver\PnpManager 850ecb38  0000003b   ; ☆ ← PDO
    !DevNode 850ec8c8 :
      DeviceInst is "Root\RDP_MOU\0000"
      ServiceName is "TermDD"
    ------------------------------------------------------
    0: kd> !devstack 0x86ae6c40 
      !DevObj   !DrvObj            !DevExt   ObjectName
    > 86ae6c40  \Driver\mouclass   86ae6cf8  PointerClass1
      86af3528  \Driver\mouhid     86af35e0 
      86af25c0  \Driver\HidUsb     86af2678  0000005e   ; ☆ ← PDO
    !DevNode 86af09b8 :
      DeviceInst is "HID\VID_413C&PID_3010\7&f562498&0&0000"
      ServiceName is "mouhid"

    0: kd> !DevNode 86af09b8
    DevNode 0x86af09b8 for PDO 0x86af25c0
      Parent 0x860b9258   Sibling 0000000000   Child 0000000000
      InstancePath is "HID\VID_413C&PID_3010\7&f562498&0&0000"
      ServiceName is "mouhid"
      TargetDeviceNotify List - f 0x8d2f1bf8  b 0x8d2f1380
      State = DeviceNodeStarted (0x308)
      Previous State = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[12] = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[11] = DeviceNodeEnumeratePending (0x30c)
      StateHistory[10] = DeviceNodeStarted (0x308)
      StateHistory[09] = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[08] = DeviceNodeEnumeratePending (0x30c)
      StateHistory[07] = DeviceNodeStarted (0x308)
      StateHistory[06] = DeviceNodeStartPostWork (0x307)
      StateHistory[05] = DeviceNodeStartCompletion (0x306)
      StateHistory[04] = DeviceNodeStartPending (0x305)
      StateHistory[03] = DeviceNodeResourcesAssigned (0x304)
      StateHistory[02] = DeviceNodeDriversAdded (0x303)
      StateHistory[01] = DeviceNodeInitialized (0x302)
      StateHistory[00] = DeviceNodeUninitialized (0x301)
      StateHistory[19] = Unknown State (0x0)
      StateHistory[18] = Unknown State (0x0)
      StateHistory[17] = Unknown State (0x0)
      StateHistory[16] = Unknown State (0x0)
      StateHistory[15] = Unknown State (0x0)
      StateHistory[14] = Unknown State (0x0)
      StateHistory[13] = Unknown State (0x0)
      Flags (0x2c000130)  DNF_ENUMERATED, DNF_IDS_QUERIED,
                          DNF_NO_RESOURCE_REQUIRED, DNF_NO_LOWER_DEVICE_FILTERS,
                          DNF_NO_LOWER_CLASS_FILTERS, DNF_NO_UPPER_DEVICE_FILTERS
      CapabilityFlags (0x00001e83)  DeviceD1, DeviceD2,
                                    SilentInstall, SurpriseRemovalOK,
                                    WakeFromD0, WakeFromD1,
                                    WakeFromD2
    0: kd> !DevNode 0x860b9258  
    DevNode 0x860b9258 for PDO 0x86aed6a8
      Parent 0x86a59e78   Sibling 0000000000   Child 0x86af09b8
      InstancePath is "USB\VID_413C&PID_3010\6&3657bec4&0&4"
      ServiceName is "HidUsb"
      State = DeviceNodeStarted (0x308)
      Previous State = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[12] = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[11] = DeviceNodeEnumeratePending (0x30c)
      StateHistory[10] = DeviceNodeStarted (0x308)
      StateHistory[09] = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[08] = DeviceNodeEnumeratePending (0x30c)
      StateHistory[07] = DeviceNodeStarted (0x308)
      StateHistory[06] = DeviceNodeStartPostWork (0x307)
      StateHistory[05] = DeviceNodeStartCompletion (0x306)
      StateHistory[04] = DeviceNodeStartPending (0x305)
      StateHistory[03] = DeviceNodeResourcesAssigned (0x304)
      StateHistory[02] = DeviceNodeDriversAdded (0x303)
      StateHistory[01] = DeviceNodeInitialized (0x302)
      StateHistory[00] = DeviceNodeUninitialized (0x301)
      StateHistory[19] = Unknown State (0x0)
      StateHistory[18] = Unknown State (0x0)
      StateHistory[17] = Unknown State (0x0)
      StateHistory[16] = Unknown State (0x0)
      StateHistory[15] = Unknown State (0x0)
      StateHistory[14] = Unknown State (0x0)
      StateHistory[13] = Unknown State (0x0)
      Flags (0x6c000130)  DNF_ENUMERATED, DNF_IDS_QUERIED,
                          DNF_NO_RESOURCE_REQUIRED, DNF_NO_LOWER_DEVICE_FILTERS,
                          DNF_NO_LOWER_CLASS_FILTERS, DNF_NO_UPPER_DEVICE_FILTERS,
                          DNF_NO_UPPER_CLASS_FILTERS
      CapabilityFlags (0x00001e13)  DeviceD1, DeviceD2,
                                    Removable, SurpriseRemovalOK,
                                    WakeFromD0, WakeFromD1,
                                    WakeFromD2

    0: kd> !devstack 0x86aed6a8
      !DevObj   !DrvObj            !DevExt   ObjectName
      86aef3d8  \Driver\HidUsb     86aef490  _HID00000001
    > 86aed6a8  \Driver\usbhub     86aed760  USBPDO-8       ; ☆ ← PDO
    !DevNode 860b9258 :
      DeviceInst is "USB\VID_413C&PID_3010\6&3657bec4&0&4"
      ServiceName is "HidUsb"

    0: kd> !DevNode 0x86a59e78  
    DevNode 0x86a59e78 for PDO 0x86a5d030
      Parent 0x8661e620   Sibling 0000000000   Child 0x86ad0008
      InstancePath is "USB\VID_0557&PID_7000\5&1ac6b29c&0&1"
      ServiceName is "usbhub"
      State = DeviceNodeStarted (0x308)
      Previous State = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[15] = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[14] = DeviceNodeEnumeratePending (0x30c)
      StateHistory[13] = DeviceNodeStarted (0x308)
      StateHistory[12] = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[11] = DeviceNodeEnumeratePending (0x30c)
      StateHistory[10] = DeviceNodeStarted (0x308)
      StateHistory[09] = DeviceNodeEnumerateCompletion (0x30d)
      StateHistory[08] = DeviceNodeEnumeratePending (0x30c)
      StateHistory[07] = DeviceNodeStarted (0x308)
      StateHistory[06] = DeviceNodeStartPostWork (0x307)
      StateHistory[05] = DeviceNodeStartCompletion (0x306)
      StateHistory[04] = DeviceNodeStartPending (0x305)
      StateHistory[03] = DeviceNodeResourcesAssigned (0x304)
      StateHistory[02] = DeviceNodeDriversAdded (0x303)
      StateHistory[01] = DeviceNodeInitialized (0x302)
      StateHistory[00] = DeviceNodeUninitialized (0x301)
      StateHistory[19] = Unknown State (0x0)
      StateHistory[18] = Unknown State (0x0)
      StateHistory[17] = Unknown State (0x0)
      StateHistory[16] = Unknown State (0x0)
      Flags (0x6c000130)  DNF_ENUMERATED, DNF_IDS_QUERIED,
                          DNF_NO_RESOURCE_REQUIRED, DNF_NO_LOWER_DEVICE_FILTERS,
                          DNF_NO_LOWER_CLASS_FILTERS, DNF_NO_UPPER_DEVICE_FILTERS,
                          DNF_NO_UPPER_CLASS_FILTERS
      CapabilityFlags (0x00001e13)  DeviceD1, DeviceD2,
                                    Removable, SurpriseRemovalOK,
                                    WakeFromD0, WakeFromD1,
                                    WakeFromD2
      DisableableDepends = 1 (from children)

    0: kd> !devstack 0x86a5d030
      !DevObj   !DrvObj            !DevExt   ObjectName
      86a69028  \Driver\usbhub     86a690e0  0000005c
    > 86a5d030  \Driver\usbhub     86a5d0e8  USBPDO-6       ; ☆ ← PDO
    !DevNode 86a59e78 :
      DeviceInst is "USB\VID_0557&PID_7000\5&1ac6b29c&0&1"
      ServiceName is "usbhub"
    ------------------------------------------------------

    2013年12月25日 7:53
  • >一般的に PDO というとバス ドライバが作るデバイス オブジェクトととらわれがちですが、クラス ドライバが提供するデバイス ノードで基底となるデバイス オブジェクトも PDO であるというのが私の認識です。

    これは理解していますが、今回の話ではNewtonさん曰く
    My current approach has been to leverage the "Xinput Driver for Microsoft Common Controller"
    by statically enumerating a PDO that looks like a suitable USB device.

    と言ってる事からここでは「USBバスドライバを模したPDO」と読みました。この文面からXnaCompositeClassのPDOを指すとは読み難いのですが・・・
    事実NewtonさんはXnaCompositeClassの詳細を知らない(と言うか誰も知らない)ので、「NewtonさんがXnaComposite クラスと同等のドライバを作成しアタッチさせた」と考えるのも無理がありませんか?
    それに「XnaComposite クラスのPDOにアタッチ」させたのなら、当然「それらドライバが USB などの接続バスを意識するのもおかしい」と思いますよ。

    ---------------------------------------

    ここからは全て想像ですが、Xbox360のコントローラがUSB機器でありXnaCompositeClassDriverが存在する(?)のであれば、HIDのスタックのように間に「秘密のXna-MiniDriver(?)」が入るのではないでしょうか。
    ※下から「USB-BusDriverが作ったPDO」→「Xna-MiniDriver(?)」→「XnaCompositeClassDriver(?)」
    で、当初の私の質問は「Xna-MiniDriver(?)」を作りたいが「XnaCompositeClass(?)」の仕様が判らない、という感じですね。

    >なぜわざわざ難しい(と思われる) PDO を提供するドライバにしたのか、その理由が全く分からないのです。

    (ここで指す"PDO"が当方が想像する"なんちゃってUSB-PDO"だという前提で)Newtonさんがなぜこのようなアプローチを取ったのかは当方では解りかねます。
    これも想像で恐縮ですが、、Newtonさんは"Xna-MiniDriver"を書くつもりは無く、Xbox360コントローラ純正ドライバを使用して動作する「Xbox360コントローラのフリをする仮想USB機器」のドライバを書きたかったのではないでしょうか。
    (つまりフェイクUSB-Xbox360コントローラを作成したかった)
    スタック的には下からこんな感じで。
    「"仮想Xbox360コントローラ"(なんちゃってUSB-PDO)」→「Xbox360コントローラ用"純正"ドライバ」→「XnaCompositeClassDriver(?)」
    であれば"a PDO that looks like a suitable USB device."と整合がとれますし、この方法が実現していれば「Xbox360コントローラ用純正ドライバ」と「XnaCompositeClassDriver(?)」の間のインターフェースを知らなくても良い事になります。

    重ねて言いますが単なる想像です。はっきりさせたければもうNewtonさん本人に聞くほか無いかと。
    ※上記書き込みは全て無責任・無保証です。
    2013年12月25日 9:09
  • > と言ってる事からここでは「USBバスドライバを模したPDO」と読みました。この文面からXnaCompositeClassのPDOを指すとは読み難いのですが・・・

    そもそも私は Newton さんが XnaComposite ドライバと同等の PDO を生成するドライバを作ったとは考えていません。
    私の勝手な解釈ですが、XnaComposite が提供するクラス ドライバ PDO と Xinput ドライバ FDO の間に、フィルタらしきドライバを組み込んだのだと想像しました。
    そのように想像した経緯は以下の通りです。

    ----------------------------------------------------------------
    <お馬鹿の想像>
    先に Comfy Guy さんが示された XnaComposite クラスの INF ファイルから、私はこれが Composite Device 用のドライバであると思いました。
    だとすると、「usbccgp ドライバと同じようなスタック構成になっているのでは?」と考えたわけです。
    (ですので一番初めの返信で、デバイス ノード構成がどうなっているのか、確認させていただきました。)

    なお usbccgp ドライバのスタック構成は、先に示した WDK Help Document の以下のトピックに図解があります。

    +++++++++++++++++++++++++++++++++++++++++++++++++++++++++
    <WDK 7600.16385.1 Help Document>
        Device and Driver Technologies
         + Bus and Port Drivers
            + Buses
               + USB
                  + Design Guide
                     + System-Supplied USB Drivers

                        + USB Driver Satck
                           + USB Driver Stack for Windows 2000
                           + USB Driver Stack for Windows XP and Later

                        + USB Device Satck
                           + USB Device Stack for Windows 2000
                           + USB Device Stack for Windows XP and Later
    +++++++++++++++++++++++++++++++++++++++++++++++++++++++++

    先の返信で私が「hidclass のようなクラス ドライバを作成すれば」と言ったのは、この usbccgp ドライバが提供しているような機能を指したつもりです。
    hidclass にしても usbccgp にしても、どちらもクラス ドライバである。。。というのが私の認識なので、「hidclass のようなクラス ドライバ」という表現をしてしまいました。
    (誤解を招くような紛らわしい表現で申し訳ありませんでした。)
    少なくとも、このような構成になるようなクラス ドライバを作成すれば、Xinput ドライバが属するデバイス スタックの PDO を、クラス ドライバで提供することが可能になると思っています。
    ですが Comfy Guy さんも指摘されていますように、「誰も知らない」XnaComposite クラスと同等のドライバを作成したとは考えにくいです。
    また「USBバスドライバを模した PDO (仮想Xbox360コントローラ)」であるならば、usbhub / usbehci 等をエミュレートするドライバ開発が必要になると思うのですが、それは現実的に不可能だと(可能であっても目茶目茶大変でクラス ドライバ開発の比ではないと)思うので、それはないだろうと(勝手に)判断しました。
    (私にとっては、「一番あり得ないだろうと。。。」と感じる方法。)
    となると、あと考えられるのは、XnaComposite ドライバが生成した(と勝手に思い込んでいますが)クラス ドライバの PDO と Xinput ドライバの間に、フィルタらしきドライバを組み込んだのかな。。。と考えた訳です。
    (これは私にとって一番現実的に感じる方法です。)

    ただ、そう考えると「一番最後の "I created the pdo so yes" って、どういう意味?」と無限ループにはまってしまうのです。
    ----------------------------------------------------------------


    > それに「XnaComposite クラスのPDOにアタッチ」させたのなら、当然「それらドライバが USB などの接続バスを意識するのもおかしい」と思いますよ。

    そうです、おかしいから質問が理解できないのです。


    要するに私には、Newton さんがどのような調査を行ったのか、その質問の背景が全く分からなかった訳で、「Holan さんもそうだったのでは?」と思ったのですが、お二人が「Holan さんは質問をはぐらかした」との認識で意見が一致しているのをみて、「Newton さんがどのような調査を行ったのか教えてほしい」と思ったわけです。
    もちろん、Newton さんの真の目的は本人に伺う以外に確かめる方法はないので、お二人にそのようなことは期待している訳ではありません。
    ただ、お二人は少なくとも「Newton さんの質問は妥当である」と感じている様だったので(これも私の勝手な思い込みですが)、だったら Newton さんがどのような調査をを行ったのか、教えていただきたいと思った次第です。
    (もちろん、教えていただいた内容が「無責任・無保証」であることも承知しています。)

    Comfy Guy さんのお考えは、ご返信いただいた内容で理解しました。(ただ残念ながら、納得はできてませんが。。。)
    どうもありがとうございました。

    2013年12月25日 11:22