Repository navigation
Alerts are hard to parse - change to JSON #564
Description
Activity
Hi @dobin ,
Thanks for raising the issue. I agree that this deserves a special configuration knob to permit encoding alerts in an alternative format.
We'll try to squeeze this into the next big 3.0.0 release.Just to confirm, we're planning to include an additional flag under
alertsenders: eventlog, let's say,format. By default, it will equal a human-readable representation, but you could change it tojsonand have all alerts reported in JSON format.Does this sound acceptable?
Having a flag completely works for me yes. I just need the data :-)
Reacted by Nedim Šabić²- linked a pull request that will close this issuefeat(alertsender,eventlog): Allow events in JSON format #566
on Jan 17, 2026 Hey @dobin,
I just pushed the pull request #566, which will be incorporated in version 3.0.0. I hope this will address your needs. The resulting JSON has the following layout:
{ "id": "64af2e2e-2309-4079-9c0f-985f1dd930f5", "title": "Suspicious Vault client DLL load", "severity": "high", "text": "Suspicious process C:\\WINDOWS\\system32\\VaultCmd.exe loaded the Credential Vault Client DLL for potential credentials harvesting\n", "description": "Identifies loading of the Vault client DLL by an unusual process. Adversaries can abuse the functions provided \nby the Credential Vault Client Library to enumerate or harvest saved credentials.\n", "labels": { "subtechnique.id": "T1555.004", "subtechnique.name": "Windows Credential Manager", "subtechnique.ref": "https://attack.mitre.org/techniques/T1555/004/", "tactic.id": "TA0006", "tactic.name": "Credential Access", "tactic.ref": "https://attack.mitre.org/tactics/TA0006/", "technique.id": "T1555", "technique.name": "Credentials from Password Stores", "technique.ref": "https://attack.mitre.org/techniques/T1555/" }, "events": [ { "name": "CreateProcess", "category": "process", "timestamp": "2026-01-17T17:06:13.8418922+01:00", "params": { "cmdline": "\"C:\\WINDOWS\\system32\\VaultCmd.exe\" \"/listcreds:Windows Credentials\" /all", "directory_table_base": "5c3e0000", "domain": "OSIRIS", "exe": "C:\\WINDOWS\\system32\\VaultCmd.exe", "exit_status": "Success", "flags": "", "kproc": "ffffad8248c4d080", "name": "VaultCmd.exe", "pid": 1192, "ppid": 16776, "real_ppid": 16776, "session_id": 1, "sid": "S-1-5-21-2271034452-2606270099-984871569-1001", "start_time": "2026-01-17 17:06:13.8418922 +0100 CET", "token_elevation_type": "FULL", "token_integrity_level": "HIGH", "token_is_elevated": true, "username": "archbunny" }, "callstack": "0xfffff805ea9e0534 C:\\WINDOWS\\system32\\ntoskrnl.exe!PsIsThreadTerminating+0x1f4|0xfffff805ea8d312d C:\\WINDOWS\\system32\\ntoskrnl.exe!KeAddProcessorAffinityEx+0x74d|0xfffff805ea91d312 C:\\WINDOWS\\system32\\ntoskrnl.exe!FsRtlAreNamesEqual+0x5b2|0xfffff805eaf4345e C:\\WINDOWS\\system32\\ntoskrnl.exe!PsAcquireProcessExitSynchronization+0x130e|0xfffff805eaf43194 C:\\WINDOWS\\system32\\ntoskrnl.exe!PsAcquireProcessExitSynchronization+0x1044|0xfffff805eae9caed C:\\WINDOWS\\system32\\ntoskrnl.exe!RtlFreeAnsiString+0x181d|0xfffff805eb0c2b5e C:\\WINDOWS\\system32\\ntoskrnl.exe!CcMdlRead+0x6abe|0xfffff805eacb5655 C:\\WINDOWS\\system32\\ntoskrnl.exe!setjmpex+0x91d5|0x7fff650c35d4 C:\\Windows\\System32\\ntdll.dll!ZwCreateUserProcess|0x7fff625061da C:\\Windows\\System32\\KernelBase.dll!CreateProcessInternalW|0x7fff62503836 C:\\Windows\\System32\\KernelBase.dll!CreateProcessW|0x7fff62e3c6d4 C:\\Windows\\System32\\kernel32.dll!CreateProcessW|0x7fff44f51876 C:\\Windows\\assembly\\NativeImages_v4.0.30319_64\\System\\22f4d83e48c2201947e262d4bca638b9\\System.ni.dll!?|0x7fff44eb3c89 C:\\Windows\\assembly\\NativeImages_v4.0.30319_64\\System\\22f4d83e48c2201947e262d4bca638b9\\System.ni.dll!?|0x7fff44eb35f9 C:\\Windows\\assembly\\NativeImages_v4.0.30319_64\\System\\22f4d83e48c2201947e262d4bca638b9\\System.ni.dll!?|0x7ffeece57359 C:\\Windows\\assembly\\NativeImages_v4.0.30319_64\\System.Manaa57fc8cc#\\ba138601d2c08733806b218620e45e0b\\System.Management.Automation.ni.dll!?|0x7ffeecd6ba1a C:\\Windows\\assembly\\NativeImages_v4.0.30319_64\\System.Manaa57fc8cc#\\ba138601d2c08733806b218620e45e0b\\System.Management.Automation.ni.dll!?|0x7ffeece18d8d C:\\Windows\\assembly\\NativeImages_v4.0.30319_64\\System.Manaa57fc8cc#\\ba138601d2c08733806b218620e45e0b\\System.Management.Automation.ni.dll!?|0x7ffeece18a4b C:\\Windows\\assembly\\NativeImages_v4.0.30319_64\\System.Manaa57fc8cc#\\ba138601d2c08733806b218620e45e0b\\System.Management.Automation.ni.dll!?|0x7ffeecef005f C:\\Windows\\assembly\\NativeImages_v4.0.30319_64\\System.Manaa57fc8cc#\\ba138601d2c08733806b218620e45e0b\\System.Management.Automation.ni.dll!?|0x7ffee95d5031 unbacked!?", "proc": { "pid": 1192, "tid": 3916, "ppid": 16776, "name": "VaultCmd.exe", "exe": "C:\\WINDOWS\\system32\\VaultCmd.exe", "cmdline": "\"C:\\WINDOWS\\system32\\VaultCmd.exe\" \"/listcreds:Windows Credentials\" /all", "parent_name": "powershell.exe", "parent_cmdline": "C:\\WINDOWS\\System32\\WindowsPowerShell\\v1.0\\powershell.exe", "sid": "S-1-5-21-2271034452-2606270099-984871569-1001", "username": "archbunny", "domain": "OSIRIS", "session_id": 1, "integrity_level": "HIGH", "is_wow64": false, "is_packaged": false, "is_protected": false, "ancestors": [ "powershell.exe (16776)", "WindowsTerminal.exe (6080)", "explorer.exe (7688)" ] } }, { "name": "LoadImage", "category": "image", "timestamp": "2026-01-17T17:06:13.8517121+01:00", "params": { "base_address": "7fff42800000", "checksum": 336202, "default_address": "7fff42800000", "file_path": "C:\\Windows\\System32\\vaultcli.dll", "image_size": 323584, "is_dll": true, "is_dotnet": false, "is_driver": false, "is_exec": false, "pid": 1192, "signature_level": "AUTHENTICODE", "signature_type": "CATALOG_CACHED" }, "callstack": "0xfffff805ea9e0534 C:\\WINDOWS\\system32\\ntoskrnl.exe!PsIsThreadTerminating+0x1f4|0xfffff805ea8d312d C:\\WINDOWS\\system32\\ntoskrnl.exe!KeAddProcessorAffinityEx+0x74d|0xfffff805ea91d312 C:\\WINDOWS\\system32\\ntoskrnl.exe!FsRtlAreNamesEqual+0x5b2|0xfffff805eaef7f48 C:\\WINDOWS\\system32\\ntoskrnl.exe!PsReferenceProcessFilePointer+0x848|0xfffff805eaef7bbb C:\\WINDOWS\\system32\\ntoskrnl.exe!PsReferenceProcessFilePointer+0x4bb|0xfffff805eaeda620 C:\\WINDOWS\\system32\\ntoskrnl.exe!NtAllocateVirtualMemory+0x5570|0xfffff805eae90f2b C:\\WINDOWS\\system32\\ntoskrnl.exe!NtMapViewOfSection+0xc7b|0xfffff805eae904fd C:\\WINDOWS\\system32\\ntoskrnl.exe!NtMapViewOfSection+0x24d|0xfffff805eacb5655 C:\\WINDOWS\\system32\\ntoskrnl.exe!setjmpex+0x91d5|0x7fff650c20c4 C:\\Windows\\System32\\ntdll.dll!ZwMapViewOfSection|0x7fff64f653db C:\\Windows\\System32\\ntdll.dll!RtlAppendUnicodeStringToString|0x7fff64f64e1e C:\\Windows\\System32\\ntdll.dll!RtlAppendUnicodeStringToString|0x7fff64f684cc C:\\Windows\\System32\\ntdll.dll!RtlInsertElementGenericTableFullAvl|0x7fff64f63c3c C:\\Windows\\System32\\ntdll.dll!RtlGetFullPathName_UstrEx|0x7fff64fd41ba C:\\Windows\\System32\\ntdll.dll!TpSetWaitEx|0x7fff64fd5180 C:\\Windows\\System32\\ntdll.dll!RtlSetThreadSubProcessTag|0x7fff64fd63c1 C:\\Windows\\System32\\ntdll.dll!RtlSetThreadSubProcessTag|0x7fff62e2e8d7 C:\\Windows\\System32\\kernel32.dll!BaseThreadInitThunk|0x7fff64fec53c C:\\Windows\\System32\\ntdll.dll!RtlUserThreadStart", "proc": { "pid": 1192, "tid": 17448, "ppid": 16776, "name": "VaultCmd.exe", "exe": "C:\\WINDOWS\\system32\\VaultCmd.exe", "cmdline": "\"C:\\WINDOWS\\system32\\VaultCmd.exe\" \"/listcreds:Windows Credentials\" /all", "parent_name": "powershell.exe", "parent_cmdline": "C:\\WINDOWS\\System32\\WindowsPowerShell\\v1.0\\powershell.exe", "sid": "S-1-5-21-2271034452-2606270099-984871569-1001", "username": "archbunny", "domain": "OSIRIS", "session_id": 1, "integrity_level": "HIGH", "is_wow64": false, "is_packaged": false, "is_protected": false, "ancestors": [ "powershell.exe (16776)", "WindowsTerminal.exe (6080)", "explorer.exe (7688)" ] } } ] }The event data format in Eventlog Viewer:

