Web Exploitation - Day 2¶
Demo
How to access Demo Ranges
CREDS: demo1 :: password
Open web browser (FIREFOX preferred) and set up proxy settings
Navigate to 10.208.50.61
OR
Navigate to 127.0.0.1:2222
Outcome:
Student will be able to:
- Describe what SQL is
- Explain how SQL injection can be used to exploit a database
- Perform basic SQL injection, to exploit a database
Understanding SQL¶
Log into any website, think about the processes and technologies that are being used to accomplish this login
- Identify the Client-Server relationship of the login process
- Specify that a user must input information into the HTML form (client-side) which is then sent to the server script that holds the Database (DB)
- Imagine the script checks the DB to determine if the login information is valid; if true then access is granted
Databases are used by companies to track/control inventories, product pricing, username/passwords, and most other types of data.
Discuss: As a group, discuss how compromised databases are a concern and how an attacker could accomplish their goals using SQL
What is SQL?¶
**S**tructured **Q**uery **L**anguage, which is the standard language utilized to interact with Relational Database Management Systems (RDMS)
Various vendors have their own additional proprietary extensions for their specific versions, which led to differences between vendors that may need to be researched, once the DB type is known. This means if you are interacting with an Microsoft SQL (MsSQL), SQLite, etc. DB, then you will likely need to adjust syntax as required.
Commands, such as below, are standardized across vendors, and can accomplish almost all tasks inside a Database:
Relational Databases
Most current SQL databases are relational, data is organized based off logical relationships and can be accessed or reassembled in different way without the need to reorganize the data.
Databases are broken up into Tables. These tables contain Columns/Fields and Rows which contain the Data/Records. Each Table has a unique primary key and relationship between tables can be built with the use of adding a foreign key, which links to the primary key of another table.
Basic SQL Commands
Command | Usage |
---|---|
USE |
Select the database to use** |
SELECT |
Extract data from a database |
UPDATE |
Update data in a database |
DELETE |
Delete data from a database |
INSERT INTO |
Insert new data into a database |
CREATE DATABASE |
Create a new database |
ALTER DATABASE |
Modify an existing database |
CREATE TABLE |
Create a new table |
ALTER TABLE |
Modify an existing table |
DROP TABLE |
Delete a table |
CREATE INDEX |
Create an index (search key) |
DROP INDEX |
Delete an index |
UNION |
Combine the result-set of two or more equal SELECT statements** |
**Commands that will be most useful for the injections in this lesson
Resource:
DEMO: SQL Commands (SQL Demo Box)¶
Note
;
terminates the command, sending it to the DB for execution.
PRACTICE: SQLBolt¶
SQLBolt.com¶
Tutorial part of lesson, so students may gain experience on interacting with a SQL Database. Students will work on Interactive Tutorials 1-11 and 13
SQL Injection¶
Overview
SQL injection is the use of Valid SQL Queries, via input data fields or attaching of queries to the end of URLs, from the client-side to a server-side application. This allows data to be read or modified. You could have a fully patched **L**inux **A**pache **M**ySQL **P**HP (LAMP) stack, yet still have a vulnerable webapp, because it was configured incorrectly, hence vulnerable to SQL injection, which relies on unsanitized input fields.
Sanitized vs Un-Sanitized Input Fields
Sanitized fields mean that user input or data is checked for items that might harm the database. For client-side this means that pieces of the data are modified by removal, escaping, or conversion to a string.
Validation, on the other hand, checks inputs to ensure that they meet a criteria, such as the string not containing a single quote. An example might be an email address input field. Instead of trying to remove known bad data, it may be better to remove all but known good data. This distinction is crucial, as an email address should only contain the following characters:
DEMO: SQL Injection (SQL Demo Box)¶
Note
It is very important to understand that Injection can be performed through various HTTP Request Methods (i.e. POST
, GET
) because either or both of these could be configured on the server to take input from a user.
Truth Statements
Perform the following Commands from the CLI:
Discuss
- Why this one is effective?
- Can only use
1=1
? - What are the differences between
INTEGER
andSTRING
values?
Understand
This works because the OR clause 1=1
is true, so the database will return all entries housed in id
field
Perform the following from the web:
- Navigate to you SQL Demo Box
http://10.50.XX.XX
- Examine
http://10.50.XX.XX/index.html
Students should identify the following in index.html
:
On the login page enter the following in both the username and password field:
- Examine the Developer Console and find the Request Header under the Network tab
- What Type of HTTP Request was performed, and can we try a different one?
POST
was utilized (Students should identify the parameters passed in the Request)
Navigate to the login.php
page. Are there any errors?
Now send a GET request while populating the items causing the error:
Discuss
- Why did our inject work with the GET Request?
- Why did our GET request SQL injection successfully dump the database?
- Examine the Developer Console and view the Request Header under the Network tab.
- What Type of HTTP Request was performed?
Unfortunately only our results are shown, NOT the PHP code (This is due to the PHP code being executed on the server-side)
The following code is the contents of /var/www/html/login.php
on the SQL Demo Server server. Look at the differences in how POST and GET are handled by the code.
Methods to find an unsanitized field:
'
(single quote) may return extraneous information if the field isn't sanitized- We are trying to end the string and attach additional variables, or clauses, to the back-end SQL query
- If
'
(single qoute) displays no error messages or generic errors than field is likely sanitized.
Stacking Statements
Imagine an attacker were to input Tom; DROP TABLE Customers
Tip
Not all applications utilizing SQL Databases allow for query stacking. For example: PHP and MYSQL or Java and ORACLE do not support stacking.
DEMO: SQL Injection - Nesting Statements (SQL Demo Box)¶
Perform the following Commands from the CLI:
The above query pulls data from two tables, combining Ford vehicles and Goodyear tires
Adding an additional nested statement, would be the following:
Perform the following using http://10.50.XX.XX/Union.html
(SQL Demo Box):
Note
UNION SELECT
demo will show the steps of how to go from determining an injectable area, to grabbing the DB schema. Demo app has separate POST and GET input functions, to show case both needing to use '
and not needing to use '
- Validate Normal Functionality
- What are the expected results?
- Test our Truth Statement
POST
Method through Cars input field:
GET
Method through Tires Selection field
Change the Selection Number to (1 - 4) to show the process of testing for URL injection Injectable Syntax:
Nesting a Query:
Comment Syntax:
#
- Anything after a pound sign will be ignored--
- This is two dashes and a trailing space. Anything after this will be ignored (INCLUDING syntax appended by the backend script/app)
This syntax will be utilized with more complex backend queries, that leverage advanced functions, or where only certain areas within the query are susceptible to injection.
More complex query (Where the injectable variable is in the middle of nested query):
We use the )
(close parenthensis) to close part of the nested query. We than need to make the query TRUE in order to inject our UNION
with a terminator, to then properly execute our modified query. We finally add the #
(pound sign) to comment out the rest of the legitimately configured query (that is embeded in the server-side PHP code).
Note
This is a little more advanced and requires us know exactly how the legitimate query is configured, so that we craft our precise inject.
As an example, you might have a page that asks for both a username
and password
.
Inject the following in the username input field:
The resulting query, being executed by the server, would look like this:
DEMO: SQL Injection - Database Enumeration (SQL Demo Box)¶
The backend PHP code utilized will dictate both what query is executed, as well as how the resulting data from the database is displayed to the user. Enumeration of the database is key to determinining what information will create a valid SQL query.
Key Items To Identify:
- Database Structure
- Databases
- Tables
- Coulumns
Other Helpful Information:
- Database Version
- Data within the Databases
Blind SQL injection:
Occurs when an attacker sends TRUE/FALSE statements to determine how the database is configured.
The above syntax inserts a SQL query at the end of URL query string (GET), OR input field (POST) to determine schema (structure) of the table, by incrementing by one more field (5,6,7,etc.) until results, or an error, are displayed. This provides an attacker more information about how may fields are configured in the query.
GET
Method (URL)
Line 4 shows a "Golden" statement, it's called this because of the value of the data it should return.
POST
Method (Form Input):
- Change the column name to a different spot, in order to see how you can manipulate the output from the SQL query.
Tip
&
(ampersand) in a URL basically means adding/attaching more variables/queries in the URL. It has special meaning in URI/URL strings. AND
, on the otherhand, will be interpreted as a combined query, not two GET variables.
SQL Injection Defense¶
To defend application side, input fields must be sanitized/validated. This means that they concatenate all statements into a single string, or escape certain characters.
A basic PHP example is utilizing the function mysql_real_escape_string
which replaces '
with a safely escaped \'
(single quote).
A SQL example is to use prepared statements such as SQLite's sqlite3_prepare()
which takes what is entered, then looks for a literal match (aka concatenation).
A single concatenated string will prevent injections such as 1 OR 1=1
modifying a scripted SQL query.