DCH 準拠のドライバー パッケージの例

この記事では、DCHUドライバー サンプルが DCH 設計原則をどのように適用するかについて説明します。 これをモデルとして使用し、ご自分のドライバー パッケージに DCH 設計原則を適用できます。

サンプル リポジトリのローカル コピーが必要な場合は、Windows-driver-samples からクローンを作成します

このサンプルの一部では、特定のバージョンの Windows 10 以降でのみ使用できるディレクティブと API を使用する場合があります。 特定のディレクティブがサポートされている OS バージョンを確認するには、「デバイスとドライバーのインストール」を参照してください。

前提条件

このセクションを読む前に、DCH 設計原則を理解しておく必要があります。

概要

サンプルで提供されているシナリオ例では、2 つのハードウェア パートナー Contoso (システム ビルダーまたは OEM) と Fabrikam (デバイスの製造元または IHV) が共同で、Contoso の次期システムのデバイス向け DCH 準拠ドライバーを作成しています。 問題のデバイスは OSR USB FX2 学習キットです。 これまで、Fabrikam は、特定の Contoso 製品ライン用にカスタマイズされたレガシ ドライバー パッケージを作成し、サービスを処理するために OEM に渡していました。 その結果、大きなメンテナンス オーバーヘッドが発生していたため、Fabrikam は、コードをリファクタリングして、代わりに DCH 準拠ドライバー パッケージを作成することを決定しました。

宣言型セクションおよびディレクティブを使用して INF を適切に分離する

最初に、Fabrikam は DCH 準拠ドライバー パッケージで無効な INF のセクションとディレクティブの一覧を確認します。 この試し中に、Fabrikam はドライバー パッケージでこれらのセクションとディレクティブの多くを使用していることに気づきました。

Fabrikam のドライバーの INF は、プラットフォームに依存する設定とファイルを適用する共同インストーラーを登録します。 これはドライバー パッケージが必要以上に大きくて、ドライバーを出荷する OEM システムの一部のみにバグが影響する場合、ドライバーのサービスを提供することが非常に困難になるということです。 また、ほとんどOEM 固有の変更はブランドに関連しているため、OEM が追加されるたび、または不具合が OEM システムの一部に影響するたびに、Fabrikam はドライバー パッケージを更新する必要があります。

Fabrikam は、非宣言型セクションとディレクティブを削除し、InfVerif ツールを使って新しいドライバー パッケージの INF ファイルが宣言型 INF の要件に従っていることを確認します。

INF拡張機能を使いようしてドライバー パッケージを広がれる

次に、Fabrikam はOEM関連(Contoso など) の固有に応じて、基本ドライバー パッケージからINF拡張機能に分離します。

osrfx2_DCHU_extension.inx]から更新された次のスニペットでは、Extensionクラスを指定し、Contoso が拡張機能ドライバー パッケージを所有することになるため、プロバイダーとして Contoso を識別します

[Version]
...
Class       = Extension
ClassGuid   = {e2f84ce7-8efa-411c-aa69-97454ca4cb57}
Provider    = Contoso
ExtensionId = {zzzzzzzz-zzzz-zzzz-zzzz-zzzzzzzzzzzz} ; replace with your own GUID
...

[osrfx2_DCHU_base.inx] では、Fabrikam によって次のエントリが指定されています。

[OsrFx2_AddReg]
HKR, OSR, "OperatingMode",, "Default" ; FLG_ADDREG_TYPE_SZ
HKR, OSR, "OperatingParams",, "None" ; FLG_ADDREG_TYPE_SZ

[osrfx2_DCHU_extension.inx] で、Contoso により基本パッケージで設定された OperatingParams レジストリ値がオーバーライドされ、OperatingExceptions が追加されます。

[OsrFx2Extension_AddReg]
HKR, OSR, "OperatingParams",, "-Extended"
HKR, OSR, "OperatingExceptions",, "x86"

拡張機能は常に基本INFの後に処理されますが、明確な順序はありません。 基本 INF が新しいバージョンに更新された場合でも、新しい基本 INF のインストール後に拡張機能が再適用されます。

INF ファイルからサービスをインストールする

