- Fix tons of bugs in KsMergeAutomationTable
- Implement removing instantiated filter from filter factory when filter is about to be closed
- Fix a memory corrupion bug in KspHandleDataIntersection

svn path=/trunk/; revision=46780
This commit is contained in:
Johannes Anderwald 2010-04-08 20:14:38 +00:00
parent 169a95782a
commit 0d672ad7cd
2 changed files with 118 additions and 23 deletions

View file

@ -2096,8 +2096,15 @@ KspCountMethodSets(
if (!AutomationTableB)
return AutomationTableA->MethodSetsCount;
DPRINT("AutomationTableA MethodItemSize %lu MethodSetsCount %lu\n", AutomationTableA->MethodItemSize, AutomationTableA->MethodSetsCount);
DPRINT("AutomationTableB MethodItemSize %lu MethodSetsCount %lu\n", AutomationTableB->MethodItemSize, AutomationTableB->MethodSetsCount);
if (AutomationTableA->MethodItemSize && AutomationTableB->MethodItemSize)
{
/* sanity check */
ASSERT(AutomationTableA->MethodItemSize == AutomationTableB->MethodItemSize);
}
/* now iterate all property sets and compare their guids */
Count = AutomationTableA->MethodSetsCount;
@ -2138,8 +2145,14 @@ KspCountEventSets(
if (!AutomationTableB)
return AutomationTableA->EventSetsCount;
DPRINT("AutomationTableA EventItemSize %lu EventSetsCount %lu\n", AutomationTableA->EventItemSize, AutomationTableA->EventSetsCount);
DPRINT("AutomationTableB EventItemSize %lu EventSetsCount %lu\n", AutomationTableB->EventItemSize, AutomationTableB->EventSetsCount);
if (AutomationTableA->EventItemSize && AutomationTableB->EventItemSize)
{
/* sanity check */
ASSERT(AutomationTableA->EventItemSize == AutomationTableB->EventItemSize);
}
/* now iterate all Event sets and compare their guids */
Count = AutomationTableA->EventSetsCount;
@ -2182,6 +2195,8 @@ KspCountPropertySets(
return AutomationTableA->PropertySetsCount;
/* sanity check */
DPRINT("AutomationTableA EventItemSize %lu PropertySetsCount %lu\n", AutomationTableA->PropertyItemSize, AutomationTableA->PropertySetsCount);
DPRINT("AutomationTableB EventItemSize %lu PropertySetsCount %lu\n", AutomationTableB->PropertyItemSize, AutomationTableB->PropertySetsCount);
ASSERT(AutomationTableA->PropertyItemSize == AutomationTableB->PropertyItemSize);
/* now iterate all property sets and compare their guids */
@ -2221,18 +2236,18 @@ KspCopyMethodSets(
if (!AutomationTableA)
{
/* copy of property set */
RtlMoveMemory((PVOID)Table->MethodSets, AutomationTableB->MethodSets, Table->MethodItemSize * AutomationTableB->MethodSetsCount);
RtlMoveMemory((PVOID)Table->MethodSets, AutomationTableB->MethodSets, sizeof(KSMETHOD_SET) * AutomationTableB->MethodSetsCount);
return STATUS_SUCCESS;
}
else if (!AutomationTableB)
{
/* copy of property set */
RtlMoveMemory((PVOID)Table->MethodSets, AutomationTableA->MethodSets, Table->MethodItemSize * AutomationTableA->MethodSetsCount);
RtlMoveMemory((PVOID)Table->MethodSets, AutomationTableA->MethodSets, sizeof(KSMETHOD_SET) * AutomationTableA->MethodSetsCount);
return STATUS_SUCCESS;
}
/* first copy all property items from dominant table */
RtlMoveMemory((PVOID)Table->MethodSets, AutomationTableA->MethodSets, Table->MethodItemSize * AutomationTableA->MethodSetsCount);
RtlMoveMemory((PVOID)Table->MethodSets, AutomationTableA->MethodSets, sizeof(KSMETHOD_SET) * AutomationTableA->MethodSetsCount);
/* set counter */
Count = AutomationTableA->MethodSetsCount;
@ -2255,7 +2270,7 @@ KspCopyMethodSets(
if (!bFound)
{
/* copy new property item set */
RtlMoveMemory((PVOID)&Table->MethodSets[Count], &AutomationTableB->MethodSets[Index], Table->MethodItemSize);
RtlMoveMemory((PVOID)&Table->MethodSets[Count], &AutomationTableB->MethodSets[Index], sizeof(KSMETHOD_SET));
Count++;
}
}
@ -2276,18 +2291,18 @@ KspCopyPropertySets(
if (!AutomationTableA)
{
/* copy of property set */
RtlMoveMemory((PVOID)Table->PropertySets, AutomationTableB->PropertySets, Table->PropertyItemSize * AutomationTableB->PropertySetsCount);
RtlMoveMemory((PVOID)Table->PropertySets, AutomationTableB->PropertySets, sizeof(KSPROPERTY_SET) * AutomationTableB->PropertySetsCount);
return STATUS_SUCCESS;
}
else if (!AutomationTableB)
{
/* copy of property set */
RtlMoveMemory((PVOID)Table->PropertySets, AutomationTableA->PropertySets, Table->PropertyItemSize * AutomationTableA->PropertySetsCount);
RtlMoveMemory((PVOID)Table->PropertySets, AutomationTableA->PropertySets, sizeof(KSPROPERTY_SET) * AutomationTableA->PropertySetsCount);
return STATUS_SUCCESS;
}
/* first copy all property items from dominant table */
RtlMoveMemory((PVOID)Table->PropertySets, AutomationTableA->PropertySets, Table->PropertyItemSize * AutomationTableA->PropertySetsCount);
RtlMoveMemory((PVOID)Table->PropertySets, AutomationTableA->PropertySets, sizeof(KSPROPERTY_SET) * AutomationTableA->PropertySetsCount);
/* set counter */
Count = AutomationTableA->PropertySetsCount;
@ -2310,7 +2325,7 @@ KspCopyPropertySets(
if (!bFound)
{
/* copy new property item set */
RtlMoveMemory((PVOID)&Table->PropertySets[Count], &AutomationTableB->PropertySets[Index], Table->PropertyItemSize);
RtlMoveMemory((PVOID)&Table->PropertySets[Count], &AutomationTableB->PropertySets[Index], sizeof(KSPROPERTY_SET));
Count++;
}
}
@ -2330,18 +2345,18 @@ KspCopyEventSets(
if (!AutomationTableA)
{
/* copy of Event set */
RtlMoveMemory((PVOID)Table->EventSets, AutomationTableB->EventSets, Table->EventItemSize * AutomationTableB->EventSetsCount);
RtlMoveMemory((PVOID)Table->EventSets, AutomationTableB->EventSets, sizeof(KSEVENT_SET) * AutomationTableB->EventSetsCount);
return STATUS_SUCCESS;
}
else if (!AutomationTableB)
{
/* copy of Event set */
RtlMoveMemory((PVOID)Table->EventSets, AutomationTableA->EventSets, Table->EventItemSize * AutomationTableA->EventSetsCount);
RtlMoveMemory((PVOID)Table->EventSets, AutomationTableA->EventSets, sizeof(KSEVENT_SET) * AutomationTableA->EventSetsCount);
return STATUS_SUCCESS;
}
/* first copy all Event items from dominant table */
RtlMoveMemory((PVOID)Table->EventSets, AutomationTableA->EventSets, Table->EventItemSize * AutomationTableA->EventSetsCount);
RtlMoveMemory((PVOID)Table->EventSets, AutomationTableA->EventSets, sizeof(KSEVENT_SET) * AutomationTableA->EventSetsCount);
/* set counter */
Count = AutomationTableA->EventSetsCount;
@ -2364,7 +2379,7 @@ KspCopyEventSets(
if (!bFound)
{
/* copy new Event item set */
RtlMoveMemory((PVOID)&Table->EventSets[Count], &AutomationTableB->EventSets[Index], Table->EventItemSize);
RtlMoveMemory((PVOID)&Table->EventSets[Count], &AutomationTableB->EventSets[Index], sizeof(KSEVENT_SET));
Count++;
}
}
@ -2428,7 +2443,7 @@ KsMergeAutomationTables(
}
/* now allocate the property sets */
Table->PropertySets = AllocateItem(NonPagedPool, Table->PropertyItemSize * Table->PropertySetsCount);
Table->PropertySets = AllocateItem(NonPagedPool, sizeof(KSPROPERTY_SET) * Table->PropertySetsCount);
if (!Table->PropertySets)
{
@ -2471,7 +2486,7 @@ KsMergeAutomationTables(
}
/* now allocate the property sets */
Table->MethodSets = AllocateItem(NonPagedPool, Table->MethodItemSize * Table->MethodSetsCount);
Table->MethodSets = AllocateItem(NonPagedPool, sizeof(KSMETHOD_SET) * Table->MethodSetsCount);
if (!Table->MethodSets)
{
@ -2514,7 +2529,7 @@ KsMergeAutomationTables(
}
/* now allocate the property sets */
Table->EventSets = AllocateItem(NonPagedPool, Table->EventItemSize * Table->EventSetsCount);
Table->EventSets = AllocateItem(NonPagedPool, sizeof(KSEVENT_SET) * Table->EventSetsCount);
if (!Table->EventSets)
{

View file

@ -44,6 +44,11 @@ const GUID IID_IKsFilter = {0x3ef6ee44L, 0x0D41, 0x11d2, {0xbe, 0xDA, 0x00, 0xc
const GUID KSPROPSETID_Topology = {0x720D4AC0L, 0x7533, 0x11D0, {0xA5, 0xD6, 0x28, 0xDB, 0x04, 0xC1, 0x00, 0x00}};
const GUID KSPROPSETID_Pin = {0x8C134960L, 0x51AD, 0x11CF, {0x87, 0x8A, 0x94, 0xF8, 0x01, 0xC1, 0x00, 0x00}};
VOID
IKsFilter_RemoveFilterFromFilterFactory(
IKsFilterImpl * This,
PKSFILTERFACTORY FilterFactory);
DEFINE_KSPROPERTY_TOPOLOGYSET(IKsFilterTopologySet, KspTopologyPropertyHandler);
DEFINE_KSPROPERTY_PINPROPOSEDATAFORMAT(IKsFilterPinSet, KspPinPropertyHandler, KspPinPropertyHandler, KspPinPropertyHandler);
@ -506,8 +511,8 @@ IKsFilter_DispatchClose(
/* complete irp */
IoCompleteRequest(Irp, IO_NO_INCREMENT);
/* FIXME remove our instance from the filter factory */
ASSERT(0);
/* remove our instance from the filter factory */
IKsFilter_RemoveFilterFromFilterFactory(This, This->Factory);
/* free object header */
KsFreeObjectHeader(This->ObjectHeader);
@ -605,6 +610,9 @@ KspHandleDataIntersection(
MultipleItem = (PKSMULTIPLE_ITEM)(Pin + 1);
DataRange = (PKSDATARANGE)(MultipleItem + 1);
/* FIXME make sure its 64 bit aligned */
ASSERT(((ULONG_PTR)DataRange & 0x3F) == 0);
if (!This->Factory->FilterDescriptor || !This->PinDescriptorCount)
{
/* no filter / pin descriptor */
@ -632,7 +640,7 @@ KspHandleDataIntersection(
Irp,
Pin,
DataRange,
(PKSDATAFORMAT)This->Factory->FilterDescriptor->PinDescriptors[Pin->PinId].PinDescriptor.DataRanges,
(PKSDATAFORMAT)This->PinDescriptorsEx[Pin->PinId].PinDescriptor.DataRanges,
DataLength,
Data,
&Length);
@ -643,6 +651,8 @@ KspHandleDataIntersection(
break;
}
DataRange = UlongToPtr(PtrToUlong(DataRange) + DataRange->FormatSize);
/* FIXME make sure its 64 bit aligned */
ASSERT(((ULONG_PTR)DataRange & 0x3F) == 0);
}
IoStatus->Status = Status;
@ -718,6 +728,8 @@ IKsFilter_DispatchDeviceIoControl(
IKsFilterImpl * This;
NTSTATUS Status;
PKSFILTER FilterInstance;
UNICODE_STRING GuidString;
PKSPROPERTY Property;
/* obtain filter from object header */
Status = IKsFilter_GetFilterFromIrp(Irp, &Filter);
@ -730,6 +742,14 @@ IKsFilter_DispatchDeviceIoControl(
/* current irp stack */
IoStack = IoGetCurrentIrpStackLocation(Irp);
/* property was not handled */
Property = (PKSPROPERTY)IoStack->Parameters.DeviceIoControl.Type3InputBuffer;
RtlStringFromGUID(&Property->Set, &GuidString);
DPRINT("IKsFilter_DispatchDeviceIoControl property Set |%S| Id %u Flags %x\n", GuidString.Buffer, Property->Id, Property->Flags);
RtlFreeUnicodeString(&GuidString);
if (IoStack->Parameters.DeviceIoControl.IoControlCode != IOCTL_KS_PROPERTY)
{
UNIMPLEMENTED;
@ -1126,12 +1146,72 @@ IKsFilter_AttachFilterToFilterFactory(
/* found last entry */
break;
}
}while(FilterFactory);
}while(TRUE);
/* attach filter factory */
BasicHeader->Next.Filter = &This->Filter;
}
VOID
IKsFilter_RemoveFilterFromFilterFactory(
IKsFilterImpl * This,
PKSFILTERFACTORY FilterFactory)
{
PKSBASIC_HEADER BasicHeader;
PKSFILTER Filter, LastFilter;
/* get filter factory basic header */
BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)FilterFactory - sizeof(KSBASIC_HEADER));
/* sanity check */
ASSERT(BasicHeader->Type == KsObjectTypeFilterFactory);
ASSERT(BasicHeader->FirstChild.Filter != NULL);
/* set to first entry */
Filter = BasicHeader->FirstChild.Filter;
LastFilter = NULL;
do
{
if (Filter == &This->Filter)
{
if (LastFilter)
{
/* get basic header */
BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)LastFilter - sizeof(KSBASIC_HEADER));
/* remove filter instance */
BasicHeader->Next.Filter = This->Header.Next.Filter;
break;
}
else
{
/* remove filter instance */
BasicHeader->FirstChild.Filter = This->Header.Next.Filter;
break;
}
}
/* get basic header */
BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)Filter - sizeof(KSBASIC_HEADER));
/* sanity check */
ASSERT(BasicHeader->Type == KsObjectTypeFilter);
LastFilter = Filter;
if (BasicHeader->Next.Filter)
{
/* iterate to next filter factory */
Filter = BasicHeader->Next.Filter;
}
else
{
/* filter is not in list */
ASSERT(0);
break;
}
}while(TRUE);
}
NTSTATUS
NTAPI
KspCreateFilter(