[KS]
authorJohannes Anderwald <johannes.anderwald@reactos.org>
Thu, 1 Apr 2010 17:22:21 +0000 (17:22 +0000)
committerJohannes Anderwald <johannes.anderwald@reactos.org>
Thu, 1 Apr 2010 17:22:21 +0000 (17:22 +0000)
- Partly implement pin property handling by using supplied pin descriptor properties
- Dynamically allocate connection format and put in pin's object bag
- Remove bogus assert as pins don't have to provide a PinDispatchCreate function
- Tuner device filter and capture device filter now successfully connect and instantiate corresponding input / output pins

svn path=/trunk/; revision=46643

reactos/drivers/ksfilter/ks/filter.c
reactos/drivers/ksfilter/ks/pin.c

index 773302b..5d06ca2 100644 (file)
@@ -746,8 +746,11 @@ IKsFilter_DispatchDeviceIoControl(
         }
     }
 
-    Irp->IoStatus.Status = Status;
-    IoCompleteRequest(Irp, IO_NO_INCREMENT);
+    if (Status != STATUS_PENDING)
+    {
+        Irp->IoStatus.Status = Status;
+        IoCompleteRequest(Irp, IO_NO_INCREMENT);
+    }
 
     /* done */
     return Status;
index a133882..5d1ee77 100644 (file)
@@ -905,6 +905,69 @@ KsStreamPointerGetNextClone(
     return &Pointer->Next->StreamPointer;
 }
 
