如何编写第一个 USB 客户端驱动程序 (KMDF)

在本文中,你将使用 Microsoft Visual Studio 随附的 USB Kernel-Mode 驱动程序 模板编写一个简单的内核模式驱动程序框架, (KMDF) 基于的客户端驱动程序。 生成并安装客户端驱动程序后,你将在 设备管理器 中查看客户端驱动程序,并在调试器中查看驱动程序输出。

有关模板生成的源代码的说明,请参阅 了解 USB 客户端驱动程序的 KMDF 模板代码

先决条件

若要开发、调试和安装内核模式驱动程序,需要两台计算机:

  • 运行 Windows 7 或更高版本的 Windows 操作系统的主计算机。 主计算机是开发环境,可在其中编写和调试驱动程序。
  • 运行 Windows Vista 或更高版本的 Windows 的目标计算机。 目标计算机具有要调试的内核模式驱动程序。

在开始之前,请确保满足以下要求:

软件要求

  • 主计算机托管开发环境,并且具有 Visual Studio。
  • 主计算机具有最新的 Windows 驱动程序工具包 (WDK) 。 该工具包包括开发、生成和调试 KMDF 驱动程序所需的标头、库、工具、文档和调试工具。 若要获取最新版本的 WDK,请参阅 下载 Windows 驱动程序工具包 (WDK)
  • 主计算机具有最新版本的 Windows 调试工具。 可以从 WDK 获取最新版本,也可以 下载并安装 Windows 调试工具
  • 目标计算机运行的是 Windows Vista 或更高版本的 Windows。
  • 主机和目标计算机配置为进行内核调试。 有关详细信息,请参阅 在 Visual Studio 中设置网络连接

硬件要求

获取要为其编写客户端驱动程序的 USB 设备。 在大多数情况下,会为你提供 USB 设备及其硬件规格。 该规范描述了设备功能和受支持的供应商命令。 使用规范确定 USB 驱动程序的功能以及相关的设计决策。

如果你不熟悉 USB 驱动程序开发,请使用 OSR USB FX2 学习工具包来研究 WDK 随附的 USB 示例。 可以从 OSR Online 获取学习工具包。 它包含 USB FX2 设备和实现客户端驱动程序所需的所有硬件规格。

还可以 (MUTT) 设备获取 Microsoft USB 测试工具。 可以从 JJG Technologies 购买 MUTT 硬件。 设备未安装固件。 若要安装固件,请从 此网站 下载 MUTT 软件包并运行 MUTTUtil.exe。 有关详细信息,请参阅 包中包含的文档。

步骤 1:使用 Visual Studio USB 驱动程序模板生成 KMDF 驱动程序代码

有关生成 KMDF 驱动程序代码的说明,请参阅 基于模板编写 KMDF 驱动程序中的步骤。

对于特定于 USB 的代码,请在 Visual Studio 中选择以下选项:

  1. 在“ 新建项目 ”对话框顶部的搜索框中,键入 “USB”。
  2. 在中间窗格中,选择“ 内核模式驱动程序”、“USB (KMDF) ”。
  3. 选择“下一页”。
  4. 输入项目名称,选择保存位置,然后选择“ 创建”。

以下屏幕截图显示了 USB Kernel-Mode 驱动程序模板的“新建项目”对话框。

visual studio 新建项目选项。

visual Studio 新建项目选项第二屏幕。

本文假定 Visual Studio 项目的名称为“MyUSBDriver_”。 它包含以下文件:

文件 说明
Public.h 提供客户端驱动程序和与 USB 设备通信的用户应用程序共享的通用声明。
<项目名称>.inf 包含在目标计算机上安装客户端驱动程序所需的信息。
Trace.h 声明跟踪函数和宏。
Driver.h;Driver.c 声明并定义驱动程序入口点和事件回调例程。
Device.h;Device.c 声明并定义 prepare-hardware 事件的事件回调例程。
Queue.h;Queue.c 声明并定义框架的队列对象引发的事件的事件回调例程。

