With pidstat On Linux, I measure CPU, memory, I/O, and thread activity for each process at fixed intervals, which allows me to identify trends rather than just snapshots. That's how I find Bottlenecks Once you've identified it reliably, assign it to a PID or a command and determine whether the cause is the CPU, RAM, I/O, or a context switch.
Key points
- Interval Measurement: Time series for each process rather than just a snapshot.
- Broad Coverage: CPU, memory, I/O, threads, and context switches.
- Targeted Filtering: Monitor focusing via PID or command.
- Easy to Use: Install sysstat, then start it right away.
- Practical benefits: Quickly identify peak loads, leaks, and I/O bottlenecks.
What is pidstat? A brief explanation
I use pidstat, to visualize the resource usage of individual processes over time. The tool is part of the package sysstat and provides metrics for each process, including CPU, memory, I/O, threads, and context switches. Unlike `top`, I don’t get a fleeting snapshot, but rather continuous measurement points at regular intervals. This allows me to identify patterns such as periodic spikes, sustained load, or gradual growth. This temporal information helps me clearly attribute causes to specific processes and avoid getting lost in the noise of a single snapshot.
Installation and Quick Setup
I install sysstat using my distribution's package manager, and I can run pidstat right away without any additional configuration. The basic syntax remains simple: pidstat [options] [interval] [count]. Without any options, the tool displays CPU-Values per process; it repeats the measurements continuously at specified intervals. Example: pidstat 2 10 It collects ten data points every two seconds. This allows me to quickly build a robust timeline for further analysis.
CPU Analysis: Visualizing the Load per Process
For CPU-related questions, I'll start by pidstat with -u, for example pidstat -u 1 for the second tick. The columns %usr, %system, and %CPU show me how much user and kernel time a process is using. If I need to focus on a specific application, I use -p or -C for name filters. If %system rises sharply, I check system calls or I/O impacts; if %usr dominates, the work is in user space. For further breakdown by process, please refer to the following if needed: Process Accounting, in order to analyze usage data in a structured manner.
Check Memory Usage in a Targeted Manner
When it comes to RAM-related topics, -r valuable insights, such as through pidstat -r -p 1234 1. I monitor how virtual and resident memory usage changes over the course of several minutes and whether page faults are increasing. If usage increases steadily in small increments, I can detect potential leaks early on. If usage remains constant and increases only during brief periods, this indicates legitimate Caching ... By using interval measurement, I can clearly distinguish outliers from genuine trends.
Understanding I/O and Context Switches
With -d I monitor read and write activity for each process to identify the sources of high wait times on the storage device. High transfer rates combined with increasing latencies indicate storage bottlenecks. In addition, I check using -w the number of context switches per second, because excessive switching can create unnecessary overhead. A high number of voluntary context switches (vswch/s) indicates synchronization; a high number of forced context switches (cswch/s) indicates intense competition for CPU time. This is how I identify inefficient workloads, which I then specifically optimize.
Monitor Threads and Find Hotspots
Do I use -t, pidstat also provides thread metrics for each process. This lets me see if individual workers in an application are behaving abnormally. For Java, PHP-FPM, databases, or queue workers, I can identify threads that are tying up the CPU or causing memory usage to spike. If I detect any imbalances, I adjust thread pools, affinities, or Limits This perspective helps me optimize not only processes but also their internal parallelism.
An Overview of Important Options
I use the core switches specifically to Analyzes to drive the process with focus and keep the output readable. The following table concisely summarizes the key options and typical use cases. This allows me to quickly select the right switch for the CPU, memory, I/O, threads, or filters. Examples help me get started right away. Each row provides me with a clear Note depending on the intended use.
| Option | Function | Example |
|---|---|---|
-u | Display CPU usage by process | pidstat -u 1 |
-r | Memory and Page Fault Values | pidstat -r -p 1234 2 |
-d | Read/Write I/O Activity | pidstat -d 1 |
-w | Context Switch per Process | pidstat -w -p 1234 1 |
-t | Show thread statistics | pidstat -t -p 1234 1 |
-p | Limit to specific process IDs | pidstat -u -p 1234 1 |
-C | Filter Processes by Command | pidstat -C php-fpm 2 |
Filters, Intervals, and Targeted Monitoring
I'm planning to take measurements with Intervals, which fit the question: seconds for sprinters, minutes for long-distance runners. About -p and -C I limit the output to relevant processes and keep the console uncluttered. pidstat 2 10 It works well for short tests; if I don't specify a number, it runs continuously until I stop it. For recurring checks, I store commands in scripts and document the Baseline of a system. This routine saves time if load problems occur again.
Comparison with top, ps, and others.
For a quick overview, I use top or P.S., but for trends and depth of detail, I turn to pidstat. Interval values allow me to identify root causes over time rather than just seeing symptoms. If I need deeper insight into CPU bottlenecks, I supplement the analysis with Linux perf for samples of the call stacks. This is how I combine process statistics with profiling when pure utilization metrics aren't enough. This combination provides me with quick insights and a well-founded Diagnosis.
Practical Tips for Everyday Life
I keep a set of tried-and-true commands on hand and adapt them as needed for Production Systems. Live CPU load: pidstat -u 1. Storage in Focus: pidstat -r -p 2. Check for I/O bottlenecks: pidstat -d 1. Threads at a Glance: pidstat -t -p 1. For more in-depth system instrumentation, I also use bpftrace Tips when kernel events require Spotlight.
Reading Output Correctly: Timelines and Multi-Core Systems
I'm paying attention to how pidstat sets the time references: The First measurement block By default, displays average values since the process started (or since the system started); all subsequent blocks refer to the selected Interval. For detailed analyses, I often ignore the first block and consider only the interval values that are comparable in terms of time.
At Multi-core systems I always interpret %CPU in the context of the available cores. A single process on an 8-core host can theoretically reach up to 800% if it scales across multiple threads. High %system values lead me to suspect system calls, lock contention, or I/O wait paths; high %usr values indicate computationally intensive routines in user space. The timestamp before each line makes outliers in the trend clearly recognizable and facilitates correlation with logs or metrics from other sources.
Methodology: Formulating Hypotheses, Selecting Measurement Windows
I never start blindly; instead, I formulate a Hypothesis Regarding the cause: „CPU-bound in user space,“ „I/O queue is backed up,“ „memory is growing steadily.“ Based on this, I determine the monitoring interval: For short spikes, I use 1–2-second intervals; for Cross-country skiers more like 10–60 seconds. It's important to adjust the window to the Dynamics to adjust the system so as to neither lose detail nor pick up an unnecessary amount of noise.
I also take measurements before and after Changes (e.g., release, configuration tuning) to make the effects visible in the metrics. A clean Baseline For each environment (DEV, STAGE, PROD), this helps me distinguish real deviations from normal patterns.
Permanent Recording and Follow-up
For problems that are difficult to grasp, I take notes for a set period of time and analyze them later. Example: pidstat -udwt 2 900 > /var/log/pidstat_$(date +%F_%H%M).log collects CPU, I/O, context switches, and threads every 2 seconds for 30 minutes. I can use grep, awk or a short script post-processing, mark peaks, and extract notable PIDs. For recurring observations, I plan to Rotation Schedule and reserve only the relevant time slots to save space.
When I need multiple perspectives, I combine switches into a single run instead of launching multiple tools in parallel. This keeps the measurement results synchronous and makes analysis easier.
Containers, Namespaces, and PIDs
In container environments, the following applies: PIDs are namespaced. When I measure on the host, I see host PIDs; when I measure in the container, I see container PIDs. To ensure unambiguous mapping, I therefore prefer to filter by command name using -C rather than using a single PID that changes after a restart. When I'm working on the host side, I supplement the process context (e.g., via service or pod names in logs) so that I can later clearly associate metrics with a Workload to assign. For long-running recordings, I avoid the PID trap (PID Reuse) also through name filters or through companion logs that document the PID's lifetime.
Reliable Measurement in Production: Overhead, Rights, Data Protection
Overhead: pidstat primarily reads from /proc and requires very little effort to measure. For very short intervals on heavily loaded hosts, I increase the interval slightly (e.g., from 1 to 2 seconds) to further reduce the impact on the CPU. I measure selectively (filters!) rather than „everything, everywhere.“.
Rights & Safety: Depending on the system configuration (hidepid at /proc) Details are not visible to all users. On the production environment, I work with elevated privileges when necessary, keep the measurement duration short, and check whether displaying the full Command lines could reveal sensitive parameters. Logs containing diagnostic data should only be stored where they can be securely saved and deleted.
Quickly Recognize Typical Patterns
- High %s system with moderate % usage: Indication of kernel-level hotspots (intensive syscall usage, lock contention, network/storage driver paths). I correlate this with I/O metrics and context switches.
- Many forced context switches (cswch/s): Heavy competition for CPU time, often due to insufficient CPU resources or too many active threads. Throttle, adjust pool sizes, or Affinities check.
- Many voluntary context switches (vswch/s): Pronounced synchronization or yield-based queues. I'm examining locks, backoff strategies, and thread pool behavior.
- Steadily Increasing Storage: Suspected leak. I'm checking to see if Page Faults (in particular majflt) and whether the process frees up memory again after load spikes. If it doesn't, I'll confirm this with a longer interval measurement.
- High I/O transfer rates with slow system throughput: When combined with wait times, the process I/O values indicate bottlenecks in the underlying storage stack. I prioritize I/O-optimization measures (batching, caching, asynchronous I/O).
- Certain threads stand outWith
-tI identify the „hot thread“ and either adjust the thread pool or specifically examine its code path.
Real-World Workflows
Identify CPU-bound operations: First pidstat -u 1 globally, then specifically with -p or -C. If %usr goes up, I'll look for the hot thread with -t and then, if necessary, analyze the results using a sampling profiler. If %s systems are dominant, I also take a look at I/O and context switches.
Confirm a memory leak: For several minutes with pidstat -r -p 5 monitor. I'm documenting a steady increase with no decline following periods of heavy load. At the same time, I'm checking whether page fault rates or I/O patterns explain this behavior. If the trend persists without a legitimate explanation, that's a clear Leak Indicator.
Identifying I/O BottlenecksWith pidstat -d 1 I identify read/write hotspots. If I see a significant write load caused by just a few processes, I focus on their flush/sync paths and batch sizes. Correlating this with context switches helps me see whether the CPU is under pressure at the same time.
Correcting Thread Imbalance: pidstat -t -p 1 shows me the load and context switches per thread. If one worker gets significantly hotter than the rest, I adjust the pool sizes, task distribution, or Affinity and check whether the distribution normalizes in the next intervals.
Limitations of pidstat and Useful Additions
pidstat displays what consumed resources and when It happens—it doesn't automatically explain that why in the code path. To understand the „why,“ I also use sampling profilers or kernel tracepoints. When it comes to memory issues, pidstat highlights trends but does not shed light on object lifecycles. I therefore view pidstat as First Responder, which helps me pinpoint problem areas with minimal effort. When simple utilization metrics are no longer sufficient, I conduct a more in-depth analysis using the tools mentioned earlier.
Quick Start Checklist
- Refine the research question: CPU, RAM, I/O, threads, or context switches?
- Select Interval: Seconds for spikes, minutes for trends.
- Set Filters:
-por-Cuse to keep the output concise. - First, the big picture; then, the details: Start globally, filter out conspicuous processes.
- Align the first block: The first line is averaged from the start; then compare the values for each interval.
- Limit the measurement duration: Collect enough data to identify trends, but keep logs under control.
- Document: Recording the baseline, hypothesis, measurement parameters, and observations—that’s what makes analyses reproducible.
Briefly summarized
With pidstat I receive time-based process data on CPU, RAM, I/O, threads, and context switches, which allows me to identify the true causes of load patterns. The combination of filters, intervals, and clear metrics makes analyses targeted and reproducible. I identify trends instead of being misled by snapshots and implement appropriate countermeasures. Commands such as pidstat -u 1, -r, -d and -w cover the most common scenarios. This is how I keep systems transparent, decisions quick, and diagnoses comprehensible.


