How to Use the sc_usage Command in macOS Terminal to Profile Mach-O System Calls and Page Faults

When high-performance native macOS applications or background daemons experience unexpected CPU spikes, thread stalls, or battery drain, standard activity monitoring tools (like Activity Monitor or top) only display coarse aggregated CPU percentages. They cannot reveal what individual threads are doing inside the Apple XNU kernel or which low-level POSIX system calls are saturating execution queues.

macOS includes a specialized, kernel-instrumented diagnostic profiler located at /usr/bin/sc_usage: sc_usage (System Call Usage). Leveraging Darwin kernel tracepoints, sc_usage samples running processes in real time, calculating the exact frequency, CPU time consumed, and page faults generated by every system call (such as read, write, select, mmap, and kevent). This guide explains how to execute and interpret sc_usage profiling sessions.

Prerequisites and Security Permissions

Because sc_usage attaches kernel-level trace hooks to monitor system calls, executing it requires root administrator privileges via sudo:

sudo sc_usage <Target_Process>

You can target an application using either its Process ID (PID) or its executable name.

Core Profiling Modes and Syntax

1. Profiling a Running Application by Name

To inspect system call activity generated by a specific process (e.g. Safari or Finder):

sudo sc_usage Safari

The terminal presents an updating live ncurses interface listing all executed system calls ranked by execution frequency and CPU consumption.

2. Filtering by Process ID (PID)

For headless daemons or background CLI utilities:

# Identify PID
pgrep -x node

# Profile specific PID
sudo sc_usage 12450

3. Logging Profiling Samples to a File

To record 30 seconds of system call activity for automated analysis:

# Sample for 30 seconds at 1-second intervals
sudo sc_usage -s 30 node > /tmp/syscall_profile.txt

Interpreting sc_usage Columns and Metrics

The profiler interface displays several critical diagnostic metrics:

Column Header Definition Performance Significance
System Call Name of kernel syscall Identifies specific I/O, IPC, or memory operation
Count Total calls during interval High counts indicate tight polling loops (e.g. nanosleep)
CPU Time Cumulative time spent in kernel Measures direct operating system overhead
Page Faults Virtual memory page faults High values indicate heavy memory pressure or thrashing
Context Switches Preemptive & voluntary switches Identifies thread contention and lock starvation

Identifying Common Bottlenecks

  • Excessive read / write Calls: Indicates that an application is performing unbuffered small I/O operations rather than batching data into larger memory blocks.
  • Frequent kevent / select: Demonstrates high event-loop socket polling in network microservices.
  • Surging Zero-Fill Page Faults: Highlights sudden massive dynamic memory allocations.

Get the best tech tips delivered straight to your inbox.

Join thousands of readers mastering Apple, Google, Microsoft, and Linux.