mod_security2 для Apache

Date January 10th, 2010 Author Vitaly Agapov

mod_securityДля защиты своих Web-приложений надо прикладывать максимум усилий и всегда быть готовым к тому, что этого всё равно окажется недостаточно. Руки, само собой, опускаться не должны (только если на клавиатуру), а мы должны знать и помнить о всех возможностях нашего любимого ПО.
Сегодня я себе в качестве памятки (а всем прочим для ознакомления или праздного интереса) вкратце опишу весьма нужный модуль для Web-сервера Apache: mod_security2.

Нельзя создать идеальный с точки зрения безопасности код Web-приложения и поместить его в абсолютно безопасное окружение, защищающее контент от любых посягательств со стороны сетевых антисоциальных элементов. Тут, конечно, можно было бы завести схоластическую беседу о текстовых html-страничках, созданных на компьютере, хранящемся в чулане без подключения к сети… но не будем.

Проблема в том, что все серверные сценарии пишутся с такими встроенными полезными фичами, как дыры в безопасности. В подавляющем большинстве они связаны с возможностью передать в качестве параметра в HTTP-запросе какое-то значение, которое девелопер просто не предусмотрел и не сделал толковую проверку входных параметров. Сам я, хоть и стараюсь постоянно об этом помнить, периодически ловлю себя на том, в том или ином месте опять забыл проверить значение переменной. Обнаружить такую дыру непросто, обычное добросовестное кликанье по ссылкам на странице приводит к ожидаемому результату – всё работает очень круто. Здесь требуется запустить шаловливые ручки в адресную строку и начать экспериментировать. Те самые упомянутые антисоциальные элементы умеют делать это в совершенстве.

mod_security

Поставить дополнительную преграду на пути SQL-инъекций нам поможет модуль mod_security для Apache. Он распространяется бесплатно, а раздобыть его или почитать про него кое-какую информацию можно на сайте www.modsecurity.org.

Модуль mod_security наделяет Apache возможностями брандмауэра: мы можем, задавая правила в конфигурации, определять, какие запросы являются легитимными, а какие следует запретить как потенциально опасные. При этом модуль поддерживает регулярные выражения, что и определяет его мощность и гибкость в использовании. Второй его важной особенностью является возможность работы как с запросами GET, так и с запросами POST.

На установке останавливаться не буду. Модуль легко ставится из репозиториев либо собирается из исходников. У него есть некоторые зависимости, но проблем с ними возникать не должно. Расписывать установку – дело неблагодарное уже хотя бы из-за особенностей установки для разных ОС. Если ставить из исходников, то потребуется в httpd.conf добавлять строки для загрузки нужных библиотек libxml, liblua и самого модуля mod_security:

LoadFile /usr/lib/libxml2.so.2
LoadFile /usr/lib/liblua5.1.so.0
LoadModule security2_module modules/mod_security2.so

Если, например, ставить из репозитория в Ubuntu с помощью

sudo aptitude install libapache-mod-security mod-security-common

,то автоматически создастся файл /etc/apache2/mods-available/mod-security.load и соответствующая ссылка в mods-available. То есть лишних телодвижений не понадобится.

Перейдем к конфигурации. После установки модуля в конфигурации сервера можно использовать директивы фильтрации запросов. Некоторые из этих директив можно использовать внутри стандартных апачевских директив Directory, Location, VirtualHost и т.д. А некоторые – только в основном конфигурационном файле. Полную документацию по всем директивам можно найти на ModSecurity.org, упомянутом выше.

В файл httpd.conf вставляем строки:

