Защищаем веб-сервер Apache

20 Янв
2008

Статья напечатана в журнале Хакер

Дочитавших до конца ждет видео (теперь с комментариями).
По последним данным британской компании Netcraft Apache является самым популярным web-сервером в Интернете, его доля за последние три года постепенно увеличивалась и сегодня составляет уже 67 % рынка. Успех Apache объясняется тем его стабильностью, он имеет хорошую репутацию в плане безопасности и прост в администрировании. Хотя Apache используется не один, а как часть набора состоящего из свободного программного обеспечения эта конфигурация известна как LAMP – Linux, Apache, MySQL и PHP/Perl. Сегодня мы разберем, как можно повысить безопасность LAMP.

Настраиваем апач

Но смотря на репутацию компонентов LAMP сегодня только и слышно о PHP Include, SQL Injection, Cross site scripting (XSS) и других атаках направленных на веб-сервисы. По статистике Web Application Security Consortium (www.webappsec.org/projects/whid/statistics.shtml) именно они занимают первые места по количеству зафиксированных инцидентов. Среди основных причин такой негативной тенденции называют широкую доступность инструментов необходимых для проведения атаки и недостаточное внимание со стороны разработчиков сайтов к вопросам безопасности. Условно можно выделить два фактора влияющие на безопасность: ошибки в администрировании и ошибки в программировании веб ресурса. С ними и будем разбираться. Советы даны применительно к Ubuntu/Debian, подправив пути можно применить их и в любом другом дистрибутиве.
При установке любой программы следует использовать репозитарий своего дистрибутива или брать файлы только с официального сайта. Возле ссылки для закачки архива обычно находится сслыка на файл, содержащий контрольную MD5 сумму или PGP/GPG ключи разработчиков. Их использование помогает не только убедиться, что архив скачан правильно, но и то, что получен оригинал.

проверяем правильность закачки

По умолчанию веб-сервер при подключении сообщает свою версию, операционную систему, и информацию о некоторых установленных модулях, которую может использовать хакер при подготовке атаки. Чтобы скрыть эту информацию следует добавить в конфигурационный файл apache2.conf (в некоторых дистрибутивах httpd.conf) директивы:

ServerSignature Off
ServerTokens Prod

Директива ServerSignature отвечает за вывод информации внизу страницы, например страницы ошибки 404 или листинга файлов каталога. Что именно выводится, определяется ServerTokens, значение которой по умолчанию Full. При установке в Prod[uctOnly] будет выведено только название сервера Apache без номера “Server: Apache”, информации о модулях и версии операционной системы. Как вариант можно сразу залезть в исходники (файл httpd.h в Apache 1.3 и ap_release.h в 2.x) и перед компиляцией подправить информацию по своему усмотрению.
В некоторых советах рекомендуют запускать веб-сервер под отдельной учетной записью, приводя в качестве примера “nobody”. Запуск нескольких различных серверов под этим пользователем делает его не менее могущественным чем root, поэтому для запуска любого сервера следует использовать отдельную учетную запись. Например в Ubuntu и некоторых дистрибутивах это www-data:

$ sudo cat /etc/apache2/apache2.conf | grep User
User www-data

Чтобы сменить пользователя, создаем его:

$ sudo adduser –no-create-home –disabled-password –disabled-login www-data

Затем указываем в конфигурационном файле:

User www-data
Group www-data

Теперь установим необходимые права:

$ sudo chown -R root:root /etc/apache2
$ sudo /etc/apache2 -type d | xargs chmod 755
$ sudo /etc/apache2 -type f | xargs chmod 644

Аналогичные команды выполняем и для каталога /var/log/apache2 в который апач сохраняет журналы и “DocumentRoot” (в Ubuntu /var/www). Нет никаких препятствий, чтобы убрать и право на чтение конфигурационных файлов:

$ sudo chmod -R go-r /etc/apache2

По умолчанию Apache загружает довольно большое количество модулей, часть из которых явно лишняя. Чтобы просмотреть модули, которые скомпилированы вместе с Apache, используйте “apache2ctl –l” или “apache2 -l”, убрать их можно, только полностью пересобрав веб-сервер.

вкомпилированные в сервер модули

Все динамически загружаемые модули (Dynamic Shared Object) можно просмотреть, введя:

