taksitaksilno
Green Team
- 21.02.2019
- 62
- 8
В октябре 2019 года мы с Эрвином Хегедусом обнаружили две уязвимости в брандмауэре веб-приложений с открытым исходным кодом «libModSecurity» (CVE-2019-19886 от версии 3.0.0 до 3.0.3), которые могут привести к обходу SecRule и отказу в обслуживании. В этой статье я опишу обе уязвимости с помощью PoC на Nginx.
t.co
Согласно проекту ModSecurity, libModSecurity является одним из компонентов проекта ModSecurity v3. Кодовая база библиотеки служит интерфейсом для коннекторов ModSecurity, принимающих веб-трафик и применяющих традиционную обработку ModSecurity. В целом, он предоставляет возможность загружать / интерпретировать правила, написанные в формате SecRules, и применять их к HTTP-контенту, предоставленному вашим приложением через Connectors.
Благодаря Эрвину Хегедусу, который, как и я, является членом команды разработчиков OWASP Core Rule Set, мы выявили некоторые проблемы в парсере строк cookie в версиях libModSecurity 3.0.0-3.0.3. Чтобы упростить процесс тестирования, Эрвин создал отдельную программу на C ++ под названием «cookieparse», которая считывает строку cookie из первого аргумента и анализирует ее, сравнивая результаты между «старой» и исправленной версией парсера. Но давайте сделаем шаг назад и сосредоточимся на cookies/
Обход SecRule
Для протокола HTTP строка cookie - это последовательность пар ключ = значение, разделенных символом ";".
Запрос строки cookie
Даже если поначалу это выглядит просто, есть много способов привести парсер к виду, который не соответствуют тому, что обеспечивает стандарт,например:
Что меня здесь удивило, так это то, что согласно RFC 6265 строка cookie, отправленная без символа "=", должна полностью игнорироваться. Еще одна интересная вещь:
В пункте 3 кажется, что cookie может иметь пустое значение или пустое имя. Я никогда не думал о том, чтобы проверить, что будет делать брандмауэр приложения, пытающийся проанализировать файл cookie с пустым именем. Используя cookieparse, Эрвин обнаружил, что старый парсер не включает часть значения cookie, если строка cookie имеет вид "foo = bar = ciao" :
cookieparse output
Как видите, для старого парсера значение cookie
cookieparse output with XSS payload
Старый синтаксический анализатор полностью игнорировал бы полезную нагрузку XSS, и можно было бы обойти гипотетическое правило, которое проверяет, содержит ли значение cookie вредоносное содержимое.
DoS уязвимость
Продолжая наши обходные тесты, то, что я обнаружил после, напугало нас и заставило попросить у Trustwave патч и релиз безопасности. Как мы уже говорили, в строке cookie каждое имя и значение отделяются символом
Разговаривая с Эрвином о последствиях, которые эта ошибка может иметь для веб-сервера, на котором работает libModSecurity, я создал докер-контейнер с Nginx и libModSecurity 3.0.3. Отправляя один запрос с заголовком Cookie: = foo Я неполучил никакого ответа от веб-сервера, даже часть заголовка ответа.
Nginx error_logs (вверху), curl output (внизу)
При чтении журнала ошибок Nginx становится ясно, что мой предыдущий запрос уничтожил рабочий процесс Nginx, который записал в журнал ту же ошибку «out of range ». С этого момента мне было действительно легко завалить Nginx,просто отправив несколько запросов с помощью curl и непрерывно уничтожая перезапускающиеся рабочие процессы Nginx с помощью:
Протестировав это с Nginx, который проксирует все запросы к WordPress, вот что произошло:
Источник
ModSecurity Denial of Service Details - CVE-2019-19886
ModSecurity is an open-source WAF engine maintained by Trustwave. As a lively open-source project, we constantly work together with the community on reported bugs, feature requests, and other issues on the ModSecurity GitHub.
Согласно проекту ModSecurity, libModSecurity является одним из компонентов проекта ModSecurity v3. Кодовая база библиотеки служит интерфейсом для коннекторов ModSecurity, принимающих веб-трафик и применяющих традиционную обработку ModSecurity. В целом, он предоставляет возможность загружать / интерпретировать правила, написанные в формате SecRules, и применять их к HTTP-контенту, предоставленному вашим приложением через Connectors.
Благодаря Эрвину Хегедусу, который, как и я, является членом команды разработчиков OWASP Core Rule Set, мы выявили некоторые проблемы в парсере строк cookie в версиях libModSecurity 3.0.0-3.0.3. Чтобы упростить процесс тестирования, Эрвин создал отдельную программу на C ++ под названием «cookieparse», которая считывает строку cookie из первого аргумента и анализирует ее, сравнивая результаты между «старой» и исправленной версией парсера. Но давайте сделаем шаг назад и сосредоточимся на cookies/
Обход SecRule
Для протокола HTTP строка cookie - это последовательность пар ключ = значение, разделенных символом ";".
Запрос строки cookie
Даже если поначалу это выглядит просто, есть много способов привести парсер к виду, который не соответствуют тому, что обеспечивает стандарт,например:
Что меня здесь удивило, так это то, что согласно RFC 6265 строка cookie, отправленная без символа "=", должна полностью игнорироваться. Еще одна интересная вещь:
В пункте 3 кажется, что cookie может иметь пустое значение или пустое имя. Я никогда не думал о том, чтобы проверить, что будет делать брандмауэр приложения, пытающийся проанализировать файл cookie с пустым именем. Используя cookieparse, Эрвин обнаружил, что старый парсер не включает часть значения cookie, если строка cookie имеет вид "foo = bar = ciao" :
cookieparse output
Как видите, для старого парсера значение cookie
foo равно bar, а не bar = ciao, как должно быть. Это означает, что можно внедрить вредоносную полезную нагрузку (такую как SQL-инъекция или межсайтовый скриптинг), просто поместив ее после символа =. Например: cookieparse output with XSS payload
Старый синтаксический анализатор полностью игнорировал бы полезную нагрузку XSS, и можно было бы обойти гипотетическое правило, которое проверяет, содержит ли значение cookie вредоносное содержимое.
DoS уязвимость
Продолжая наши обходные тесты, то, что я обнаружил после, напугало нас и заставило попросить у Trustwave патч и релиз безопасности. Как мы уже говорили, в строке cookie каждое имя и значение отделяются символом
=, а каждая пара имя / значение файла cookie - символом ; . После нескольких тестов я начал ставить случайные последовательности ; и = пытается разбить его. Отправив ;=; ничего не произошло, кроме удаления первого ; / что-то пошло не так. Старый парсер выдал следующую ошибку: Разговаривая с Эрвином о последствиях, которые эта ошибка может иметь для веб-сервера, на котором работает libModSecurity, я создал докер-контейнер с Nginx и libModSecurity 3.0.3. Отправляя один запрос с заголовком Cookie: = foo Я неполучил никакого ответа от веб-сервера, даже часть заголовка ответа.
Nginx error_logs (вверху), curl output (внизу)
При чтении журнала ошибок Nginx становится ясно, что мой предыдущий запрос уничтожил рабочий процесс Nginx, который записал в журнал ту же ошибку «out of range ». С этого момента мне было действительно легко завалить Nginx,просто отправив несколько запросов с помощью curl и непрерывно уничтожая перезапускающиеся рабочие процессы Nginx с помощью:
curl -H 'Cookie: =;' 'http://localhost/?a=[0-10000]' Протестировав это с Nginx, который проксирует все запросы к WordPress, вот что произошло:
Источник