flawopen.com/Command Injection/Java
Imagine a smart home speaker. Safe execution is pressing the preset button. Command injection is when someone shouts into the microphone 'Play music AND unlock front door', and the speaker executes both commands.
In Java applications, command injection typically occurs when developers call Runtime.getRuntime().exec(queryString) or construct a shell call (sh -c or cmd.exe /c) with concatenated request parameters.
Enterprise Java systems, including Jenkins, Apache Struts, and Spring Cloud Gateway, have suffered severe critical CVEs enabling unauthorized remote shell access across enterprise intranets.
CVE-2022-22947 & NIST National Vulnerability Database.// Runtime.exec with string concatenation
public class PingService {
public void ping(String host) throws Exception {
// Attacker input: "127.0.0.1; whoami"
String command = "sh -c ping -c 1 " + host;
Process process = Runtime.getRuntime().exec(command);
}
}
// ProcessBuilder with discrete argument list
public class PingService {
public void ping(String host) throws Exception {
// host is strictly isolated as an argument
List command = List.of("ping", "-c", "1", host);
ProcessBuilder pb = new ProcessBuilder(command);
Process process = pb.start();
}
}
ProcessBuilder passes the command and arguments as a distinct array directly to the underlying OS API (CreateProcessW on Windows or execve on Linux), bypassing shell command parsers completely.
Java tokenizes by spaces, meaning arguments containing spaces cannot be passed reliably without breaking quotes, leading developers to wrap commands in sh -c.
SecurityManager has been deprecated for removal since Java 17. ProcessBuilder and OS containment are the true security controls.
grep -rn "Runtime.getRuntime().exec(" --include="*.java" .
ProcessBuilder(List<String>)sh -c or cmd.exe /c with concatenated inputYes from shell injection. However, you must still ensure the program being executed does not interpret user arguments as unintended option flags.