The OpenNET Project / Index page

[ новости /+++ | форум | wiki | теги | ]

Защита сетевых сервисов с помощью stunnel (stunnel tunnel ssl crypt freebsd linux pop3 http mysql auth cert)


<< Предыдущая ИНДЕКС Исправить src / Печать Следующая >>
Ключевые слова: stunnel, tunnel, ssl, crypt, freebsd, linux, pop3, http, mysql, auth, cert,  (найти похожие документы)
From: Андрей Бешков <http://onix.opennet.ru>; Date: Sun, 23 Feb 2008 17:02:14 +0000 (UTC) Subject: Защита сетевых сервисов с помощью stunnel Оригинал: http://onix.opennet.ru/content/view/34/26/ http://onix.opennet.ru/content/view/38/26/ http://onix.opennet.ru/content/view/39/26/ Инциденты с безопасностью были и, видимо, будут всегда. Не последнюю роль в этом играет изначально ошибочный дизайн многих сетевых протоколов. Большинство из них передают и принимают данные либо в открытом виде, либо с минимальным шифрованием. Криптография не стоит на месте, и постепенно некоторые протоколы обзаводятся функциями, реализующими стойкое шифрование, но, к сожалению, процесс этот идет не слишком быстро. Для подавляющего большинства разработчиков программного обеспечения вопросы безопасности создаваемого продукта стоят далеко не на первом месте. Обычно все делается по принципу "лишь бы приложение хоть как-то заработало", а потом мы уже исправим все недочеты. Обычно это "потом" растягивается на годы. И чаще всего для внедрения в уже работающий программный комплекс механизмов безопасности необходимо достаточно сильно менять не только код, но и многие идеи, лежащие в основе всего дизайна. Не каждый производитель программного обеспечения с радостью пойдет на дополнительные трудозатраты. Благодаря инициативе компании Netscape стандартом де факто для задач шифрования веб-коммуникаций стал SSL (Security Socket Layer). Первоначально он применялся для защиты данных, передаваемых с помощью HTTP. Годы активного использования в сфере веб-коммерции доказали стабильность и надежность этого решения. Таким образом, возникла защищенная версия протокола HTTP, в дальнейшем получившая название HTTPS. Вслед за этим появились протоколы IMAPS, POP3S, SMTPS, NNTPS, LDAPS. Они призваны со временем заменить своих небезопасных предков. По идее, использование SSL вместо стандартного API для работы с сетевыми сокетами должно быть довольно простым и прозрачным для приложения. На первый взгляд, нужно всего лишь заменить в исходном коде защищаемого приложения вызовы стандартных функций на их SSL-аналоги и произвести перекомпиляцию. Но не тут то было, при работе в многопоточной и многопользовательской среде приходится добавлять в свое приложение довольно много кода поддержки SSL. На данный момент в сети существует несколько библиотек, реализующих функции SSL. Самой популярной из них является OpenSSL, распространяемая по открытой лицензии. Как я говорил ранее, переделка обычной программы в SSL-версию - уже нетривиальный процесс, но на этом трудности не заканчиваются. К сожалению, настройка и установка на сервере программного обеспечения, реализующего защищенные версии протоколов, упомянутых выше, часто тоже довольно непроста. Кроме этого, иногда встречаются ситуации, когда производитель того или иного серверного или клиентского обеспечения, работающего с небезопасными протоколами, канул в Лету, не успев создать защищенных версий своих программ и оборудования. За право пользования этими разработками когда-то были заплачены лицензионные отчисления и, соответственно, отказаться от работы с ними экономически невыгодно. Иногда это сделать вообще невозможно по причине того, что ни одно из решений, предлагаемых сторонними поставщиками, не реализует нужные функции. Но чаще всего складывается ситуация, когда безопасные приложения от нового поставщика не удается встроить в устаревшее оборудование и программные среды, до сих пор используемые во многих производственных процессах и служащие нам верой и правдой. Таким образом, мы незаметно подошли к предмету нашей сегодняшней беседы. Говорить мы будем о программе Stunnel, которая позволяет защитить небезопасные сервисы. Механика действия довольно проста. Stunnel позволяет шифровать любое TCP-соединение с помощью SSL. При этом ни отправитель, ни получатель не подозревают о том, что трафик в процессе передачи по сети шифруется с помощью внешней программы. Программа работает на следующих операционных системах: * FreeBSD * NetBSD * OpenBSD * GNU/Linux * AmigaOS * BeOS * IBM AIX * Mac OS X * OpenVMS * HP NonStop(TM) Kernel * HP-UX * Plan 9 * QNX * SCO OpenServer * SGI IRIX * Solaris * Tru64, он же Digital Unix, он же DEC OSF/1 * Windows 95/98/ME/NT/2000/XP Итак, рассмотрим пример превращения небезопасных сервисов pop3, imap, smtp в их безопасные аналоги IMAPS, POP3S, SMTPS. Представим, что у нас есть сервер, функционирующий под управлением FreeBSD 4.10. Он называется freebsd410.unreal.net и доступен нашему клиенту по адресу 10.10.21.134. Кроме всего прочего, на нем работают программы dkimap, postfix, cucipop, которые и реализуют ту самую "святую троицу" протоколов. Все они принимают входящие соединения на любом сетевом интерфейсе. Postfix работает как резидентный демон, а остальные демоны запускаются с помощью inetd, как только кто-нибудь попытается присоединиться к нужным портам. Соответственно, в /etc/inetdd.conf присутствуют следующие строки: pop3 stream tcp nowait root /usr/local/libexec/cucipop cucipop -Y imap stream tcp nowait root /usr/local/libexec/dkimap4 dkimap Таким образом, картина, показываемая командой: # netstat -na | grep LISTEN выглядит следующим образом: tcp4 0 0 *.25 *.* LISTEN tcp4 0 0 *.143 *.* LISTEN tcp4 0 0 *.110 *.* LISTEN Демоны ждут входящих соединений на портах 25, 110, 143. Что означают эти номера, можно узнать, пролистав файл /etc/services. Кстати, стоит убедиться, что в этом же файле есть записи, описывающие наши будущие защищенные сервисы: imaps 993/tcp # imap4 protocol over TLS/SSL imaps 993/udp pop3s 95/tcp spop3 # pop3 protocol over TLS/SSL pop3s 995/udp spop3 smtps 465/tcp # smtp protocol over TLS/SSL (was ssmtp) smtps 465/udp При отправке сообщений почтовый клиент, умеющий работать с SSL, шифрует пакеты и передает их демону stunnel. Тот в свою очередь расшифровывает их и отдает демонам imap, pop3, smtp. А почтовые демоны в ответ на запросы отдают данные в открытом виде stunnel, который шифрует их и передает клиенту. При этом ни клиент, ни демоны не догадываются о том, что общаются друг с другом через посредника. Итак, приступаем к установке stunnel на сервер. Предварительно в систему должен быть проинсталлирован OpenSSL, так как для правильного функционирования stunnel требуются криптоалгоритмы, реализуемые именно этой библиотекой. Для FreeBSD проводить инсталляцию удобнее всего из портов. # cd /usr/ports/security/stunnel # make all install По окончании сборки будет автоматически создан поль-зователь stunnel, входящий в одноименную группу. Затем произойдет установка, и нам будет доступен stunnel версии 4.04. Сразу же после этого система начнет создавать секретный ключ и сертификат. Вы можете воспользоваться этим способом и начать отвечать на задаваемые вопросы или просто нажимать Enter и впоследствии самостоятельно создать нужные файлы. Я предпочитаю второй способ. Создаем директорию, где у нас будут храниться сертификаты и ключи. # mkdir /usr/local/etc/stunnel/certs # cd /usr/local/etc/stunnel/certs Самостоятельно создаем ключи и сертификаты со сроком действия 1 год. В связи с тем, что stunnel не умеет работать с ключами, защищенными паролями, используем опцию -nodes. # openssl req -new -x509 -days 365 -nodes -out mailserver.cert -keyout mailserver.key Generating a 1024 bit RSA private key ................++++++ ......................++++++ writing new private key to 'mailserver.key' ----- You are about to be asked to enter information that will be incorporated into your certificate request. What you are about to enter is what is called a Distinguished Name or a DN. There are quite a few fields but you can leave some blank For some fields there will be a default value, If you enter '.', the field will be left blank. ----- Country Name (2 letter code) [AU]:RU State or Province Name (full name) [Some-State]:Rostov region Locality Name (eg, city) []:Rostov-on-Don Organization Name (eg, company) [Internet Widgits Pty Ltd]:Tigrisha home Organizational Unit Name (eg, section) []:Test Lab Common Name (eg, YOUR name) []:freebsd410.unreal.net Email Address []: Обратите внимание, что для заполнения поля Common Name или CN было использовано DNS-имя сервера. Это обязательно нужно делать, иначе почтовый клиент будет постоянно возмущаться несовпадением фактического имени сервера и того, что записано в недрах сертификата. Также необходимо убедиться, что на клиентском компьютере правильно работает разрешение имени freebsd410. unreal.net. Покончив с предыдущим пунктом, устанавливаем правильные права доступа к файлам. # chmod 600 ./mailserver.cert ./mailserver.key Создаем директорию, куда демон перейдет в chroot, и устанавливаем на нее нужные права: # mkdir /var/tmp/stunnel # chown stunnel:stunnel /var/tmp/stunnel # chmod 700 /var/tmp/stunnel При запуске без параметров stunnel будет использовать файл конфигурации /usr/local/etc/stunnel/stunnel.conf. Записываем в него следующие строки: # Ключи и сертификаты cert = /usr/local/etc/stunnel/certs/mailserver.cert key = /usr/local/etc/stunnel/certs/mailserver.key # Директория, внутри которой будет работать демон chroot = /var/tmp/stunnel # Файл pid. pid = /stunnel.pid # Имя пользователя и группа, с чьими правами будет работать демон setuid = stunnel setgid = stunnel # Уровень подробности отладочных сообщений debug = 7 # Имя файла протоколирования output = /var/log/stunnel.log # Описание наших сервисов [pop3s] accept = 10.10.21.134:995 connect = 110 [imaps] accept = 993 connect = 143 [ssmtp] accept = 465 connect = 127.0.0.1:25 В описании сервисов стоит обратить особое внимание на ключевые слова accept и connect. Первое описывает адрес и порт, через который к нам и от нас будут идти зашифрованные данные, а второе, соответственно, адрес и порт для обмена расшифрованными данными с демонами. Описание обоих переменных может быть в нескольких форматах. Адрес:порт - данные принимаются и отправляются только на интерфейсе и порте с указанным адресом. В случае если адрес не указан, по необходимости будут задействованы соответствующие порты на всех доступных интерфейсах. В моем конфигурационном файле для наглядности продемонстрированы оба вида настроек. Запускаем stunnel и смотрим, что демон пишет в /var/log/stunnel.log. Должны увидеть что-то подобное: 2004.12.04 19:09:15 LOG5[2405:134598656]: stunnel 4.04 on i386-portbld-freebsd4.10 PTHREAD+LIBWRAP with OpenSSL 0.9.7d 17 Mar 2004 2004.12.04 19:09:15 LOG7[2405:134598656]: Snagged 64 random bytes from /root/.rnd 2004.12.04 19:09:15 LOG7[2405:134598656]: Wrote 1024 new random bytes to /root/.rnd 2004.12.04 19:09:15 LOG7[2405:134598656]: RAND_status claims sufficient entropy for the PRNG 2004.12.04 19:09:15 LOG6[2405:134598656]: PRNG seeded successfully 2004.12.04 19:09:15 LOG7[2405:134598656]: Certificate: /usr/local/etc/stunnel/certs/mailserver.cert 2004.12.04 19:09:15 LOG7[2405:134598656]: Key file: /usr/local/etc/stunnel/certs/mailserver.key 2004.12.04 19:09:15 LOG5[2405:134598656]: FD_SETSIZE=1024, file ulimit=957 -> 467 clients allowed 2004.12.04 19:09:15 LOG7[2405:134598656]: FD 6 in non-blocking mode 2004.12.04 19:09:15 LOG7[2405:134598656]: SO_REUSEADDR option set on accept socket 2004.12.04 19:09:15 LOG7[2405:134598656]: pop3s bound to 10.10.21.134:995 2004.12.04 19:09:15 LOG7[2405:134598656]: FD 7 in non-blocking mode 2004.12.04 19:09:15 LOG7[2405:134598656]: SO_REUSEADDR option set on accept socket 2004.12.04 19:09:15 LOG7[2405:134598656]: imaps bound to 0.0.0.0:993 2004.12.04 19:09:15 LOG7[2405:134598656]: FD 8 in non-blocking mode 2004.12.04 19:09:15 LOG7[2405:134598656]: SO_REUSEADDR option set on accept socket 2004.12.04 19:09:15 LOG7[2405:134598656]: ssmtp bound to 0.0.0.0:465 2004.12.04 19:09:15 LOG7[2405:134598656]: FD 9 in non-blocking mode 2004.12.04 19:09:15 LOG7[2405:134598656]: FD 10 in non-blocking mode 2004.12.04 19:09:15 LOG7[2406:134598656]: Created pid file /stunnel.pid Теперь нужно снова посмотреть, что нам скажет команда: # netstat -na | grep LISTEN tcp4 0 0 *.465 *.* LISTEN tcp4 0 0 *.993 *.* LISTEN tcp4 0 0 *.995 *.* LISTEN tcp4 0 0 *.25 *.* LISTEN tcp4 0 0 *.143 *.* LISTEN tcp4 0 0 *.110 *.* LISTEN Как видите, список портов, ожидающих входящие соединения, существенно увеличился. Самое время настроить почтовый клиент. В качестве подопытного кролика будет использоваться Microsoft Outlook Express 6. Первым делом будут не самолеты, о которых подумали поклонники советской эстрады, а копирование сертификата с почтового сервера и импортирование его в почтовый клиент. С первым заданием, я думаю, вы и сами справитесь. Подойдет любой способ, лишь бы файл mailserver.cert оказался на Windows-машине. В Outlook Express задействуем меню "Сервис -> Параметры", затем выбираем вкладку "Безопасность", незамедлительно жмем на кнопки "Сертификаты" и "Импортировать". После этого в списке доверенных центров сертификации должно появиться имя нашего сервера. На этом возню с сертификатом можно считать законченной. Переходим к настройке учетной записи. Тут тоже нет ничего сложного: нужно всего лишь сделать все так, как изображено на следующих снимках. После этого вся принимаемая и отправляемая почта будет шифроваться с помощью SSL, а в файле /var/log/stunnel.log будут появляться подобные надписи: 2004.12.04 22:40:01 LOG7[2406:134598656]: pop3s accepted FD=11 from 10.10.21.162:32872 2004.12.04 22:40:01 LOG7[2406:134598656]: FD 11 in non-blocking mode 2004.12.04 22:40:01 LOG7[2406:134600704]: pop3s started 2004.12.04 22:40:01 LOG5[2406:134600704]: pop3s connected from 10.10.21.162:32872 2004.12.04 22:40:02 LOG7[2406:134600704]: Relying on OpenSSL RSA Blinding. 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): before/accept initialization 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 read client hello A 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 write server hello A 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 write certificate A 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 write server done A 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 flush data 2004.12.04 22:40:02 LOG7[2406:134600704]: waitforsocket: FD=11, DIR=read 2004.12.04 22:40:02 LOG7[2406:134600704]: waitforsocket: ok 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 read client key exchange A 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 read finished A 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 write change cipher spec A 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 write finished A 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL state (accept): SSLv3 flush data 2004.12.04 22:40:02 LOG7[2406:134600704]: 3 items in the session cache 2004.12.04 22:40:02 LOG7[2406:134600704]: 0 client connects (SSL_connect()) 2004.12.04 22:40:02 LOG7[2406:134600704]: 0 client connects that finished 2004.12.04 22:40:02 LOG7[2406:134600704]: 0 client renegotiatations requested 2004.12.04 22:40:02 LOG7[2406:134600704]: 9 server connects (SSL_accept()) 2004.12.04 22:40:02 LOG7[2406:134600704]: 9 server connects that finished 2004.12.04 22:40:02 LOG7[2406:134600704]: 0 server renegotiatiations requested 2004.12.04 22:40:02 LOG7[2406:134600704]: 1 session cache hits 2004.12.04 22:40:02 LOG7[2406:134600704]: 1 session cache misses 2004.12.04 22:40:02 LOG7[2406:134600704]: 5 session cache timeouts 2004.12.04 22:40:02 LOG6[2406:134600704]: Negotiated ciphers: AES256-SHA SSLv3 Kx=RSA Au=RSA Enc=AES(256) Mac=SHA1 2004.12.04 22:40:02 LOG7[2406:134600704]: FD 12 in non-blocking mode 2004.12.04 22:40:02 LOG7[2406:134600704]: pop3s connecting 127.0.0.1:110 2004.12.04 22:40:02 LOG7[2406:134600704]: Remote FD=12 initialized 2004.12.04 22:40:02 LOG7[2406:134600704]: Socket closed on read 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL alert (write): warning: close notify 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL write shutdown (output buffer empty) 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL alert (read): warning: close notify 2004.12.04 22:40:02 LOG7[2406:134600704]: SSL closed on SSL_read 2004.12.04 22:40:02 LOG7[2406:134600704]: Socket write shutdown (output buffer empty) 2004.12.04 22:40:02 LOG5[2406:134600704]: Connection closed: 12678 bytes sent to SSL, 10178 bytes sent to socket 2004.12.04 22:40:02 LOG7[2406:134600704]: pop3s finished (0 left) Для того чтобы забирать письма с сервера, в данном примере использовался POP3S, но смею вас уверить, что IMAPS будет также надежно выполнять эту задачу. Вдоволь наигравшись с Outlook Express, я принялся тестировать все почтовые клиенты, что были под рукой. Поэтому могу смело заявить: как и ожидалось, Mozilla Thunderbird 0.6 и Ximian Evolution 2.0.2 работают с SSL вполне стабильно и быстро. Единственное нарекание стоит адресовать Kmail 1.7.1, который при использовании защищенных протоколов стал шевелиться в несколько раз медленнее, чем обычно. В частности, на получение тестового письма из 500 байт у него в среднем уходило примерно 45 секунд. The Bat, любимый многими на постсоветских просторах, тоже отлично работает в наших условиях. Тесты, описанные ниже, проводились на версии 3.0.1.33. Впрочем, думаю, что с большинством версий The Bat это тоже будет работать. Итак, для того чтобы включить ночного вампира в нашу связку, нужно установить все так же, как изображено на следующем снимке. Удивляться тому, что вместо SSL приходится выбирать TLS, не стоит. Главное, что такой подход работает. При первой попытке соединения с сервером получаем следующее предупреждение. За исключением опечаток все в нем выглядит неплохо. Первым делом жмем "Просмотреть сертификат". И убеждаемся в том, что он действительно принадлежит нам. С помощью кнопки "Добавить к доверенным" завершаем процедуру. Отныне все операции с почтой будут шифроваться с помощью этого SSL-сертификата. Ради интереса загляните в список доверенных сертификатов. На экране должно появиться что-то вроде следующего снимка. Итак, мы добились того, что данные нормально передаются по сети в защищенном виде. Теперь осталось сделать так, чтобы никто, кроме stunnel, не смог воспользоваться старыми версиями наших сервисов. Для этого нужно, чтобы стандартные демоны SMTP, POP3, IMAP принимали соединения только от 127.0.0.1. Соответственно, клиенты смогут работать с сервером только через stunnel. В случае c postfix все довольно просто: необходимо всего лишь установить переменную inet_interfaces = localhost в файле main.cf и перезапустить его. А вот с cucipop и dkimap4 есть два варианта решения проблемы. Первый - запретить входящие соединения с помощью межсетевого экрана. Второй - использовать tcp wrapper. О первом способе написано достаточно много статей, поэтому давайте посмотрим, как работать с tcp wrapper. При обнаружении нового входящего соединения inetd вызывает демона tcpd. Тот в свою очередь просматривает файл /etc/host.allow и в зависимости от адреса вызывающей стороны принимает решение о том, что делать с соединением. Если соединение проходит через этот контроль, то его передают демону, который будет в дальнейшем его обслуживать. В отличие от межсетевого экрана, который для принятия решений оперирует адресами и номерами портов, tcpd работает с адресами клиентов и именами вызываемых демонов. По умолчанию в /etc/hosts.allow описано разрешение принимать данные от любых хостов. Это нам не подходит, а значит, надо удалить или закомментировать строку ALL : ALL : allow и добавить в файл вот это: cucipop : localhost 127.0.0.1 : allow dkimap : localhost 127.0.0.1 : allow После внесения изменений все должно работать как часы. Впрочем, для достижения наилучшего эффекта никто не мешает комбинировать настройки tcpd и запреты пакетов на межсетевом экране. После всех действий данные, выдаваемые netstat, должны выглядеть так: tcp4 0 0 *.465 *.* LISTEN tcp4 0 0 *.993 *.* LISTEN tcp4 0 0 10.10.21.134.995 *.* LISTEN tcp4 0 0 127.0.0.1.25 *.* LISTEN tcp4 0 0 *.143 *.* LISTEN tcp4 0 0 *.110 *.* LISTEN После некоторого количества тестов можно понижать уровень подробности отладочных сообщений, описываемый переменной debug в файле /usr/local/etc/stunnel/stunnel.conf. Приемлемым значением будет цифра 3. Кстати, если нужно, чтобы stunnel автоматически запускался после перезагрузки машины, не забудьте переименовать /usr/local/etc/rc.d/stunnel.sh.sample в /usr/local/etc/rc.d/stunnel.sh. В случае, когда у нас есть клиент, способный самостоятельно работать с SSL, все выглядит довольно просто. А вот что делать, если такового нет? Этот и многие другие вопросы мы обсудим в следующей статье. =============== Часть 2 В первой части статьи мы говорили о том, как защищать сервисы с помощью программы stunnel. SSL-шифрование данных выполняется посредством OpenSSL. Как обычно, все, о чем шла речь, работало под управлением FreeBSD 4.10. Чтобы проверить, как эта конструкция будет жить на пятой ветке, я перенес тестовое окружение на FreeBSD 5.3. Так что теперь мы будем работать на этой платформе. Процедура установки и настройки практически ничем не отличается от того, что было описано в первой части статьи, если, конечно, следовать официально рекомендованному пути и ставить все из портов. Продолжим рассмотрение новых способов применения stunnel. На предложение шифровать http-трафик с помощью stunnel большинство читателей, cкорее всего, посмотрит на меня с некоторой долей удивления во взгляде, а кое кто, возможно, даже покрутит пальцем у виска. А ведь они частично правы. Зачем использовать внешнюю утилиту, если для этой задачи у нас есть отлично работающий Apache и mod_ssl? Но все же не Apache единым жив администратор. Во многих организациях используется Samba. Для облегчения жизни вместе с ней поставляется программа SWAT, которая позволяет управлять демонами, принтерами, правами и учетными записями пользователей с помощью веб-интерфейса. Беда в том, что в качестве веб-сервера, отображающего интерфейс управления, используется не Apache, а собственная разработка. С точки зрения экономии ресурсов такое решение вполне оправданно, ведь Apache даже в самом обглоданном состоянии все равно будет содержать в себе больше возможностей, чем нам необходимо для выполнения задачи. На первый взгляд все очень хорошо, но, к сожалению, реализация веб-сервера SWAT не поддерживает никакого шифрования. А это значит, что пароли, имена, явки, адреса конспиративных квартир и прочие секреты передаются по сети с помощью стандартного HTTP. Переносить интерфейс на Apache лениво, да и трудозатраты себя не оправдают, а взять на себя миссию переписывать SWAT для поддержки SSL рискнет тоже не каждый. Невооруженным глазом видно, что в нашем положении применение stunnel - это как раз то, что доктор прописал. Сразу после инсталляции SWAT вписываем директивы вызова в /etc/services следующим образом: swat 901/tcp # Samba web configuration tool Ну а в /etc/inetd.conf будет такая строка: swat stream tcp nowait/400 root /usr/local/sbin/swat swat Это значит, что SWAT принимает входящие соединения на порт 901. Из этой точки мы можем пойти несколькими путями. Повесить stunnel на порт 902 и соответственно на нем принимать SSL-соединения. Затем расшифровывать данные и отдавать их на порт 901. Тут снова есть варианты - запускать stunnel как отдельный демон или из inetd. Если не стоит задача жесткой экономии ресурсов, то, по моему мнению, наилучшим решением будет запуск stunnel в качестве самостоятельного демона. Так будет проще и надежнее. Ну а в следующих версиях программы возможность запуска stunnel из-под inetd, скорее всего, будет полностью удалена, потому что ей мало кто пользуется. Для приема соединений на порту 902 и передачи расшифрованных данных на порт 901 нужно дописать в конфигурационный файл /usr/local/etc/stunnel/stunnel.conf вот такие строки: [swats] accept = 902 connect = 901 Второй способ состоит в том, чтобы прикрепить swat к порту 901 на локальной петле 127.0.0.1, а stunnel на порт 901 внешних интерфейсов. Примеры методики, которой нужно придерживаться, приводились в предыдущей статье. Дальнейшая механика полностью повторяет способ номер один. Третий способ выглядит оригинальнее. Вешаем stunnel на порт 901 и при появлении входящих соединений самостоятельно, то есть без помощи inetd, запускаем SWAT. [swats] accept = 901 exec = /usr/local/bin/swat execargs = swat С воплощением в жизнь этого способа могут возникнуть проблемы. Во-первых, потому что мы работаем от имени пользователя stunnel, а значит, и SWAT будет запущен с такими же правами. Это можно обойти с помощью sudo. А вот вторая неувязка немного сложнее: после запуска сервер stunnel уходит в chroot и значит не сможет работать с файлами, находящимися за пределами /var/tmp/stunnel/. Это можно будет победить переназначением chroot для stunnel в директорию, где живет Samba. На этом можно завершить рассмотрение приемов обращения с stunnel, который работает в качестве одиночного демона и общается только с SSL-клиентами. Теперь хотелось бы продемонстрировать методику работы для случая, когда ни клиент, ни сервер не умеют работать с SSL. В качестве примера будут выбраны сервер MySQL, работающий под управлением FreeBSD, и стандартный консольный клиент MySQL под управлением Linux. Впрочем, клиент необязательно должен быть консольным, в его качестве может выступать любая программа, умеющая дружить с сервером MySQL через сеть. Схема взаимодействия будет выглядеть примерно так (см. рис. 1). На рабочей станции MySQL-клиент общается с клиентом stunnel, ждушим входящих соединений на порту 127.0.0.1:3307. Stunnel-клиент шифрует полученные данные и отдает их через сеть демону stunnel, работающему на сервере баз данных. Тот, в свою очередь, расшифровывает пакеты и передает их MySQL-серверу. Обратная цепочка работает с точностью до наоборот. Для простоты восприятия материала вместо создания нового SSL-сертификата будем использовать тот, что создали в первой статье. Сетевой адрес сервера базы данных 10.10.21.29, а рабочая станция соответственно имеет адрес 10.10.21.75. Как я уже говорил, рабочая станция у нас функционирует под ALT Linux. К сожалению, в официальном репозитарии пакетов Sysyphus хранится stunnel весьма просроченной версии. К тому же в личной переписке человек, ответственный за сборку пакета, упомянул, что не планирует обновлять его в ближайшее время. Поэтому придется проводить самостоятельную компиляцию из исходников. Берем пакет с официального сайта http://stunnel.org, распаковываем, настраиваем и собираем. Всем желающим подправить установки по умолчанию предлагается воспользоваться ключами команды configure, благо их достаточно много. # tar zxvf stunnel-4.05.tar.gz # cd stunnel-4.05 # ./configure # make all # make install Создаем пользователя, от имени которого будет работать stunnel. # adduser stunnel И, конечно же, проверяем, что из этого вышло. # id stunnel uid=502(stunnel) gid=503(stunnel) groups=503(stunnel) Не забываем про создание директорий для временных файлов и сертификатов. Плюс к этому настраиваем права доступа. Не хотелось бы, чтобы к столь важным сведениям имел доступ кто попало. # mkdir /var/tmp/stunnel # mkdir /usr/local/etc/stunnel/certs/ Затем копируем с сервера в папку клиента /usr/local/etc/stunnel/certs/ сертификат и ключ. # chown stunnel:stunnel /var/tmp/stunnel/usr/local/etc/stunnel/certs/ # chmod -R 700 /var/tmp/stunnel/usr/local/etc/stunnel/certs/ Создаем файл /usr/local/etc/stunnel/mysql-client.conf следующего содержания: cert = /usr/local/etc/stunnel/certs/mailserver.cert key = /usr/local/etc/stunnel/certs/mailserver.key chroot = /var/tmp/stunnel/ pid = /stunnel.pid setuid = stunnel setgid = stunnel debug = 7 output = /var/log/stunnel.log client = yes [mysqls] accept = 127.0.0.1:3307 connect = 10.10.21.29:3307 А на сервере соответственно создаем /usr/local/etc/stunnel/mysql-client.conf и вписываем в него вот это: cert = /usr/local/etc/stunnel/certs/mailserver.cert key = /usr/local/etc/stunnel/certs/mailserver.key chroot = /var/tmp/stunnel pid = /stunnel.pid setuid = stunnel setgid = stunnel debug = 7 output = /var/log/stunnel.log [mysqls] accept = 10.10.21.29:3307 connect = 3306 Запускаем stunnel с обеих сторон: # stunnel /usr/local/etc/stunnel/mysql-client.conf # stunnel /usr/local/etc/stunnel/mysql-server.conf Не забываем с помощью: netstat -na | grep LISTEN проверить состояние интересующих нас портов. И обязательно заглядываем в файлы протоколов /var/log/stunnel.log, дабы убедиться в отсутствии ошибок. На рабочей станции пытаемся соединиться с MySQL-сервером. И, скорее всего, получаем ошибку. # mysql -h 127.0.0.1 -P 3307 -u root -p ERROR 1130: Host 'localhost.unreal.net' is not allowed to connect to this MySQL server Дело в том, что демон stunnel после расшифровки отдает данные серверу MySQL от имени сетевого интерфейса 127.0.0.1. Соответственно, MySQL считает, что мы присоединяемся к нему с localhost. К сожалению, под FreeBSD избавиться от этого никак нельзя. Для Linux выход из ситуации есть, но о нем мы поговорим в следующей статье. Для того чтобы как-то обойти эту неприятность, добавьте пользователя Этот адрес e-mail защищен от спам-ботов. Чтобы увидеть его, у Вас должен быть включен Java-Script в таблицу users и не забудьте обновить текущие привилегии # mysql > use mysq; > INSERT INTO user VALUES ('localhost.unreal.net','root','Rw8304MH','Y','Y','Y','Y','Y','Y','Y', 'Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','Y','','' ,'','',0,0,0); > flush privileges; > quit; После этого соединение клиента MySQL с сервером должно пройти как по маслу. В принципе работа stunnel под Linux почти ничем не отличается от работы под FreeBSD. Единственная загвоздка будет в том, что вместо inetd придется использовать xinetd. Думаю, что читатель, работающий с Linux, без труда сможет самостоятельно разобраться с этими мелкими несходствами. Казалось бы, мы описали все возможные применения stunnel, но на самом деле это не так. В следующей статье поговорим о том как с помощью stunnel проводить проверку клиентских сертификатов и о том, какие выгоды это нам сулит. =============== Часть 3. Сегодня мы займемся изучением тонкостей работы механизма аутентификации stunnel с помощью SSL-сертификатов. Плюс заодно разберемся, для чего может пригодиться Windows-версия этой программы. Представим, что у нас есть сервер, на котором работает Windows 2000 Advanced Server. Хотелось бы уметь удаленно управлять сервером с двух UNIX-машин. В качестве таковых выступают рабочая станция на основе FreeBSD 5.3 и ноутбук c ALT Linux Master 2.4. Соответственно, машины имеют имена win2000.unreal.net, altlinux.unreal.net, freebsd53. unreal.net и адреса 10.10.21.46, 10.10.21.29, 10.10.21.30. Для решения поставленной задачи можно использовать несколько программ. К примеру, Citrix ICA Client, Radmin, Rdesktop, VNC. Устанавливать и настраивать на сервере Citrix или Terminal Server ради одного человека смысла нет. Radmin для UNIX в природе не существует, значит, опять пришлось бы возиться с каким-либо эмулятором. Решив не плодить сущностей без надобности, я воспользовался последним вариантом в виде VNC, так как бесплатен и существует для всех указанных платформ. Реализаций протокола VNC на свете довольно много. Наиболее известны из них RealVNC, TightVNC, t-VNC и еще несколько клонов. Некоторые, как TightVNC и t-VNC, направлены на минимизацию сетевого трафика, другие же, такие как RealVNC, - на использование шифрования. К сожалению, под Windows RealVNC не бесплатна, поэтому пришлось использовать стандартную свободную реализацию TightVNC без шифрования. Для защиты передаваемых данных, как вы уже, наверно, догадались, будет использоваться stunnel. Займемся установкой нужных пакетов на Windows-сервер. Скачиваем с сайта TightVNC: http://tightvnc.com свежий релиз программы. На момент написания статьи была актуальна версия 1.2.9. Инсталляция достаточно тривиальна: большую часть времени можно просто нажимать кнопку "Далее". Затем нужно убедиться, что был выбран следующий набор компонентов. Разрешаем стартовать серверу VNC автоматически как системному сервису. После этого получаем предупреждение об отсутствии пароля и на следующем экране вводим его. По умолчанию VNC ждет соединений на порту 5800 для стандартных клиентов и 5900 для тех, кто использует в качестве клиента браузер. Нажав кнопку "Advanced", получаем следующий диалог, с помощью которого разрешаем входящие соединения только с интерфейса локальной петли. Таким образом, получается, что на внешнем интерфейсе входящие соединения на порты 5800 и 5900 будет получать stunnel и после расшифровки передавать их на соответствующий порт локальной петли. Теперь уже можно проверить работу VNC c помощью клиента, установленного на локальной машине. Не забываем, что присоединяться надо по адресу 127.0.0.1. Если все работает, переходим к установке stunnel. Сделать это можно двумя путями: либо компилировать пакет из исходных текстов, либо взять уже готовый по адресу: http://stunnel.org/download/binaries.html. Там же не забываем взять реализацию OpenSSL для Windows. Полный пакет OpenSSL нам не нужен, необходимы лишь библиотеки libeay32.dll и libssl32.dll, скачать их можно на той же странице. Нормальным инсталлятором stunnel так до сих пор и не обзавелся, поэтому приходится делать все вручную. Кладем stunnel-4.05.exe в C:\Stunnel и добавляем туда же весь OpenSSL или скачанные dll. Затем создаем директорию C:\Stunnel\certs. На этом процедуру установки для Windows можно считать законченной. Осталось лишь настроить stunnel, но об этом позже. Установку stunnel и OpenSSL для FreeBSD и Linux мы обсуждали в первой и второй частях этой статьи, поэтому останавливаться на данном вопросе не будем. Теперь нужно поставить VNC. Для FreeBSD устанавливаем tightVNC стандартным способом из портов. К сожалению, в репозитарии пакетов ALT Linux пакет tightVNC отсутствует, поэтому ставим стандартный VNC, они все равно совместимы между собой. Пришло время создать SSL-сертификаты, с помощью которых мы будем проводить взаимную аутентификацию клиентов и сервера. Это можно сделать на любой из используемых нами платформ. Но все же стоит отметить, что под Windows выполнять подобные действия неудобно из-за бедности функционала, портированного OpenSSL. Для остальных обсуждаемых в этой статье систем процедура практически одинакова, все отличия обычно состоят в именах директорий, используемых во время работы. FreeBSD хранит исполняемый файл openssl в /usr/local/bin/openssl, а ALT Linux - в /usr/bin/openssl. Плюс к этому вспомогательный скрипт CA.pl, представляющий для нас особую важность, в первом случае лежит в директории /usr/local/openssl/misc, а во втором - внутри /var/lib/ssl/misc. Впрочем, не стоит переживать: я обязательно подробно опишу всю процедуру генерации сертификатов для обеих систем. Авторизацию с помощью сертификатов можно настроить разными путями даже внутри одной и той же системы. Итак, подход первый: создать три независимых самодельных сертификата, по одному для всех участников шифрованного туннеля. Такой способ подкупает простотой реализации, но в качестве минусов получаем невозможность, проверить подлинность сертификата через корневой сервер сертификации. Впрочем, в нашем случае это не играет особой роли. Для начала исправляем файл openssl.cnf, дабы не набирать нижеприведенные данные каждый раз заново при создании сертификата. countryName_default = RU stateOrProvinceName_default = Rostov region localityName = Rostov-on-Don 0.organizationName_default = Tigrisha Home emailAddress = e-mail Во FreeBSD openssl.cnf находится в /usr/local/openssl/, а под ALT Linux соответственно в /var/lib/ssl/. Начнем с FreeBSD. Переходим в любую удобную директорию и выполняем команды: # openssl req -nodes -new -days 365 -newkey rsa:1024 -x509 -keyout win2000key.pem -out win2000cert.pem # openssl req -nodes -new -days 365 -newkey rsa:1024 -x509 -keyout altlinuxkey.pem -out altlinuxcert.pem # openssl req -nodes -new -days 365 -newkey rsa:1024 -x509 -keyout freebsdkey.pem -out freebsdcert.pem Большинство полей в сертификате совпадают с нашими значениями по умолчанию, во время генерации сертификатов нам просто нужно нажимать "Enter". Единственное, что нужно менять, - это поле CN (Common name). Заполнять его нужно в соответствии с полным доменным именем компьютера, для которого предназначается сертификат. Таким образом, мы создали пару сертификат-ключ для всех наших машин. Теперь ключ лежит в файле с суффиксом key, а сертификат соответственно в файле с суффиксом cert. В ALT Linux все вышеприведенные команды будут иметь тот же эффект. Хотя для этой системы есть и другой способ. Чтобы изучить его, переходим в /var/lib/ssl/certs/ и выполняем команды: # make win2000.pem # make altlinux.pem # make freebsd.pem Это способ не столь удобен, как предыдущий, и требует больше ручного труда. Дело в том, что теперь ключ и сертификат каждой машины лежат вместе в одном файле. Следовательно, придется вручную разносить их по отдельным файлам. Для того чтобы системы, соединенные с помощью stunnel, могли провести аутентификацию, они должны доверять публичным сертификатам друг друга. Соответственно клиенты должны доверять сертификату сервера и наоборот. Давайте изготовим файл с доверенными сертификатами для машины win2000. Для этого объединяем сертификаты altlinuxcert.pem и freebsdcert.pem в файл trusted.pem. # cat altlinuxcert.pem freebsdcert.pem > trusted.pem Переносим файлы win2000key.pem, win2000cert.pem и trusted.pem на Windows-машину и кладем в директорию C:\Stunnel\certs\. Таким же образом на FreeBSD копируем файлы freebsd-key.pem и freebsdcert.pem, а на Linux, соответственно, altlinuxkey.pem altlinuxcert.pem. Для клиентов в качестве файла с сертификатом доверия выступает win2000cert.pem, поэтому обязательно отправляем его на обе машины и для единообразия переименовываем в trusted.pem. Также не забываем на клиентских машинах положить файлы ключа и сертификатов в /usr/local/etc/stunnel/certs/. Стоит обратить внимание на то, что vnc может работать либо самостоятельно, либо как подключаемый модуль веб-браузера. В первом случае нужно проводить аутентификацию и шифровать трафик, а во втором случае будет доступно только шифрование, потому что непонятно, как клиентский браузер сможет предъявить свой сертификат серверу. Отсюда делаем вывод, что на машине с Windows должно работать два независимых демона stunnel. Один с авторизацией, другой - без. Теперь пришло время создать конфигурационные файлы. Для Windows содержимое vnc_server.cnf выглядит так: cert = C:\stunnel\certs\win2000cert.pem key = C:\stunnel\certs\win2000key.pem CAFile = C:\stunnel\certs\trusted.pem CRLfile = C:\stunnel\certs\crl.pem debug = 7 output = C:\stunnel\stunnel.log verify = 3 [vnc] accept = 10.10.21.46:5800 connect = 127.0.0.1:5800 Конфигурация второго экземпляра stunnel, хранящаяся в vnc_server1.cnf, соответственно такова: [vnc-https] cert = C:\stunnel\certs\win2000cert.pem key = C:\stunnel\certs\win2000key.pem debug = 7 output = C:\stunnel\stunnel.log accept = 10.10.21.46:5900 connect = 127.0.0.1:5900 Теперь посмотрим, на что похожа конфигурация для FreeBSD. cert = /usr/local/etc/stunnel/certs/freebsdcert.pem key = /usr/local/etc/stunnel/certs/freebsdkey.pem CAFile = /usr/local/etc/stunnel/certs/trusted.pem CRLfile = /usr/local/etc/stunnel/certs/crl.pem chroot = /var/tmp/stunnel/ pid = /stunnel.pid setuid = stunnel setgid = stunnel debug = 7 output = /var/log/stunnel.log client = yes verify = 3 [vnc] accept = 127.0.0.1:5800 connect = 10.10.21.46:5800 Конфигурационный файл для ALT Linux выглядит так: cert = /usr/local/etc/stunnel/certs/altlinuxcert.pem key = /usr/local/etc/stunnel/certs/altlinuxkey.pem CAFile = /usr/local/etc/stunnel/certs/trusted.pem CRLfile = /usr/local/etc/stunnel/certs/crl.pem chroot = /var/tmp/stunnel/ pid = /stunnel.pid setuid = stunnel setgid = stunnel debug = 7 output = /var/log/stunnel.log client = yes verify = 3 [vnc] accept = 127.0.0.1:5800 connect = 10.10.21.46:5800 На этом можно остановиться. Перед запуском стоит обсудить особенности конфигурационных файлов, с которыми мы еще не сталкивались. CAFile - указывает, в каком файле хранятся доверенные сертификаты. CRLfile - описывает имя файла, где должны находиться отозванные сертификаты. Такая возможность полезна, к примеру, если сертификат клиента каким-либо образом попал к злоумышленнику, и теперь нам нужно заблокировать его. И, наконец, самая важная опция - verify. Она определяет, каким образом при начале соединения будут проверяться сертификаты клиента и сервера. Значением переменной должно быть число от 0 до 3. Давайте посмотрим, что значит каждое из них. * 0 - наличие и подлинность сертификатов не проверяется. Это значение по умолчанию, оно также эквивалентно слову "no". * 1 - подлинность сертификата проверяется только при наличии такового. В случае если сертификат не проходит проверку, то соединение будет разорвано. В то же время при отсутствии сертификата соединение будет разрешено. * 2 - проверяется наличие и подлинность сертификата. Если сертификат отсутствует или в результате проверки считается фальшивым, соединение разрывается. * 3 - для создания соединения требуется обязательное наличие сертификата и его присутствие в списке доверенных. Итак, разобравшись с опциями, запускаем stunnel на всех машинах и смотрим, что появляется в файлах stunnel.log под Windows. 2005.02.28 19:10:33 LOG5[776:724]: stunnel 4.05 on x86-pc-mingw32-gnu WIN32 with OpenSSL 0.9.7e 25 Oct 2004 2005.02.28 19:10:33 LOG7[776:1108]: RAND_status claims sufficient entropy for the PRNG 2005.02.28 19:10:33 LOG6[776:1108]: PRNG seeded successfully 2005.02.28 19:10:33 LOG7[776:1108]: Certificate: C:\stunnel\certs\win2000cert.pem 2005.02.28 19:10:33 LOG7[776:1108]: Key file: C:\stunnel\certs\win2000key.pem 2005.02.28 19:10:33 LOG7[776:1108]: Loaded verify certificates from C:\stunnel\certs\trusted.pem 2005.02.28 19:10:33 LOG5[776:1108]: WIN32 platform: 30000 clients allowed 2005.02.28 19:10:33 LOG7[776:1108]: FD 156 in non-blocking mode 2005.02.28 19:10:33 LOG7[776:1108]: SO_REUSEADDR option set on accept socket 2005.02.28 19:10:33 LOG7[776:1108]: vnc bound to 10.10.21.46:5800 2005.02.28 19:10:33 LOG7[776:1108]: vnc-https bound to 10.10.21.46:5900 2005.02.28 19:10:33 LOG7[776:1108]: FD 189 in non-blocking mode 2005.02.28 19:10:33 LOG7[776:1108]: SO_REUSEADDR option set on accept socket 2005.02.28 19:10:33 LOG7[776:1108]: vnc-https bound to 10.10.21.46:5900 Ну а для Linux записи в файле протокола должны выглядеть примерно так: 2005.02.28 10:26:08 LOG5[10323:16384]: stunnel 4.05 on i686-pc-linux-gnu PTHREAD with OpenSSL 0.9.7d 17 Mar 2004 2005.02.28 10:26:08 LOG7[10323:16384]: Snagged 64 random bytes from /root/.rnd 2005.02.28 10:26:08 LOG7[10323:16384]: Wrote 1024 new random bytes to /root/.rnd 2005.02.28 10:26:08 LOG7[10323:16384]: RAND_status claims sufficient entropy for the PRNG 2005.02.28 10:26:08 LOG6[10323:16384]: PRNG seeded successfully 2005.02.28 10:26:08 LOG7[10323:16384]: Certificate: /usr/local/etc/stunnel/certs/altlinuxcert.pem 2005.02.28 10:26:08 LOG7[10323:16384]: Key file: /usr/local/etc/stunnel/certs/altlinuxkey.pem 2005.02.28 10:26:08 LOG7[10323:16384]: Loaded verify certificates from /usr/local/etc/stunnel/certs/trusted.pem 2005.02.28 10:26:08 LOG5[10323:16384]: FD_SETSIZE=1024, file ulimit=1024 -> 500 clients allowed 2005.02.28 10:26:08 LOG7[10323:16384]: FD 6 in non-blocking mode 2005.02.28 10:26:08 LOG7[10323:16384]: SO_REUSEADDR option set on accept socket 2005.02.28 10:26:08 LOG7[10323:16384]: vnc bound to 10.10.21.75:3307 Думаю, всем понятно, что в протоколах системы FreeBSD будет написано примерно то же, что хранится в протоколах системы Linux. Особое внимание стоит обратить на сообщения о считывании файлов сертификатов. Теперь нужно попробовать присоединиться к серверу Windows с любой из клиентских машин с помощью программы vncviewer. Все должно пройти как по маслу. А в файлах протоколов соответственно появится что-то вроде: 2005.02.26 21:48:00 LOG7[7492:16384]: vnc accepted FD=11 from 10.10.21.29:51902 2005.02.26 21:48:00 LOG7[7492:16384]: FD 11 in non-blocking mode 2005.02.26 21:48:00 LOG7[8003:32770]: vnc started 2005.02.26 21:48:00 LOG5[8003:32770]: vnc connected from 10.10.21.29:51902 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): before/accept initialization 2005.02.26 21:48:00 LOG7[8003:32770]: waitforsocket: FD=11, DIR=read 2005.02.26 21:48:00 LOG7[8003:32770]: waitforsocket: ok 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 read client hello A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 write server hello A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 write certificate A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 write certificate request A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 flush data 2005.02.26 21:48:00 LOG7[8003:32770]: waitforsocket: FD=11, DIR=read 2005.02.26 21:48:00 LOG7[8003:32770]: waitforsocket: ok 2005.02.26 21:48:00 LOG5[8003:32770]: VERIFY OK: depth=0, /C=RU/ST=Rostov region/O=Tigrisha Home/OU=Test Lab/CN=win2000.unreal.net 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 read client certificate A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 read client key exchange A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 read certificate verify A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 read finished A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 write change cipher spec A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 write finished A 2005.02.26 21:48:00 LOG7[8003:32770]: SSL state (accept): SSLv3 flush data 2005.02.26 21:48:00 LOG7[8003:32770]: 2 items in the session cache 2005.02.26 21:48:00 LOG7[8003:32770]: 0 client connects (SSL_connect()) 2005.02.26 21:48:00 LOG7[8003:32770]: 0 client connects that finished 2005.02.26 21:48:00 LOG7[8003:32770]: 0 client renegotiatations requested 2005.02.26 21:48:00 LOG7[8003:32770]: 2 server connects (SSL_accept()) 2005.02.26 21:48:00 LOG7[8003:32770]: 2 server connects that finished 2005.02.26 21:48:00 LOG7[8003:32770]: 0 server renegotiatiations requested 2005.02.26 21:48:00 LOG7[8003:32770]: 0 session cache hits 2005.02.26 21:48:00 LOG7[8003:32770]: 0 session cache misses 2005.02.26 21:48:00 LOG7[8003:32770]: 0 session cache timeouts 2005.02.26 21:48:00 LOG6[8003:32770]: Negotiated ciphers: AES256-SHA SSLv3 Kx=RSA Au=RSA Enc=AES(256) Mac=SHA1 2005.02.26 21:48:00 LOG7[8003:32770]: FD 14 in non-blocking mode 2005.02.26 21:48:00 LOG7[8003:32770]: vnc connecting 127.0.0.1:5800 2005.02.26 21:48:00 LOG7[8003:32770]: remote connect #1: EINPROGRESS: retrying 2005.02.26 21:48:00 LOG7[8003:32770]: waitforsocket: FD=14, DIR=write 2005.02.26 21:48:00 LOG7[8003:32770]: waitforsocket: ok 2005.02.26 21:48:00 LOG7[8003:32770]: Remote FD=14 initialized 2005.02.26 21:49:09 LOG7[8003:32770]: Socket closed on read 2005.02.26 21:49:09 LOG7[8003:32770]: SSL write shutdown (output buffer empty) 2005.02.26 21:49:09 LOG7[8003:32770]: SSL alert (write): warning: close notify 2005.02.26 21:49:09 LOG7[8003:32770]: SSL_shutdown retrying 2005.02.26 21:49:09 LOG7[8003:32770]: SSL alert (read): warning: close notify 2005.02.26 21:49:09 LOG7[8003:32770]: SSL closed on SSL_read 2005.02.26 21:49:09 LOG7[8003:32770]: Socket write shutdown (output buffer empty) 2005.02.26 21:49:09 LOG5[8003:32770]: Connection closed: 229164 bytes sent to SSL, 188234 bytes sent to socket 2005.02.26 21:49:09 LOG7[8003:32770]: vnc finished (0 left) Особое внимание стоит обратить на строчку со следующими символами: VERIFY OK: depth=0, /C=RU/ST=Rostov region/O=Tigrisha Home/OU=Test Lab/CN=win2000.unreal.net Четко видно, как сертификат сервера был опознан клиентом. Соответственно, в протоколах сервера можно увидеть: VERIFY OK: depth=0, /C=RU/ST=Rostov region/O=Tigrisha Home/OU=Test Lab/CN=freebsd53.unreal.net Стоит отметить, что в случае, если файл crl.pem не будет содержать сертификатов, stunnel не запустится. Все, что мы получим, - это вот такое сообщение об ошибке: 2005.03.12 10:52:12 LOG3[5934:16384]: Error loading CRLs from /usr/local/etc/stunnel/certs/crl.pem Поэтому включайте возможность отзыва сертификатов только в том случае, если она действительно необходима. Разобравшись с авторизацией, давайте посмотрим на еще один способ создания сертификатов клиента и сервера. В составе пакета OpenSSL версий выше 0.9.6 поставляется утилита CA.pl, с помощью которой генерирование сертификатов превращается из нелегкого труда по запоминанию длинных команд в забаву. На этот раз мы поступим в соответствии со всеми правилами. Сначала создадим корневой сертификат для unreal.net, а потом с помощью него заверим все клиентские сертификаты. # /var/lib/ssl/misc/CA.pl -newca CA certificate filename (or enter to create) Making CA certificate ... Generating a 1024 bit RSA private key .....++++++ .......................................++++++ writing new private key to './demoCA/private/cakey.pem' Enter PEM pass phrase: Verifying - Enter PEM pass phrase: ----- You are about to be asked to enter information that will be incorporated into your certificate request. What you are about to enter is what is called a Distinguished Name or a DN. There are quite a few fields but you can leave some blank For some fields there will be a default value, If you enter '.', the field will be left blank. ----- Country Name (2 letter code) [AU]:RU State or Province Name (full name) [Some-State]:Rostov region Locality Name (eg, city) []:Rostov-on-Don Organization Name (eg, company) [Internet Widgits Pty Ltd]:Tigrisha home Organizational Unit Name (eg, section) []:Test Lab Common Name (eg, your name or your server's hostname) []:unreal.net Email Address []: В результате этих действий в файле cakey.pem появится секретный ключ, а в cacert.pem наш корневой сертификат. Затем создаем запрос на новый клиентский сертификат для машины altlinux.unreal.net. # /var/lib/ssl/misc/CA.pl -newreq Generating a 1024 bit RSA private key ...................................................................... .++++++ ........................................++++++ writing new private key to 'newreq.pem' Enter PEM pass phrase: Verifying - Enter PEM pass phrase: ----- You are about to be asked to enter information that will be incorporated into your certificate request. What you are about to enter is what is called a Distinguished Name or a DN. There are quite a few fields but you can leave some blank For some fields there will be a default value, If you enter '.', the field will be left blank. ----- Country Name (2 letter code) [AU]:RU State or Province Name (full name) [Some-State]:Rostov region Locality Name (eg, city) []:Rostov-on-Don Organization Name (eg, company) [Internet Widgits Pty Ltd]:Tigrisha home Organizational Unit Name (eg, section) []:Test Lab Common Name (eg, your name or your server's hostname) []:altlinux.unreal.net Email Address []: После этого во вновь созданном файле newreq.pem будет находиться секретный ключ клиента и запрос на создание сертификата. Осталось только заверить его с помощью корневого сертификата, сгенерировав таким образом новый клиентский сертификат. # /var/lib/ssl/misc/CA.pl -sign Using configuration from /var/lib/ssl/openssl.cnf 18596:error:0E06D06C:configuration file routines:NCONF_get_string:no value:conf_lib.c:329:group=CA_default name=unique_subject Enter pass phrase for ./demoCA/private/cakey.pem: Check that the request matches the signature Signature ok Certificate Details: Serial Number: 1 (0x1) Validity Not Before: Feb 8 18:39:33 2005 GMT Not After : Feb 8 18:39:33 2006 GMT Subject: countryName = RU stateOrProvinceName = Rostov region localityName = Rostov-on-Don organizationName = Tigrisha home organizationalUnitName = Test Lab commonName = altlinux.unreal.net emailAddress = e-mail X509v3 extensions: X509v3 Basic Constraints: CA:FALSE Netscape Comment: OpenSSL Generated Certificate X509v3 Subject Key Identifier: BF:01:B4:1C:AA:2C:46:8E:0B:B6:9D:70:BA:AA:D3:86:DC:8F:8A:09 X509v3 Authority Key Identifier: keyid:F8:66:F7:4E:F9:3F:7A:C7:83:BC:0C:84:40:AD:2F:3F:FC:5A:9C:AC DirName:/C=RU/ST=Rostov region/L=Rostov-on-Don/O=Tigrisha home/OU=Test Lab/CN=unreal.net/emailAddress=e-mail serial:00 Certificate is to be certified until Feb 8 18:39:33 2006 GMT (365 days) Sign the certificate? [y/n]:y 1 out of 1 certificate requests certified, commit? [y/n]y Write out database with 1 new entries Data Base Updated Signed certificate is in newcert.pem После всех этих мытарств сертификат клиента находится в файле newcert.pem. Повторяем эти шаги для остальных клиентов. При этом не стоит забывать, что в файлы newcert.pem и newreq.pem перезаписываются при каждом запуске CA.pl c ключами -sign и -newreq, отсюда следует, что после завершения цикла генерации ключа и сертификата лучше переименовывать эти файлы так, чтобы своим именем они отражали принадлежность тому или иному клиенту. К примеру, для клиента altlinux.unreal.net файлы должны называться altlinuxcert.pem и altlinuxkey.pem. Еще одно обстоятельство, о котором стоит помнить, - из файла newreq.pem после заверения сертификата лучше всего удалять запрос на сертификацию. Он начинается строкой -------BEGIN CERTIFICATE REQUEST--------- и заканчивается, соответственно ----END CERTIFICATE REQUEST----- Если этого не сделать, то некоторые версии stunnel завершаются с ошибкой при попытке работы с таким файлом. Итак, мы создали все необходимые сертификаты и поместили их в trusted.pem. Конечно, не стоит забывать, что файл trusted.pem должен быть разным для клиентов и сервера. В остальном этот способ полностью совпадает с тем, что мы протестировали выше. Вручную добавлять сертификаты в trusted.pem довольно просто, а вот удалять их потом оттуда в случае, если хочется отказать какому-либо клиенту в доступе, несколько неудобно. В системах с малым количеством клиентов это еще терпимо, а в большом вычислительном комплексе с несколькими сотнями сертификатов это может превратиться в головную боль. Поэтому давайте рассмотрим другой способ управления сертификатами. В этом случае мы будем помещать каждый сертификат в отдельный файл. Затем доверенные сертификаты кладем в директорию trusted, а отозванные - в папку crl. На клиентах и сервере создаем обе папки внутри директории certs. Затем вносим следующие изменения в конфигурационные файлы. Вместо строк CAFile и CRLfile вписываем следующее: Для ALT Linux: CRLpath = /usr/local/etc/stunnel/certs/trusted/ CApath = /usr/local/etc/stunnel/certs/crl/ Для FreeBSD вносим те же изменения, что и для ALT Linux. Для Windows: CRLpath = C:\stunnel\certs\crl\ CApath = C:\stunnel\certs\trusted\ Если опираться в своих действиях на официальную документацию к stunnel, то, сложив все доверенные сертификаты в папку trusted, можно было бы попытаться запустить демонов на сервере и клиентах и радоваться полученному результату. Но не тут то было - запуск пройдет гладко, а вот аутентификация функционировать не будет. По крайней мере, у меня таким способом вообще ничего не заработало. Все дело в том, что для совместимости со специфическими особенностями stunnel имена файлов доверенных сертификатов должны быть в особом формате. А точнее имя файла должно соответствовать хэшу, вычисленному по содержимому сертификата. Чтобы узнать хэш того или иного файла под ALT Linux, нужно выполнить следующую команду: # /var/lib/ssl/misc/c_hash / /usr/local/etc/stunnel/certs/trusted/*.pem b71698b3.0 => /usr/local/etc/stunnel/certs/trusted/win2000cert.pem Таким образом, становится понятно, что файл сертификата win2000cert.pem нужно переименовать в b71698b3.0. После того как вы проведете подобные действия на остальных машинах, можно запускать stunnel. Стоит отметить, что во FreeBSD утилита c_hash будет находиться в директории /usr/local/openssl/misc. Также необходимо обратить внимание на тот факт, что для Windows в стандартной поставке openssl программа c_hash отсутствует. Поэтому хэши ключей нужно будет вычислять на Linux или FreeBSD. Единственное различие будет в том, что в файл протокола при старте записываются следующие сообщения, касающиеся доверенных сертификатов. 2005.03.14 11:19:03 LOG7[7068:16384]: Verify directory set to /usr/local/etc/stunnel/certs/trusted/ 2005.03.14 11:19:03 LOG5[7068:16384]: Peer certificate location /usr/local/etc/stunnel/certs/trusted/ В остальном работа системы будет выглядеть точно так же, как если бы доверенные сертификаты хранились в одном файле. Думаю, на этом можно считать тему аутентификации клиентов stunnel с помощью сертификатов исчерпанной. А значит, подошла к концу и эта серия статей.

<< Предыдущая ИНДЕКС Исправить src / Печать Следующая >>

Обсуждение [ RSS ]
  • 1, sNeo (??), 17:55, 27/07/2011 [ответить]  
  • +/
    Спасибо тебе добрый человек
     
  • 2, BBher (?), 00:47, 05/08/2015 [ответить]  
  • +/
    Храни тебя господь
     

    игнорирование участников | лог модерирования

     Добавить комментарий
    Имя:
    E-Mail:
    Заголовок:
    Текст:




    Партнёры:
    PostgresPro
    Inferno Solutions
    Hosting by Hoster.ru
    Хостинг:

    Закладки на сайте
    Проследить за страницей
    Created 1996-2024 by Maxim Chirkov
    Добавить, Поддержать, Вебмастеру