2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS Kernel Streaming
4 * FILE: drivers/ksfilter/swenum/swenum.c
5 * PURPOSE: KS Allocator functions
6 * PROGRAMMER: Johannes Anderwald
12 const GUID KSMEDIUMSETID_Standard
= {0x4747B320L
, 0x62CE, 0x11CF, {0xA5, 0xD6, 0x28, 0xDB, 0x04, 0xC1, 0x00, 0x00}};
17 IN PDEVICE_OBJECT DeviceObject
,
20 NTSTATUS Status
, PnpStatus
;
22 PIO_STACK_LOCATION IoStack
;
23 PDEVICE_OBJECT PnpDeviceObject
= NULL
;
25 /* get current stack location */
26 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
28 /* check if the device object is a child device */
29 Status
= KsIsBusEnumChildDevice(DeviceObject
, &ChildDevice
);
31 /* get bus enum pnp object */
32 PnpStatus
= KsGetBusEnumPnpDeviceObject(DeviceObject
, &PnpDeviceObject
);
34 /* check for success */
35 if (!NT_SUCCESS(Status
) || !NT_SUCCESS(PnpStatus
))
37 /* start next power irp */
38 PoStartNextPowerIrp(Irp
);
40 /* just complete the irp */
41 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
43 /* complete the irp */
44 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
47 return STATUS_SUCCESS
;
50 if (IoStack
->MinorFunction
== IRP_MN_SET_POWER
|| IoStack
->MinorFunction
== IRP_MN_QUERY_POWER
)
53 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
58 /* forward to pnp device object */
59 PoStartNextPowerIrp(Irp
);
61 /* skip current location */
62 IoSkipCurrentIrpStackLocation(Irp
);
65 return PoCallDriver(PnpDeviceObject
, Irp
);
68 /* start next power irp */
69 PoStartNextPowerIrp(Irp
);
71 /* just complete the irp */
72 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
74 /* complete the irp */
75 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
78 return STATUS_SUCCESS
;
84 IN PDEVICE_OBJECT DeviceObject
,
89 PIO_STACK_LOCATION IoStack
;
90 PDEVICE_OBJECT PnpDeviceObject
= NULL
;
92 /* get current stack location */
93 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
95 /* check if the device object is a child device */
96 Status
= KsIsBusEnumChildDevice(DeviceObject
, &ChildDevice
);
98 /* check for success */
99 if (!NT_SUCCESS(Status
))
102 Irp
->IoStatus
.Status
= Status
;
103 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
107 DPRINT("SwDispatchPnp ChildDevice %u Request %x\n", ChildDevice
, IoStack
->MinorFunction
);
109 /* let ks handle it */
110 Status
= KsServiceBusEnumPnpRequest(DeviceObject
, Irp
);
112 /* check if the request was for a pdo */
115 if (Status
!= STATUS_NOT_SUPPORTED
)
118 Irp
->IoStatus
.Status
= Status
;
121 /* complete request */
122 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
128 DPRINT("SwDispatchPnp KsServiceBusEnumPnpRequest Status %x\n", Status
);
130 if (NT_SUCCESS(Status
))
132 /* invalid request or not supported */
133 Irp
->IoStatus
.Status
= Status
;
134 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
138 /* get bus enum pnp object */
139 Status
= KsGetBusEnumPnpDeviceObject(DeviceObject
, &PnpDeviceObject
);
141 DPRINT("SwDispatchPnp KsGetBusEnumPnpDeviceObject Status %x\n", Status
);
143 /* check for success */
144 if (!NT_SUCCESS(Status
))
146 /* failed to get pnp object */
147 Irp
->IoStatus
.Status
= STATUS_NOT_SUPPORTED
;
148 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
149 return STATUS_NOT_SUPPORTED
;
153 ASSERT(PnpDeviceObject
);
155 /* get current stack location */
156 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
158 if (IoStack
->MinorFunction
== IRP_MN_REMOVE_DEVICE
)
160 /* delete the device */
161 IoDeleteDevice(DeviceObject
);
165 if (IoStack
->MinorFunction
== IRP_MN_QUERY_RESOURCES
|| IoStack
->MinorFunction
== IRP_MN_QUERY_RESOURCE_REQUIREMENTS
)
167 /* no resources required */
168 Irp
->IoStatus
.Information
= 0;
169 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
171 /* skip current location */
172 IoSkipCurrentIrpStackLocation(Irp
);
174 /* call the pnp device object */
175 return IoCallDriver(PnpDeviceObject
, Irp
);
178 if (IoStack
->MajorFunction
== IRP_MN_QUERY_PNP_DEVICE_STATE
)
180 /* device cannot be disabled */
181 Irp
->IoStatus
.Information
|= PNP_DEVICE_NOT_DISABLEABLE
;
182 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
184 /* skip current location */
185 IoSkipCurrentIrpStackLocation(Irp
);
187 /* call the pnp device object */
188 return IoCallDriver(PnpDeviceObject
, Irp
);
191 if (Status
== STATUS_NOT_SUPPORTED
)
193 /* skip current location */
194 IoSkipCurrentIrpStackLocation(Irp
);
196 /* call the pnp device object */
197 return IoCallDriver(PnpDeviceObject
, Irp
);
201 /* complete the request */
202 Irp
->IoStatus
.Status
= Status
;
203 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
210 SwDispatchSystemControl(
211 IN PDEVICE_OBJECT DeviceObject
,
216 PDEVICE_OBJECT PnpDeviceObject
;
218 /* check if the device object is a child device */
219 Status
= KsIsBusEnumChildDevice(DeviceObject
, &ChildDevice
);
221 /* check for success */
222 if (NT_SUCCESS(Status
))
226 /* bus devices dont support internal requests */
227 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
228 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
229 return STATUS_SUCCESS
;
232 /* get bus enum pnp object */
233 Status
= KsGetBusEnumPnpDeviceObject(DeviceObject
, &PnpDeviceObject
);
235 /* check for success */
236 if (NT_SUCCESS(Status
))
238 /* skip current location */
239 IoSkipCurrentIrpStackLocation(Irp
);
240 /* call the pnp device object */
241 return IoCallDriver(PnpDeviceObject
, Irp
);
246 /* complete the request */
247 Irp
->IoStatus
.Status
= Status
;
248 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
256 SwDispatchDeviceControl(
257 IN PDEVICE_OBJECT DeviceObject
,
260 PIO_STACK_LOCATION IoStack
;
263 /* get current stack location */
264 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
266 if (IoStack
->Parameters
.DeviceIoControl
.IoControlCode
== IOCTL_SWENUM_INSTALL_INTERFACE
)
268 /* install interface */
269 Status
= KsInstallBusEnumInterface(Irp
);
270 DPRINT("SwDispatchDeviceControl IOCTL_SWENUM_INSTALL_INTERFACE %x\n", Status
);
272 else if (IoStack
->Parameters
.DeviceIoControl
.IoControlCode
== IOCTL_SWENUM_REMOVE_INTERFACE
)
274 /* remove interface */
275 Status
= KsRemoveBusEnumInterface(Irp
);
276 DPRINT("SwDispatchDeviceControl IOCTL_SWENUM_REMOVE_INTERFACE %x\n", Status
);
279 else if (IoStack
->Parameters
.DeviceIoControl
.IoControlCode
== IOCTL_SWENUM_GET_BUS_ID
)
282 Status
= KsGetBusEnumIdentifier(Irp
);
283 DPRINT("SwDispatchDeviceControl IOCTL_SWENUM_GET_BUS_ID %x\n", Status
);
287 DPRINT("SwDispatchDeviceControl Unknown IOCTL %x\n", IoStack
->Parameters
.DeviceIoControl
.IoControlCode
);
288 Status
= STATUS_INVALID_PARAMETER
;
292 Irp
->IoStatus
.Status
= Status
;
295 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
305 IN PDEVICE_OBJECT DeviceObject
,
311 /* check if the device object is a child device */
312 Status
= KsIsBusEnumChildDevice(DeviceObject
, &ChildDevice
);
314 DPRINT("SwDispatchCreate %x\n", Status
);
316 /* check for success */
317 if (NT_SUCCESS(Status
))
321 /* child devices cant create devices */
322 Irp
->IoStatus
.Status
= STATUS_OBJECT_NAME_NOT_FOUND
;
323 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
324 return STATUS_OBJECT_NAME_NOT_FOUND
;
326 /* perform the create request */
327 Status
= KsServiceBusEnumCreateRequest(DeviceObject
, Irp
);
328 DPRINT("SwDispatchCreate %x\n", Status
);
331 /* check the irp is pending */
332 if (Status
!= STATUS_PENDING
)
334 /* irp is ok to complete */
335 Irp
->IoStatus
.Status
= Status
;
336 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
346 IN PDEVICE_OBJECT DeviceObject
,
349 /* just complete the irp */
350 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
352 /* complete the irp */
353 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
356 return STATUS_SUCCESS
;
363 IN PDRIVER_OBJECT DriverObject
,
364 IN PDEVICE_OBJECT PhysicalDeviceObject
)
367 PDEVICE_OBJECT FunctionalDeviceObject
;
369 DPRINT("SWENUM AddDevice\n");
370 /* create the device */
371 Status
= IoCreateDevice(DriverObject
, sizeof(KSDEVICE_HEADER
), NULL
, FILE_DEVICE_BUS_EXTENDER
, 0, FALSE
, &FunctionalDeviceObject
);
373 if (!NT_SUCCESS(Status
))
379 /* create the bus enum object */
380 Status
= KsCreateBusEnumObject(L
"SW", FunctionalDeviceObject
, PhysicalDeviceObject
, NULL
, &KSMEDIUMSETID_Standard
, L
"Devices");
382 /* check for success */
383 if (NT_SUCCESS(Status
))
385 /* set device flags */
386 FunctionalDeviceObject
->Flags
|= DO_POWER_PAGABLE
;
387 FunctionalDeviceObject
->Flags
&= ~ DO_DEVICE_INITIALIZING
;
391 /* failed to create bus enum object */
392 IoDeleteDevice(FunctionalDeviceObject
);
402 IN PDRIVER_OBJECT DriverObject
)
410 IN PDRIVER_OBJECT DriverObject
,
411 IN PUNICODE_STRING RegistryPathName
)
414 /* setup add device routine */
415 DriverObject
->DriverExtension
->AddDevice
= SwAddDevice
;
417 /* setup unload routine */
418 DriverObject
->DriverUnload
= SwUnload
;
420 /* misc irp handling routines */
421 DriverObject
->MajorFunction
[IRP_MJ_CREATE
] = SwDispatchCreate
;
422 DriverObject
->MajorFunction
[IRP_MJ_CLOSE
] = SwDispatchClose
;
423 DriverObject
->MajorFunction
[IRP_MJ_PNP
] = SwDispatchPnp
;
424 DriverObject
->MajorFunction
[IRP_MJ_POWER
] = SwDispatchPower
;
425 DriverObject
->MajorFunction
[IRP_MJ_DEVICE_CONTROL
] = SwDispatchDeviceControl
;
426 DriverObject
->MajorFunction
[IRP_MJ_SYSTEM_CONTROL
] = SwDispatchSystemControl
;
428 DPRINT("SWENUM loaded\n");
429 return STATUS_SUCCESS
;