https://git.reactos.org/?p=reactos.git;a=commitdiff;h=8bf3f3feb96697d5bee34…
commit 8bf3f3feb96697d5bee34ccc0fd4c4a4022ee387
Author: Eric Kohl <eric.kohl(a)reactos.org>
AuthorDate: Sat Nov 9 18:48:10 2019 +0100
Commit: Eric Kohl <eric.kohl(a)reactos.org>
CommitDate: Sat Nov 9 18:48:10 2019 +0100
[UMPNPMGR] Validate device instance IDs before use
---
base/services/umpnpmgr/rpcserver.c | 109 ++++++++++++++++++++++++++++++++++++-
1 file changed, 108 insertions(+), 1 deletion(-)
diff --git a/base/services/umpnpmgr/rpcserver.c b/base/services/umpnpmgr/rpcserver.c
index 70f77600f9c..e8a4890ffda 100644
--- a/base/services/umpnpmgr/rpcserver.c
+++ b/base/services/umpnpmgr/rpcserver.c
@@ -226,6 +226,72 @@ GetDeviceStatus(
}
+static
+BOOL
+IsValidDeviceInstanceID(
+ _In_ PWSTR pszDeviceInstanceID)
+{
+ INT nPartLength[3] = {0, 0, 0};
+ INT nLength = 0, nParts = 0;
+ PWCHAR p;
+
+ DPRINT("IsValidDeviceInstanceID(%S)\n",
+ pszDeviceInstanceID);
+
+ if (pszDeviceInstanceID == NULL)
+ {
+ DPRINT("Device instance ID is NULL!\n");
+ return FALSE;
+ }
+
+ p = pszDeviceInstanceID;
+ while (*p != UNICODE_NULL)
+ {
+ if (*p == L'\\')
+ {
+ nParts++;
+ if (nParts >= 3)
+ {
+ DPRINT("Too many separators: %d\n", nParts);
+ return FALSE;
+ }
+ }
+ else
+ {
+ nPartLength[nParts]++;
+ }
+
+ nLength++;
+ if (nLength >= MAX_DEVICE_ID_LEN)
+ {
+ DPRINT("Too long: %d\n", nLength);
+ return FALSE;
+ }
+
+ p++;
+ }
+
+ if (nParts != 2)
+ {
+ DPRINT("Invalid number of separtors: %d\n", nParts);
+ return FALSE;
+ }
+
+ if ((nPartLength[0] == 0) ||
+ (nPartLength[1] == 0) ||
+ (nPartLength[2] == 0))
+ {
+ DPRINT("Invalid part lengths: %d %d %d\n",
+ nPartLength[0], nPartLength[1], nPartLength[2]);
+ return FALSE;
+ }
+
+ DPRINT("Valid device instance ID!\n");
+
+ return TRUE;
+}
+
+
/* PUBLIC FUNCTIONS **********************************************************/
/* Function 0 */
@@ -361,6 +427,9 @@ PNP_ValidateDeviceInstance(
DPRINT("PNP_ValidateDeviceInstance(%S %lx) called\n",
pDeviceID, ulFlags);
+ if (!IsValidDeviceInstanceID(pDeviceID))
+ return CR_INVALID_DEVINST;
+
if (RegOpenKeyExW(hEnumKey,
pDeviceID,
0,
@@ -441,6 +510,9 @@ PNP_GetRelatedDeviceInstance(
DPRINT(" Relationship %ld\n", ulRelationship);
DPRINT(" DeviceId %S\n", pDeviceID);
+ if (!IsValidDeviceInstanceID(pDeviceID))
+ return CR_INVALID_DEVINST;
+
RtlInitUnicodeString(&PlugPlayData.TargetDeviceInstance,
pDeviceID);
@@ -1349,6 +1421,9 @@ PNP_GetDepth(
DPRINT("PNP_GetDepth() called\n");
+ if (!IsValidDeviceInstanceID(pszDeviceID))
+ return CR_INVALID_DEVINST;
+
RtlInitUnicodeString(&PlugPlayData.DeviceInstance,
pszDeviceID);
@@ -1406,7 +1481,12 @@ PNP_GetDeviceRegProp(
goto done;
}
- /* FIXME: Check pDeviceID */
+ /* Check pDeviceID */
+ if (!IsValidDeviceInstanceID(pDeviceID))
+ {
+ ret = CR_INVALID_DEVINST;
+ goto done;
+ }
if (*pulLength < *pulTransferLen)
*pulLength = *pulTransferLen;
@@ -1653,6 +1733,9 @@ PNP_SetDeviceRegProp(
DPRINT("DataType: %lu\n", ulDataType);
DPRINT("Length: %lu\n", ulLength);
+ if (!IsValidDeviceInstanceID(pDeviceId))
+ return CR_INVALID_DEVINST;
+
switch (ulProperty)
{
case CM_DRP_DEVICEDESC:
@@ -1790,6 +1873,9 @@ PNP_GetClassInstance(
DPRINT("PNP_GetClassInstance(%p %S %p %lu)\n",
hBinding, pDeviceId, pszClassInstance, ulLength);
+ if (!IsValidDeviceInstanceID(pDeviceId))
+ return CR_INVALID_DEVINST;
+
ulTransferLength = ulLength;
ret = PNP_GetDeviceRegProp(hBinding,
pDeviceId,
@@ -2091,6 +2177,9 @@ PNP_GetInterfaceDeviceList(
UNREFERENCED_PARAMETER(hBinding);
+ if (!IsValidDeviceInstanceID(pszDeviceID))
+ return CR_INVALID_DEVINST;
+
RtlInitUnicodeString(&PlugPlayData.DeviceInstance,
pszDeviceID);
@@ -2134,6 +2223,9 @@ PNP_GetInterfaceDeviceListSize(
DPRINT("PNP_GetInterfaceDeviceListSize() called\n");
+ if (!IsValidDeviceInstanceID(pszDeviceID))
+ return CR_INVALID_DEVINST;
+
RtlInitUnicodeString(&PlugPlayData.DeviceInstance,
pszDeviceID);
@@ -2729,6 +2821,9 @@ PNP_GetDeviceStatus(
DPRINT("PNP_GetDeviceStatus(%p %S %p %p)\n",
hBinding, pDeviceID, pulStatus, pulProblem, ulFlags);
+ if (!IsValidDeviceInstanceID(pDeviceID))
+ return CR_INVALID_DEVINST;
+
return GetDeviceStatus(pDeviceID, pulStatus, pulProblem);
}
@@ -2961,6 +3056,9 @@ PNP_QueryRemove(
if (ulFlags & ~CM_REMOVE_BITS)
return CR_INVALID_FLAG;
+ if (!IsValidDeviceInstanceID(pszDeviceID))
+ return CR_INVALID_DEVINST;
+
if (pVetoType != NULL)
*pVetoType = PNP_VetoTypeUnknown;
@@ -3006,6 +3104,9 @@ PNP_RequestDeviceEject(
if (ulFlags != 0)
return CR_INVALID_FLAG;
+ if (!IsValidDeviceInstanceID(pszDeviceID))
+ return CR_INVALID_DEVINST;
+
if (pVetoType != NULL)
*pVetoType = PNP_VetoTypeUnknown;
@@ -3140,6 +3241,9 @@ PNP_HwProfFlags(
DPRINT("PNP_HwProfFlags() called\n");
+ if (!IsValidDeviceInstanceID(pDeviceID))
+ return CR_INVALID_DEVINST;
+
if (ulConfig == 0)
{
wcscpy(szKeyName,
@@ -3748,6 +3852,9 @@ PNP_GetCustomDevProp(
goto done;
}
+ if (!IsValidDeviceInstanceID(pDeviceID))
+ return CR_INVALID_DEVINST;
+
if (*pulLength < *pulTransferLen)
*pulLength = *pulTransferLen;