2 * PROJECT: ReactOS Device Managment
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: base/system/devmgmt/enumdevices.c
5 * PURPOSE: Enumerates all devices on the local machine
6 * COPYRIGHT: Copyright 2006 Ged Murphy <gedmurphy@gmail.com>
12 static SP_CLASSIMAGELIST_DATA ImageListData
;
13 static HDEVINFO hDevInfo
;
17 FreeDeviceStrings(HWND hTreeView
)
21 hItem
= TreeView_GetRoot(hTreeView
);
25 hItem
= TreeView_GetChild(hTreeView
,
27 /* loop the parent items */
30 hItem
= TreeView_GetChild(hTreeView
,
35 /* loop the child items and free the DeviceID */
43 tvItem
.mask
= TVIF_PARAM
;// | TVIF_TEXT;
44 //tvItem.pszText = Buf;
45 //tvItem.cchTextMax = 99;
47 (void)TreeView_GetItem(hTreeView
, &tvItem
);
49 //MessageBox(NULL, Buf, NULL, 0);
51 HeapFree(GetProcessHeap(),
53 (LPTSTR
)tvItem
.lParam
);
57 hItem
= TreeView_GetNextSibling(hTreeView
,
66 hItem
= TreeView_GetParent(hTreeView
,
68 hItem
= TreeView_GetNextSibling(hTreeView
,
76 OpenPropSheet(HWND hTreeView
,
82 tvItem
.mask
= TVIF_PARAM
;
84 if (TreeView_GetItem(hTreeView
, &tvItem
) &&
85 (LPTSTR
)tvItem
.lParam
!= NULL
)
87 DevicePropertiesExW(hTreeView
,
89 (LPTSTR
)tvItem
.lParam
,
98 InsertIntoTreeView(HWND hTreeView
,
106 TV_INSERTSTRUCT tvins
;
108 ZeroMemory(&tvi
, sizeof(tvi
));
109 ZeroMemory(&tvins
, sizeof(tvins
));
111 tvi
.mask
= TVIF_TEXT
| TVIF_PARAM
| TVIF_IMAGE
| TVIF_SELECTEDIMAGE
;
112 tvi
.pszText
= lpLabel
;
113 tvi
.cchTextMax
= lstrlen(lpLabel
);
114 tvi
.lParam
= (LPARAM
)DeviceID
;
115 tvi
.iImage
= DevImage
;
116 tvi
.iSelectedImage
= DevImage
;
120 tvi
.stateMask
= TVIS_OVERLAYMASK
;
122 if (DevProb
== CM_PROB_DISABLED
)
124 /* FIXME: set the overlay icon */
130 tvins
.hParent
= hRoot
;
132 return TreeView_InsertItem(hTreeView
, &tvins
);
137 EnumDeviceClasses(INT ClassIndex
,
145 TCHAR ClassName
[MAX_CLASS_NAME_LEN
];
146 DWORD RequiredSize
= MAX_CLASS_NAME_LEN
;
150 *DevClassName
= _T('\0');
152 Ret
= CM_Enumerate_Classes(ClassIndex
,
155 if (Ret
!= CR_SUCCESS
)
157 /* all classes enumerated */
158 if(Ret
== CR_NO_SUCH_VALUE
)
164 if (Ret
== CR_INVALID_DATA
)
166 ; /*FIXME: what should we do here? */
169 /* handle other errors... */
172 if (SetupDiClassNameFromGuid(&ClassGuid
,
177 lstrcpy(DevClassName
, ClassName
);
180 if (!SetupDiGetClassImageIndex(&ImageListData
,
184 /* FIXME: can we do this?
185 * Set the blank icon: IDI_SETUPAPI_BLANK = 41
186 * it'll be image 24 in the imagelist */
190 /* Get device info for all devices of a particular class */
191 hDevInfo
= SetupDiGetClassDevs(&ClassGuid
,
195 if (hDevInfo
== INVALID_HANDLE_VALUE
)
201 KeyClass
= SetupDiOpenClassRegKeyEx(&ClassGuid
,
206 if (KeyClass
!= INVALID_HANDLE_VALUE
)
209 LONG dwSize
= MAX_DEV_LEN
;
211 if (RegQueryValue(KeyClass
,
214 &dwSize
) != ERROR_SUCCESS
)
216 *DevClassDesc
= _T('\0');
226 RegCloseKey(KeyClass
);
233 EnumDevices(INT index
,
234 LPTSTR DeviceClassName
,
238 SP_DEVINFO_DATA DeviceInfoData
;
240 ULONG Status
, ProblemNumber
;
243 *DeviceName
= _T('\0');
246 ZeroMemory(&DeviceInfoData
, sizeof(SP_DEVINFO_DATA
));
247 DeviceInfoData
.cbSize
= sizeof(SP_DEVINFO_DATA
);
249 if (!SetupDiEnumDeviceInfo(hDevInfo
,
257 /* get the device ID */
258 if (!SetupDiGetDeviceInstanceId(hDevInfo
,
264 if (GetLastError() == ERROR_INSUFFICIENT_BUFFER
)
266 (*DeviceID
) = (LPTSTR
)HeapAlloc(GetProcessHeap(),
268 DevIdSize
* sizeof(TCHAR
));
271 if (!SetupDiGetDeviceInstanceId(hDevInfo
,
277 HeapFree(GetProcessHeap(),
286 /* get the device's friendly name */
287 if (!SetupDiGetDeviceRegistryProperty(hDevInfo
,
295 /* if the friendly name fails, try the description instead */
296 SetupDiGetDeviceRegistryProperty(hDevInfo
,
305 cr
= CM_Get_DevNode_Status_Ex(&Status
,
307 DeviceInfoData
.DevInst
,
310 if (cr
== CR_SUCCESS
&& (Status
& DN_HAS_PROBLEM
))
312 return ProblemNumber
;
320 ListDevicesByType(HWND hTreeView
,
324 TCHAR DevName
[MAX_DEV_LEN
];
325 TCHAR DevDesc
[MAX_DEV_LEN
];
326 LPTSTR DeviceID
= NULL
;
327 BOOL DevExist
= FALSE
;
334 ClassRet
= EnumDeviceClasses(index
,
340 if ((ClassRet
!= -1) && (DevExist
))
342 TCHAR DeviceName
[MAX_DEV_LEN
];
346 if (DevDesc
[0] != _T('\0'))
348 hDevItem
= InsertIntoTreeView(hTreeView
,
357 hDevItem
= InsertIntoTreeView(hTreeView
,
367 Ret
= EnumDevices(DevIndex
,
373 InsertIntoTreeView(hTreeView
,
385 /* kill InfoList initialized in EnumDeviceClasses */
388 SetupDiDestroyDeviceInfoList(hDevInfo
);
392 /* don't insert classes with no devices */
393 if (!TreeView_GetChild(hTreeView
,
396 (void)TreeView_DeleteItem(hTreeView
,
401 (void)TreeView_SortChildren(hTreeView
,
409 } while (ClassRet
!= -1);
411 (void)TreeView_Expand(hTreeView
,
415 (void)TreeView_SortChildren(hTreeView
,
422 InitTreeView(HWND hTreeView
)
426 TCHAR ComputerName
[MAX_PATH
];
427 DWORD dwSize
= MAX_PATH
;
430 (void)TreeView_DeleteAllItems(hTreeView
);
432 /* get the device image List */
433 ImageListData
.cbSize
= sizeof(ImageListData
);
434 SetupDiGetClassImageList(&ImageListData
);
436 hComp
= LoadBitmap(hInstance
,
437 MAKEINTRESOURCE(IDB_ROOT_IMAGE
));
439 ImageList_Add(ImageListData
.ImageList
,
445 (void)TreeView_SetImageList(hTreeView
,
446 ImageListData
.ImageList
,
449 if (!GetComputerName(ComputerName
,
452 ComputerName
[0] = _T('\0');
455 RootImage
= ImageList_GetImageCount(ImageListData
.ImageList
) - 1;
457 /* insert the root item into the tree */
458 hRoot
= InsertIntoTreeView(hTreeView
,