Command Injection: How it Works and 5 Ways to Protect Yourself

Admir Dizdar
Share on facebook
Share on twitter
Share on linkedin

What is Command Injection?

A command injection involves the exploitation of a vulnerable application for the purpose of executing arbitrary commands on its host operating system. These exploits usually target the privileges of a vulnerable application. 

Typically, it is insufficient input validation that enables actors to exploit the application. When the application passess insecure user-supplied data, such as cookies, forms, or HTTP headers to the system shell, actors can execute malicious commands. 

While code injection and command injection may seem like the same attack, the two differ significantly. Code injection attacks enable actors to add malicious code to the application, which then executes it. Command injection extends the default functionality of an application, tricking it into executing system commands.

In this article:

How Does a Command Injection Attack Work?

Step 1 

During this stage, threat actors locate a vulnerability in an application which allows them to run malicious operating system commands.

Step 2 

The attacker engineers a command which will cause the application to execute a desired action in the host operating system. They typically use an input mechanism like HTML code, cookies or form fields to inject this command into the application.

Step 3 

The browser interprets the command and it is translated to an operating system command on the host. Threat actors can then execute specific commands on the host machine and the network of the infected system.

Command Injection Example

This example is based on code provided by OWASP. Consider the following C code that prints the contents of a file to the console. It is based on the UNIX command cat.

The problem with this code is that it does not validate the input parameter argv. A user can, for example, invoke this code with the following input:

$ ./catWrapper "Story.txt; ls"

The output will display the content of the Story.txt file as expected, but will continue to interpret the rest of the input parameter. The ; character indicates a break, and the text after it is evaluated as a new command. In this case, the ls command will be executed and the program prints the content of the current directory.

The attacker can substitute ls with a string of commands that can perform malicious actions on the host machine. If the catWrapper application is allowed to run with root privileges, for example, this would allow the attacker to take complete control over the host.

Command Injection Vulnerabilities

Below are common vulnerabilities, which can potentially expose an application to command injection attacks.

Arbitrary Command Injection

Applications can receive arbitrary system commands directly from end users. Once the application receives the commands, it executes them on the host. This is a common vulnerability that allows command injections.

Arbitrary File Uploads

Applications may allow end users to upload files containing arbitrary file extensions. This vulnerability can allow actors to inject commands once the uploaded files are added to the webroot.  

Server-side Template Injection

Web applications sometimes use server-side templating tools, like Twig or Jinja2, when generating dynamic HTML responses. A server-side template injection (SSTI) vulnerability occurs when user input is insecurely embedded within a template in a manner that allows threat actors to remotely execute code on the server.

XML External Entity Injection

XML external entity (XXE) vulnerabilities occur in applications that use weakly configured XML parsers to parse user-controlled XML input. XXE vulnerabilities can allow threat actors to read arbitrary files from the server and cause Denial of Service (DoS) attacks. 

5 Ways to Prevent Command Injection

Here are several methods you can employ to prevent command injection attacks:

1. Don’t Run System Commands with User-Supplied Input

If you do need to use user-input for a system command, do not call operating system commands directly. Instead, you can use built-in library functions. 

For example, if you are using the Python os library, do not use this command, which directly calls an operating system command: 

os.system(“listdir <directory-path>”)

Instead, use this command, which uses a library function:

os.listdir(“<directory-path>”)

This protects the integrity of existing system files that are included, executed, or parsed by your code. 

2. Use Strong Input Validation for Input Passed into Commands 

You can achieve this by using a whitelist for strings or allowed characters. To enable users to execute arbitrary commands, for example, you can whitelist certain commands, like ls and pwd, to allow only these input strings.

Alternatively, you can whitelist only allowed characters. For example, the regular expression ^[a-z0–9]{1,10}$ allows only numbers and lowercase letters and numbers. It does not allow special characters at all, because actors can use them to manipulate the logic of the command. This expression also limits the length of the input string 10 characters.

You can also escape values that are inserted into operating system commands. Here are several dangerous characters you should escape:

& | ; $ > < ` \ !

However, this method is often less effective, because threat actors constantly come up with inventive techniques to bypass input validation based on whitelists or blacklists.

3. Use the Principle of Least Privilege

This method strives to provide applications and processes with only the minimum privileges they need for their tasks. The goal is to lower the risk and damage of successful attacks. This way, if threat actors manage to inject commands, they are restricted to the privileges allowed to the application or process. 

4. Update and Patch Applications Often

Make sure you stay up-to-date with patches and updates. This can help keep applications and systems secure and prevent dependencies from introducing command injection vulnerabilities. Additionally, you can use a web application firewall (WAF), which can block suspicious traffic that may include attempted command injection.

5. Test Your Application with Neuralegion Nexploit

One of the simplest and most effective ways to prevent command injections is to scan your application with a dynamic application security testing (DAST) tool like Neuralegion’s Nexploit. 

Our black-box security testing solution automatically examines your application for OS command injection vulnerabilities. If one is detected, Nexploit provides remediation guidelines for your developers or SecOps team. No need for lengthy, cumbersome manual testing. 

Learn more about Nexploit and get started free!

Secure your app with every build

Sign up for a FREE NeuraLegion account.
Share on facebook
Share on twitter
Share on linkedin
Related Articles

Put and end to Command Injection Vulnerabilities. Run a security scan with every build

  • Easily and quickly find & fix security bugs

  • Automate it in your build pipeline

  • No false positives

  • Scan any target: web apps & APIs