[MOUNTMGR] Misc. fixes for WorkerThread()
authorPierre Schweitzer <pierre@reactos.org>
Mon, 21 Oct 2019 08:54:51 +0000 (10:54 +0200)
committerPierre Schweitzer <pierre@reactos.org>
Mon, 21 Oct 2019 08:58:14 +0000 (10:58 +0200)
- Properly quit the active loop when we're out of work items;
- Fix timeout duration (setting it to 1s);
- Fix handling the "Unloading" variable in case of a shutdown
  so that waiting loop is properly stopped;
- Documented why we're waiting on VolumesSafeForWriteAccess.

This fixes shutting down ReactOS with work items queued.
This is needed here because no one ever sets that event (properly)
created by SMSS though. A. Ionescu was explaining in 2018 that it's
autochk responsibility, but it doesn't seem to be the case in W2K3.
To be investigated.

This fix with all the previous ones and more uncommitted stuff (yet ;-))
allows reaching the first steps towards a NT5 storage stack:
https://twitter.com/HeisSpiter/status/1186199631740506112

drivers/filters/mountmgr/database.c

index aa0c6a4..694c98a 100644 (file)
@@ -1168,21 +1168,40 @@ WorkerThread(IN PDEVICE_OBJECT DeviceObject,
                                NULL,
                                NULL);
     KeInitializeEvent(&Event, NotificationEvent, FALSE);
-    Timeout.LowPart = 0xFFFFFFFF;
-    Timeout.HighPart = 0xFF676980;
+    Timeout.QuadPart = -10000000LL; /* Wait for 1 second */
 
-    /* Try to wait as long as possible */
-    for (i = (Unloading ? 999 : 0); i < 1000; i++)
+    /* Wait as long as possible for clearance from autochk
+     * We will write remote databases only if it is safe
+     * to access volumes.
+     * First, given we start before SMSS, wait for the
+     * event creation.
+     */
+    i = 0;
+    do
     {
-        Status = ZwOpenEvent(&SafeEvent, EVENT_ALL_ACCESS, &ObjectAttributes);
-        if (NT_SUCCESS(Status))
+        /* If we started to shutdown, stop waiting forever and jump to last attempt */
+        if (Unloading)
         {
-            break;
+            i = 999;
+        }
+        else
+        {
+            /* Attempt to open the event */
+            Status = ZwOpenEvent(&SafeEvent, EVENT_ALL_ACCESS, &ObjectAttributes);
+            if (NT_SUCCESS(Status))
+            {
+                break;
+            }
+
+            /* Wait a bit to give SMSS a chance to create the event */
+            KeWaitForSingleObject(&Event, Executive, KernelMode, FALSE, &Timeout);
         }
 
-        KeWaitForSingleObject(&Event, Executive, KernelMode, FALSE, &Timeout);
+        ++i;
     }
+    while (i < 1000);
 
+    /* We managed to open the event, wait until autochk signals it */
     if (i < 1000)
     {
         do
@@ -1220,7 +1239,7 @@ WorkerThread(IN PDEVICE_OBJECT DeviceObject,
         IoFreeWorkItem(WorkItem->WorkItem);
         FreePool(WorkItem);
 
-        if (InterlockedDecrement(&(DeviceExtension->WorkerReferences)) == 0)
+        if (InterlockedDecrement(&(DeviceExtension->WorkerReferences)) < 0)
         {
             return;
         }
@@ -1603,6 +1622,9 @@ ReconcileThisDatabaseWithMaster(IN PDEVICE_EXTENSION DeviceExtension,
         return;
     }
 
+    UNIMPLEMENTED;
+    return;
+
     /* Allocate a work item */
     WorkItem = AllocatePool(sizeof(RECONCILE_WORK_ITEM));
     if (!WorkItem)