PowerEye is a lightweight command-line utility for measuring power consumption using Intel's RAPL (Running Average Power Limit) interface, with optional NVIDIA GPU (NVML) and IPMI sources.
It is implemented in C and built with CMake.
- CPU package power & energy via Intel RAPL
- Optional DRAM domain power & energy (
-d) - Optional system-wide power via IPMI (
-I) - Optional GPU total and per-GPU power & energy via NVIDIA NVML (
-f g,-f G) - Per-process attribution (
-p <pid>): CPU energy is split by each pid's CPU utilization, and GPU energy is split by each pid'snvmlDeviceGetProcessUtilizationSM utilization, weighted by per-device power on multi-GPU systems
- OS: Linux with
/sys/class/powercap(RAPL) support. Readingenergy_ujmay require root or a udev rule. - CPU: Intel processor with RAPL package—and optionally DRAM—domains
- GPU (optional): NVIDIA driver + NVML (
libnvidia-ml.so) if using-f g/-f G - IPMI (optional):
ipmitoolaccessible on PATH if using-I
Make sure you have CMake (version 3.22 or higher) and a C compiler installed.
git clone https://github.com/your-username/power_eye.git
cd power_eye
cmake -B build
cmake --build buildAfter building, the executable will be available at build/power_eye.
- CPU-only (no NVML dependency)
cmake -B build -DCMAKE_BUILD_TYPE=Release
cmake --build build- NVML-enabled build (adds GPU monitoring)
cmake -B build -DUSE_NVML=ON -DCMAKE_BUILD_TYPE=Release
cmake --build buildUSE_NVML=ON requires the CUDA toolkit's nvml headers/library. Adjust include/lib paths for your distribution if CMake cannot find them (e.g., /usr/local/cuda/include, /usr/local/cuda/lib64).
./power_eye [-i <interval>] [-t <timeout>] [-d] [-I] [-p <pid>]... [-f <specs>] [-h]Options:
-i <interval>: Sampling interval in seconds (default: 1)-t <timeout>: Total measurement duration in seconds (default: 120)-d: Enable DRAM power/energy (if the DRAM RAPL domain exists)-I: Enable IPMI power measurement-p <pid>: Monitor a specific process by PID. May be given multiple times.-f <specs>: Field/output specs.<specs>is a string of letters (e.g.-f cEH):d: PrependMM-ddto the timestampc: Include CPU power/energy columnsg: Include GPU total power/energy columns (requiresUSE_NVML=ON)G: Include per-GPU columns; impliesgE: Include energy(J)columns in addition to power(W)H: Print a one-line header describing the output columns
-h: Show help and exit
Timestamp
- Default:
HH:MM:SS - With
-f d:MM-DD HH:MM:SS
Columns (by flags)
-
CPU only (
-f c):[time] CPU(W) -
CPU with energy (
-f cE):[time] CPU(W) CPU(J) -
CPU + DRAM (
-d -f c):[time] CPU(W) DRAM(W) -
CPU + DRAM with energy (
-d -f cE):[time] CPU(W) CPU(J) DRAM(W) DRAM(J) -
Add GPU total (
-f cg):[time] CPU(W) GPU(W) [GPU(J) if E] -
Add per-GPU (
-f cG):[time] CPU(W) GPU(W) [GPU(J)] GPU00(W) [GPU00(J)] GPU01(W) [GPU01(J)] ... -
Per-process attribution (
-p <pid>): Per-pid columns are appended at the end. Without GPU, each pid contributes one (or two withE) columns:... PID<n>(W) [PID<n>(J)] ...With GPU enabled (
-f gor-f G), each pid contributes CPU and GPU columns:... PID<n>-CPU(W) [PID<n>-CPU(J)] PID<n>-GPU(W) [PID<n>-GPU(J)] ...Per-pid GPU values are derived from
nvmlDeviceGetProcessUtilizationSM samples and are proportional to the total GPU power/energy across all NVIDIA devices.
-
CPU power, with energy and header, sampled every 1s for 30s:
./power_eye -t 30 -f cEH
-
CPU + DRAM + GPU per-device, with energy and header:
./power_eye -d -t 60 -f cGEH
-
Per-process CPU/GPU attribution for two pids:
./power_eye -p 1234 -p 5678 -t 60 -f cgEH
This project is licensed under the MIT License. See the LICENSE file for details.
-
Platform support
- Requires Linux with RAPL exposed under
/sys/class/powercap. - Works on Intel CPUs that support RAPL. AMD/others are not supported.
- Only package 0 (
intel-rapl:0) is read; multi-socket systems beyond pkg0 are not measured. - The DRAM RAPL domain may not be present on all platforms.
- Requires Linux with RAPL exposed under
-
Permissions
- Reading
energy_ujmay require elevated privileges. Usesudoor adjust permissions via a udev rule (distro-specific).
- Reading
-
DRAM flag (
-d)- If your system lacks a DRAM RAPL domain, using
-dwill fail. Omit-din that case.
- If your system lacks a DRAM RAPL domain, using
-
GPU measurement (
-f g,-f G)- Requires NVIDIA driver + NVML (
libnvidia-ml.so) and a build with-DUSE_NVML=ON. -f Gincludes per-GPU metrics and implies-f g.- If NVML isn't available or no NVIDIA GPUs are present, GPU measurement will not work.
- Requires NVIDIA driver + NVML (
-
Per-process measurement (
-p <pid>)- CPU energy per pid is proportional to the pid's CPU time delta over the interval (from
/proc/<pid>/stat). - GPU energy per pid is proportional to its average
smUtilfromnvmlDeviceGetProcessUtilization. On multi-GPU systems, each device's contribution is weighted by that device's current power so a pid using only one GPU is not credited for power drawn by idle GPUs. - The pid must be visible to the user running
power_eye. NVML process utilization may require the same user/permissions as the GPU process.
- CPU energy per pid is proportional to the pid's CPU time delta over the interval (from
-
Timing & alignment
- Using absolute time scheduling, sampling is aligned to second-of-minute boundaries, keeping timing consistent across runs.
-
Units & fields
- Power is in watts (W) and energy in joules (J).
- Use
-f Eto include energy columns;-f Hprints a header row;-f daddsMM-DDto the timestamp.
-
Accuracy considerations
- CPU energy uses RAPL counters (platform-estimated). GPU energy is trapezoid-integrated from instantaneous NVML power readings.
- Shorter intervals generally improve integration accuracy but increase overhead.
-
Containers/VMs
- Some containers or virtual machines do not expose
/sys/class/powercapor NVML; measurements may be unavailable there.
- Some containers or virtual machines do not expose
-
More info
- See the Linux powercap documentation: https://www.kernel.org/doc/Documentation/power/powercap/powercap.txt