#87660 - 2002-09-06 05:03 AM
Function: Read eventlog with WMI (buggy)
|
Sealeopard
KiX Master
   
Registered: 2001-04-25
Posts: 11165
Loc: Boston, MA, USA
|
I've been working on a neat little function for the last couple of days which I am unable to finish due to a peculiar issue.
I wrote a UDF that can read eventlog entries through WMI from both local and remote computers including full authentication against remote computers.
It does work successfully when querying small eventlog event lists but it does fail for larger lists.
I am testing it on a P3-1000 and a P3-450 and both have the same execution times for the WMI commands, so it doesn't seem to be a case of not enough horsepower (MHz).
The issue is that counting the number of records in an object takes a whopping 6 seconds for just 84 records whereas all other WMI-related lines of code execute in a matter of milliseconds. Furthermore, KiXtart just quits without an error message at all if I run it for larger eventlog lists.
I have posted below the test script I am using including the GetEvents() UDF. I would appreciate it if anybody could test it on their machines and report back. The code has a lot of error checking and timing displays but it was the only way for me to track down what exactly was going on.
code:
; to be run with KiXtart 4.11 ; has not been tested under any previous version
break on cls
dim $rc $rc=SETCONSOLE('SHOW') $rc=SETCONSOLE('FOREGROUND') $rc=SETOPTION('Explicit','ON') $rc=SETOPTION('HideCursor','ON') $rc=SETOPTION('NoVarsInStrings','ON') $rc=SETOPTION('WrapAtEOL','ON')
? 'KiXtart v'+@KIX
dim $eventlog, $eventid, $events, $event dim $computer, $username, $password, $date
; pull all log-on events from the SECURITY evenltlog $eventlog='Security' $eventid=528
; specify the name of the remote comuter, a username with administrative access ; and the password for that username $computer='workstaion' $username='administrator' $password='password'
$date=@DATE+' '+@TIME
;$events=GetEvents($eventlog, $eventid)
;$events=GetEvents($eventlog, $eventid, $date)
? '' ? 'Calling GetEvents' $events=GetEvents($eventlog, $eventid,,'workstation')
? '' ? 'Calling GetEvents' $events=GetEvents($eventlog, $eventid,,'workstation',$username,$password)
? '' ? 'Calling GetEvents' $events=GetEvents($eventlog, $eventid,,'server')
? '' ? 'Calling GetEvents' $events=GetEvents($eventlog, $eventid,,'server',$username,$password)
;for each $event in $events ; ? 'Event = '+$event ;next ;FUNCTION GetEvents() ; ;ACTION Retreives event from the eventlog ; ;VERSION 0.9 ; ;KIXTART VER 4.11 ; ;AUTHOR Jens Meyer ; ;SYNTAX RETCODE = GETEVENTS(EVENTLOG, EVENTID, OPTIONAL DATE, ; OPTIONAL COMPUTER, OPTIONAL USERNAME, ; OPTIONAL PASSWORD) ; ;PARAMETERS self-explanatory ? ; ;RETURN array of events or empty string (not yet implemented) ; ;REMARKS debugging version since it only seems to work for small recordsets ; ;DEPENDENCIES WMI ; ;EXAMPLE $events = GetEvents('Security',528) ; ;KIXTART BBS not yet posted for general use ;
function GetEvents($eventlog, $eventid, optional $date, optional $computer, optional $username, optional $password)
dim $objLocator, $objWBEM, $objWMIResults dim $event, $wqlQuery, $resultcount dim $ticks, $queryticks
; check to see whether we're connecting to a local or remote eventlog $computer=trim($computer) select case $computer=@WKSTA $computer='.' $computer=@WKSTA case $computer case 1 $computer='.' $computer=@WKSTA endselect
; check to see whether we're connecting to a valid eventlog if $eventlog<>'Application' and $eventlog<>'Security' and $eventlog<>'System' exit 2 endif
; create locator object for credentialed connection to a remote computer $ticks = @TICKS $objLocator = CreateObject('WbemScripting.SWbemLocator') $ticks = @TICKS - $ticks ? 'Execution time [ms] : '+$ticks+' for CreateObject("WbemScripting.SWbemLocator")' if @ERROR ? ''+@ERROR+' - '+@SERROR exit @ERROR endif
if $username and $computer<>@WKSTA and $computer<>'.' ; create an credentialed connection to a remote computer ? 'Remote credentialed connection to '+$computer+' for '+$username+' and password '+$password $ticks = @TICKS $objWBEM=$objLocator.ConnectServer($computer,,$username,$password) $ticks = @TICKS - $ticks ? 'Execution time [ms] : '+$ticks+' for $objLocator.ConnectServer($computer,,$username,$password)' if @ERROR ? ''+@ERROR+' - '+@SERROR exit @ERROR endif
else ; create an non-credentialed connection to a lcoal or remote computer ? 'Non-credentialed connection to '+$computer $ticks = @TICKS $objWBEM=$objLocator.ConnectServer() $ticks = @TICKS - $ticks ? 'Execution time [ms] : '+$ticks+' for $objLocator.ConnectServer()' if @ERROR ? ''+@ERROR+' - '+@SERROR exit @ERROR endif
endif
; set the impersonation level $ticks = @TICKS $objWBEM.Security_.ImpersonationLevel = 3 $ticks = @TICKS - $ticks ? 'Execution time [ms] : '+$ticks+' for $objWBEM.Security_.ImpersonationLevel = 3' if @ERROR ? ''+@ERROR+' - '+@SERROR exit @ERROR endif
; set the impersonation level and make sure we have backup and security permissions $ticks = @TICKS $objWBEM=GetObject('winmgmts:{impersonationLevel=impersonate, (Backup, Security)}!//'+$computer) $ticks = @TICKS - $ticks ? 'Execution time [ms] : '+$ticks+' for GetObject("winmgmts:{impersonationLevel=impersonate, (Backup, Security)}!//"+$computer))' if @ERROR ? ''+@ERROR+' - '+@SERROR exit @ERROR endif
; check to see whether we're looking for an event ID or if there's a custom query if instr($eventid,'select') else $eventid=val($eventid) $wqlQuery="SELECT * FROM Win32_NTLogEvent WHERE Logfile='"+$eventlog+"' AND EventCode="+$eventID endif
? 'Executing query: '+$wqlQuery $ticks = @TICKS $objWMIResults = $objWBEM.ExecQuery($wqlQuery) $ticks = @TICKS - $ticks $queryticks = $ticks ? 'Execution time [ms]: '+$ticks+' for $objWBEM.ExecQuery($wqlQuery)'
if @ERROR ? ''+@ERROR+' - '+@SERROR exit @ERROR endif
$ticks = @TICKS $resultcount = $objWMIResults.Count $ticks = @TICKS - $ticks ? 'Execution time [ms] : '+$ticks+' for $objWMIResults.Count'
? 'Time for query [ms]: '+$queryticks if $objWMIResults.Count ? 'Time per record [ms]: '+(CDBL($queryticks)/$resultcount) endif
? 'Resultset count : '+$resultcount
; for each $event in $objWMIResults ; ? 'Category = '+$event.Category ; ? 'CategoryString = '+$event.CategoryString ; ? 'ComputerName = '+$event.computerName ; ? 'Data = '+$event.Data ; ? 'EventCode = '+$event.EventCode ; ? 'EventIdentifier = '+$event.EventIdentifier ; ? 'EventType = '+$event.EventType ; ? 'InsertionStrings = '+join($event.Insertionstrings,' - ') ; ? 'Logfile = '+$event.Logfile ; ? 'Message = '+join(split($event.Message,@CRLF),' - ') ; ? 'RecordNumber = '+$event.RecordNumber ; ? 'Source Name = '+$event.SourceName ; ? 'TimeGenerated = '+$event.TimeGenerated ; ? 'TimeWritten = '+$event.TimeWritten ; ? 'Type = '+$event.Type ; ? 'User = '+$event.User ; next ; ? 'Resultset count: '+$objWMIResults.Count
$objWMIResults = 0 $objWBEM = 0 $objLocator = 0 $GetEvents = $event endfunction
[ 06. September 2002, 05:04: Message edited by: sealeopard ]
_________________________
There are two types of vessels, submarines and targets.
|
|
Top
|
|
|
|
Moderator: Shawn, ShaneEP, Ruud van Velsen, Arend_, Jochen, Radimus, Glenn Barnas, Allen, Mart
|
1 registered
(Allen)
and 1198 anonymous users online.
|
|
|