
Running a Linux server means dealing with processes constantly. You need to find them, monitor them, and sometimes kill them when they hang. The problem is that most administrators only know ps and grep, which creates messy output and false positives. You need a cleaner, more precise tool for process ID lookup.
The pidof command solves this problem by returning the exact Process ID (PID) when you search by process name. This Linux server tutorial shows you how to install pidof, use all its options, and apply it in real automation scripts. After reading this guide, you will master the pidof Command in Linux with Examples for production environments.
I have spent 10 years as a Linux sysadmin managing servers for production workloads. During that time, I learned that pidof is indispensable for shell scripting and service monitoring. This guide reflects actual field experience, not just textbook theory.
Prerequisites
Before you start using pidof, make sure you have the following:
- Operating System: Any Linux distribution (Fedora, Ubuntu, Debian, CentOS, AlmaLinux, Rocky Linux)
- Access Level: Root or sudo privileges for installation and some advanced options
- Terminal Access: SSH connection or direct terminal access to your system
- Package Manager:
dnf(RHEL/Fedora),apt(Debian/Ubuntu), oryum(older CentOS) - Basic Shell Knowledge: Understanding of bash scripting helps for automation examples
You do not need prior experience with pidof. This guide starts from installation and builds up to advanced scripting patterns.
Step 1: Install the pidof Command on Your Linux System
Check if pidof Is Already Installed
First, verify whether pidof exists on your system:
pidof --version
WHAT this does: Runs pidof with the version flag to confirm installation.
WHY you need this: Many modern Linux distributions include pidof by default, but some minimal installations do not. Checking first saves time if you already have it.
Expected output (if installed):
pidof from procps-ng 3.9.0
If you get command not found, proceed to installation.
Install pidof on Fedora, RHEL, AlmaLinux, or Rocky Linux
On Red Hat-based systems, pidof comes from the procps-ng package:
sudo dnf install procps-ng -y
WHAT this does: Uses dnf to install the procps-ng package with automatic confirmation (-y).
WHY you need this: Fedora and RHEL 8+ split process management tools into procps-ng. Without this package, pidof is missing from your system.
Expected output:
Installing:
procps-ng-3.9.0-5.fc38.x86_64
Transaction Summary
Install 1 Package
Total download size: 150 kB
Installed size: 480 kB
Install pidof on Ubuntu, Debian, or Kali Linux
On Debian-based systems, pidof comes from sysvinit-utils:
sudo apt install sysvinit-utils -y
WHAT this does: Uses apt to install sysvinit-utils with automatic confirmation.
WHY you need this: Debian and Ubuntu package pidof differently than Red Hat. The sysvinit-utils package contains init system utilities including pidof.
Expected output:
Reading package lists... Done
Building dependency tree... Done
The following NEW packages will be installed:
sysvinit-utils
Summary: 1 new package, 150 kB
Verify Installation After Installing
Confirm pidof is now available:
pidof bash
WHAT this does: Runs a basic pidof command to test functionality.
WHY you need this: Verification ensures the installation succeeded and pidof works correctly before you use it in scripts.
Expected output:
1234
(The number is your bash process PID, which will differ on your system)
Step 2: Understand pidof Syntax and Core Options
Basic Syntax Structure
The pidof command follows this pattern:
pidof [options] [program_name]
WHAT this means: You provide options (starting with -) followed by the process name you want to find.
WHY this matters: Understanding syntax prevents errors. Place options before the program name, and you can search for multiple programs in one command.
Essential Options You Must Know
Run pidof with help to see all options:
pidof --help
WHAT this does: Displays pidof’s built-in help text with all available options.
WHY you need this: Help text is your quick reference when you forget option details. Keep it handy for future lookups.
Output highlights:
pidof [options] [program...]
Options:
-s Return only one PID
-c Show PIDs with same root directory (root only)
-n Skip stat() for NFS binaries
-q Quiet mode, exit with success/failure only
-x Include PIDs of shells running named scripts
-z Detect and include zombie processes
-d sep Use sep as separator for multiple PIDs
-o omit Omit specified PID
The -s Option for Single PID Output
pidof -s firefox
WHAT this does: Returns only the first PID instead of all matching PIDs.
WHY you need this: Modern applications like Firefox run multiple processes. Scripts often need exactly one PID. Without -s, you get space-separated multiple PIDs that break simple variable assignment.
Without -s output:
2847 2848 2849 2850
With -s output:
2847
The -q Option for Script Boolean Checks
pidof -q nginx && echo "Running" || echo "Not running"
WHAT this does: Runs pidof quietly (no output) and checks exit status with && and ||.
WHY you need this: Production monitoring scripts need boolean checks without output noise. Quiet mode returns true (0) if PID found, false (1) if not. This pattern is standard for service health checks.
Expected output when nginx runs:
Running
Expected output when nginx stops:
Not running
The -x Option for Script Process Detection
pidof -x backup.sh
WHAT this does: Finds PIDs of shell processes running the named script.
WHY you need this: Scripts run inside shells, not as standalone binaries. Regular pidof misses script processes. The -x flag includes shells running named scripts, which is critical for debugging long-running automation.
Real scenario: You have a backup script running for 6 hours. You need to kill it, but pidof backup.sh returns nothing. Adding -x finds the bash process running your script.
Step 3: Execute Basic pidof Commands for Process Lookup
Find PID of a Single Running Process
pidof bash
WHAT this does: Returns the PID of the bash process on your system.
WHY you need this: This is the foundation of all pidof usage. You provide a process name, and pidof returns its PID. Every advanced example builds on this basic pattern.
Expected output:
1452
(The number is your actual bash PID)
Find PIDs of Multi-Process Applications
pidof firefox
WHAT this does: Returns all PIDs for Firefox, which runs multiple processes.
WHY this matters: Modern applications use process isolation for security and stability. Firefox creates separate processes for the browser, GPU, network, and tabs. pidof shows all of them.
Expected output:
2847 2848 2849 2850 2851
Expert note: This space-separated output works great with command substitution but requires the -s flag for single-PID scripts.
Search for Multiple Process Names in One Command
pidof nginx apache2
WHAT this does: Finds PIDs for both nginx and apache2 in a single execution.
WHY you need this: Efficiency. Instead of running pidof twice, you get both results together. This is useful when checking if multiple services are running.
Expected output (if both run):
554 553 552 1890 1891
(The first three are nginx workers, the last two are apache processes)
Verify a Process Is Not Running
pidof squid
WHAT this does: Attempts to find the squid process.
WHY you need this: When a process is not running, pidof produces no output and returns exit code 1. This is how you confirm a service is stopped.
Expected output (when squid not running):
(no output)
Check exit status:
pidof squid; echo "Exit code: $?"
Output:
Exit code: 1
WHY exit codes matter: Exit code 0 means success (PID found), exit code 1 means failure (no PID). Scripts use this for logic decisions.
Step 4: Apply Advanced pidof Options for Complex Scenarios
Change PID Separator for CSV or Script Output
pidof -d ',' firefox
WHAT this does: Uses a comma instead of space to separate multiple PIDs.
WHY you need this: Default space separators break CSV parsing and some scripting contexts. Commas work better for data pipelines, database imports, and log aggregation.
Space separator output (default):
2847 2848 2849
Comma separator output:
2847,2848,2849
Expert tip: Use -d '|' for pipe-separated output when working with awk or sed.
Omit a Specific PID from Results
pidof -o 8148 nginx
WHAT this does: Finds all nginx PIDs except 8148.
WHY you need this: Sometimes you need to exclude a known safe instance while targeting other processes. You can also use %PPID to omit the parent shell.
Real scenario: You have two nginx master processes. One is healthy (PID 8148), the other is hung. You want to kill only the hung one.
Include Zombie Processes in Search
pidof -z firefox
WHAT this does: Detects and returns PIDs of zombie processes.
WHY you need this: Zombie processes complete execution but remain in the process table. pidof skips them by default. The -z flag explicitly includes them, which is critical for debugging process cleanup issues.
Warning: This option may cause pidof to hang on some systems with many zombies.
WHY zombies happen: A child process finishes but its parent hasn’t called wait() to read its exit status. The zombie stays until the parent exits or calls wait.
Skip NFS stat() Calls to Prevent Hangs
pidof -n apache2
WHAT this does: Skips stat() calls when checking if binaries are on network filesystems.
WHY you need this: Network filesystems (NFS) cause pidof to hang during stat() calls. The -n option prevents this by skipping the check. Alternatively, set the PIDOF_NETFS environment variable.
Without -n on NFS:
(pidof hangs for 30+ seconds)
With -n on NFS:
1890 1891 1892
(Returns immediately)
Find PIDs in the Same Root Directory (Root Only)
sudo pidof -c firefox
WHAT this does: Shows PIDs of processes sharing the same root directory.
WHY you need this: Only root can check root directories of processes owned by other users. This is essential for container and chroot environment debugging.
Real use case: You run multiple containers with separate root directories. You need to find which processes belong to the same container. The -c flag groups processes by root directory.
Expected output:
2847 2848 2849
(All three firefox processes share the same container root)
Step 5: Kill Unresponsive Processes Using pidof and kill
Kill a Single Process with pidof One-Liner
pidof firefox
sudo kill -9 $(pidof firefox)
WHAT these commands do: First finds the Firefox PID, then passes it to kill -9 for forced termination.
WHY this pattern works: Command substitution $(...) captures pidof’s output and feeds it directly to kill. This creates a clean one-liner: kill -9 $(pidof process_name).
WHY -9 matters: The -9 flag sends SIGKILL, which forces immediate termination. Processes cannot ignore SIGKILL. Use this when a process ignores softer signals like SIGTERM.
Expected output (after kill):
(no output from kill)
Verify process is killed:
pidof firefox
Output:
(no output - process stopped)
Kill Multiple Process Instances Simultaneously
pidof nginx
554 553 552
sudo kill -9 $(pidof nginx)
WHAT this does: pidof returns all nginx worker PIDs space-separated. kill accepts multiple PIDs, so all workers terminate in one command.
WHY this matters: Services like nginx run multiple worker processes. Killing only one leaves the service partially running. This pattern kills all instances at once.
Real scenario: nginx workers are hung due to a memory leak. You need to restart the entire service. Killing all workers prepares for systemctl restart nginx.
After killing workers:
sudo systemctl start nginx
Kill Process Gracefully Before Using SIGKILL
sudo kill -SIGTERM $(pidof -s nginx)
WHAT this does: Sends SIGTERM (signal 15) instead of SIGKILL to the first nginx PID.
WHY prefer SIGTERM: SIGTERM allows processes to clean up resources before stopping. SIGKILL forces immediate termination without cleanup. Use SIGTERM first, then SIGKILL if the process ignores it.
Graceful termination sequence:
# Step 1: Try soft termination
sudo kill -SIGTERM $(pidof nginx)
# Step 2: Wait 5 seconds
sleep 5
# Step 3: Force kill if still running
pidof -q nginx && sudo kill -SIGKILL $(pidof nginx)
WHY this sequence works: Most processes handle SIGTERM properly. Only use SIGKILL as a fallback when soft termination fails.
Kill Script Processes with the -x Option
pidof -x backup.sh
sudo kill -9 $(pidof -x backup.sh)
WHAT this does: Finds the bash process running backup.sh, then kills it.
WHY you need -x: Regular pidof backup.sh returns nothing because scripts run inside shells. The -x flag includes shell processes running named scripts.
Real scenario: Your backup script is stuck in an infinite loop. You need to stop it, but standard pidof fails. Adding -x finds the correct PID.
Step 6: Build Production Monitoring Scripts with pidof
Create a Service Health Check Script
#!/bin/bash
# Service monitoring script using pidof
SERVICE_NAME="nginx"
if pidof -q $SERVICE_NAME; then
echo "✓ $SERVICE_NAME is running"
exit 0
else
echo "✗ $SERVICE_NAME is NOT running"
echo "Attempting to start $SERVICE_NAME..."
sudo systemctl start $SERVICE_NAME
# Verify restart succeeded
if pidof -q $SERVICE_NAME; then
echo "✓ $SERVICE_NAME restarted successfully"
exit 0
else
echo "✗ Failed to start $SERVICE_NAME"
exit 1
fi
fi
WHAT this script does: Checks if nginx runs, starts it if missing, and verifies the restart succeeded.
WHY this pattern is production-ready:
- Uses
-qfor quiet boolean checks - Includes automatic service recovery
- Verifies restart success before exiting
- Returns proper exit codes (0 for success, 1 for failure)
How to use it:
# Save as /usr/local/bin/service-monitor.sh
sudo nano /usr/local/bin/service-monitor.sh
# Make executable
sudo chmod +x /usr/local/bin/service-monitor.sh
# Run it
/usr/local/bin/service-monitor.sh
Expected output (when nginx runs):
✓ nginx is running
Expected output (when nginx stopped):
✗ nginx is NOT running
Attempting to start nginx...
✓ nginx restarted successfully
Create a Process Cleanup Script for Hanging Applications
#!/bin/bash
# Cleanup script for hanging GUI applications
APP_NAME="amarokapp"
PIDS=$(pidof -d ',' $APP_NAME)
if [ -n "$PIDS" ]; then
echo "Found $APP_NAME processes: $PIDS"
kill -9 $PIDS
echo "Killed $APP_NAME processes"
# Verify cleanup
if pidof -q $APP_NAME; then
echo "WARNING: $APP_NAME still running after kill"
else
echo "✓ $APP_NAME completely removed"
fi
else
echo "✓ $APP_NAME is not running"
fi
WHAT this script does: Finds all amarokapp processes using comma-separated output, kills them, and verifies cleanup.
WHY comma separator helps: Storing PIDs in a variable with comma separation prevents word-splitting issues that spaces cause.
Real use case: GUI applications like amarokapp sometimes hang and don’t respond to the normal close button. This script forcefully terminates them.
Add pidof Checks to CI/CD Pipeline Pre-Deployment
#!/bin/bash
# CI/CD pre-deployment check
echo "=== Pre-deployment Service Checks ==="
# Check Docker
if pidof -q docker; then
echo "✓ Docker service ready"
else
echo "✗ Docker not running - aborting deployment"
exit 1
fi
# Check nginx
if pidof -q nginx; then
echo "✓ nginx service ready"
else
echo "✗ nginx not running - aborting deployment"
exit 1
fi
echo "=== All checks passed ==="
exit 0
WHAT this script does: Verifies Docker and nginx run before allowing deployment to proceed.
WHY this protects production: CI/CD pipelines need clear pass/fail signals. If a required service is down, exit 1 stops the pipeline and prevents broken deployments.
Expected output (all services running):
=== Pre-deployment Service Checks ===
✓ Docker service ready
✓ nginx service ready
=== All checks passed ===
Expected output (Docker down):
=== Pre-deployment Service Checks ===
✗ Docker not running - aborting deployment
Troubleshooting Common pidof Errors
Error 1: pidof Returns No Output When Process Is Running
Problem: You run pidof squid but get no output, even though squid is running.
Root cause: The process name doesn’t match the exact executable name. Squid daemon might be called squid-server instead of squid.
Solution: Find the exact process name using ps:
ps -ef | grep squid
/usr/bin/squid-server -d
Correct command:
pidof squid-server
WHY this works: pidof matches exact process names only. It does not support pattern matching like pgrep.
Error 2: pidof Command Not Found
Problem: You get bash: pidof: command not found when running the command.
Root cause: The procps-ng or sysvinit-utils package is not installed on your system.
Solution for Fedora/RHEL:
sudo dnf install procps-ng -y
Solution for Ubuntu/Debian:
sudo apt install sysvinit-utils -y
Verify installation:
pidof --version
WHY this happens: Minimal Linux installations often exclude process management tools. You must install them manually.
Error 3: Multiple PIDs Confuse Your Script
Problem: Your script expects one PID but gets multiple space-separated PIDs, causing errors.
Root cause: Modern applications run multiple processes (Firefox, nginx), and pidof returns all of them.
Solution 1: Use single-shot mode:
PID=$(pidof -s firefox)
Solution 2: Handle all PIDs properly:
PIDS=$(pidof firefox)
kill -9 $PIDS
WHY this matters: Command substitution captures all PIDs, and kill accepts multiple arguments. The problem only occurs when you try to assign to a single variable without -s.
Error 4: pidof Hangs on Network Filesystem Binaries
Problem: pidof takes 30+ seconds to return when checking processes with binaries on NFS.
Root cause: pidof runs stat() calls on binary paths, which hang on network filesystems.
Solution 1: Use the -n option:
pidof -n apache2
Solution 2: Set environment variable:
export PIDOF_NETFS=1
pidof apache2
WHY this works: Both approaches skip stat() calls for network filesystem binaries, preventing the hang.
Error 5: -c Option Returns Permission Denied
Problem: Running pidof -c firefox returns “permission denied” even though you’re logged in.
Root cause: The -c option checks root directories of processes, which requires root access for processes owned by other users.
Solution: Add sudo:
sudo pidof -c firefox
WHY this happens: Linux security prevents users from inspecting other users’ process root directories. sudo bypasses this restriction.
Error 6: Docker Container PIDs Not Found
Problem: You run pidof nginx from inside a Docker container but get no output, even though nginx runs inside the container.
Root cause: pidof searches the process table of the current namespace. Inside containers, you only see processes in that container’s namespace, not the host system.
Solution: Run pidof from inside the container where the process runs:
docker exec my-container pidof nginx
WHY this works: docker exec runs the command inside the container’s namespace, where pidof can see the container’s nginx process.
Error 7: pidof Finds Host Process Instead of Container Process
Problem: Running pidof postgres on the Docker host returns the host’s postgres PID, not the container’s postgres PID.
Root cause: When running pidof on the host, it sees all processes in the host namespace, including container processes (which appear as regular processes on Docker host).
Solution 1: Use container-specific query:
docker inspect --format='{{.State.Pid}}' my-postgres-container
Solution 2: Run pidof inside container:
docker exec my-postgres-container pidof postgres
WHY this matters: Container processes have different namespaces. You need container-specific tools for accurate PID lookup.
Error 8: Script Fails with Multiple SSH Sessions
Problem: Your monitoring script kills the wrong bash process when multiple SSH sessions are active.
Root cause: pidof bash returns all bash PIDs, including your monitoring script’s own bash session.
Solution: Use -o %PPID to exclude the parent shell:
pidof -o %PPID bash
WHY this works: %PPID automatically excludes the parent process ID, preventing self-termination in scripts.
Error 9: pidof Returns Wrong PID for Systemd Services
Problem: pidof nginx returns the systemd service manager PID, not the actual nginx worker PID.
Root cause: Some systemd services run under a manager process that shares the service name in certain contexts.
Solution: Use systemctl for service-specific PID:
systemctl show nginx --property=MainPID
WHY this is better: systemctl knows the exact service structure and returns the correct worker PID, not the manager.
Error 10: Zombie Processes Cause pidof to Hang
Problem: Using pidof -z causes pidof to hang indefinitely when many zombie processes exist.
Root cause: The -z option requires additional system calls to check zombie status, which can block on systems with process table issues.
Solution 1: Avoid -z unless necessary:
Zombie processes are rare. Use -z only when debugging specific process cleanup issues.
Solution 2: Use timeout wrapper:
timeout 5 pidof -z firefox
WHY this works: timeout prevents indefinite hangs by killing pidof after 5 seconds if it doesn’t complete.