Read Linux memory and CPU pressure with vmstat
You will use vmstat to take a quick, repeatable look at runnable work, blocked processes, memory, swap traffic, block I/O and CPU time. The useful result is not one alarming number. It is a short sample that lets you tell CPU pressure from waiting on I/O, and swap activity from merely allocated swap.
The route
Jump straight to the step you need, or tick off Done means at the end.
Allow about ten minutes on a familiar host. You need a shell account with read access to /proc, which is normally an ordinary user operation. This guide describes procps-ng 4.0.4, installed here as Ubuntu package procps 2:4.0.4-4ubuntu3.3. Values and device names will differ on every host.
1. Confirm the installed command
Check which executable your shell will run and record its version before comparing output with another machine:
$ command -v vmstat
/usr/bin/vmstat
$ vmstat --version
vmstat from procps-ng 4.0.4
If command -v returns nothing, install the distribution's procps package through your normal package-management process. Do not copy a binary from another host merely to get the same output format.
Checkpoint
You have confirmed the binary and version. The rest of the examples are unprivileged and do not change system state.
2. Take a baseline snapshot
Run vmstat without a delay:
$ vmstat
procs -----------memory---------- ---swap-- -----io---- -system-- -------cpu-------
r b swpd free buff cache si so bi bo in cs us sy id wa st gu
4 0 3943984 1000824 2429760 20892688 6 17 1028 1195 4956 11 7 2 88 4 0 0
The first report contains averages since the last reboot for the rate-style fields. The process and memory values are instantaneous. Read the columns as follows:
ris runnable work, including work waiting for CPU time;bis work blocked waiting for I/O.swpdis used swap memory, whilesiandsoare memory swapped in and out per second.free,buffandcachedescribe available and cached memory in the displayed unit.biandboare block-device input and output rates.incounts interrupts per second andcscounts context switches per second.us,sy,id,wa,standguare percentages for user, kernel, idle, I/O wait, stolen virtual-machine time and KVM guest time.
Do not treat a large swpd value as proof of current memory trouble. It can be old, unused swap. Current pressure is more usefully indicated by sustained non-zero si or so, rising r, low useful memory and the workload's own symptoms.
3. Sample a live workload
Use a delay and count to collect a bounded sample. This command waits one second between reports and stops after three updates:
$ vmstat 1 3
procs -----------memory---------- ---swap-- -----io---- -system-- -------cpu-------
r b swpd free buff cache si so bi bo in cs us sy id wa st gu
1 0 3943984 1000824 2429760 20892688 6 17 1028 1195 4956 11 7 2 88 4 0 0
0 0 3943984 1000428 2429760 20892668 0 0 0 147 2791 4622 3 1 96 0 0 0
4 0 3943984 1019916 2429760 20892708 0 0 0 64 7110 13516 8 4 88 0 0 0
The exact numbers are host-specific. The first line is still the since-boot report, so compare the second and later lines when you want the sampled interval. A persistently high r with low id suggests CPU contention. High wa or b points towards waiting on I/O. Non-zero si and so across several samples indicate active swap traffic.
For a long observation, omit count, but stop it deliberately with Ctrl-C. A bounded count is safer in scripts and easier to attach to an incident record.
4. Remove the confusing first report
When you only want interval samples, add --no-first (or -y):
$ vmstat --no-first 1 2
procs -----------memory---------- ---swap-- -----io---- -system-- -------cpu-------
r b swpd free buff cache si so bi bo in cs us sy id wa st gu
2 2 3943984 992176 2429772 20902116 0 0 8 29923 14339 22198 48 4 41 6 0 0
1 2 3943984 934376 2429804 20933968 0 0 0 61784 7157 14603 37 4 48 11 0 0
Use --one-header (or -n) as well when a longer sample should print the headings only once. This makes redirected output less repetitive, but it does not change the measurements.
Checkpoint
You can now produce a bounded sample and know which rows describe the boot average and which rows describe the interval.
5. Choose units without misreading swap and I/O
Memory fields can be displayed in 1024-byte units with --unit K, or in 1000-byte units with --unit k. For example:
$ vmstat --unit K 1 1
procs -----------memory---------- ---swap-- -----io---- -system-- -------cpu-------
r b swpd free buff cache si so bi bo in cs us sy id wa st gu
2 2 3943984 934376 2429804 20933968 6 17 1028 1195 4956 11 7 2 88 4 0 0
The unit option affects memory and related byte-sized fields, but not si, so, bi or bo. The latter retain their documented rate conventions. Keep the unit choice in notes or scripts so a later reader does not compare unlike reports.
6. Inspect counters and disks when the baseline is not enough
Use vmstat --stats (or -s) for one non-repeating table of event counters and memory statistics:
$ vmstat --stats | head -n 6
32644620 K total memory
10081152 K used memory
10964716 K active memory
14822324 K inactive memory
934376 K free memory
2429804 K buffer memory
The counters are useful context, but they are not interval measurements. For per-device read, write and I/O-in-progress figures, use vmstat --disk (or -d):
$ vmstat --disk | head -n 4
disk- ------------reads------------ ------------writes----------- -----IO------
total merged sectors ms total merged sectors ms cur sec
loop0 3195 0 293054 29710 0 0 0 0 0 29
Device names such as loop0, sda and md0 depend on the host. Do not infer that a device is busy from its cumulative totals alone; use the current I/O column and a repeated sample or another tool when timing matters.
7. Handle common traps safely
Most readings are available without sudo. The --slabs mode, vmstat -m, reads /proc/slabinfo and may be unavailable to ordinary users. If it fails, check the permission error and host policy first. Do not loosen /proc permissions just to complete a diagnostic.
A container or a /proc mount using subset=pid can expose only part of the host's information. Treat missing or unusual data as a visibility boundary, not automatically as a kernel fault. If a command is interrupted, it has only read statistics; there is no configuration to undo.
For time-stamped samples, add --timestamp. For large-memory systems where columns wrap, add --wide. These options change presentation, not the underlying counters. If output is going into a parser, pin the procps version and test the exact flags on the target distribution.
Done means
- You confirmed the installed procps-ng version and that
vmstatcan read the host's/proc. - You captured a bounded sample with a delay and count.
- You ignored the first boot-average row when analysing interval behaviour, or used
--no-first. - You distinguished swap in use from active swap traffic, and CPU wait from CPU use.
- You selected units consciously and did not apply them to the swap or block-I/O rate fields.
- You know when disk, slab and container visibility changes the evidence available to you.