Эта статья в пошаговом режиме покажет, как установить и
сконфигурировать Apache 1.3.x Web server так, чтобы уменьшить риск удачного проникновения в
систему, при обнаружении новых дыр в этом по праву считающимся одним из лучших Web серверов.
Функциональные возможности
Прежде чем мы начнем "защищать" Apache, мы должны определить, какие функции должен
выполнять наш сервер. На данный момент Apache используют для решения совершенно разных задач,
поэтому очень сложно написать универсальное руководство по установки
защищенного web
сервера. Именно по этому в этой статье мы будем опираться на следующие
функциональные возможности:
- Web сервер будет доступен
через Интернет;
- Будут
использоваться только статические HTML страницы
- Сервер
будет поддерживать name-based virtual hosting механизм
- Некоторые
Web
страницы будут доступны только пользователям с определенным IP адресом
- Сервер
будет записывать все Web
запросы (включая информацию о Web браузерах)
Стоит подчеркнуть, что приведенная выше модель не
поддерживает PHP, JSP, CGI или
любые другие технологии, которые дают возможность взаимодействовать с Web службами. Использование таких технологий может
серьезно повлиять на безопасность сервера. Даже маленький неприметный сценарий
может очень сильно уменьшить уровень защиты Web сервера. Почему? Прежде всего, приложения ASP/CGI могут
содержать уязвимость защиты (например SQL
injection или cross-site-scripting). Во вторых, сама технология
может быть опасной (уязвимости в PHP и Perl модулях и т.д.). Именно поэтому я настоятельно
рекомендую использовать такие технологии только, когда обойтись без них просто
невозможно.
Проектирование защиты
Одним из наиболее важных элементов любого компьютерного
проекта является проектирование защиты. Эта операция должна быть выполнена еще
до того, как проект будет закончен. Вот как мы спроектируем защиту нашего Web сервера:
- Операционная
система должна быть максимально защищена как от локальных, так и от
удаленных атак;
- Сервер
не должен предоставлять какие-либо сетевые сервисы, кроме HTTP: (80/TCP);
- Удаленный
доступ к серверу должен быть под контролем файерволла, который должен
блокировать подключения к любым другим портам, кроме 80/TCP (порт
Web
сервера);
- Apache Web server должен быть единственной
службой, запущенной в системе;
- Только
самые необходимые модули Apache
должны быть включены;
- Всякие
Web-страницы
диагностики должны быть отключены;
- Сервер
должен выдавать как можно меньше информации о себе;
- Apache Web сервер должен быть запущен
под уникальными UID/GID, которые не используются
другими процессами;
- Процесс
Apache
должен иметь ограниченный доступ к файловой системе (chrooting); и
- Никакие
оболочки командного интерпритатора не должны находиться в chroot окружении (/bin/sh, /bin/csh и т. д.).
Установка операционной системы
Перед установкой Apache мы
должны выбрать операционную систему, на которой будет работать наш Web сервер. Здесь мы имеем широкий выбор, потому что Apache может быть скомпилирован и установлен практически
на любой операционной системе. Оставшаяся часть статьи покажет, как обеспечить
высокий уровень безопасности Apache
Web сервера на ОС FreeBSD (4.7), однако описанные методы
можно применить и на других UNIX/Linux системах. Единственная операционная система,
которую я не рекомендую использовать – MS Windows – главным образом из-за
ограничений в настройке безопасности Apache.
Первым шагом в обеспечении хорошей защиты Web сервера является
улучшение/укрепление безопасности операционной системы. К сожалению, эта
тема выходит за рамки данной статьи. Однако, существует множество
статей/документов/заметок в сети по этому чрезвычайно важному вопросу.
После того как система установлена и защищена должным
образом, мы должны добавить новую группу и обычного пользователя "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 уникального пользователя/группы, которые будут
работать только с нашим Web
сервером и ни с каким другим софтом.
Подготовка Программного обеспечения
Следующий шаг – вы должны загрузить самую последнюю версию Apache Web server. Некоторые опции Apache могут быть включены только при компиляции, таким
образом очень важно скачать исходный код, а не так называемую "binary-версию".
После успешной загрузки Apache, мы должны его распаковать. Затем нам предстоит
решить, какие модули нам пригодятся, а какие нет. Короткие описания всех
модулей можно найти на http://httpd.apache.org/docs/mod/.
Модули Apache
Выбор модулей – один из наиболее важных шагов в
обеспечении хорошей защиты Apache
Web server. Мы должны руководствоваться одним хорошим
правилом: чем меньше, тем лучше. Чтобы задействовать нужные нам функциональные
возможности и обеспечить хорошую защиту, должны быть включены следующие модули:
Название модуля
|
Описание
|
httpd_core
|
Ядро Apache,
требуется при каждой установке Apache.
|
mod_access
|
Контроль доступа к каталогам сервера в зависимости от
IP-адреса или имени узла клиента.
|
mod_auth
|
Требуется, чтобы осуществлять авторизацию пользователей,
используя текстовые файлы.
|
mod_dir
|
Требуется, чтобы искать индексные файлы: "index.html", "default.html", и т. д.
|
mod_log_config
|
Обеспечивает регистрацию запросов, направляемых серверу.
|
mod_mime
|
Содержит директивы, способствующие организации на
сервере различных типов MIME.
|
Все остальные модули Apache должны быть выключены. Мы можем спокойно их
отключить, потому что они нам не понадобятся. Отключая ненужные модули, мы
предотвращаем возможность взломщика эксплуатировать уязвимость, которая была
найдена в одном из этих модулей.
Также стоит обратить внимание, что два модуля Apache (mod_autoindex и mod_info) являются наиболее опасными.
Первый модуль позволяет автоматически проиндексировать каталог и он включен по
умолчанию. Чтобы посмотреть, как он работает, введите, например, http://server_name/icons/ и если в этом
каталоге нет индексных файлов, то будет выведено содержание всего каталога.
Второй модуль, mod_info, никогда не должен быть
доступен через Интернет, потому что он показывает всю конфигурацию Web сервера 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
Chroot'им сервер
Делая следующий шаг, мы ограничим доступ процессу Apache к файловой системе. Достигнуть этой цели мы можем,
путем chroot'a главного демона Apache (httpd).
Вообще, chroot – это
создание новой структуры каталога root,
перемещение всех демонов в новый каталог и запуск надлежащих демонов в этой
новой среде. Благодаря этому, daemon (и все
порожденные им процессы) будет иметь доступ только к этой новой структуре
каталога.
Теперь создадим новую структуру каталога root (/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
Владельцем
вышеперечисленных каталогов должен быть root, и права доступа должны быть
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, чтобы сделанные нами изменения
вступили в силу.
Сейчас нам следует скопировать главную httpd программу в новое дерево каталогов со всеми
необходимыми файлами. Чтобы осуществить это, мы должны приготовить список всех
требуемых файлов. Чтобы сделать этот список, мы можем воспользоваться
следующими командами (их присутствие зависит от конкретной операционной
системы):
Команда
|
ОС
|
Описание
|
ldd
|
Все
|
Показывает динамическую зависимость исполняемых файлов
или общедоступных библиотек.
|
ktrace/ktruss/kdump
|
*BSD
|
Включает отслеживание вызовов ядра
|
sotruss
|
Solaris
|
Трассирует вызовы функций из разделяемых библиотек.
|
strace/ltrace
|
Linux
|
Отслеживает системные вызовы, которые делает программа в
процессе своей работы
|
strings
|
Все
|
Позволяет просмотреть в любом (в том чис-
ле выполнимом) файле все строки (в коде ASCII)
|
trace
|
AIX
|
Записывает выбранные системные вызовы
|
truss
|
FreeBSD, Solaris, AIX 5L, SCO Unixware
|
Трассирует системные вызовы и сигналы
|
trusc (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, следующие файлы должны быть
скопированы в новую root
директорию:
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 мы обнаружим, что следующие конфигурационные файлы
также должны присутствовать в новой среде:
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 сервер в новой среде. Для этого нам нужно
скопировать файл конфигурации 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
Если появились проблемы, я рекомендую проанализировать log файлы 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 [email protected]
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>
В представленном конфигурационном файле есть два виртуальных
хоста:
- www.ebank.lab (www.e-bank.lab)
- www.test.lab
Контент вышеупомянутых сайтов находится в следующих
каталогах:
- /chroot/httpd/www/vhosts/www.ebank.lab
- /chroot/httpd/www/vhosts/www.test.lab
Каждый сайт имеет собственные log файлы, которые находятся в следующих
каталогах:
- /chroot/httpd/usr/local/apache/logs/www.ebank.lab
- /chroot/httpd/usr/local/apache/logs/www.test.lab
Эти каталоги должны быть созданы еще до того, как вы в
первый раз запустите Apache
– иначе Apache не будет
работать корректно. Владельцем вышеупомянутых каталогов должен быть root:sys, а
права доступа должны быть 0755.
По сравнению с настройками по умолчанию, в файле
конфигурации Apache
были сделаны следующие изменения:
Число доступных/включенных модулей значительно
уменьшено
Apache
не выдает информацию о номере версии (директивы: ServerTokens, ServerSignature)
Процессы Apache (за исключением процесса root) выполняются с привилегиями
уникального пользователя/группы (директивы: 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,
выключив службу индексации каталогов, проведя операцию chroot, мы насколько это возможно затруднили
проникновение взломщику.
Ссылки
Apache HTTP Server Project
Привер
httpd.conf
Пример
apache.sh