How to obtain IKsControl for a MSVAD device

I am using the MSVAD-Simple sample as the base for the creation of an Audio Loopback device. I’m able to create the loopback.
Now I’m trying to control the device from my application.
As pointed out in other threads I have to create a custom KS property and then use IKsControl to sends commands and data from my application.
So as first test I’m trining to call one of the original MSVAD-Simple’s property.
However I’m not able to retrieve a valid IKsControl for any device.

To enumerate the devices I employed this code:

////////////////////////////////////////////////////////////

#include <atlbase.h>
#include <dshow.h>
#include <mmdeviceapi.h>
#include <devicetopology.h>
#include <functiondiscoverykeys.h>
#include <ks.h>

#pragma comment( lib, “strmiids.lib” )

#define LOG(formatstring, …) _tprintf(formatstring _T(“\n”), VA_ARGS )

int provaEnumerate1()
{
HRESULT hr;

CoInitialize(NULL);
CComPtr< IBaseFilter > pFilt;

// Create an enumerator.
CComPtr< ICreateDevEnum > pCreateDevEnum;
pCreateDevEnum.CoCreateInstance( CLSID_SystemDeviceEnum );
if( !pCreateDevEnum )
return E_FAIL;

// Enumerate the list of audio renderer devices.
CComPtr< IEnumMoniker > pEm;
pCreateDevEnum->CreateClassEnumerator( CLSID_AudioRendererCategory, &pEm, 0 );

if( !pEm ) {
return E_FAIL;
}
pEm->Reset( );

while( 1 )
{
ULONG ulFetched = 0;
CComPtr< IMoniker > pM;
hr = pEm->Next( 1, &pM, &ulFetched );

if( FAILED(hr) || !pM ) break;

// Get the property bag interface from the moniker.
CComPtr< IPropertyBag > pBag;
hr = pM->BindToStorage( 0, 0, IID_IPropertyBag, (void**) &pBag );
if( FAILED(hr) ) continue;

// Go read the friendly name from the property bag.
CComVariant var;
var.vt = VT_BSTR;
hr = pBag->Read( L"FriendlyName", &var, NULL );
if( FAILED(hr) ) continue;
LOG(_T(“%ls”), var.bstrVal );

hr = pM->BindToObject( 0, 0, __uuidof(IBaseFilter), (void**) &pFilt);
//LOG(_T(“%08x %p”), hr, pFilt );

CComPtr ctrl;
hr = pFilt->QueryInterface(__uuidof(IKsControl), (void **)&ctrl);
if(SUCCEEDED(hr)){
LOG(_T(“%08x %p”), hr, ctrl );
ctrl.Release();
}else{
LOG(_T(“Failed hr = %08x”), hr);
}

pFilt.Release();
pM.Release();
pBag.Release();
}
pEm.Release();
pCreateDevEnum.Release();

return 0;
}

////////////////////////////////////////////////////////////

My questions are:
1) Can someone provide a sample code for obtaining a valid IKsControl for the MSVAD simple driver?
2) Given the IKsControl how can I Send/Retrieve data from the driver?</ks.h></functiondiscoverykeys.h></devicetopology.h></mmdeviceapi.h></dshow.h></atlbase.h>

xxxxx@bittree.it wrote:

I am using the MSVAD-Simple sample as the base for the creation of an Audio Loopback device. I’m able to create the loopback.
Now I’m trying to control the device from my application.
As pointed out in other threads I have to create a custom KS property and then use IKsControl to sends commands and data from my application.
So as first test I’m trining to call one of the original MSVAD-Simple’s property.
However I’m not able to retrieve a valid IKsControl for any device.

To enumerate the devices I employed this code:

Your code looks mostly correct. You use BindToObject to get an
IBaseFilter from the enumerator, then you query the IBaseFilter to give
you an IKsControl. Are you saying this didn’t work?

The only comment I would make is that you are looping forever.
Typically, you compare against the FriendlyName string to find the
device you want, then you call BindToObject and exit the loop, returning
the IBaseFilter interface for the rest of the code to use.

My questions are:

  1. Can someone provide a sample code for obtaining a valid IKsControl for the MSVAD simple driver?

You have that.

  1. Given the IKsControl how can I Send/Retrieve data from the driver?

Have you looked at the documentation for IKsControl? You’re going to
call IKsControl::KsProperty to send a property request. The input
buffer typically has a KSPROPERTY structure that identifies the property
you want, and the output buffer typically has the data to be read or
written. The following page has an example, although they use the new
audio engine APIs to find the device, not the DirectShow APIs:

https://msdn.microsoft.com/en-us/library/windows/desktop/dd316787.aspx


Tim Roberts, xxxxx@probo.com
Providenza & Boekelheide, Inc.

Thank you
After some try and repead I was able to to obtain a valid an handler to the topology object of my Virtual device.
As you suggested, then I was able to send and recive data from the driver using a modified version of the code reported in MSDN
https://msdn.microsoft.com/en-us/library/windows/desktop/dd316787.aspx