Adding HID interface to virtual audio device

what is the minimum OS version you are targeting? have you looked at the virtual hid framework? https://learn.microsoft.com/en-us/windows-hardware/drivers/hid/virtual-hid-framework--vhf-

This will be for windows 10.

I have used VHF in the past. I’m not sure it will work here. These HID commands will need to retrieve/change audio settings for the audio driver itself.

I want to link a HID filter to the audio driver itself. Would an extension work here? It would load my HID service as a lower filter.

I think VHF should work. The theoretical stack would be

FDO: audio driver
Device lower Filter1: your hidsource driver
Device lower filter2: vhf.sys

Audio driver and hidsource drivers communicate to share sate. The audio driver would have to pass the VHF IOCTLs down the stack. Hidsource driver communicates these changes to Vhfkm.lib, it takes care of the HID stack.

I think it is possible to combine your hidsource and audio drivers into one driver as vhfkm.lib should be compatible with the audio class driver, eliminating complexity,

If VHF is not possible, your lower filter will have to be a KMDF hid miniport and all the complexity that arises from that.

Thank you for your response.

I once built and tested the HID_Injector sample. I was able to simulate keyboard commands by sending the equivalent HID command to VhfReadReportSubmit.

In this case, I was sending these commands to the OS and not a particular device.

How would I direct vhf to target my specific audio driver?

Perhaps I misunderstood your goal. I thought you wanted to expose HID controls for your audio device (vol +, -, mute, etc). Your last response contradicts my understanding of the goal. You are asking how you can send HID commands TO your audio driver? As in send a volume up to the audio driver from your lower filter?

“You are asking how you can send HID commands TO your audio driver? As in send a volume up to the audio driver from your lower filter?”

Yes, that is correct,

I need to add a HID interface to an audio driver that doesn’t have one such as SysVad or SimpleAudioSample (from driver samples).

Would VHF work here?

“I think it is possible to combine your hidsource and audio drivers into one driver as vhfkm.lib should be compatible with the audio class driver, eliminating complexity,”

Does this mean merging the statements from the HID interface INX file to that of the audio INX?

Or, would it be better if the HID interface had it’s own INF to extent the already loaded audio driver?

Thanks again for your attention.

A single INF can only handle one class of device. However, if your driver creates a HID device object with the correct naming convention, no INF is necessary.

Sorry, but your answer creates more questions.

Are you saying that I can just create a HID service and include that in the INX for the audio driver?

How would it know that the service is HID?

Yes, you can use the same INF to place the audio driver as the FDO and your hid vhf (or mini port) as the lower filter. The device class of the HID vhf/mini port doesn’t matter, it can be any device class. When the hid stack reports a new child device based on the report descriptor your hid vhf provides (one child per TLC) the child will be installed in the HID device class as it will match a system HID INF.

Hello Again,

I followed the advise given me in this thread. I think I’m close but not quite there. The HID portion of the driver appears to load but it stops shortly after starting. Enumerating the device shows:

Instance ID: ROOT\MyHid\0
Device Description: My HID Device
Class Name: MEDIA
Class GUID: {4d36e96c-e325-11ce-bfc1-08002be10318}
Manufacturer Name: TODO-Set-Manufacturer
Status: Stopped
Driver Name: oem2.inf

The device install section from setupapi.dev.log shows:

