Skip to content

Process Trees and Call Chains

How to Check

A process tree puts each process under the one that started it, so a pair that never belongs together stands out. A shell under a service, or anything at all under lsass.exe, can give a break-in away at a glance. On a clean machine the core processes always start under the same parents, and a person's programs under explorer.exe or the terminal they opened. Live views and memory link a process to its recorded parent ID alone, which Windows reuses, so rebuild a chain from creation records where they exist. Check the parent and its start time first, because a parent that started after its child is not its parent.

What It Shows

A tree puts each process under the one that started it, so a pair that never belongs together stands out. Creation records, such as event 4688 in the Security log, Sysmon event 1 and the DeviceProcessEvents table, are written while the parent runs, so they name launchers that have exited. Live views and memory keep only a parent PID that a newer process may reuse, so join creation records on unique process IDs where a record has them.

Inside Parts It Reads

This check reads these parts, and each page shows what normal looks like.

Where Each Creation Record Keeps the Parent

Each kind of creation record names the parent in its own fields, and only some carry a value unique enough to join a whole chain without the reused-PID trap. Windows writes events 4688 and 4689 to the Security log only when Audit Process Creation and Audit Process Termination are on. Sysmon writes events 1 and 5 to Microsoft-Windows-Sysmon/Operational on machines running Sysmon, and DeviceProcessEvents comes from devices onboarded to Defender for Endpoint.

RecordFields That Name the ProcessFields That Name Its ParentJoin a Chain On
Security event 4688New Process ID, New Process NameCreator Process ID, Creator Process Name (Windows 10 and later)Nothing unique, since both IDs are hexadecimal PIDs, so pair each with the computer and the time
Sysmon event 1ProcessGuid, ProcessId, Image, CommandLineParentProcessGuid, ParentProcessId, ParentImage, ParentCommandLineProcessGuid and ParentProcessGuid, unique across a domain
DeviceProcessEventsProcessUniqueId, FileName, FolderPath, ProcessCommandLineInitiatingProcessUniqueId, InitiatingProcessFileName, InitiatingProcessCommandLineProcessUniqueId and InitiatingProcessUniqueId
Security event 4689 and Sysmon event 5Process ID and Process Name, then ProcessGuid, ProcessId and UtcTimeNoneThe exit time, since a parent that ended before its child started cannot be its parent

Live and in Memory

Each question has the tools that answer it on a running machine, and in a memory image, a copy of its memory saved to a file.

  • Who started this process, and is that parent still the same process?

    On a Running Machine

    In a Memory Image

  • What did a process start, including children that have already ended?

    On a Running Machine

    In a Memory Image

  • Can the recorded parent be trusted?

    On a Running Machine

    In a Memory Image

What It Misses

Every way of looking has gaps, so cover these from another source.

  • A live tree and windows.pstree link each process to its recorded parent PID, so an exited launcher shows as no parent, and a reused PID as the wrong one.
  • Trackers, Sysmon and EDR hold nothing from before they started, so a process older than the sensor has no creation record.
  • A parent can be set on purpose when a process is created, so pair the tree with telemetry that records the real creator.

False Positives

These look odd but are normal, so rule them out before you act.

  • csrss.exe, wininit.exe, winlogon.exe and explorer.exe show no parent in a live tree, because their launchers (a session's copy of smss.exe, and userinit.exe for explorer.exe) exit by design, and creation records still name them.
  • An elevated program's recorded parent is the program that asked for it, though a SYSTEM service created it, because User Account Control sets that parent on purpose.

Before You Start

Agree these with the machine's owner before you begin.

  • Velociraptor's Windows.Events.TrackProcesses installs Sysmon with a configuration it downloads, which changes the machine, so agree it before you start it.
  • Windows.Events.TrackProcessesETW and Windows.Events.TrackProcessesBasic need no Sysmon, and only one tracker should run at a time.

Proves These Red Flags

This check is a step in confirming each sign below.

Hunt It

The same hunt is written for four tools, so pick the one you use. Defender XDR and Sentinel queries are in KQL, which you paste into Advanced hunting in the Defender portal or into Sentinel's Logs page. Splunk queries are in SPL, for its Search page, and Velociraptor queries are in VQL, which you run as a hunt.

Needs Defender for Endpoint on every device. The Initiating columns name the parent as it ran, so an exited launcher still shows. A rare chain is a lead, not a verdict, and Microsoft does not say whether a parent set on purpose or the real creator lands in these columns, so test that before trusting them.

KQLDefender XDR, Advanced hunting
// Who starts each command shell and script host: grandparent, parent and child, rarest chains firstDeviceProcessEvents| where Timestamp > ago(30d)| where FileName in~ ("cmd.exe", "powershell.exe", "pwsh.exe", "wscript.exe", "cscript.exe")| summarize Devices = dcount(DeviceId), Starts = count(), FirstSeen = min(Timestamp), LastSeen = max(Timestamp), Example = take_any(ProcessCommandLine) by InitiatingProcessParentFileName, InitiatingProcessFileName, FileName| order by Devices asc, Starts asc| take 100

Sources