forked from MicksITBlogs/PowerShell
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathLogonTimes.ps1
More file actions
338 lines (292 loc) · 10.6 KB
/
LogonTimes.ps1
File metadata and controls
338 lines (292 loc) · 10.6 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
<#
.SYNOPSIS
User Logon Report
.DESCRIPTION
This script will query the event viewer logs of a specified system for a list of logon times for a specific user. There are four fields in the report: Keyboard logons, Screen Unlock, Remote Session logons, and Cached Logon. It has the option to either generate a report in a CSV file with all of the above field data, or it can generate a TXT file containing the raw message data with each data field split off by two dash rows.
NOTE: This does not require WinRM to be enabled to run on external systems. Also, this can take quite a while to execute if the logs are really big.
.PARAMETER ComputerName
Name of system to retrieve the logs from. If this is left blank, the script will use "." representing the computer this script is executing on.
.PARAMETER Rawdata
Generate a report using the raw data from the event viewer logs of the specified user
.PARAMETER Username
Username to generate this report of.
.EXAMPLE
Generate a CSV file report containing the times and sorted by each logon type
powershell.exe -file LogonTimes.ps1 -Username MickPletcher -ComputerName PC01
Generate a TXT file that contains all of the raw message data fields for the specified system
powershell.exe -file LogonTimes.ps1 -Username MickPletcher -ComputerName PC01 -Rawdata
.NOTES
===========================================================================
Created with: SAPIEN Technologies, Inc., PowerShell Studio 2017 v5.4.136
Created on: 3/15/2017 12:00 PM
Created by: Mick Pletcher
Filename: LogonTimes.ps1
===========================================================================
#>
[CmdletBinding()]
param
(
[String]$ComputerName,
[switch]$Rawdata,
[ValidateNotNullOrEmpty()][string]$Username
)
function Get-FilteredData {
<#
.SYNOPSIS
Filter By LogonType Type
.DESCRIPTION
This will filter the data for the specified LogonType type
.PARAMETER LogonType
Specified LogonType type
.PARAMETER Message
Message to display on the screen
.PARAMETER Logons
Array containing all logons
.NOTES
Additional information about the function.
#>
[CmdletBinding()]
param
(
[ValidateNotNullOrEmpty()]$LogonType,
[ValidateNotNullOrEmpty()][string]$Message,
[ValidateNotNullOrEmpty()]$Logons
)
$Errors = $false
Write-Host $Message"....." -NoNewline
Try {
$Data = $Logons | Where-Object { $_.Message -like "*Logon Type*"+[char]9+[char]9+$LogonType+"*" }
} catch {
$Errors = $true
}
If ($Errors -eq $false) {
Write-Host "Success" -ForegroundColor Yellow
} else {
Write-Host "Failed" -ForegroundColor Red
}
Return $Data
}
function Get-SID {
<#
.SYNOPSIS
Retrieve SID from HKEY_LOCAL_MACHINE
.DESCRIPTION
This script will retrieve the SID by querying the HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\ProfileList by matching the ProfileImagePath value with the Username parameter.
.EXAMPLE
PS C:\> Get-SID
.NOTES
Additional information about the function.
#>
[CmdletBinding()][OutputType([string])]
param ()
Write-Host "Retrieving SID for $Username....." -NoNewline
If ($ComputerName -eq ".") {
#Get associated SID of User Profile
$SID = (get-childitem -path REGISTRY::"HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\ProfileList" | Where-Object { $_.Name -like "*S-1-5-21*" } | ForEach-Object { Get-ItemProperty REGISTRY::$_ } | Where-Object { $_.ProfileImagePath -like "*$Username*" }).PSChildName
} else {
$HKEY_LOCAL_MACHINE = 2147483650
$Key = "SOFTWARE\Microsoft\Windows NT\CurrentVersion\ProfileList"
$RegClass = Get-WMIObject -Namespace "Root\Default" -List -ComputerName $ComputerName | Where-object { $_.Name -eq "StdRegProv" }
$Value = "ProfileImagePath"
$SID = ($RegClass.EnumKey($HKEY_LOCAL_MACHINE, $Key)).sNames | Where-Object { $_ -like "*S-1-5-21*" } | ForEach-Object {
If (($RegClass.GetStringValue($HKEY_LOCAL_MACHINE, $Key + "\" + $_, $Value)).sValue -like "*" + $Username + "*") {
$_
}
}
}
If (($SID -ne "") -and ($SID -ne $null)) {
Write-Host "Success" -ForegroundColor Yellow
} else {
Write-Host "Failed" -ForegroundColor Red
}
Return $SID
}
function Get-RelativePath {
<#
.SYNOPSIS
Get the relative path
.DESCRIPTION
Returns the location of the currently running PowerShell script
.NOTES
Additional information about the function.
#>
[CmdletBinding()][OutputType([string])]
param ()
$Path = (split-path $SCRIPT:MyInvocation.MyCommand.Path -parent) + "\"
Return $Path
}
function New-Report {
<#
.SYNOPSIS
Generate CSV Report File
.DESCRIPTION
This function will generate a CSV report.
.PARAMETER Keyboard
A description of the Keyboard parameter.
.PARAMETER Unlock
A description of the Unlock parameter.
.PARAMETER Remote
A description of the Remote parameter.
.PARAMETER Cached
A description of the Cached parameter.
.EXAMPLE
PS C:\> New-Report
.NOTES
Additional information about the function.
#>
[CmdletBinding()]
param
(
$Keyboard,
$Unlock,
$Remote,
$Cached
)
$RelativePath = Get-RelativePath
#Name of report file
$FileName = $RelativePath + "$Username.csv"
#Delete report file if it exists
If ((Test-Path $FileName) -eq $true) {
Write-Host "Deleting $Username.csv....." -NoNewline
Remove-Item -Path $FileName -Force
If ((Test-Path $FileName) -eq $false) {
Write-Host "Success" -ForegroundColor Yellow
} else {
Write-Host "Failed" -ForegroundColor Red
}
}
Write-Host "Generating $Username.csv report file....." -NoNewline
#Create new file
"Logon Type,Date/Time" | Out-File -FilePath $FileName -Encoding UTF8 -Force
$Errors = $false
#Report all keyboard logons
foreach ($Logon in $Keyboard) {
$Item = "Keyboard," + [string]$Logon.TimeCreated
try {
$Item | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
} catch {
$Errors = $true
}
}
#Report all screen unlocks
foreach ($Logon in $Unlock) {
$Item = "Unlock," + [string]$Logon.TimeCreated
Try {
$Item | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
} catch {
$Errors = $true
}
}
#Report all remote logons
foreach ($Logon in $Remote) {
$Item = "Remote," + [string]$Logon.TimeCreated
Try {
$Item | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
} catch {
$Errors = $true
}
}
#Report all cached logons
foreach ($Logon in $Cached) {
$Item = "Cached," + [string]$Logon.TimeCreated
Try {
$Item | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
} catch {
$Errors = $true
}
}
If ($Errors -eq $false) {
Write-Host "Success" -ForegroundColor Yellow
} else {
Write-Host "Failed" -ForegroundColor Red
}
}
function Get-LogonLogs {
<#
.SYNOPSIS
Retrieve all Logon Logs from Event Viewer
.DESCRIPTION
This function will query the event viewer for all Event ID 4624, filtered with the user's SID.
.PARAMETER SID
User's SID
.EXAMPLE
PS C:\> Get-LogonLogs
.NOTES
Additional information about the function.
#>
[CmdletBinding()]
param
(
[ValidateNotNullOrEmpty()]$SID
)
If ($ComputerName -ne ".") {
Write-Host "Retrieving all logon logs for $Username on $ComputerName....." -NoNewline
} else {
Write-Host "Retrieving all logon logs for $Username on $env:COMPUTERNAME....." -NoNewline
}
$Errors = $false
Try {
If ($ComputerName -ne ".") {
$AllLogons = Get-WinEvent -FilterHashtable @{ logname = 'security'; ID = 4624 } -ComputerName $ComputerName | where-object { ($_.properties.value -like "*$SID*") }
} else {
$AllLogons = Get-WinEvent -FilterHashtable @{ logname = 'security'; ID = 4624 } | where-object { ($_.properties.value -like "*$SID*") }
}
} catch {
$Errors = $true
}
If ($Errors -eq $false) {
Write-Host "Success" -ForegroundColor Yellow
} else {
Write-Host "Failed" -ForegroundColor Red
}
Return $AllLogons
}
#******************************************************************************
#******************************************************************************
Clear-Host
If (($ComputerName -eq "") -or ($ComputerName -eq $null)) {
$ComputerName = "."
}
$SID = Get-SID
#Retrieve all logon logs
$AllLogons = Get-LogonLogs -SID $SID
#Logon at keyboard and screen of system
$KeyboardLogons = Get-FilteredData -Logons $AllLogons -LogonType "2" -Message "Filtering keyboard logons"
#Unlock workstation with password protected screen saver
$Unlock = Get-FilteredData -Logons $AllLogons -LogonType "7" -Message "Filtering system unlocks"
#Terminal Services, Remote Desktop or Remote Assistance
$Remote = Get-FilteredData -Logons $AllLogons -LogonType "10" -Message "Filtering remote accesses"
#logon with cached domain credentials such as when logging on to a laptop when away from the network
$CachedCredentials = Get-FilteredData -Logons $AllLogons -LogonType "11" -Message "Filtering cached logins"
#Generate a rawdata report
If ($Rawdata.IsPresent) {
$RelativePath = Get-RelativePath
#Name of report file
$FileName = $RelativePath + "$Username.txt"
#Delete report file if it exists
If ((Test-Path $FileName) -eq $true) {
Write-Host "Deleting $Username.txt....." -NoNewline
Remove-Item -Path $FileName -Force
If ((Test-Path $FileName) -eq $false) {
Write-Host "Success" -ForegroundColor Yellow
} else {
Write-Host "Failed" -ForegroundColor Red
}
}
Write-Host "Generating raw data file....." -NoNewline
foreach ($Logon in $AllLogons) {
[string]$Logon.TimeCreated | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
$Logon.Message | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
" " | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
"----------------------------------------------------------------------------------------------------------------------------------------------------------------" | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
"----------------------------------------------------------------------------------------------------------------------------------------------------------------" | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
" " | Out-File -FilePath $FileName -Encoding UTF8 -Append -Force
}
If ((Test-Path $FileName) -eq $true) {
Write-Host "Success" -ForegroundColor Yellow
} else {
Write-Host "Failed" -ForegroundColor Red
}
} else {
New-Report -Keyboard $KeyboardLogons -Unlock $Unlock -Remote $Remote -Cached $CachedCredentials
}