ReactOS  0.4.13-dev-66-gc714b7f
filter.c
Go to the documentation of this file.
1 /*
2  * COPYRIGHT: See COPYING in the top level directory
3  * PROJECT: ReactOS Kernel Streaming
4  * FILE: drivers/ksfilter/ks/filter.c
5  * PURPOSE: KS IKsFilter interface functions
6  * PROGRAMMER: Johannes Anderwald
7  */
8 
9 #include "precomp.h"
10 
11 #define NDEBUG
12 #include <debug.h>
13 
14 typedef struct
15 {
17  KSFILTER Filter;
18 
19  IKsControlVtbl *lpVtblKsControl;
20  IKsFilterFactory * FilterFactory;
21  IKsProcessingObjectVtbl * lpVtblKsProcessingObject;
23 
26  PKSFILTERFACTORY Factory;
30 
31  PKSWORKER Worker;
33  KSGATE Gate;
34 
35  PFNKSFILTERPOWER Sleep;
36  PFNKSFILTERPOWER Wake;
37 
39  PKSPIN * FirstPin;
41 
43 
44 const GUID IID_IKsControl = {0x28F54685L, 0x06FD, 0x11D2, {0xB2, 0x7A, 0x00, 0xA0, 0xC9, 0x22, 0x31, 0x96}};
45 const GUID IID_IKsFilter = {0x3ef6ee44L, 0x0D41, 0x11d2, {0xbe, 0xDA, 0x00, 0xc0, 0x4f, 0x8e, 0xF4, 0x57}};
46 const GUID KSPROPSETID_Topology = {0x720D4AC0L, 0x7533, 0x11D0, {0xA5, 0xD6, 0x28, 0xDB, 0x04, 0xC1, 0x00, 0x00}};
47 const GUID KSPROPSETID_Pin = {0x8C134960L, 0x51AD, 0x11CF, {0x87, 0x8A, 0x94, 0xF8, 0x01, 0xC1, 0x00, 0x00}};
48 const GUID KSPROPSETID_General = {0x1464EDA5L, 0x6A8F, 0x11D1, {0x9A, 0xA7, 0x00, 0xA0, 0xC9, 0x22, 0x31, 0x96}};
49 
50 VOID
53  PKSFILTERFACTORY FilterFactory);
54 
58 
62 
63 KSPROPERTY_SET FilterPropertySet[] =
64 {
65  {
67  sizeof(IKsFilterTopologySet) / sizeof(KSPROPERTY_ITEM),
68  (const KSPROPERTY_ITEM*)&IKsFilterTopologySet,
69  0,
70  NULL
71  },
72  {
74  sizeof(IKsFilterPinSet) / sizeof(KSPROPERTY_ITEM),
75  (const KSPROPERTY_ITEM*)&IKsFilterPinSet,
76  0,
77  NULL
78  },
79  {
81  sizeof(IKsFilterGeneralSet) / sizeof(KSPROPERTY_ITEM),
82  (const KSPROPERTY_ITEM*)&IKsFilterGeneralSet,
83  0,
84  NULL
85  }
86 };
87 
89 NTAPI
91  IKsProcessingObject * iface,
92  IN REFIID refiid,
93  OUT PVOID* Output)
94 {
95  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsProcessingObject);
96 
97  if (IsEqualGUIDAligned(refiid, &IID_IUnknown))
98  {
99  *Output = &This->Header.OuterUnknown;
101  return STATUS_SUCCESS;
102  }
103  return STATUS_UNSUCCESSFUL;
104 }
105 
106 ULONG
107 NTAPI
109  IKsProcessingObject * iface)
110 {
111  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsProcessingObject);
112 
113  return InterlockedIncrement(&This->ref);
114 }
115 
116 ULONG
117 NTAPI
119  IKsProcessingObject * iface)
120 {
121  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsProcessingObject);
122 
123  InterlockedDecrement(&This->ref);
124 
125  /* Return new reference count */
126  return This->ref;
127 }
128 
129 VOID
130 NTAPI
132  IKsProcessingObject * iface)
133 {
135  LARGE_INTEGER TimeOut;
136  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsProcessingObject);
137 
138  DPRINT1("processing object\n");
139  /* first check if running at passive level */
141  {
142  /* acquire processing mutex */
144  }
145  else
146  {
147  /* dispatch level processing */
148  if (KeReadStateMutex(&This->ControlMutex) == 0)
149  {
150  /* some thread was faster */
151  DPRINT1("processing object too slow\n");
152  return;
153  }
154 
155  /* acquire processing mutex */
156  TimeOut.QuadPart = 0LL;
157  Status = KeWaitForSingleObject(&This->ControlMutex, Executive, KernelMode, FALSE, &TimeOut);
158 
159  if (Status == STATUS_TIMEOUT)
160  {
161  /* some thread was faster */
162  DPRINT1("processing object too slow\n");
163  return;
164  }
165  }
166 
167  do
168  {
169 
170  /* check if the and-gate has been enabled again */
171  if (&This->Gate.Count != 0)
172  {
173  /* gate is open */
174  DPRINT1("processing object gate open\n");
175  break;
176  }
177 
178  DPRINT1("IKsProcessingObject_fnProcessingObjectWork not implemented\n");
179  ASSERT(0);
180 
181  }while(TRUE);
182 
183  /* release process mutex */
184  KeReleaseMutex(&This->ProcessingMutex, FALSE);
185 }
186 
187 PKSGATE
188 NTAPI
190  IKsProcessingObject * iface)
191 {
192  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsProcessingObject);
193 
194  /* return and gate */
195  return &This->Gate;
196 }
197 
198 VOID
199 NTAPI
201  IKsProcessingObject * iface,
203 {
204  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsProcessingObject);
205 
206  /* should the action be asynchronous */
207  if (Asynchronous)
208  {
209  /* queue work item */
210  KsQueueWorkItem(This->Worker, &This->WorkItem);
211 DPRINT1("queueing\n");
212  /* done */
213  return;
214  }
215 
216  /* does the filter require explicit deferred processing */
217  if ((This->Filter.Descriptor->Flags & (KSFILTER_FLAG_DISPATCH_LEVEL_PROCESSING | KSFILTER_FLAG_CRITICAL_PROCESSING | KSFILTER_FLAG_HYPERCRITICAL_PROCESSING)) &&
219  {
220  /* queue work item */
221  KsQueueWorkItem(This->Worker, &This->WorkItem);
222 DPRINT1("queueing\n");
223  /* done */
224  return;
225  }
226 DPRINT1("invoke\n");
227  /* call worker routine directly */
228  iface->lpVtbl->ProcessingObjectWork(iface);
229 }
230 
231 VOID
232 NTAPI
234  IKsProcessingObject * iface)
235 {
236  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsProcessingObject);
237 
238  /* acquire processing mutex */
239  KeWaitForSingleObject(&This->ProcessingMutex, Executive, KernelMode, FALSE, NULL);
240 
241  /* check if the filter supports dispatch routines */
242  if (This->Filter.Descriptor->Dispatch)
243  {
244  /* has the filter a reset routine */
245  if (This->Filter.Descriptor->Dispatch->Reset)
246  {
247  /* reset filter */
248  This->Filter.Descriptor->Dispatch->Reset(&This->Filter);
249  }
250  }
251 
252  /* release process mutex */
253  KeReleaseMutex(&This->ProcessingMutex, FALSE);
254 }
255 
256 VOID
257 NTAPI
259  IKsProcessingObject * iface)
260 {
261 
262 }
263 
264 static IKsProcessingObjectVtbl vt_IKsProcessingObject =
265 {
274 };
275 
276 
277 //---------------------------------------------------------------------------------------------------------
278 NTSTATUS
279 NTAPI
281  IKsControl * iface,
282  IN REFIID refiid,
283  OUT PVOID* Output)
284 {
285  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsControl);
286 
287  if (IsEqualGUIDAligned(refiid, &IID_IUnknown))
288  {
289  *Output = &This->Header.OuterUnknown;
291  return STATUS_SUCCESS;
292  }
293  return STATUS_UNSUCCESSFUL;
294 }
295 
296 ULONG
297 NTAPI
299  IKsControl * iface)
300 {
301  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsControl);
302 
303  return InterlockedIncrement(&This->ref);
304 }
305 
306 ULONG
307 NTAPI
309  IKsControl * iface)
310 {
311  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsControl);
312 
313  InterlockedDecrement(&This->ref);
314 
315  /* Return new reference count */
316  return This->ref;
317 }
318 
319 NTSTATUS
320 NTAPI
322  IKsControl * iface,
324  IN ULONG PropertyLength,
325  IN OUT PVOID PropertyData,
328 {
329  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsControl);
330 
331  return KsSynchronousIoControlDevice(This->FileObject, KernelMode, IOCTL_KS_PROPERTY, Property, PropertyLength, PropertyData, DataLength, BytesReturned);
332 }
333 
334 
335 NTSTATUS
336 NTAPI
338  IKsControl * iface,
339  IN PKSMETHOD Method,
340  IN ULONG MethodLength,
341  IN OUT PVOID MethodData,
344 {
345  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsControl);
346 
347  return KsSynchronousIoControlDevice(This->FileObject, KernelMode, IOCTL_KS_METHOD, Method, MethodLength, MethodData, DataLength, BytesReturned);
348 }
349 
350 
351 NTSTATUS
352 NTAPI
354  IKsControl * iface,
356  IN ULONG EventLength,
357  IN OUT PVOID EventData,
360 {
361  IKsFilterImpl * This = (IKsFilterImpl*)CONTAINING_RECORD(iface, IKsFilterImpl, lpVtblKsControl);
362 
363  if (Event)
364  {
365  return KsSynchronousIoControlDevice(This->FileObject, KernelMode, IOCTL_KS_ENABLE_EVENT, Event, EventLength, EventData, DataLength, BytesReturned);
366  }
367  else
368  {
370  }
371 
372 }
373 
374 static IKsControlVtbl vt_IKsControl =
375 {
382 };
383 
384 
385 NTSTATUS
386 NTAPI
388  IKsFilter * iface,
389  IN REFIID refiid,
390  OUT PVOID* Output)
391 {
394 
395  if (IsEqualGUIDAligned(refiid, &IID_IUnknown) ||
397  {
398  *Output = &This->Header.OuterUnknown;
400  return STATUS_SUCCESS;
401  }
402  else if (IsEqualGUIDAligned(refiid, &IID_IKsControl))
403  {
404  *Output = &This->lpVtblKsControl;
406  return STATUS_SUCCESS;
407  }
408 
409  if (This->Header.ClientAggregate)
410  {
411  /* using client aggregate */
412  Status = This->Header.ClientAggregate->lpVtbl->QueryInterface(This->Header.ClientAggregate, refiid, Output);
413 
414  if (NT_SUCCESS(Status))
415  {
416  /* client aggregate supports interface */
417  return Status;
418  }
419  }
420 
421  DPRINT("IKsFilter_fnQueryInterface no interface\n");
422  return STATUS_NOT_SUPPORTED;
423 }
424 
425 ULONG
426 NTAPI
428  IKsFilter * iface)
429 {
431 
432  return InterlockedIncrement(&This->ref);
433 }
434 
435 ULONG
436 NTAPI
438  IKsFilter * iface)
439 {
441 
442  InterlockedDecrement(&This->ref);
443 
444  if (This->ref == 0)
445  {
446  FreeItem(This);
447  return 0;
448  }
449  /* Return new reference count */
450  return This->ref;
451 
452 }
453 
454 PKSFILTER
455 NTAPI
457  IKsFilter * iface)
458 {
460 
461  return &This->Filter;
462 }
463 
464 BOOL
465 NTAPI
467  IKsFilter * iface)
468 {
470  return FALSE;
471 }
472 
473 NTSTATUS
474 NTAPI
476  IKsFilter * iface,
477  IN PIRP Irp,
478  IN IKsPin * Pin,
479  IN PLIST_ENTRY ListEntry)
480 {
482  return STATUS_NOT_IMPLEMENTED;
483 }
484 
485 NTSTATUS
486 NTAPI
488  IKsFilter * iface,
489  IN struct KSPROCESSPIPESECTION *Section,
490  IN PVOID Create,
491  IN PKSPIN KsPin,
492  OUT IKsPin **Pin,
493  OUT PKSGATE *OutGate)
494 {
496  return STATUS_NOT_IMPLEMENTED;
497 }
498 
499 NTSTATUS
500 NTAPI
502  IKsFilter * iface,
503  IN struct KSPROCESSPIPESECTION *Section)
504 {
506  return STATUS_NOT_IMPLEMENTED;
507 }
508 
509 NTSTATUS
510 NTAPI
512  IKsFilter * iface,
513  IN PKSPROCESSPIN ProcessPin)
514 {
517 
518  /* first acquire processing mutex */
519  KeWaitForSingleObject(&This->ProcessingMutex, Executive, KernelMode, FALSE, NULL);
520 
521  /* sanity check */
522  ASSERT(This->Filter.Descriptor->PinDescriptorsCount > ProcessPin->Pin->Id);
523 
524  /* allocate new process pin array */
525  Status = _KsEdit(This->Filter.Bag, (PVOID*)&This->ProcessPinIndex[ProcessPin->Pin->Id].Pins,
526  (This->Filter.Descriptor->PinDescriptorsCount + 1) * sizeof(PVOID),
527  This->Filter.Descriptor->PinDescriptorsCount * sizeof(PVOID),
528  0);
529 
530  if (NT_SUCCESS(Status))
531  {
532  /* store process pin */
533  This->ProcessPinIndex[ProcessPin->Pin->Id].Pins[This->ProcessPinIndex[ProcessPin->Pin->Id].Count] = ProcessPin;
534  This->ProcessPinIndex[ProcessPin->Pin->Id].Count++;
535  }
536 
537  /* release process mutex */
538  KeReleaseMutex(&This->ProcessingMutex, FALSE);
539 
540  return Status;
541 }
542 
543 NTSTATUS
544 NTAPI
546  IKsFilter * iface,
547  IN PKSPROCESSPIN ProcessPin)
548 {
549  ULONG Index;
550  ULONG Count;
551  PKSPROCESSPIN * Pins;
552 
554 
555  /* first acquire processing mutex */
556  KeWaitForSingleObject(&This->ProcessingMutex, Executive, KernelMode, FALSE, NULL);
557 
558  /* sanity check */
559  ASSERT(ProcessPin->Pin);
560  ASSERT(ProcessPin->Pin->Id);
561 
562  Count = This->ProcessPinIndex[ProcessPin->Pin->Id].Count;
563  Pins = This->ProcessPinIndex[ProcessPin->Pin->Id].Pins;
564 
565  /* search for current process pin */
566  for(Index = 0; Index < Count; Index++)
567  {
568  if (Pins[Index] == ProcessPin)
569  {
570  RtlMoveMemory(&Pins[Index], &Pins[Index + 1], (Count - (Index + 1)) * sizeof(PVOID));
571  break;
572  }
573 
574  }
575 
576  /* decrement pin count */
577  This->ProcessPinIndex[ProcessPin->Pin->Id].Count--;
578 
579  if (!This->ProcessPinIndex[ProcessPin->Pin->Id].Count)
580  {
581  /* clear entry object bag will delete it */
582  This->ProcessPinIndex[ProcessPin->Pin->Id].Pins = NULL;
583  }
584 
585  /* release process mutex */
586  KeReleaseMutex(&This->ProcessingMutex, FALSE);
587 
588  /* done */
589  return STATUS_SUCCESS;
590 }
591 
592 BOOL
593 NTAPI
595  IKsFilter * iface,
596  IN struct KSPROCESSPIPESECTION *PipeSection,
597  IN PULONG Data)
598 {
600  return FALSE;
601 }
602 
603 VOID
604 NTAPI
606  IKsFilter * iface,
607  IN struct KSPROCESSPIPESECTION *PipeSection,
609 {
611 }
612 
613 BOOL
614 NTAPI
616  IKsFilter * iface)
617 {
619  return FALSE;
620 }
621 
622 VOID
623 NTAPI
625  IKsFilter * iface,
626  IKsQueue *Queue,
627  BOOL Register)
628 {
630 }
631 
633 NTAPI
635  IKsFilter * iface)
636 {
638 
639  return This->ProcessPinIndex;
640 }
641 
642 static IKsFilterVtbl vt_IKsFilter =
643 {
659 };
660 
661 NTSTATUS
663  IN PIRP Irp,
664  OUT IKsFilter **Filter)
665 {
666  PIO_STACK_LOCATION IoStack;
667  PKSIOBJECT_HEADER ObjectHeader;
669 
670  /* get current irp stack */
672 
673  /* sanity check */
674  ASSERT(IoStack->FileObject != NULL);
675 
676  ObjectHeader = (PKSIOBJECT_HEADER)IoStack->FileObject->FsContext2;
677 
678  /* sanity is important */
679  ASSERT(ObjectHeader != NULL);
680  ASSERT(ObjectHeader->Type == KsObjectTypeFilter);
681  ASSERT(ObjectHeader->Unknown != NULL);
682 
683  /* get our private interface */
684  Status = ObjectHeader->Unknown->lpVtbl->QueryInterface(ObjectHeader->Unknown, &IID_IKsFilter, (PVOID*)Filter);
685 
686  if (!NT_SUCCESS(Status))
687  {
688  /* something is wrong here */
689  DPRINT1("KS: Misbehaving filter %p\n", ObjectHeader->Unknown);
690  Irp->IoStatus.Status = Status;
691 
692  /* complete and forget irp */
694  return Status;
695  }
696  return Status;
697 }
698 
699 
700 NTSTATUS
701 NTAPI
704  IN PIRP Irp)
705 {
706  IKsFilter * Filter;
709 
710  /* obtain filter from object header */
712  if (!NT_SUCCESS(Status))
713  return Status;
714 
715  /* get our real implementation */
717 
718  /* does the driver support notifications */
719  if (This->Filter.Descriptor && This->Filter.Descriptor->Dispatch && This->Filter.Descriptor->Dispatch->Close)
720  {
721  /* call driver's filter close function */
722  Status = This->Filter.Descriptor->Dispatch->Close(&This->Filter, Irp);
723  }
724 
726  {
727  /* save the result */
728  Irp->IoStatus.Status = Status;
729  /* complete irp */
731 
732  /* remove our instance from the filter factory */
734 
735  /* free object header */
736  KsFreeObjectHeader(This->ObjectHeader);
737  }
738  else
739  {
740  /* complete and forget */
741  Irp->IoStatus.Status = Status;
742  /* complete irp */
744  }
745 
746  /* done */
747  return Status;
748 }
749 
750 NTSTATUS
754  IN OUT PVOID Data,
756  IN BOOL Global)
757 {
758  KSPIN_CINSTANCES * Instances;
759  KSP_PIN * Pin = (KSP_PIN*)Request;
760 
761  if (!This->Filter.Descriptor || !This->Filter.Descriptor->PinDescriptorsCount)
762  {
763  /* no filter / pin descriptor */
765  return STATUS_NOT_IMPLEMENTED;
766  }
767 
768  /* ignore custom structs for now */
769  ASSERT(This->Filter.Descriptor->PinDescriptorSize == sizeof(KSPIN_DESCRIPTOR_EX));
770  ASSERT(This->Filter.Descriptor->PinDescriptorsCount > Pin->PinId);
771 
772  Instances = (KSPIN_CINSTANCES*)Data;
773  /* max instance count */
774  Instances->PossibleCount = This->Filter.Descriptor->PinDescriptors[Pin->PinId].InstancesPossible;
775  /* current instance count */
776  Instances->CurrentCount = This->PinInstanceCount[Pin->PinId];
777 
778  IoStatus->Information = sizeof(KSPIN_CINSTANCES);
779  IoStatus->Status = STATUS_SUCCESS;
780  return STATUS_SUCCESS;
781 }
782 
783 NTSTATUS
787  IN OUT PVOID Data,
789 {
790  PULONG Result;
791  KSP_PIN * Pin = (KSP_PIN*)Request;
792 
793  if (!This->Filter.Descriptor || !This->Filter.Descriptor->PinDescriptorsCount)
794  {
795  /* no filter / pin descriptor */
797  return STATUS_NOT_IMPLEMENTED;
798  }
799 
800  /* ignore custom structs for now */
801  ASSERT(This->Filter.Descriptor->PinDescriptorSize == sizeof(KSPIN_DESCRIPTOR_EX));
802  ASSERT(This->Filter.Descriptor->PinDescriptorsCount > Pin->PinId);
803 
804  Result = (PULONG)Data;
805  *Result = This->Filter.Descriptor->PinDescriptors[Pin->PinId].InstancesNecessary;
806 
807  IoStatus->Information = sizeof(ULONG);
808  IoStatus->Status = STATUS_SUCCESS;
809  return STATUS_SUCCESS;
810 }
811 
812 NTSTATUS
814  IN PIRP Irp,
817  IN OUT PVOID Data,
820 {
821  PKSMULTIPLE_ITEM MultipleItem;
822  PKSDATARANGE DataRange;
824  ULONG Index, Length;
825  PIO_STACK_LOCATION IoStack;
826  KSP_PIN * Pin = (KSP_PIN*)Request;
827 
828  /* get stack location */
830 
831  /* sanity check */
832  ASSERT(DataLength == IoStack->Parameters.DeviceIoControl.OutputBufferLength);
833 
834  /* Access parameters */
835  MultipleItem = (PKSMULTIPLE_ITEM)(Pin + 1);
836  DataRange = (PKSDATARANGE)(MultipleItem + 1);
837 
838  /* FIXME make sure its 64 bit aligned */
839  ASSERT(((ULONG_PTR)DataRange & 0x7) == 0);
840 
841  if (!This->Filter.Descriptor || !This->Filter.Descriptor->PinDescriptorsCount)
842  {
843  /* no filter / pin descriptor */
845  return STATUS_NOT_IMPLEMENTED;
846  }
847 
848  /* ignore custom structs for now */
849  ASSERT(This->Filter.Descriptor->PinDescriptorSize == sizeof(KSPIN_DESCRIPTOR_EX));
850  ASSERT(This->Filter.Descriptor->PinDescriptorsCount > Pin->PinId);
851 
852  if (This->Filter.Descriptor->PinDescriptors[Pin->PinId].IntersectHandler == NULL ||
853  This->Filter.Descriptor->PinDescriptors[Pin->PinId].PinDescriptor.DataRanges == NULL ||
854  This->Filter.Descriptor->PinDescriptors[Pin->PinId].PinDescriptor.DataRangesCount == 0)
855  {
856  /* no driver supported intersect handler / no provided data ranges */
858  return STATUS_NOT_IMPLEMENTED;
859  }
860 
861  for(Index = 0; Index < MultipleItem->Count; Index++)
862  {
863  UNICODE_STRING MajorFormat, SubFormat, Specifier;
864  /* convert the guid to string */
865  RtlStringFromGUID(&DataRange->MajorFormat, &MajorFormat);
866  RtlStringFromGUID(&DataRange->SubFormat, &SubFormat);
867  RtlStringFromGUID(&DataRange->Specifier, &Specifier);
868 
869  DPRINT("KspHandleDataIntersection Index %lu PinId %lu MajorFormat %S SubFormat %S Specifier %S FormatSize %lu SampleSize %lu Align %lu Flags %lx Reserved %lx DataLength %lu\n", Index, Pin->PinId, MajorFormat.Buffer, SubFormat.Buffer, Specifier.Buffer,
870  DataRange->FormatSize, DataRange->SampleSize, DataRange->Alignment, DataRange->Flags, DataRange->Reserved, DataLength);
871 
872  /* FIXME implement KsPinDataIntersectionEx */
873  /* Call miniport's proprietary handler */
874  Status = This->Filter.Descriptor->PinDescriptors[Pin->PinId].IntersectHandler(&This->Filter,
875  Irp,
876  Pin,
877  DataRange,
878  This->Filter.Descriptor->PinDescriptors[Pin->PinId].PinDescriptor.DataRanges[0], /* HACK */
879  DataLength,
880  Data,
881  &Length);
882  DPRINT("KspHandleDataIntersection Status %lx\n", Status);
883 
885  {
886  ASSERT(Length);
887  IoStatus->Information = Length;
888  break;
889  }
890 
891  DataRange = (PKSDATARANGE)((PUCHAR)DataRange + DataRange->FormatSize);
892  /* FIXME make sure its 64 bit aligned */
893  ASSERT(((ULONG_PTR)DataRange & 0x7) == 0);
894  }
895  IoStatus->Status = Status;
896  return Status;
897 }
898 
899 NTSTATUS
900 NTAPI
902  IN PIRP Irp,
904  IN OUT PVOID Data)
905 {
907 
908  /* get filter implementation */
909  This = (IKsFilterImpl*)KSPROPERTY_ITEM_IRP_STORAGE(Irp);
910 
911  /* sanity check */
912  ASSERT(This);
913 
914  return KsTopologyPropertyHandler(Irp, Request, Data, &This->Topology);
915 
916 }
917 
918 NTSTATUS
919 NTAPI
921  IN PIRP Irp,
923  IN OUT PVOID Data)
924 {
925  PIO_STACK_LOCATION IoStack;
927 
928  /* get filter implementation */
929  This = (IKsFilterImpl*)KSPROPERTY_ITEM_IRP_STORAGE(Irp);
930 
931  /* sanity check */
932  ASSERT(This);
933 
934  /* get current stack location */
936  ASSERT(IoStack->Parameters.DeviceIoControl.OutputBufferLength >= sizeof(KSCOMPONENTID));
937 
938  if (This->Filter.Descriptor->ComponentId != NULL)
939  {
940  RtlMoveMemory(Data, This->Filter.Descriptor->ComponentId, sizeof(KSCOMPONENTID));
941  Irp->IoStatus.Information = sizeof(KSCOMPONENTID);
942  return STATUS_SUCCESS;
943  }
944  else
945  {
946  /* not valid */
947  return STATUS_NOT_FOUND;
948  }
949 
950 }
951 
952 NTSTATUS
953 NTAPI
955  IN PIRP Irp,
957  IN OUT PVOID Data)
958 {
959  PIO_STACK_LOCATION IoStack;
962 
963  /* get filter implementation */
964  This = (IKsFilterImpl*)KSPROPERTY_ITEM_IRP_STORAGE(Irp);
965 
966  /* sanity check */
967  ASSERT(This);
968 
969  /* get current stack location */
971 
972  switch(Request->Id)
973  {
981  case KSPROPERTY_PIN_NAME:
983  Status = KspPinPropertyHandler(Irp, Request, Data, This->Filter.Descriptor->PinDescriptorsCount, (const KSPIN_DESCRIPTOR*)This->Filter.Descriptor->PinDescriptors, This->Filter.Descriptor->PinDescriptorSize);
984  break;
987  break;
990  break;
993  break;
994 
996  Status = KspHandleDataIntersection(Irp, &Irp->IoStatus, Request, Data, IoStack->Parameters.DeviceIoControl.OutputBufferLength, This);
997  break;
998  default:
1001  }
1002  DPRINT("KspPinPropertyHandler Pins %lu Request->Id %lu Status %lx\n", This->Filter.Descriptor->PinDescriptorsCount, Request->Id, Status);
1003 
1004 
1005  return Status;
1006 }
1007 
1008 NTSTATUS
1009 NTAPI
1012  IN PIRP Irp)
1013 {
1014  PIO_STACK_LOCATION IoStack;
1015  IKsFilter * Filter;
1016  IKsFilterImpl * This;
1017  NTSTATUS Status;
1018  PKSFILTER FilterInstance;
1021  ULONG SetCount = 0;
1022  PKSP_NODE NodeProperty;
1023  PKSNODE_DESCRIPTOR NodeDescriptor;
1024 
1025  /* obtain filter from object header */
1027  if (!NT_SUCCESS(Status))
1028  return Status;
1029 
1030  /* get our real implementation */
1032 
1033  /* current irp stack */
1034  IoStack = IoGetCurrentIrpStackLocation(Irp);
1035 
1036  /* get property from input buffer */
1037  Property = (PKSPROPERTY)IoStack->Parameters.DeviceIoControl.Type3InputBuffer;
1038 
1039  /* get filter instance */
1040  FilterInstance = Filter->lpVtbl->GetStruct(Filter);
1041 
1042  /* sanity check */
1043  ASSERT(IoStack->Parameters.DeviceIoControl.InputBufferLength >= sizeof(KSIDENTIFIER));
1044  ASSERT(FilterInstance);
1045  ASSERT(FilterInstance->Descriptor);
1046  ASSERT(FilterInstance->Descriptor->AutomationTable);
1047 
1048  /* acquire control mutex */
1049  KeWaitForSingleObject(This->Header.ControlMutex, Executive, KernelMode, FALSE, NULL);
1050 
1051  if (IoStack->Parameters.DeviceIoControl.IoControlCode == IOCTL_KS_METHOD)
1052  {
1053  const KSMETHOD_SET *MethodSet = NULL;
1054  ULONG MethodItemSize = 0;
1055 
1056  /* check if the driver supports method sets */
1057  if (FilterInstance->Descriptor->AutomationTable->MethodSetsCount)
1058  {
1059  SetCount = FilterInstance->Descriptor->AutomationTable->MethodSetsCount;
1060  MethodSet = FilterInstance->Descriptor->AutomationTable->MethodSets;
1061  MethodItemSize = FilterInstance->Descriptor->AutomationTable->MethodItemSize;
1062  }
1063 
1064  /* call method set handler */
1065  Status = KspMethodHandlerWithAllocator(Irp, SetCount, MethodSet, NULL, MethodItemSize);
1066  }
1067  else if (IoStack->Parameters.DeviceIoControl.IoControlCode == IOCTL_KS_PROPERTY)
1068  {
1069  const KSPROPERTY_SET *PropertySet = NULL;
1070  ULONG PropertyItemSize = 0;
1071 
1072  /* check if the driver supports method sets */
1073  if (Property->Flags & KSPROPERTY_TYPE_TOPOLOGY)
1074  {
1075  ASSERT(IoStack->Parameters.DeviceIoControl.InputBufferLength >= sizeof(KSP_NODE));
1076  NodeProperty = (PKSP_NODE)Property;
1077  NodeDescriptor = (PKSNODE_DESCRIPTOR)((ULONG_PTR)FilterInstance->Descriptor->NodeDescriptors + FilterInstance->Descriptor->NodeDescriptorSize * NodeProperty->NodeId);
1078  if (NodeDescriptor->AutomationTable != NULL)
1079  {
1080  SetCount = NodeDescriptor->AutomationTable->PropertySetsCount;
1081  PropertySet = NodeDescriptor->AutomationTable->PropertySets;
1082  PropertyItemSize = 0;
1083  }
1084  }
1085  else if (FilterInstance->Descriptor->AutomationTable->PropertySetsCount)
1086  {
1087  SetCount = FilterInstance->Descriptor->AutomationTable->PropertySetsCount;
1088  PropertySet = FilterInstance->Descriptor->AutomationTable->PropertySets;
1089  PropertyItemSize = FilterInstance->Descriptor->AutomationTable->PropertyItemSize;
1090  // FIXME: handle variable sized property items
1091  ASSERT(PropertyItemSize == sizeof(KSPROPERTY_ITEM));
1092  PropertyItemSize = 0;
1093  }
1094 
1095  /* needed for our property handlers */
1096  KSPROPERTY_ITEM_IRP_STORAGE(Irp) = (KSPROPERTY_ITEM*)This;
1097 
1098  /* call property handler */
1099  Status = KspPropertyHandler(Irp, SetCount, PropertySet, NULL, PropertyItemSize);
1100  }
1101  else
1102  {
1103  /* sanity check */
1104  ASSERT(IoStack->Parameters.DeviceIoControl.IoControlCode == IOCTL_KS_ENABLE_EVENT ||
1105  IoStack->Parameters.DeviceIoControl.IoControlCode == IOCTL_KS_DISABLE_EVENT);
1106 
1107  if (IoStack->Parameters.DeviceIoControl.IoControlCode == IOCTL_KS_ENABLE_EVENT)
1108  {
1109  /* call enable event handlers */
1111  FilterInstance->Descriptor->AutomationTable->EventSetsCount,
1112  (PKSEVENT_SET)FilterInstance->Descriptor->AutomationTable->EventSets,
1113  &This->Header.EventList,
1115  (PVOID)&This->Header.EventListLock,
1116  NULL,
1117  FilterInstance->Descriptor->AutomationTable->EventItemSize);
1118  }
1119  else
1120  {
1121  /* disable event handler */
1122  Status = KsDisableEvent(Irp, &This->Header.EventList, KSEVENTS_SPINLOCK, &This->Header.EventListLock);
1123  }
1124  }
1125 
1127  DPRINT("IKsFilter_DispatchDeviceIoControl property PinCount %x\n", FilterInstance->Descriptor->PinDescriptorsCount);
1128  DPRINT("IKsFilter_DispatchDeviceIoControl property Set |%S| Id %u Flags %x Status %lx ResultLength %lu\n", GuidString.Buffer, Property->Id, Property->Flags, Status, Irp->IoStatus.Information);
1130 
1131  /* release filter */
1132  Filter->lpVtbl->Release(Filter);
1133 
1134  /* release control mutex */
1135  KeReleaseMutex(This->Header.ControlMutex, FALSE);
1136 
1137  if (Status != STATUS_PENDING)
1138  {
1139  Irp->IoStatus.Status = Status;
1141  }
1142 
1143  /* done */
1144  return Status;
1145 }
1146 
1147 static KSDISPATCH_TABLE DispatchTable =
1148 {
1159 };
1160 
1161 
1162 NTSTATUS
1164  IKsFilterImpl * This,
1165  KSFILTER_DESCRIPTOR* FilterDescriptor)
1166 {
1167  ULONG Index = 0;
1168  NTSTATUS Status;
1169  PKSNODE_DESCRIPTOR NodeDescriptor;
1170 
1171  /* initialize pin descriptors */
1172  This->FirstPin = NULL;
1173  This->PinInstanceCount = NULL;
1174  This->ProcessPinIndex = NULL;
1175 
1176  /* initialize topology descriptor */
1177  This->Topology.CategoriesCount = FilterDescriptor->CategoriesCount;
1178  This->Topology.Categories = FilterDescriptor->Categories;
1179  This->Topology.TopologyNodesCount = FilterDescriptor->NodeDescriptorsCount;
1180  This->Topology.TopologyConnectionsCount = FilterDescriptor->ConnectionsCount;
1181  This->Topology.TopologyConnections = FilterDescriptor->Connections;
1182 
1183  /* are there any templates */
1184  if (FilterDescriptor->PinDescriptorsCount)
1185  {
1186  /* sanity check */
1187  ASSERT(FilterDescriptor->PinDescriptors);
1188 
1189  /* FIXME handle variable sized pin descriptors */
1190  ASSERT(FilterDescriptor->PinDescriptorSize == sizeof(KSPIN_DESCRIPTOR_EX));
1191 
1192  /* store pin descriptors ex */
1193  Status = _KsEdit(This->Filter.Bag, (PVOID*)&This->Filter.Descriptor->PinDescriptors, FilterDescriptor->PinDescriptorSize * FilterDescriptor->PinDescriptorsCount,
1194  FilterDescriptor->PinDescriptorSize * FilterDescriptor->PinDescriptorsCount, 0);
1195 
1196  if (!NT_SUCCESS(Status))
1197  {
1198  DPRINT("IKsFilter_CreateDescriptors _KsEdit failed %lx\n", Status);
1199  return Status;
1200  }
1201 
1202  /* store pin instance count */
1203  Status = _KsEdit(This->Filter.Bag, (PVOID*)&This->PinInstanceCount, sizeof(ULONG) * FilterDescriptor->PinDescriptorsCount,
1204  sizeof(ULONG) * FilterDescriptor->PinDescriptorsCount, 0);
1205 
1206  if (!NT_SUCCESS(Status))
1207  {
1208  DPRINT("IKsFilter_CreateDescriptors _KsEdit failed %lx\n", Status);
1209  return Status;
1210  }
1211 
1212  /* store instantiated pin arrays */
1213  Status = _KsEdit(This->Filter.Bag, (PVOID*)&This->FirstPin, sizeof(PVOID) * FilterDescriptor->PinDescriptorsCount,
1214  sizeof(PVOID) * FilterDescriptor->PinDescriptorsCount, 0);
1215 
1216  if (!NT_SUCCESS(Status))
1217  {
1218  DPRINT("IKsFilter_CreateDescriptors _KsEdit failed %lx\n", Status);
1219  return Status;
1220  }
1221 
1222  /* add new pin factory */
1223  RtlMoveMemory((PVOID)This->Filter.Descriptor->PinDescriptors, FilterDescriptor->PinDescriptors, FilterDescriptor->PinDescriptorSize * FilterDescriptor->PinDescriptorsCount);
1224 
1225  /* allocate process pin index */
1226  Status = _KsEdit(This->Filter.Bag, (PVOID*)&This->ProcessPinIndex, sizeof(KSPROCESSPIN_INDEXENTRY) * FilterDescriptor->PinDescriptorsCount,
1227  sizeof(KSPROCESSPIN_INDEXENTRY) * FilterDescriptor->PinDescriptorsCount, 0);
1228 
1229  if (!NT_SUCCESS(Status))
1230  {
1231  DPRINT("IKsFilter_CreateDescriptors _KsEdit failed %lx\n", Status);
1232  return Status;
1233  }
1234 
1235  }
1236 
1237 
1238  if (FilterDescriptor->ConnectionsCount)
1239  {
1240  /* modify connections array */
1241  Status = _KsEdit(This->Filter.Bag,
1242  (PVOID*)&This->Filter.Descriptor->Connections,
1243  FilterDescriptor->ConnectionsCount * sizeof(KSTOPOLOGY_CONNECTION),
1244  FilterDescriptor->ConnectionsCount * sizeof(KSTOPOLOGY_CONNECTION),
1245  0);
1246 
1247  This->Topology.TopologyConnections = This->Filter.Descriptor->Connections;
1248  This->Topology.TopologyConnectionsCount = ((PKSFILTER_DESCRIPTOR)This->Filter.Descriptor)->ConnectionsCount = FilterDescriptor->ConnectionsCount;
1249  }
1250 
1251  if (FilterDescriptor->NodeDescriptorsCount)
1252  {
1253  /* sanity check */
1254  ASSERT(FilterDescriptor->NodeDescriptors);
1255 
1256  /* sanity check */
1257  ASSERT(FilterDescriptor->NodeDescriptorSize >= sizeof(KSNODE_DESCRIPTOR));
1258 
1259  This->Topology.TopologyNodes = AllocateItem(NonPagedPool, sizeof(GUID) * FilterDescriptor->NodeDescriptorsCount);
1260  /* allocate topology node types array */
1261  if (!This->Topology.TopologyNodes)
1262  {
1263  DPRINT("IKsFilter_CreateDescriptors OutOfMemory TopologyNodesCount %lu\n", FilterDescriptor->NodeDescriptorsCount);
1265  }
1266 
1267  This->Topology.TopologyNodesNames = AllocateItem(NonPagedPool, sizeof(GUID) * FilterDescriptor->NodeDescriptorsCount);
1268  /* allocate topology names array */
1269  if (!This->Topology.TopologyNodesNames)
1270  {
1271  FreeItem((PVOID)This->Topology.TopologyNodes);
1272  DPRINT("IKsFilter_CreateDescriptors OutOfMemory TopologyNodesCount %lu\n", FilterDescriptor->NodeDescriptorsCount);
1274  }
1275 
1276  DPRINT("NodeDescriptorCount %lu\n", FilterDescriptor->NodeDescriptorsCount);
1277  NodeDescriptor = (PKSNODE_DESCRIPTOR)FilterDescriptor->NodeDescriptors;
1278  for(Index = 0; Index < FilterDescriptor->NodeDescriptorsCount; Index++)
1279  {
1280  DPRINT("Index %lu Type %p Name %p\n", Index, NodeDescriptor->Type, NodeDescriptor->Name);
1281 
1282  /* copy topology type */
1283  if (NodeDescriptor->Type)
1284  RtlMoveMemory((PVOID)&This->Topology.TopologyNodes[Index], NodeDescriptor->Type, sizeof(GUID));
1285 
1286  /* copy topology name */
1287  if (NodeDescriptor->Name)
1288  RtlMoveMemory((PVOID)&This->Topology.TopologyNodesNames[Index], NodeDescriptor->Name, sizeof(GUID));
1289 
1290  // next node descriptor
1291  NodeDescriptor = (PKSNODE_DESCRIPTOR)((ULONG_PTR)NodeDescriptor + FilterDescriptor->NodeDescriptorSize);
1292  }
1293  }
1294  /* done! */
1295  return STATUS_SUCCESS;
1296 }
1297 
1298 NTSTATUS
1300  IKsFilterImpl * This,
1301  const KSFILTER_DESCRIPTOR* FilterDescriptor)
1302 {
1303  NTSTATUS Status;
1304  KSAUTOMATION_TABLE AutomationTable;
1305 
1306  This->Filter.Descriptor = AllocateItem(NonPagedPool, sizeof(KSFILTER_DESCRIPTOR));
1307  if (!This->Filter.Descriptor)
1309 
1310  Status = KsAddItemToObjectBag(This->Filter.Bag, (PVOID)This->Filter.Descriptor, NULL);
1311  if (!NT_SUCCESS(Status))
1312  {
1313  FreeItem((PVOID)This->Filter.Descriptor);
1314  This->Filter.Descriptor = NULL;
1316  }
1317 
1318  /* copy filter descriptor fields */
1319  RtlMoveMemory((PVOID)This->Filter.Descriptor, FilterDescriptor, sizeof(KSFILTER_DESCRIPTOR));
1320 
1321  /* zero automation table */
1322  RtlZeroMemory(&AutomationTable, sizeof(KSAUTOMATION_TABLE));
1323 
1324  /* setup filter property sets */
1325  AutomationTable.PropertyItemSize = sizeof(KSPROPERTY_ITEM);
1326  AutomationTable.PropertySetsCount = 3;
1327  AutomationTable.PropertySets = FilterPropertySet;
1328 
1329  /* merge filter automation table */
1330  Status = KsMergeAutomationTables((PKSAUTOMATION_TABLE*)&This->Filter.Descriptor->AutomationTable, (PKSAUTOMATION_TABLE)FilterDescriptor->AutomationTable, &AutomationTable, This->Filter.Bag);
1331 
1332  return Status;
1333 }
1334 
1335 
1336 VOID
1338  PKSFILTER Filter,
1339  PKSPIN Pin)
1340 {
1341  PKSPIN NextPin, CurPin;
1342  PKSBASIC_HEADER BasicHeader;
1344 
1345  /* sanity check */
1346  ASSERT(Pin->Id < This->Filter.Descriptor->PinDescriptorsCount);
1347 
1348  if (This->FirstPin[Pin->Id] == NULL)
1349  {
1350  /* welcome first pin */
1351  This->FirstPin[Pin->Id] = Pin;
1352  This->PinInstanceCount[Pin->Id]++;
1353  return;
1354  }
1355 
1356  /* get first pin */
1357  CurPin = This->FirstPin[Pin->Id];
1358 
1359  do
1360  {
1361  /* get next instantiated pin */
1362  NextPin = KsPinGetNextSiblingPin(CurPin);
1363  if (!NextPin)
1364  break;
1365 
1366  NextPin = CurPin;
1367 
1368  }while(NextPin != NULL);
1369 
1370  /* get basic header */
1371  BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)CurPin - sizeof(KSBASIC_HEADER));
1372 
1373  /* store pin */
1374  BasicHeader->Next.Pin = Pin;
1375 }
1376 
1377 VOID
1379  PKSFILTER Filter,
1380  PKSPIN Pin)
1381 {
1382  PKSPIN NextPin, CurPin, LastPin;
1383  PKSBASIC_HEADER BasicHeader;
1385 
1386  /* sanity check */
1387  ASSERT(Pin->Id < This->Filter.Descriptor->PinDescriptorsCount);
1388 
1389  /* get first pin */
1390  CurPin = This->FirstPin[Pin->Id];
1391 
1392  LastPin = NULL;
1393  do
1394  {
1395  /* get next instantiated pin */
1396  NextPin = KsPinGetNextSiblingPin(CurPin);
1397 
1398  if (CurPin == Pin)
1399  {
1400  if (LastPin)
1401  {
1402  /* get basic header of last pin */
1403  BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)LastPin - sizeof(KSBASIC_HEADER));
1404 
1405  BasicHeader->Next.Pin = NextPin;
1406  }
1407  else
1408  {
1409  /* erase last pin */
1410  This->FirstPin[Pin->Id] = NextPin;
1411  }
1412  /* decrement pin instance count */
1413  This->PinInstanceCount[Pin->Id]--;
1414  return;
1415  }
1416 
1417  if (!NextPin)
1418  break;
1419 
1420  LastPin = CurPin;
1421  NextPin = CurPin;
1422 
1423  }while(NextPin != NULL);
1424 
1425  /* pin not found */
1426  ASSERT(0);
1427 }
1428 
1429 
1430 NTSTATUS
1431 NTAPI
1434  IN PIRP Irp)
1435 {
1436  IKsFilterImpl * This;
1437  PKSOBJECT_CREATE_ITEM CreateItem;
1439  NTSTATUS Status;
1440 
1441  DPRINT("IKsFilter_DispatchCreatePin\n");
1442 
1443  /* get the create item */
1444  CreateItem = KSCREATE_ITEM_IRP_STORAGE(Irp);
1445 
1446  /* get the filter object */
1447  This = (IKsFilterImpl*)CreateItem->Context;
1448 
1449  /* sanity check */
1450  ASSERT(This->Header.Type == KsObjectTypeFilter);
1451 
1452  /* acquire control mutex */
1453  KeWaitForSingleObject(This->Header.ControlMutex, Executive, KernelMode, FALSE, NULL);
1454 
1455  /* now validate the connect request */
1456  Status = KspValidateConnectRequest(Irp, This->Filter.Descriptor->PinDescriptorsCount, (PVOID)This->Filter.Descriptor->PinDescriptors, This->Filter.Descriptor->PinDescriptorSize, &Connect);
1457 
1458  DPRINT("IKsFilter_DispatchCreatePin KsValidateConnectRequest %lx\n", Status);
1459 
1460  if (NT_SUCCESS(Status))
1461  {
1462  /* sanity check */
1463  ASSERT(Connect->PinId < This->Filter.Descriptor->PinDescriptorsCount);
1464 
1465  DPRINT("IKsFilter_DispatchCreatePin KsValidateConnectRequest PinId %lu CurrentInstanceCount %lu MaxPossible %lu\n", Connect->PinId,
1466  This->PinInstanceCount[Connect->PinId],
1467  This->Filter.Descriptor->PinDescriptors[Connect->PinId].InstancesPossible);
1468 
1469  if (This->PinInstanceCount[Connect->PinId] < This->Filter.Descriptor->PinDescriptors[Connect->PinId].InstancesPossible)
1470  {
1471  /* create the pin */
1472  Status = KspCreatePin(DeviceObject, Irp, This->Header.KsDevice, This->FilterFactory, (IKsFilter*)&This->Header.OuterUnknown, Connect, (KSPIN_DESCRIPTOR_EX*)&This->Filter.Descriptor->PinDescriptors[Connect->PinId]);
1473 
1474  DPRINT("IKsFilter_DispatchCreatePin KspCreatePin %lx\n", Status);
1475  }
1476  else
1477  {
1478  /* maximum instance count reached, bye-bye */
1480  DPRINT("IKsFilter_DispatchCreatePin MaxInstance %lu CurInstance %lu %lx\n", This->Filter.Descriptor->PinDescriptors[Connect->PinId].InstancesPossible, This->PinInstanceCount[Connect->PinId]);
1481  }
1482  }
1483 
1484  /* release control mutex */
1485  KeReleaseMutex(This->Header.ControlMutex, FALSE);
1486 
1487  if (Status != STATUS_PENDING)
1488  {
1489  /* complete request */
1490  Irp->IoStatus.Status = Status;
1492  }
1493 
1494  /* done */
1495  DPRINT("IKsFilter_DispatchCreatePin Result %lx\n", Status);
1496  return Status;
1497 }
1498 
1499 NTSTATUS
1500 NTAPI
1503  IN PIRP Irp)
1504 {
1505  UNIMPLEMENTED;
1506  Irp->IoStatus.Status = STATUS_UNSUCCESSFUL;
1508  return STATUS_UNSUCCESSFUL;
1509 }
1510 
1511 
1512 VOID
1514  IKsFilterImpl * This,
1515  PKSFILTERFACTORY FilterFactory)
1516 {
1517  PKSBASIC_HEADER BasicHeader;
1518  PKSFILTER Filter;
1519 
1520 
1521  /* get filter factory basic header */
1522  BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)FilterFactory - sizeof(KSBASIC_HEADER));
1523 
1524  /* sanity check */
1525  ASSERT(BasicHeader->Type == KsObjectTypeFilterFactory);
1526 
1527  if (BasicHeader->FirstChild.FilterFactory == NULL)
1528  {
1529  /* welcome first instantiated filter */
1530  BasicHeader->FirstChild.Filter = &This->Filter;
1531  return;
1532  }
1533 
1534  /* set to first entry */
1535  Filter = BasicHeader->FirstChild.Filter;
1536 
1537  do
1538  {
1539  /* get basic header */
1540  BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)Filter - sizeof(KSBASIC_HEADER));
1541  /* sanity check */
1542  ASSERT(BasicHeader->Type == KsObjectTypeFilter);
1543 
1544  if (BasicHeader->Next.Filter)
1545  {
1546  /* iterate to next filter factory */
1547  Filter = BasicHeader->Next.Filter;
1548  }
1549  else
1550  {
1551  /* found last entry */
1552  break;
1553  }
1554  }while(TRUE);
1555 
1556  /* attach filter factory */
1557  BasicHeader->Next.Filter = &This->Filter;
1558 }
1559 
1560 VOID
1562  IKsFilterImpl * This,
1563  PKSFILTERFACTORY FilterFactory)
1564 {
1565  PKSBASIC_HEADER BasicHeader;
1566  PKSFILTER Filter, LastFilter;
1567 
1568  /* get filter factory basic header */
1569  BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)FilterFactory - sizeof(KSBASIC_HEADER));
1570 
1571  /* sanity check */
1572  ASSERT(BasicHeader->Type == KsObjectTypeFilterFactory);
1573  ASSERT(BasicHeader->FirstChild.Filter != NULL);
1574 
1575 
1576  /* set to first entry */
1577  Filter = BasicHeader->FirstChild.Filter;
1578  LastFilter = NULL;
1579 
1580  do
1581  {
1582  if (Filter == &This->Filter)
1583  {
1584  if (LastFilter)
1585  {
1586  /* get basic header */
1587  BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)LastFilter - sizeof(KSBASIC_HEADER));
1588  /* remove filter instance */
1589  BasicHeader->Next.Filter = This->Header.Next.Filter;
1590  break;
1591  }
1592  else
1593  {
1594  /* remove filter instance */
1595  BasicHeader->FirstChild.Filter = This->Header.Next.Filter;
1596  break;
1597  }
1598  }
1599 
1600  /* get basic header */
1601  BasicHeader = (PKSBASIC_HEADER)((ULONG_PTR)Filter - sizeof(KSBASIC_HEADER));
1602  /* sanity check */
1603  ASSERT(BasicHeader->Type == KsObjectTypeFilter);
1604 
1605  LastFilter = Filter;
1606  if (BasicHeader->Next.Filter)
1607  {
1608  /* iterate to next filter factory */
1609  Filter = BasicHeader->Next.Filter;
1610  }
1611  else
1612  {
1613  /* filter is not in list */
1614  ASSERT(0);
1615  break;
1616  }
1617  }while(TRUE);
1618 }
1619 
1620 VOID
1621 NTAPI
1623  IN PVOID Ctx)
1624 {
1625  IKsProcessingObject * Object = (IKsProcessingObject*)Ctx;
1626 
1627  /* sanity check */
1628  ASSERT(Object);
1629 
1630  /* perform work */
1631  Object->lpVtbl->ProcessingObjectWork(Object);
1632 }
1633 
1634 NTSTATUS
1635 NTAPI
1638  IN PIRP Irp,
1639  IN IKsFilterFactory *iface)
1640 {
1641  IKsFilterImpl * This;
1642  IKsDevice *KsDevice;
1643  PKSFILTERFACTORY Factory;
1644  PIO_STACK_LOCATION IoStack;
1645  PDEVICE_EXTENSION DeviceExtension;
1646  NTSTATUS Status;
1647  PKSOBJECT_CREATE_ITEM CreateItem;
1648 
1649  /* get device extension */
1650  DeviceExtension = (PDEVICE_EXTENSION)DeviceObject->DeviceExtension;
1651 
1652  /* get the filter factory */
1653  Factory = iface->lpVtbl->GetStruct(iface);
1654 
1655  if (!Factory || !Factory->FilterDescriptor)
1656  {
1657  /* Sorry it just will not work */
1658  return STATUS_UNSUCCESSFUL;
1659  }
1660 
1661  if (Factory->FilterDescriptor->Flags & KSFILTER_FLAG_DENY_USERMODE_ACCESS)
1662  {
1663  if (Irp->RequestorMode == UserMode)
1664  {
1665  /* filter not accessible from user mode */
1666  DPRINT1("Access denied\n");
1667  return STATUS_UNSUCCESSFUL;
1668  }
1669  }
1670 
1671  /* allocate filter instance */
1673  if (!This)
1674  {
1675  DPRINT1("KspCreateFilter OutOfMemory\n");
1677  }
1678 
1679  /* initialize object bag */
1680  This->Filter.Bag = AllocateItem(NonPagedPool, sizeof(KSIOBJECT_BAG));
1681  if (!This->Filter.Bag)
1682  {
1683  /* no memory */
1684  FreeItem(This);
1685  DPRINT1("KspCreateFilter OutOfMemory\n");
1687  }
1688  KsDevice = (IKsDevice*)&DeviceExtension->DeviceHeader->BasicHeader.OuterUnknown;
1689  KsDevice->lpVtbl->InitializeObjectBag(KsDevice, (PKSIOBJECT_BAG)This->Filter.Bag, NULL);
1690 
1691  /* copy filter descriptor */
1692  Status = IKsFilter_CopyFilterDescriptor(This, Factory->FilterDescriptor);
1693  if (!NT_SUCCESS(Status))
1694  {
1695  /* not enough memory */
1696  FreeItem(This->Filter.Bag);
1697  FreeItem(This);
1698  DPRINT("KspCreateFilter IKsFilter_CopyFilterDescriptor failed %lx\n", Status);
1700  }
1701 
1702  /* get current irp stack */
1703  IoStack = IoGetCurrentIrpStackLocation(Irp);
1704 
1705  /* allocate create items */
1706  CreateItem = AllocateItem(NonPagedPool, sizeof(KSOBJECT_CREATE_ITEM) * 2);
1707  if (!CreateItem)
1708  {
1709  /* no memory */
1710  FreeItem(This->Filter.Bag);
1711  FreeItem(This);
1712  DPRINT1("KspCreateFilter OutOfMemory\n");
1714  }
1715 
1716  /* initialize pin create item */
1717  CreateItem[0].Create = IKsFilter_DispatchCreatePin;
1718  CreateItem[0].Context = (PVOID)This;
1719  CreateItem[0].Flags = KSCREATE_ITEM_FREEONSTOP;
1720  RtlInitUnicodeString(&CreateItem[0].ObjectClass, KSSTRING_Pin);
1721  /* initialize node create item */
1722  CreateItem[1].Create = IKsFilter_DispatchCreateNode;
1723  CreateItem[1].Context = (PVOID)This;
1724  CreateItem[1].Flags = KSCREATE_ITEM_FREEONSTOP;
1725  RtlInitUnicodeString(&CreateItem[1].ObjectClass, KSSTRING_TopologyNode);
1726 
1727 
1728  /* initialize filter instance */
1729  This->ref = 1;
1730  This->Header.OuterUnknown = (PUNKNOWN)&vt_IKsFilter;
1731  This->lpVtblKsControl = &vt_IKsControl;
1732  This->lpVtblKsProcessingObject = &vt_IKsProcessingObject;
1733 
1734  This->Factory = Factory;
1735  This->FilterFactory = iface;
1736  This->FileObject = IoStack->FileObject;
1737  KeInitializeMutex(&This->ProcessingMutex, 0);
1738 
1739  /* initialize basic header */
1740  This->Header.KsDevice = &DeviceExtension->DeviceHeader->KsDevice;
1741  This->Header.Parent.KsFilterFactory = iface->lpVtbl->GetStruct(iface);
1742  This->Header.Type = KsObjectTypeFilter;
1743  This->Header.ControlMutex = &This->ControlMutex;
1744  KeInitializeMutex(This->Header.ControlMutex, 0);
1745  InitializeListHead(&This->Header.EventList);
1746  KeInitializeSpinLock(&This->Header.EventListLock);
1747 
1748  /* initialize and gate */
1749  KsGateInitializeAnd(&This->Gate, NULL);
1750 
1751  /* FIXME initialize and gate based on pin flags */
1752 
1753  /* initialize work item */
1754  ExInitializeWorkItem(&This->WorkItem, IKsFilter_FilterCentricWorker, (PVOID)This->lpVtblKsProcessingObject);
1755 
1756  /* allocate counted work item */
1758  if (!NT_SUCCESS(Status))
1759  {
1760  /* what can go wrong, goes wrong */
1761  DPRINT1("KsRegisterCountedWorker failed with %lx\n", Status);
1762  FreeItem(This);
1763  FreeItem(CreateItem);
1764  return Status;
1765  }
1766 
1767  /* allocate the stream descriptors */
1768  Status = IKsFilter_CreateDescriptors(This, (PKSFILTER_DESCRIPTOR)Factory->FilterDescriptor);
1769  if (!NT_SUCCESS(Status))
1770  {
1771  /* what can go wrong, goes wrong */
1772  DPRINT1("IKsFilter_CreateDescriptors failed with %lx\n", Status);
1773  KsUnregisterWorker(This->Worker);
1774  FreeItem(This);
1775  FreeItem(CreateItem);
1776  return Status;
1777  }
1778 
1779 
1780 
1781  /* does the filter have a filter dispatch */
1782  if (Factory->FilterDescriptor->Dispatch)
1783  {
1784  /* does it have a create routine */
1785  if (Factory->FilterDescriptor->Dispatch->Create)
1786  {
1787  /* now let driver initialize the filter instance */
1788 
1789  ASSERT(This->Header.KsDevice);
1790  ASSERT(This->Header.KsDevice->Started);
1791  Status = Factory->FilterDescriptor->Dispatch->Create(&This->Filter, Irp);
1792 
1793  if (!NT_SUCCESS(Status) && Status != STATUS_PENDING)
1794  {
1795  /* driver failed to initialize */
1796  DPRINT1("Driver: Status %x\n", Status);
1797 
1798  /* free filter instance */
1799  KsUnregisterWorker(This->Worker);
1800  FreeItem(This);
1801  FreeItem(CreateItem);
1802  return Status;
1803  }
1804  }
1805  }
1806 
1807  /* now allocate the object header */
1808  Status = KsAllocateObjectHeader((PVOID*)&This->ObjectHeader, 2, CreateItem, Irp, &DispatchTable);
1809  if (!NT_SUCCESS(Status))
1810  {
1811  /* failed to allocate object header */
1812  DPRINT1("Failed to allocate object header %x\n", Status);
1813 
1814  return Status;
1815  }
1816 
1817  /* initialize object header extra fields */
1818  This->ObjectHeader->Type = KsObjectTypeFilter;
1819  This->ObjectHeader->Unknown = (PUNKNOWN)&This->Header.OuterUnknown;
1820  This->ObjectHeader->ObjectType = (PVOID)&This->Filter;
1821 
1822  /* attach filter to filter factory */
1823  IKsFilter_AttachFilterToFilterFactory(This, This->Header.Parent.KsFilterFactory);
1824 
1825  /* completed initialization */
1826  DPRINT1("KspCreateFilter done %lx KsDevice %p\n", Status, This->Header.KsDevice);
1827  return Status;
1828 }
1829 
1830 /*
1831  @implemented
1832 */
1833 KSDDKAPI
1834 VOID
1835 NTAPI
1837  IN PKSFILTER Filter)
1838 {
1840 
1841  KeWaitForSingleObject(&This->ProcessingMutex, Executive, KernelMode, FALSE, NULL);
1842 }
1843 
1844 /*
1845  @implemented
1846 */
1847 KSDDKAPI
1848 VOID
1849 NTAPI
1851  IN PKSFILTER Filter)
1852 {
1854 
1855  KeReleaseMutex(&This->ProcessingMutex, FALSE);
1856 }
1857 
1858 
1859 /*
1860  @implemented
1861 */
1862 KSDDKAPI
1863 NTSTATUS
1864 NTAPI
1866  IN PKSFILTER Filter,
1867  IN ULONG NewConnectionsCount,
1868  IN const KSTOPOLOGY_CONNECTION *const NewTopologyConnections)
1869 {
1870  ULONG Count;
1871  NTSTATUS Status;
1873 
1874  DPRINT("KsFilterAddTopologyConnections\n");
1875 
1876  ASSERT(This->Filter.Descriptor);
1877  Count = This->Filter.Descriptor->ConnectionsCount + NewConnectionsCount;
1878 
1879 
1880  /* modify connections array */
1881  Status = _KsEdit(This->Filter.Bag,
1882  (PVOID*)&This->Filter.Descriptor->Connections,
1883  Count * sizeof(KSTOPOLOGY_CONNECTION),
1884  This->Filter.Descriptor->ConnectionsCount * sizeof(KSTOPOLOGY_CONNECTION),
1885  0);
1886 
1887  if (!NT_SUCCESS(Status))
1888  {
1889  /* failed */
1890  DPRINT("KsFilterAddTopologyConnections KsEdit failed with %lx\n", Status);
1891  return Status;
1892  }
1893 
1894  /* FIXME verify connections */
1895 
1896  /* copy new connections */
1897  RtlMoveMemory((PVOID)&This->Filter.Descriptor->Connections[This->Filter.Descriptor->ConnectionsCount],
1898  NewTopologyConnections,
1899  NewConnectionsCount * sizeof(KSTOPOLOGY_CONNECTION));
1900 
1901  /* update topology */
1902  This->Topology.TopologyConnectionsCount += NewConnectionsCount;
1903  ((PKSFILTER_DESCRIPTOR)This->Filter.Descriptor)->ConnectionsCount += NewConnectionsCount;
1904  This->Topology.TopologyConnections = This->Filter.Descriptor->Connections;
1905 
1906  return Status;
1907 }
1908 
1909 /*
1910  @implemented
1911 */
1912 KSDDKAPI
1913 VOID
1914 NTAPI
1916  IN PKSFILTER Filter,
1918 {
1919  PKSGATE Gate;
1921 
1922  /* get gate */
1923  Gate = This->lpVtblKsProcessingObject->GetAndGate((IKsProcessingObject*)This->lpVtblKsProcessingObject);
1924 
1925  if (!KsGateCaptureThreshold(Gate))
1926  {
1927  /* filter control gate is closed */
1928  return;
1929  }
1930 DPRINT1("processing\n");
1931  /* try initiate processing */
1932  This->lpVtblKsProcessingObject->Process((IKsProcessingObject*)This->lpVtblKsProcessingObject, Asynchronous);
1933 }
1934 
1935 /*
1936  @unimplemented
1937 */
1938 KSDDKAPI
1939 NTSTATUS
1940 NTAPI
1942  IN PKSFILTER Filter,
1943  IN const KSNODE_DESCRIPTOR *const NodeDescriptor,
1944  OUT PULONG NodeID)
1945 {
1946  UNIMPLEMENTED;
1947  return STATUS_NOT_IMPLEMENTED;
1948 }
1949 
1950 /*
1951  @implemented
1952 */
1953 KSDDKAPI
1954 NTSTATUS
1955 NTAPI
1957  IN PKSFILTER Filter,
1958  IN const KSPIN_DESCRIPTOR_EX *const InPinDescriptor,
1959  OUT PULONG PinID)
1960 {
1961  ULONG Count;
1962  NTSTATUS Status;
1964 
1965  DPRINT("KsFilterCreatePinFactory\n");
1966 
1967  /* calculate new count */
1968  Count = This->Filter.Descriptor->PinDescriptorsCount + 1;
1969 
1970  /* sanity check */
1971  ASSERT(This->Filter.Descriptor->PinDescriptorSize == sizeof(KSPIN_DESCRIPTOR_EX));
1972 
1973  /* modify pin descriptors ex array */
1974  Status = _KsEdit(This->Filter.Bag, (PVOID*)&This->Filter.Descriptor->PinDescriptors, Count * This->Filter.Descriptor->PinDescriptorSize, This->Filter.Descriptor->PinDescriptorsCount * This->Filter.Descriptor->PinDescriptorSize, 0);
1975  if (!NT_SUCCESS(Status))
1976  {
1977  /* failed */
1978  DPRINT("KsFilterCreatePinFactory _KsEdit failed with %lx\n", Status);
1979  return Status;
1980  }
1981 
1982  /* modify pin instance count array */
1983  Status = _KsEdit(This->Filter.Bag,(PVOID*)&This->PinInstanceCount, sizeof(ULONG) * Count, sizeof(ULONG) * This->Filter.Descriptor->PinDescriptorsCount, 0);
1984  if (!NT_SUCCESS(Status))
1985  {
1986  /* failed */
1987  DPRINT("KsFilterCreatePinFactory _KsEdit failed with %lx\n", Status);
1988  return Status;
1989  }
1990 
1991  /* modify first pin array */
1992  Status = _KsEdit(This->Filter.Bag,(PVOID*)&This->FirstPin, sizeof(PVOID) * Count, sizeof(PVOID) * This->Filter.Descriptor->PinDescriptorsCount, 0);
1993  if (!NT_SUCCESS(Status))
1994  {
1995  /* failed */
1996  DPRINT("KsFilterCreatePinFactory _KsEdit failed with %lx\n", Status);
1997  return Status;
1998  }
1999 
2000  /* add new pin factory */
2001  RtlMoveMemory((PVOID)&This->Filter.Descriptor->PinDescriptors[This->Filter.Descriptor->PinDescriptorsCount], InPinDescriptor, sizeof(KSPIN_DESCRIPTOR_EX));
2002 
2003  /* allocate process pin index */
2004  Status = _KsEdit(This->Filter.Bag, (PVOID*)&This->ProcessPinIndex, sizeof(KSPROCESSPIN_INDEXENTRY) * Count,
2005  sizeof(KSPROCESSPIN_INDEXENTRY) * This->Filter.Descriptor->PinDescriptorsCount, 0);
2006 
2007  if (!NT_SUCCESS(Status))
2008  {
2009  DPRINT("KsFilterCreatePinFactory _KsEdit failed %lx\n", Status);
2010  return Status;
2011  }
2012 
2013  /* store new pin id */
2014  *PinID = This->Filter.Descriptor->PinDescriptorsCount;
2015 
2016  /* increment pin descriptor count */
2017  ((PKSFILTER_DESCRIPTOR)This->Filter.Descriptor)->PinDescriptorsCount++;
2018 
2019 
2020  DPRINT("KsFilterCreatePinFactory done\n");
2021  return STATUS_SUCCESS;
2022 
2023 }
2024 
2025 /*
2026  @unimplemented
2027 */
2028 KSDDKAPI
2029 PKSGATE
2030 NTAPI
2032  IN PKSFILTER Filter)
2033 {
2035 
2036  /* return and-gate */
2037  return &This->Gate;
2038 }
2039 
2040 /*
2041  @implemented
2042 */
2043 KSDDKAPI
2044 ULONG
2045 NTAPI
2047  IN PKSFILTER Filter,
2048  IN ULONG PinId)
2049 {
2051 
2052  if (PinId >= This->Filter.Descriptor->PinDescriptorsCount)
2053  {
2054  /* index is out of bounds */
2055  return 0;
2056  }
2057  /* return pin instance count */
2058  return This->PinInstanceCount[PinId];
2059 }
2060 
2061 /*
2062  @implemented
2063 */
2064 KSDDKAPI
2065 PKSPIN
2066 NTAPI
2068  IN PKSFILTER Filter,
2069  IN ULONG PinId)
2070 {
2072 
2073  if (PinId >= This->Filter.Descriptor->PinDescriptorsCount)
2074  {
2075  /* index is out of bounds */
2076  return NULL;
2077  }
2078 
2079  /* return first pin index */
2080  return This->FirstPin[PinId];
2081 }
2082 
2083 /*
2084  @implemented
2085 */
2086 KSDDKAPI
2087 VOID
2088 NTAPI
2090  IN PKSFILTER Filter,
2091  IN PFNKSFILTERPOWER Sleep OPTIONAL,
2092  IN PFNKSFILTERPOWER Wake OPTIONAL)
2093 {
2095 
2096  This->Sleep = Sleep;
2097  This->Wake = Wake;
2098 }
2099 
2100 /*
2101  @implemented
2102 */
2103 KSDDKAPI
2104 PKSFILTER
2105 NTAPI
2107  IN PIRP Irp)
2108 {
2109  PIO_STACK_LOCATION IoStack;
2110  PKSIOBJECT_HEADER ObjectHeader;
2111 
2112  DPRINT("KsGetFilterFromIrp\n");
2113 
2114  /* get current irp stack location */
2115  IoStack = IoGetCurrentIrpStackLocation(Irp);
2116 
2117  /* sanity check */
2118  ASSERT(IoStack->FileObject);
2119 
2120  /* get object header */
2121  ObjectHeader = (PKSIOBJECT_HEADER)IoStack->FileObject->FsContext2;
2122 
2123  if (ObjectHeader->Type == KsObjectTypeFilter)
2124  {
2125  /* irp is targeted at the filter */
2126  return (PKSFILTER)ObjectHeader->ObjectType;
2127  }
2128  else if (ObjectHeader->Type == KsObjectTypePin)
2129  {
2130  /* irp is for a pin */
2131  return KsPinGetParentFilter((PKSPIN)ObjectHeader->ObjectType);
2132  }
2133  else
2134  {
2135  /* irp is unappropiate to retrieve a filter */
2136  return NULL;
2137  }
2138 }
ULONG Count
Definition: ks.h:2010
#define KeGetCurrentIrql()
Definition: env_spec_w32.h:706
PKSFILTER NTAPI KsPinGetParentFilter(IN PKSPIN Pin)
Definition: pin.c:1097
LONG ref
Definition: filter.c:22
WORK_QUEUE_ITEM WorkItem
Definition: filter.c:32
struct KSBASIC_HEADER * PKSBASIC_HEADER
static PWSTR GuidString
Definition: apphelp.c:91
#define IOCTL_KS_PROPERTY
Definition: ks.h:150
#define IN
Definition: typedefs.h:38
NTSTATUS IKsFilter_CopyFilterDescriptor(IKsFilterImpl *This, const KSFILTER_DESCRIPTOR *FilterDescriptor)
Definition: filter.c:1299
const KSFILTER_DESCRIPTOR FilterDescriptor
Definition: splitter.c:229
IKsProcessingObjectVtbl * lpVtblKsProcessingObject
Definition: filter.c:21
PUNKNOWN Unknown
Definition: kstypes.h:29
IKsFilterFactory * FilterFactory
Definition: filter.c:20
#define REFIID
Definition: guiddef.h:113
#define TRUE
Definition: types.h:120
KSDDKAPI NTSTATUS NTAPI KsDispatchSetSecurity(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: irp.c:67
PKSPIN * FirstPin
Definition: filter.c:39
VOID WINAPI DECLSPEC_HOTPATCH Sleep(IN DWORD dwMilliseconds)
Definition: synch.c:736
#define LL
Definition: tui.h:72
#define IOCTL_KS_DISABLE_EVENT
Definition: ks.h:127
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
PKSPROCESSPIN_INDEXENTRY ProcessPinIndex
Definition: filter.c:40
NTSTATUS NTAPI KsAddItemToObjectBag(IN KSOBJECT_BAG ObjectBag, IN PVOID Item, IN PFNKSFREE Free OPTIONAL)
Definition: bag.c:86
const GUID IID_IKsFilter
Definition: filter.c:45
KSDDKAPI NTSTATUS NTAPI KsQueueWorkItem(IN PKSWORKER Worker, IN PWORK_QUEUE_ITEM WorkItem)
Definition: worker.c:252
PFNKSFILTERPOWER Wake
Definition: filter.c:36
ULONG NTAPI IKsFilter_fnRelease(IKsFilter *iface)
Definition: filter.c:437
NTSTATUS KspPropertyHandler(IN PIRP Irp, IN ULONG PropertySetsCount, IN const KSPROPERTY_SET *PropertySet, IN PFNKSALLOCATOR Allocator OPTIONAL, IN ULONG PropertyItemSize OPTIONAL)
Definition: property.c:138
_In_ PKSPIN_CONNECT Connect
Definition: ks.h:4565
KSDDKAPI NTSTATUS NTAPI KsDispatchQuerySecurity(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: irp.c:22
NTSTATUS KspHandleDataIntersection(IN PIRP Irp, IN PIO_STATUS_BLOCK IoStatus, IN PKSIDENTIFIER Request, IN OUT PVOID Data, IN ULONG DataLength, IN IKsFilterImpl *This)
Definition: filter.c:813
KSOBJECTTYPE Type
Definition: kstypes.h:23
KSDDKAPI PKSPIN NTAPI KsFilterGetFirstChildPin(IN PKSFILTER Filter, IN ULONG PinId)
Definition: filter.c:2067
const GUID IID_IKsControl
Definition: filter.c:44
#define STATUS_NOT_IMPLEMENTED
Definition: ntstatus.h:225
NTSTATUS NTAPI KsMergeAutomationTables(OUT PKSAUTOMATION_TABLE *AutomationTableAB, IN PKSAUTOMATION_TABLE AutomationTableA OPTIONAL, IN PKSAUTOMATION_TABLE AutomationTableB OPTIONAL, IN KSOBJECT_BAG Bag OPTIONAL)
Definition: api.c:2303
IN PLARGE_INTEGER IN ULONG IN BOOLEAN IN ULONG IN BOOLEAN OUT PIO_STATUS_BLOCK IoStatus
Definition: fatprocs.h:2650
_In_ PIRP Irp
Definition: csq.h:116
IUnknown * PUNKNOWN
Definition: com_apitest.h:45
VOID NTAPI IKsFilter_fnDeliverResetState(IKsFilter *iface, IN struct KSPROCESSPIPESECTION *PipeSection, IN KSRESET ResetState)
Definition: filter.c:605
_In_ BOOLEAN Create
Definition: pstypes.h:511
struct KSIOBJECT_HEADER * PKSIOBJECT_HEADER
unsigned char * PUCHAR
Definition: retypes.h:3
PVOID AllocateItem(IN POOL_TYPE PoolType, IN SIZE_T NumberOfBytes)
Definition: misc.c:30
#define KSSTRING_Pin
Definition: ks.h:48
LONG NTSTATUS
Definition: precomp.h:26
KSDDKAPI NTSTATUS NTAPI _KsEdit(IN KSOBJECT_BAG ObjectBag, IN OUT PVOID *PointerToPointerToItem, IN ULONG NewSize, IN ULONG OldSize, IN ULONG Tag)
Definition: bag.c:358
PKSPROCESSPIN_INDEXENTRY NTAPI IKsFilter_fnGetProcessDispatch(IKsFilter *iface)
Definition: filter.c:634
KSDDKAPI BOOLEAN NTAPI KsDispatchFastIoDeviceControlFailure(IN PFILE_OBJECT FileObject, IN BOOLEAN Wait, IN PVOID InputBuffer OPTIONAL, IN ULONG InputBufferLength, OUT PVOID OutputBuffer OPTIONAL, IN ULONG OutputBufferLength, IN ULONG IoControlCode, OUT PIO_STATUS_BLOCK IoStatus, IN PDEVICE_OBJECT DeviceObject)
Definition: irp.c:1218
_Inout_ __drv_aliasesMem PSLIST_ENTRY _Inout_ PSLIST_ENTRY _In_ ULONG Count
Definition: exfuncs.h:1015
NTSTATUS NTAPI IKsControl_fnKsProperty(IKsControl *iface, IN PKSPROPERTY Property, IN ULONG PropertyLength, IN OUT PVOID PropertyData, IN ULONG DataLength, OUT ULONG *BytesReturned)
Definition: filter.c:321
KSDDKAPI VOID NTAPI KsFilterReleaseProcessingMutex(IN PKSFILTER Filter)
Definition: filter.c:1850
PKSPIN NTAPI KsPinGetNextSiblingPin(IN PKSPIN Pin)
Definition: pin.c:1086
KSTOPOLOGY Topology
Definition: filter.c:25
NTSTATUS NTAPI IKsFilter_DispatchClose(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: filter.c:702
NTSTATUS NTAPI KspMethodHandlerWithAllocator(IN PIRP Irp, IN ULONG MethodSetsCount, IN const KSMETHOD_SET *MethodSet, IN PFNKSALLOCATOR Allocator OPTIONAL, IN ULONG MethodItemSize OPTIONAL)
Definition: methods.c:99
LONG NTAPI KeReleaseMutex(IN PKMUTEX Mutex, IN BOOLEAN Wait)
Definition: mutex.c:189
NTSTATUS KspEnableEvent(IN PIRP Irp, IN ULONG EventSetsCount, IN const KSEVENT_SET *EventSet, IN OUT PLIST_ENTRY EventsList OPTIONAL, IN KSEVENTS_LOCKTYPE EventsFlags OPTIONAL, IN PVOID EventsLock OPTIONAL, IN PFNKSALLOCATOR Allocator OPTIONAL, IN ULONG EventItemSize OPTIONAL)
Definition: event.c:87
NTSTATUS NTAPI KeWaitForSingleObject(IN PVOID Object, IN KWAIT_REASON WaitReason, IN KPROCESSOR_MODE WaitMode, IN BOOLEAN Alertable, IN PLARGE_INTEGER Timeout OPTIONAL)
Definition: wait.c:416
#define KSDDKAPI
Definition: ks.h:40
UNICODE_STRING Global
Definition: symlink.c:37
PFNKSFILTERPOWER Sleep
Definition: filter.c:35
KSDDKAPI NTSTATUS NTAPI KsDisableEvent(IN PIRP Irp, IN OUT PLIST_ENTRY EventsList, IN KSEVENTS_LOCKTYPE EventsFlags, IN PVOID EventsLock)
Definition: event.c:469
KSDDKAPI VOID NTAPI KsFreeObjectHeader(IN PVOID Header)
Definition: api.c:720
#define RtlMoveMemory(Destination, Source, Length)
Definition: typedefs.h:263
static VOID Wake(USHORT Csn)
Definition: hardware.c:100
PKSFILTER NTAPI IKsFilter_fnGetStruct(IKsFilter *iface)
Definition: filter.c:456
#define STATUS_BUFFER_TOO_SMALL
Definition: shellext.h:64
#define IsEqualGUIDAligned(guid1, guid2)
Definition: wdm.template.h:233
uint32_t ULONG_PTR
Definition: typedefs.h:63
NTSTATUS NTAPI IKsFilter_fnBindProcessPinsToPipeSection(IKsFilter *iface, IN struct KSPROCESSPIPESECTION *Section, IN PVOID Create, IN PKSPIN KsPin, OUT IKsPin **Pin, OUT PKSGATE *OutGate)
Definition: filter.c:487
_In_ NDIS_HANDLE _In_ PNDIS_REQUEST Request
Definition: ndis.h:5155
KSDDKAPI NTSTATUS NTAPI KsSynchronousIoControlDevice(IN PFILE_OBJECT FileObject, IN KPROCESSOR_MODE RequestorMode, IN ULONG IoControl, IN PVOID InBuffer, IN ULONG InSize, OUT PVOID OutBuffer, IN ULONG OutSize, OUT PULONG BytesReturned)
Definition: api.c:1099
#define STATUS_TIMEOUT
Definition: ntstatus.h:81
NTSTATUS NTAPI IKsFilter_DispatchCreateNode(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: filter.c:1501
PKSWORKER Worker
Definition: filter.c:31
VOID FreeItem(IN PVOID Item)
Definition: misc.c:43
long __cdecl _InterlockedIncrement(_Interlocked_operand_ long volatile *_Addend)
_In_ SYSTEM_POWER_STATE _In_ ULONG _In_ BOOLEAN Asynchronous
Definition: ntpoapi.h:303
ULONG PinId
Definition: ks.h:2632
NTSTATUS(* NTAPI)(IN PFILE_FULL_EA_INFORMATION EaBuffer, IN ULONG EaLength, OUT PULONG ErrorOffset)
Definition: IoEaTest.cpp:117
Definition: Header.h:8
unsigned int BOOL
Definition: ntddk_ex.h:94
BOOL NTAPI IKsFilter_fnDoAllNecessaryPinsExist(IKsFilter *iface)
Definition: filter.c:466
long LONG
Definition: pedump.c:60
NTSTATUS NTAPI IKsFilter_fnCreateNode(IKsFilter *iface, IN PIRP Irp, IN IKsPin *Pin, IN PLIST_ENTRY ListEntry)
Definition: filter.c:475
NTSTATUS KspHandleNecessaryPropertyInstances(IN PIO_STATUS_BLOCK IoStatus, IN PKSIDENTIFIER Request, IN OUT PVOID Data, IN IKsFilterImpl *This)
Definition: filter.c:784
_Must_inspect_result_ _In_opt_ PFLT_FILTER Filter
Definition: fltkernel.h:1802
BOOL NTAPI IKsFilter_fnIsFrameHolding(IKsFilter *iface)
Definition: filter.c:615
KSDDKAPI NTSTATUS NTAPI KsFilterCreateNode(IN PKSFILTER Filter, IN const KSNODE_DESCRIPTOR *const NodeDescriptor, OUT PULONG NodeID)
Definition: filter.c:1941
VOID IKsFilter_RemoveFilterFromFilterFactory(IKsFilterImpl *This, PKSFILTERFACTORY FilterFactory)
Definition: filter.c:1561
FORCEINLINE VOID KeInitializeSpinLock(_Out_ PKSPIN_LOCK SpinLock)
Definition: kefuncs.h:251
ULONG NTAPI IKsControl_fnRelease(IKsControl *iface)
Definition: filter.c:308
NTSTATUS NTAPI FilterGeneralComponentIdHandler(IN PIRP Irp, IN PKSIDENTIFIER Request, IN OUT PVOID Data)
Definition: filter.c:920
PVOID DeviceExtension
Definition: env_spec_w32.h:418
unsigned char BOOLEAN
DEFINE_KSPROPERTY_PINPROPOSEDATAFORMAT(IKsFilterPinSet, FilterPinPropertyHandler, FilterPinPropertyHandler, FilterPinPropertyHandler)
smooth NULL
Definition: ftsmooth.c:416
_At_(*)(_In_ PWSK_CLIENT Client, _In_opt_ PUNICODE_STRING NodeName, _In_opt_ PUNICODE_STRING ServiceName, _In_opt_ ULONG NameSpace, _In_opt_ GUID *Provider, _In_opt_ PADDRINFOEXW Hints, _Outptr_ PADDRINFOEXW *Result, _In_opt_ PEPROCESS OwningProcess, _In_opt_ PETHREAD OwningThread, _Inout_ PIRP Irp Result)(Mem)) NTSTATUS(WSKAPI *PFN_WSK_GET_ADDRESS_INFO
Definition: wsk.h:426
Definition: ks.h:2104
KSOBJECTTYPE Type
Definition: kstypes.h:56
void DPRINT(...)
Definition: polytest.cpp:61
VOID NTAPI IKsProcessingObject_fnTriggerNotification(IKsProcessingObject *iface)
Definition: filter.c:258
static IKsControlVtbl vt_IKsControl
Definition: filter.c:374
union KSBASIC_HEADER::@955 FirstChild
IKsControlVtbl * lpVtblKsControl
Definition: filter.c:19
NTSTATUS NTAPI IKsControl_fnKsMethod(IKsControl *iface, IN PKSMETHOD Method, IN ULONG MethodLength, IN OUT PVOID MethodData, IN ULONG DataLength, OUT ULONG *BytesReturned)
Definition: filter.c:337
void * PVOID
Definition: retypes.h:9
NTSTATUS KspValidateConnectRequest(IN PIRP Irp, IN ULONG DescriptorsCount, IN PVOID Descriptors, IN ULONG DescriptorSize, OUT PKSPIN_CONNECT *Connect)
Definition: connectivity.c:60
const GUID KSPROPSETID_Pin
Definition: filter.c:47
#define IOCTL_KS_METHOD
Definition: ks.h:142
NTSTATUS IKsFilter_GetFilterFromIrp(IN PIRP Irp, OUT IKsFilter **Filter)
Definition: filter.c:662
PFLT_MESSAGE_WAITER_QUEUE CONTAINING_RECORD(Csq, DEVICE_EXTENSION, IrpQueue)) -> WaiterQ.mLock) _IRQL_raises_(DISPATCH_LEVEL) VOID NTAPI FltpAcquireMessageWaiterLock(_In_ PIO_CSQ Csq, _Out_ PKIRQL Irql)
Definition: Messaging.c:560
PFILE_OBJECT FileObject
Definition: filter.c:27
PVOID ObjectType
Definition: kstypes.h:30
VOID NTAPI IKsFilter_FilterCentricWorker(IN PVOID Ctx)
Definition: filter.c:1622
PKSPIN Pin
Definition: kstypes.h:74
NTSTATUS NTAPI IKsFilter_fnAddProcessPin(IKsFilter *iface, IN PKSPROCESSPIN ProcessPin)
Definition: filter.c:511
#define STATUS_NOT_FOUND
Definition: shellext.h:67
NTSTATUS NTAPI IKsFilter_DispatchCreatePin(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: filter.c:1432
NTSTATUS NTAPI IKsFilter_fnQueryInterface(IKsFilter *iface, IN REFIID refiid, OUT PVOID *Output)
Definition: filter.c:387
KSDDKAPI NTSTATUS NTAPI KsDispatchInvalidDeviceRequest(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: irp.c:1156
#define ExInitializeWorkItem(Item, Routine, Context)
Definition: exfuncs.h:265
Definition: ks.h:672
VOID IKsFilter_RemovePin(PKSFILTER Filter, PKSPIN Pin)
Definition: filter.c:1378
if(!(yy_init))
Definition: macro.lex.yy.c:714
IN PDCB IN VBO IN ULONG IN BOOLEAN Pin
Definition: fatprocs.h:415
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
#define STATUS_PENDING
Definition: ntstatus.h:82
ULONG PossibleCount
Definition: ks.h:681
PKSFILTERFACTORY Factory
Definition: filter.c:26
const GUID IID_IUnknown
static const UCHAR Index[8]
Definition: usbohci.c:18
LONGLONG Alignment
Definition: ks.h:286
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
KSPROPERTY_SET FilterPropertySet[]
Definition: filter.c:63
_In_ ULONG _In_ ULONG _In_ ULONG Length
Definition: ntddpcm.h:101
* PFILE_OBJECT
Definition: iotypes.h:1954
DEFINE_KSPROPERTY_TOPOLOGYSET(IKsFilterTopologySet, FilterTopologyPropertyHandler)
NTSTATUS NTAPI CompleteRequest(IN PIRP Irp, IN NTSTATUS Status, IN ULONG_PTR Information)
Definition: dispatch.c:19
static IUnknown Object
Definition: main.c:512
NTSTATUS IKsFilter_CreateDescriptors(IKsFilterImpl *This, KSFILTER_DESCRIPTOR *FilterDescriptor)
Definition: filter.c:1163
VOID NTAPI IKsProcessingObject_fnReset(IKsProcessingObject *iface)
Definition: filter.c:233
KSBASIC_HEADER Header
Definition: filter.c:16
KSDDKAPI NTSTATUS NTAPI KsRegisterCountedWorker(IN WORK_QUEUE_TYPE WorkQueueType, IN PWORK_QUEUE_ITEM CountedWorkItem, OUT PKSWORKER *Worker)
Definition: worker.c:166
ASSERT((InvokeOnSuccess||InvokeOnError||InvokeOnCancel) ?(CompletionRoutine !=NULL) :TRUE)
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
const KSNODE_DESCRIPTOR NodeDescriptor[]
Definition: splitter.c:217
KSDDKAPI NTSTATUS NTAPI KsTopologyPropertyHandler(IN PIRP Irp, IN PKSPROPERTY Property, IN OUT PVOID Data, IN const KSTOPOLOGY *Topology)
Definition: topology.c:144
ULONG NTAPI IKsProcessingObject_fnAddRef(IKsProcessingObject *iface)
Definition: filter.c:108
VOID IKsFilter_AddPin(PKSFILTER Filter, PKSPIN Pin)
Definition: filter.c:1337
VOID NTAPI KeInitializeMutex(IN PKMUTEX Mutex, IN ULONG Level)
Definition: mutex.c:67
static const WCHAR L[]
Definition: oid.c:1250
#define InterlockedDecrement
Definition: armddk.h:52
PKSGATE NTAPI IKsProcessingObject_fnGetAndGate(IKsProcessingObject *iface)
Definition: filter.c:189
#define IOCTL_KS_ENABLE_EVENT
Definition: ks.h:134
BOOL NTAPI IKsFilter_fnReprepareProcessPipeSection(IKsFilter *iface, IN struct KSPROCESSPIPESECTION *PipeSection, IN PULONG Data)
Definition: filter.c:594
Definition: arc.h:85
NTSTATUS NTAPI KspCreateFilter(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN IKsFilterFactory *iface)
Definition: filter.c:1636
union KSBASIC_HEADER::@954 Next
struct KSMULTIPLE_ITEM * PKSMULTIPLE_ITEM
NTSTATUS KspHandlePropertyInstances(IN PIO_STATUS_BLOCK IoStatus, IN PKSIDENTIFIER Request, IN OUT PVOID Data, IN IKsFilterImpl *This, IN BOOL Global)
Definition: filter.c:751
Definition: typedefs.h:117
NTSYSAPI NTSTATUS WINAPI RtlStringFromGUID(REFGUID, PUNICODE_STRING)
#define PASSIVE_LEVEL
Definition: env_spec_w32.h:693
KSGATE Gate
Definition: filter.c:33
static IKsProcessingObjectVtbl vt_IKsProcessingObject
Definition: filter.c:264
const GUID KSPROPSETID_Topology
Definition: filter.c:46
Status
Definition: gdiplustypes.h:24
static IKsFilterVtbl vt_IKsFilter
Definition: filter.c:642
union KSDATAFORMAT * PKSDATARANGE
_In_ DWORD Property
Definition: setupapi.h:1545
ULONG NodeId
Definition: ks.h:2106
IN PDEVICE_OBJECT DeviceObject
Definition: fatprocs.h:1560
__drv_aliasesMem FORCEINLINE PIO_STACK_LOCATION IoGetCurrentIrpStackLocation(_In_ PIRP Irp)
Definition: iofuncs.h:2745
PFILE_OBJECT FileObject
Definition: iotypes.h:2812
#define InterlockedIncrement
Definition: armddk.h:53
KSDDKAPI PKSGATE NTAPI KsFilterGetAndGate(IN PKSFILTER Filter)
Definition: filter.c:2031
#define STATUS_BUFFER_OVERFLOW
Definition: shellext.h:61
VOID IKsFilter_AttachFilterToFilterFactory(IKsFilterImpl *This, PKSFILTERFACTORY FilterFactory)
Definition: filter.c:1513
NTSTATUS KspCreatePin(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PKSDEVICE KsDevice, IN IKsFilterFactory *FilterFactory, IN IKsFilter *Filter, IN PKSPIN_CONNECT Connect, IN KSPIN_DESCRIPTOR_EX *Descriptor)
Definition: pin.c:2283
NTSTATUS NTAPI IKsFilter_fnUnbindProcessPinsFromPipeSection(IKsFilter *iface, IN struct KSPROCESSPIPESECTION *Section)
Definition: filter.c:501
KSDDKAPI BOOLEAN NTAPI KsDispatchFastReadFailure(IN PFILE_OBJECT FileObject, IN PLARGE_INTEGER FileOffset, IN ULONG Length, IN BOOLEAN Wait, IN ULONG LockKey, OUT PVOID Buffer, OUT PIO_STATUS_BLOCK IoStatus, IN PDEVICE_OBJECT DeviceObject)
Definition: irp.c:1238
static KSDISPATCH_TABLE DispatchTable
Definition: filter.c:1147
PKSIOBJECT_HEADER ObjectHeader
Definition: filter.c:24
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
#define STATUS_NO_MATCH
Definition: ntstatus.h:737
NTSTATUS NTAPI FilterPinPropertyHandler(IN PIRP Irp, IN PKSIDENTIFIER Request, IN OUT PVOID Data)
Definition: filter.c:954
PKSFILTER Filter
Definition: kstypes.h:73
_In_ FILTER_INFORMATION_CLASS _In_ ULONG _Out_ PULONG BytesReturned
Definition: fltkernel.h:1716
ULONG NTAPI IKsProcessingObject_fnRelease(IKsProcessingObject *iface)
Definition: filter.c:118
ULONG * PinInstanceCount
Definition: filter.c:38
unsigned int * PULONG
Definition: retypes.h:1
KSDDKAPI NTSTATUS NTAPI KsFilterCreatePinFactory(IN PKSFILTER Filter, IN const KSPIN_DESCRIPTOR_EX *const InPinDescriptor, OUT PULONG PinID)
Definition: filter.c:1956
ULONG CurrentCount
Definition: ks.h:682
struct _KSPROCESSPIN_INDEXENTRY * PKSPROCESSPIN_INDEXENTRY
Definition: ks.h:3057
KSFILTER Filter
Definition: filter.c:17
#define KSSTRING_TopologyNode
Definition: ks.h:52
VOID NTAPI IKsProcessingObject_fnProcessingObjectWork(IKsProcessingObject *iface)
Definition: filter.c:131
KSDDKAPI PKSFILTER NTAPI KsGetFilterFromIrp(IN PIRP Irp)
Definition: filter.c:2106
#define DPRINT1
Definition: precomp.h:8
KSDDKAPI VOID NTAPI KsFilterAcquireProcessingMutex(IN PKSFILTER Filter)
Definition: filter.c:1836
KSDDKAPI ULONG NTAPI KsFilterGetChildPinCount(IN PKSFILTER Filter, IN ULONG PinId)
Definition: filter.c:2046
HRESULT QueryInterface([in] REFIID riid, [out, iid_is(riid)] void **ppvObject)
ULONG NTAPI IKsFilter_fnAddRef(IKsFilter *iface)
Definition: filter.c:427
KSDDKAPI VOID NTAPI KsUnregisterWorker(IN PKSWORKER Worker)
Definition: worker.c:128
#define OUT
Definition: typedefs.h:39
DEFINE_KSPROPERTY_GENEREAL_COMPONENTID(IKsFilterGeneralSet, FilterGeneralComponentIdHandler)
KSDDKAPI VOID NTAPI KsFilterAttemptProcessing(IN PKSFILTER Filter, IN BOOLEAN Asynchronous)
Definition: filter.c:1915
struct _KSPROCESSPIN_INDEXENTRY KSPROCESSPIN_INDEXENTRY
Definition: ks.h:3057
NTSTATUS NTAPI IKsFilter_fnRemoveProcessPin(IKsFilter *iface, IN PKSPROCESSPIN ProcessPin)
Definition: filter.c:545
KSDDKAPI NTSTATUS NTAPI KsAllocateObjectHeader(OUT KSOBJECT_HEADER *Header, IN ULONG ItemsCount, IN PKSOBJECT_CREATE_ITEM ItemsList OPTIONAL, IN PIRP Irp, IN KSDISPATCH_TABLE *Table)
Definition: api.c:610
#define STATUS_NOT_SUPPORTED
Definition: ntstatus.h:409
unsigned int ULONG
Definition: retypes.h:1
#define IO_NO_INCREMENT
Definition: iotypes.h:565
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
#define UNIMPLEMENTED
Definition: debug.h:114
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:261
const GUID KSPROPSETID_General
Definition: filter.c:48
struct KSIDENTIFIER * PKSPROPERTY
PKSFILTERFACTORY FilterFactory
Definition: kstypes.h:72
NTSTATUS NTAPI IKsFilter_DispatchDeviceIoControl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: filter.c:1010
#define KSPROPERTY_TYPE_TOPOLOGY
Definition: dmksctrl.h:53
KMUTEX ControlMutex
Definition: filter.c:28
_Must_inspect_result_ _Out_writes_to_ DataLength PHIDP_DATA _Inout_ PULONG DataLength
Definition: hidpi.h:333
struct _NAMED_PIPE_CREATE_PARAMETERS * Parameters
Definition: iotypes.h:2771
NTSTATUS NTAPI FilterTopologyPropertyHandler(IN PIRP Irp, IN PKSIDENTIFIER Request, IN OUT PVOID Data)
Definition: filter.c:901
return STATUS_SUCCESS
Definition: btrfs.c:2725
KSDDKAPI VOID NTAPI KsFilterRegisterPowerCallbacks(IN PKSFILTER Filter, IN PFNKSFILTERPOWER Sleep OPTIONAL, IN PFNKSFILTERPOWER Wake OPTIONAL)
Definition: filter.c:2089
KSDDKAPI NTSTATUS NTAPI KsFilterAddTopologyConnections(IN PKSFILTER Filter, IN ULONG NewConnectionsCount, IN const KSTOPOLOGY_CONNECTION *const NewTopologyConnections)
Definition: filter.c:1865
NTSTATUS NTAPI IKsControl_fnKsEvent(IKsControl *iface, IN PKSEVENT Event OPTIONAL, IN ULONG EventLength, IN OUT PVOID EventData, IN ULONG DataLength, OUT ULONG *BytesReturned)
Definition: filter.c:353
ULONG NTAPI IKsControl_fnAddRef(IKsControl *iface)
Definition: filter.c:298
VOID NTAPI IKsProcessingObject_fnProcess(IKsProcessingObject *iface, IN BOOLEAN Asynchronous)
Definition: filter.c:200
NTSTATUS NTAPI IKsControl_fnQueryInterface(IKsControl *iface, IN REFIID refiid, OUT PVOID *Output)
Definition: filter.c:280
KMUTEX ProcessingMutex
Definition: filter.c:29
struct _BEEP_DEVICE_EXTENSION * PDEVICE_EXTENSION
LONGLONG QuadPart
Definition: typedefs.h:112
KSDDKAPI NTSTATUS NTAPI KspPinPropertyHandler(IN PIRP Irp, IN PKSPROPERTY Property, IN OUT PVOID Data, IN ULONG DescriptorsCount, IN const KSPIN_DESCRIPTOR *Descriptors, IN ULONG DescriptorSize)
Definition: connectivity.c:324
KSRESET
Definition: ks.h:1256
NTSTATUS NTAPI IKsProcessingObject_fnQueryInterface(IKsProcessingObject *iface, IN REFIID refiid, OUT PVOID *Output)
Definition: filter.c:90
VOID NTAPI IKsFilter_fnRegisterForCopyCallbacks(IKsFilter *iface, IKsQueue *Queue, BOOL Register)
Definition: filter.c:624
struct KSP_NODE * PKSP_NODE
PULONG MinorVersion OPTIONAL
Definition: CrossNt.h:68