<IfModule mod_security2.c>
 Include conf.d/modsec/*.conf
</IfModule>

И создаём файлы:

mkdir /etc/httpd/conf.d/modsec
mkdir /var/log/httpd/modsec
touch /etc/httpd/conf.d/modsec/modsecurity_crs_10_config.conf
touch /etc/httpd/conf.d/modsec/modsecurity_crs_15_customrules.conf

В файле modsecurity_crs_10_config.conf содержатся все основные директивы модуля, например, пути к лог-файлам и директивы включения режима фильтрации, а файл modsecurity_crs_15_customrules.conf при запуске Apache будет прочитан вторым и до всех остальных файлов конфигурации, что позволяет более гибко управлять правилами, например, в нём можно прописать нужные IP-адреса в белые списки, тем самым отменив необходимость продираться им через все остальные системы фильтров.

Итак, пропишем в основной лог следующее:

# Включить движок фильтра
SecRuleEngine On

# Вести лог только для подозрительных запросов
SecAuditEngine RelevantOnly

# Имя файла лога
SecAuditLog /var/log/httpd/modsec/audit_log

# Вывод отладочной информации
SecDebugLog /var/log/httpd/modsec/debug_log
SecDebugLogLevel 1

# Для подозрительных запросов по умолчанию писать в лог
# и возвращать HTTP ответ с кодом 403
SecDefaultAction log,auditlog,deny,status:403,phase:2

Эта конфигурация просто активирует движок mod_security и в общем-то больше ничего не делает. Мы просто подготовили себе и модулю рабочее место и подошли к самому интересному – к правилам фильтрации. Прежде, чем к ним обратиться, стоит сделать небольшую ремарку относительно фаз обработки запросов сервером Apache. Их всего пять, и, начиная, с версии mod_security 2.5, для правил эту фазу надо указывать. Итак, на первой фазе обрабатываютя заголовки запроса, на второй – тело запроса, на третьей – заголовки ответа, на четвёртой – тело ответа, а на пятой происходит логирование события.

Обычно формат правила фильтрации выглядит следующим образом:

SecRule <Переменная> <Оператор> [<Действия>]

Переменная определяет объект для сравнения с шаблоном. Самые используемые значения:

  • ARGS – параметры запроса GET или тело запроса POST (как частные случаи – ARGS_GET и ARGS_POST).
  • ARGS_NAMES – имена параметров в запросе GET или POST
  • FILES – запрошенные файлы
  • FILES_COMBINED_SIZE – общий объем загружаемых файлов
  • FILES_NAMES – имена загружаемых файлов
  • FILES_SIZES – отдельные размеры загружаемых файлов
  • GEO – наборы параметров для управления трафиком в зависимости от региона, к которому принадлежит IP-адрес
  • PATH_INFO – путь (часть URL)
  • QUERY_STRING – полная строка запроса с аргументами
  • REMOTE_ADDR или REMOTE_HOST – IP-адрес или доменное имя удаленного пользователя
  • REMOTE_PORT – порт, с которого устанавливается соединение
  • REQUEST_BASENAME – имя запрашиваемого файла (например, index.php)
  • REQUEST_HEADERS – заголовки запроса
  • REQUEST_HEADERS_NAMES – имена заголовков
  • REQUEST_LINE – полная строка запроса, включая версию HTTP
  • REQUEST_URI – URL запроса без доменного имени
  • REQUEST_URI_RAW – URL запроса с доменным именем

В качестве оператора используется либо некоторая константа, либо регулярное выражение (оператор по умолчанию – rx), либо непосредственно оператор, использующийся для сравнения:

  • beginsWith
  • contains
  • endsWith
  • eq
  • ge – больше или равно
  • gt
  • le – меньше или равно
  • lt
  • pm – сравнение по списку слов
  • pmFromFile – сравнение со списком слов из файла
  • rx – регулярное выражение
  • streq – сравнение строк на точное соответствие
  • validateByteRange – сравнение с диапазоном байтов

В поле действий мы можем задать последовательность действий для модуля в случае соответствия переменной шаблону. Поле является необязательным, и по умолчанию будут выполнены действия, указанные директивой SecDefaultAction. Действия перечисляются через запятую. Из полезных действий следует упомянуть следующие:

  • allow – прекратить проверку и разрешить транзакцию
  • auditlog – сделать запись в auditlog
  • deny – прекратить проверку и завершить транзакцию
  • deprecatevar – уменьшать переменную с течением времени
  • drop – завершить IP-соединение
  • exec – выполнить внешний скрипт или команду
  • expirevar – обнулять переменную через промежуток времени
  • id – уникальный id правила
  • initcol – создать набор переменных (например, для слежения за IP-адресами)
  • log – создать запись в error.log и audit.log
  • logdata – записать часть запроса в лог
  • msg – записать в лог дополнительное сообщение
  • pass – продолжить проверку
  • pause – задержать обработку транзакции на определенное количество миллисекунд
  • phase – приписать правило к определенной фазе
  • proxy – перенаправить запрос на другой web-сервер
  • redirect – вернуть ответ 302с новым адресом
  • setvar – создание и управление переменными
  • status – ответить с данным HTTP-кодом
  • within

Вся эта теория очень, конечно, полезна, но самое интересное впереди – мы рассмотрим некоторые полезные правила, которые либо прямо так, либо после некоторого допиливания можно использовать на своих серверах:

SecRule FILES "\.conf$" log,deny,status:403,phase:2

Проверяет запросы, требующие файлы конфигурации.

SecRule PATH_INFO "^/(bin|etc|sbin|opt|usr)"

Проверяет запросы, обращающиеся к файлам в системных директориях.

SecRule REQUEST_BASENAME "^login\.php$" phase:2,t:none,t:lowercase

Проверяет обращение к определённому скрипту

SecAction phase:1,initcol:ip=%{REMOTE_ADDR},nolog
SecRule ARGS:login "!^$" nolog,phase:1,setvar:ip.auth_attempt=+1,deprecatevar:ip.auth_attempt=20/120
SecRule IP:AUTH_ATTEMPT "@gt 25" \ "log,drop,phase:1,msg:'Possible Brute Force Attack'"

Подсчитывает количество попыток логина для каждого IP (здесь попыткой логина считается непустое значение поля login), и если их было более 25 за две минуты, то IP-соединение разрывается.

SecRule ARGS:text "@validateByteRange 10, 13, 32-126"

Проверяет наличие символов на соответствие указанному диапазону в поле text.

SecRule ARGS "\.\./"

Проверяет наличие двух точек в запросе. Одна из возможных атак на сервер.

SecRule ARGS "delete.+from" "t:lowercase"
SecRule ARGS "insert.+into" "t:lowercase"
SecRule ARGS "select.+from" "t:lowercase"

Проверяет на возможные SQL-инъекции.

Ссылки:
www.modsecurity.org

Tags: ,
Category: Apache, Linux, Security, Web-dev | 6 Comments »

Comments

6 комментариев на “mod_security2 для Apache”

  1. Alexandr

    В статье наконец-то нашёл ответ чем отличаются настройки mod_security от настройки mod_security2. Краткая, полезная и понятная статья!

  2. andrey

    Как удалить установленный модуль mod_security2 и все настройки.

  3. andrey

    как удалить mod_security2

  4. Vitaly Agapov

    Например, так:
    apt-get purge libapache-mod-security

    О какой системе вообще идёт речь?

  5. agapoff.name | IT блог » Blog Archive » Защита web-приложения, использующего Ajax (Ajax Fingerprinting)

    […] в заголовке XHR (XMLHttpRequest), а на стороне сервера с помощью mod_security фильтруем всё Ajax-запросы, не содержащие этого поля или […]

  6. agapoff.name | IT блог » Blog Archive » Заметки об Apache, часть 6: Простая защита от ДДоС/брутфорса средствами ModSecurity

    […] эдак, три назад я уже постил здесь статейку "mod_security2 для Apache", касающуюся использования модуля ModSecurity. Она и […]

Leave a comment

 Comment Form