Looking good. That fulfills my requirement.
But, the callstack is a bit chunky, a long string (here with inserted newlines):
"callstack": "0xfffff805ea9e0534 C:\\WINDOWS\\system32\\ntoskrnl.exe!PsIsThreadTerminating+0x1f4|0xfffff805ea8d312d C:\\WINDOWS\\system32\\ntoskrnl.exe!KeAddProcessorAffinityEx+0x74d|0xfffff805ea91d312 C:\\WINDOWS\\system32\\ntoskrnl.exe!FsRtlAreNamesEqual+0x5b2|0xfffff805eaf4345e ..."Does the first address have a special purpose? It has no string associated with it. But the thing is parseable if i need to.
To store it a bit more accessible, something like this could be useful, but not mandatory - add it as an array instead of a string:
"callstack": [ "C:\\WINDOWS\\system32\\ntoskrnl.exe!PsIsThreadTerminating+0x1f4|0xfffff805ea8d312d" "C:\\WINDOWS\\system32\\ntoskrnl.exe!KeAddProcessorAffinityEx+0x74d|0xfffff805ea91d312" "C:\\WINDOWS\\system32\\ntoskrnl.exe!FsRtlAreNamesEqual+0x5b2|0xfffff805eaf4345e" ....Makes sense. I'll nuke the return address from the callstack summary and append each frame as a separate string to the
callstackarray.@dobin This is the layout of the
callstackfield after proposed adjustments:"callstack": [ "C:\\WINDOWS\\system32\\ntoskrnl.exe!PsIsThreadTerminating", "C:\\WINDOWS\\system32\\ntoskrnl.exe!KeAddProcessorAffinityEx", "C:\\WINDOWS\\system32\\ntoskrnl.exe!FsRtlAreNamesEqual", "C:\\WINDOWS\\system32\\ntoskrnl.exe!PsAcquireProcessExitSynchronization", "C:\\WINDOWS\\system32\\ntoskrnl.exe!PsAcquireProcessExitSynchronization", "C:\\WINDOWS\\system32\\ntoskrnl.exe!RtlFreeAnsiString", "C:\\WINDOWS\\system32\\ntoskrnl.exe!CcMdlRead", "C:\\WINDOWS\\system32\\ntoskrnl.exe!setjmpex", "C:\\Windows\\System32\\ntdll.dll!ZwCreateUserProcess", "C:\\Windows\\System32\\KernelBase.dll!CreateProcessInternalW", "C:\\Windows\\System32\\KernelBase.dll!CreateProcessW", "C:\\Windows\\System32\\kernel32.dll!CreateProcessW", "C:\\Windows\\System32\\windows.storage.dll!HideExtension", "C:\\Windows\\System32\\windows.storage.dll!App_IsLFNAware", "C:\\Windows\\System32\\windows.storage.dll!Global_WindowsStorage_csIconCache", "C:\\Windows\\System32\\windows.storage.dll!CheckSmartScreenWithAltFile", "C:\\Windows\\System32\\windows.storage.dll!CheckSmartScreenWithAltFile", "C:\\Windows\\System32\\windows.storage.dll!CheckSmartScreenWithAltFile", "C:\\Windows\\System32\\windows.storage.dll!CheckSmartScreenWithAltFile", "C:\\Windows\\System32\\windows.storage.dll!CheckSmartScreenWithAltFile", "C:\\Windows\\System32\\windows.storage.dll!CViewSettings_CreateInstance", "C:\\Windows\\System32\\windows.storage.dll!SHCoCreateInstanceWorker", "C:\\Windows\\System32\\shell32.dll!SHAppBarMessage", "C:\\Windows\\System32\\shell32.dll!SHAppBarMessage", "C:\\Windows\\System32\\shell32.dll!SHCreateDrvExtIcon", "C:\\Windows\\System32\\shell32.dll!SHFormatDrive", "C:\\Windows\\System32\\windows.storage.dll!ICI2ICIX", "C:\\Windows\\System32\\windows.storage.dll!STORAGE_CreateStorageItemFromShellItem_FullTrustCaller_ForPackage", "C:\\Windows\\System32\\windows.storage.dll!STORAGE_CreateStorageItemFromShellItem_FullTrustCaller_ForPackage", "C:\\Windows\\System32\\shell32.dll!SHCreateDrvExtIcon", "C:\\Windows\\System32\\shell32.dll!SHFormatDrive", "C:\\Windows\\System32\\windows.storage.dll!GetSelectionStateFromItemArray", "C:\\Windows\\System32\\windows.storage.dll!RealShellExecuteW", "C:\\Windows\\System32\\windows.storage.dll!RealShellExecuteW", "C:\\Windows\\System32\\windows.storage.dll!CViewSettings_CreateInstance", "C:\\Windows\\System32\\windows.storage.dll!CFileOperationRecorder_CreateInstance", "C:\\Windows\\System32\\windows.storage.dll!ShellExecuteExW", "C:\\Windows\\System32\\Taskbar.dll!?", "C:\\Windows\\System32\\Taskbar.dll!?", "C:\\Windows\\System32\\Taskbar.dll!?", "C:\\Windows\\System32\\Taskbar.dll!DllGetActivationFactory", "C:\\Windows\\System32\\SHCore.dll!Ordinal234", "C:\\Windows\\System32\\kernel32.dll!BaseThreadInitThunk", "C:\\Windows\\System32\\ntdll.dll!RtlUserThreadStart" ],
Hm. I like the previous one more:
C:\\WINDOWS\\system32\\ntoskrnl.exe!PsIsThreadTerminating+0x1f4|0xfffff805ea8d312dEven tho the offset / absolute address is rarely used, it does points exactly to the precise address - if someone would want to use it. Only giving the module name is removing "relevant" information.
My issue was with the lonely return address without module, which makes it inconsistent, and makes parsing harder:
"callstack": "0xfffff805ea9e0534 <-------- no module? C:\\WINDOWS\\system32\\ntoskrnl.exe!PsIsThreadTerminating+0x1f4|0xfffff805ea8d312d C:\\WINDOWS\\system32\\ntoskrnl.exe!KeAddProcessorAffinityEx+0x74d|0xfffff805ea91d312 C:\\WINDOWS\\system32\\ntoskrnl.exe!FsRtlAreNamesEqual+0x5b2|0xfffff805eaf4345e ..."Callstack return address is predictable (meaning, it is always present). Unlikely, the offset exists only for kernel addresses. Do you agree if we just add the return address?
The +0x1f4? Could have been useful, but not really for kernel addresses.
Only the return address is good.
@dobin Fibratus 3.0.0 has been released with this feature in. Sorry for the delay.
Download: https://fibratus.io/downloads
For documentation purposes, here is the relevant config section:
# =============================== Alert senders ======================================== # Alert senders deal with emitting alerts via different channels. alertsenders: eventlog: # Specifies the eventlog record format for the alert. Can be pretty|json format: jsonParser updated dobin/DetonatorAgent@ffeacdc
Works very well.
@dobin Looks awesome! Thanks for you patience.
Could we use Detonator Agent to improve Fibratus detection blind spots? Like, increasing coverage on techniques malware rely on and Fibratus can't currently detect?
Motivation
I want to parse the alerts of fibratus to ingest them into my own project.
For that i need information like alert/detection ID, category, severity, threat name etc.
I parse the windows event logs, as in https://www.fibratus.io/#/alerts/senders/eventlog.
The relevant information is separated by newlines, whitespace, and colons.
Like this:
Additionally, some information is stored with UTF8 arrows like "directory_table_base➜ 530c7000, domain➜ DESKTOP-C0HF6MF, exe➜ C:\Program Files (x86)".
This makes it hard to write a parser to extract the information.
Feature
Either change, or make an option which changes the output to JSON:
Like this:
Make sure that additional data like callstacks are nicely integrated.
Alternatives
XML or whatever.
Additional context
While the event logs in the current state are nicely human readable, it should be machine readable first.
My ugly LLM generated fibratus log parser: https://github.com/dobin/DetonatorAgent/blob/main/EdrPlugins/FibratusEdrPlugin.cs#L208
I need output like the following example: https://detonator.r00ted.ch/submissions/9