Commit 62520da8 authored by Alexander Morozov's avatar Alexander Morozov Committed by Alexandre Julliard

setupapi: Prevent of reallocating memory for _SP_DEVINFO_DATA structures.

parent cb2274e6
......@@ -98,7 +98,13 @@ struct DeviceInfoSet
GUID ClassGuid;
HWND hwndParent;
DWORD cDevices;
SP_DEVINFO_DATA *devices;
struct list devices;
};
struct DeviceInstance
{
struct list entry;
SP_DEVINFO_DATA data;
};
/* Pointed to by SP_DEVICE_INTERFACE_DATA's Reserved member */
......@@ -541,27 +547,24 @@ static BOOL SETUPDI_AddDeviceToSet(struct DeviceInfoSet *set,
if (devInfo)
{
if (set->devices)
set->devices = HeapReAlloc(GetProcessHeap(), 0, set->devices,
(set->cDevices + 1) * sizeof(SP_DEVINFO_DATA));
else
set->devices = HeapAlloc(GetProcessHeap(), 0,
sizeof(SP_DEVINFO_DATA));
if (set->devices)
struct DeviceInstance *devInst =
HeapAlloc(GetProcessHeap(), 0, sizeof(struct DeviceInstance));
if (devInst)
{
WCHAR classGuidStr[39];
SP_DEVINFO_DATA *DeviceInfoData = &set->devices[set->cDevices++];
DeviceInfoData->cbSize = sizeof(SP_DEVINFO_DATA);
DeviceInfoData->ClassGuid = *guid;
DeviceInfoData->DevInst = devInfo->devId;
DeviceInfoData->Reserved = (ULONG_PTR)devInfo;
list_add_tail(&set->devices, &devInst->entry);
set->cDevices++;
devInst->data.cbSize = sizeof(SP_DEVINFO_DATA);
devInst->data.ClassGuid = *guid;
devInst->data.DevInst = devInfo->devId;
devInst->data.Reserved = (ULONG_PTR)devInfo;
SETUPDI_GuidToString(guid, classGuidStr);
SetupDiSetDeviceRegistryPropertyW((HDEVINFO)set,
DeviceInfoData, SPDRP_CLASSGUID, (const BYTE *)classGuidStr,
&devInst->data, SPDRP_CLASSGUID, (const BYTE *)classGuidStr,
lstrlenW(classGuidStr) * sizeof(WCHAR));
if (dev)
*dev = DeviceInfoData;
if (dev) *dev = &devInst->data;
ret = TRUE;
}
else
......@@ -1185,7 +1188,7 @@ SetupDiCreateDeviceInfoListExW(const GUID *ClassGuid,
ClassGuid ? ClassGuid : &GUID_NULL,
sizeof(list->ClassGuid));
list->cDevices = 0;
list->devices = NULL;
list_init(&list->devices);
return (HDEVINFO)list;
}
......@@ -1423,12 +1426,12 @@ BOOL WINAPI SetupDiCreateDeviceInfoW(
if (set->cDevices)
{
DWORD i, highestDevID = 0;
DWORD highestDevID = 0;
struct DeviceInstance *devInst;
for (i = 0; i < set->cDevices; i++)
LIST_FOR_EACH_ENTRY(devInst, &set->devices, struct DeviceInstance, entry)
{
struct DeviceInfo *devInfo =
(struct DeviceInfo *)set->devices[i].Reserved;
struct DeviceInfo *devInfo = (struct DeviceInfo *)devInst->data.Reserved;
LPCWSTR devName = strrchrW(devInfo->instanceId, '\\');
DWORD id;
......@@ -1460,14 +1463,13 @@ BOOL WINAPI SetupDiCreateDeviceInfoW(
}
else
{
DWORD i;
struct DeviceInstance *devInst;
ret = TRUE;
instanceId = DeviceName;
for (i = 0; ret && i < set->cDevices; i++)
LIST_FOR_EACH_ENTRY(devInst, &set->devices, struct DeviceInstance, entry)
{
struct DeviceInfo *devInfo =
(struct DeviceInfo *)set->devices[i].Reserved;
struct DeviceInfo *devInfo = (struct DeviceInfo *)devInst->data.Reserved;
if (!lstrcmpiW(DeviceName, devInfo->instanceId))
{
......@@ -1579,7 +1581,18 @@ BOOL WINAPI SetupDiEnumDeviceInfo(
{
if (info->cbSize == sizeof(SP_DEVINFO_DATA))
{
memcpy(info, &list->devices[index], info->cbSize);
struct DeviceInstance *devInst;
DWORD i = 0;
LIST_FOR_EACH_ENTRY(devInst, &list->devices,
struct DeviceInstance, entry)
{
if (i++ == index)
{
*info = devInst->data;
break;
}
}
ret = TRUE;
}
else
......@@ -2817,16 +2830,17 @@ BOOL WINAPI SetupDiEnumDeviceInterfaces(
}
else
{
DWORD i, cEnumerated = 0;
struct DeviceInstance *devInst;
DWORD cEnumerated = 0;
BOOL found = FALSE;
for (i = 0; !found && cEnumerated < MemberIndex + 1 &&
i < set->cDevices; i++)
LIST_FOR_EACH_ENTRY(devInst, &set->devices, struct DeviceInstance, entry)
{
struct DeviceInfo *devInfo =
(struct DeviceInfo *)set->devices[i].Reserved;
struct DeviceInfo *devInfo = (struct DeviceInfo *)devInst->data.Reserved;
struct InterfaceInstances *iface;
if (found || cEnumerated >= MemberIndex + 1)
break;
if (SETUPDI_FindInterface(devInfo, InterfaceClassGuid, &iface))
{
if (cEnumerated + iface->cInstances < MemberIndex + 1)
......@@ -2871,12 +2885,15 @@ BOOL WINAPI SetupDiDestroyDeviceInfoList(HDEVINFO devinfo)
if (list->magic == SETUP_DEVICE_INFO_SET_MAGIC)
{
DWORD i;
struct DeviceInstance *devInst, *devInst2;
for (i = 0; i < list->cDevices; i++)
SETUPDI_FreeDeviceInfo(
(struct DeviceInfo *)list->devices[i].Reserved);
HeapFree(GetProcessHeap(), 0, list->devices);
LIST_FOR_EACH_ENTRY_SAFE(devInst, devInst2, &list->devices,
struct DeviceInstance, entry)
{
SETUPDI_FreeDeviceInfo( (struct DeviceInfo *)devInst->data.Reserved );
list_remove(&devInst->entry);
HeapFree(GetProcessHeap(), 0, devInst);
}
HeapFree(GetProcessHeap(), 0, list);
ret = TRUE;
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment