[NTOSKRNL]
authorCameron Gutman <aicommander@gmail.com>
Thu, 22 Apr 2010 21:07:46 +0000 (21:07 +0000)
committerCameron Gutman <aicommander@gmail.com>
Thu, 22 Apr 2010 21:07:46 +0000 (21:07 +0000)
- Add a stub for IRP_MN_REMOVE_DEVICE in PnpRoot
- Revert 2 incorrect changes from r46983 (DNF_ENUMERATED added to the DNF_ADDED assertion and setting the DNF_RESOURCE_REPORTED flag in IopStartDevice2)
- Set the DNF_LEGACY_DRIVER flag if the AddDevice handler is missing
- Add a helper function called IopSendRemoveDevice which sends IRP_MN_REMOVE_DEVICE to a device object
- Call IopSendRemoveDevice if IRP_MN_START_DEVICE fails
- Set the DNF_STARTED and DNF_ADDED flags for legacy drivers
- Enable the DNF_ADDED assertion in IopStartDevice2

svn path=/trunk/; revision=46997

reactos/ntoskrnl/io/pnpmgr/pnpmgr.c
reactos/ntoskrnl/io/pnpmgr/pnproot.c

index dbfada1..645b837 100644 (file)
@@ -66,19 +66,20 @@ IopInitializeDevice(PDEVICE_NODE DeviceNode,
    NTSTATUS Status;
 
    if (!DriverObject->DriverExtension->AddDevice)
+   {
+      DeviceNode->Flags |= DNF_LEGACY_DRIVER;
+   }
+
+   if (DeviceNode->Flags & DNF_LEGACY_DRIVER)
+   {
+      DeviceNode->Flags |= DNF_ADDED + DNF_STARTED;
       return STATUS_SUCCESS;
+   }
 
    /* This is a Plug and Play driver */
    DPRINT("Plug and Play driver found\n");
    ASSERT(DeviceNode->PhysicalDeviceObject);
 
-   /* Check if this plug-and-play driver is used as a legacy one for this device node */
-   if (IopDeviceNodeHasFlag(DeviceNode, DNF_LEGACY_DRIVER))
-   {
-      IopDeviceNodeSetFlag(DeviceNode, DNF_ADDED);
-      return STATUS_SUCCESS;
-   }
-
    DPRINT("Calling %wZ->AddDevice(%wZ)\n",
       &DriverObject->DriverName,
       &DeviceNode->InstancePath);
@@ -122,6 +123,21 @@ IopInitializeDevice(PDEVICE_NODE DeviceNode,
    return STATUS_SUCCESS;
 }
 
+VOID
+NTAPI
+IopSendRemoveDevice(IN PDEVICE_OBJECT DeviceObject)
+{
+    IO_STACK_LOCATION Stack;
+    PVOID Dummy;
+
+    RtlZeroMemory(&Stack, sizeof(IO_STACK_LOCATION));
+    Stack.MajorFunction = IRP_MJ_PNP;
+    Stack.MinorFunction = IRP_MN_REMOVE_DEVICE;
+
+    /* Drivers should never fail a IRP_MN_REMOVE_DEVICE request */
+    IopSynchronousCall(DeviceObject, &Stack, &Dummy);
+}
+
 VOID
 NTAPI
 IopStartDevice2(IN PDEVICE_OBJECT DeviceObject)
@@ -156,10 +172,11 @@ IopStartDevice2(IN PDEVICE_OBJECT DeviceObject)
     Status = IopSynchronousCall(DeviceObject, &Stack, &Dummy);
     if (!NT_SUCCESS(Status))
     {
-        /* We failed start */
-        DeviceNode->Flags |= DNF_START_FAILED;
+        /* Send an IRP_MN_REMOVE_DEVICE request */
+        IopSendRemoveDevice(DeviceObject);
 
-        /* TODO: Undo all the stuff we did up to this point */
+        /* Set the appropriate flag */
+        DeviceNode->Flags |= DNF_START_FAILED;
 
         DPRINT1("Warning: PnP Start failed (%wZ)\n", &DeviceNode->InstancePath);
         return;
@@ -168,9 +185,6 @@ IopStartDevice2(IN PDEVICE_OBJECT DeviceObject)
     /* Otherwise, mark us as started */
     DeviceNode->Flags |= DNF_STARTED;
 
-    /* We reported the resources */
-    DeviceNode->Flags |= DNF_RESOURCE_REPORTED;
-
     /* We now need enumeration */
     DeviceNode->Flags |= DNF_NEED_ENUMERATION_ONLY;
 }
@@ -184,10 +198,7 @@ IopStartAndEnumerateDevice(IN PDEVICE_NODE DeviceNode)
     PAGED_CODE();
     
     /* Sanity check */
-  //  ASSERT((DeviceNode->Flags & DNF_ADDED) || (DeviceNode->Flags & DNF_ENUMERATED));
-    if (!(DeviceNode->Flags & DNF_ADDED) && !(DeviceNode->Flags & DNF_ENUMERATED))
-        DPRINT1("Warning: Starting a device node without DNF_ADDED or DNF_ENUMERATED (%wZ)\n",
-                &DeviceNode->InstancePath);
+    ASSERT((DeviceNode->Flags & DNF_ADDED));
     ASSERT((DeviceNode->Flags & (DNF_RESOURCE_ASSIGNED |
                                  DNF_RESOURCE_REPORTED |
                                  DNF_NO_RESOURCE_REQUIRED)));
@@ -243,6 +254,12 @@ IopStartDevice(
    UNICODE_STRING KeyName;
    OBJECT_ATTRIBUTES ObjectAttributes;
 
+   if (DeviceNode->Flags & (DNF_STARTED | DNF_START_REQUEST_PENDING))
+   {
+       /* Nothing to do here */
+       return STATUS_SUCCESS;
+   }
+
    Status = IopAssignDeviceResources(DeviceNode);
    if (!NT_SUCCESS(Status))
        goto ByeBye;
@@ -542,8 +559,9 @@ IopCreateDeviceNode(PDEVICE_NODE ParentNode,
           return Status;
       }
 
-      /* This is for drivers passed on the command line to ntoskrnl.exe */
       IopDeviceNodeSetFlag(Node, DNF_LEGACY_DRIVER);
+      IopDeviceNodeSetFlag(Node, DNF_ADDED);
+      IopDeviceNodeSetFlag(Node, DNF_STARTED);
    }
 
    Node->PhysicalDeviceObject = PhysicalDeviceObject;
index 30c612f..6f1834e 100644 (file)
@@ -1069,6 +1069,11 @@ PnpRootPdoPnpControl(
         DPRINT("IRP_MJ_PNP / IRP_MN_FILTER_RESOURCE_REQUIREMENTS\n");
         break;
 
+    case IRP_MN_REMOVE_DEVICE:
+        DPRINT1("IRP_MN_REMOVE_DEVICE is UNIMPLEMENTED!\n");
+        Status = STATUS_SUCCESS;
+        break;
+
     case IRP_MN_QUERY_ID: /* 0x13 */
       Status = PdoQueryId(DeviceObject, Irp, IrpSp);
       break;