Tracking user logon activity

Mark Russinovich has presented a screenshot of the autoruns utility during his Malware Hunting with the Sysinternals Tools session at Teched 2012.
He also reported a slowdown issue while he was at Teched 2012 in Europe in the following blog post.

We can actually see more about these scheduled tasks as he posted the following image:
MS tasks Russinovich

These special scheduled tasks remind me the question that Jonathan Walz (‏@jonwalz)
asked on twitter:

Does anyone have a good method for detecting a logon or unlock of a computer (besides the security log (way too chatty)) with WMI?

Well, you may wonder what’s the link between the scheduled tasks from Microsoft on Mark’s laptop and Jonathan’s question ?

I’ve actually been using these kind of scheduled tasks to track user logon activity as the scheduler has now new triggers: Logon,SessionUnlock,RemoteDisconnect,ConsoleConnect,RemoteConnect,SessionLock,RemoteConnect and ConsoleDisconnect

I have been using the following code in quick and dirty mode to create all these local tasks:

Function Get-Template
    $template = @"
    <?xml version="1.0" encoding="UTF-16"?>
    <Task version="1.3" xmlns="">
        <Principal id="Author">
      <Actions Context="Author">
          <Arguments>-ExecutionPolicy RemoteSigned -File "$env:systemroot\scripts\Get-userinfo.ps1"</Arguments>
    return $template
} # end of function

Function Get-SessionTrigger
    $sessiontrigger = @"
    return $sessiontrigger

# Handle the logon trigger
$logontrigger = @"

# Create the Logon task
$xml = Get-Template -trigger $logontrigger
$xml | Out-File -FilePath ($env:temp +"\tmp.xml") -Encoding Unicode -Force 
Invoke-Expression -Command ("schtasks.exe /create /RU SYSTEM /TN Logon /F /XML " + ($env:temp +"\tmp.xml"))

# Define an array of each connection state
$arraytriggersstate = @(

# Loop into the array and create the task
for ($i = 0 ; $i -lt $arraytriggersstate.count ; $i++)
    Write-Host -ForegroundColor Green -Object ($arraytriggersstate[$i])
    $xml = Get-Template -trigger  (Get-SessionTrigger -trigger $arraytriggersstate[$i])
    $xml | Out-File -FilePath ($env:temp +"\tmp.xml") -Encoding Unicode -Force 
    Invoke-Expression -Command ("schtasks.exe /create /RU SYSTEM /F /TN " + $arraytriggersstate[$i] + " /XML " + ($env:temp +"\tmp.xml"))

The tasks names are important as I’ve been extracting the last tasks names from the new Microsoft-Windows-TaskScheduler/Operational log to know what the user did and writing it to a CSV file that can be read afterward by custom helpdesk tools.

Here is the XML query passed to the Get-WinEvent cmdlet I’ve been using in my Get-userinfo.ps1 script:

  # Wait a little bit until event 129 occurs
 Start-Sleep -Seconds 10
 $query =@"
 <Query Id="0" Path="Microsoft-Windows-TaskScheduler/Operational">
    <Select Path="Microsoft-Windows-TaskScheduler/Operational">*[System[Provider[@Name='Microsoft-Windows-TaskScheduler'] and (Level=4 or Level=0) and ( Task = 129 ) and TimeCreated[timediff(@SystemTime) &lt;=200000 ]]]</Select>

To know who logged on, I’m using the technique I’ve previously described in the following post Get Logged on users.

As far as I remember, there’s another way to play with logon triggers. It was published as a powershell tip in April on and using the Register-ObjectEvent cmdlet and the [Microsoft.Win32.SystemEvents] .net objects.


Leave a Reply

Fill in your details below or click an icon to log in: Logo

You are commenting using your account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s