diff --git a/drivers/bus/pci/fdo.c b/drivers/bus/pci/fdo.c index 94f7a5f8c3a..4b12ded5b4e 100644 --- a/drivers/bus/pci/fdo.c +++ b/drivers/bus/pci/fdo.c @@ -96,7 +96,6 @@ FdoEnumerateDevices( { PFDO_DEVICE_EXTENSION DeviceExtension; PCI_COMMON_CONFIG PciConfig; - PLIST_ENTRY CurrentEntry; PPCI_DEVICE Device; PCI_SLOT_NUMBER SlotNumber; ULONG DeviceNumber; @@ -108,15 +107,6 @@ FdoEnumerateDevices( DeviceExtension = (PFDO_DEVICE_EXTENSION)DeviceObject->DeviceExtension; - /* Mark all devices to be removed. If we don't discover them again during - enumeration, assume that they have been surprise removed */ - CurrentEntry = DeviceExtension->DeviceListHead.Flink; - while (CurrentEntry != &DeviceExtension->DeviceListHead) { - Device = CONTAINING_RECORD(CurrentEntry, PCI_DEVICE, ListEntry); - Device->RemovePending = TRUE; - CurrentEntry = CurrentEntry->Flink; - } - DeviceExtension->DeviceListCount = 0; /* Enumerate devices on the PCI bus */ @@ -190,9 +180,6 @@ FdoEnumerateDevices( &DeviceExtension->DeviceListLock); } - /* Don't remove this device */ - Device->RemovePending = FALSE; - DeviceExtension->DeviceListCount++; /* Skip to next device if the current one is not a multifunction device */ diff --git a/drivers/bus/pci/pdo.c b/drivers/bus/pci/pdo.c index a3391795812..26569a45129 100644 --- a/drivers/bus/pci/pdo.c +++ b/drivers/bus/pci/pdo.c @@ -1443,11 +1443,34 @@ PdoPnpControl( case IRP_MN_STOP_DEVICE: case IRP_MN_QUERY_REMOVE_DEVICE: case IRP_MN_CANCEL_REMOVE_DEVICE: - case IRP_MN_REMOVE_DEVICE: case IRP_MN_SURPRISE_REMOVAL: Status = STATUS_SUCCESS; break; + case IRP_MN_REMOVE_DEVICE: + { + PPDO_DEVICE_EXTENSION DeviceExtension = DeviceObject->DeviceExtension; + PFDO_DEVICE_EXTENSION FdoDeviceExtension = DeviceExtension->Fdo->DeviceExtension; + KIRQL OldIrql; + + /* Remove it from the device list */ + KeAcquireSpinLock(&FdoDeviceExtension->DeviceListLock, &OldIrql); + RemoveEntryList(&DeviceExtension->PciDevice->ListEntry); + FdoDeviceExtension->DeviceListCount--; + KeReleaseSpinLock(&FdoDeviceExtension->DeviceListLock, OldIrql); + + /* Free the device */ + ExFreePool(DeviceExtension->PciDevice); + + /* Complete the IRP */ + Irp->IoStatus.Status = STATUS_SUCCESS; + IoCompleteRequest(Irp, IO_NO_INCREMENT); + + /* Delete the DO */ + IoDeleteDevice(DeviceObject); + return STATUS_SUCCESS; + } + case IRP_MN_QUERY_INTERFACE: DPRINT("IRP_MN_QUERY_INTERFACE received\n"); Status = PdoQueryInterface(DeviceObject, Irp, IrpSp); diff --git a/drivers/hid/hidclass/fdo.c b/drivers/hid/hidclass/fdo.c index 7604d5104e8..e909d67a07d 100644 --- a/drivers/hid/hidclass/fdo.c +++ b/drivers/hid/hidclass/fdo.c @@ -554,6 +554,7 @@ HidClassFDO_PnP( { return HidClassFDO_RemoveDevice(DeviceObject, Irp); } + case IRP_MN_QUERY_REMOVE_DEVICE: case IRP_MN_QUERY_STOP_DEVICE: { // @@ -567,6 +568,7 @@ HidClassFDO_PnP( IoSkipCurrentIrpStackLocation(Irp); return IoCallDriver(FDODeviceExtension->Common.HidDeviceExtension.NextDeviceObject, Irp); } + case IRP_MN_CANCEL_REMOVE_DEVICE: case IRP_MN_CANCEL_STOP_DEVICE: { // diff --git a/drivers/hid/hidusb/hidusb.c b/drivers/hid/hidusb/hidusb.c index f859b2bd118..f97c9f9fed0 100644 --- a/drivers/hid/hidusb/hidusb.c +++ b/drivers/hid/hidusb/hidusb.c @@ -1561,8 +1561,11 @@ HidPnp( } // - // done + // delete and detach device // + IoDetachDevice(DeviceExtension->NextDeviceObject); + IoDeleteDevice(DeviceObject); + return Status; } case IRP_MN_QUERY_PNP_DEVICE_STATE: @@ -1583,6 +1586,25 @@ HidPnp( // return Status; } + case IRP_MN_QUERY_STOP_DEVICE: + case IRP_MN_QUERY_REMOVE_DEVICE: + { + // + // we're fine with it + // + Irp->IoStatus.Status = STATUS_SUCCESS; + + // + // pass request to next driver + // + IoSkipCurrentIrpStackLocation(Irp); + Status = IoCallDriver(DeviceExtension->NextDeviceObject, Irp); + + // + // done + // + return Status; + } case IRP_MN_STOP_DEVICE: { // diff --git a/drivers/hid/kbdhid/kbdhid.c b/drivers/hid/kbdhid/kbdhid.c index eec804bc87b..7871b37e7cb 100644 --- a/drivers/hid/kbdhid/kbdhid.c +++ b/drivers/hid/kbdhid/kbdhid.c @@ -737,7 +737,11 @@ KbdHid_Pnp( IoStack = IoGetCurrentIrpStackLocation(Irp); DPRINT1("[KBDHID] IRP_MJ_PNP Request: %x\n", IoStack->MinorFunction); - if (IoStack->MinorFunction == IRP_MN_STOP_DEVICE || IoStack->MinorFunction == IRP_MN_CANCEL_REMOVE_DEVICE || IoStack->MinorFunction == IRP_MN_QUERY_STOP_DEVICE || IoStack->MinorFunction == IRP_MN_CANCEL_STOP_DEVICE) + if (IoStack->MinorFunction == IRP_MN_STOP_DEVICE || + IoStack->MinorFunction == IRP_MN_CANCEL_REMOVE_DEVICE || + IoStack->MinorFunction == IRP_MN_QUERY_STOP_DEVICE || + IoStack->MinorFunction == IRP_MN_CANCEL_STOP_DEVICE || + IoStack->MinorFunction == IRP_MN_QUERY_REMOVE_DEVICE) { /* indicate success */ Irp->IoStatus.Status = STATUS_SUCCESS; diff --git a/drivers/hid/mouhid/mouhid.c b/drivers/hid/mouhid/mouhid.c index 350b4abeadc..013bf807908 100644 --- a/drivers/hid/mouhid/mouhid.c +++ b/drivers/hid/mouhid/mouhid.c @@ -788,7 +788,11 @@ MouHid_Pnp( IoStack = IoGetCurrentIrpStackLocation(Irp); DPRINT1("[MOUHID] IRP_MJ_PNP Request: %x\n", IoStack->MinorFunction); - if (IoStack->MinorFunction == IRP_MN_STOP_DEVICE || IoStack->MinorFunction == IRP_MN_CANCEL_REMOVE_DEVICE || IoStack->MinorFunction == IRP_MN_QUERY_STOP_DEVICE || IoStack->MinorFunction == IRP_MN_CANCEL_STOP_DEVICE) + if (IoStack->MinorFunction == IRP_MN_STOP_DEVICE || + IoStack->MinorFunction == IRP_MN_CANCEL_REMOVE_DEVICE || + IoStack->MinorFunction == IRP_MN_QUERY_STOP_DEVICE || + IoStack->MinorFunction == IRP_MN_CANCEL_STOP_DEVICE || + IoStack->MinorFunction == IRP_MN_QUERY_REMOVE_DEVICE) { /* indicate success */ Irp->IoStatus.Status = STATUS_SUCCESS; diff --git a/drivers/usb/usbccgp/fdo.c b/drivers/usb/usbccgp/fdo.c index 04d38e927bd..c370343b0a1 100644 --- a/drivers/usb/usbccgp/fdo.c +++ b/drivers/usb/usbccgp/fdo.c @@ -481,6 +481,20 @@ FDO_HandlePnp( } break; } + case IRP_MN_QUERY_REMOVE_DEVICE: + case IRP_MN_QUERY_STOP_DEVICE: + { + // + // sure + // + Irp->IoStatus.Status = STATUS_SUCCESS; + + // + // forward irp to next device object + // + IoSkipCurrentIrpStackLocation(Irp); + return IoCallDriver(FDODeviceExtension->NextDeviceObject, Irp); + } default: { // diff --git a/drivers/usb/usbccgp/pdo.c b/drivers/usb/usbccgp/pdo.c index 1a2c0be7b1a..a78f7cea3c2 100644 --- a/drivers/usb/usbccgp/pdo.c +++ b/drivers/usb/usbccgp/pdo.c @@ -391,6 +391,15 @@ PDO_HandlePnp( IoCompleteRequest(Irp, IO_NO_INCREMENT); return STATUS_SUCCESS; } + case IRP_MN_QUERY_REMOVE_DEVICE: + case IRP_MN_QUERY_STOP_DEVICE: + { + // + // sure + // + Status = STATUS_SUCCESS; + break; + } case IRP_MN_START_DEVICE: { // @@ -406,6 +415,7 @@ PDO_HandlePnp( // do nothing // Status = Irp->IoStatus.Status; + break; } } diff --git a/drivers/usb/usbehci_new/hub_controller.cpp b/drivers/usb/usbehci_new/hub_controller.cpp index b24ab7d269e..8342a7d17b9 100644 --- a/drivers/usb/usbehci_new/hub_controller.cpp +++ b/drivers/usb/usbehci_new/hub_controller.cpp @@ -434,6 +434,15 @@ CHubController::HandlePnp( Status = SetDeviceInterface(TRUE); break; } + case IRP_MN_QUERY_STOP_DEVICE: + case IRP_MN_QUERY_REMOVE_DEVICE: + { + // + // sure + // + Status = STATUS_SUCCESS; + break; + } case IRP_MN_QUERY_ID: { DPRINT1("CHubController::HandlePnp IRP_MN_QUERY_ID Type %x\n", IoStack->Parameters.QueryId.IdType); diff --git a/drivers/usb/usbhub_new/fdo.c b/drivers/usb/usbhub_new/fdo.c index 89b178744bd..d0f11ca2d2d 100644 --- a/drivers/usb/usbhub_new/fdo.c +++ b/drivers/usb/usbhub_new/fdo.c @@ -1883,6 +1883,22 @@ USBHUB_FdoHandlePnp( } break; } + case IRP_MN_QUERY_REMOVE_DEVICE: + case IRP_MN_QUERY_STOP_DEVICE: + { + Irp->IoStatus.Status = STATUS_SUCCESS; + return ForwardIrpAndForget(DeviceObject, Irp); + } + case IRP_MN_REMOVE_DEVICE: + { + Irp->IoStatus.Status = STATUS_SUCCESS; + IoCompleteRequest(Irp, IO_NO_INCREMENT); + + IoDetachDevice(HubDeviceExtension->LowerDeviceObject); + IoDeleteDevice(DeviceObject); + + return STATUS_SUCCESS; + } case IRP_MN_QUERY_BUS_INFORMATION: { DPRINT1("IRP_MN_QUERY_BUS_INFORMATION\n"); diff --git a/drivers/usb/usbhub_new/pdo.c b/drivers/usb/usbhub_new/pdo.c index 48b31d7746c..e40f1f28436 100644 --- a/drivers/usb/usbhub_new/pdo.c +++ b/drivers/usb/usbhub_new/pdo.c @@ -586,6 +586,14 @@ USBHUB_PdoHandlePnp( IoDeleteDevice(DeviceObject); return STATUS_SUCCESS; } + case IRP_MN_QUERY_STOP_DEVICE: + case IRP_MN_QUERY_REMOVE_DEVICE: + { + /* Sure, no problem */ + Status = STATUS_SUCCESS; + Information = 0; + break; + } default: { DPRINT1("PDO IRP_MJ_PNP / unknown minor function 0x%lx\n", MinorFunction); diff --git a/drivers/usb/usbohci/hub_controller.cpp b/drivers/usb/usbohci/hub_controller.cpp index 8b9b87720cf..aef53d11144 100644 --- a/drivers/usb/usbohci/hub_controller.cpp +++ b/drivers/usb/usbohci/hub_controller.cpp @@ -437,6 +437,15 @@ CHubController::HandlePnp( Status = SetDeviceInterface(TRUE); break; } + case IRP_MN_QUERY_STOP_DEVICE: + case IRP_MN_QUERY_REMOVE_DEVICE: + { + // + // sure + // + Status = STATUS_SUCCESS; + break; + } case IRP_MN_QUERY_ID: { DPRINT1("CHubController::HandlePnp IRP_MN_QUERY_ID Type %x\n", IoStack->Parameters.QueryId.IdType); diff --git a/drivers/usb/usbstor/fdo.c b/drivers/usb/usbstor/fdo.c index 2d7123f14bc..c3d12b59cf3 100644 --- a/drivers/usb/usbstor/fdo.c +++ b/drivers/usb/usbstor/fdo.c @@ -339,9 +339,11 @@ USBSTOR_FdoHandlePnp( break; } case IRP_MN_STOP_DEVICE: + { DPRINT1("USBSTOR_FdoHandlePnp: IRP_MN_STOP_DEVICE unimplemented\n"); Status = STATUS_NOT_SUPPORTED; break; + } case IRP_MN_REMOVE_DEVICE: { DPRINT1("IRP_MN_REMOVE_DEVICE\n"); @@ -356,6 +358,29 @@ USBSTOR_FdoHandlePnp( IoSkipCurrentIrpStackLocation(Irp); return IoCallDriver(DeviceExtension->LowerDeviceObject, Irp); } + case IRP_MN_QUERY_STOP_DEVICE: + case IRP_MN_QUERY_REMOVE_DEVICE: + { + // + // we can if nothing is pending + // + if (DeviceExtension->IrpPendingCount != 0 || + DeviceExtension->ActiveSrb != NULL) + { + /* We have pending requests */ + DPRINT1("Failing removal/stop request due to pending requests present\n"); + Status = STATUS_UNSUCCESSFUL; + } + else + { + /* We're all clear */ + Irp->IoStatus.Status = STATUS_SUCCESS; + + IoSkipCurrentIrpStackLocation(Irp); + return IoCallDriver(DeviceExtension->LowerDeviceObject, Irp); + } + break; + } case IRP_MN_START_DEVICE: { Status = USBSTOR_FdoHandleStartDevice(DeviceObject, DeviceExtension, Irp); diff --git a/drivers/usb/usbstor/pdo.c b/drivers/usb/usbstor/pdo.c index 4a50a00609f..3361351bee8 100644 --- a/drivers/usb/usbstor/pdo.c +++ b/drivers/usb/usbstor/pdo.c @@ -873,6 +873,18 @@ USBSTOR_PdoHandlePnp( } break; } + case IRP_MN_QUERY_REMOVE_DEVICE: + case IRP_MN_QUERY_STOP_DEVICE: + { + // + // if we're not claimed it's ok + // + if (DeviceExtension->Claimed) + Status = STATUS_UNSUCCESSFUL; + else + Status = STATUS_SUCCESS; + break; + } case IRP_MN_START_DEVICE: { //