Skip to content

Instantly share code, notes, and snippets.

@tyranid
Last active March 8, 2022 12:35
Show Gist options
  • Save tyranid/a219ed36c7bca7a23036d9f6cedf0cdf to your computer and use it in GitHub Desktop.
Save tyranid/a219ed36c7bca7a23036d9f6cedf0cdf to your computer and use it in GitHub Desktop.
param(
[Parameter(Mandatory)]
[string]$Path
)
# Simple script to parse permissive learning mode log entries.
Import-Module NtObjectManager
function Read-Sid {
param(
[Parameter(Mandatory, ParameterSetName="FromReader")]
[System.IO.BinaryReader]$Reader,
[Parameter(Mandatory, ParameterSetName="FromString")]
[string]$Data
)
if ($Reader -eq $null) {
if ("" -eq $Data) {
return
}
$ba = ConvertFrom-HexDump $Data
$stm = [System.IO.MemoryStream]::new($ba)
$Reader = [System.IO.BinaryReader]::new($stm)
}
if ($Reader.ReadByte() -ne 1) {
throw "Invalid SID Revision."
}
$count = $Reader.ReadByte()
$authority = $Reader.ReadBytes(6)
$rids = $()
while($count -gt 0) {
$rids += @($Reader.ReadUInt32())
$count--
}
Get-NtSid -SecurityAuthorityByte $authority -RelativeIdentifier $rids
}
function Read-Groups {
param([string]$Data)
if ("" -eq $Data) {
return
}
$ba = ConvertFrom-HexDump $Data
$stm = [System.IO.MemoryStream]::new($ba)
$reader = [System.IO.BinaryReader]::new($stm)
while($stm.Position -lt $stm.Length) {
$attr = $reader.ReadUInt32()
$sid = Read-Sid -Reader $reader
[NtApiDotNet.UserGroup]::new($sid, $attr)
}
}
function Read-Acl {
param([string]$Data)
if ("" -eq $Data) {
return
}
$ba = ConvertFrom-HexDump $Data
$stm = [System.IO.MemoryStream]::new($ba)
$reader = [System.IO.BinaryReader]::new($stm)
while($stm.Position -lt $stm.Length) {
$type = $reader.ReadUInt32()
$flags = $reader.ReadUInt32()
$mask = $reader.ReadUInt32()
$sid = Read-Sid -Reader $reader
[NtApiDotNet.Ace]::new($type, $flags, $mask, $sid)
}
}
function Convert-EventToHashTable {
param([xml]$event)
$ht = @{}
$event.Event.EventData.ChildNodes | ForEach-Object {$ht[$_.Name] = $_.'#text'}
$ht
}
function Get-SecurityDescriptor {
param($ht)
$owner = Get-NtSid -Sddl $ht['SecurityDescriptorOwner']
$group = Get-NtSid -Sddl $ht['SecurityDescriptorGroup']
$dacl = Read-Acl $ht['DaclAce']
$sacl = Read-Acl $ht['SaclAce']
$objtype = $ht['ObjectType']
if ($null -eq $objtype) {
$objtype = "File"
}
$type = Get-NtType -TypeName $objtype -ErrorAction SilentlyContinue
if ($null -eq $type) {
$type = Get-NtType -TypeName File
}
New-NtSecurityDescriptor -Owner $owner -Group $group -Dacl $dacl -Sacl $sacl -Type $type
}
function Read-AccessCheckEvent {
[CmdletBinding()]
param(
[Parameter(Mandatory, ValueFromPipeline)]
$LogEntry
)
PROCESS {
try {
$event = $LogEntry.ToXml()
$ht = Convert-EventToHashTable $event
if ($ht['Mode'] -ne 'Permissive') {
return
}
$sd = Get-SecurityDescriptor $ht
$mask = [uint32]$ht['AccessMask']
$name = $ht["ObjectName"]
if ($null -eq $name) {
$name = ""
}
$type = $ht["ObjectType"]
if ($null -eq $type) {
$type = ""
}
[PSCustomObject]@{
Name=$name
Type=$type
ProcessName=$ht['ProcessName']
Mask = Get-NtAccessMask -AccessMask $mask -AsTypeAccess $sd.NtType
PackageSid=Read-Sid -Data $ht['TokenPackage']
Groups=Read-Groups -Data $ht['TokenGroups']
Capabilities=Read-Groups -Data $ht['TokenCapabilities']
SecurityDescriptor=$sd
}
} catch {
Write-Error $_
}
}
}
try {
$Path = Resolve-Path $Path
Get-WinEvent -Path $Path -Oldest | Read-AccessCheckEvent
} catch {
Write-Error $_
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment