UMDF’s content in the WDK contains a handful of examples for controlling a USB device. Unfortunately they only show how to do it on Vista. The problem was that WinUSB’s co-installer wasn’t added to the WDK until very late – too late for us to be able to change our samples to show how to use it.
WINUSB introduces a number of new things into the INF because of the complexity of installing it on XP and making it work with the in-box Vista support. In Vista WinUSB is present on the disk but the driver & service aren’t “installed” until some INF copies them into place. The WinUSB folks provided an in-box INF (winusb.inf) that you can reference in your INF with the Includes/Needs directives so that you don’t have to setup the service entries yourself.
On XP WinUSB doesn’t exist until someone installs it. The preferred installation route is to use the WinUsbCoinstaller. However because WINUSB.INF isn’t already on the machine in XP, you can’t depend on it to setup the WinUSB service entries. And we couldn’t rely on the WinUsbCoinstaller to do it because the device installer requires that your INF have an AddService directive for the driver which will act as the FDO.
The result is that installing WinUSB requires you to add a few things to your INF. Some of these are already demonstrated in the existing sample INFs. Others are new, and there’s one “bug fix”. I’ve added the full INF as an attachment to this blog entry.
So starting with the Fx2 driver’s INF, here are the necessary changes to build a driver package that will install both on XP and Vista.
Include sections from WINUSB.INF in your INF
Specifically in your [DDInstall.NT] section you add:
Include=WINUSB.INF ; Import sections from WINUSB.INF
Needs=WINUSB.NT ; Run the CopyFiles & AddReg directives
The first tells Device Installation to locate WINUSB.INF and read in all of its sections. The second tells DI that it should import any directives in the “WINUSB.NT” section into this section as well. WINUSB.NT contains CopyFiles & AddReg directives that tell Vista to copy the WinUSB.Sys binary as part of your driver package & sets up some registry entries.
Now you may recall I said that there was a problem on XP because this INF doesn’t exist. However when you ask DI to include an INF file that doesn’t exist (or say you Need a section that doesn’t exist) the installer just ignores you. Normally that would drive me nuts (I hate hidden errors) but it works in my favor in this case.
On XP these two directives are benign and we depend on the WinUsbCoinstaller to copy the files into place and setup the registry entries. On Vista WinUsbCoinstaller doesn’t do anything and we depend on these directives to copy the binaries.
This leads us to step 2 …
Copy & Invoke the WinUsbCoinstaller in your INF
To invoke the WinUSB coinstaller requires three things in your INF:
Add the file to [SourceDisksFiles] so that DI knows where to get the file from
Add the file to [CoInstallers_CopyFiles] so that DI knows that it needs to copy it
Add the name of the coinstaller to the CoInstallers32 registry entry so that DI knows to invoke it.
Note that the names of the last two sections need to match what you provide to CopyFiles and AddReg in your INF’s [DDInstall.Coinstallers] section.
Fix the bug in the [WinUsb_Install] section
WinUsb requires version 1.5 of KMDF, not version 1.0. We didn’t catch this before the samples shipped. Change the section to look like:
Include WinUsbCoinstaller.dll as part of your signed driver package
Along with WudfUpdate_01005.dll & WdfCoinstaller01005.dll you also now need to copy WinUsbCoinstaller.dll & add it to the catalog for your INF. You can find this file in c:\winddk\6000\redist\winusb\<arch>.
Like the KMDF and UMDF coinstallers, it comes in a _chk version also. If you’re installing your driver (whether you built it checked or free) on a checked system you should use the _chk version of the DLL.
Four little changes and you’re done. The same changes apply to any of the UMDF USB samples.