From: Vibhav Pant vibhavp@gmail.com
--- dlls/cfgmgr32/main.c | 94 ++++++++++++++++++++++++++++++++-- dlls/cfgmgr32/tests/cfgmgr32.c | 6 +-- 2 files changed, 93 insertions(+), 7 deletions(-)
diff --git a/dlls/cfgmgr32/main.c b/dlls/cfgmgr32/main.c index 28b43a22b3c..6dbdc9ef9ef 100644 --- a/dlls/cfgmgr32/main.c +++ b/dlls/cfgmgr32/main.c @@ -295,8 +295,33 @@ CONFIGRET WINAPI CM_Get_Device_Interface_PropertyW( LPCWSTR device_interface, co } }
-BOOL dev_objects_append_iface( DEV_OBJECT **objects, ULONG *len, const WCHAR *path, DEV_OBJECT_TYPE type ) +static BOOL dev_properties_append( DEVPROPERTY **properties, ULONG *props_len, const DEVPROPKEY *key, DEVPROPTYPE type, + ULONG buf_size, void *buf ) { + DEVPROPERTY *tmp; + + if (!(tmp = realloc( *properties, (*props_len + 1) * sizeof( **properties )))) + return FALSE; + *properties = tmp; + + tmp = &tmp[*props_len]; + tmp->CompKey.Key = *key; + tmp->CompKey.Store = DEVPROP_STORE_SYSTEM; + tmp->CompKey.LocaleName = NULL; + tmp->Type = type; + tmp->BufferSize = buf_size; + tmp->Buffer = buf; + + *props_len += 1; + return TRUE; +} + +BOOL dev_objects_append_iface( DEV_OBJECT **objects, ULONG *len, const WCHAR *path, DEV_OBJECT_TYPE type, HDEVINFO set, + SP_DEVICE_INTERFACE_DATA *iface_data, ULONG props_len, const DEVPROPCOMPKEY *props, + BOOL all_props ) +{ + DEVPROPKEY *all_keys = NULL; + DWORD keys_len = 0, i = 0; DEV_OBJECT *tmp; WCHAR *id;
@@ -316,6 +341,58 @@ BOOL dev_objects_append_iface( DEV_OBJECT **objects, ULONG *len, const WCHAR *pa tmp->pProperties = NULL;
*len += 1; + + if (!props && !all_props) + return TRUE; + + if (all_props) + { + DWORD req = 0; + if (SetupDiGetDeviceInterfacePropertyKeys( set, iface_data, NULL, 0, &req, 0 ) + || GetLastError() != ERROR_INSUFFICIENT_BUFFER) + return TRUE; + + keys_len = req; + if (!(all_keys = calloc( keys_len, sizeof( *all_keys ) ))) + return TRUE; + if (!SetupDiGetDeviceInterfacePropertyKeys( set, iface_data, all_keys, keys_len, &req, 0 )) + { + free( all_keys ); + return TRUE; + } + } + else + keys_len = props_len; + + for (i = 0; i < keys_len; i++) + { + const DEVPROPKEY *key = all_keys ? &all_keys[i] : &props[i].Key; + DWORD req = 0, size; + DEVPROPTYPE type; + BYTE *buf; + + if (props && props[i].Store != DEVPROP_STORE_SYSTEM) + { + FIXME( "Unsupported Store value: %d\n", props[i].Store ); + continue; + } + if (SetupDiGetDeviceInterfacePropertyW( set, iface_data, key, &type, NULL, 0, &req, 0 ) + || GetLastError() != ERROR_INSUFFICIENT_BUFFER) + { + if (props) + dev_properties_append( (DEVPROPERTY **)&tmp->pProperties, &tmp->cPropertyCount, key, DEVPROP_TYPE_EMPTY, + 0, NULL ); + } + + size = req; + if (!(buf = calloc( 1, size ))) continue; + if (SetupDiGetDeviceInterfacePropertyW( set, iface_data, key, &type, buf, size, &req, 0 ) + && dev_properties_append( (DEVPROPERTY **)&tmp->pProperties, &tmp->cPropertyCount, key, type, size, buf )) + continue; + free( buf ); + } + + free( all_keys ); return TRUE; }
@@ -341,8 +418,6 @@ HRESULT WINAPI DevGetObjectsEx( DEV_OBJECT_TYPE type, ULONG flags, ULONG props_l
if (!!props_len != !!props || !!filters_len != !!filters || !!params_len != !!params || (flags & ~valid_flags)) return E_INVALIDARG; - if (props || flags & DevQueryFlagAllProperties) - FIXME( "Object properties are not supported!\n" ); if (filters) FIXME( "Query filters are not supported!\n" ); if (params) @@ -392,7 +467,9 @@ HRESULT WINAPI DevGetObjectsEx( DEV_OBJECT_TYPE type, ULONG flags, ULONG props_l { detail->cbSize = sizeof( *detail ); if (!SetupDiGetDeviceInterfaceDetailW( set, &iface, detail, sizeof( buffer ), NULL, NULL )) continue; - if (!dev_objects_append_iface( &objects, &objects_len, detail->DevicePath, type )) hr = E_OUTOFMEMORY; + if (!dev_objects_append_iface( &objects, &objects_len, detail->DevicePath, type, set, &iface, props_len, + props, !!(flags & DevQueryFlagAllProperties) )) + hr = E_OUTOFMEMORY; }
if (set != INVALID_HANDLE_VALUE) @@ -435,7 +512,16 @@ void WINAPI DevFreeObjects( ULONG objs_len, const DEV_OBJECT *objs ) TRACE( "(%lu, %p)\n", objs_len, objs );
for (i = 0; i < objs_len; i++) + { + DEVPROPERTY *props = (DEVPROPERTY *)objects[i].pProperties; + ULONG j; + + for (j = 0; j < objects[i].cPropertyCount; j++) + free( props[j].Buffer ); + free( props ); + free( (void *)objects[i].pszObjectId ); + } free( objects ); return; } diff --git a/dlls/cfgmgr32/tests/cfgmgr32.c b/dlls/cfgmgr32/tests/cfgmgr32.c index 02741d0d963..e217534261e 100644 --- a/dlls/cfgmgr32/tests/cfgmgr32.c +++ b/dlls/cfgmgr32/tests/cfgmgr32.c @@ -589,8 +589,8 @@ static void test_DevGetObjects( void )
winetest_push_context( "device %s", debugstr_w( obj->pszObjectId ) ); ok( obj->ObjectType == test_cases[i].object_type, "got ObjectType %d\n", obj->ObjectType ); - todo_wine ok( obj->cPropertyCount >= test_cases[i].props_len, "got cPropertyCount %lu, should be >= %lu\n", - obj->cPropertyCount, test_cases[i].props_len ); + ok( obj->cPropertyCount >= test_cases[i].props_len, "got cPropertyCount %lu, should be >= %lu\n", + obj->cPropertyCount, test_cases[i].props_len ); for (k = 0; k < obj->cPropertyCount && rem_props; k++) { const DEVPROPERTY *property = &obj->pProperties[k]; @@ -641,7 +641,7 @@ static void test_DevGetObjects( void ) } } } - todo_wine ok( rem_props == 0, "got rem %lu != 0\n", rem_props ); + ok( rem_props == 0, "got rem %lu != 0\n", rem_props ); winetest_pop_context(); } winetest_pop_context();