Fabrikam は、Win32 サービスを使用して OSR ボード上の LED を制御します。 同社にとってこのコンポーネントはデバイスのコア機能の一部であるため、基本 INF ([osrfx2_DCHU_base.inx]) の一部として組み込みます。 このユーザー モード サービス (usersvc) は、INF ファイルでAddService ディレクティブを指定することによって、宣言的に追加および開始できます。

[OsrFx2_Install.NT]
CopyFiles = OsrFx2_CopyFiles

[OsrFx2_Install.NT.Services]
AddService = WUDFRd, 0x000001fa, WUDFRD_ServiceInstall    ; Flag 0x2 sets this as the service for the device
AddService = osrfx2_DCHU_usersvc,, UserSvc_ServiceInstall

[UserSvc_ServiceInstall]
DisplayName = %UserSvcDisplayName%
ServiceType = 0x10                                ; SERVICE_WIN32_OWN_PROCESS
StartType = 0x3                                   ; SERVICE_DEMAND_START
ErrorControl = 0x1                                ; SERVICE_ERROR_NORMAL
ServiceBinary = %13%\osrfx2_DCHU_usersvc.exe
AddTrigger = UserSvc_AddTrigger                   ; AddTrigger syntax is only available in Windows 10 Version 2004 and above

[UserSvc_AddTrigger]
TriggerType = 1                                   ; SERVICE_TRIGGER_TYPE_DEVICE_INTERFACE_ARRIVAL
Action = 1                                        ; SERVICE_TRIGGER_ACTION_SERVICE_START
SubType = %GUID_DEVINTERFACE_OSRFX2%              ; Interface GUID
DataItem = 2, "USB\VID_0547&PID_1002"             ; SERVICE_TRIGGER_DATA_TYPE_STRING

[OsrFx2_CopyFiles]
osrfx2_DCHU_base.dll
osrfx2_DCHU_filter.dll
osrfx2_DCHU_usersvc.exe

このようなサービスは、シナリオに応じてコンポーネントまたは拡張 INF にインストールすることもできます。

コンポーネントを使用してドライバー パッケージからレガシー ソフトウェアをインストールする

Fabrikam には、以前に共同インストーラーを使用してインストールした実行可能ファイルosrfx2_DCHU_componentsoftware.exeがあります。 このレガシー ソフトウェアは、ボードによって設定されたレジストリ キーを表示し、OEM によって必要とされます。 これは、デスクトップ エディションの Windows 上でのみ実行される GUI ベースの実行可能ファイルです。 これをインストールするために、Fabrikam は別のコンポーネント ドライバー パッケージを作成し、それを拡張機能 INF に追加します。

[osrfx2_DCHU_extension.inx] の次のスニペットは、AddComponent ディレクティブを使って仮想子デバイスを作成します。

[OsrFx2Extension_Install.NT.Components]
AddComponent = osrfx2_DCHU_component,,OsrFx2Extension_ComponentInstall


[OsrFx2Extension_ComponentInstall]
ComponentIds=VID_045e&PID_94ab

その後、コンポーネントの INF [osrfx2_DCHU_component.inx] で指定されている AddSoftware ディレクティブによって、オプションの実行可能ファイルがインストールされます。

[OsrFx2Component_Install.NT.Software]
AddSoftware = osrfx2_DCHU_componentsoftware,, OsrFx2Component_SoftwareInstall

[OsrFx2Component_SoftwareInstall]
SoftwareType = 1
SoftwareBinary = osrfx2_DCHU_componentsoftware.exe
SoftwareArguments = <<DeviceInstanceId>>
SoftwareVersion = 1.0.0.0

[OsrFx2Component_CopyFiles]
osrfx2_DCHU_componentsoftware.exe

Win32 アプリのソース コードは、サンプルに含まれます。

Windows ハードウェア デベロッパー センター ダッシュボードで設定された対象設定により、コンポーネント ドライバー パッケージはデスクトップ SKU でのみ配布されます。 詳細については、「Windows Update へのドライバーの公開」を参照してください。

ハードウェア サポート アプリとの通信を許可する

