SQL Injection
Forms are sometimes vulnerable to SQL injection
This happens because developers use unsafe queries like the following to log someone in:
select username from users where username = '[user input]' and password = '[user input]'We can exploit this by breaking their single quotes but submitting something in the username like:
admin' OR 1=1;-- -This turns their unsafe query into the following:
select username from users where username = 'admin' OR 1=1;-- - and password = 'whatever'This means: Select the username from users where the username is admin or 1=1 (in other words, true), and then comments out the rest of the statement. This will log us in to the first user that is returned
If we know a username and we want to log in as them, we can use a similar attack with the AND keyword:
admin' AND 1=1;-- -Thus making the query:
select username from users where username = 'admin' AND 1=1;-- - and password = 'whatever'This means: Select the username from users where the username is admin AND 1=1 (in other words, true), and then comments out the rest of the statement. This will log us in to the first user with the username of admin
Union
The union operator can be used to exfitrate data out of the database.
IMPORTANT: We can only select the same number of columns as the original query - and the data we are retrieving must be of the same TYPE, meaning we cannot select an int value from a string column and vice versa.
In order to find the number of columns, we can iterate using union:
No result, we send two nulls - no result, so we send three:
We get a result, so we now know the number of columns is 3. We can start filling the null values to see which fields are being output to the screen. Getting the version SQL is a good check:
Once we find out which columns are being output to the page, we can get more information:
We can get a lot of information this way about the database and the data we can gather
column_name from information_schema.columns
Other Inputs
Don't pass up opportunities to attempt sqli because it didn't work on one input. Think of other things as well, are we able to create users with a username containing sqli? A badly written query inside the application could use the username to run a query and in turn output data it didn't intend to display.
Blind
Sometimes our fields may not be directly injectable - however there may be other parts of the authorization process that are. For instance, if you are able to see the whole process (default creds, low privilege user, etc) and there is a cookie that is passed along to the page following the login, that cookie data may be injectable.
We can try changing the cookie and see if we get an error (we should), then we can try some injection techniques on it and see if we are still successful with the original cookie data with injection:
We have discovered a blind SQL injection - this is because the page output does not reflect any information for us, but we can see if our injection fails or succeeds. This means we need to use true/false statements to get our information.
Let's demonstrate this by getting the version:
We can use Intruder with Sniper for doing this one at a time, but the better option would be to use sqlmap I WAS NOT ABLE TO GET SQLMAP TO RUN THIS REQUEST AS A REQUEST FILE
Sqlmap
Sqlmap can do a lot of the heavy lifting for us, and can also test for sqli in applications. The simplest way is to grab a copy of the request to log in from BurpSuite or Caido, or something similar and save it to a file. For this example, that will be login.req
Testing for SQLi
Finding the Technique
There are various types of sql injection techniques - we've discovered a boolean-based blind injection, so we can specify a technique to search for it specifically :
Finding Boolean
Adding the technique will make this a bit faster as well as adding the level of aggressiveness. With a boolean injection, more aggressive is fine
Dumping data
Now that we've confirmed there's a boolean based blind injection, we can start dumping some data
Last updated