Author: janderwald
Date: Sun Feb 22 21:58:51 2009
New Revision: 39715
URL:
http://svn.reactos.org/svn/reactos?rev=39715&view=rev
Log:
- Implement a common property handler for filter property requests
- Always queue a work item for pin creation requests
- Handle KSPROPERTY_PIN_DATAFLOW, KSPROPERTY_PIN_DATARANGES, KSPROPERTY_PIN_INTERFACES,
KSPROPERTY_PIN_MEDIUMS, KSPROPERTY_PIN_COMMUNICATION, KSPROPERTY_PIN_CATEGORY,
qKSPROPERTY_PIN_NAME, KSPROPERTY_PIN_GLOBALCINSTANCES, KSPROPERTY_PIN_CINSTANCES,
KSPROPERTY_PIN_NECESSARYINSTANCES
- Fix several bugs in property copying code
- Change the pin creation path in sysaudio in order to have client information as this was
previously not available (see DPRINT using hack)
- Close file handels in wdmaud / sysaudio
- set Iostatus before queing an irp as the irp might complete before accessing status io
Modified:
trunk/reactos/drivers/wdm/audio/backpln/portcls/filter_wavecyclic.c
trunk/reactos/drivers/wdm/audio/backpln/portcls/interfaces.h
trunk/reactos/drivers/wdm/audio/backpln/portcls/port_topology.c
trunk/reactos/drivers/wdm/audio/backpln/portcls/private.h
trunk/reactos/drivers/wdm/audio/backpln/portcls/propertyhandler.c
trunk/reactos/drivers/wdm/audio/backpln/portcls/undoc.c
trunk/reactos/drivers/wdm/audio/legacy/wdmaud/control.c
trunk/reactos/drivers/wdm/audio/legacy/wdmaud/entry.c
trunk/reactos/drivers/wdm/audio/legacy/wdmaud/wdmaud.h
trunk/reactos/drivers/wdm/audio/sysaudio/control.c
trunk/reactos/drivers/wdm/audio/sysaudio/dispatcher.c
trunk/reactos/drivers/wdm/audio/sysaudio/pin.c
trunk/reactos/drivers/wdm/audio/sysaudio/sysaudio.h
Modified: trunk/reactos/drivers/wdm/audio/backpln/portcls/filter_wavecyclic.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/backpln/…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/backpln/portcls/filter_wavecyclic.c [iso-8859-1]
(original)
+++ trunk/reactos/drivers/wdm/audio/backpln/portcls/filter_wavecyclic.c [iso-8859-1] Sun
Feb 22 21:58:51 2009
@@ -133,7 +133,7 @@
}
/*
- * @unimplemented
+ * @implemented
*/
NTSTATUS
NTAPI
@@ -142,8 +142,23 @@
IN PDEVICE_OBJECT DeviceObject,
IN PIRP Irp)
{
-
- return STATUS_UNSUCCESSFUL;
+ PIO_STACK_LOCATION IoStack;
+ ISubdevice *SubDevice = NULL;
+ SUBDEVICE_DESCRIPTOR * Descriptor;
+
+ IPortFilterWaveCyclicImpl * This = (IPortFilterWaveCyclicImpl *)iface;
+
+ IoStack = IoGetCurrentIrpStackLocation(Irp);
+ ASSERT(IoStack->Parameters.DeviceIoControl.IoControlCode == IOCTL_KS_PROPERTY);
+ ASSERT(This->Port->lpVtbl->QueryInterface(This->Port,
&IID_ISubdevice, (PVOID*)&SubDevice) == STATUS_SUCCESS);
+ ASSERT(SubDevice != NULL);
+
+ ASSERT(SubDevice->lpVtbl->GetDescriptor(SubDevice, &Descriptor) ==
STATUS_SUCCESS);
+ ASSERT(Descriptor != NULL);
+
+ SubDevice->lpVtbl->Release(SubDevice);
+
+ return PcPropertyHandler(Irp, Descriptor);
}
/*
Modified: trunk/reactos/drivers/wdm/audio/backpln/portcls/interfaces.h
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/backpln/…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/backpln/portcls/interfaces.h [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/backpln/portcls/interfaces.h [iso-8859-1] Sun Feb 22
21:58:51 2009
@@ -99,9 +99,20 @@
typedef struct
{
+ ULONG MaxGlobalInstanceCount;
+ ULONG MaxFilterInstanceCount;
+ ULONG MinFilterInstanceCount;
+ ULONG CurrentFilterInstanceCount;
+
+}PIN_INSTANCE_INFO, *PPIN_INSTANCE_INFO;
+
+
+typedef struct
+{
ULONG PinDescriptorCount;
ULONG PinDescriptorSize;
KSPIN_DESCRIPTOR * KsPinDescriptor;
+ PIN_INSTANCE_INFO * Instances;
}KSPIN_FACTORY;
typedef struct
Modified: trunk/reactos/drivers/wdm/audio/backpln/portcls/port_topology.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/backpln/…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/backpln/portcls/port_topology.c [iso-8859-1]
(original)
+++ trunk/reactos/drivers/wdm/audio/backpln/portcls/port_topology.c [iso-8859-1] Sun Feb
22 21:58:51 2009
@@ -486,8 +486,10 @@
ISubdevice * SubDevice;
PPCLASS_DEVICE_EXTENSION DeviceExt;
SUBDEVICE_ENTRY * Entry;
- IIrpTarget *Filter, *Pin;
+ IIrpTarget *Filter;
PKSOBJECT_CREATE_ITEM CreateItem;
+ PPIN_WORKER_CONTEXT Context;
+ PIO_WORKITEM WorkItem;
DPRINT1("PcCreateItemDispatch called DeviceObject %p\n", DeviceObject);
@@ -567,7 +569,6 @@
}
else
{
- KSOBJECT_CREATE Create;
LPWSTR Buffer = IoStack->FileObject->FileName.Buffer;
static LPWSTR KS_NAME_PIN = L"{146F1A80-4791-11D0-A5D6-28DB04C10000}";
@@ -576,51 +577,33 @@
if (!wcsncmp(KS_NAME_PIN, Buffer, wcslen(KS_NAME_PIN)))
{
/* try to create new pin */
-
- if (KeGetCurrentIrql() >= APC_LEVEL)
- {
- PPIN_WORKER_CONTEXT Context = AllocateItem(NonPagedPool,
sizeof(PIN_WORKER_CONTEXT), TAG_PORTCLASS);
- if (!Context)
- {
- Irp->IoStatus.Information = 0;
- Irp->IoStatus.Status = STATUS_INSUFFICIENT_RESOURCES;
- return STATUS_INSUFFICIENT_RESOURCES;
- }
- Context->Filter = Filter;
- Context->Irp = Irp;
-
- PIO_WORKITEM WorkItem = IoAllocateWorkItem(DeviceObject);
- if (!WorkItem)
- {
- Irp->IoStatus.Information = 0;
- Irp->IoStatus.Status = STATUS_INSUFFICIENT_RESOURCES;
- return STATUS_INSUFFICIENT_RESOURCES;
- }
-
- IoQueueWorkItem(WorkItem, CreatePinWorkerRoutine, DelayedWorkQueue,
(PVOID)Context);
- Irp->IoStatus.Information = 0;
- Irp->IoStatus.Status = STATUS_PENDING;
- IoMarkIrpPending(Irp);
- return STATUS_PENDING;
- }
-
- Create.CreateItemsCount = 1;
- Create.CreateItemsList =
(PKSOBJECT_CREATE_ITEM)(IoStack->FileObject->FileName.Buffer + (wcslen(KS_NAME_PIN)
+ 1));
-
- Status = Filter->lpVtbl->NewIrpTarget(Filter,
- &Pin,
- KS_NAME_PIN,
- NULL,
- NonPagedPool,
- DeviceObject,
- Irp,
- &Create);
- if (NT_SUCCESS(Status))
+ Context = AllocateItem(NonPagedPool, sizeof(PIN_WORKER_CONTEXT),
TAG_PORTCLASS);
+ if (!Context)
{
- /* create the dispatch object */
- Status = NewDispatchObject(Irp, Pin);
- DPRINT1("Pin %p\n", Pin);
+ Irp->IoStatus.Information = 0;
+ Irp->IoStatus.Status = STATUS_INSUFFICIENT_RESOURCES;
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ return STATUS_INSUFFICIENT_RESOURCES;
}
+ Context->Filter = Filter;
+ Context->Irp = Irp;
+
+ WorkItem = IoAllocateWorkItem(DeviceObject);
+ if (!WorkItem)
+ {
+ Irp->IoStatus.Information = 0;
+ Irp->IoStatus.Status = STATUS_INSUFFICIENT_RESOURCES;
+ FreeItem(Context, TAG_PORTCLASS);
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ return STATUS_INSUFFICIENT_RESOURCES;
+ }
+ DPRINT1("Queueing IRP %p\n", Irp);
+ Irp->IoStatus.Information = 0;
+ Irp->IoStatus.Status = STATUS_PENDING;
+ IoMarkIrpPending(Irp);
+ IoQueueWorkItem(WorkItem, CreatePinWorkerRoutine, DelayedWorkQueue,
(PVOID)Context);
+
+ return STATUS_PENDING;
}
}
Irp->IoStatus.Information = 0;
Modified: trunk/reactos/drivers/wdm/audio/backpln/portcls/private.h
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/backpln/…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/backpln/portcls/private.h [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/backpln/portcls/private.h [iso-8859-1] Sun Feb 22
21:58:51 2009
@@ -220,5 +220,11 @@
IN PDEVICE_OBJECT DeviceObject,
IN PIRP Irp);
+NTSTATUS
+NTAPI
+PcPropertyHandler(
+ IN PIRP Irp,
+ IN PSUBDEVICE_DESCRIPTOR Descriptor);
+
#endif
Modified: trunk/reactos/drivers/wdm/audio/backpln/portcls/propertyhandler.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/backpln/…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/backpln/portcls/propertyhandler.c [iso-8859-1]
(original)
+++ trunk/reactos/drivers/wdm/audio/backpln/portcls/propertyhandler.c [iso-8859-1] Sun Feb
22 21:58:51 2009
@@ -1,4 +1,62 @@
#include "private.h"
+
+NTSTATUS
+HandlePropertyInstances(
+ IN PIRP Irp,
+ IN PKSIDENTIFIER Request,
+ IN OUT PVOID Data,
+ IN PSUBDEVICE_DESCRIPTOR Descriptor,
+ IN BOOL Global)
+{
+ KSPIN_CINSTANCES * Instances;
+ KSP_PIN * Pin = (KSP_PIN*)Request;
+
+ if (Pin->PinId >= Descriptor->Factory.PinDescriptorCount)
+ {
+ Irp->IoStatus.Information = 0;
+ Irp->IoStatus.Status = STATUS_INVALID_PARAMETER;
+ return STATUS_INVALID_PARAMETER;
+ }
+
+ Instances = (KSPIN_CINSTANCES*)Data;
+
+ if (Global)
+ Instances->PossibleCount =
Descriptor->Factory.Instances[Pin->PinId].MaxGlobalInstanceCount;
+ else
+ Instances->PossibleCount =
Descriptor->Factory.Instances[Pin->PinId].MaxFilterInstanceCount;
+
+ Instances->CurrentCount =
Descriptor->Factory.Instances[Pin->PinId].CurrentFilterInstanceCount;
+
+ Irp->IoStatus.Information = sizeof(KSPIN_CINSTANCES);
+ Irp->IoStatus.Status = STATUS_SUCCESS;
+ return STATUS_SUCCESS;
+}
+
+NTSTATUS
+HandleNecessaryPropertyInstances(
+ IN PIRP Irp,
+ IN PKSIDENTIFIER Request,
+ IN OUT PVOID Data,
+ IN PSUBDEVICE_DESCRIPTOR Descriptor)
+{
+ PULONG Result;
+ KSP_PIN * Pin = (KSP_PIN*)Request;
+
+ if (Pin->PinId >= Descriptor->Factory.PinDescriptorCount)
+ {
+ Irp->IoStatus.Information = 0;
+ Irp->IoStatus.Status = STATUS_INVALID_PARAMETER;
+ return STATUS_INVALID_PARAMETER;
+ }
+
+ Result = (PULONG)Data;
+ *Result = Descriptor->Factory.Instances[Pin->PinId].MinFilterInstanceCount;
+
+ Irp->IoStatus.Information = sizeof(ULONG);
+ Irp->IoStatus.Status = STATUS_SUCCESS;
+ return STATUS_SUCCESS;
+}
+
NTSTATUS
NTAPI
@@ -7,7 +65,11 @@
IN PKSIDENTIFIER Request,
IN OUT PVOID Data)
{
+ PSUBDEVICE_DESCRIPTOR Descriptor;
NTSTATUS Status = STATUS_UNSUCCESSFUL;
+
+ Descriptor = (PSUBDEVICE_DESCRIPTOR)KSPROPERTY_ITEM_IRP_STORAGE(Irp);
+ ASSERT(Descriptor);
switch(Request->Id)
{
@@ -19,12 +81,19 @@
case KSPROPERTY_PIN_COMMUNICATION:
case KSPROPERTY_PIN_CATEGORY:
case KSPROPERTY_PIN_NAME:
- // KsPinPropertyHandler
- break;
+ Status = KsPinPropertyHandler(Irp, Request, Data,
Descriptor->Factory.PinDescriptorCount, Descriptor->Factory.KsPinDescriptor);
+ break;
+ case KSPROPERTY_PIN_GLOBALCINSTANCES:
+ Status = HandlePropertyInstances(Irp, Request, Data, Descriptor, TRUE);
+ break;
+ case KSPROPERTY_PIN_CINSTANCES:
+ Status = HandlePropertyInstances(Irp, Request, Data, Descriptor, FALSE);
+ break;
+ case KSPROPERTY_PIN_NECESSARYINSTANCES:
+ Status = HandleNecessaryPropertyInstances(Irp, Request, Data, Descriptor);
+ break;
+
case KSPROPERTY_PIN_DATAINTERSECTION:
- case KSPROPERTY_PIN_CINSTANCES:
- case KSPROPERTY_PIN_GLOBALCINSTANCES:
- case KSPROPERTY_PIN_NECESSARYINSTANCES:
case KSPROPERTY_PIN_PHYSICALCONNECTION:
case KSPROPERTY_PIN_CONSTRAINEDDATARANGES:
DPRINT1("Unhandled %x\n", Request->Id);
@@ -52,3 +121,85 @@
NULL /* FIXME */);
}
+NTSTATUS
+NTAPI
+PcPropertyHandler(
+ IN PIRP Irp,
+ IN PSUBDEVICE_DESCRIPTOR Descriptor)
+{
+ ULONG Index, ItemIndex;
+ PIO_STACK_LOCATION IoStack;
+ PKSPROPERTY Property;
+ PFNKSHANDLER PropertyHandler = NULL;
+ UNICODE_STRING GuidString;
+ NTSTATUS Status = STATUS_UNSUCCESSFUL;
+
+ IoStack = IoGetCurrentIrpStackLocation(Irp);
+
+ Property = (PKSPROPERTY)IoStack->Parameters.DeviceIoControl.Type3InputBuffer;
+ ASSERT(Property);
+
+ DPRINT1("Num of Property Sets %u\n",
Descriptor->FilterPropertySet.FreeKsPropertySetOffset);
+ for(Index = 0; Index < Descriptor->FilterPropertySet.FreeKsPropertySetOffset;
Index++)
+ {
+ RtlStringFromGUID ((GUID*)Descriptor->FilterPropertySet.Properties[Index].Set,
&GuidString);
+ DPRINT1("Current GUID %S\n", GuidString.Buffer);
+ RtlFreeUnicodeString(&GuidString);
+
+ if (IsEqualGUIDAligned(&Property->Set,
Descriptor->FilterPropertySet.Properties[Index].Set))
+ {
+ DPRINT1("Found Property Set Properties %u\n",
Descriptor->FilterPropertySet.Properties[Index].PropertiesCount);
+ for(ItemIndex = 0; ItemIndex <
Descriptor->FilterPropertySet.Properties[Index].PropertiesCount; ItemIndex++)
+ {
+ if
(Descriptor->FilterPropertySet.Properties[Index].PropertyItem[ItemIndex].PropertyId ==
Property->Id)
+ {
+ DPRINT1("Found property set identifier %u\n",
Property->Id);
+ if (Property->Flags & KSPROPERTY_TYPE_SET)
+ PropertyHandler =
Descriptor->FilterPropertySet.Properties[Index].PropertyItem[ItemIndex].SetPropertyHandler;
+
+ if (Property->Flags & KSPROPERTY_TYPE_GET)
+ PropertyHandler =
Descriptor->FilterPropertySet.Properties[Index].PropertyItem[ItemIndex].GetPropertyHandler;
+
+ if
(Descriptor->FilterPropertySet.Properties[Index].PropertyItem[ItemIndex].MinProperty
> IoStack->Parameters.DeviceIoControl.InputBufferLength)
+ {
+ /* too small input buffer */
+ Irp->IoStatus.Information =
Descriptor->FilterPropertySet.Properties[Index].PropertyItem[ItemIndex].MinProperty;
+ Irp->IoStatus.Status = STATUS_BUFFER_TOO_SMALL;
+ return STATUS_BUFFER_TOO_SMALL;
+ }
+
+ if
(Descriptor->FilterPropertySet.Properties[Index].PropertyItem[ItemIndex].MinData >
IoStack->Parameters.DeviceIoControl.OutputBufferLength)
+ {
+ /* too small output buffer */
+ Irp->IoStatus.Information =
Descriptor->FilterPropertySet.Properties[Index].PropertyItem[ItemIndex].MinData;
+ Irp->IoStatus.Status = STATUS_BUFFER_TOO_SMALL;
+ return STATUS_BUFFER_TOO_SMALL;
+ }
+
+ if (PropertyHandler)
+ {
+ KSPROPERTY_ITEM_IRP_STORAGE(Irp) = (PVOID)Descriptor;
+ DPRINT1("Calling property handler %p\n",
PropertyHandler);
+ Status = PropertyHandler(Irp, Property, Irp->UserBuffer);
+ }
+
+ /* the information member is set by the handler */
+ Irp->IoStatus.Status = Status;
+ DPRINT1("Result %x\n", Status);
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ return Status;
+ }
+ }
+ }
+ }
+
+ RtlStringFromGUID(&Property->Set, &GuidString);
+ DPRINT1("Unhandeled property: Set %S Id %u Flags %x\n", GuidString.Buffer,
Property->Id, Property->Flags);
+ DbgBreakPoint();
+ RtlFreeUnicodeString(&GuidString);
+ Irp->IoStatus.Information = 0;
+ Irp->IoStatus.Status = STATUS_NOT_IMPLEMENTED;
+ return STATUS_NOT_IMPLEMENTED;
+}
+
+
Modified: trunk/reactos/drivers/wdm/audio/backpln/portcls/undoc.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/backpln/…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/backpln/portcls/undoc.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/backpln/portcls/undoc.c [iso-8859-1] Sun Feb 22
21:58:51 2009
@@ -108,7 +108,17 @@
RtlMoveMemory((PVOID)Descriptor->FilterPropertySet.Properties[Descriptor->FilterPropertySet.FreeKsPropertySetOffset].PropertyItem,
FilterProperty->PropertyItem,
sizeof(KSPROPERTY_ITEM) * FilterProperty->PropertiesCount);
- }
+
+ }
+
Descriptor->FilterPropertySet.Properties[Descriptor->FilterPropertySet.FreeKsPropertySetOffset].Set
= AllocateItem(NonPagedPool, sizeof(GUID), TAG_PORTCLASS);
+ if
(!Descriptor->FilterPropertySet.Properties[Descriptor->FilterPropertySet.FreeKsPropertySetOffset].Set)
+ return STATUS_INSUFFICIENT_RESOURCES;
+
+
RtlCopyMemory((PVOID)Descriptor->FilterPropertySet.Properties[Descriptor->FilterPropertySet.FreeKsPropertySetOffset].Set,
FilterProperty->Set, sizeof(GUID));
+
+ /* ignore fast io table for now */
+
Descriptor->FilterPropertySet.Properties[Descriptor->FilterPropertySet.FreeKsPropertySetOffset].FastIoCount
= 0;
+
Descriptor->FilterPropertySet.Properties[Descriptor->FilterPropertySet.FreeKsPropertySetOffset].FastIoTable
= NULL;
Descriptor->FilterPropertySet.FreeKsPropertySetOffset++;
@@ -177,12 +187,22 @@
if (!Descriptor->Factory.KsPinDescriptor)
goto cleanup;
+ Descriptor->Factory.Instances = AllocateItem(NonPagedPool,
FilterDescription->PinCount * sizeof(PIN_INSTANCE_INFO), TAG_PORTCLASS);
+ if (!Descriptor->Factory.Instances)
+ goto cleanup;
+
Descriptor->Factory.PinDescriptorCount = FilterDescription->PinCount;
Descriptor->Factory.PinDescriptorSize = FilterDescription->PinSize;
/* copy pin factories */
for(Index = 0; Index < FilterDescription->PinCount; Index++)
+ {
RtlMoveMemory(&Descriptor->Factory.KsPinDescriptor[Index],
&FilterDescription->Pins[Index].KsPinDescriptor, FilterDescription->PinSize);
+ Descriptor->Factory.Instances[Index].CurrentFilterInstanceCount = 0;
+ Descriptor->Factory.Instances[Index].MaxFilterInstanceCount =
FilterDescription->Pins[Index].MaxFilterInstanceCount;
+ Descriptor->Factory.Instances[Index].MaxGlobalInstanceCount =
FilterDescription->Pins[Index].MaxGlobalInstanceCount;
+ Descriptor->Factory.Instances[Index].MinFilterInstanceCount =
FilterDescription->Pins[Index].MinFilterInstanceCount;
+ }
}
*OutSubdeviceDescriptor = Descriptor;
Modified: trunk/reactos/drivers/wdm/audio/legacy/wdmaud/control.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/legacy/w…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/legacy/wdmaud/control.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/legacy/wdmaud/control.c [iso-8859-1] Sun Feb 22
21:58:51 2009
@@ -44,6 +44,7 @@
ACCESS_MASK DesiredAccess = 0;
HANDLE PinHandle;
KSPIN_CONNECT * PinConnect;
+ ULONG Length;
KSDATAFORMAT_WAVEFORMATEX * DataFormat;
if (DeviceInfo->DeviceType != WAVE_OUT_DEVICE_TYPE)
@@ -52,7 +53,8 @@
return SetIrpIoStatus(Irp, STATUS_UNSUCCESSFUL, 0);
}
- InstanceInfo = ExAllocatePool(NonPagedPool, sizeof(KSDATAFORMAT_WAVEFORMATEX) +
sizeof(KSPIN_CONNECT));
+ Length = sizeof(KSDATAFORMAT_WAVEFORMATEX) + sizeof(KSPIN_CONNECT) +
sizeof(SYSAUDIO_INSTANCE_INFO);
+ InstanceInfo = ExAllocatePool(NonPagedPool, Length);
if (!InstanceInfo)
{
/* no memory */
@@ -90,7 +92,7 @@
DesiredAccess |= GENERIC_WRITE;
}
- PinConnect = (KSPIN_CONNECT*)InstanceInfo;
+ PinConnect = (KSPIN_CONNECT*)(InstanceInfo + 1);
PinConnect->Interface.Set = KSINTERFACESETID_Standard;
@@ -100,7 +102,7 @@
PinConnect->Medium.Id = KSMEDIUM_TYPE_ANYINSTANCE;
PinConnect->Medium.Flags = 0;
PinConnect->PinId = 0; //FIXME
- PinConnect->PinToHandle = NULL;
+ PinConnect->PinToHandle = ClientInfo->hSysAudio;
PinConnect->Priority.PriorityClass = KSPRIORITY_NORMAL;
PinConnect->Priority.PrioritySubClass = 1;
@@ -125,16 +127,25 @@
DataFormat->DataFormat.Specifier = KSDATAFORMAT_SPECIFIER_WAVEFORMATEX;
DataFormat->DataFormat.SampleSize = 4;
-
- Status = KsCreatePin(ClientInfo->hSysAudio, PinConnect, DesiredAccess,
&PinHandle);
- DPRINT1("KsCreatePin Status %x\n", Status);
-
-
- /* free buffer */
- ExFreePool(InstanceInfo);
-
+ /* ros specific pin creation request */
+ InstanceInfo->Property.Id = (ULONG)-1;
+ Status = KsSynchronousIoControlDevice(ClientInfo->FileObject, KernelMode,
IOCTL_KS_PROPERTY, (PVOID)InstanceInfo, Length, &PinHandle, sizeof(HANDLE),
&BytesReturned);
if (NT_SUCCESS(Status))
{
+ PHANDLE Handels = ExAllocatePool(NonPagedPool, sizeof(HANDLE) *
(ClientInfo->NumPins+1));
+
+ if (Handels)
+ {
+ if (ClientInfo->NumPins)
+ {
+ RtlMoveMemory(Handels, ClientInfo->hPins, sizeof(HANDLE) *
ClientInfo->NumPins);
+ ExFreePool(ClientInfo->hPins);
+ }
+
+ ClientInfo->hPins = Handels;
+ ClientInfo->hPins[ClientInfo->NumPins] = PinHandle;
+ ClientInfo->NumPins++;
+ }
DeviceInfo->hDevice = PinHandle;
}
else
@@ -338,7 +349,6 @@
IoStack = IoGetCurrentIrpStackLocation(Irp);
DPRINT1("WdmAudDeviceControl entered\n");
- DbgBreakPoint();
if (IoStack->Parameters.DeviceIoControl.InputBufferLength <
sizeof(WDMAUD_DEVICE_INFO))
{
Modified: trunk/reactos/drivers/wdm/audio/legacy/wdmaud/entry.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/legacy/w…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/legacy/wdmaud/entry.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/legacy/wdmaud/entry.c [iso-8859-1] Sun Feb 22 21:58:51
2009
@@ -167,53 +167,64 @@
{
NTSTATUS Status = STATUS_SUCCESS;
PWDMAUD_DEVICE_EXTENSION DeviceExtension;
+
+ DPRINT1("WdmAudClose\n");
+
+ DeviceExtension = (PWDMAUD_DEVICE_EXTENSION)DeviceObject->DeviceExtension;
+
+#if KS_IMPLEMENTED
+ Status = KsDereferenceSoftwareBusObject(DeviceExtension->DeviceHeader);
+
+ if (NT_SUCCESS(Status))
+ {
+ if (DeviceExtension->SysAudioNotification)
+ Status =
IoUnregisterPlugPlayNotification(DeviceExtension->SysAudioNotification);
+ }
+#endif
+
+ Irp->IoStatus.Status = Status;
+ Irp->IoStatus.Information = 0;
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
+
+ return Status;
+}
+
+NTSTATUS
+NTAPI
+WdmAudCleanup(
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PIRP Irp)
+{
PIO_STACK_LOCATION IoStack;
WDMAUD_CLIENT *pClient;
-
- DPRINT1("WdmAudClose\n");
-
- DeviceExtension = (PWDMAUD_DEVICE_EXTENSION)DeviceObject->DeviceExtension;
-
-#if KS_IMPLEMENTED
- Status = KsDereferenceSoftwareBusObject(DeviceExtension->DeviceHeader);
-
- if (NT_SUCCESS(Status))
- {
- if (DeviceExtension->SysAudioNotification)
- Status =
IoUnregisterPlugPlayNotification(DeviceExtension->SysAudioNotification);
- }
-#endif
+ ULONG Index;
+
+ DPRINT1("WdmAudCleanup\n");
IoStack = IoGetCurrentIrpStackLocation(Irp);
pClient = (WDMAUD_CLIENT*)IoStack->FileObject->FsContext;
+
if (pClient)
{
+ for (Index = 0; Index < pClient->NumPins; Index++)
+ ZwClose(pClient->hPins[Index]);
+
+ if (pClient->hPins)
+ {
+ ExFreePool(pClient->hPins);
+ }
+
ObDereferenceObject(pClient->FileObject);
ZwClose(pClient->hSysAudio);
ExFreePool(pClient);
IoStack->FileObject->FsContext = NULL;
}
- Irp->IoStatus.Status = Status;
- Irp->IoStatus.Information = 0;
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
- return Status;
-}
-
-NTSTATUS
-NTAPI
-WdmAudCleanup(
- IN PDEVICE_OBJECT DeviceObject,
- IN PIRP Irp)
-{
- UNIMPLEMENTED
-
Irp->IoStatus.Status = STATUS_SUCCESS;
Irp->IoStatus.Information = 0;
IoCompleteRequest(Irp, IO_NO_INCREMENT);
-
+ DPRINT1("WdmAudCleanup complete\n");
return STATUS_SUCCESS;
}
Modified: trunk/reactos/drivers/wdm/audio/legacy/wdmaud/wdmaud.h
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/legacy/w…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/legacy/wdmaud/wdmaud.h [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/legacy/wdmaud/wdmaud.h [iso-8859-1] Sun Feb 22
21:58:51 2009
@@ -65,6 +65,8 @@
HANDLE hProcess;
HANDLE hSysAudio;
PFILE_OBJECT FileObject;
+ ULONG NumPins;
+ HANDLE * hPins;
}WDMAUD_CLIENT, *PWDMAUD_CLIENT;
Modified: trunk/reactos/drivers/wdm/audio/sysaudio/control.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/sysaudio…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/sysaudio/control.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/sysaudio/control.c [iso-8859-1] Sun Feb 22 21:58:51
2009
@@ -19,6 +19,8 @@
const GUID KSPROPSETID_Sysaudio = {0xCBE3FAA0L, 0xCC75, 0x11D0, {0xB4,
0x65, 0x00, 0x00, 0x1A, 0x18, 0x18, 0xE6}};
const GUID KSPROPSETID_Sysaudio_Pin = {0xA3A53220L, 0xC6E4, 0x11D0, {0xB4,
0x65, 0x00, 0x00, 0x1A, 0x18, 0x18, 0xE6}};
const GUID KSPROPSETID_General = {0x1464EDA5L, 0x6A8F, 0x11D1, {0x9A,
0xA7, 0x00, 0xA0, 0xC9, 0x22, 0x31, 0x96}};
+const GUID KSPROPSETID_Pin = {0x8C134960L, 0x51AD, 0x11CF, {0x87,
0x8A, 0x94, 0xF8, 0x01, 0xC1, 0x00, 0x00}};
+const GUID KSPROPSETID_Connection = {0x1D58C920L, 0xAC9B, 0x11CF, {0xA5,
0xD6, 0x28, 0xDB, 0x04, 0xC1, 0x00, 0x00}};
NTSTATUS
@@ -57,6 +59,7 @@
PSYSAUDIODEVEXT DeviceExtension)
{
PULONG Index;
+ PHANDLE Handle;
ULONG Count;
PSYSAUDIO_CLIENT ClientInfo;
PKSAUDIO_DEVICE_ENTRY Entry;
@@ -88,8 +91,17 @@
/* no memory */
return SetIrpIoStatus(Irp, STATUS_NO_MEMORY, 0);
}
+
+ ClientInfo->Handels = ExAllocatePool(NonPagedPool, sizeof(HANDLE));
+ if (!ClientInfo->Devices)
+ {
+ /* no memory */
+ return SetIrpIoStatus(Irp, STATUS_NO_MEMORY, 0);
+ }
+
ClientInfo->NumDevices = 1;
ClientInfo->Devices[0] = DeviceNumber;
+ ClientInfo->Handels[0] = NULL;
/* increase usage count */
Entry->NumberOfClients++;
return SetIrpIoStatus(Irp, STATUS_SUCCESS, 0);
@@ -111,18 +123,157 @@
/* no memory */
return SetIrpIoStatus(Irp, STATUS_NO_MEMORY, 0);
}
+
+ Handle = ExAllocatePool(NonPagedPool, sizeof(HANDLE) * (ClientInfo->NumDevices +
1));
+ if (!Handle)
+ {
+ /* no memory */
+ ExFreePool(Index);
+ return SetIrpIoStatus(Irp, STATUS_NO_MEMORY, 0);
+ }
+
/* increase usage count */
Entry->NumberOfClients++;
/* copy device count array */
- RtlMoveMemory(Index, ClientInfo->Devices, ClientInfo->NumDevices *
sizeof(ULONG));
+ if (ClientInfo->NumDevices)
+ {
+ RtlMoveMemory(Index, ClientInfo->Devices, ClientInfo->NumDevices *
sizeof(ULONG));
+ RtlMoveMemory(Handle, ClientInfo->Handels, ClientInfo->NumDevices *
sizeof(HANDLE));
+ }
+
Index[ClientInfo->NumDevices] = DeviceNumber;
+ Handle[ClientInfo->NumDevices] = NULL;
+ ExFreePool(ClientInfo->Handels);
ExFreePool(ClientInfo->Devices);
ClientInfo->NumDevices++;
ClientInfo->Devices = Index;
+ ClientInfo->Handels = Handle;
return SetIrpIoStatus(Irp, STATUS_SUCCESS, 0);
-
+}
+
+VOID
+NTAPI
+CreatePinWorkerRoutine(
+ IN PDEVICE_OBJECT DeviceObject,
+ IN PVOID Context)
+{
+ NTSTATUS Status;
+ HANDLE PinHandle;
+ HANDLE Filter;
+ PFILE_OBJECT FileObject;
+ PPIN_WORKER_CONTEXT WorkerContext = (PPIN_WORKER_CONTEXT)Context;
+ Filter = WorkerContext->PinConnect->PinToHandle;
+
+ WorkerContext->PinConnect->PinToHandle = NULL;
+
+
+ if (WorkerContext->CreateRealPin)
+ {
+ /* create the real pin */
+ Status = KsCreatePin(WorkerContext->Entry->Handle,
WorkerContext->PinConnect, GENERIC_READ | GENERIC_WRITE, &PinHandle);
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failed to create Pin with %x\n", Status);
+ SetIrpIoStatus(WorkerContext->Irp, STATUS_UNSUCCESSFUL, 0);
+ ExFreePool(WorkerContext);
+ return;
+ }
+
+ /* get pin file object */
+ Status = ObReferenceObjectByHandle(PinHandle,
+ GENERIC_READ | GENERIC_WRITE,
+ IoFileObjectType, KernelMode,
(PVOID*)&FileObject, NULL);
+
+
WorkerContext->Entry->Pins[WorkerContext->PinConnect->PinId].PinHandle =
PinHandle;
+
WorkerContext->Entry->Pins[WorkerContext->PinConnect->PinId].References = 1;
+ WorkerContext->DispatchContext->Handle = PinHandle;
+ WorkerContext->DispatchContext->PinId =
WorkerContext->PinConnect->PinId;
+ WorkerContext->DispatchContext->AudioEntry = WorkerContext->Entry;
+
+ if (NT_SUCCESS(Status))
+ WorkerContext->DispatchContext->FileObject = FileObject;
+ else
+ WorkerContext->DispatchContext->FileObject = NULL;
+ }
+ else
+ {
+ WorkerContext->DispatchContext->AudioEntry = WorkerContext->Entry;
+ WorkerContext->DispatchContext->Handle =
WorkerContext->Entry->Pins[WorkerContext->PinConnect->PinId].PinHandle;
+ WorkerContext->DispatchContext->PinId =
WorkerContext->PinConnect->PinId;
+
+ /* get pin file object */
+ Status = ObReferenceObjectByHandle(PinHandle,
+ GENERIC_READ | GENERIC_WRITE,
+ IoFileObjectType, KernelMode,
(PVOID*)&FileObject, NULL);
+
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failed to get file object with %x\n", Status);
+ SetIrpIoStatus(WorkerContext->Irp, STATUS_UNSUCCESSFUL, 0);
+ ExFreePool(WorkerContext);
+ return;
+ }
+ WorkerContext->DispatchContext->FileObject = FileObject;
+ }
+
+ DPRINT1("creating virtual pin\n");
+ /* now create the virtual audio pin which is exposed to wdmaud */
+ Status = KsCreatePin(Filter, WorkerContext->PinConnect, GENERIC_READ |
GENERIC_WRITE, &PinHandle);
+
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failed to create virtual pin with %x\n", Status);
+ if (WorkerContext->CreateRealPin)
+ {
+ /* mark pin as free to use */
+
WorkerContext->Entry->Pins[WorkerContext->PinConnect->PinId].References = 0;
+ }
+
+ SetIrpIoStatus(WorkerContext->Irp, STATUS_UNSUCCESSFUL, 0);
+ ExFreePool(WorkerContext);
+ return;
+ }
+
+ /* get pin file object */
+ Status = ObReferenceObjectByHandle(PinHandle,
+ GENERIC_READ | GENERIC_WRITE,
+ IoFileObjectType, KernelMode,
(PVOID*)&FileObject, NULL);
+
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failed to get file object with %x\n", Status);
+ if (WorkerContext->CreateRealPin)
+ {
+ /* mark pin as free to use */
+
WorkerContext->Entry->Pins[WorkerContext->PinConnect->PinId].References = 0;
+ }
+
+ ZwClose(PinHandle);
+ SetIrpIoStatus(WorkerContext->Irp, STATUS_UNSUCCESSFUL, 0);
+ ExFreePool(WorkerContext);
+ return;
+ }
+
+ ASSERT(WorkerContext->DispatchContext);
+ ASSERT(WorkerContext->DispatchContext->AudioEntry != NULL);
+ ASSERT(WorkerContext->DispatchContext->FileObject != NULL);
+ ASSERT(WorkerContext->DispatchContext->Handle != NULL);
+ ASSERT(WorkerContext->AudioClient);
+ ASSERT(WorkerContext->AudioClient->Handels);
+
ASSERT(WorkerContext->AudioClient->Handels[WorkerContext->AudioClient->NumDevices
-1] == NULL);
+
+ /* store pin context */
+ FileObject->FsContext2 = (PVOID)WorkerContext->DispatchContext;
+
+ /* store pin handle in client specific struct */
+ WorkerContext->AudioClient->Handels[WorkerContext->AudioClient->NumDevices-1]
= PinHandle;
+
+ DPRINT1("Successfully created Pin %p\n", WorkerContext->Irp);
+ *((PHANDLE)WorkerContext->Irp->UserBuffer) = PinHandle;
+
+ SetIrpIoStatus(WorkerContext->Irp, STATUS_SUCCESS, sizeof(HANDLE));
}
@@ -144,6 +295,14 @@
ULONG Count, BytesReturned;
PKSOBJECT_CREATE_ITEM CreateItem;
UNICODE_STRING GuidString;
+ ULONG Length;
+ KSPIN_CONNECT * PinConnect;
+ KSP_PIN PinRequest;
+ KSPIN_CINSTANCES PinInstances;
+ PPIN_WORKER_CONTEXT WorkerContext;
+ PDISPATCH_CONTEXT DispatchContext;
+ PIO_WORKITEM WorkItem;
+ PFILE_OBJECT FileObject;
/* access the create item */
CreateItem = KSCREATE_ITEM_IRP_STORAGE(Irp);
@@ -279,6 +438,194 @@
return SetIrpIoStatus(Irp, STATUS_UNSUCCESSFUL, 0);
}
}
+ else if (Property->Id == (ULONG)-1)
+ {
+ /* ros specific pin creation request */
+ DPRINT1("Initiating create request\n");
+
+ Length = sizeof(KSDATAFORMAT) + sizeof(KSPIN_CONNECT) +
sizeof(SYSAUDIO_INSTANCE_INFO);
+ if (IoStack->Parameters.DeviceIoControl.InputBufferLength < Length ||
+ IoStack->Parameters.DeviceIoControl.OutputBufferLength <
sizeof(HANDLE))
+ {
+ /* invalid parameters */
+ return SetIrpIoStatus(Irp, STATUS_INVALID_PARAMETER, 0);
+ }
+
+ /* get input parameter */
+ InstanceInfo = (PSYSAUDIO_INSTANCE_INFO)Property;
+ if (DeviceExtension->NumberOfKsAudioDevices <=
InstanceInfo->DeviceNumber)
+ {
+ /* invalid parameters */
+ return SetIrpIoStatus(Irp, STATUS_INVALID_PARAMETER, 0);
+ }
+
+ /* get client context */
+ ClientInfo = (PSYSAUDIO_CLIENT)CreateItem->Context;
+ ASSERT(ClientInfo);
+ ASSERT(ClientInfo->NumDevices >= 1);
+ ASSERT(ClientInfo->Devices != NULL);
+ ASSERT(ClientInfo->Devices[ClientInfo->NumDevices-1] ==
InstanceInfo->DeviceNumber);
+
+ /* get sysaudio entry */
+ Entry = GetListEntry(&DeviceExtension->KsAudioDeviceList,
InstanceInfo->DeviceNumber);
+ ASSERT(Entry != NULL);
+
+ if (!Entry->Pins)
+ {
+ PropertyRequest.Set = KSPROPSETID_Pin;
+ PropertyRequest.Flags = KSPROPERTY_TYPE_GET;
+ PropertyRequest.Id = KSPROPERTY_PIN_CTYPES;
+
+ /* query for num of pins */
+ Status = KsSynchronousIoControlDevice(Entry->FileObject, KernelMode,
IOCTL_KS_PROPERTY, (PVOID)&PropertyRequest, sizeof(KSPROPERTY), (PVOID)&Count,
sizeof(ULONG), &BytesReturned);
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT("Property Request KSPROPERTY_PIN_CTYPES failed with
%x\n", Status);
+ return SetIrpIoStatus(Irp, Status, 0);
+ }
+ DPRINT("KSPROPERTY_TYPE_GET num pins %d\n", Count);
+
+ Entry->Pins = ExAllocatePool(NonPagedPool, Count * sizeof(PIN_INFO));
+ if (!Entry->Pins)
+ {
+ /* invalid parameters */
+ return SetIrpIoStatus(Irp, STATUS_NO_MEMORY, 0);
+ }
+ /* clear array */
+ RtlZeroMemory(Entry->Pins, sizeof(PIN_INFO) * Count);
+ Entry->NumberOfPins = Count;
+
+ }
+
+ /* get connect details */
+ PinConnect = (KSPIN_CONNECT*)(InstanceInfo + 1);
+
+ if (Entry->NumberOfPins <= PinConnect->PinId)
+ {
+ DPRINT("Invalid PinId %x\n", PinConnect->PinId);
+ return SetIrpIoStatus(Irp, STATUS_INVALID_PARAMETER, 0);
+ }
+
+ PinRequest.PinId = PinConnect->PinId;
+ PinRequest.Property.Set = KSPROPSETID_Pin;
+ PinRequest.Property.Flags = KSPROPERTY_TYPE_GET;
+ PinRequest.Property.Id = KSPROPERTY_PIN_CINSTANCES;
+
+ //RtlZeroMemory(&PinInstances, sizeof(KSPIN_CINSTANCES));
+ Status = KsSynchronousIoControlDevice(Entry->FileObject, KernelMode,
IOCTL_KS_PROPERTY, (PVOID)&PinRequest, sizeof(KSP_PIN), (PVOID)&PinInstances,
sizeof(KSPIN_CINSTANCES), &BytesReturned);
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT("Property Request KSPROPERTY_PIN_GLOBALCINSTANCES failed with
%x\n", Status);
+ return SetIrpIoStatus(Irp, Status, 0);
+ }
+ DPRINT1("PinInstances Current %u Max %u\n",
PinInstances.CurrentCount, PinInstances.PossibleCount);
+
+ WorkItem = IoAllocateWorkItem(DeviceObject);
+ if (!WorkItem)
+ {
+ Irp->IoStatus.Information = 0;
+ Irp->IoStatus.Status = STATUS_INSUFFICIENT_RESOURCES;
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ return STATUS_INSUFFICIENT_RESOURCES;
+ }
+
+ /* create worker context */
+ WorkerContext = ExAllocatePool(NonPagedPool, sizeof(PIN_WORKER_CONTEXT));
+ if (!WorkerContext)
+ {
+ /* invalid parameters */
+ IoFreeWorkItem(WorkItem);
+ return SetIrpIoStatus(Irp, STATUS_NO_MEMORY, 0);
+ }
+
+ /* create worker context */
+ DispatchContext = ExAllocatePool(NonPagedPool, sizeof(DISPATCH_CONTEXT));
+ if (!DispatchContext)
+ {
+ /* invalid parameters */
+ IoFreeWorkItem(WorkItem);
+ ExFreePool(WorkerContext);
+ return SetIrpIoStatus(Irp, STATUS_NO_MEMORY, 0);
+ }
+ /* prepare context */
+ RtlZeroMemory(WorkerContext, sizeof(PIN_WORKER_CONTEXT));
+ RtlZeroMemory(DispatchContext, sizeof(DISPATCH_CONTEXT));
+
+ if (PinInstances.CurrentCount == PinInstances.PossibleCount)
+ {
+ /* pin already exists */
+ DPRINT1("Pins %p\n", Entry->Pins);
+ DbgBreakPoint();
+ ASSERT(Entry->Pins[PinConnect->PinId].PinHandle != NULL);
+
+ if (Entry->Pins[PinConnect->PinId].References != 0)
+ {
+ /* FIXME need ksmixer */
+ DPRINT1("Device %u Pin %u is already occupied, try
later\n", InstanceInfo->DeviceNumber, PinConnect->PinId);
+ IoFreeWorkItem(WorkItem);
+ ExFreePool(WorkerContext);
+ ExFreePool(DispatchContext);
+ return SetIrpIoStatus(Irp, STATUS_UNSUCCESSFUL, 0);
+ }
+ /* re-using pin */
+ PropertyRequest.Set = KSPROPSETID_Connection;
+ PropertyRequest.Flags = KSPROPERTY_TYPE_SET;
+ PropertyRequest.Id = KSPROPERTY_CONNECTION_DATAFORMAT;
+
+ /* get pin file object */
+ Status =
ObReferenceObjectByHandle(Entry->Pins[PinConnect->PinId].PinHandle,
+ GENERIC_READ | GENERIC_WRITE,
+ IoFileObjectType, KernelMode,
(PVOID*)&FileObject, NULL);
+
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failed to get pin file object with %x\n",
Status);
+ IoFreeWorkItem(WorkItem);
+ ExFreePool(WorkerContext);
+ ExFreePool(DispatchContext);
+ return SetIrpIoStatus(Irp, Status, 0);
+ }
+
+ Length -= sizeof(KSPIN_CONNECT) + sizeof(SYSAUDIO_INSTANCE_INFO);
+ Status = KsSynchronousIoControlDevice(FileObject, KernelMode,
IOCTL_KS_PROPERTY, (PVOID)&PropertyRequest, sizeof(KSPROPERTY),
+ (PVOID)(PinConnect + 1), Length,
&BytesReturned);
+
+ ObDereferenceObject(FileObject);
+
+ if (!NT_SUCCESS(Status))
+ {
+ DPRINT1("Failed to set format with Status %x\n", Status);
+ IoFreeWorkItem(WorkItem);
+ ExFreePool(WorkerContext);
+ ExFreePool(DispatchContext);
+ return SetIrpIoStatus(Irp, Status, 0);
+ }
+
+ }
+ else
+ {
+ /* create the real pin */
+ WorkerContext->CreateRealPin = TRUE;
+ }
+
+ /* set up context */
+
+ WorkerContext->DispatchContext = DispatchContext;
+ WorkerContext->Entry = Entry;
+ WorkerContext->Irp = Irp;
+ WorkerContext->PinConnect = PinConnect;
+ WorkerContext->AudioClient = ClientInfo;
+
+ DPRINT("Queing Irp %p\n", Irp);
+ /* queue the work item */
+ IoMarkIrpPending(Irp);
+ Irp->IoStatus.Status = STATUS_PENDING;
+ Irp->IoStatus.Information = 0;
+ IoQueueWorkItem(WorkItem, CreatePinWorkerRoutine, DelayedWorkQueue,
(PVOID)WorkerContext);
+
+ /* mark irp as pending */
+ return STATUS_PENDING;
+ }
}
RtlStringFromGUID(&Property->Set, &GuidString);
@@ -288,5 +635,3 @@
return Status;
}
-
-
Modified: trunk/reactos/drivers/wdm/audio/sysaudio/dispatcher.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/sysaudio…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/sysaudio/dispatcher.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/sysaudio/dispatcher.c [iso-8859-1] Sun Feb 22 21:58:51
2009
@@ -66,7 +66,11 @@
PIRP Irp)
{
DPRINT1("Dispatch_fnFlush called DeviceObject %p Irp %p\n", DeviceObject);
-
+ //FIXME
+ // cleanup resources
+ Irp->IoStatus.Status = STATUS_SUCCESS;
+ Irp->IoStatus.Information = 0;
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
return STATUS_SUCCESS;
}
@@ -76,9 +80,39 @@
PDEVICE_OBJECT DeviceObject,
PIRP Irp)
{
+ PSYSAUDIO_CLIENT Client;
+ PIO_STACK_LOCATION IoStatus;
+ ULONG Index;
+
+
DPRINT1("Dispatch_fnClose called DeviceObject %p Irp %p\n", DeviceObject);
-
+ IoStatus = IoGetCurrentIrpStackLocation(Irp);
+
+ Client = (PSYSAUDIO_CLIENT)IoStatus->FileObject->FsContext2;
+
+ DPRINT1("Client %p NumDevices %u\n", Client, Client->NumDevices);
+ for(Index = 0; Index < Client->NumDevices; Index++)
+ {
+ if (Client->Handels[Index])
+ {
+ ZwClose(Client->Handels[Index]);
+ }
+ }
+
+ if (Client->Handels)
+ ExFreePool(Client->Handels);
+
+ if (Client->Devices)
+ ExFreePool(Client->Devices);
+
+ ExFreePool(Client);
+
+ //FIXME
+ // cleanup resources
+ Irp->IoStatus.Status = STATUS_SUCCESS;
+ Irp->IoStatus.Information = 0;
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
return STATUS_SUCCESS;
}
@@ -175,61 +209,6 @@
Dispatch_fnFastWrite,
};
-VOID
-NTAPI
-CreatePinWorkerRoutine(
- IN PDEVICE_OBJECT DeviceObject,
- IN PVOID Context)
-{
- NTSTATUS Status;
- HANDLE PinHandle;
- HANDLE * Handels;
- PFILE_OBJECT FileObject;
- PIRP Irp;
- PPIN_WORKER_CONTEXT WorkerContext = (PPIN_WORKER_CONTEXT)Context;
-
- Handels = ExAllocatePool(NonPagedPool, (WorkerContext->Entry->NumberOfPins + 1)
* sizeof(HANDLE));
- if (!Handels)
- {
- DPRINT1("No Memory \n");
- WorkerContext->Irp->IoStatus.Status = STATUS_NO_MEMORY;
- WorkerContext->Irp->IoStatus.Information = 0;
- IoCompleteRequest(WorkerContext->Irp, IO_SOUND_INCREMENT);
- return;
- }
-
-
- Status = KsCreatePin(WorkerContext->Entry->Handle,
WorkerContext->PinConnect, GENERIC_READ | GENERIC_WRITE, &PinHandle);
- DPRINT1("KsCreatePin status %x\n", Status);
-
- if (NT_SUCCESS(Status))
- {
- Status = ObReferenceObjectByHandle(PinHandle, GENERIC_READ | GENERIC_WRITE,
IoFileObjectType, KernelMode, (PVOID*)&FileObject, NULL);
- if (NT_SUCCESS(Status))
- {
- Status = CreateDispatcher(WorkerContext->Irp, PinHandle, FileObject);
- DPRINT1("Pins %x\n", WorkerContext->Entry->NumberOfPins);
- if (WorkerContext->Entry->NumberOfPins)
- {
- RtlMoveMemory(Handels, WorkerContext->Entry->Pins,
WorkerContext->Entry->NumberOfPins * sizeof(HANDLE));
- ExFreePool(WorkerContext->Entry->Pins);
- }
- Handels[WorkerContext->Entry->NumberOfPins-1] = PinHandle;
- WorkerContext->Entry->Pins = Handels;
- WorkerContext->Entry->NumberOfPins++;
- }
- }
-
- DPRINT1("CreatePinWorkerRoutine completing irp\n");
- WorkerContext->Irp->IoStatus.Status = Status;
- WorkerContext->Irp->IoStatus.Information = 0;
-
- Irp = WorkerContext->Irp;
- ExFreePool(Context);
-
- IoCompleteRequest(Irp, IO_SOUND_INCREMENT);
-}
-
NTSTATUS
NTAPI
DispatchCreateSysAudio(
@@ -242,12 +221,7 @@
PKSOBJECT_CREATE_ITEM CreateItem;
PIO_STACK_LOCATION IoStatus;
LPWSTR Buffer;
- ULONG Length, DeviceIndex;
- PSYSAUDIODEVEXT DeviceExtension;
- PKSAUDIO_DEVICE_ENTRY Entry;
- KSPIN_CONNECT * PinConnect;
- PIO_WORKITEM WorkItem;
- PPIN_WORKER_CONTEXT Context;
+
static LPWSTR KS_NAME_PIN = L"{146F1A80-4791-11D0-A5D6-28DB04C10000}";
IoStatus = IoGetCurrentIrpStackLocation(Irp);
@@ -260,57 +234,12 @@
/* is the request for a new pin */
if (!wcsncmp(KS_NAME_PIN, Buffer, wcslen(KS_NAME_PIN)))
{
- Client =
(PSYSAUDIO_CLIENT)Irp->Tail.Overlay.OriginalFileObject->FsContext2;
- DeviceExtension = (PSYSAUDIODEVEXT)DeviceObject->DeviceExtension;
- if (Client)
- {
- ASSERT(Client->NumDevices >= 1);
- DeviceIndex = Client->Devices[Client->NumDevices-1];
- }
- else
- {
- DPRINT1("Warning: using HACK\n");
- DeviceIndex = 0;
- }
- ASSERT(DeviceIndex < DeviceExtension->NumberOfKsAudioDevices);
- Entry = GetListEntry(&DeviceExtension->KsAudioDeviceList,
DeviceIndex);
- ASSERT(Entry);
-
- Length = (IoStatus->FileObject->FileName.Length -
((wcslen(KS_NAME_PIN)+1) * sizeof(WCHAR)));
- PinConnect = ExAllocatePool(NonPagedPool, Length);
- if (!PinConnect)
- {
- Irp->IoStatus.Status = STATUS_NO_MEMORY;
- Irp->IoStatus.Information = 0;
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
- return STATUS_NO_MEMORY;
- }
- RtlMoveMemory(PinConnect, IoStatus->FileObject->FileName.Buffer +
(wcslen(KS_NAME_PIN)+1), Length);
- Context = ExAllocatePool(NonPagedPool, sizeof(PIN_WORKER_CONTEXT));
- if (!Context)
- {
- Irp->IoStatus.Information = 0;
- Irp->IoStatus.Status = STATUS_INSUFFICIENT_RESOURCES;
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
- return STATUS_INSUFFICIENT_RESOURCES;
- }
- Context->PinConnect = PinConnect;
- Context->Entry = Entry;
- Context->Irp = Irp;
-
- WorkItem = IoAllocateWorkItem(DeviceObject);
- if (!WorkItem)
- {
- Irp->IoStatus.Information = 0;
- Irp->IoStatus.Status = STATUS_INSUFFICIENT_RESOURCES;
- IoCompleteRequest(Irp, IO_NO_INCREMENT);
- return STATUS_INSUFFICIENT_RESOURCES;
- }
- IoQueueWorkItem(WorkItem, CreatePinWorkerRoutine, DelayedWorkQueue,
(PVOID)Context);
+ Status = CreateDispatcher(Irp);
+ DPRINT1("Virtual pin Status %x\n", Status);
Irp->IoStatus.Information = 0;
- Irp->IoStatus.Status = STATUS_PENDING;
- IoMarkIrpPending(Irp);
- return STATUS_PENDING;
+ Irp->IoStatus.Status = Status;
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
+ return Status;
}
}
@@ -341,6 +270,10 @@
Status = KsAllocateObjectHeader(&ObjectHeader, 1, CreateItem, Irp,
&DispatchTable);
DPRINT1("KsAllocateObjectHeader result %x\n", Status);
+ /* complete the irp */
+ Irp->IoStatus.Information = 0;
+ Irp->IoStatus.Status = Status;
+ IoCompleteRequest(Irp, IO_NO_INCREMENT);
return Status;
}
Modified: trunk/reactos/drivers/wdm/audio/sysaudio/pin.c
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/sysaudio…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/sysaudio/pin.c [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/sysaudio/pin.c [iso-8859-1] Sun Feb 22 21:58:51 2009
@@ -23,18 +23,16 @@
PIRP Irp)
{
PDISPATCH_CONTEXT Context;
- PKSOBJECT_CREATE_ITEM CreateItem;
NTSTATUS Status;
ULONG BytesReturned;
PIO_STACK_LOCATION IoStack;
DPRINT1("Pin_fnDeviceIoControl called DeviceObject %p Irp %p\n",
DeviceObject);
- /* access the create item */
- CreateItem = KSCREATE_ITEM_IRP_STORAGE(Irp);
- Context = (PDISPATCH_CONTEXT)CreateItem->Context;
-
IoStack = IoGetCurrentIrpStackLocation(Irp);
+
+ Context = (PDISPATCH_CONTEXT)IoStack->FileObject->FsContext2;
+ ASSERT(Context);
Status = KsSynchronousIoControlDevice(Context->FileObject, KernelMode,
IoStack->Parameters.DeviceIoControl.IoControlCode,
IoStack->Parameters.DeviceIoControl.Type3InputBuffer,
@@ -84,18 +82,16 @@
PIRP Irp)
{
PDISPATCH_CONTEXT Context;
- PKSOBJECT_CREATE_ITEM CreateItem;
PIO_STACK_LOCATION IoStack;
ULONG BytesReturned;
NTSTATUS Status;
DPRINT1("Pin_fnWrite called DeviceObject %p Irp %p\n", DeviceObject);
- /* access the create item */
- CreateItem = KSCREATE_ITEM_IRP_STORAGE(Irp);
- Context = (PDISPATCH_CONTEXT)CreateItem->Context;
-
IoStack = IoGetCurrentIrpStackLocation(Irp);
+
+ Context = (PDISPATCH_CONTEXT)IoStack->FileObject->FsContext2;
+ ASSERT(Context);
Status = KsSynchronousIoControlDevice(Context->FileObject, KernelMode,
IOCTL_KS_WRITE_STREAM,
IoStack->Parameters.DeviceIoControl.Type3InputBuffer,
@@ -228,34 +224,12 @@
NTSTATUS
CreateDispatcher(
- IN PIRP Irp,
- IN HANDLE Handle,
- IN PFILE_OBJECT FileObject)
-{
- PKSOBJECT_CREATE_ITEM CreateItem;
+ IN PIRP Irp)
+{
NTSTATUS Status;
KSOBJECT_HEADER ObjectHeader;
- PDISPATCH_CONTEXT Context;
-
- /* allocate create item */
- CreateItem = ExAllocatePool(NonPagedPool, sizeof(KSOBJECT_CREATE_ITEM));
- if (!CreateItem)
- return STATUS_INSUFFICIENT_RESOURCES;
-
- Context = ExAllocatePool(NonPagedPool, sizeof(DISPATCH_CONTEXT));
- if (!Context)
- {
- ExFreePool(CreateItem);
- return STATUS_INSUFFICIENT_RESOURCES;
- }
-
- Context->Handle = Handle;
- Context->FileObject = FileObject;
-
-
- CreateItem->Context = (PVOID)Context;
/* allocate object header */
- Status = KsAllocateObjectHeader(&ObjectHeader, 1, CreateItem, Irp,
&PinTable);
+ Status = KsAllocateObjectHeader(&ObjectHeader, 0, NULL, Irp, &PinTable);
return Status;
}
Modified: trunk/reactos/drivers/wdm/audio/sysaudio/sysaudio.h
URL:
http://svn.reactos.org/svn/reactos/trunk/reactos/drivers/wdm/audio/sysaudio…
==============================================================================
--- trunk/reactos/drivers/wdm/audio/sysaudio/sysaudio.h [iso-8859-1] (original)
+++ trunk/reactos/drivers/wdm/audio/sysaudio/sysaudio.h [iso-8859-1] Sun Feb 22 21:58:51
2009
@@ -5,8 +5,15 @@
{
ULONG NumDevices;
PULONG Devices;
+ PHANDLE Handels;
}SYSAUDIO_CLIENT, *PSYSAUDIO_CLIENT;
+
+typedef struct
+{
+ HANDLE PinHandle;
+ ULONG References;
+}PIN_INFO;
typedef struct
@@ -18,7 +25,7 @@
ULONG NumberOfClients;
ULONG NumberOfPins;
- HANDLE * Pins;
+ PIN_INFO * Pins;
}KSAUDIO_DEVICE_ENTRY, *PKSAUDIO_DEVICE_ENTRY;
@@ -38,17 +45,22 @@
typedef struct
{
- PIRP Irp;
- PKSAUDIO_DEVICE_ENTRY Entry;
- KSPIN_CONNECT * PinConnect;
+ HANDLE Handle;
+ PFILE_OBJECT FileObject;
+ ULONG PinId;
+ PKSAUDIO_DEVICE_ENTRY AudioEntry;
-}PIN_WORKER_CONTEXT, *PPIN_WORKER_CONTEXT;
+}DISPATCH_CONTEXT, *PDISPATCH_CONTEXT;
typedef struct
{
- HANDLE Handle;
- PFILE_OBJECT FileObject;
-}DISPATCH_CONTEXT, *PDISPATCH_CONTEXT;
+ PIRP Irp;
+ BOOL CreateRealPin;
+ PKSAUDIO_DEVICE_ENTRY Entry;
+ KSPIN_CONNECT * PinConnect;
+ PDISPATCH_CONTEXT DispatchContext;
+ PSYSAUDIO_CLIENT AudioClient;
+}PIN_WORKER_CONTEXT, *PPIN_WORKER_CONTEXT;
NTSTATUS
SysAudioAllocateDeviceHeader(
@@ -75,8 +87,6 @@
NTSTATUS
CreateDispatcher(
- IN PIRP Irp,
- IN HANDLE Handle,
- IN PFILE_OBJECT FileObject);
+ IN PIRP Irp);
#endif