{Select Drivers - ROOT\MyHid\0} 09:13:53.239
Driver Node:
Status - Selected
Driver INF - oem2.inf (C:\Windows\System32\DriverStore\FileRepository\simpleaudiosample.inf_amd64_7367a01941e9ec44\simpleaudiosample.inf)
Class GUID - {4d36e96c-e325-11ce-bfc1-08002be10318}
Driver Version - 04/14/2023,9.11.3.252
Configuration - ROOT\MyHid
Driver Rank - 80FF0000
Signer Score - Unsigned (80000000)
{Select Drivers - exit(0x00000000} 09:13:53.239
{Core Device Install} 09:13:53.239
{Configure Device - ROOT\MyHid\0} 09:13:53.255
Device Status: 0x01802401 [0x12 - 0xc0000493]
Config Flags: 0x00000020
Parent Device: HTREE\ROOT\0
{Configure Driver Package: C:\Windows\System32\DriverStore\FileRepository\simpleaudiosample.inf_amd64_7367a01941e9ec44\simpleaudiosample.inf}
Source Filter = ROOT\MyHid
Class GUID = {4d36e96c-e325-11ce-bfc1-08002be10318}
Class Options = Configurable
{Configure Device: ROOT\MyHid\0}
Device Instance Id = ROOT\MyHid\0
Updating existing device instance.
{Configure Device: exit(0x00000000)}
{Configure Driver: My HID Device}
Section Name = MyHid.NT
{Add Service: MyHid}
Start Type = 3
Service Type = 1
Error Control = 1
Image Path = \SystemRoot\System32\DriverStore\FileRepository\simpleaudiosample.inf_amd64_7367a01941e9ec44\MyHid.sys
Display Name = My HID Service
Reactivating service ‘MyHid’ pended for deletion.
Updated service ‘MyHid’.
Service image path changed. Restart required for any devices using this service.
{Add Service: exit(0x00000000)}
Hardware Id = ROOT\MyHid
{Configure Driver Configuration: MyHid.NT}
Service Name =
Declarative Filters = MyHid
vhf
Config Flags = 0x00000000
{Configure Driver Configuration: exit(0x00000000)}
{Configure Driver: exit(0x00000000)}
{FILE_QUEUE_COMMIT} 09:13:53.302
{FILE_QUEUE_COMMIT - exit(0x00000000)} 09:13:53.302
Existing files modified, may need to restart related services.
{Configure Driver Package: exit(0x00000bc3)}
Restart required for any devices using this driver.
Install Device: Configuring device. 09:13:53.302
Configuration: oem2.inf:ROOT\MyHid,*
Install Device: Configuring device completed. 09:13:53.302
Device Status: 0x01802001
{Restarting Devices} 09:13:53.302
Start: ROOT\MyHid\0
Device ‘ROOT\MyHid\0’ not started (unknown reason): Device has no problem.
{Restarting Devices exit} 09:13:53.317
{Configure Device - exit(0x00000000)} 09:13:53.317
{Core Device Install - exit(0x00000000)} 09:13:53.317

I’ve included the section that I added to the SimpleAudioSample.inx file:

[Manufacturer]
%MfgName%=SIMPLEAUDIOSAMPLE,NT$ARCH$.6.1

[SIMPLEAUDIOSAMPLE.NT$ARCH$.6.1]
%SIMPLEAUDIOSAMPLE_SA.DeviceDesc%=SIMPLEAUDIOSAMPLE_SA, ROOT\SimpleAudioSample
%MY_HID.DeviceDesc%=MY_HID, ROOT\MyHid

[DestinationDirs]
SIMPLEAUDIOSAMPLE_SA.CopyList=13
MY_HID.CopyList = 13
;
;======================================================
; MY_HID
;======================================================
[MY_HID.NT]
CopyFiles=MY_HID.CopyList

Level Order: A, B, C
DefaultFilterLevel: C

[MY_HID.NT.Filters]
AddFilter=MyHid,MY_HID.NT.LevelA
AddFilter=vhf,MY_HID.NT.LevelB

[MY_HID.NT.LevelA]
FilterLevel=A

[MY_HID.NT.LevelB]
FilterLevel=B

[MY_HID.NT.Services]
AddService=MyHid,MY_HID_Service_Inst
AddService=,2

[MY_HID_Service_Inst]
DisplayName = %MY_HID.ServiceDesc%
ServiceType = 1
StartType = 3
ErrorControl = 1
ServiceBinary = %13%\MyHid.sys

[MY_HID.NT.Wdf]
KmdfService=MyHid, MY_HID_wdfsect

[MY_HID_wdfsect]
KmdfLibraryVersion=$KMDFVERSION$

[MY_HID.CopyList]
MyHid.sys

[DeviceInstall32]
AddDevice = ROOT\MyHid\0,MY_HID_RootDevice_Inst

[MY_HID_RootDevice_Inst]
HardwareIds = ROOT\MyHid

The only other addition that I made to the INX was to add some strings.

Is there anything obvious in my INX that would cause my service to fail to run.

That service was the code lifted from was the HID Injector Sample - which works fine when it is a standalone.

Thanks in advance for your help.

You are installing the hid filter as it’s own device with this line %MY_HID.DeviceDesc%=MY_HID, ROOT\MyHid Remove it

testing

Thanks for the quick response.

I followed your advice and removed that line. However, it generated warnings that indicated all of the sections that I added to the INX would NOT be referenced.

Section [my_hid.nt] not referenced or used.
Section [my_hid.nt.filters] not referenced or used.
Section [my_hid.nt.levela] not referenced or used.
Section [my_hid.nt.levelb] not referenced or used.
Section [my_hid.nt.services] not referenced or used.
Section [my_hid_service_inst] not referenced or used.
Section [my_hid.nt.wdf] not referenced or used.
Section [my_hid_wdfsect] not referenced or used.
Section [my_hid.copylist] not referenced or used.

testing

Your inf has

Level Order: A, B, C
DefaultFilterLevel: C

INF files always use the equals sign as a separator, not a colon.

I followed your advice and removed that line. However, it generated warnings that indicated all of the sections that I added to the INX
would NOT be referenced.

Section [my_hid.nt] not referenced or used.

Well, yes, I can’t tell from this what you are actually trying to accomplish. The INF you have provided expects to create a new, software-only device to the system, and to supply a driver for that. Such a device has no connection to any other device. You’re calling it “SimpleAudioFilter”, but there’s nothing “audio” about this INF at all. How are you expecting this all to get loaded? Is this supposed to be a filter driver for your audio device? Is your audio device creating a new device object that you expect to drive?

If you’re expecting this to be a filter to your audio device, then you just need to add a few entries in your audio device’s INF, not use a separate INF.

Actually it’s SimpleAudioSample which is from the Microsoft Driver Samples under audio.

I simply added to it a HID interface so that Telephony Hid commands could be sent to it.

I attempted this by following an earlier post on this thread to use my filter as a lower filter and to use vhf under that.

My “Level Order” commands came straight from Microsoft’s “Device filter driver ordering” page.

https://learn.microsoft.com/en-us/windows-hardware/drivers/develop/device-filter-driver-ordering

So my question to you is:

Did I properly represent this HID filter addition to an already existing Audio driver?

“If you’re expecting this to be a filter to your audio device, then you just need to add a few entries in your audio device’s INF, not use a separate INF.”

That’s exactly what I try to accomplish.

What am I missing?

What am I missing?

You were creating a new dummy object (ROOT\MyHid\0), and installing your filter as the primary driver for that object, which is TOTALLY unrelated to your audio device. Further, since the INF is of “media” class, that object is going to be listed in media class.

Back out all your changes. Go back to JUST the audio driver INF. Now, add the one or two lines you need to copy your filter into place, add a service entry that maps your service name to your filter driver’s binary, and add an UpperFilters registry to your audio device to add the service name. That’s all you need. As long as the file and the service entry exists, the ONLY change needed to add an upper filter is manipulating the UpperFilters registry key. Nothing else is required. It doesn’t get its own sections – it leeches off of the audio device’s sections.

Hi Tim,

I followed your advice.

It works!

Thanks for your help.

JoeT

Thanks for the quick response.

I followed your advice and removed that line. However, it generated warnings that indicated all of the sections that I added to the INX would NOT be referenced.

Build started…
1>------ Build started: Project: Main (Main\Main), Configuration: Debug x64 ------
1>Building ‘Main’ with toolset ‘WindowsKernelModeDriver10.0’ and the ‘Universal’ target platform.
1>Stamping x64\Debug\SimpleAudioSample.inf
1>Stamping [Version] section with DriverVer=04/14/2023,11.6.43.271
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(41-41): warning 2083: Section [my_hid.nt] not referenced or used.
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(47-47): warning 2083: Section [my_hid.nt.filters] not referenced or used.
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(51-51): warning 2083: Section [my_hid.nt.levela] not referenced or used.
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(54-54): warning 2083: Section [my_hid.nt.levelb] not referenced or used.
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(57-57): warning 2083: Section [my_hid.nt.services] not referenced or used.
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(61-61): warning 2083: Section [my_hid_service_inst] not referenced or used.
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(68-68): warning 2083: Section [my_hid.nt.wdf] not referenced or used.
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(71-71): warning 2083: Section [my_hid_wdfsect] not referenced or used.
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(74-74): warning 2083: Section [my_hid.copylist] not referenced or used.
1>C:\Users\jtomczyk\Desktop\MyProjects\SimpleAudio\Source\Main\SimpleAudioSample.inx(80-80): error 1270: INF does not install a driver for any hardware IDs created in [DeviceInstall32] section.
1>Done building project “Main.vcxproj” – FAILED.