ReactOS 0.4.15-dev-7961-gdcf9eb0
adapter.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/api.cpp
5 * PURPOSE: Port Class driver / DriverEntry and IRP handlers
6 * PROGRAMMER: Andrew Greenwood
7 * Johannes Anderwald
8 * HISTORY:
9 * 27 Jan 07 Created
10 */
11
12#include "private.hpp"
13
14#define NDEBUG
15#include <debug.h>
16
17//
18// This is called from DriverEntry so that PortCls can take care of some
19// IRPs and map some others to the main KS driver. In most cases this will
20// be the first function called by an audio driver.
21//
22// First 2 parameters are from DriverEntry.
23//
24// The AddDevice parameter is a driver-supplied pointer to a function which
25// typically then calls PcAddAdapterDevice (see below.)
26//
31 IN PUNICODE_STRING RegistryPathName,
33{
34 DPRINT("PcInitializeAdapterDriver\n");
36
37 // Our IRP handlers
38 DPRINT("Setting IRP handlers\n");
40 DriverObject->MajorFunction[IRP_MJ_PNP] = PcDispatchIrp;
41 DriverObject->MajorFunction[IRP_MJ_POWER] = PcDispatchIrp;
44
45 // The driver-supplied AddDevice
46 DriverObject->DriverExtension->AddDevice = AddDevice;
47
48 // KS handles these
49 DPRINT("Setting KS function handlers\n");
57
58 DPRINT("PortCls has finished initializing the adapter driver\n");
59
60 return STATUS_SUCCESS;
61}
62
63//
64// Typically called by a driver's AddDevice function, which is set when
65// calling PcInitializeAdapterDriver. This performs some common driver
66// operations, such as creating a device extension.
67//
68// The StartDevice parameter is a driver-supplied function which gets
69// called in response to IRP_MJ_PNP / IRP_MN_START_DEVICE.
70//
77 IN ULONG MaxObjects,
78 IN ULONG DeviceExtensionSize)
79{
82 PDEVICE_OBJECT PrevDeviceObject;
83 PPCLASS_DEVICE_EXTENSION portcls_ext = NULL;
84
85 DPRINT("PcAddAdapterDevice called\n");
87
89 {
91 }
92
93 // check if the DeviceExtensionSize is provided
94 if ( DeviceExtensionSize < PORT_CLASS_DEVICE_EXTENSION_SIZE )
95 {
96 // driver does not need a device extension
97 if ( DeviceExtensionSize != 0 )
98 {
99 // DeviceExtensionSize must be zero
101 }
102 // set size to our extension size
103 DeviceExtensionSize = PORT_CLASS_DEVICE_EXTENSION_SIZE;
104 }
105
106 // create the device
108 DeviceExtensionSize,
109 NULL,
112 FALSE,
113 &fdo);
114
115 if (!NT_SUCCESS(status))
116 {
117 DPRINT("IoCreateDevice() failed with status 0x%08lx\n", status);
118 return status;
119 }
120
121 // Obtain the new device extension
122 portcls_ext = (PPCLASS_DEVICE_EXTENSION) fdo->DeviceExtension;
123 // initialize the device extension
124 RtlZeroMemory(portcls_ext, DeviceExtensionSize);
125 // allocate create item
126 portcls_ext->CreateItems = (PKSOBJECT_CREATE_ITEM)AllocateItem(NonPagedPool, MaxObjects * sizeof(KSOBJECT_CREATE_ITEM), TAG_PORTCLASS);
127
128 if (!portcls_ext->CreateItems)
129 {
130 // not enough resources
132 goto cleanup;
133 }
134
135 // store max subdevice count
136 portcls_ext->MaxSubDevices = MaxObjects;
137 // store the physical device object
139 // set up the start device function
140 portcls_ext->StartDevice = StartDevice;
141 // initialize timer lock
142 KeInitializeSpinLock(&portcls_ext->TimerListLock);
143 // initialize timer list
144 InitializeListHead(&portcls_ext->TimerList);
145 // initialize io timer
147 // start the io timer
148 IoStartTimer(fdo);
149
150 // set io flags
152 // clear initializing flag
153 fdo->Flags &= ~ DO_DEVICE_INITIALIZING;
154
155 // allocate the device header
156 status = KsAllocateDeviceHeader(&portcls_ext->KsDeviceHeader, MaxObjects, portcls_ext->CreateItems);
157 // did we succeed
158 if (!NT_SUCCESS(status))
159 {
160 goto cleanup;
161 }
162
163 // attach device to device stack
164 PrevDeviceObject = IoAttachDeviceToDeviceStack(fdo, PhysicalDeviceObject);
165 // did we succeed
166 if (PrevDeviceObject)
167 {
168 // store the device object in the device header
169 //KsSetDevicePnpBaseObject(portcls_ext->KsDeviceHeader, fdo, PrevDeviceObject);
170 portcls_ext->PrevDeviceObject = PrevDeviceObject;
171 }
172 else
173 {
174 // return error code
176 goto cleanup;
177 }
178
179 // register shutdown notification
181
182 return status;
183
184cleanup:
185
186 if (portcls_ext->KsDeviceHeader)
187 {
188 // free the device header
190 }
191
192 if (portcls_ext->CreateItems)
193 {
194 // free previously allocated create items
195 FreeItem(portcls_ext->CreateItems, TAG_PORTCLASS);
196 }
197
198 // delete created fdo
199 IoDeleteDevice(fdo);
200
201 return status;
202}
203
205NTAPI
208 IN PWCHAR Name,
210{
211 PPCLASS_DEVICE_EXTENSION DeviceExt;
213 ISubdevice *SubDevice;
215 PSUBDEVICE_DESCRIPTOR SubDeviceDescriptor;
216 ULONG Index;
217 UNICODE_STRING RefName;
218 PSYMBOLICLINK_ENTRY SymEntry;
219
220 DPRINT("PcRegisterSubdevice DeviceObject %p Name %S Unknown %p\n", DeviceObject, Name, Unknown);
221
223
224 // check if all parameters are valid
225 if (!DeviceObject || !Name || !Unknown)
226 {
227 DPRINT("PcRegisterSubdevice invalid parameter\n");
229 }
230
231 // get device extension
232 DeviceExt = (PPCLASS_DEVICE_EXTENSION)DeviceObject->DeviceExtension;
233
234 if (!DeviceExt)
235 {
236 // should not happen
238 return STATUS_UNSUCCESSFUL;
239 }
240
241 // look up our undocumented interface
242 Status = Unknown->QueryInterface(IID_ISubdevice, (LPVOID*)&SubDevice);
243 if (!NT_SUCCESS(Status))
244 {
245 DPRINT("No ISubdevice interface\n");
246 // the provided port driver doesnt support ISubdevice
248 }
249
250 // get the subdevice descriptor
251 Status = SubDevice->GetDescriptor(&SubDeviceDescriptor);
252 if (!NT_SUCCESS(Status))
253 {
254 DPRINT("Failed to get subdevice descriptor %x\n", Status);
255 SubDevice->Release();
256 return STATUS_UNSUCCESSFUL;
257 }
258
259 // add an create item to the device header
261 if (!NT_SUCCESS(Status))
262 {
263 // failed to attach
264 SubDevice->Release();
265 DPRINT("KsAddObjectCreateItemToDeviceHeader failed with %x\n", Status);
266 return Status;
267 }
268
269 // initialize reference string
270 RtlInitUnicodeString(&RefName, Name);
271 RtlInitUnicodeString(&SubDeviceDescriptor->RefString, Name);
272
273 for(Index = 0; Index < SubDeviceDescriptor->InterfaceCount; Index++)
274 {
275 // FIXME
276 // check if reference string with that name already exists
277
279 &SubDeviceDescriptor->Interfaces[Index],
280 &RefName,
282
283 if (NT_SUCCESS(Status))
284 {
285 // activate device interface
287 // allocate symbolic link entry
289 if (SymEntry)
290 {
291 // initialize symbolic link item
293 // store item
294 InsertTailList(&SubDeviceDescriptor->SymbolicLinkList, &SymEntry->Entry);
295 }
296 else
297 {
298 // allocating failed
300 }
301 }
302 }
303
304 // release SubDevice reference
305 SubDevice->Release();
306
307 return STATUS_SUCCESS;
308}
NTSTATUS NTAPI PcAddAdapterDevice(IN PDRIVER_OBJECT DriverObject, IN PDEVICE_OBJECT PhysicalDeviceObject, IN PCPFNSTARTDEVICE StartDevice, IN ULONG MaxObjects, IN ULONG DeviceExtensionSize)
Definition: adapter.cpp:73
NTSTATUS NTAPI PcInitializeAdapterDriver(IN PDRIVER_OBJECT DriverObject, IN PUNICODE_STRING RegistryPathName, IN PDRIVER_ADD_DEVICE AddDevice)
Definition: adapter.cpp:29
NTSTATUS NTAPI PcRegisterSubdevice(IN PDEVICE_OBJECT DeviceObject, IN PWCHAR Name, IN PUNKNOWN Unknown)
Definition: adapter.cpp:206
struct SYMBOLICLINK_ENTRY * PSYMBOLICLINK_ENTRY
LONG NTSTATUS
Definition: precomp.h:26
PDEVICE_OBJECT PhysicalDeviceObject
Definition: btrfs_drv.h:1157
#define FILE_DEVICE_SECURE_OPEN
Definition: cdrw_usr.h:46
#define IRP_MJ_PNP
Definition: cdrw_usr.h:52
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define NT_SUCCESS(StatCode)
Definition: apphelp.c:32
static void cleanup(void)
Definition: main.c:1335
KSDDKAPI NTSTATUS NTAPI KsAllocateDeviceHeader(OUT KSDEVICE_HEADER *OutHeader, IN ULONG ItemsCount, IN PKSOBJECT_CREATE_ITEM ItemsList OPTIONAL)
Definition: api.c:522
KSDDKAPI NTSTATUS NTAPI KsAddObjectCreateItemToDeviceHeader(IN KSDEVICE_HEADER DevHeader, IN PDRIVER_DISPATCH Create, IN PVOID Context, IN PWCHAR ObjectClass, IN PSECURITY_DESCRIPTOR SecurityDescriptor)
Definition: api.c:798
KSDDKAPI VOID NTAPI KsFreeDeviceHeader(IN KSDEVICE_HEADER DevHeader)
Definition: api.c:590
KSDDKAPI NTSTATUS NTAPI KsSetMajorFunctionHandler(IN PDRIVER_OBJECT DriverObject, IN ULONG MajorFunction)
Definition: irp.c:2050
VOID NTAPI PcIoTimerRoutine(IN PDEVICE_OBJECT DeviceObject, IN PVOID Context)
Definition: api.cpp:46
#define InsertTailList(ListHead, Entry)
#define PASSIVE_LEVEL
Definition: env_spec_w32.h:693
#define DO_DIRECT_IO
Definition: env_spec_w32.h:396
#define NonPagedPool
Definition: env_spec_w32.h:307
#define InitializeListHead(ListHead)
Definition: env_spec_w32.h:944
#define KeInitializeSpinLock(sl)
Definition: env_spec_w32.h:604
Status
Definition: gdiplustypes.h:25
@ Unknown
Definition: i8042prt.h:114
NTSYSAPI void WINAPI DbgBreakPoint(void)
NTSTATUS NTAPI IoInitializeTimer(IN PDEVICE_OBJECT DeviceObject, IN PIO_TIMER_ROUTINE TimerRoutine, IN PVOID Context)
Definition: iotimer.c:92
VOID NTAPI IoStartTimer(IN PDEVICE_OBJECT DeviceObject)
Definition: iotimer.c:133
NTSTATUS NTAPI PcDispatchIrp(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
Definition: irp.cpp:409
PVOID AllocateItem(IN POOL_TYPE PoolType, IN SIZE_T NumberOfBytes)
Definition: misc.c:29
VOID FreeItem(IN PVOID Item)
Definition: misc.c:37
if(dx< 0)
Definition: linetemp.h:194
#define FILE_AUTOGENERATED_DEVICE_NAME
Definition: iotypes.h:138
static BOOL StartDevice(IN HDEVINFO DeviceInfoSet, IN PSP_DEVINFO_DATA DevInfoData OPTIONAL, IN BOOL bEnable, IN DWORD HardwareProfile OPTIONAL, OUT BOOL *bNeedReboot OPTIONAL)
Definition: wizard.c:173
NTSYSAPI VOID NTAPI RtlInitUnicodeString(PUNICODE_STRING DestinationString, PCWSTR SourceString)
NTSYSAPI VOID NTAPI RtlFreeUnicodeString(PUNICODE_STRING UnicodeString)
PDEVICE_OBJECT NTAPI IoAttachDeviceToDeviceStack(IN PDEVICE_OBJECT SourceDevice, IN PDEVICE_OBJECT TargetDevice)
Definition: device.c:966
NTSTATUS NTAPI IoCreateDevice(IN PDRIVER_OBJECT DriverObject, IN ULONG DeviceExtensionSize, IN PUNICODE_STRING DeviceName, IN DEVICE_TYPE DeviceType, IN ULONG DeviceCharacteristics, IN BOOLEAN Exclusive, OUT PDEVICE_OBJECT *DeviceObject)
Definition: device.c:1031
NTSTATUS NTAPI IoRegisterShutdownNotification(PDEVICE_OBJECT DeviceObject)
Definition: device.c:1694
VOID NTAPI IoDeleteDevice(IN PDEVICE_OBJECT DeviceObject)
Definition: device.c:1251
NTSTATUS NTAPI IoRegisterDeviceInterface(IN PDEVICE_OBJECT PhysicalDeviceObject, IN CONST GUID *InterfaceClassGuid, IN PUNICODE_STRING ReferenceString OPTIONAL, OUT PUNICODE_STRING SymbolicLinkName)
Definition: deviface.c:955
NTSTATUS NTAPI IoSetDeviceInterfaceState(IN PUNICODE_STRING SymbolicLinkName, IN BOOLEAN Enable)
Definition: deviface.c:1311
DRIVER_ADD_DEVICE AddDevice
Definition: parport.h:72
NTSTATUS NTAPI PcCreateItemDispatch(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp)
#define PORT_CLASS_DEVICE_EXTENSION_SIZE
Definition: portcls.h:160
NTSTATUS(NTAPI * PCPFNSTARTDEVICE)(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp, IN PRESOURCELIST ResourceList)
Definition: portcls.h:2304
#define PC_ASSERT_IRQL_EQUAL(x)
Definition: private.hpp:31
struct PCLASS_DEVICE_EXTENSION * PPCLASS_DEVICE_EXTENSION
#define TAG_PORTCLASS
Definition: private.hpp:24
#define FILE_DEVICE_KS
Definition: winioctl.h:153
#define IRP_MJ_CLOSE
Definition: rdpdr.c:45
#define IRP_MJ_READ
Definition: rdpdr.c:46
#define IRP_MJ_DEVICE_CONTROL
Definition: rdpdr.c:52
#define IRP_MJ_WRITE
Definition: rdpdr.c:47
#define IRP_MJ_CREATE
Definition: rdpdr.c:44
#define STATUS_SUCCESS
Definition: shellext.h:65
#define DPRINT
Definition: sndvol32.h:71
KSDEVICE_HEADER KsDeviceHeader
Definition: private.hpp:401
PDEVICE_OBJECT PhysicalDeviceObject
Definition: private.hpp:402
PDEVICE_OBJECT PrevDeviceObject
Definition: private.hpp:403
KSOBJECT_CREATE_ITEM * CreateItems
Definition: private.hpp:408
PCPFNSTARTDEVICE StartDevice
Definition: private.hpp:404
KSPIN_LOCK TimerListLock
Definition: private.hpp:413
UNICODE_STRING RefString
Definition: interfaces.hpp:221
LIST_ENTRY SymbolicLinkList
Definition: interfaces.hpp:219
Definition: interfaces.hpp:174
LIST_ENTRY Entry
Definition: interfaces.hpp:175
UNICODE_STRING SymbolicLink
Definition: interfaces.hpp:176
PVOID DeviceExtension
Definition: env_spec_w32.h:418
Definition: ps.c:97
#define NTAPI
Definition: typedefs.h:36
#define RtlZeroMemory(Destination, Length)
Definition: typedefs.h:262
#define IN
Definition: typedefs.h:39
uint16_t * PWCHAR
Definition: typedefs.h:56
uint32_t ULONG
Definition: typedefs.h:59
#define STATUS_INVALID_PARAMETER
Definition: udferr_usr.h:135
#define STATUS_UNSUCCESSFUL
Definition: udferr_usr.h:132
#define STATUS_INSUFFICIENT_RESOURCES
Definition: udferr_usr.h:158
_In_ WDFCOLLECTION _In_ ULONG Index
_In_ PDEVICE_OBJECT DeviceObject
Definition: wdfdevice.h:2055
_Must_inspect_result_ _In_ WDFDEVICE _In_ PCUNICODE_STRING SymbolicLinkName
Definition: wdfdevice.h:3739
_Must_inspect_result_ _In_ PDRIVER_OBJECT DriverObject
Definition: wdfdriver.h:213
DRIVER_ADD_DEVICE * PDRIVER_ADD_DEVICE
Definition: iotypes.h:2216
#define IRP_MJ_QUERY_SECURITY
#define DO_POWER_PAGABLE
#define IRP_MJ_SYSTEM_CONTROL
#define IRP_MJ_FLUSH_BUFFERS
#define IRP_MJ_SHUTDOWN
#define IRP_MJ_POWER
#define IRP_MJ_SET_SECURITY