3. Improper Neutralization of Special Elements used in a SQL Command
The vulnerability consists of an attacker interfering with the SQL queries an application make to the database. The web application does not neutralize or incorrectly neutralizes special elements that could modify the inteneded SQL command that is sent to the database. This attack is also known as SQL Injection.
Below is a diagram that illustrates the attack.
SQL Injection in python
Let's look at an example for a Flask web application that has the following code for logging users to the web application. The web application has a form that accepts a username and a password and sends the data to the /login endpoint.
Here is the python code of the vulnerable /login endpoint:
@app.route('/')
@app.route('/login',methods=['GET', 'POST'])
def login():
msg = ''
if request.method == 'POST' and 'username' in request.form and 'password' in request.form:
username=request.form['username']
password=request.form['password']
cursor= mysql.connection.cursor(MySQLdb.cursors.DictCursor)
cursor.execute("SELECT * FROM accounts WHERE username = '%s' AND password = '%s'" % (username,password))
account = cursor.fetchone()
if account:
session['loggedin']=True
session['id']=account['id']
session['username']=account['username']
if(session['username']=='admin'):
return render_template('admin.html')
else:
return redirect(url_for('account',name=session['username']))
#return render_template('index.html',msg='Logged in successfully!')
else:
msg = 'Incorrect username/password!'
return render_template('login.html',msg=msg)
In this example the web application has a login form that accepts a username and a password and if the user enters the correct login
information he application will authenticate the user and redirects them to their home page. This code is vulnerable to SQL injection and we can see in the code that the username and password are concatenated directly to the SQL query made to the database.
Exploitation
To exploit the SQL injection of this application, we will manipulate the username and password field to alter the SQL query going to the database. One exploitation scenario would be to perform a login bypass and login as the administrator. This can be performed by entering the following payload in the username field and any value to the password field:
Payload: admin'; --
#This payload alters the SQL query to the following SQL statement:
# SELECT * FROM accounts WHERE username = 'admin'; -- ' AND password = 'aaaaaa'
#The SQL statement portion after -- is commented out so the executed SQL statement will be:
# SELECT * FROM accounts WHERE username = 'admin';
This will can potentially allow the attacker to login as the administrator and potentially and perform a lot of damage to the web application. This is possible because the web application interprets user input as code that is part of the SQL statement.
Other Exploitation Techniques
The attacker could have altered the SQL statement in different ways to perform any of the following:
- Login as other users
- Delete database tables
- Exfiltrate user's sensitive information
Mitigation
- Use of prepared statements and parameterized queries. This allows to differentiate between SQL code and data. Data values are provided as parameters at execution time, rather than being directly concatenated into the SQL string.
- Input validation and escaping (partial mitigation)
- Use of stored procedures (partial mitigation)