защищаем веб-сервер Apache
В этой статье мы шаг за шагом расскажем, как правильно устанавливать и конфигурировать Apache 1.3.x Web сервер, для того чтобы смягчить или избежать возможность успешного взлома, в случае обнаружения новой уязвимости в этом популярном веб-сервере.
функциональные возможности
Прежде чем защищать Apache, нужно определить функциональные возможности, ожидаемые от сервера. Разнообразие в использовании Apache делает трудным написание универсальной процедуры для защиты сервера в каждом отдельном случае. Именно поэтому в этой статье мы будем базироваться на следующих функциональных возможностях:
— веб-сервер будет доступен из Internet;
— будут обслуживаться только статические HTML-страницы;
— сервер будет поддерживать виртуальный механизм хостинга на основе имен;
— указанные веб-страницы могут быть доступны только для выбранных IP-адресов или пользователей (базовая идентификация);
— сервер регистрирует все веб-запросы (включая информацию о браузерах).
Стоит подчеркнуть, что вышеупомянутая модель не поддерживает PHP, JSP, CGI и любые другие технологии, которые позволяют взаимодействовать с веб-службами. Использование таких технологий может представлять большую угрозу защите, так, даже маленький, неприметный сценарий может радикально уменьшить уровень защиты сервера. Почему? Прежде всего, PHP/CGI приложения могут содержать уязвимость защиты (например, SQL-инъекцию или межсайтовый скриптинг). /* Здесь автор привел достаточно специфический, труднореализуемый пример, при том что 70% веб-программистов «погорает» на куда более глупых ошибках программирования, например, передаче в скрипт полного пути к файлу для редактирования/просмотра или отсутствии проверки пользовательского ввода напредмет, скажем, символов конвейера, приводящем к выполнению произвольного кода. Большинство веб-серверов во всем мире ломают именно через эти дыры ;) — прим. ред. */ Во вторых, опасна сама технология (уязвимость в PHP, Perl модулях и т.д.). Именно поэтому настоятельно рекомендуется использовать такие технологии только в тех случаях, когда взаимодействие с веб-cайтом абсолютно необходимо.
предложения по защите
Одним из наиболее важных элементов каждого компьютерного проекта является спецификация предложений по защите. Она должна быть выполнена прежде, чем проект осуществлен. Предложения по защите для нашего веб-сервера следующие:
— операционная система должна быть в максимально возможной степени защищена от локальных и удаленных нападений;
— сервер не должен поддерживать отличные от HTTP(80/TCP) сетевые протоколы;
— удаленный доступ к серверу должен управляться межсетевой защитой, которая должна блокировать все внешние подключения и разрешать входящие подключения только через 80/TCP порт веб-сервера;
— Apache Web server должен быть единственной службой, доступной системе;
— нужно разрешить использование только самых необходимых модулей Apache;
— должны быть выключены любые диагностические веб-страницы и автоматические службы индексации каталога;
— сервер должен раскрывать наименьшее количество информации о себе (защита втемную);
— сервер Apache должен выполняться под уникальным UID/GID, не используемым никаким другим системным процессом;
— процессы Apache должны быть ограничены доступом к системным файлам (chrooting);
— никакие программы-оболочки не должны присутствовать в chrooted среде Apache (/bin/sh,/bin/csh и т.д.).
инсталляция операционной системы
Перед установкой Apache мы должны выбрать операционную систему, на которой будет установлен сервер. У нас имеется широкий выбор, потому что Apache может компилироваться и устанавливаться почти на каждой операционной системе. В оставшейся части статьи мы расскажем, как защитить веб-сервер Apache на FreeBSD (4.7). Описанные методы можно применить в большинстве UNIX/Linux-систем. Единственная операционная система, которую не рекомендуется использовать — MS Windows, главным образомиз-за ограниченных возможностей поддержки Apache.
Первый шаг в защите веб-сервера — укрепление операционной системы, но обсуждение этого вопроса выходит за рамки этой статьи.
После того, как система установлена и укреплена, мы должны добавить новую группу, а пользователя назвать "apache". Пример для FreeBSD:
pw groupadd apache
pw useradd apache -c "Apache Server" -d /dev/null -g apache -s /sbin/nologin
По умолчанию, процессы Apache выполняются с привилегиями пользователя nobody (кроме главного процесса, который выполняется с привилегиями root) и GID группы nogroup. Это может создать существенную угрозу защите. В случае успешного прорыва вторгшийся может получить доступ ко всем другим процессам, которые выполняются под тем же самым UID/GID. Следовательно, оптимальное решение состоит в том, чтобы выполнить Apache под UID/GID уникального пользователя/группы, специально созданного под это программное обеспечение.
подготовка программного обеспечения
Следующий шаг заключается в загрузке самой последней версии веб-сервера Apache с сайтаhttp://httpd.Apache.org/. Некоторые из параметров Apache доступны только во время компиляции, таким образом, важно загрузить исходный код вместо двоичной версии.
Модули Apache
После загрузки и распаковки пакета мы должны решить, какие модули оставить доступными. Краткое описание всех модулей, доступных в самой последней версии Apache 1.3.x (1.3.27) можно найти вhttp://httpd.Apache.org/docs/mod/.
Выбор модулей — один из наиболее важных шагов защиты Apache. Нужно действовать в соответствии с правилом: чем меньше — тем лучше. Для сохранения выбранных нами функциональных возможностей и выполнения предложений по защите, следующие модули должны остаться доступными:
Название модуля | Описание |
httpd_core | Ядро Apache, требуется при каждой установке Apache |
mod_access | Обеспечивает управление доступом, основанным на имени хоста клиента, IP-адресе и других характеристиках запроса клиента. Поскольку этот модуль необходим, чтобы использовать директивы "order", "allow" и "deny", он должен оставаться доступным. |
mod_auth | Требуется для осуществления пользовательской идентификации (базовая HTTP-идентификация). |
mod_dir | Требуется, для поиска и обслуживания каталога с индексными файлами: "index.html", "default.htm", и т.д. |
mod_log_config | Требуется для регистрации запросов, сделанных на сервер. |
mod_mime | Требуется для установки кодировок (content encoding), языков (content-language) и MIME-типов. |
Все другие модули Apache должны быть отключены. Мы можем их совершенно спокойно отключать, главным образом потому, что они нам не нужны :). Отключая ненужные модули, мы избегаем потенциального взлома, когда будет найдена новая уязвимость защиты в одном из них.
Также стоит обратить внимание на то, что два из модулей Apache могут быть наиболее опасны, чем другие:mod_autoindex и mod_info. Первый модуль обеспечивает автоматическую индексацию каталогов и доступен по умолчанию. Этот модуль удобен для проверки выполнения Apache на сервере (например, http://server_name/icons/) и получения содержимого каталогов веб-сервера, когда в них отсутствуют индексные файлы. Второй модуль,mod_info, никогда не должен быть доступен из Internet, главным образом потому, что он показывает конфигурацию сервера Apache.
Слеюующий вопрос — как правильно скомпилировать модули. Лучше использовать статический метод. Если будет найдена новая уязвимость в Apache, мы, вероятно, повторно скомпилируем не только уязвимые модули, но и всю программу. Выбирая статический метод, мы также устраняем потребность в еще одном модуле —mod_so.
компиляция программы
Сначала, если возможно, должны быть установлены все патчи защиты. Затем сервер должен быть скомпилирован и установлен следующим образом:
./configure --prefix=/usr/local/apache --disable-module=all --server-uid=apache --server-gid=apache --enable-module=access --enable-module=log_config --enable-module=dir --enable-module=mime --enable-module=auth
make
su
umask 022
make install
chown -R root:sys /usr/local/apache
chrooting сервера
Cредства методики chrooting создают новую структуру корневого каталога, перемещая в него все файлы демона, и выполняя демон в этой новой среде. Благодаря этому, демон (и все дочерние процессы) будет иметь доступ только к новой структуре каталога.
Мы запустим этот процесс, создавая новую структуру корневого каталога из /chroot/httpd:
mkdir -p /chroot/httpd/dev
mkdir -p /chroot/httpd/etc
mkdir -p /chroot/httpd/var/run
mkdir -p /chroot/httpd/usr/lib
mkdir -p /chroot/httpd/usr/libexec
mkdir -p /chroot/httpd/usr/local/apache/bin
mkdir -p /chroot/httpd/usr/local/apache/logs
mkdir -p /chroot/httpd/usr/local/apache/conf
mkdir -p /chroot/httpd/www
Владельцем всех каталогов должен быть корневой каталог, а права доступа должны быть установлены в 0755. Затем, мы создадим специальный файл устройства: /dev/null
ls -al /dev/null
crw-rw-rw- 1 root wheel 2, 2 Mar 14 12:53 /dev/null
mknod /chroot/httpd/dev/null c 2 2
chown root:sys /chroot/httpd/dev/null
chmod 666 /chroot/httpd/dev/null
Различные методы должны использоваться для создания устройства /chroot/httpd/dev/log, которое также необходимо для правильной работы сервера. В случае системы FreeBSD, к /etc/rc.conf должна быть добавлена следующая строка:
syslogd_flags="-l /chroot/httpd/dev/log"
Мы должны перезапустить систему или демон syslogd непосредственно для вступления в силу сделанных изменений. Для создания устройства /chroot/httpd/dev/log на других операционных системах, нужно смотреть справочное руководство (man syslogd).
В следующем шаге мы должны скопировать httpd в новое дерево каталога со всеми необходимыми кодами и библиотеками. Для осуществления этого, мы должны подготовить список всех требуемых файлов. Мы можем сделать такой список, используя следующие команды (их присутствие зависит от особенностей операционной системы):
Команда | Принадлежность | Описание |
ldd | Все | Показывает динамические отношения исполняемых файлов или общедоступных библиотек |
ktrace/ktruss/kdump | *BSD | Разрешает трассировку процессов ядра . Отображает данные трассировки адра. |
sotruss | Solaris | Трассирует вызовы процедур совместно используемых библиотек |
Strace/ltrace | Linux | Отслеживает системные вызовы и сигналы. |
strings | Все | Находит печатаемые строки в двоичных файлах. |
trace | AIX | Осуществляет запись выбранных системных событий. |
trace (freeware) | HP-UX <10.20 | Отображает системные вызовы и трассировку kernal процессов. |
truss | FreeBSD, Solaris, AIX 5L, SCO Unixware | Отслеживает системные вызовы и сигналы. |
tusc (freeware) | HP-UX>11 | Отслеживает системные вызовы и процессы, вызванные из HP-UX 11 |
Ниже представлены примеры использования ldd, strings и truss команд.
localhost# ldd /usr/local/apache/bin/httpd
/usr/local/apache/bin/httpd:
libcrypt.so.2 => /usr/lib/libcrypt.so.2 (0x280bd000)
libc.so.4 => /usr/lib/libc.so.4 (0x280d6000)localhost# strings /usr/local/apache/bin/httpd
| grep lib /usr/libexec/ld-elf.so.1
libcrypt.so.2
libc.so.4
localhost# truss /usr/local/apache/bin/httpd | grep open
(...)
open("/var/run/ld-elf.so.hints",0,00) = 3
(0x3)open("/usr/lib/libcrypt.so.2",0,027757775370) = 3
(0x3)open("/usr/lib/libc.so.4",0,027757775370) = 3
(0x3)open("/etc/spwd.db",0,00) = 3
(0x3)open("/etc/group",0,0666) = 3
(0x3)open("/usr/local/apache/conf/httpd.conf",0,0666) = 3 (0x3)
(...)
Вышеупомянутые команды должны применяться не только для httpd-программ, но также и для всех библиотек и исходников (библиотеки часто требуют других библиотек). В случае FreeBSD-системы, следующие файлы должны быть скопированы в новую структуру корневого каталога:
cp /usr/local/apache/bin/httpd /chroot/httpd/usr/local/apache/bin/
cp /var/run/ld-elf.so.hints /chroot/httpd/var/run/
cp /usr/lib/libcrypt.so.2 /chroot/httpd/usr/lib/
cp /usr/lib/libc.so.4 /chroot/httpd/usr/lib/
cp /usr/libexec/ld-elf.so.1 /chroot/httpd/usr/libexec/
Используя команду truss, мы можем обнаружить, что следующие файлы конфигурации должны присутствовать в chrooted среде:
cp /etc/hosts /chroot/httpd/etc/
cp /etc/host.conf /chroot/httpd/etc/
cp /etc/resolv.conf /chroot/httpd/etc/
cp /etc/group /chroot/httpd/etc/
cp /etc/master.passwd /chroot/httpd/etc/passwords
cp /usr/local/apache/conf/mime.types /chroot/httpd/usr/local/apache/conf/
Обратите внимание, что мы должны удалить все строки из/chroot/httpd/etc/passwords, кроме"nobody"и"apache". Подобным способом, мы должны удалить все строки кроме"apache"и"nogroup"из/chroot/httpd/etc/group. Затем, мы должны построить базу данных паролей следующим образом:
cd /chroot/httpd/etc
pwd_mkdb -d /chroot/httpd/etc passwords
rm -rf /chroot/httpd/etc/master.passwd
Следующий шаг состоит в проверке правильности выполнения httpd-сервера в новой chrooted среде. Для этого, мы должны скопировать файл конфигурации Apache и index.html:
cp /usr/local/apache/conf/httpd.conf /chroot/httpd/usr/local/apache/conf/
cp /usr/local/apache/htdocs/index.html.en /chroot/httpd/www/index.html
После копирования вышеупомянутых файлов, мы должны изменить директиву DocumentRoot так, как представлено ниже (в /chroot/ httpd/usr/local/apache/conf/httpd.conf):
DocumentRoot "/www"
Затем, мы можем пробовать запустить сервер:
chroot /chroot/httpd /usr/local/apache/bin/httpd
Если возникают какие-либо проблемы, рекомендуется проанализировать логи Apache (/chroot/httpd/usr/local/apache/logs). Также может использоваться следующая команда:
truss chroot /chroot/httpd /usr/local/apache/bin/httpd
Программа Truss должна показать причину проблемы. После устранения любых возможных ошибок, мы можем конфигурировать Apache.
конфигурирование Apache
Сначала должен быть удален /chroot/httpd/usr/local/apache/conf/httpd.conf файл и создан новый на его месте, с приблизительно следующим содержимым:
# =================================================
# Basic settings
# =================================================
ServerType standalone
ServerRoot "/usr/local/apache"
PidFile /usr/local/apache/logs/httpd.pid
ScoreBoardFile /usr/local/apache/logs/httpd.scoreboard
ResourceConfig /dev/null
AccessConfig /dev/null
# =================================================
# Performance settings
# =================================================
Timeout 300
KeepAlive On
MaxKeepAliveRequests 100
KeepAliveTimeout 15
MinSpareServers 5
MaxSpareServers 10
StartServers 5
MaxClients 150
MaxRequestsPerChild 0
# =================================================
# Apache's modules
# =================================================
ClearModuleList
AddModule mod_log_config.c
AddModule mod_mime.c
AddModule mod_dir.c
AddModule mod_access.c
AddModule mod_auth.c
# =================================================
# General settings
# =================================================
Port 80
User apache
Group apache
ServerAdmin Webmaster@www.ebank.lab
UseCanonicalName Off
ServerSignature Off
HostnameLookups Off
ServerTokens Prod
<IfModule mod_dir.c>
DirectoryIndex index.html</IfModule>
DocumentRoot "/www/vhosts"
# =================================================
# Access control
# =================================================
<Directory>
Options None AllowOverride None Order deny,allow
Deny from all</Directory>
<Directory "/www/vhosts/www.ebank.lab">
Order allow,deny Allow from all</Directory>
<Directory "/www/vhosts/www.test.lab">
Order allow,deny Allow from all</Directory>
# =================================================
# MIME encoding
# =================================================
<IfModule mod_mime.c>
TypesConfig /usr/local/apache/conf/mime.types</IfModule>
DefaultType text/plain
<IfModule mod_mime.c>
AddEncoding x-compress Z AddEncoding x-gzip gz tgz
AddType application/x-tar .tgz</IfModule>
# =================================================
# Logs
# =================================================
LogLevel warn
LogFormat "%h %l %u %t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\"" combined
LogFormat "%h %l %u %t \"%r\" %>s %b" common
LogFormat "%{Referer}i -> %U" referer
LogFormat "%{User-agent}i" agent
ErrorLog /usr/local/apache/logs/error_log
CustomLog /usr/local/apache/logs/access_log combined
# =================================================
# Virtual hosts
# =================================================
NameVirtualHost *
<VirtualHost *>
DocumentRoot "/www/vhosts/www.ebank.lab"
ServerName "www.ebank.lab"
ServerAlias "www.e-bank.lab"
ErrorLog logs/www.ebank.lab/error_log
CustomLog logs/www.ebank.lab/access_log combined
</VirtualHost>
<VirtualHost *>
DocumentRoot "/www/vhosts/www.test.lab"
ServerName "www.test.lab"
ErrorLog logs/www.test.lab/error_log
CustomLog logs/www.test.lab/access_log combined
</VirtualHost>
Вышеупомянутая конфигурация включает в себя только те команды, которые необходимы для сделанных предложений по защите и описанных функциональных возможностей.
В представленной конфигурации присутствуют два виртуальных хоста, поддерживаемые веб-сервером. Наполнение вышеупомянутых сайтов физически существует в каталогах /chroot/httpd/www/vhosts/www.ebank.lab и /chroot/httpd/www/vhosts/www.test.lab.
Каждый сайт имеет свои собственные журналы регистраций, которые присутствуют в следующих каталогах /chroot/httpd/usr/local/apache/logs/www.ebank.lab и /chroot/httpd/usr/local/apache/logs/www.test.lab.
Вышеупомянутые каталоги должны быть созданы перед первым запуском Apache, иначе он не будет правильно выполняться. Владельцем вышеупомянутых каталогов должен быть root:sys и права доступа должны быть установлены к 0755.
По сравнению с базовым файлом конфигурации Apache, были сделаны следующие изменения:
— было уменьшено число доступных модулей;
— Apache не раскрывает информацию о номере своей версии (директивы: ServerTokens, ServerSignature);
— процессы Apache (кроме корневого процесса) были установлены, чтобы выполняться с привилегиями уникального пользователя/группы (директивы: User, Group);
— Apache разрешает доступ только к тем каталогам, подкаталогам и файлам, которые были явно определены в файле конфигурации (директивы: Directory, Allow); все другие запросы будут отклонены по умолчанию;
— Apache регистрирует большее количество информации о HTTP-запросах.
финальные шаги
В конце, мы должны создать запускающий сценарий "apache.sh", содержание которого будет подобно следующему:
#!/bin/sh
CHROOT=/chroot/httpd/
HTTPD=/usr/local/apache/bin/httpd
PIDFILE=/usr/local/apache/logs/httpd.pid
echo -n " apache"
case "$1" in
start)
/usr/sbin/chroot $CHROOT $HTTPD ;;stop)
kill `cat ${CHROOT}/${PIDFILE}` ;;*)
echo "" echo "Usage: `basename $0` {start|stop}"
>&2 exit 64 ;;esac
exit 0
Вышеупомянутый сценарий должен быть скопирован в надлежащий каталог (зависит от специфики UNIX-системы), где по умолчанию содержатся сценарии запуска. В случае FreeBSD это каталог/usr/local/etc/rc.d.
выводы
Вышеупомянутый метод позволяет достигнуть более высокого уровня защиты веб-сервера Apache, чем тот, который предлагается в заданной по умолчанию инсталляции.
Благодаря активации только абсолютно необходимых модулей Apache, обнаружение новой уязвимости в любом из них не должно указывать на то, что сервер уязвим. Сокрытие номера версии Apache, отключение службы индексации каталогов, изменение корневой директории и ограниченная конфигурация затрудняют успешный взлом. Сhrooted среда имеет также еще одно важное преимущество — устойчивость к большому количеству эксплойтов, главным образом из-за отсутствия оболочки (/bin/sh,/bin/csh и т.д.). Даже если вторгшийся сможет выполнять произвольные команды системы, выход из chrooted среды будет настоящей проблемой.
Андрей Греков
обсуждение статьи
Сетевые решения. Статья была опубликована в номере 03 за 2004 год в рубрике save ass…