Injection is an issue that arises quite often and in several forms, things like SQL databases for example might contain issues such as SQL injection and the same might go for things like LDAP, XML, OS commands,... . In other words, there is a range of different injection vulnerabilities that can occur and we will be discussing them in this article.
Threat agents/attack vectors
Wherever user input is taken into the application and passed on to a processor they have the possibility to add in malicious code. This means that we need to look further than the basic parameters alone and we need to look more in the direction of anything that is user controllable include environment variables, parameters, external and internal web services, import functionality and any other possibility for users to insert their own attack vectors.
This issue type often occurs when code has been left over from other projects or other developers and passed on the a fresh team. Often documentation is lacking and this can lead to the new developers not properly implementing security features. We also need to look in the direction of any processors that takes user input such as SQL, XPath, LDAP, SMTP headers and others. We need to make sure to not pass any unsanitized data to these processing engines. If we want to test for these issues we might find benefit in fuzzers and automated scanners but we should not rely on them solely.
The impact highly depends on the functionality of the application and what type of injection is being exploited. It can lead to data loss, unauthorised actions, data corruption and much more.
Often developers will rely on certain techniques to make their web applications less static. This can include things like CRUD actions in the database, Login actions via LDAP or OS commands. These are just a few examples of how a developer can make a web application less static and they all have the same possibilities for vulnerabilities in them which arise when user input is processed without sanitising it. This is when users with malicious intent can insert their own malicious input into these processes which can lead to extremely bad consequences such as SQL injection or even OS command injection leading to remote code execution.This is an issue type from the top 10 OWASP you do not want to miss!
Types of Injection
SQLi is a vulnerability type that arises when developers use things like SQL queries that get data to create their queries from the user's input. If the developer does not properly sanitise this input, they run the risk of the user injection code that will terminate the SQL query after which they can inject their own.
LDAP is a system that is often used in web applications to authenticate users but it comes with some deep pitfalls to which we need to build bridges or we could be allowing malicious actors to intercept our LDAP queries and modify them to inject their own LDAP statements. This problem is made worse by the fact that there is no one single great implementation of LDAP interfaces with easy and safe to use parameters.
At times we may need to generate XML input as a developer. This XML file can come in many different forms and does not have to be limited to pure XML files in an upload functionality. We can see this issue manifest in several different ways ranging from SOAP calls that contain user supplied input to XML files that will also use the user supplied input to generate the file. The attacker will attempt to input values that will disrupt the structure of the generated XML file and attempt to insert their own values.
OS command Injection
OS commands can sometimes be directly executed from the code they are running. While this is a useful feature, it does have its downsides and especially if user supplied input is used to run the command. This may lead to bad actors ending the command string and inserting their own. The impact of this is usually quite severe as it will lead to remote code execution.
Web applications can make the choice to store their data in XML files and just like SQL is used to search databases, we can use XPATH to search these XML files. If user input is supplied to the XPATH query and not sanitised properly it could lead to malicious actors injecting their own XPATH query. The impact of this could be sensitive information exposure or more technical issues such as login bypasses when login data is stored in XML files.
CRLF refers to Carriage Return Line Feed, which are two ways of terminating a line. Depending on the application and how it is set up, this could have serious consequences if the attacker is able to insert their own line feeds and subsequently maybe even code for the application to run. This could happen in the form of log injection or HTTP response splitting.
Email Header Injection
Our application might allow users to send email from within the functionality. This email needs some input such as an email address and content. If some of that input ends up in the headers of the email and is not sanitised properly, an attacker might be able to inject their own SMTP headers. Usually, this issue will be exploited by spammers who want to send phishing emails or perform malicious actions such as attach viruses to emails.
In some applications, user input might be passed on to the headers which could cause serious issues if the user input is not sanitised properly. Malicious actors could insert their own HTTP headers which could even lead to XSS attacks if the header is reflected onto the page.
How Injection Can Affect Business
The business impact of this vulnerability is hard to predict in advance and depends on what type of injection is exploited and the functionality that injection is found in. We can state that in general, injection vulnerabilities will have a decent impact however and could lead to data loss, remote code execution and authentication bypasses.
How to detect Injection Vulnerabilities
To detect injection vulnerabilities we have to fuzz user inputs and make sure that we fuzz even the hidden parameters as hackers will find them and abuse them. We need to make sure to fuzz every input that feeds into the following processes with the appropriate attack vectors and we must make sure to implement features in production such as a WAF or API security to protect from any of the missed vulnerabilities:
A query statements (This can be SQL but don’t neglect graphQL or noSQL or other query languages either)
Example attack scenario
An example we can think of is when developers write queries like this:
“Select * from users where username =’” . $_POST['user'] . “‘ and password = ‘“ . $_POST['password'] . “‘
If we do not sanitise the users input, they will be able to insert something like ‘; or 1=1-- into the password field which will terminate the query and always return true, this will allow the attacker to skip entering a password as the server will always return true anyway. This is an example of an SQL injection but there are many more things an attacker can do with this technique.
A second example we have seen a lot in real targets is when the application generates XML files based on the users input. A user can input their own XML with the following statements “<action>deleteUsersTable</action>” and when the XML file is processed by the server, the server might take this user supplied input and perform unwanted actions such as delete all users in our example.
Let’s also look at some examples of hacktivities on injections.I’ve chosen CVE-2021-32590 for this because of the high impact. In this vulnerability an attacker can inject any SQL code due to improper user input sanitization in multiple locations which shows us again how important it is to investigate all of the possible avenues of user input and sanitise it all.
I have also picked this “hacktivity” writeup that talks about regex injection. The reason I picked it is because of the high payout and the regex injection which is not something you hear about a lot. The payout for this bug was a whopping $4,500! The research was able to abuse this to cause things like changing the applications behavior and causing a DoS attack.
We have to create separate layers to store our data and to process our queries. Keeping these separate will ensure that we can sanitise all the data in the data layer before it enter any queries or processes if we can not avoid using that user supplied input.
As developers we can also move away from this model and move to tools such as Object Relational Mapping Tools (ORMs). This creates, in effect, a "virtual object database" which is separate from our real database, keeping it safer.
When validating the input data and sanitising it, it is good practice to rely on white listing but this might not always be possible.
After all of these mitigations, we might still run into dynamic queries that process user input. In this case we have to make sure to escape all the special characters our technology stack uses before sending off the data to the query.
If after all of this SQL injection still occurs, we should rely on the use of the LIMIT statement in SQL to try to ensure that attackers can not dump the database tables in one query.
Injection vulnerabilities are often overlooked due to their deceiving simplicity. It seems simple to “sanitise all user input that reaches dynamic queries or processes” but it’s not easy to define all the points where user data enters our applications’ flows. We have to make sure to test every parameter thoroughly before approving a feature according to OWASP A1: Injection and we have to fuzz with the proper attack vectors. This is a vulnerability type we need to protect from on the back-end side to increase our server and API protection.