Diagnostics
Open Process diagnostics… from the inspector. Escape closes it.
Detail is expensive to collect, so it is read on request rather than streamed. Only the page you are looking at is collected, each page carries its own capture time, and the window refreshes no more often than every five seconds while open. Switching pages collects that page fresh rather than presenting an older snapshot as a new one. There is a refresh button for collecting immediately.
The process identity is checked before and after every read. A process that exits mid-walk cannot have its successor's files attributed to it, and a process macOS declines to describe is reported as declined rather than as exited.
Overview
Executable, working and root directories, virtual and resident size, running threads, priority and scheduling policy, faults, page-ins, copy-on-write faults, context switches, Mach messages sent and received, and Mach and Unix call counts.
Below those, the resource counters from proc_pid_rusage: wired memory, peak and interval
physical footprint, logical writes, instructions and cycles, wake-ups, child accounting,
the per-QoS CPU times, billed and serviced system time, runnable time, and the energy
counters.
Two of those need their units read carefully, and the table labels them:
- QoS and billed-time counters are Mach ticks, not seconds.
- The energy counters have no documented unit. They are shown as raw values and are not presented as watts or as an Energy Impact score.
Threads
Unique thread IDs where the kernel provides them, names, the scheduler's CPU estimate, accumulated user and system times, run state, scheduling policy, priorities and sleep duration.
The scheduler estimate and the accumulated times are different measurements and are not interchangeable — one is the kernel's own instantaneous figure, the other is a lifetime total. The thread times are nanoseconds already; applying the Mach timebase to them again would inflate them by roughly forty.
Where only reusable cthread handles are available, the page says so: a thread that exits can then be replaced by an unrelated one under the same label.
Open files
Descriptor number, kind, path or endpoint, family, TCP state, size, queued bytes and inode.
Sockets are resolved to endpoints: TCP and UDP over IPv4 and IPv6 with their addresses and
ports, Unix domain sockets with their paths, and kernel-control endpoints with their
names. Ports arrive in network byte order inside an int, and an IPv4 address sits after
padding inside its address union — both are handled where the fields are read.
A descriptor the kernel refused individually shows unavailable (errno N) rather than
being dropped from the list.
This is descriptors only. lsof also prints the working directory and every mapped file;
those are not descriptors and are not here. On a Finder process both report the same
eleven.
Memory map
Every readable mapping: address, size, resident, private, shared, dirty and swapped bytes, protection and maximum protection, share mode, and the mapped file.
Three visualisations sit above the table, all following the table's own snapshot, with Resident or Virtual size selectable. The two are never stacked, because resident pages are part of a virtual mapping.
By protection groups the selected measure by access bits. This is the one grouping where the parts genuinely sum to the whole.
Mapped images ranks the eight largest images with an Other bar covering the rest. Bars aggregate by full path, so repeated mappings of one image share a bar while identical basenames in different directories stay separate. These are observed mapping bytes, not file sizes, and shared-cache libraries may not appear individually.
Address ranges places the eight largest virtual mappings on a linear address axis, in address order, with the gaps between them intact. Addresses are subtracted from the lowest mapping before becoming chart coordinates, so precision is kept where the mappings actually are.
Virtual size is mostly reservation
A process's virtual total is dominated by address space that was reserved and never mapped. On a Finder process:
446.49 GB virtual across 1,326 mappings
412.32 GB no access, share mode SM_EMPTY
12.79 GB no access, share mode SM_EMPTY
12.78 GB no access, share mode SM_EMPTY
which is why vmmap headlines 3.2 GB for the same process while the kernel's own
pti_virtual_size agrees with Starf's 446 GB. The map reports reserved space separately,
and the address plot leaves those mappings at their true size — a small mapping beside a
412 GB reservation genuinely is that thin. Filter the table to look at a smaller part of
the address space.
Resident mappings can include pages shared with other processes, so they do not add up to the process's footprint.
Mach ports
IPC names and the rights held on them. These have nothing to do with network ports.
Enumeration needs a task-name port, which macOS refuses for most processes you do not own. That refusal is reported as a refusal, not as an absence of ports.
Reports
Nothing on this page is collected until you ask for it. Each report is a deliberate request, because each one either runs a tool or reads something sensitive.
| Report | Source |
|---|---|
| Stack sample | /usr/bin/sample, three seconds |
| Open files (lsof) | /usr/sbin/lsof -p — everything lsof lists, including the working directory and mapped files, unlike the Open files page |
| Virtual memory (vmmap) | /usr/bin/vmmap, which coalesces mappings differently from the Memory map page |
| Launch arguments | sysctl(KERN_PROCARGS2) — the kernel, not a tool |
| Environment | the same buffer, read past the arguments |
| Code signature | /usr/bin/codesign -dv --verbose=4 |
| Entitlements | /usr/bin/codesign -d --entitlements - |
Tools run without a shell, so nothing in a path or argument can be interpreted as one. Each has a fifteen-second deadline, output capped at 4 MB, and can be cancelled. Output is read on its own thread, so a tool that fills a pipe cannot deadlock and the deadline stays enforceable even if one stream stays open. The process identity is checked before and after; output from a process that changed identity mid-run is discarded rather than shown under the new one's name.
The environment is only ever yours
Environment values routinely hold credentials, so they are read only through this one
explicit report — never alongside anything else, never in an export, and never to satisfy
the Launch arguments report, which stops at argc for exactly that reason.
It also mostly cannot be had. Verified on macOS 26: KERN_PROCARGS2 returns a process's
environment only to that process itself. A probe reading its own buffer got 3,495 bytes
of variables after the arguments; the same probe reading a child of its own, with the same
owner, got the arguments and nothing after them. The report says so rather than printing
Environment (0) and letting you conclude the process has none.
Fileports
File descriptors this process exported as Mach ports, so another process can be handed one over IPC. Unlike the Mach ports page this needs no task port, so a process holding none is the ordinary case rather than a refusal — and the page says "0 exported descriptors", not "unavailable".
Telling those apart took care. proc_pidinfo answers "none" by returning zero and leaving
errno untouched, so a stale value from an earlier call reads as a failure. Clearing
errno before the call is what separates the two, and the same fix applies to the open
files page.
Export
Every table exports as CSV, carrying every field — including ones a narrow window hides — for the rows the filter left, in the order they are sorted. Unavailable values leave the cell empty.
Collection limits
Bounded at 4,096 threads, 8,192 file descriptors and 16,384 memory regions or Mach ports. Reaching a limit is labelled in the result rather than silently shortening the list.