步骤 2:修改 INF 文件以添加有关设备的信息

在生成驱动程序之前,必须使用有关设备的信息(特别是硬件 ID 字符串)修改模板 INF 文件。

“解决方案资源管理器”中的“驱动程序文件”下,双击 INF 文件。

在 INF 文件中,可以提供制造商和提供商名称、设备设置类等信息。 必须提供的一条信息是设备的硬件标识符。

提供硬件 ID 字符串:

  1. 将 USB 设备连接到主计算机,并让 Windows 枚举该设备。

  2. 打开设备管理器并打开设备的属性。

  3. “详细信息”选项卡上,选择“属性”下的“硬向 ID”。

    设备的硬件 ID 显示在列表框中。 选择并按住 (或右键单击) 并复制硬件 ID 字符串。

  4. 将以下行中的 USB\VID_vvvv&PID_pppp 替换为硬件 ID 字符串。

    [Standard.NT$ARCH$] %MyUSBDriver_.DeviceDesc%=MyUSBDriver__Device, USB\VID_vvvv&PID_pppp

步骤 3:生成 USB 客户端驱动程序代码

若要生成驱动程序,请执行以下操作:

  1. 在 Visual Studio 中打开驱动程序项目或解决方案
  2. 选择并按住 (或右键单击) 解决方案资源管理器中的解决方案,然后选择“Configuration Manager”。
  3. Configuration Manager中,选择“活动解决方案配置” (例如“调试”或“发布) ”和“活动解决方案平台” (Win32) ,这些配置对应于你感兴趣的生成类型。
  4. 从“构建”菜单中,选择“构建解决方案”。

有关详细信息,请参阅构建驱动程序

步骤 4:配置计算机以进行测试和调试

若要测试和调试驱动程序,请在主计算机上运行调试器,在目标计算机上运行驱动程序。 到目前为止,你已在主计算机上使用了 Visual Studio 来生成驱动程序。 接下来,需要配置目标计算机。 若要配置目标计算机,请按照 预配计算机进行驱动程序部署和测试中的说明进行操作。

步骤 5:为内核调试启用跟踪

模板代码包含多个跟踪消息 (TraceEvents) ,可帮助跟踪函数调用。 源代码中的所有函数都包含标记例程的进入和退出的跟踪消息。 对于错误,跟踪消息包含错误代码和有意义的字符串。 由于为驱动程序项目启用了 WPP 跟踪,因此在生成过程中创建的 PDB 符号文件包含跟踪消息格式设置说明。 如果为 WPP 跟踪配置主机和目标计算机,驱动程序可以将跟踪消息发送到文件或调试器。

