Однажды передо мной предстала задача реализации безопасного доступа из внешнего мира к внутренней корпоративной сети. На выходе из корпоративной сети стоял FreeBSD 7.0, в качестве реализации был выбран OpenVPN. В данной статье я на примере из личной практики опишу процесс создания OpenVPN сервера на системе FreeBSD, с возможностью подключения к нему удаленных пользователей (с различных операционных систем: Windows, Linux, MacOS etc.).
Настройка проводилась на системе FreeBSD версии 7.0, настройка на других версиях аналогична данной.
Адрес внутренней сети - 192.168.1.0/24
1. Установка OpenVPN, создание сертификатов и ключей
затем добавляем в файле vars к переменной export KEY_DIR=$D/keys еще каталог server (для удобства). Должно получиться так:
export KEY_DIR=$D/keys/server
Загружаем переменные в оболочку:
sh . ./vars
создаем каталог keys и в нем подкаталог server
mkdir -p keys/server
создаем сертификат для сервера:
chmod +x build-ca ./build-ca
Пример ввода данных:
#./build-ca Generating a 1024 bit RSA private key
writing new private key to 'ca.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) [UA]:UA State or Province Name (full name) [Kiev]:Kharkov Locality Name (eg, city) [Kiev]:Kharkov Organization Name (eg, company) [x]:server Organizational Unit Name (eg, section) []:server Common Name (eg, your name or your server's hostname) []:server Email Address [root@localhost]:
Затем создаем сертификат X.509 для сервера. Всё необходимо заполнить аналогично и добавить строки с указанием пароля и имени организации:
chmod +x build-key-server ./build-key-server server
#./build-key-server server Country Name (2 letter code) [UA]:UA State or Province Name (full name) [Kiev]:Kharkov Locality Name (eg, city) [Kiev]:Kharkov Organization Name (eg, company) [x]:server Organizational Unit Name (eg, section) []:server Common Name (eg, your name or your server's hostname) []:server Email Address [root@localhost]: Please enter the following 'extra' attributes to be sent with your certificate request A challenge password []: your_password An optional company name []:server
Если все пункты выполнены в строгой последовательности, то далее должно быть предложено скриптом согласиться с созданием сертификатов.
Создаём ключ для клиента:
chmod +x build-key ./build-key client
# ./build-key client Generating a 1024 bit RSA private key
writing new private key to 'client.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) [KG]:UA State or Province Name (full name) [NA]:Kharkov Locality Name (eg, city) [BISHKEK]:Kharkov Organization Name (eg, company) [OpenVPN-TEST]:server Organizational Unit Name (eg, section) []:client Common Name (eg, your name or your server's hostname) []:client Email Address [me@myhost.mydomain]:root@localhost Please enter the following 'extra' attributes to be sent with your certificate request A challenge password []:your_password An optional company name []:client
Стоит заметить, что поле organizationName должно совпадать с тем, которое мы ввели при создании сертификата сервера. В нашем случае это будет имя server.
Создаем ключ Диффи-Хелмана (необходим для безопасной авторизации двух сторон):
chmod +x build-dh ./build-dh
выходим из sh:
exit
Создаем ключ для tls-аутентификации:
openvpn --genkey --secret keys/server/ta.key
создаем каталоги для нашего openvpn-сервера:
cd /usr/local/etc/ mkdir openvpn cd openvpn/ mkdir keys mkdir ccd
Переходим в каталог /usr/local/etc/openvpn/keys и копируем в него необходимые для сервера ключи и сертификаты:
Когда сертификаты и ключи созданы, переходим к настройке OpenVPN-сервера.
2. Настройка сервера
в каталоге /usr/local/etc/openvpn создаем файл конфигурации нашего openvpn-сервера
touch server.conf
#указываем порт, на котором будет работать наш сервер port 2000 # протокол будет использоваться udp (по идее он работает быстрее чем tcp) proto udp # используемый тип устройства и номер dev tun0 #указываем файл CA ca /usr/local/etc/openvpn/keys/ca.crt #указываем файл с сертификатом сервера cert /usr/local/etc/openvpn/keys/server.crt #указываем файл с ключем сервера key /usr/local/etc/openvpn/keys/server.key #указываем файл Диффи Хельман dh /usr/local/etc/openvpn/keys/dh1024.pem
#задаем виртуальный IP-адрес сервера и маску подсети, которые будут использоваться в нашем туннеле между сервером и удаленным клиентом server 10.0.0.0 255.255.255.0
#указываем клиенту маршрут к серверу по виртуальному интерфейсу push "route 10.0.0.0 255.255.255.0"
# указываем где хранятся файлы с настройками клиентов client-config-dir ccd
# включаем TLS аутентификацию tls-server # указываем tls-ключ, и указываем 0 для сервера, а 1 для клиента tls-auth keys/ta.key 0 # таймаут до реконекта tls-timeout 120 auth MD5 # включаем шифрацию пакетов с использованием алгоритма симметричного шифрования Blowfish. Пока не было известно ни одно случая взлома данного алгоритма + он быстрее DES cipher BF-CBC
#указывем, что каждые 10 секунд пинговать удаленный хост, и в случае если, в течении 120 секунд не будет ответа - то разрывать соединение keepalive 10 120
#по умолчанию используется аутентификация пользователей по файлам сертификатов, то есть пользователь у себя хранит файлы сертификатов, соответственно пароль в таком случае не используется. На мой взгляд это не совсем безопасно (т.к. если кому-то удастся заполучить эти сертификаты, то он легко сможет получить доступ к нашей корпоративной сети). Я решил добавить к аутентификации по сертификатам еще и аутентификацию по паролю. Будет использоваться пара логин/пароль пользователя в системе FreeBSD ( которого необходимо заранее создать). Для добавления аутентификации по паролю подключаем плагин openvpn-auth-pam (который обычно идет вместе с пакетом OpenVPN):
plugin /usr/local/lib/openvpn-auth-pam.so login
user nobody group nobody # Не перечитывать ключи после получения # SIGUSR1 или ping-restart persist-key # Не закрывать и переоткрывать TUN\TAP # устройство, после получения # SIGUSR1 или ping-restart persist-tun # логирование (не забудьте создать дирректорию /var/log/openvpn/) status /var/log/openvpn/openvpn-status.log log /var/log/openvpn/openvpn.log # Уровень информации для отладки verb 3
затем создаем в каталоге ccd файл с настройками удаленного клиента (имя файла должно строго совпадать с именем сертификата, то есть в нашем случае это имя client) следующего содержания:
push "route 192.168.1.0 255.255.255.0"
это сделано для того, чтобы когда пользователь подключался к нашему серверу, ему автоматически прописывался марштрут к внутренней офисной сети, которая находится за сервером.
добавляем в файл /etc/rc.conf следующие строчки, для атоматического запуска openvpn-сервера при загрузке системы
Если у вас стоит фаервол, то не забудьте открыть в нем порт. У меня стоит pf, я добавляю следующие правила:
set skip on tun0 pass in inet proto udp from any to $ext_if port 2000 keep state pass quick on tun0
Все. На этом настройка нашего сервера закончена.
3. Настройка клиента
С сервера необходимо скопировать созданные ранее сертификаты, но не все, а только необходимые пользователю, а именно: ca.crt, client.crt, client.key, dh1024.pem, ta.key.
В рабочем каталоге OpenVPN на стороне клиента создаем папку keys, куда и копируем вышеприведенные файлы. Затем создаем конфигурационный файл с любым именем, например client.ovpn, со следующим содержимым:
dev tun proto udp remote 11.11.11.11 #(вместо 11.11.11.11 необходимо указать внешний IP вашего сервера) port 2000 #(порт к которому устанавливать соединение) client resolv-retry infinite ca keys/ca.crt cert keys/client.crt key keys/client.key tls-client tls-auth keys/ta.key 1 auth MD5 auth-user-pass # команда, указывающая клиенту использовать авторизацию по паролю cipher BF-CBC ns-cert-type server comp-lzo persist-key persist-tun
#proxy 192.168.1.50:3128 #Раскомментируйте эту строчку, если вы работаете через прокси-сервер
status /var/log/openvpn/openvpn-status.log log /var/log/openvpn/openvpn.log verb 3
На этом настройка закончена. Все конфиги брались с рабочего сервера. Процесс создания OpenVPN-сервера на других системах (Debian, Gentoo, Slackware, *BSD) будет аналогичен данному. Тем и хорош OpenVPN.