[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[PATCH 2/5] Refactor monitor.c registry enumeration



Move registry enumeration code into a function, using a callback that is called
for each sub key of the specified key.

Signed-off-by: Owen Smith <owen.smith@xxxxxxxxxx>
---
 src/monitor/monitor.c | 149 ++++++++++++++++++++++++++++--------------
 1 file changed, 100 insertions(+), 49 deletions(-)

diff --git a/src/monitor/monitor.c b/src/monitor/monitor.c
index 1154de5..52311aa 100644
--- a/src/monitor/monitor.c
+++ b/src/monitor/monitor.c
@@ -856,23 +856,25 @@ fail1:
     return;
 }
 
-static VOID
-CheckRequestSubKeys(
-    VOID
+typedef BOOLEAN(*PREGENUM_FUNC)(HKEY, PTSTR, PVOID);
+
+static HRESULT
+RegEnumSubKeys(
+    _In_ HKEY           BaseKey,
+    _In_ PREGENUM_FUNC  Callback,
+    _In_opt_ PVOID      Context
     )
 {
-    PMONITOR_CONTEXT    Context = &MonitorContext;
     DWORD               SubKeys;
     DWORD               MaxSubKeyLength;
     DWORD               SubKeyLength;
     PTSTR               SubKeyName;
     DWORD               Index;
-    HKEY                SubKey;
     HRESULT             Error;
 
     Log("====>");
 
-    Error = RegQueryInfoKey(Context->RequestKey,
+    Error = RegQueryInfoKey(BaseKey,
                             NULL,
                             NULL,
                             NULL,
@@ -896,14 +898,10 @@ CheckRequestSubKeys(
         goto fail2;
 
     for (Index = 0; Index < SubKeys; Index++) {
-        DWORD   Length;
-        DWORD   Type;
-        DWORD   Reboot;
-
         SubKeyLength = MaxSubKeyLength + sizeof (TCHAR);
         memset(SubKeyName, 0, SubKeyLength);
 
-        Error = RegEnumKeyEx(Context->RequestKey,
+        Error = RegEnumKeyEx(BaseKey,
                              Index,
                              (LPTSTR)SubKeyName,
                              &SubKeyLength,
@@ -918,59 +916,112 @@ CheckRequestSubKeys(
 
         Log("%s", SubKeyName);
 
-        Error = RegOpenKeyEx(Context->RequestKey,
-                             SubKeyName,
-                             0,
-                             KEY_READ,
-                             &SubKey);
-        if (Error != ERROR_SUCCESS)
-            continue;
+        if (!Callback(BaseKey, SubKeyName, Context))
+            break;
+    }
 
-        Length = sizeof (DWORD);
-        Error = RegQueryValueEx(SubKey,
-                                "Reboot",
-                                NULL,
-                                &Type,
-                                (LPBYTE)&Reboot,
-                                &Length);
-        if (Error != ERROR_SUCCESS ||
-            Type != REG_DWORD)
-            goto loop;
+    free(SubKeyName);
 
-        if (Reboot != 0)
-            goto found;
+    return ERROR_SUCCESS;
 
-loop:
-        RegCloseKey(SubKey);
+fail3:
+    Log("fail3");
+
+    free(SubKeyName);
+
+fail2:
+    Log("fail2");
+
+fail1:
+    Error = GetLastError();
+
+    {
+        PTSTR   Message;
+        Message = GetErrorMessage(Error);
+        Log("fail1 (%s)", Message);
+        LocalFree(Message);
     }
 
-    Error = RegDeleteValue(Context->ParametersKey,
-                           "RebootCount");
-    if (Error == ERROR_SUCCESS)
-        (VOID) RegFlushKey(Context->ParametersKey);
+    return Error;
+}
 
-    goto done;
+static BOOLEAN
+CheckRequestSubKey(
+    _In_ HKEY           BaseKey,
+    _In_ PTSTR          SubKeyName,
+    _In_opt_ PVOID      Context
+    )
+{
+    DWORD               Length;
+    DWORD               Reboot;
+    DWORD               Type;
+    HKEY                SubKey;
+    HRESULT             Error;
+    PBOOLEAN            Found = (PBOOLEAN)Context;
 
-found:
-    RegCloseKey(SubKey);
+    Error = RegOpenKeyEx(BaseKey,
+                         SubKeyName,
+                         0,
+                         KEY_READ,
+                         &SubKey);
+    if (Error != ERROR_SUCCESS)
+        return TRUE;
+
+    Length = sizeof (DWORD);
+    Error = RegQueryValueEx(SubKey,
+                            "Reboot",
+                            NULL,
+                            &Type,
+                            (LPBYTE)&Reboot,
+                            &Length);
+    if (Error != ERROR_SUCCESS ||
+        Type != REG_DWORD)
+        goto loop;
+
+    if (Reboot == 0)
+        goto loop;
 
-    if (!Context->RebootRequestedBy)
+    if (Found != NULL)
+        *Found = TRUE;
+
+    if (!MonitorContext.RebootRequestedBy)
         TryAutoReboot(SubKeyName);
 
-done:
-    free(SubKeyName);
+loop:
+    RegCloseKey(SubKey);
 
-    Log("<====");
+    return (Found != NULL) ? !(*Found) : TRUE;
+}
 
-    return;
+static VOID
+CheckRequestSubKeys(
+    VOID
+    )
+{
+    PMONITOR_CONTEXT    Context = &MonitorContext;
+    BOOLEAN             Found;
+    HRESULT             Error;
 
-fail3:
-    Log("fail3");
+    Log("====>");
 
-    free(SubKeyName);
+    Found = FALSE;
 
-fail2:
-    Log("fail2");
+    Error = RegEnumSubKeys(Context->RequestKey,
+                           CheckRequestSubKey,
+                           &Found);
+    if (Error != ERROR_SUCCESS)
+        goto fail1;
+
+    if (!Found) {
+        Error = RegDeleteValue(Context->ParametersKey,
+                               "RebootCount");
+        if (Error == ERROR_SUCCESS)
+            (VOID) RegFlushKey(Context->ParametersKey);
+    }
+
+    Log("<====");
+
+    return;
 
 fail1:
     Error = GetLastError();
-- 
2.51.2.windows.1




 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.