Manual Code Execution
Depending on the underlying database system we are targeting,
we need to adapt our strategy to obtain code execution.
In Microsoft SQL Server,
the xp_cmdshell function takes a string
and passes it to a command shell for execution.
The function returns any output as rows of text.
xp_cmdshell is disabled by default and, once enabled,
it must be called with the EXECUTE keyword instead of SELECT.
In our database,
the Administrator user already has the appropriate permissions.
Let’s enable xp_cmdshell by simulating a SQL injection.
After logging in from our Kali VM to the MSSQL instance,
we can enable show advanced options by setting its value to 1,
then applying the changes to the running configuration
via the RECONFIGURE statement.
Next, we’ll enable xp_cmdshell
and apply the configuration again using RECONFIGURE.
With this feature enabled,
we can execute any Windows shell command
through the EXECUTE statement followed by the feature name.
Since we have full control over the system,
we can now easily upgrade our SQL shell
to a more standard reverse shell.
Although the various MySQL database variants
don’t offer a single function to escalate to RCE,
we can abuse the SELECT INTO_OUTFILE statement
write files on the web server.
For this attack to work,
the file location must be writable to the OS user running the database software.
As an example,
let’s resume the UNION payload
on our MySQL target application we explored previously,
expanding the query that writes a webshell on disk.
We’ll issue the UNION SELECT SQL keywords to include a single PHP line,
into the first column
and save it as webshell.php in a writable web folder.
The written PHP code file results in the following:
The PHP system function will parse any statement included in the cmd parameter
coming from the client HTTP REQUEST,
thus acting like a web-interactive command shell.
If we try to use the payload inside the Lookup field of the search.php endpoint,
we receive an error.
Fortunately, this error is related to the incorrect return type,
and should not impact writing the webshell on disk.
To confirm,
we can access the newly created webshell inside the tmp folder
along with the id command.
Great!
The webshell is working as expected,
since the output of the id command is returned to us through the web browser.
We discovered that we are executing commands as the www-data user,
an identity commonly associated with web servers on Linux systems.
Now that we understand how to leverage SQLi to manually obtain command execution,
let’s discover how to automate the process with specific tools.