The PowerShell script is designed to extract information about Remote Desktop Protocol (RDP) local session manager events from the Windows event logs on a RDS host and save it to a CSV file.
Script: Get events with EventID 40 from Microsoft-Windows-TerminalServices-LocalSessionManager/Operational Event Log
$RDPAuths = Get-WinEvent -LogName 'Microsoft-Windows-TerminalServices-LocalSessionManager/Operational'-FilterXPath '<QueryList><Query Id="0"><Select>*[System[EventID=40]]</Select></Query></QueryList>' [xml[]]$xml = $RDPAuths | ForEach-Object { $_.ToXml() } $EventData = $xml.Event | ForEach-Object { [PSCustomObject]@{ TimeCreated = (Get-Date $_.System.TimeCreated.SystemTime -Format 'yyyy-MM-dd hh:mm:ss K') Session = $_.UserData.EventXML.Session Reason = $_.UserData.EventXML.Reason EventID = $_.System.EventID User = $_.UserData.EventXML.User SessionID = $_.UserData.EventXML.SessionID Address = $_.UserData.EventXML.Address } } $EventData | Export-Csv -Path c:\rdlog-LSM-Operational.csv -Encoding ASCII
Here is an explanation of how the code works.
- First, the script uses the
Get-WinEvent
cmdlet to retrieve events from the ‘Microsoft-Windows-TerminalServices-LocalSessionManager/Operational’ log. This log contains information about RDP disconnections. The events are stored in the$RDPAuths
variable. - The
$RDPAuths
variable is then piped to theForEach-Object
cmdlet to convert each event to XML format using theToXml()
method. The resulting array of XML objects is stored in the$xml
variable. - Next, the script uses the
ForEach-Object
cmdlet again to iterate over the$xml.Event
array. For each event, a new custom object is created using the[PSCustomObject]@{}
syntax. This custom object contains the following properties:TimeCreated
,Session
,Reason
,EventID
,User
,SessionID
, andAddress
. These properties are extracted from the event XML data using dot notation. - Finally, the custom objects are piped to the
Export-Csv
cmdlet, which saves the objects as a CSV file at the specified path (c:\rdlog-LSM-Operational.csv
) with ASCII encoding.
This PowerShell script is useful for extracting and analyzing RDP local session manager events, such as monitoring for disconnect reasons. The resulting CSV file provides a simple, convenient way to view and analyze the RDP events.
RDS Session Host Server Disconnect Codes
RDS server client disconnect code | Disconnect reason |
---|---|
0x00000001 | The disconnection was initiated by an administrative tool on the server in another session. |
0x00000002 | The disconnection was due to a forced logoff initiated by an administrative tool on the server in another session. |
0x00000003 | The idle session limit timer on the server has elapsed. |
0x00000004 | The active session limit timer on the server has elapsed. |
0x00000005 | Another user connected to the server, forcing the disconnection of the current connection. |
0x00000006 | The server ran out of available memory resources. |
0x00000007 | The server denied the connection. |
0x00000009 | The user cannot connect to the server due to insufficient access privileges. |
0x0000000A (10) | The server does not accept saved user credentials and requires that the user enter their credentials for each connection. |
0x0000000B (11) | The disconnection was initiated by the user disconnecting his or her session on the server or by an administrative tool on the server. |
0x0000000C (12) | The disconnection was initiated by the user logging off his or her session on the server. |
Extended Disconnect Reason Codes
Reference: https://learn.microsoft.com/en-us/windows/win32/termserv/extendeddisconnectreasoncode
Extended Reason | Code |
---|---|
NoInfo | 0 |
APIInitiatedDisconnect | 1 |
APIInitiatedLogoff | 2 |
ServerIdleTimeout | 3 |
ServerLogonTimeout | 4 |
ReplacedByOtherConnection | 5 |
OutOfMemory | 6 |
ServerDeniedConnection | 7 |
ServerDeniedConnectionFips | 8 |
ServerInsufficientPrivileges | 9 |
ServerFreshCredsRequired | 10 |
RpcInitiatedDisconnectByUser | 11 |
LogoffByUser | 2 |
LicenseInternal | 256 |
LicenseNoLicenseServer | 257 |
LicenseNoLicense | 258 |
LicenseErrClientMsg | 259 |
LicenseHwidDoesntMatchLicense | 260 |
LicenseErrClientLicense | 261 |
LicenseCantFinishProtocol | 262 |
LicenseClientEndedProtocol | 263 |
LicenseErrClientEncryption | 264 |
LicenseCantUpgradeLicense | 265 |
LicenseNoRemoteConnections | 266 |
LicenseCreatingLicStoreAccDenied | 267 |
RdpEncInvalidCredentials | 768 |
ProtocolRangeStart | 4096 |
ProtocolRangeEnd | 32767 |