ReactOS  0.4.15-dev-4916-gd519b11
service_group.cpp
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/wdm/audio/backpln/portcls/service_group.cpp
5  * PURPOSE: ServiceGroup object implementation
6  * PROGRAMMER: Johannes Anderwald
7  */
8 
9 #include "private.hpp"
10 
11 #ifndef YDEBUG
12 #define NDEBUG
13 #endif
14 
15 #include <debug.h>
16 
17 VOID
18 NTAPI
20  IN struct _KDPC *Dpc,
24  );
25 
26 typedef struct
27 {
31 
32 class CServiceGroup : public CUnknownImpl<IServiceGroup>
33 {
34 public:
36 
38  CServiceGroup(IUnknown * OuterUnknown);
39  virtual ~CServiceGroup() {}
40 
41 protected:
42 
44 
49 
51 };
52 
53 
54 
55 //---------------------------------------------------------------
56 // IUnknown methods
57 //
58 
59 
61 NTAPI
63  IN REFIID refiid,
64  OUT PVOID* Output)
65 {
67 
68  if (IsEqualGUIDAligned(refiid, IID_IServiceGroup) ||
69  IsEqualGUIDAligned(refiid, IID_IServiceSink) ||
71  {
72  *Output = PVOID(PSERVICEGROUP(this));
73  PUNKNOWN(*Output)->AddRef();
74  return STATUS_SUCCESS;
75  }
76 
78  {
79  DPRINT1("CServiceGroup::QueryInterface no interface!!! iface %S\n", GuidString.Buffer);
81  }
82 
83  return STATUS_UNSUCCESSFUL;
84 }
85 //---------------------------------------------------------------
86 // IServiceSink methods
87 //
88 
90 {
91  // initialize dpc
93 
94  // set highest importance
96 
97  // initialize service group list lock
99 
100  // initialize service group list
102 }
103 
104 VOID
105 NTAPI
106 CServiceGroup::RequestService()
107 {
108  KIRQL OldIrql;
109 
110  DPRINT("CServiceGroup::RequestService() Dpc at Level %u\n", KeGetCurrentIrql());
111 
112  if (m_TimerInitialized)
113  {
115 
116  // no due time
117  DueTime.QuadPart = 0LL;
118 
119  // delayed service requested
121  }
122  else
123  {
124  // check current irql
126  {
127  //insert dpc to queue
129  }
130  else
131  {
132  // raise irql to dispatch level to make dpc fire immediately
134  // insert dpc to queue
136  // lower irql to old level
138  }
139  }
140 }
141 
142 //---------------------------------------------------------------
143 // IServiceGroup methods
144 //
145 
146 NTSTATUS
147 NTAPI
148 CServiceGroup::AddMember(
149  IN PSERVICESINK pServiceSink)
150 {
152  KIRQL OldLevel;
153 
154  // sanity check
156 
157  // allocate service sink entry
159  if (!Entry)
160  {
161  // out of memory
163  }
164 
165  // initialize service sink entry
166  Entry->pServiceSink = pServiceSink;
167  // increment reference count
168  pServiceSink->AddRef();
169 
170  // acquire service group list lock
171  KeAcquireSpinLock(&m_Lock, &OldLevel);
172 
173  // insert into service sink list
175 
176  // release service group list lock
177  KeReleaseSpinLock(&m_Lock, OldLevel);
178 
179  return STATUS_SUCCESS;
180 }
181 
182 VOID
183 NTAPI
184 CServiceGroup::RemoveMember(
185  IN PSERVICESINK pServiceSink)
186 {
187  PLIST_ENTRY CurEntry;
189  KIRQL OldLevel;
190 
191  // sanity check
193 
194  // acquire service group list lock
195  KeAcquireSpinLock(&m_Lock, &OldLevel);
196 
197  // grab first entry
198  CurEntry = m_ServiceSinkHead.Flink;
199 
200  // loop list until the passed entry is found
201  while (CurEntry != &m_ServiceSinkHead)
202  {
203  // grab entry
205 
206  // check if it matches the passed entry
207  if (Entry->pServiceSink == pServiceSink)
208  {
209  // remove entry from list
211 
212  // release service sink reference
213  pServiceSink->Release();
214 
215  // free service sink entry
217 
218  // leave loop
219  break;
220  }
221  // move to next entry
222  CurEntry = CurEntry->Flink;
223  }
224 
225  // release service group list lock
226  KeReleaseSpinLock(&m_Lock, OldLevel);
227 
228 }
229 
230 VOID
231 NTAPI
233  IN struct _KDPC *Dpc,
237  )
238 {
239  PLIST_ENTRY CurEntry;
242 
243  // acquire service group list lock
245 
246  // grab first entry
247  CurEntry = This->m_ServiceSinkHead.Flink;
248 
249  // loop the list and call the attached service sink/group
250  while (CurEntry != &This->m_ServiceSinkHead)
251  {
252  //grab current entry
254 
255  // call service sink/group
256  Entry->pServiceSink->RequestService();
257 
258  // move to next entry
259  CurEntry = CurEntry->Flink;
260  }
261 
262  // release service group list lock
264 }
265 
266 VOID
267 NTAPI
268 CServiceGroup::SupportDelayedService()
269 {
271 
272  // initialize the timer
274 
275  // use the timer to perform service requests
277 }
278 
279 VOID
280 NTAPI
281 CServiceGroup::RequestDelayedService(
282  IN ULONGLONG ullDelay)
283 {
285 
286  // sanity check
289 
290  DueTime.QuadPart = ullDelay;
291 
292  // set the timer
294 }
295 
296 VOID
297 NTAPI
298 CServiceGroup::CancelDelayedService()
299 {
302 
303  // cancel the timer
305 }
306 
307 NTSTATUS
308 NTAPI
310  OUT PSERVICEGROUP* OutServiceGroup,
311  IN PUNKNOWN OuterUnknown OPTIONAL)
312 {
315 
316  DPRINT("PcNewServiceGroup entered\n");
317 
318  //FIXME support aggregation
319  PC_ASSERT(OuterUnknown == NULL);
320 
321  // allocate a service group object
322  This = new(NonPagedPool, TAG_PORTCLASS)CServiceGroup(OuterUnknown);
323 
324  if (!This)
325  {
326  // out of memory
328  }
329 
330  // request IServiceSink interface
331  Status = This->QueryInterface(IID_IServiceSink, (PVOID*)OutServiceGroup);
332 
333  if (!NT_SUCCESS(Status))
334  {
335  // failed to acquire service sink interface
336  delete This;
337  return Status;
338  }
339 
340  // done
341  return Status;
342 }
#define KeGetCurrentIrql()
Definition: env_spec_w32.h:706
IServiceGroup * PSERVICEGROUP
Definition: portcls.h:614
static PWSTR GuidString
Definition: apphelp.c:93
#define IN
Definition: typedefs.h:39
VOID NTAPI IServiceGroupDpc(IN struct _KDPC *Dpc, IN PVOID DeferredContext, IN PVOID SystemArgument1, IN PVOID SystemArgument2)
#define REFIID
Definition: guiddef.h:118
#define LL
Definition: tui.h:150
BOOLEAN NTAPI KeSetTimer(IN OUT PKTIMER Timer, IN LARGE_INTEGER DueTime, IN PKDPC Dpc OPTIONAL)
Definition: timerobj.c:281
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
LIST_ENTRY Entry
_Must_inspect_result_ _In_ PWDF_DPC_CONFIG _In_ PWDF_OBJECT_ATTRIBUTES _Out_ WDFDPC * Dpc
Definition: wdfdpc.h:107
struct _Entry Entry
Definition: kefuncs.h:629
#define TRUE
Definition: types.h:120
IUnknown * PUNKNOWN
Definition: com_apitest.h:45
#define TAG_PORTCLASS
Definition: private.hpp:24
PVOID AllocateItem(IN POOL_TYPE PoolType, IN SIZE_T NumberOfBytes)
Definition: misc.c:30
VOID NTAPI KeAcquireSpinLockAtDpcLevel(IN PKSPIN_LOCK SpinLock)
Definition: spinlock.c:198
BOOLEAN NTAPI KeInsertQueueDpc(IN PKDPC Dpc, IN PVOID SystemArgument1, IN PVOID SystemArgument2)
Definition: dpc.c:725
LONG NTSTATUS
Definition: precomp.h:26
VOID NTAPI KeAcquireSpinLock(PKSPIN_LOCK SpinLock, PKIRQL OldIrql)
Definition: spinlock.c:50
VOID NTAPI KeSetImportanceDpc(IN PKDPC Dpc, IN KDPC_IMPORTANCE Importance)
Definition: dpc.c:958
IServiceSink * PSERVICESINK
Definition: portcls.h:569
LIST_ENTRY m_ServiceSinkHead
#define InsertTailList(ListHead, Entry)
#define PC_ASSERT(exp)
Definition: private.hpp:26
#define IsEqualGUIDAligned(guid1, guid2)
Definition: wdm.template.h:235
FORCEINLINE BOOLEAN RemoveEntryList(_In_ PLIST_ENTRY Entry)
Definition: rtlfuncs.h:105
UCHAR KIRQL
Definition: env_spec_w32.h:591
VOID FreeItem(IN PVOID Item)
Definition: misc.c:43
NTSTATUS(* NTAPI)(IN PFILE_FULL_EA_INFORMATION EaBuffer, IN ULONG EaLength, OUT PULONG ErrorOffset)
Definition: IoEaTest.cpp:117
unsigned int BOOL
Definition: ntddk_ex.h:94
Entry(ENTRY_TYPE etype)
Definition: entries.cpp:35
#define STDMETHODIMP
Definition: basetyps.h:43
CServiceGroup(IUnknown *OuterUnknown)
FORCEINLINE VOID KeInitializeSpinLock(_Out_ PKSPIN_LOCK SpinLock)
Definition: kefuncs.h:240
VOID NTAPI KeInitializeTimer(OUT PKTIMER Timer)
Definition: timerobj.c:233
void * PVOID
Definition: retypes.h:9
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
IN PSERVICESINK pServiceSink
Status
Definition: gdiplustypes.h:24
_In_opt_ PVOID _In_opt_ PVOID SystemArgument1
Definition: ketypes.h:675
struct _LIST_ENTRY * Flink
Definition: typedefs.h:121
BOOLEAN NTAPI KeCancelTimer(IN OUT PKTIMER Timer)
Definition: timerobj.c:206
KSPIN_LOCK m_Lock
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
uint64_t ULONGLONG
Definition: typedefs.h:67
const GUID IID_IUnknown
VOID NTAPI KeReleaseSpinLockFromDpcLevel(IN PKSPIN_LOCK SpinLock)
Definition: spinlock.c:221
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
#define PC_ASSERT_IRQL_EQUAL(x)
Definition: private.hpp:31
ULONG AddRef()
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
_Requires_lock_held_ Interrupt _Releases_lock_ Interrupt _In_ _IRQL_restores_ KIRQL OldIrql
Definition: kefuncs.h:792
Definition: ketypes.h:687
Definition: arc.h:85
Definition: typedefs.h:119
#define PASSIVE_LEVEL
Definition: env_spec_w32.h:693
_In_opt_ PVOID _In_opt_ PVOID _In_opt_ PVOID SystemArgument2
Definition: ketypes.h:675
#define DISPATCH_LEVEL
Definition: env_spec_w32.h:696
IN PVOID IN PVOID IN USHORT IN USHORT IN PINTERFACE Interface
Definition: pci.h:361
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
ULONG KSPIN_LOCK
Definition: env_spec_w32.h:72
NTSYSAPI NTSTATUS WINAPI RtlStringFromGUID(REFGUID, PUNICODE_STRING)
#define NULL
Definition: types.h:112
#define KeReleaseSpinLock(sl, irql)
Definition: env_spec_w32.h:627
VOID NTAPI KeRaiseIrql(KIRQL NewIrql, PKIRQL OldIrql)
Definition: spinlock.c:27
_In_ WDFTIMER _In_ LONGLONG DueTime
Definition: wdftimer.h:187
#define DPRINT1
Definition: precomp.h:8
#define OUT
Definition: typedefs.h:40
struct GROUP_ENTRY * PGROUP_ENTRY
NTSTATUS NTAPI PcNewServiceGroup(OUT PSERVICEGROUP *OutServiceGroup, IN PUNKNOWN OuterUnknown OPTIONAL)
virtual ~CServiceGroup()
#define STATUS_SUCCESS
Definition: shellext.h:65
#define DPRINT
Definition: sndvol32.h:71
VOID NTAPI KeLowerIrql(KIRQL NewIrql)
Definition: spinlock.c:39
VOID NTAPI KeInitializeDpc(IN PKDPC Dpc, IN PKDEFERRED_ROUTINE DeferredRoutine, IN PVOID DeferredContext)
Definition: dpc.c:712
STDMETHODIMP QueryInterface(REFIID InterfaceId, PVOID *Interface)
base of all file and directory entries
Definition: entries.h:82
#define PC_ASSERT_IRQL(x)
Definition: private.hpp:30
friend VOID NTAPI IServiceGroupDpc(IN struct _KDPC *Dpc, IN PVOID DeferredContext, IN PVOID SystemArgument1, IN PVOID SystemArgument2)
PULONG MinorVersion OPTIONAL
Definition: CrossNt.h:68
_In_opt_ PVOID DeferredContext
Definition: ketypes.h:675