Обход WAF при помощи некорректных настроек прокси-сервера

Обход WAF при помощи некорректных настроек прокси-сервера

Автор: Red Timmy Security Staff

Привет, друзья! Как вы думаете, что общего между участием в конкурсе по отлову багов и устройствами сетевой безопасности? Обычно ничего. С другой стороны, устройства безопасности позволяют реализовать виртуальный патчинг и используются регулярно с целью снижения вознаграждения исследователям за найденные ошибки… однако дальше будет полностью противоположная история: мы получили премию, благодаря неправильно настроенному средству безопасности. Мы не будем раскрывать ни имя компании (кроме того, что организация входит в список Fortune 500), ни один из уязвимых компонентов. Мы лишь рассмотрим используемую технику вследствие чрезвычайной и обезоруживающей простоты.

Исследование цели

Все началось с изучения цели, которая на тот момент не рассматривалась как заслуживающая внимания. Предположим, что у целевой системы адрес

«https://targetdomain»
. Практически случайно мы заметили, что на поддомене, отвечающим за аутентификацию на сайте, были доступны некоторые CSS и Javascript ресурсы, имеющие отношение к Java-компоненту, который был хорошо известен как подверженный уязвимости, связанной с удаленным выполнением кода.

Странным был тот факт, что во время просмотра конечного узла (нечто вроде

«https://auth.targetdomain/vulnerable_endpoint?param=malicious_RCE_payload»
) мы получали ответ HTTP 404 от сервера, что заставило нас подозревать присутствие WAF (Web Application Firewall). Почему конкретно эта система могла выдавать ошибку при попытке доступа к ресурсам определенного рода (а конкретно - к файлам .css и .js)? Сразу же возникает гипотеза, что мы имеем дело с WAF. После еще нескольких заблокированных запросов было подтверждено присутствие правила в WAF, блокирующего доступ к целевой системе.

«Странная» вещь

Просматривая одно из приложений на хосте (допустим, https://targetdomain/appname/appname), мы попали на аутентификацию по адресу «https://auth.targetdomain». Во время аутентификации мы заметили еще одну странную вещь. В какой-то момент случилось перенаправление на адрес вроде https://targetdomain/?cfru=aHR0cHM6Ly90YXJnZXRkb21haW4vYXBwbmFtZQ==

Строка «aHR0cHM6Ly90YXJnZXRkb21haW4vYXBwbmFtZQ==» явно закодирована в base64. После декодирования эта полезная нагрузка оказалась ничем иным, как адресом «https://targetdomain/appname», к которому мы пытались получить доступ перед началом аутентификации.

Сразу же возник вопрос, что на самом деле представлял собой параметр «cfru»? Некоторые исследования показывают, что мы имеем дело с технологией веб-фильтрации хорошо известного прокси-сервера Bluecoat, и теперь мы стали чуть лучше понимать детали удаленной инфраструктуры. HTTP-запросы, отсылаемые в целевую систему, пересекались с как минимум одним WAF-устройством и прокси-сервером Bluecoat перед достижением веб-серверов и сервером приложений, как показано на рисунке ниже.

Рисунок 1: Приблизительная схема удаленной инфраструктуры

Идея

Как только мы обнаружили, что параметр «cfru» публично доступен, тут же возникла мысль – для передачи нашей полезной нагрузки не требовалась аутентификация на портале.

Таким образом, мы начали кодировать URL’ы внешних доменов, находящихся под нашим контролем, в base64 и передавать полученные строки через параметр «cfru». Мы надеялись, что получится реализовать нечто вроде SSRF (Server-Side Request Forgery). Однако итоге все получилось намного интереснее.

К сожалению, на тот момент мы не получили в ответ ни одного HTTP-запроса. Однако в системах, видимых из интернета, мы видели процесс, связанный с преобразованием DNS, начиная с имени «targetdomain». Казалось, что исходящие TCP соединения от целевого сайта были запрещены кроме DNS трафика. Затем, вместо инициации SSRF-запросов к внешним хостам, внимание было переключено на внутренние поддомены: https://auth.targetdomain, https://blog.targetdomain, https://www.targetdomain и так далее.

Мы начали передавать через параметр «cfru» некоторые из вышеуказанных URL'ов, закодированных в base64, и практически сразу заметили еще одну странность. Для некоторых URL’ов мы получили ответ в виде перенаправления HTTP 302. В некоторых случаях никакого ответа не было. В последнем случае вместо тела HTTP-запроса в ответе был HTML-код запрашиваемого ресурса, как если бы Bluecoat пересылал запрос к целевому ресурсу и получил содержимое обратно, выполняя роль веб-прокси. Наиболее важный момент – это явление наблюдалось даже когда мы передавали через параметр «cfru» поддомен, отвечающий за аутентификацию на портале (https//auth.targetdomain), а конкретно – на портале, где, как мы предполагали, находился Java-компонент, уязвимый к удаленному выполнению кода.

Переломный момент

Поворотная точка возникла в тот момент, когда мы сделали следующее предположение: если ресурс

https://auth.targetdomain/vulnerable_endpoint?param=malicious_RCE_payload

просматривается напрямую, наш HTTP-запрос тут же попадает в WAF, где есть правило распознающее подозрительное поведение (вредоносную полезную нагрузку, на которую указывает «param»), отправляет в ответ ошибку HTTP 404 и фактически блокирует атаку.

Но что если мы закодируем URL

https://auth.targetdomain/vulnerable_endpoint?param=malicious_RCE_payload

в base64 и полученную строку

“aHR0cHM6Ly9hdXRoLnRhcmdldGRvbWFpbi92dWxuZXJhYmxlX2VuZHBvaW50P3BhcmFtPW1hbGljaW91c19SQ0VfcGF5bG9hZA==“

передадим через параметр «cfru»

https//targetdomain/?cfru=aHR0cHM6Ly9hdXRoLnRhcmdldGRvbWFpbi92dWxuZXJhYmxlX2VuZHBvaW50P3BhcmFtPW1hbGljaW91c19SQ0VfcGF5bG9hZA==

В этом случае:

  1. Запрос проходит через WAF и не распознается как подозрительный.

  2. Затем запрос попадает к Bluecoat, где происходит декодирование параметра «cfru» и отправка GET-запроса к внутреннему хосту

    https://auth.targetdomain/vulnerable_endpoint?param=malicious_RCE_payload.
    

  3. В итоге инициируется уязвимость.

Бинго!

Мы видим результат выполнения вредоносной полезной нагрузки (в виде команды «hostname»), пройденную через DNS (как упоминалось ранее, исходящие TCP-подключение к нашему хосту в интернете блокировались).

Рисунок 2: DNS запрос к внутреннему хосту

Более того, мы немного поигрались с полезной нагрузкой, чтобы получить результаты инжектированных команд, возвращаемых напрямую, как часть HTTP-заголовков во время ответа сервера.

Рисунок 3: Результат выполнения команды внутри HTTP-заголовка

Заключение

В результате можно выделить две ошибки в конфигурации:

  • Прокси-сервер bluecoat выступал в качестве «пересыльщика» запросов вместо ответа в виде HTTP-редиректа как в случае с другими URL’ами (что привело бы к тому, что последующие клиентские запросы были пойманы и заблокированы WAF).

  • Не было правила, реализованного на уровне WAF, для анализа декодированного параметра «cfru» перед передачей в Bluecoat на предмет соответствия содержимого запроса одному из правил для блокировки, настроенному на стороне WAF.

Мы сразу сообщили об уязвимости компании и получили финансовое вознаграждение.

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

Тени в интернете всегда следят за вами

Станьте невидимкой – подключайтесь к нашему каналу.