若要为 WPP 跟踪配置主计算机,请执行以下操作:

  1. 通过从 PDB 符号文件提取跟踪消息格式设置说明, (TMF) 文件创建跟踪消息格式。

    可以使用 Tracepdb.exe 创建 TMF 文件。 该工具位于 WDK 的 <安装文件夹>Windows Kits\10.0\bin\<architecture> 文件夹中。 以下命令为驱动程序项目创建 TMF 文件。

    tracepdb -f <PDBFiles> -p <TMFDirectory>

    -f 选项指定 PDB 符号文件的位置和名称。 -p 选项指定 Tracepdb 创建的 TMF 文件的位置。 有关详细信息,请参阅 Tracepdb 命令

    在指定位置,你将看到项目) 中每个 .c 文件 (三个文件。 它们具有 GUID 文件名。

  2. 在调试器中,键入以下命令:

    1. .load Wmitrace

      加载 Wmitrace.dll 扩展。

    2. 。链

      验证是否已加载调试器扩展。

    3. !wmitrace.searchpath +<TMF 文件位置>

      将 TMF 文件的位置添加到调试器扩展的搜索路径。

      输出如下所示:

      Trace Format search path is: 'C:\Program Files (x86)\Microsoft Visual Studio 14.0\Common7\IDE;c:\drivers\tmf'

若要为 WPP 跟踪配置目标计算机,请执行以下操作:

  1. 请确保目标计算机上具有 Tracelog 工具。 该工具位于 <WDK install_folder>Windows Kits\8.0\Tools\<arch> 文件夹中。 有关详细信息,请参阅 Tracelog 命令语法

  2. 打开 命令窗口 并以管理员身份运行。

  3. 输入以下命令:

    tracelog -start MyTrace -guid #c918ee71-68c7-4140-8f7d-c907abbcb05d -flag 0xFFFF -level 7-rt -kd

    命令启动名为 MyTrace 的跟踪会话。

    guid 参数指定跟踪提供程序(即客户端驱动程序)的 GUID。 可以从 Visual Studio Professional 2019 项目中的 Trace.h 获取 GUID。 另一个选项是,可以键入以下命令并在 .guid 文件中指定 GUID。 文件包含连字符格式的 GUID:

    tracelog -start MyTrace -guid c:\drivers\Provider.guid -flag 0xFFFF -level 7-rt -kd

    可以通过键入以下命令来停止跟踪会话:

    tracelog -stop MyTrace

步骤 6:在目标计算机上部署驱动程序

  1. “解决方案资源管理器”窗口中,选择并按住 (或右键单击) “<项目名称>*”,然后选择“属性”。
  2. 在左窗格中,导航到 “配置属性驱动程序 > 安装 > 部署”。
  3. 选中“启用部署”,检查导入驱动程序存储。
  4. 对于 “远程计算机名称”,指定目标计算机的名称。
  5. 选择“安装并验证” 。
  6. 选择“确定” 。
  7. 在“调试” 菜单上,选择“开始调试” 或按键盘上的 F5

注意

不要在“硬件 ID 驱动程序更新”下指定设备的硬件 ID。 只能在驱动程序的信息中指定硬件 ID, (INF) 文件。

有关在 Visual Studio 中将驱动程序部署到目标系统的详细信息,请参阅 将驱动程序部署到测试计算机

还可以使用 设备管理器 在目标计算机上安装驱动程序。 如果要从命令提示符安装驱动程序,可以使用以下实用工具:

  • PnPUtil

    此工具随 Windows 一起提供。 它位于 Windows\System32 中。 可以使用此实用工具将驱动程序添加到驱动程序存储。

    C:\>pnputil /a m:\MyDriver_.inf
    Microsoft PnP Utility
    
    Processing inf : MyDriver_.inf
    Driver package added successfully.
    Published name : oem22.inf
    

    有关详细信息,请参阅 PnPUtil 示例

  • DevCon Update

    此工具随 WDK 一起提供。 可以使用它来安装和更新驱动程序。

    devcon update c:\windows\inf\MyDriver_.inf USB\VID_0547&PID_1002\5&34B08D76&0&6
    

步骤 7:在 设备管理器 中查看驱动程序

  1. 输入以下命令以打开设备管理器

    devmgmt
    
  2. 验证设备管理器是否显示以下节点的节点:

    示例

    MyUSBDriver_Device

步骤 8:在调试器中查看输出

Visual Studio 首先在 “输出 ”窗口中显示进度。 然后,它会打开 调试器即时窗口。 验证跟踪消息是否显示在主计算机上的调试器中。 输出应如下所示,其中“MyUSBDriver_”是驱动程序模块的名称:

[3]0004.0054::00/00/0000-00:00:00.000 [MyUSBDriver_]MyUSBDriver_EvtDriverContextCleanup Entry
[1]0004.0054::00/00/0000-00:00:00.000 [MyUSBDriver_]MyUSBDriver_EvtDriverDeviceAdd Entry
[1]0004.0054::00/00/0000-00:00:00.000 [MyUSBDriver_]MyUSBDriver_EvtDriverDeviceAdd Exit
[0]0004.0054::00/00/0000-00:00:00.000 [MyUSBDriver_]DriverEntry Entry
[0]0004.0054::00/00/0000-00:00:00.000 [MyUSBDriver_]DriverEntry Exit