Fabrikam は、Windows ドライバー パッケージの一部として GUI ベースのコンパニオン アプリを提供したいと考えています。 Win32 ベースのコンパニオン アプリケーションは Windows ドライバー パッケージの一部にできないため、Win32 アプリをユニバーサル Windows プラットフォーム (UWP) に移植し、アプリとデバイスをペアリングします

「タグの挿入」の次のスニペットosrfx2_DCHU_base/device.cは、基本ドライバー パッケージがデバイス インターフェイス インスタンスにカスタム機能を追加する方法を示しています。

    WDF_DEVICE_INTERFACE_PROPERTY_DATA PropertyData = { 0 };
    static const wchar_t customCapabilities[] = L"CompanyName.yourCustomCapabilityName_YourStorePubId\0";

    WDF_DEVICE_INTERFACE_PROPERTY_DATA_INIT(&PropertyData,
                                            &GUID_DEVINTERFACE_OSRUSBFX2,
                                            &DEVPKEY_DeviceInterface_UnrestrictedAppCapabilities);

    Status = WdfDeviceAssignInterfaceProperty(Device,
                                              &PropertyData,
                                              DEVPROP_TYPE_STRING_LIST,
                                              sizeof(customCapabilities),
                                              (PVOID)customCapabilities);

(サンプルに含まれない) 新しいアプリは、セキュリティで保護され、Microsoft Store で簡単に更新することができます。 UWP アプリケーション対応になったことで、Contoso は DISM (展開イメージのサービスと管理) を使ってアプリケーションを Windows デスクトップ エディションのイメージに事前に読み込みます。

複数の INF ファイルを密結合する

基本パッケージ、拡張パッケージ、コンポーネント パッケージの間には、優れたバージョン管理コントラクトが存在するのが理想です。 これら 3 つのパッケージを個別にサービスすること (「疎結合」シナリオ) にはサービス上の利点がありますが、バージョン管理契約が不十分なために、これらを 1 つのドライバー パッケージにバンドルする必要がある (「密結合」) シナリオもあります。 サンプルには、両方のシナリオの例が含まれています。

[OsrFx2Extension_Install.NT]
CopyInf=osrfx2_DCHU_component.inf

このディレクティブは、多機能デバイスへの INF ファイルのインストールを調整するために使用することもできます。 詳細については、「INF ファイルのコピー」を参照してください。

Note

ベース ドライバーのペイロードに拡張機能を格納する (そして、配送先住所ラベルでベース ドライバーをターゲットにする) ことはできますが、別のドライバーとバンドルされている拡張機能を、拡張機能のハードウェア ID に公開することはできません。

ドライバー ストアから実行する

ドライバーを容易に更新できるように、Fabrikam は、可能であれば dirid 13 を使って、ドライバー ストアをドライバー ファイルのコピー先として指定します。 宛先ディレクトリの値 13 を使用すると、ドライバーの更新プロセス中の安定性が向上する可能性があります。 [osrfx2_DCHU_base.inx]の例を次に示します

[DestinationDirs]
OsrFx2_CopyFiles = 13 ; copy to Driver Store

ファイルを動的に見つけてドライバー ストアから読み込む方法の詳細については、「ドライバー ストアから実行する」ページを参照してください。

まとめ

次の図は、Fabrikam と Contoso が DCH 準拠ドライバー用に作成したドライバー パッケージを示したものです。 疎結合の例では、Windows ハードウェア デベロッパー センターのダッシュボードで 3 つの別々の送信を行います。1 つはベース、1 つは拡張機能、もう 1 つはコンポーネントです。 密結合の例では、ベースと拡張/コンポーネントの 2 つの送信を行います。

Extension, base, and component driver packages.

コンポーネント INF はコンポーネント ハードウェア ID と一致しますが、ベースと拡張機能はボードのハードウェア ID と一致します。

関連項目

Windows ドライバーの概要

拡張 INF ファイルの使用

osrfx2_DCHU_base.inx

"疎結合" osrfx2_DCHU_component.inx

"疎結合" osrfx2_DCHU_extension.inx

"密結合" osrfx2_DCHU_component.inx

"密結合" osrfx2_DCHU_extension.inx