Software has a variety of different vulnerabilities with a range of potential impacts on the organization. Exploitation of a vulnerable application can lead to a data breach, malware infection, denial of service (DoS) attack, and other disastrous attacks. Code injection vulnerabilities are especially dangerous to an organization because they can be used by a hacker to execute all of these attacks and more.
A code injection can be used to execute, or “inject,” malicious code into a system hosting a vulnerable application. This provides the attacker with initial access to an organization’s environment and the potential to expand this foothold and their privileges to achieve a range of different malicious goals.
What is a code injection attack?
Injection attacks take advantage of the fact that many types of applications use user-provided input when building commands. For example, when authenticating a user in a password-based authentication system, a username may be included in an SQL query to look up the corresponding password.
Injection attacks use deliberately malformed inputs to cause user-provided data to be interpreted as code. This is accomplished by terminating the data section within the input.
For example, consider the SQL query SELECT * FROM customers WHERE username = ‘<username>’. If a user provides the username a’ OR ‘1’=’1, this becomes SELECT * FROM customers WHERE username = ‘a’ OR ‘1’=’1’.
This changes the command executed, and, since ‘1’ always equals ‘1’, this will return all records in the database.
Code injection attacks come in a variety of different forms. Some of the common types of code injection attacks include:
- SQL Injection: As demonstrated above, malicious inputs can change the interpretation of an SQL command. This can be used to access other records, modify the database, or take other actions.
- Cross-Site Scripting (XSS): XSS attacks take advantage of the fact that executable scripts can be included in HTML files. Websites that embed user-provided data within a webpage can be exploited to run malicious scripts within a user’s browser.
- Command Injection: Some applications are designed to include user-provided data within commands executed in the shell of the computer running the program. Attacker-provided data can modify the command run or terminate it and run shell commands selected by the attacker.
- File Injection: An application may accept and process a user-provided or user-selected file. Exploitation of vulnerable code may allow an attacker to execute code embedded within a user-provided file.
- Deserialization: Some applications will serialize multiple variables into a single string to simplify transmission. Malicious user input may be designed to exploit vulnerabilities in the deserialization code or to have user-provided data interpreted as part of one of the other fields within the data (which may influence code execution).
- Software supply chain attacks: Software supply chain attacks like NotPetya demonstrated the extreme harm a malicious code injection can cause. To execute a software supply chain attack, hackers gain access to a compromised network and then are able to inject malware into the software that lets attackers gain access to resources.
How to prevent malicious code injection attacks
Code injection attacks pose a significant threat to enterprise cybersecurity because they allow an attacker to execute malware and gain complete access and control over a vulnerable machine. Protecting against code injection vulnerabilities is an essential part of an organization’s DevSecOps strategy and should include the following best practices:
- Sanitize user input: Injection vulnerabilities are made possible by a failure to validate user input before processing it, enabling malformed or otherwise invalid inputs to affect an application’s control flow. Before processing user-provided data, an application should test that it is valid and fulfills any assumptions made by the application (length, acceptable characters, etc.).
- Shift security left: Security is often addressed towards the end of the software development lifecycle in the testing phase, leaving little time for in-depth testing and to correct any issues before release. Applications should be designed to include input validation and should be tested for injection and other vulnerabilities earlier in the development process to minimize the cost and impact of fixing vulnerable code.
- Control repo access: Injection and other vulnerabilities can be included in an application unintentionally by developers or intentionally by attackers with access to the development environment. Controlling access to code repositories by only allowing commits by validated corporate identities helps to protect against attackers attempting to insert vulnerabilities into code for later exploitation.
Secure your code with Beyond Identity Secure DevOps
Code injection vulnerabilities are a common and significant threat to application security. A code injection vulnerability can allow an attacker to execute arbitrary code within an application, allowing them to steal data, install malware, or take over control over the computer hosting the vulnerable application.
Code injection vulnerabilities are enabled by poor input validation. Building test cases for input validation and integrating vulnerability scanning into automated DevOps pipelines can help to detect these vulnerabilities early in the development process when they are relatively easy and inexpensive to remediate.
However, some cybercriminals don’t wait for developers to make mistakes, opting to insert malicious or vulnerable code into an application themselves for use in software supply chain attacks. To learn more about protecting against these supply chain exploits, check out Beyond Identity’s Secure DevOps.