PowerShell: Извлечь из события название приложения

Если приложение блокируется встроенным файрволом, и при этом настроена запись логов для соединений, то такие события записываются в Журнал событий Security.
При просмотре такой записи можно увидеть примерно такую информацию:

The Windows Filtering Platform has blocked a connection.

Application Information:
Process ID: 1740
Application Name: \device\harddiskvolume4\windows\system32\svchost.exe

Network Information:
Direction: Inbound
Source Address: 192.168.0.9
Source Port: 5353
Destination Address: 224.0.0.251
Destination Port: 5353
Protocol: 17

Filter Information:
Filter Run-Time ID: 553388
Layer Name: Receive/Accept
Layer Run-Time ID: 44

То же самое можно получить ОДНОЙ СТРОКОЙ в переменную типа String (строка), если вызвать код:

$event = Get-WinEvent -FilterHashtable @{logname='Security'; Keywords=0x8010000000000000;ID=5157} -MaxEvents 1 -Oldest
$event.Message

Чтобы мне получить из этой строки путь к приложению, я сначала хотел просто парсить эту строку — искать подстроку вроде «Application Name:», потом, определив разделитель строки в виде символа окончания строки, получить новую строку и т.п. Но всё оказалось гораздо проще!
События в Журнале хранятся в виде XML. Например это событие было представлено так:

- <Event xmlns="http://schemas.microsoft.com/win/2004/08/events/event">
- <System>
<Provider Name="Microsoft-Windows-Security-Auditing" Guid="{54849625-5478-4994-A5BA-3E3B0328C30D}" />
<EventID>5157</EventID>
<Version>1</Version>
<Level>0</Level>
<Task>12810</Task>
<Opcode>0</Opcode>
<Keywords>0x8010000000000000</Keywords>
<TimeCreated SystemTime="2019-02-27T16:09:13.061655900Z" />
<EventRecordID>1131018</EventRecordID>
<Correlation />
<Execution ProcessID="4" ThreadID="7576" />
<Channel>Security</Channel>
<Computer>CompName</Computer>
<Security />
</System>
- <EventData>
<Data Name="ProcessID">1740</Data>
<Data Name="Application">\device\harddiskvolume4\windows\system32\svchost.exe</Data>
<Data Name="Direction">%%14592</Data>
<Data Name="SourceAddress">192.168.0.9</Data>
<Data Name="SourcePort">5353</Data>
<Data Name="DestAddress">224.0.0.251</Data>
<Data Name="DestPort">5353</Data>
<Data Name="Protocol">17</Data>
<Data Name="FilterRTID">378824</Data>
<Data Name="LayerName">%%14610</Data>
<Data Name="LayerRTID">44</Data>
<Data Name="RemoteUserID">S-1-0-0</Data>
<Data Name="RemoteMachineID">S-1-0-0</Data>
</EventData>
</Event>

Зная это, можно было вытаскивать сразу нужный элемент XML. Например в моем случае это можно было сделать с помощью такого кода:

$event = Get-WinEvent -FilterHashtable @{logname='Security';Keywords=0x8010000000000000;ID=5157} -MaxEvents 1 -Oldest
[xml]$eventXML = [xml]$event.ToXml()
$applicationPath = $eventXML.Event.EventData.Data | where Name -eq 'Application' | select -ExpandProperty '#text'

Если теперь вызвать переменную $applicationPath, то мы увидем её значение:

PS C:\Windows\system32> $applicationPath
\device\harddiskvolume4\users\denis\appdata\local\mail.ru\disk-o\vcurrent\disko.exe


Подписаться
Уведомление о
guest
0 Комментарий
Inline Feedbacks
View all comments