BlackHoleSun Posted December 29, 2010 Posted December 29, 2010 I have a script that pulls information from the different Win32 databases on a machine the user inputs. With certain machines the program will crash while it's trying to access the database. The message I get is that it "Variable must be of type Object". The code for one of the databases where it's crashing is: $colItems = $objWMIService.ExecQuery("SELECT Caption, FreePhysicalMemory, ServicePackMajorVersion, Version FROM Win32_OperatingSystem", "WQL", $wbemFlagReturnImmediately + $wbemFlagForwardOnly) If IsObj($colItems) Then For $objItem In $colItems $returnArr[0] = $objItem.Caption $returnArr[1] = $objItem.FreePhysicalMemory $returnArr[2] = $objItem.ServicePackMajorVersion $returnArr[3] = $objItem.Version Next Else Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_OperatingSystem" ) Endif It doesn't matter if I put the query inside IsObj(), it still crashes. It doesn't happen with every computer I try. I think there may be a security rights issue behind the problem. My main concern is, is there a way for it to not crash on errors? I would rather it show an empty value than crash completely.
KaFu Posted December 29, 2010 Posted December 29, 2010 (edited) - You didn't post a working example- My guess is, that the WMI service is not started on those machines where your script crashes, so the correct check would be IsObj($objWMIService)In SMF I use this UDF by Xenobiologist to check whether the service is running and if not trying to start it with this code:Local $b_WMI_was_running = True While Not _ServiceRunning("", "winmgmt") ; Check that WMI service is running $b_WMI_was_running = False Switch MsgBox(4 + 16 + 262144, "SMF - Computer Info Report - Error", "The WMI service is stopped." & @CRLF & "Do you want SMF to try to start it?") Case 6 _StartService("", "winmgmt") Sleep(2000) Case Else Return EndSwitch WEnd ; RUN YOUR WMI CODE HERE If $b_WMI_was_running = False Then While Not _ServiceRunning("", "winmgmt") ; Check that WMI service is running Switch MsgBox(4 + 16 + 262144, "SMF - Computer Info Report - Finished", "The WMI service has been started by SMF." & @CRLF & "Do you want SMF to stop the WMI service again?") Case 6 _StopService("", "winmgmt") Sleep(2000) Case Else Return EndSwitch WEnd EndIf- Instead if relying on WMI I recommend to extract the infos you listed above by using this + a call to MemGetStats()Edit: Upsa, $colItems is an Object, corrected. Edited December 29, 2010 by KaFu OS: Win10-22H2 - 64bit - German, AutoIt Version: 3.3.16.1, AutoIt Editor: SciTE, Website: https://funk.eu AMT - Auto-Movie-Thumbnailer (2024-Oct-13) BIC - Batch-Image-Cropper (2023-Apr-01) COP - Color Picker (2009-May-21) DCS - Dynamic Cursor Selector (2024-Oct-13) HMW - Hide my Windows (2024-Oct-19) HRC - HotKey Resolution Changer (2012-May-16) ICU - Icon Configuration Utility (2018-Sep-16) SMF - Search my Files (2025-May-18) - THE file info and duplicates search tool SSD - Set Sound Device (2017-Sep-16)
BlackHoleSun Posted December 29, 2010 Author Posted December 29, 2010 OK, here's the complete re-worked function I have. I only extracted that one part in my first post since I could get the error with only that query. I added the "If IsObj($objWMIService) Then" test starting on line 17 and that worked. So would I need the further IsObj() If Then loops later? It would be nice to take those out, but I can leave them in. expandcollapse popupFunc _CompInfo($computer) $queryPing = Ping($computer) Dim $returnArr[25] If $queryPing Then $wbemFlagReturnImmediately = 0x10 $wbemFlagForwardOnly = 0x20 $colItems = "" If $computer <> "" Then $strComputer = $computer Else $strComputer = "localhost" EndIf $objWMIService = ObjGet("winmgmts:\\" & $strComputer & "\root\CIMV2") If IsObj($objWMIService) Then $colItems = $objWMIService.ExecQuery("SELECT Caption, Domain, Manufacturer, Model, Name, PartOfDomain, Status, SystemType, TotalPhysicalMemory, UserName, Workgroup FROM Win32_ComputerSystem", "WQL", $wbemFlagReturnImmediately + $wbemFlagForwardOnly) If IsObj($colItems) Then For $objItem In $colItems $returnArr[0] = $objItem.Caption $returnArr[1] = $objItem.Domain $returnArr[2] = $objItem.Manufacturer $returnArr[3] = $objItem.Model $returnArr[4] = $objItem.Name $returnArr[5] = $objItem.PartOfDomain $returnArr[6] = $objItem.Status $returnArr[7] = $objItem.SystemType $returnArr[8] = $objItem.TotalPhysicalMemory $returnArr[9] = $objItem.UserName $returnArr[10] = $objItem.Workgroup Next Else Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_ComputerSystem" ) Endif $colItems = $objWMIService.ExecQuery("SELECT * FROM Win32_ComputerSystemProduct", "WQL", $wbemFlagReturnImmediately + $wbemFlagForwardOnly) If IsObj($colItems) Then For $objItem In $colItems $returnArr[11] = $objItem.Caption $returnArr[12] = $objItem.Description $returnArr[13] = $objItem.IdentifyingNumber $returnArr[14] = $objItem.Name $returnArr[15] = $objItem.SKUNumber $returnArr[16] = $objItem.UUID $returnArr[17] = $objItem.Vendor $returnArr[18] = $objItem.Version Next Else Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_ComputerSystemProduct" ) Endif $colItems = $objWMIService.ExecQuery("SELECT Caption, FreePhysicalMemory, ServicePackMajorVersion, Version FROM Win32_OperatingSystem", "WQL", $wbemFlagReturnImmediately + $wbemFlagForwardOnly) If IsObj($colItems) Then For $objItem In $colItems $returnArr[19] = $objItem.Caption $returnArr[20] = $objItem.FreePhysicalMemory $returnArr[21] = $objItem.ServicePackMajorVersion $returnArr[22] = $objItem.Version Next Else Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_OperatingSystem" ) Endif $colItems = $objWMIService.ExecQuery("SELECT MaxClockSpeed FROM Win32_Processor", "WQL", $wbemFlagReturnImmediately + $wbemFlagForwardOnly) If IsObj($colItems) Then For $objItem In $colItems $returnArr[23] = $objItem.MaxClockSpeed Next Else Msgbox(0,"WMI Output","No WMI Objects Found for class: " & "Win32_Processor" ) Endif Else $i = 0 Do $returnArr[$i] = "" $i = $i + 1 Until $i = 25 EndIf Return $returnArr EndIf EndFunc ;==> _CompInfo On a side note, I realized I was causing a lot of extra work by calling the function for each thing I need to set (i.e. a = func($comp, 1), b = func($comp, 2)). I cleaned it up to just return the whole array and pick what it needs from the returned array. So it speeds things up a little bit.
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now