$ sudo grep –R LoadModule /etc/apache2/*

Смотрим внимательно полученный список и отключаем то, что ненужно, просто поставив значок комментария перед ним. Вот список модулей, которые вполне можно и отключить, естественно, убедившись вначале, что они действительно не используются: mod_imap, mod_autoindex, mod_include, mod_info, mod_userdir, mod_status.
Apache поддерживает два типа аутентификации: basic и digest (обеспечивается модулем mod_auth_digest). В первом случае пароль передается в открытом виде. У хакера всегда будет возможность перехватить логин и пароль и получить доступ ко всей охраняемой области. В digest передается Response, который представляет собой контрольную (обычно MD5) сумму от комбинации логина, пароля, запрашиваемого URL, метода HTTP и строки nonce, генерируемой сервером при ответе. Последняя позволяет сделать эту строку поистине уникальной. Для включения digest-аутентификации используем:

AuthType Digest

Одной из особенностей Apache является использование типового доступа, когда многие параметры либо устанавливаются по умолчанию, либо наследуются от родительского каталога. Чтобы избежать неприятностей, следует принудительно ограничивать выполнение CGI-скриптов, SSI (Server Side Includes) включений и индексирования каталога и следование символическим ссылкам. Для этого в описании ресурса необходимо включать следующие директивы:

Options -Indexes
Options -Includes
Options –ExecCGI
Options -FollowSymLinks

Либо все сразу “Options None”. Чтобы хакер не смог прочитать временные или конфигурационные файлы, на всякий случай используем такую конструкцию:

<Files «(^\.ht|~$|\.bak$|\.BAK$)»>
Order Allow,Deny
Deny from all
</Files>

А чтобы избежать возможного доступа к файлам, расположенным вне корневого каталога веб-сервера, следует сначала принудительно ограничить доступ, а затем явно разрешить его в тех каталогах, где это нужно. В нормальных случаях пользователь за “DocumentRoot” выйти не сможет, но мы ведь не говорим о нормальных случаях:
<Directory />
Order Deny,Allow
Deny from all
Options None
AllowOverride None
</Directory>
<Directory /var/www>
Order Allow,Deny
Allow from all
</Directory>

Другим выходом не выпустить пользователя за “DocumentRoot” является использование chroot, о котором дальше. При необходимости AllowOverride и Options переопределяем в конкретном каталоге. Не всегда веб-сервер или отдельный ресурс должен быть виден из сети. Например, используется прокси, либо это внутренний сервер компании. Если нет возможности закрыть доступ брандмауэром, либо использовать отдельный интерфейс, то в этом случае следует ограничить к ресурсу доступ на основании IP-адреса или сети:
Order Deny,Allow
Deny from all
Allow from 192.168.0.0/24

Директива Satisfy, несмотря на то, что имеет всего два параметра, All и Any, дает возможность более гибко контролировать доступ к ресурсу. Например, нам нужно, чтобы доступ к определенному ресурсу могли получить только зарегистрированные пользователи и только с указанных адресов. Как это сделать? А очень просто.
Order Deny,Allow
Deny from all
Require valid-user
Allow from 192.168.0.0/24
Satisfy All

А для того чтобы пользователи внутренней сети могли вообще не регистрироваться, ставим вместо All – Any.
Если изменить значения некоторых параметров, можно смягчить эффект DoS-атаки. Например, значение Timeout, в течение которого сервер будет ожидать ответ клиента, в более ранних версиях Apache равнялось 1200 секунд, затем оно было уменьшено до 300. Но его спокойно можно еще уменьшить, например до 60:

Timeout 60

Хотя это и может вызвать проблемы у пользователей с плохим соединением.
По умолчанию размер клиентского запроса не ограничен. Этот также может быть использовано для организации DoS-атаки. Администратор может принудительно указать размер запроса в пределах от 0 (неограничен) до 2147483647 (2Гб) как для всего сервера в целом, так и для отдельных ресурсов. Например, вот так можно ограничить размер запроса 100 килобайтами:

LimitRequestBody 102400

Если клиент загружает на сервер, некоторые данные, например заполняя форму, то этот параметр следует подкорректировать. Как вариант можно для борьбы с DOS применять специальный модуль mod_evasive (www.zdziarski.com/projects/mod_evasive).
Кроме этого есть еще ряд директив LimitRequestFields, LimitRequestFieldSize и LimitRequestLine, MaxRequestsPerChild, MaxClients и некоторые другие. Их значения, возможно, стоит пересмотреть, выставив при необходимости оптимальные для ваших условий.

Устанавливаем ModSecurity

Значительно повысить защищенность веб-ресурса можно с помощью ModSecurity. Этот проект создан Иваном Ристиком (Ivan Ristic) в 2003 году и представляет собой файервол веб-приложений. Он может работать как модуль веб-сервера Apache, либо в автономном режиме, позволяя позволяяя защитить веб-приложения как от известных, так и неизвестных атак. Его использование прозрачно, как установка так и удаление не требует изменения настройки сервисов и сетевой топологии, кроме того при обнаружении уязвимого места, теперь не обязательно изменять исходный код проекта создавая новые ошибки, достаточно на первых порах просто добавить новое правило запрещающее вредную комбинацию. В репозитарии некоторых дистрибутивов уже включен нужный пакет, следует поискать что-то вроде mod-security. В Debian достаточно добавить в /etc/apt/sources.list новый репозитарий:

deb http://etc.inittab.org/~agi/debian/libapache-mod-security2/ etch/

И затем можно устанавливать:

# apt-get update
# apt-get install libapache2-mod-security2

Установить используя исходные тексты также просто. Для сборки используется apxs (APache eXtenSion tool). Если Apache устанавливался вместе с дистрибутивом, убедитесь в наличии заголовочных файлов и утилиты apxs (во второй версии apxs2). Устанавливаем исходные тексты веб-сервера из репозитария или берем их с сайта проекта:

$ sudo apt-get apache2-src libxml2-dev

Если используются исходные тексты, взятые с сайта проекта, то перед компиляцией модуля mod_security вначале следует, как минимум сконфигурировать веб-сервер, командой «./configure» с нужными параметрами ( для работы ModSecurity понадобится –enable-unique-id). Далее распаковываем архив:

$ wget –c http://www.modsecurity.org/download/modsecurity-apache_2.х.х.tar.gz
$ tar xzvf modsecurity-apache_2.х.х.tar.gz
$ cd modsecurity-apache_2.х.х/apache2

Теперь редактируем Makefile:

$ mcedit Makefile

# меняем apxs на apxs2
APXS = apxs2
# каталог с исходными текстами Apache
top_dir = /home/grinder/source/httpd-2.2.4

редактируем Makefile

Компилируем модуль, останавливаем Apache, устанавливаем модуль:

$ make
$ sudo /etc/init.d/apache2 stop
$ sudo make install

В конфигурационный файл веб-сервера добавим две строки:

LoadFile /usr/lib/libxml2.so
LoadModule security2_module /usr/lib/modules/mod_security2.so

Для удобства настройки ModSecurity лучше вынести в отдельный файл, взяв за пример готовый шаблон и подключив его в apache2.conf директивой:

Include /etc/apache2/mod_security.conf

Копируем шаблон и правим:

$ sudo cp modsecurity-apache_2.1.1/modsecurity.conf-minimal /etc/apache2/mod_security.conf

$ sudo mcedit /etc/apache2/mod_security.conf

<IfModule mod_security2.c>
SecRuleEngine On
SecRequestBodyAccess On
SecResponseBodyAccess Off
SecUploadKeepFiles Off
SecDebugLog /var/log/apache2/modsec_debug.log
SecDebugLogLevel 0
SecAuditEngine RelevantOnly
SecAuditLogRelevantStatus ^5
SecAuditLogParts ABIFHZ
SecAuditLogType Serial
SecAuditLog /var/log/apache2/modsec_audit.log
SecRequestBodyLimit 131072
SecRequestBodyInMemoryLimit 131072
SecResponseBodyLimit 524288
SecFilterDefaultAction «deny,log,status:430″
</IfModule>

Активируем модуль mod_unique_id:

$ sudo a2enmod unique_id

Теперь можно запускать апач:

$ sudo /etc/init.d/apache2 start

Если все работает нормально, можно добавлять правила. Команда разработчиков больше уделяет внимание усовершенствованию кода ModSecurity, оставляя создание правил пользователям, поэтому оригинальный конфигурационный файл имеет всего несколько правил находящихся в подкаталоге rules и на сайте проекта лежит отдельный архив modsecurity-core-rules. Чтобы их подключить достаточно, скопировать правила в каталог /etc/apache2 и подключить в секции mod_security2.c:

Include rules/*.conf
Include rules/blocking/*.conf

Подключать сразу все не стоит.

правила ModSecurity

Некоторые из правил требуют редактирования под конкретные условия, лучше разбираться постепенно.

Защищаем PHP с помощью Suhosin

Задача проекта Suhosin (www.hardened-php.net/suhosin) защита серверов и пользователей от целого ряда известных проблем в приложениях и ядре PHP, в том числе и от неизвестных уязвимостей, так как “safe_mode” помогает далеко не во всех случаях. Сам Suhosin состоит из двух независимых частей, которые могут использоваться как раздельно, так и совместно. Первая часть – небольшой патч к ядру осуществляющий низкоуровневую защиту структур данных против переполнения буфера, уязвимости форматной строки и от ошибок в реализации функции realpath присущей некоторым платформам (приводя ее к принятой в FreeBSD) и других уязвимостей ядра PHP. Вторая часть реализована в виде расширения, которое фактически и осуществляет всю основную защиту, при необходимости его очень просто доустановить в уже рабочую систему, без полной пересборки PHP. Его возможности еще шире (полный список приведен на сайте проекта www.hardened-php.net/suhosin/a_feature_list.html).
В случае нарушения установленных правил возможна блокировка переменных, отсылка определенного HTTP кода ответа, перенаправление браузера пользователя, выполнение другого PHP скрипта. Все события заносятся в журналы, для чего может использоваться syslog, свой модуль или внешний скрипт. При этом Suhosin-Patch привязан к соответствующей версии PHP, а последние версии расширения Suhosin совместимы практически со всеми версиями PHP.
Установка Suhosin состоит из двух этапов: наложение патча на PHP с последующей его пересборкой, и компиляция модуля расширения. Хотя возможна и сборка со встроенным расширением. Чтобы не было проблем с зависимостями, в Ubuntu перед началом рекомендую дать команду “sudo apt-get build-dep php5”. Скачиваем PHP, патч suhosin под используемую версию PHP и расширение. Все это распаковываем, накладываем патч и компилируем:

$ tar -xvjf php-5.x.x.tar.bz2
$ gunzip suhosin-patch-5.x.x-x.x.x.x.patch.gz
$ cd php-5.2.3
$ patch -p 1 -i ../suhosin-patch-5.x.x-x.x.x.patch
$ ./configure [--enable-so и другие параметры по необходимости]
$ make
$ make test
$ sudo make install

устанавливаем Suhosin

Теперь собираем модуль расширения:

$ tar -xzvf suhosin-0.x.x.tgz
$ cd suhosin-0.x.x
$ phpize
Configuring for:
PHP Api Version: 20041225
Zend Module Api No: 20060613
Zend Extension Api No: 220060519
$ ./configure –prefix=/usr/lib/php5/20060613+lfs/
$ make
$ make test
$ sudo make install

Проверить сборку, можно введя команду:

$ php –v
PHP 5.2.3 with Suhosin-Patch 0.9.6.2 (cli) (built: Jul 26 2007 11:35:13)
Copyright (c) 1997-2007 The PHP Group
Zend Engine v2.2.0, Copyright (c) 1998-2007 Zend Technologies

Все настройки Suhosin производятся в файле php.ini. Патч поддерживает только опции регистрации, поэтому первой записью обязательно подключаем модуль suhosin.so (он должен быть виден переменной LD_RUN_PATH).
extension=suhosin.so
После установки Suhosin будет работать с настройками по умолчанию, которые достаточно, но возможно не оптимальны, посмотреть их можно на сайте проекта (www.hardened-php.net/suhosin/configuration.html).

Строим chroot

Для построения chroot окружения нам понадобится модуль mod_chroot (core.segfault.pl/~hobbit/mod_chroot). В репозитарии Ubuntu он есть:

$ sudo apt-get install libapache2-mod-chroot

Параллельно будет установлен пакет mod-chroot-common содержащий документацию (/usr/share/doc/mod-chroot-common). Собрать его самостоятельно также просто, достаточно распаковать и ввести команду «apxs2 -cia mod_chroot.c». Можно создать отдельный каталог для chroot, лучше просто указать, что рабочий каталог теперь является корневым, то есть в apache2.conf пишем:

<IfModule mod_chroot.c>
LoadFile /lib/libgcc_s.so.1
PidFile /var/run/httpd.pid
ChrootDir /var/www
DocumentRoot /
</IfModule>

Значение DocumentRoot меняем с /var/www на /, и все ссылки на ресурсы теперь даем относительно корня. И про модуль не забываем, добавляем в apache2.conf:

LoadModule chroot_module /usr/lib/apache2/modules/mod_chroot.so

Либо правильней так:

$ sudo a2enmod mod_chroot

Во второй версии Apache, понадобится создать каталог для PID файла.

$ sudo mkdir -p /var/www/var/run
$ sudo chown -R root:root /var/www/var/run
$ sudo ln -s /var/www/var/run/httpd.pid /var/run/httpd.pid

Перезапускаем сервер и проверяем работу.
Это далеко не все, что можно сделать чтобы защитить LAMP. Также следует учесть, что данные советы не могут гарантировать абсолютной безопасности, такого просто не бывает в природе, хотя несколько уменьшить риск они позволяют. Кроме того, в некоторых средах некоторые параметры могут вызывать проблемы или влиять на производительность. Поэтому к их использованию следует подходить, осторожно используя их на свой страх и риск, вводя изменения постепенно и тщательно тестируя результат. Универсальный совет по прежнему один, изучите документацию и включите, то что нужно именно вам.

Видео по защите Apache

1 Комментарий к Защищаем веб-сервер Apache

Аватар

Linuxoid - все что знаю о Туксе » Архив блога » Zorp – модульный файервол уровня приложений

Февраль 8th, 2008 | 13:31

[...]  http://www.tux.in.ua/articles/249 был рассмотрен OpenSource файервол седьмого уровня ModSecurity, [...]

Комментировать

Наверх