Войти

Показать полную графическую версию : [решено] Получить список оборудования с неустановленными/неправильно установленными драйверами


saavaage
05-08-2010, 22:15
Собственно проблема:

1. Можно ли штатными средствами autoit получить список проблемного оборудования в системе? Под проблемным я понимаю: без драйверов, с некорректно работающим (установленными) драйверами.
Если, да, то покажите где искать. Буду благодарен за любую помощь.
2. Список - в простом виде (Название железа - проблема), в виде Диспетчера устройств с таким же функционалом (но только, не всех, а проблемных) было бы идеально.

PS "штатными" означает - без использования сторонних утилит. Использовать "родные" средства Win XP можно.

madmasles
05-08-2010, 22:48
saavaage,
Есть такая UDF: DeviceAPI.au3 (http://www.autoitscript.com/forum/index.php?showtopic=77731). Посмотрите в ней.

saavaage
06-08-2010, 00:03
madmasles, посмотрел функции, посмотрел примеры. Не понял как использовать. Как вывести все оборудование, которое есть -понятно, но как наложить ограничение вывода по признаку "отсутствие драйвера", не понимаю.

Код примера с гуи из http://www.autoitscript.com/forum/index.php?showtopic=77731

#include <GuiConstantsEx.au3>
#include <GuiTreeView.au3>
#include <TreeViewConstants.au3>
#Include <GuiListView.au3>
#include <WindowsConstants.au3>
#include <GuiImageList.au3>
#include "DeviceAPI.au3"

Global $aAssoc[1][2]

$GUI = GUICreate("Device Management API - GUI Example", 800, 500)

Dim $iStyle = BitOR($TVS_EDITLABELS, $TVS_HASBUTTONS, $TVS_HASLINES, $TVS_LINESATROOT, $TVS_DISABLEDRAGDROP, $TVS_SHOWSELALWAYS)
$hTreeView = _GUICtrlTreeView_Create($GUI, 5, 5, 300, 450, $iStyle, $WS_EX_STATICEDGE )
$hListView = GUICtrlCreateListView ("Key|Value", 310, 5, 485,450)
GUISetState()

GUIRegisterMsg($WM_NOTIFY, "WM_NOTIFY")

;Assign image list to treeview
_GUICtrlTreeView_SetNormalImageList($hTreeView, _DeviceAPI_GetClassImageList())

Dim $total_devices = 0

_DeviceAPI_GetClasses()
While _DeviceAPI_EnumClasses()
;Get icon index from image list for given class
$Icon_Index = _DeviceAPI_GetClassImageIndex($p_currentGUID)

;Build list of devices within current class, if class doesn't contain any devices it will be skipped
_DeviceAPI_GetClassDevices($p_currentGUID)

;Skip classes without devices
If _DeviceAPI_GetDeviceCount() > 0 Then
;Add parent class to treeview
$parent = _GUICtrlTreeView_Add($hTreeView, 0, _DeviceAPI_GetClassDescription($p_currentGUID), $Icon_Index, $Icon_Index)

;Loop through all devices by index
While _DeviceAPI_EnumDevices()

$description = _DeviceAPI_GetDeviceRegistryProperty($SPDRP_DEVICEDESC)
$friendly_name = _DeviceAPI_GetDeviceRegistryProperty($SPDRP_FRIENDLYNAME)

;If a friendly name is available, use it instead of description
If $friendly_name <> "" Then $description = $friendly_name

;Add device to treeview below parent
$handle = _GUICtrlTreeView_AddChild($hTreeView, $parent, $description, $Icon_Index, $Icon_Index)

If $total_devices > 0 Then
ReDim $aAssoc[$total_devices+1][2]
EndIf

;Add treeview item handle to array along with device Unique Instance Id (For lookup)
$aAssoc[$total_devices][0] = $handle
$aAssoc[$total_devices][1] = _DeviceAPI_GetDeviceId()

;Update running total count of devices
$total_devices += 1
WEnd
EndIf
WEnd

While 1
Switch GUIGetMsg()
Case $GUI_EVENT_CLOSE
ExitLoop
EndSwitch
WEnd

Func WM_NOTIFY($hWnd, $iMsg, $iwParam, $ilParam)
#forceref $hWnd, $iMsg, $iwParam
Local $hWndFrom, $iIDFrom, $iCode, $tNMHDR, $hWndTreeview

$hWndTreeview = $hTreeView
If Not IsHWnd($hTreeView) Then $hWndTreeview = GUICtrlGetHandle($hTreeView)

$tNMHDR = DllStructCreate($tagNMHDR, $ilParam)
$hWndFrom = HWnd(DllStructGetData($tNMHDR, "hWndFrom"))
$iIDFrom = DllStructGetData($tNMHDR, "IDFrom")
$iCode = DllStructGetData($tNMHDR, "Code")
Switch $hWndFrom
Case $hWndTreeview
Switch $iCode
Case $TVN_SELCHANGEDA, $TVN_SELCHANGEDW
RefreshDeviceProperties()
EndSwitch
EndSwitch
Return $GUI_RUNDEFMSG
EndFunc ;==>WM_NOTIFY

;Triggered when a device is selected in the treeview
Func RefreshDeviceProperties()
Local $hSelected = _GUICtrlTreeView_GetSelection($hTreeView)

;Don't do anything if a class name (root item) was clicked
If _GUICtrlTreeView_Level($hTreeView, $hSelected) = 0 Then Return

;Lookup treeview item handle in global array
For $X = 0 to Ubound($aAssoc)-1

If $hSelected = $aAssoc[$X][0] Then
;MsgBox(0,"", "Handle: " & $aAssoc[$X][0] & @CRLF & "Unique Instance Id: " & $aAssoc[$X][1])

;Build list of ALL device classes
_DeviceAPI_GetClassDevices()

;Loop through all devices by index
While _DeviceAPI_EnumDevices()
If $aAssoc[$X][1] = _DeviceAPI_GetDeviceId() Then

;Empty listview
_GUICtrlListView_DeleteAllItems($hListView)

GUICtrlCreateListViewItem ("Hardware ID: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_HARDWAREID), $hListView )
GUICtrlCreateListViewItem ("Unique Instance ID: |" & _DeviceAPI_GetDeviceId(), $hListView )
GUICtrlCreateListViewItem ("Manufacturer: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_MFG), $hListView )
GUICtrlCreateListViewItem ("Driver: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_DRIVER), $hListView )
GUICtrlCreateListViewItem ("Friendly Name: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_FRIENDLYNAME), $hListView )
GUICtrlCreateListViewItem ("Physical Device Object Name: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_PHYSICAL_DEVICE_OBJECT_NAME), $hListView )
GUICtrlCreateListViewItem ("Upper Filters: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_UPPERFILTERS), $hListView )
GUICtrlCreateListViewItem ("Lower Filters: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_LOWERFILTERS), $hListView )
GUICtrlCreateListViewItem ("Enumerator: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_ENUMERATOR_NAME), $hListView )

;Resize columns to fit text
_GUICtrlListView_SetColumnWidth($hListView, 0,$LVSCW_AUTOSIZE)
_GUICtrlListView_SetColumnWidth($hListView, 1,$LVSCW_AUTOSIZE)
EndIf
WEnd
EndIf
Next
EndFunc

;Cleanup image list
_DeviceAPI_DestroyClassImageList()

_DeviceAPI_DestroyDeviceInfoList() ;Cleanup for good measure

Есть подозрение, что надо рыть в сторону функции _DeviceAPI_GetDeviceRegistryProperty и делать проверку на отсутствие значения у переменной $SPDRP_DRIVER, но как это вставить в скрипт?

madmasles
06-08-2010, 10:14
saavaage,
Мне кажется, что надо копать в сторону системной библиотеки devmgr.dll. В ней есть 4 функции DeviceProblem.... Но как ей пользоваться, я не знаю.

saavaage
06-08-2010, 10:25
madmasles, к сожалению для меня, я -тоже не знаю... Остается надеяться, что, м.б., Creat0R, что-нибудь подскажет...

madmasles
12-08-2010, 21:26
saavaage,
Найти неизвестные устройства у меня получилось так:#include (http://www.autoitscript.com/autoit3/docs/keywords.htm##include) "DeviceAPI.au3"
#include (http://www.autoitscript.com/autoit3/docs/keywords.htm##include) <Array.au3>

$j = 0
$aDiv = _DeviceAPI_GetClassArray()
;_ArrayDisplay($aDiv)
Dim (http://www.autoitscript.com/autoit3/docs/keywords.htm#Dim) $aUnknownDiv[1][3]
For (http://www.autoitscript.com/autoit3/docs/keywords.htm#For) $i = 0 To (http://www.autoitscript.com/autoit3/docs/keywords.htm#To) UBound (http://www.autoitscript.com/autoit3/docs/functions/UBound.htm)($aDiv) - 1
If (http://www.autoitscript.com/autoit3/docs/keywords.htm#If) StringInStr (http://www.autoitscript.com/autoit3/docs/functions/StringInStr.htm)($aDiv[$i][1], 'Unknown') Then (http://www.autoitscript.com/autoit3/docs/keywords.htm#Then)
$j += 1
ReDim (http://www.autoitscript.com/autoit3/docs/keywords.htm#ReDim) $aUnknownDiv[UBound (http://www.autoitscript.com/autoit3/docs/functions/UBound.htm)($aUnknownDiv) + 1][3]
$aUnknownDiv[$j][0] = $aDiv[$i][0]
$aUnknownDiv[$j][1] = $aDiv[$i][1]
$aUnknownDiv[$j][2] = $aDiv[$i][2]
EndIf (http://www.autoitscript.com/autoit3/docs/keywords.htm#EndIf)
Next (http://www.autoitscript.com/autoit3/docs/keywords.htm#Next)
$aUnknownDiv[0][0] = UBound (http://www.autoitscript.com/autoit3/docs/functions/UBound.htm)($aUnknownDiv) - 1
_ArrayDisplay (http://dundats.mvps.org/help/html/libfunctions/_arraydisplay.htm)($aUnknownDiv)

saavaage
12-08-2010, 22:38
madmasles, а выйти на название оборудования (в стиле авторского вывода) как-нибудь можно?

Я, честно говоря, взялся за изучение справки и еще до массивов не дошел. Поэтому своих версий предложить не могу. Заранее извиняюсь за иждивенческий подход в этом топике (жду манны небесной от гуру autoit).

saavaage
06-09-2010, 18:48
Вообщем, у меня получилось сделать список, слегка изменив файл - пример поста http://forum.oszone.net/post-1467800-3.html,
а именно добавив в соответствующую строку доп. условие:

;Skip classes without devices or devices have drivers
If _DeviceAPI_GetDeviceCount() > 0 and _DeviceAPI_GetDeviceRegistryProperty($SPDRP_DRIVER) = '' Then

полностью новый код примера:

#include <GuiConstantsEx.au3>
#include <GuiTreeView.au3>
#include <TreeViewConstants.au3>
#Include <GuiListView.au3>
#include <WindowsConstants.au3>
#include <GuiImageList.au3>
#include "DeviceAPI.au3"

Global $aAssoc[1][2]

$GUI = GUICreate("Device Management API - GUI Example", 800, 500)

Dim $iStyle = BitOR($TVS_EDITLABELS, $TVS_HASBUTTONS, $TVS_HASLINES, $TVS_LINESATROOT, $TVS_DISABLEDRAGDROP, $TVS_SHOWSELALWAYS)
$hTreeView = _GUICtrlTreeView_Create($GUI, 5, 5, 300, 450, $iStyle, $WS_EX_STATICEDGE )
$hListView = GUICtrlCreateListView ("Key|Value", 310, 5, 485,450)
GUISetState()

GUIRegisterMsg($WM_NOTIFY, "WM_NOTIFY")

;Assign image list to treeview
_GUICtrlTreeView_SetNormalImageList($hTreeView, _DeviceAPI_GetClassImageList())

Dim $total_devices = 0

_DeviceAPI_GetClasses()
While _DeviceAPI_EnumClasses()

;Get icon index from image list for given class
$Icon_Index = _DeviceAPI_GetClassImageIndex($p_currentGUID)

;Build list of devices within current class, if class doesn't contain any devices it will be skipped

_DeviceAPI_GetClassDevices($p_currentGUID)

;Skip classes without devices or devices have drivers
If _DeviceAPI_GetDeviceCount() > 0 and _DeviceAPI_GetDeviceRegistryProperty($SPDRP_DRIVER) = '' Then


;Add parent class to treeview
$parent = _GUICtrlTreeView_Add($hTreeView, 0, _DeviceAPI_GetClassDescription($p_currentGUID), $Icon_Index, $Icon_Index)

;Loop through all devices by index
While _DeviceAPI_EnumDevices()

$description = _DeviceAPI_GetDeviceRegistryProperty($SPDRP_DEVICEDESC)
$friendly_name = _DeviceAPI_GetDeviceRegistryProperty($SPDRP_FRIENDLYNAME)

;If a friendly name is available, use it instead of description
If $friendly_name <> "" Then
$description = $friendly_name
EndIf


;Add device to treeview below parent
$handle = _GUICtrlTreeView_AddChild($hTreeView, $parent, $description, $Icon_Index, $Icon_Index)

If $total_devices > 0 Then
ReDim $aAssoc[$total_devices+1][2]
EndIf

;Add treeview item handle to array along with device Unique Instance Id (For lookup)
$aAssoc[$total_devices][0] = $handle
$aAssoc[$total_devices][1] = _DeviceAPI_GetDeviceId()

;Update running total count of devices
$total_devices += 1
WEnd
EndIf
WEnd


While 1
Switch GUIGetMsg()
Case $GUI_EVENT_CLOSE
ExitLoop
EndSwitch
WEnd

Func WM_NOTIFY($hWnd, $iMsg, $iwParam, $ilParam)
#forceref $hWnd, $iMsg, $iwParam
Local $hWndFrom, $iIDFrom, $iCode, $tNMHDR, $hWndTreeview

$hWndTreeview = $hTreeView
If Not IsHWnd($hTreeView) Then $hWndTreeview = GUICtrlGetHandle($hTreeView)

$tNMHDR = DllStructCreate($tagNMHDR, $ilParam)
$hWndFrom = HWnd(DllStructGetData($tNMHDR, "hWndFrom"))
$iIDFrom = DllStructGetData($tNMHDR, "IDFrom")
$iCode = DllStructGetData($tNMHDR, "Code")
Switch $hWndFrom
Case $hWndTreeview
Switch $iCode
Case $TVN_SELCHANGEDA, $TVN_SELCHANGEDW
RefreshDeviceProperties()
EndSwitch
EndSwitch
Return $GUI_RUNDEFMSG
EndFunc ;==>WM_NOTIFY

;Triggered when a device is selected in the treeview
Func RefreshDeviceProperties()
Local $hSelected = _GUICtrlTreeView_GetSelection($hTreeView)

;Don't do anything if a class name (root item) was clicked
If _GUICtrlTreeView_Level($hTreeView, $hSelected) = 0 Then Return

;Lookup treeview item handle in global array
For $X = 0 to Ubound($aAssoc)-1

If $hSelected = $aAssoc[$X][0] Then
;MsgBox(0,"", "Handle: " & $aAssoc[$X][0] & @CRLF & "Unique Instance Id: " & $aAssoc[$X][1])

;Build list of ALL device classes
_DeviceAPI_GetClassDevices()

;Loop through all devices by index
While _DeviceAPI_EnumDevices()
If $aAssoc[$X][1] = _DeviceAPI_GetDeviceId() Then

;Empty listview
_GUICtrlListView_DeleteAllItems($hListView)

GUICtrlCreateListViewItem ("Hardware ID: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_HARDWAREID), $hListView )
GUICtrlCreateListViewItem ("Unique Instance ID: |" & _DeviceAPI_GetDeviceId(), $hListView )
GUICtrlCreateListViewItem ("Manufacturer: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_MFG), $hListView )
GUICtrlCreateListViewItem ("Driver: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_DRIVER), $hListView )
GUICtrlCreateListViewItem ("Friendly Name: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_FRIENDLYNAME), $hListView )
GUICtrlCreateListViewItem ("Physical Device Object Name: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_PHYSICAL_DEVICE_OBJECT_NAME), $hListView )
GUICtrlCreateListViewItem ("Upper Filters: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_UPPERFILTERS), $hListView )
GUICtrlCreateListViewItem ("Lower Filters: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_LOWERFILTERS), $hListView )
GUICtrlCreateListViewItem ("Enumerator: |" & _DeviceAPI_GetDeviceRegistryProperty($SPDRP_ENUMERATOR_NAME), $hListView )

;Resize columns to fit text
_GUICtrlListView_SetColumnWidth($hListView, 0,$LVSCW_AUTOSIZE)
_GUICtrlListView_SetColumnWidth($hListView, 1,$LVSCW_AUTOSIZE)
EndIf
WEnd
EndIf
Next
EndFunc

;Cleanup image list
_DeviceAPI_DestroyClassImageList()

_DeviceAPI_DestroyDeviceInfoList() ;Cleanup for good measure

Само собой, что для работы этого скрипта нужна библиотека DeviceAPI.au3, указанная madmasles в одном из вышестоящих постов.

Просьба to All, проверить работу скрипта на корректность.

NikLok
07-09-2010, 10:35
saavaage, У меня к сожалению выводится только окно без всякого списка, хотя одно устройство без драйверов есть. Это USB hub.
Как планируется использовать данный скрипт?
Я в свое время хотел сделать такой для составления списка для значения OemPnPDriversPath в файле winnt.sif.

То есть где нить на Т40 он запускается, составляет список устройств, ищет драйвера и найденные пути приписывает в OemPnPDriversPath.

Вы не то же самое планируете?

saavaage
07-09-2010, 10:51
NikLok, нет.
Честно говоря, пока только осваиваю autoit (пошел 2-ой месяц), раньше опыта программирования не имел. Поэтому чувствую себя очень неуверенно. Решил в качестве "контрольной работы" по введению в основы autoit , сделать утилиту по диагностике системы сразу после установки XP + драйверов (у меня часть из них ставится вместе с системой). Будет несколько вкладок, одна из них - Оборудование без драйверов. Думаю через неделю-другую выложить свой первый "блин".
Насчет драйверов - тестировал на своем ПК (отрубив дрова на модем) - вроде отобразило то, что надо.
Насчет USB hub » ничего конкретного сказать не могу. Скорее всего, Вам надо обратиться к автору библиотеки (ссылка дана в топике madmasles).

NikLok
10-09-2010, 14:28
saavaage, Запустил на другой машине и увидел список оборудования с и без драйверов.
При переходе по дереву устройств, перерисовка идет чудовищно долго! При этом машина если не супер то относительно быстрая (6.5 по оценке Win7). Если планируешь дальше развивать, то надо бы пофиксить!

saavaage
10-09-2010, 14:38
NikLok, У меня все быстро работает. Отрисовка тоже. Машина -средняя. Как вариант -попробуй отключить прорисовку иконок..
Кстати, попробуй последнее решение от CreaTor. Обсуждение этого дела как-то плавно перетекло в http://autoit-script.ru/index.php/topic,2634.msg19010.html#msg19010 Плиз, посмотри и заодно потести там последний вариант. у меня возможность только вечером появится.

PS не проповал использовать утилиты devcon и DevManView.exe? Интересно, что у тебя выдаст в виде списка? Посмотри и поиграй с ними, если они подхватят инфу о хабе, то буду, наверное, их подключать..

Прикрепляю, на всякий случай, архив с DevManView.exe. Распакуйте и запустите cmd. Ну и посмотрите, есть ли оборудование + инфа по драйверам?

saavaage
10-09-2010, 14:48
NikLok, у Вас Win7 или XP? Дело в том, что изначально тестирую работу на XP SP3. На win 7 буду переходить после SP1

NikLok
13-09-2010, 11:40
saavaage, У меня XP но пак 2-й - /(:
На win 7 буду переходить после SP1 »
Целиком с Вами согласен, и также в ожидании!

DevManView.exe показал мое устройство. Драйверов нет!
USB Device USB\Vid_04e8&Pid_2004\5&2cf28e88&0&1 USB Device 0x00000004 0x00000000 No No 13.09.2010 10:36:22 20.11.2008 13:33:06

saavaage
13-09-2010, 13:25
NikLok, Вы ходили по ссылке, которую я дал постом выше? Посмотрите, как там отображается ваше оборудование. Там несколько режимов просмотра (думаю разберетесь). Меня интересуют 2 вещи:
1. когда режим полного отображения оборудования (с дровами и без), виден ли в списке ваш хаб? Если виден, то, что у него с дровами(поле ListView),
2. Вы жаловались на скорость отрисовки, как ситуация? Пробовали отключить отображение иконок?

NikLok
13-09-2010, 16:42
saavaage, Мой хаб не видно ни втом ни в этом режиме.
2. Вы жаловались на скорость отрисовки, как ситуация? Пробовали отключить отображение иконок? »
Не понял где это делать? В исходнике?

Последняя версия (из ссылки стала отображать пошустрее)

У меня стоит разрешение экрана 120 dpi. Надписи в несколько строк у чекбоксов отрезаются сверху и снизу.
В принципе это решается сменой размера фонтов или изменением геометрии.

Ну и хорошо бы окошко уметь растягивать. При моем 2560х1600 оно уж совсем малюсенькое.

saavaage
19-09-2010, 15:05
NikLok, да под отключением, я имел в виду в коде.

У меня еще один вопрос:
в последнем варианте предусмотрены 2 новых чекбокса, запускающих твики системы:
1. отображать скрытые устройства
2. отображать детальную информацию

Вы пробовали активировать 1-ый? Если да, то искали свой хаб в "Драйверы устройств не plug & play"? Если не сложно, сделайте это. По идее, он должен быть в этом списке. + Рекомендую посмотреть эту статью http://www.docwin.ru/article852.html и попробовать сделать так, как там советуют.

Если возможно, выложите скрин описанных проблем с разрешением и обрезанием чек-боксов).

PS Пока работы на этом направлении временно приостановлены. Болел и сейчас буду "разгребать" накопившееся. Возможно, приступлю через неделю (не раньше).




© OSzone.net 2001-2012