+NTSTATUS
+IKsPin_DispatchKsProperty(
+    PDEVICE_OBJECT DeviceObject,
+    PIRP Irp,
+    IKsPinImpl * This)
+{
+    NTSTATUS Status;
+    PKSPROPERTY Property;
+    PIO_STACK_LOCATION IoStack;
+    UNICODE_STRING GuidString;
+    ULONG PropertySetsCount = 0, PropertyItemSize = 0;
+    const KSPROPERTY_SET* PropertySets = NULL;
+
+    /* sanity check */
+    ASSERT(This->Pin.Descriptor);
+
+    /* get current irp stack */
+    IoStack = IoGetCurrentIrpStackLocation(Irp);
+
+
+    if (This->Pin.Descriptor->AutomationTable)
+    {
+        /* use available driver property sets */
+        PropertySetsCount = This->Pin.Descriptor->AutomationTable->PropertySetsCount;
+        PropertySets = This->Pin.Descriptor->AutomationTable->PropertySets;
+        PropertyItemSize = This->Pin.Descriptor->AutomationTable->PropertyItemSize;
+    }
+
+
+    /* try driver provided property sets */
+    Status = KspPropertyHandler(Irp,
+                                PropertySetsCount,
+                                PropertySets,
+                                NULL,
+                                PropertyItemSize);
+
+    DPRINT("IKsPin_DispatchKsProperty PropertySetCount %lu Status %lu\n", PropertySetsCount, Status);
+
+    if (Status != STATUS_NOT_FOUND)
+    {
+        /* property was handled by driver */
+        if (Status != STATUS_PENDING)
+        {
+            Irp->IoStatus.Status = Status;
+            IoCompleteRequest(Irp, IO_NO_INCREMENT);
+        }
+        return Status;
+    }
+
+    /* property was not handled */
+    Property = (PKSPROPERTY)IoStack->Parameters.DeviceIoControl.Type3InputBuffer;
+
+    RtlStringFromGUID(&Property->Set, &GuidString);
+    DPRINT("IKsPin_DispatchKsProperty Unhandled property Set |%S| Id %u Flags %x\n", GuidString.Buffer, Property->Id, Property->Flags);
+    RtlFreeUnicodeString(&GuidString);
+
+    Irp->IoStatus.Status = STATUS_NOT_FOUND;
+    IoCompleteRequest(Irp, IO_NO_INCREMENT);
+
+    return STATUS_NOT_FOUND;
+
+}
+
 NTSTATUS
 NTAPI
 IKsPin_DispatchDeviceIoControl(
@@ -926,10 +989,17 @@ IKsPin_DispatchDeviceIoControl(
     /* get the object header */
     ObjectHeader = (PKSIOBJECT_HEADER)IoStack->FileObject->FsContext2;
 
-    /* locate ks pin implemention fro KSPIN offset */
+    /* locate ks pin implemention from KSPIN offset */
     This = (IKsPinImpl*)CONTAINING_RECORD(ObjectHeader->ObjectType, IKsPinImpl, Pin);
 
-    if (IoStack->Parameters.DeviceIoControl.IoControlCode != IOCTL_KS_WRITE_STREAM && IoStack->Parameters.DeviceIoControl.IoControlCode == IOCTL_KS_READ_STREAM)
+    if (IoStack->Parameters.DeviceIoControl.IoControlCode == IOCTL_KS_PROPERTY)
+    {
+        /* handle ks properties */
+        return IKsPin_DispatchKsProperty(DeviceObject, Irp, This);
+    }
+
+
+    if (IoStack->Parameters.DeviceIoControl.IoControlCode != IOCTL_KS_WRITE_STREAM && IoStack->Parameters.DeviceIoControl.IoControlCode != IOCTL_KS_READ_STREAM)
     {
         UNIMPLEMENTED;
         Irp->IoStatus.Status = STATUS_NOT_IMPLEMENTED;
@@ -1084,10 +1154,10 @@ KspCreatePin(
     PDEVICE_EXTENSION DeviceExtension;
     PKSOBJECT_CREATE_ITEM CreateItem;
     NTSTATUS Status;
+    PKSDATAFORMAT DataFormat;
 
     /* sanity checks */
     ASSERT(Descriptor->Dispatch);
-    ASSERT(Descriptor->Dispatch->Create);
 
     DPRINT("KspCreatePin\n");
 
@@ -1134,9 +1204,6 @@ KspCreatePin(
     InitializeListHead(&This->IrpList);
     KeInitializeSpinLock(&This->IrpListLock);
 
-    /* initialize ks pin descriptor */
-    This->Pin.Descriptor = Descriptor;
-    This->Pin.Id = Connect->PinId;
 
     /* allocate object bag */
     This->Pin.Bag = AllocateItem(NonPagedPool, sizeof(KSIOBJECT_BAG));
@@ -1151,12 +1218,33 @@ KspCreatePin(
     /* initialize object bag */
     Device->lpVtbl->InitializeObjectBag(Device, This->Pin.Bag, &This->BasicHeader.ControlMutex); /* is using control mutex right? */
 
+    /* get format */
+    DataFormat = (PKSDATAFORMAT)(Connect + 1);
+
+    /* initialize ks pin descriptor */
+    This->Pin.Descriptor = Descriptor;
+    This->Pin.Context = NULL;
+    This->Pin.Id = Connect->PinId;
     This->Pin.Communication = Descriptor->PinDescriptor.Communication;
-    This->Pin.ConnectionIsExternal = FALSE; /* FIXME */
-    //FIXME This->Pin.ConnectionInterface = Descriptor->PinDescriptor.Interfaces;
-    //FIXME This->Pin.ConnectionMedium = Descriptor->PinDescriptor.Mediums;
-    //FIXME This->Pin.ConnectionPriority = KSPRIORITY_NORMAL;
-    This->Pin.ConnectionFormat = (PKSDATAFORMAT) (Connect + 1);
+    This->Pin.ConnectionIsExternal = FALSE; //FIXME
+    RtlMoveMemory(&This->Pin.ConnectionInterface, &Connect->Interface, sizeof(KSPIN_INTERFACE));
+    RtlMoveMemory(&This->Pin.ConnectionMedium, &Connect->Medium, sizeof(KSPIN_MEDIUM));
+    RtlMoveMemory(&This->Pin.ConnectionPriority, &Connect->Priority, sizeof(KSPRIORITY));
+
+    /* allocate format */
+    Status = _KsEdit(This->Pin.Bag, (PVOID*)&This->Pin.ConnectionFormat, DataFormat->FormatSize, DataFormat->FormatSize, 0);
+    if (!NT_SUCCESS(Status))
+    {
+        /* failed to allocate format */
+        KsFreeObjectBag((KSOBJECT_BAG)This->Pin.Bag);
+        FreeItem(This);
+        FreeItem(CreateItem);
+        return STATUS_INSUFFICIENT_RESOURCES;
+    }
+
+    /* copy format */
+    RtlMoveMemory((PVOID)This->Pin.ConnectionFormat, DataFormat, DataFormat->FormatSize);
+
     This->Pin.AttributeList = NULL; //FIXME
     This->Pin.StreamHeaderSize = sizeof(KSSTREAM_HEADER);
     This->Pin.DataFlow = Descriptor->PinDescriptor.DataFlow;