2 * PROJECT: ReactOS Composite Battery Driver
3 * LICENSE: BSD - See COPYING.ARM in the top level directory
4 * FILE: boot/drivers/bus/acpi/compbatt/comppnp.c
5 * PURPOSE: Plug-and-Play IOCTL/IRP Handling
6 * PROGRAMMERS: ReactOS Portable Systems Group
9 /* INCLUDES *******************************************************************/
13 /* FUNCTIONS ******************************************************************/
17 CompBattPowerDispatch(IN PDEVICE_OBJECT DeviceObject
,
20 PCOMPBATT_DEVICE_EXTENSION DeviceExtension
= DeviceObject
->DeviceExtension
;
21 if (CompBattDebug
& 1) DbgPrint("CompBatt: PowerDispatch recieved power IRP.\n");
23 /* Start the next IRP */
24 PoStartNextPowerIrp(Irp
);
26 /* Call the next driver in the stack */
27 IoSkipCurrentIrpStackLocation(Irp
);
28 return PoCallDriver(DeviceExtension
->AttachedDevice
, Irp
);
31 PCOMPBATT_BATTERY_ENTRY
33 RemoveBatteryFromList(IN PCUNICODE_STRING BatteryName
,
34 IN PCOMPBATT_DEVICE_EXTENSION DeviceExtension
)
42 IsBatteryAlreadyOnList(IN PCUNICODE_STRING BatteryName
,
43 IN PCOMPBATT_DEVICE_EXTENSION DeviceExtension
)
51 CompBattAddNewBattery(IN PCUNICODE_STRING BatteryName
,
52 IN PCOMPBATT_DEVICE_EXTENSION DeviceExtension
)
55 return STATUS_NOT_IMPLEMENTED
;
60 CompBattRemoveBattery(IN PCUNICODE_STRING BatteryName
,
61 IN PCOMPBATT_DEVICE_EXTENSION DeviceExtension
)
64 return STATUS_NOT_IMPLEMENTED
;
69 CompBattGetBatteries(IN PCOMPBATT_DEVICE_EXTENSION DeviceExtension
)
72 return STATUS_NOT_IMPLEMENTED
;
77 CompBattPnpEventHandler(IN PDEVICE_INTERFACE_CHANGE_NOTIFICATION Notification
,
78 IN PCOMPBATT_DEVICE_EXTENSION DeviceExtension
)
81 return STATUS_NOT_IMPLEMENTED
;
86 CompBattAddDevice(IN PDRIVER_OBJECT DriverObject
,
87 IN PDEVICE_OBJECT PdoDeviceObject
)
90 UNICODE_STRING DeviceName
;
91 PCOMPBATT_DEVICE_EXTENSION DeviceExtension
;
92 PDEVICE_OBJECT DeviceObject
;
93 UNICODE_STRING SymbolicLinkName
;
94 BATTERY_MINIPORT_INFO MiniportInfo
;
95 if (CompBattDebug
& 2) DbgPrint("CompBatt: Got an AddDevice - %x\n", PdoDeviceObject
);
97 /* Create the device */
98 RtlInitUnicodeString(&DeviceName
, L
"\\Device\\CompositeBattery");
99 Status
= IoCreateDevice(DriverObject
,
100 sizeof(COMPBATT_DEVICE_EXTENSION
),
103 FILE_DEVICE_SECURE_OPEN
,
106 if (!NT_SUCCESS(Status
)) return Status
;
108 /* Setup symbolic link for Win32 access */
109 RtlInitUnicodeString(&SymbolicLinkName
, L
"\\DosDevices\\CompositeBattery");
110 IoCreateSymbolicLink(&SymbolicLinkName
, &DeviceName
);
112 /* Initialize the device extension */
113 DeviceExtension
= DeviceObject
->DeviceExtension
;
114 RtlZeroMemory(DeviceExtension
, 0x1B0u
);
116 /* Attach to device stack and set DO pointers */
117 DeviceExtension
->AttachedDevice
= IoAttachDeviceToDeviceStack(DeviceObject
,
119 DeviceExtension
->DeviceObject
= DeviceObject
;
120 if (!DeviceExtension
->AttachedDevice
)
123 if (CompBattDebug
& 8)
124 DbgPrint("CompBattAddDevice: Could not attach to LowerDevice.\n");
125 IoDeleteDevice(DeviceObject
);
126 return STATUS_UNSUCCESSFUL
;
129 /* Set device object flags */
130 DeviceObject
->Flags
|= (DO_POWER_PAGABLE
| DO_BUFFERED_IO
);
131 DeviceObject
->Flags
&= ~DO_DEVICE_INITIALIZING
;
133 /* Setup the device extension */
134 ExInitializeFastMutex(&DeviceExtension
->Lock
);
135 InitializeListHead(&DeviceExtension
->BatteryList
);
136 DeviceExtension
->Flags
= 0;
137 DeviceExtension
->NextTag
= 1;
139 /* Setup the miniport data */
140 RtlZeroMemory(&MiniportInfo
, sizeof(MiniportInfo
));
141 MiniportInfo
.MajorVersion
= BATTERY_CLASS_MAJOR_VERSION
;
142 MiniportInfo
.MinorVersion
= BATTERY_CLASS_MINOR_VERSION
;
143 MiniportInfo
.Context
= DeviceExtension
;
144 MiniportInfo
.DeviceName
= &DeviceName
;
145 MiniportInfo
.QueryTag
= (BCLASS_QUERY_TAG
)CompBattQueryTag
;
146 MiniportInfo
.QueryInformation
= (BCLASS_QUERY_INFORMATION
)CompBattQueryInformation
;
147 MiniportInfo
.SetInformation
= NULL
;
148 MiniportInfo
.QueryStatus
= (BCLASS_QUERY_STATUS
)CompBattQueryStatus
;
149 MiniportInfo
.SetStatusNotify
= (BCLASS_SET_STATUS_NOTIFY
)CompBattSetStatusNotify
;
150 MiniportInfo
.DisableStatusNotify
= (BCLASS_DISABLE_STATUS_NOTIFY
)CompBattDisableStatusNotify
;
151 MiniportInfo
.Pdo
= NULL
;
153 /* Register with the class driver */
154 Status
= BatteryClassInitializeDevice(&MiniportInfo
,
155 &DeviceExtension
->ClassData
);
156 if (!NT_SUCCESS(Status
))
158 /* Undo everything */
159 IoDetachDevice(DeviceExtension
->AttachedDevice
);
160 IoDeleteDevice(DeviceObject
);
169 CompBattPnpDispatch(IN PDEVICE_OBJECT DeviceObject
,
172 PIO_STACK_LOCATION IoStackLocation
= IoGetCurrentIrpStackLocation(Irp
);
174 PCOMPBATT_DEVICE_EXTENSION DeviceExtension
= DeviceObject
->DeviceExtension
;
175 if (CompBattDebug
& 1) DbgPrint("CompBatt: ENTERING PnpDispatch\n");
177 /* Set default error */
178 Status
= STATUS_NOT_SUPPORTED
;
180 /* Check what kind of PnP function this is */
181 switch (IoStackLocation
->MinorFunction
)
183 case IRP_MN_START_DEVICE
:
185 /* Device is starting, register for new batteries and pick up current ones */
186 Status
= IoRegisterPlugPlayNotification(EventCategoryDeviceInterfaceChange
,
188 (PVOID
)&GUID_DEVICE_BATTERY
,
189 DeviceObject
->DriverObject
,
190 (PDRIVER_NOTIFICATION_CALLBACK_ROUTINE
)CompBattPnpEventHandler
,
192 &DeviceExtension
->NotificationEntry
);
193 if (NT_SUCCESS(Status
))
195 /* Now go get the batteries */
196 if (CompBattDebug
& 2)
197 DbgPrint("CompBatt: Successfully registered for PnP notification\n");
198 Status
= CompBattGetBatteries(DeviceExtension
);
203 if (CompBattDebug
& 8)
204 DbgPrint("CompBatt: Couldn't register for PnP notification - %x\n",
208 case IRP_MN_CANCEL_STOP_DEVICE
:
210 /* Explicitly say ok */
211 Status
= STATUS_SUCCESS
;
214 case IRP_MN_CANCEL_REMOVE_DEVICE
:
216 /* Explicitly say ok */
217 Status
= STATUS_SUCCESS
;
220 case IRP_MN_SURPRISE_REMOVAL
:
222 /* Explicitly say ok */
223 Status
= STATUS_SUCCESS
;
226 case IRP_MN_QUERY_PNP_DEVICE_STATE
:
229 Irp
->IoStatus
.Information
|= PNP_DEVICE_NOT_DISABLEABLE
;
230 Status
= STATUS_SUCCESS
;
236 Status
= STATUS_INVALID_DEVICE_REQUEST
;
240 /* Set IRP status if we have one */
241 if (Status
!= STATUS_NOT_SUPPORTED
) Irp
->IoStatus
.Status
= Status
;
243 /* Did someone pick it up? */
244 if ((NT_SUCCESS(Status
)) || (Status
== STATUS_NOT_SUPPORTED
))
246 /* Still unsupported, try ACPI */
247 IoSkipCurrentIrpStackLocation(Irp
);
248 Status
= IoCallDriver(DeviceExtension
->AttachedDevice
, Irp
);
252 /* Complete the request */
253 Status
= Irp
->IoStatus
.Status
;
254 IofCompleteRequest(Irp
, IO_NO_INCREMENT
);
257 /* Release the remove lock and return status */
258 if (CompBattDebug
& 1) DbgPrint("CompBatt: EXITING PnpDispatch\n");