Author: janderwald Date: Tue Oct 25 19:20:09 2016 New Revision: 73033
URL: http://svn.reactos.org/svn/reactos?rev=73033&view=rev Log: [USBAUDIO] - implement mute control property handler
Modified: trunk/reactos/drivers/usb/usbaudio/filter.c trunk/reactos/drivers/usb/usbaudio/guid.c trunk/reactos/drivers/usb/usbaudio/pin.c trunk/reactos/drivers/usb/usbaudio/usbaudio.h
Modified: trunk/reactos/drivers/usb/usbaudio/filter.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/usb/usbaudio/filter... ============================================================================== --- trunk/reactos/drivers/usb/usbaudio/filter.c [iso-8859-1] (original) +++ trunk/reactos/drivers/usb/usbaudio/filter.c [iso-8859-1] Tue Oct 25 19:20:09 2016 @@ -89,6 +89,155 @@ NULL, NULL }; + +NTSTATUS NTAPI FilterAudioVolumeHandler(IN PIRP Irp, IN PKSIDENTIFIER Request, IN OUT PVOID Data); +NTSTATUS NTAPI FilterAudioMuteHandler(IN PIRP Irp, IN PKSIDENTIFIER Request, IN OUT PVOID Data); + +DEFINE_KSPROPERTY_TABLE_AUDIO_VOLUME(FilterAudioVolumePropertySet, FilterAudioVolumeHandler); +DEFINE_KSPROPERTY_TABLE_AUDIO_MUTE(FilterAudioMutePropertySet, FilterAudioMuteHandler); + + +static KSPROPERTY_SET FilterAudioVolumePropertySetArray[] = +{ + { + &KSPROPSETID_Audio, + sizeof(FilterAudioVolumePropertySet) / sizeof(KSPROPERTY_ITEM), + (const KSPROPERTY_ITEM*)&FilterAudioVolumePropertySet, + 0, + NULL + } +}; + +static KSPROPERTY_SET FilterAudioMutePropertySetArray[] = +{ + { + &KSPROPSETID_Audio, + sizeof(FilterAudioMutePropertySet) / sizeof(KSPROPERTY_ITEM), + (const KSPROPERTY_ITEM*)&FilterAudioMutePropertySet, + 0, + NULL + } +}; + +NTSTATUS +UsbAudioGetSetProperty( + IN PDEVICE_OBJECT DeviceObject, + IN UCHAR Request, + IN USHORT Value, + IN USHORT Index, + IN PVOID TransferBuffer, + IN ULONG TransferBufferLength, + IN ULONG TransferFlags) +{ + PURB Urb; + NTSTATUS Status; + + /* allocate urb */ + Urb = AllocFunction(sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST)); + if (!Urb) + { + /* no memory */ + return STATUS_INSUFFICIENT_RESOURCES; + } + + /* format urb */ + UsbBuildVendorRequest(Urb, + URB_FUNCTION_CLASS_INTERFACE, + sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST), + TransferFlags, + 0, + Request, + Value, + Index, + TransferBuffer, + NULL, + TransferBufferLength, + NULL); + + /* submit urb */ + Status = SubmitUrbSync(DeviceObject, Urb); + + DPRINT1("UsbAudioGetSetProperty Status %x\n", Status); + FreeFunction(Urb); + return Status; +} + +PNODE_CONTEXT +FindNodeContextWithNode( + IN PNODE_CONTEXT NodeContext, + IN ULONG NodeContextCount, + IN ULONG NodeId) +{ + ULONG Index, NodeIndex; + for (Index = 0; Index < NodeContextCount; Index++) + { + for (NodeIndex = 0; NodeIndex < NodeContext[Index].NodeCount; NodeIndex++) + { + if (NodeContext[Index].Nodes[NodeIndex] == NodeId) + { + return &NodeContext[Index]; + } + } + } + return NULL; +} + + +NTSTATUS +NTAPI +FilterAudioMuteHandler( + IN PIRP Irp, + IN PKSIDENTIFIER Request, + IN OUT PVOID Data) +{ + PKSNODEPROPERTY_AUDIO_CHANNEL Property; + PKSFILTER Filter; + PFILTER_CONTEXT FilterContext; + PNODE_CONTEXT NodeContext; + PUSB_AUDIO_CONTROL_FEATURE_UNIT_DESCRIPTOR FeatureUnitDescriptor; + NTSTATUS Status = STATUS_INVALID_PARAMETER; + + /* get filter from irp */ + Filter = KsGetFilterFromIrp(Irp); + + if (Filter) + { + /* get property */ + Property = (PKSNODEPROPERTY_AUDIO_CHANNEL)Request; + + /* get filter context */ + FilterContext = (PFILTER_CONTEXT)Filter->Context; + + /* search for node context */ + NodeContext = FindNodeContextWithNode(FilterContext->DeviceExtension->NodeContext, FilterContext->DeviceExtension->NodeContextCount, Property->NodeProperty.NodeId); + if (NodeContext) + { + FeatureUnitDescriptor = (PUSB_AUDIO_CONTROL_FEATURE_UNIT_DESCRIPTOR)NodeContext->Descriptor; + if (Property->NodeProperty.Property.Flags & KSPROPERTY_TYPE_GET) + { + Status = UsbAudioGetSetProperty(FilterContext->DeviceExtension->LowerDevice, 0x81, 0x100, FeatureUnitDescriptor->bUnitID << 8, Data, 1, USBD_TRANSFER_DIRECTION_IN); + Irp->IoStatus.Information = sizeof(BOOL); + } + else + { + Status = UsbAudioGetSetProperty(FilterContext->DeviceExtension->LowerDevice, 0x01, 0x100, FeatureUnitDescriptor->bUnitID << 8, Data, 1, USBD_TRANSFER_DIRECTION_OUT); + } + } + } + return Status; +} + +NTSTATUS +NTAPI +FilterAudioVolumeHandler( + IN PIRP Irp, + IN PKSIDENTIFIER Request, + IN OUT PVOID Data) +{ + UNIMPLEMENTED + return STATUS_SUCCESS; +} +
ULONG CountTopologyComponents( @@ -200,10 +349,11 @@ PUSB_AUDIO_CONTROL_INPUT_TERMINAL_DESCRIPTOR InputTerminalDescriptor; PUSB_AUDIO_CONTROL_FEATURE_UNIT_DESCRIPTOR FeatureUnitDescriptor; PUSB_AUDIO_CONTROL_MIXER_UNIT_DESCRIPTOR MixerUnitDescriptor; - PUSB_AUDIO_CONTROL_OUTPUT_TERMINAL_DESCRIPTOR OutputTerminalDescriptor; + PUSB_AUDIO_CONTROL_OUTPUT_TERMINAL_DESCRIPTOR OutputTerminalDescriptor; PKSNODE_DESCRIPTOR NodeDescriptors; PNODE_CONTEXT NodeContext, PreviousNodeContext; PKSTOPOLOGY_CONNECTION Connections; + PKSAUTOMATION_TABLE AutomationTable;
/* get device extension */ DeviceExtension = Device->Context; @@ -220,12 +370,13 @@ } FilterDescriptor->NodeDescriptorSize = sizeof(KSNODE_DESCRIPTOR);
- NodeContext = AllocFunction(sizeof(NODE_CONTEXT) * ControlDescriptorCount); + DeviceExtension->NodeContext = NodeContext = AllocFunction(sizeof(NODE_CONTEXT) * ControlDescriptorCount); if (!NodeContext) { /* no memory */ return STATUS_INSUFFICIENT_RESOURCES; } + DeviceExtension->NodeContextCount = ControlDescriptorCount; DescriptorCount = 0;
/* first enumerate all topology nodes */ @@ -336,7 +487,13 @@ { NodeDescriptors[FilterDescriptor->NodeDescriptorsCount].Type = &KSNODETYPE_MUTE; NodeDescriptors[FilterDescriptor->NodeDescriptorsCount].Name = &KSNODETYPE_MUTE; - NodeDescriptors[FilterDescriptor->NodeDescriptorsCount].AutomationTable = AllocFunction(sizeof(KSAUTOMATION_TABLE)); + NodeDescriptors[FilterDescriptor->NodeDescriptorsCount].AutomationTable = AutomationTable = AllocFunction(sizeof(KSAUTOMATION_TABLE)); + if (AutomationTable) + { + AutomationTable->PropertySets = FilterAudioMutePropertySetArray; + AutomationTable->PropertySetsCount = 1; + AutomationTable->PropertyItemSize = sizeof(KSPROPERTY_ITEM); + }
/* insert into node context*/ NodeContext[DescriptorCount].Nodes[NodeContext[DescriptorCount].NodeCount] = FilterDescriptor->NodeDescriptorsCount; @@ -348,7 +505,13 @@ { NodeDescriptors[FilterDescriptor->NodeDescriptorsCount].Type = &KSNODETYPE_VOLUME; NodeDescriptors[FilterDescriptor->NodeDescriptorsCount].Name = &KSNODETYPE_VOLUME; - NodeDescriptors[FilterDescriptor->NodeDescriptorsCount].AutomationTable = AllocFunction(sizeof(KSAUTOMATION_TABLE)); + NodeDescriptors[FilterDescriptor->NodeDescriptorsCount].AutomationTable = AutomationTable = AllocFunction(sizeof(KSAUTOMATION_TABLE)); + if (AutomationTable) + { + AutomationTable->PropertySets = FilterAudioVolumePropertySetArray; + AutomationTable->PropertySetsCount = 1; + AutomationTable->PropertyItemSize = sizeof(KSPROPERTY_ITEM); + }
/* insert into node context*/ NodeContext[DescriptorCount].Nodes[NodeContext[DescriptorCount].NodeCount] = FilterDescriptor->NodeDescriptorsCount;
Modified: trunk/reactos/drivers/usb/usbaudio/guid.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/usb/usbaudio/guid.c... ============================================================================== --- trunk/reactos/drivers/usb/usbaudio/guid.c [iso-8859-1] (original) +++ trunk/reactos/drivers/usb/usbaudio/guid.c [iso-8859-1] Tue Oct 25 19:20:09 2016 @@ -16,4 +16,5 @@ DEFINE_GUID(KSNODETYPE_SUPERMIX, 0xE573ADC0L, 0xC555, 0x11D0, 0x8A, 0x2B, 0x00, 0xA0, 0xC9, 0x25, 0x5A, 0xC1); DEFINE_GUID(KSNODETYPE_VOLUME, 0x3A5ACC00L, 0xC557, 0x11D0, 0x8A, 0x2B, 0x00, 0xA0, 0xC9, 0x25, 0x5A, 0xC1); DEFINE_GUID(KSCOMPONENTID_USBAUDIO, 0x8F1275F0L, 0x26E9, 0x4264, 0xBA, 0x4D, 0x39, 0xFF, 0xF0, 0x1D, 0x94, 0xAA); +DEFINE_GUID(KSPROPSETID_Audio, 0x45FFAAA0L, 0x6E1B, 0x11D0, 0xBC, 0xF2, 0x44, 0x45, 0x53, 0x54, 0x00, 0x00); /* NO CODE HERE, THIS IS JUST REQUIRED FOR THE GUID DEFINITIONS */
Modified: trunk/reactos/drivers/usb/usbaudio/pin.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/usb/usbaudio/pin.c?... ============================================================================== --- trunk/reactos/drivers/usb/usbaudio/pin.c [iso-8859-1] (original) +++ trunk/reactos/drivers/usb/usbaudio/pin.c [iso-8859-1] Tue Oct 25 19:20:09 2016 @@ -88,58 +88,6 @@ *OutUrb = Urb; return STATUS_SUCCESS;
-} - -NTSTATUS -UsbAudioSetMuteOff( - IN PKSPIN Pin) -{ - PURB Urb; - PVOID SampleRateBuffer; - PPIN_CONTEXT PinContext; - NTSTATUS Status; - - /* allocate sample rate buffer */ - SampleRateBuffer = AllocFunction(sizeof(ULONG)); - if (!SampleRateBuffer) - { - /* no memory */ - return STATUS_INSUFFICIENT_RESOURCES; - } - - /* allocate urb */ - Urb = AllocFunction(sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST)); - if (!Urb) - { - /* no memory */ - FreeFunction(SampleRateBuffer); - return STATUS_INSUFFICIENT_RESOURCES; - } - - /* FIXME: determine controls and format urb */ - UsbBuildVendorRequest(Urb, - URB_FUNCTION_CLASS_INTERFACE, - sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST), - USBD_TRANSFER_DIRECTION_OUT, - 0, - 0x01, - 0x100, - 0x300, - SampleRateBuffer, - NULL, - 1, - NULL); - - /* get pin context */ - PinContext = Pin->Context; - - /* submit urb */ - Status = SubmitUrbSync(PinContext->LowerDevice, Urb); - - DPRINT1("UsbAudioSetMuteOff Pin %p Status %x\n", Pin, Status); - FreeFunction(Urb); - FreeFunction(SampleRateBuffer); - return Status; }
NTSTATUS @@ -696,7 +644,6 @@ }
/* FIXME move to build filter topology*/ - UsbAudioSetMuteOff(Pin); UsbAudioSetVolume(Pin);
/* select streaming interface */
Modified: trunk/reactos/drivers/usb/usbaudio/usbaudio.h URL: http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/usb/usbaudio/usbaud... ============================================================================== --- trunk/reactos/drivers/usb/usbaudio/usbaudio.h [iso-8859-1] (original) +++ trunk/reactos/drivers/usb/usbaudio/usbaudio.h [iso-8859-1] Tue Oct 25 19:20:09 2016 @@ -35,6 +35,35 @@ #define USB_AUDIO_INPUT_TERMINAL (0x02) #define USB_AUDIO_OUTPUT_TERMINAL (0x03)
+#define DEFINE_KSPROPERTY_ITEM_AUDIO_VOLUME(Handler)\ + DEFINE_KSPROPERTY_ITEM(\ + KSPROPERTY_AUDIO_VOLUMELEVEL,\ + (Handler),\ + sizeof(KSNODEPROPERTY_AUDIO_CHANNEL),\ + sizeof(LONG),\ + (Handler), NULL, 0, NULL, NULL, 0) + + +#define DEFINE_KSPROPERTY_TABLE_AUDIO_VOLUME(TopologySet, Handler)\ +DEFINE_KSPROPERTY_TABLE(TopologySet) {\ + DEFINE_KSPROPERTY_ITEM_AUDIO_VOLUME(Handler)\ +} + +#define DEFINE_KSPROPERTY_ITEM_AUDIO_MUTE(Handler)\ + DEFINE_KSPROPERTY_ITEM(\ + KSPROPERTY_AUDIO_MUTE,\ + (Handler),\ + sizeof(KSNODEPROPERTY_AUDIO_CHANNEL),\ + sizeof(BOOL),\ + (Handler), NULL, 0, NULL, NULL, 0) + +#define DEFINE_KSPROPERTY_TABLE_AUDIO_MUTE(TopologySet, Handler)\ +DEFINE_KSPROPERTY_TABLE(TopologySet) {\ + DEFINE_KSPROPERTY_ITEM_AUDIO_MUTE(Handler)\ +} + + + #include <pshpack1.h>
typedef struct @@ -128,6 +157,13 @@
#include <poppack.h>
+typedef struct +{ + PUSB_COMMON_DESCRIPTOR Descriptor; + ULONG NodeCount; + ULONG Nodes[20]; +}NODE_CONTEXT, *PNODE_CONTEXT; + typedef struct __DEVICE_EXTENSION__ { PDEVICE_OBJECT LowerDevice; /* lower device*/ @@ -135,7 +171,8 @@ PUSB_DEVICE_DESCRIPTOR DeviceDescriptor; /* usb device descriptor */ PUSBD_INTERFACE_INFORMATION InterfaceInfo; /* interface information */ USBD_CONFIGURATION_HANDLE ConfigurationHandle; /* configuration handle */ - + PNODE_CONTEXT NodeContext; /* node context */ + ULONG NodeContextCount; /* node context count */ }DEVICE_EXTENSION, *PDEVICE_EXTENSION;
typedef struct @@ -161,14 +198,6 @@ PKSWORKER StarvationWorker; /* capture worker */ }PIN_CONTEXT, *PPIN_CONTEXT;
-typedef struct -{ - PUSB_COMMON_DESCRIPTOR Descriptor; - ULONG NodeCount; - ULONG Nodes[20]; -}NODE_CONTEXT, *PNODE_CONTEXT; - - /* filter.c */
NTSTATUS