У тебя могут быть самые разные мотивы, чтобы пользоваться VPN: недоверенные сети, разного рода ограничения или просто разумное желание не распространять лишний раз свои данные. В этой статье я расскажу, как сделать себе личный VPN на арендованном сервере и настроить OpenVPN и stunnel таким образом, чтобы даже глубокая инспекция пакетов ничего не давала.
 

О сервисах и блокировках

Существует бесчисленное множество сервисов, которые предоставляют VPN, в том числе и бесплатные. Вот несколько причин, почему бесплатный VPN — это плохая идея.

  1. Качество. Те, кто пользовался бесплатным VPN, знают, что в большинстве случаев сервис просто ужасен: низкая скорость, постоянные обрывы. Это и неудивительно, ведь, кроме тебя, им одновременно может пользоваться еще пара сотен человек.
  2. Безопасность. Даже если качество более-менее сносное, ты не знаешь, что на самом деле происходит с твоим трафиком. Хранится и анализируется ли он, кто и в каких целях оперирует сервисом. Бесплатный сыр, как говорится…
  3. Малое количество или полное отсутствие опций и настроек: нет возможности выбрать шифр, протокол и порт. Остается только пользоваться тем, что дали.

С платными сервисами дела обстоят лучше: можно ожидать какого-то гарантированного качества и наличия настроек. Но ты все еще не можешь знать наверняка, хранятся твои логи непосредственно на сервере или нет. К тому же твоего провайдера могут заблокировать.

Великий китайский файрвол, к примеру, научили определять и блокировать трафик OpenVPN при помощи техники Deep packet inspection (DPI). На какой бы порт ты его ни прятал, будь то UDP 53 или TCP 443, в Китае просто так OpenVPN не попользуешься. Дело в том, что в режиме TLS трафик OpenVPN отличается от обычного трафика HTTPS. Если под рукой есть сниффер, в этом несложно убедиться.

TLS-трафик OpenVPN
TLS-трафик OpenVPN

А вот как выглядит обычный HTTPS.

Трафик HTTPS
Трафик HTTPS

Некоторые популярные платные VPN предоставляют средства обхода DPI, но чем больше популярность, тем больше шанс, что провайдер узнает о сервисе и сможет полностью заблокировать доступ к нему. От полной блокировки не защищен никто, но, когда используешь публичный сервис, шанс всегда выше.

 

Пара слов об OpenVPN

OpenVPN использует два канала: канал управления (control channel) и канал данных (data channel). В первом случае задействуется TLS — с его помощью ведется аутентификация и обмен ключами для симметричного шифрования. Эти ключи используются в канале данных, где и происходит само шифрование трафика.

Существуют скрипты, которые автоматизируют установку, и процесс занимает меньше времени. Но, во-первых, эти скрипты подходят только для конкретных дистрибутивов, а во-вторых, они не предоставляют выбора. Например, используют RSA и AES-CBC, когда есть поддержка ECDSA и AES-GCM. Таким образом, без знания и понимания того, как это работает, ты не сможешь подправить скрипт, чтобы он исполнялся на других системах или делал то, что ты хочешь.

 

Что такое stunnel

Stunnel — это утилита для обеспечения защищенного соединения между клиентом и сервером посредством TLS для программ, которые сами шифровать трафик не умеют. Например, можно туннелировать трафик для netcat, vnc и даже bash. В нашем случае stunnel будет использоваться для маскировки трафика OpenVPN под «чистый» TLS, чтобы его было невозможно определить посредством DPI и, следовательно, заблокировать.

Трафик, туннелируемый через stunnel, ничем не отличается от обычного HTTPS
Трафик, туннелируемый через stunnel, ничем не отличается от обычного HTTPS

С учетом того что OpenVPN использует шифрование для своего канала данных, у нас есть два варианта настройки:

  • использовать шифрование stunnel плюс шифрование канала данных OpenVPN;
  • использовать шифрование stunnel, а шифрование канала данных OpenVPN отключить.

Таким образом, в первом варианте получается два слоя: один от stunnel, второй от OpenVPN. Этот вариант позволит использовать RSA вместе с ECDSA. Недостаток в том, что тратится больше ресурсов, и второй вариант позволит этого избежать. В любом случае настройка stunnel остается неизменной.

 

Что нам понадобится

 

Провайдер VPS

Первым делом нужно выбрать провайдера, который нам предоставит виртуальный выделенный сервер (VPS). Что выбирать — дело каждого и зависит от страны и от того, сколько ты готов платить. Главная рекомендация — выбирай страну, наиболее близкую по географическому расположению, это сведет задержку к минимуму. Но, конечно, живя в Китае, покупать сервис в Индии или Пакистане смысла мало.

 

Выбор ОС

Я буду использовать RHEL 7.4. Для точного копирования команд из статьи годится и CentOS 7 (1708), так как это бесплатная и почти идентичная копия RHEL, основанная на его коде. Возможно, подойдут другие дистрибутивы, а также производные RHEL (Fedora), но пути конфигурационных файлов и версии программ могут отличаться.

 

Подготовка и первичная настройка

После покупки сервера и установки системы нам нужно попасть на сервер. Я буду делать это с помощью SSH. Вся конфигурация будет проходить в два этапа: настройка на сервере (включает в себя первичную настройку) и настройка клиентов.

После покупки, скорее всего, тебе дадут доступ по SSH с логином root и паролем. Позже лучше создать обычного пользователя, а рутовые команды выполнять после sudo -i. Нужно это в том числе для защиты от брутфорса — пользователь root общеизвестный, и при попытках брута, вероятней всего, будет использоваться именно он.

Для начала нам понадобится подключить репозиторий EPEL — пакет openvpn лежит именно там.

$ yum install -y https://dl.fedoraproject.org/pub/epel/epel-release-latest-7.noarch.rpm
$ yum update -y

На RHEL, CentOS, Fedora, OpenSUSE и, возможно, других установлен и включен по умолчанию SELinux. Проверить это можно командой getenforce или sestatus. Чтобы не нырять в дебри его настроек и спастись от возможной головной боли, мы переведем его в режим permissive. В этом режиме он будет оповещать нас о нарушениях политик безопасности, но предпринимать никаких действий не станет. Таким образом, у тебя всегда будет возможность его поизучать. Для этого нужно изменить следующую директиву в файле /etc/selinux/config:

SELINUX=permissive

Перезагружаемся и ставим необходимые пакеты:

$ yum install -y iptables-services openvpn unzip
  • iptables-services — файлы .service для управления утилитой iptables;
  • openvpn — сам сервер OpenVPN;
  • зачем нужен unzip, попробуй догадаться сам. 🙂
 

Базовая защита

Поскольку китайские боты и скрипт-киддиз не дремлют и, скорее всего, уже сейчас пробуют подобрать пароль к твоему серверу, перенесем sshd на другой порт и запретим логин от рута. Перед тем как это сделать, нужно убедиться, что в системе существует другой пользователь с доступом по SSH, или добавить нового и установить для него пароль.

$ useradd -G wheel -m eakj
$ passwd eakj

где eakj — имя пользователя. В идеале нужно использовать ключи SSH, но в этом случае обойдемся паролем. Не забудь проверить, раскомментирована ли строчка %wheel ALL=(ALL) ALL в файле /etc/sudoers. Теперь изменим следующие директивы в файле /etc/ssh/sshd_config:

Port 12222
PermitRootLogin no
PasswordAuthentication yes

Перечитаем конфиги (systemctl reload sshd), убедимся, что sshd поднялся без проблем (systemctl status sshd), и попробуем открыть дополнительную сессию SSH, не закрывая текущей.

Продолжение доступно только подписчикам

Вариант 1. Оформи подписку на «Хакер», чтобы читать все материалы на сайте

Подписка позволит тебе в течение указанного срока читать ВСЕ платные материалы сайта. Мы принимаем оплату банковскими картами, электронными деньгами и переводами со счетов мобильных операторов. Подробнее о подписке

Вариант 2. Купи один материал

Заинтересовала информация, но нет возможности оплатить подписку? Тогда этот вариант для тебя! Обрати внимание: этот способ покупки доступен только для материалов, опубликованных более двух месяцев назад.


24 комментария

  1. Antek

    08.12.2017 at 14:13

    Спасибо. Уже давно хотел поднять себе личный VPN, но смущала необходимость копаться в настройках, а сторонним скриптам доверять не хотелось.

  2. intrud3r

    10.12.2017 at 22:47

    за stunnel +
    благодарка 🙂

  3. Shenziger

    11.12.2017 at 00:29

  4. Gen

    13.12.2017 at 11:31

    Статья супер, побольше бы таких+

  5. leverage83

    14.12.2017 at 21:42

    Возникли сложности при вызове easy-rsa для сервера, есть идеи как побороть? Лог:

    # ./easyrsa build-server-full openvpn-server nopass

    Note: using Easy-RSA configuration from: ./vars
    Generating a 2048 bit RSA private key
    …………………………………………………….+++
    ………………………………….+++
    writing new private key to ‘/opt/easy-rsa-master/easyrsa3/pki/private/openvpn-se rver.key.xxVAWx4qkn’
    ——
    Using configuration from ./openssl-easyrsa.cnf
    ERROR: on line 16 of config file ‘/opt/easy-rsa-master/easyrsa3/pki/extensions.t emp’
    139801300330400:error:02001002:system library:fopen:No such file or directory:bs s_file.c:175:fopen(‘/opt/easy-rsa-master/easyrsa3/pki/index.txt.attr’,’rb’)
    139801300330400:error:2006D080:BIO routines:BIO_new_file:no such file:bss_file.c :182:
    139801300330400:error:0E078072:configuration file routines:DEF_LOAD:no such file :conf_def.c:195:
    139801300330400:error:0E079065:configuration file routines:DEF_LOAD_BIO:missing equal sign:conf_def.c:345:line 16

    Easy-RSA error:

    signing failed (openssl output above may have more detail)

    • nevalashka

      15.12.2017 at 06:06

      Время/часовой пояс проверяли?

    • mastanggt

      30.12.2017 at 18:58

      Эта проблема в том что у easy-rsa в master ветке находятся не релизы, и там бывают баги.
      Скачивайте его по другому, а именно —
      cd /tmp/ && git clone https://github.com/OpenVPN/easy-rsa && mv easy-rsa easy-rsa-master
      После этого у вас будет последняя стабильная версия easy-rsa и все заработает

      • leverage83

        03.01.2018 at 20:44

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

  6. inkognito.o

    16.12.2017 at 10:32

    жалко что MAC OS X не упомянули

  7. arifmetik

    28.12.2017 at 17:23

    OpenVPN на телефоне с Android часто теряет связь (из-за мобильного интернета). И быстро расходует батарею 🙁 Иногда сливает её в ноль за считанные часы, — не понял почему.
    Настроил ipsec (в Android есть меню для подключения искоропки) — не знаю бед. Да и автореконнект на Android радует 🙂

  8. Themistocles

    05.01.2018 at 01:25

    спасибо за статью. очень полезна

  9. dimas9009

    14.01.2018 at 09:34

    Всё конечно классно, но не всё. Ожидал что увижу в статье это после слов 443 порт…
    0. Делаем всё как в статье
    1. Покупаем доменное имя.
    2. Поднимаем на сервере NGINX + php
    3. Ставим (для примера абсолютно не имеет значения, на вкус и цвет) WordPress/Drupal etc.
    4. Ставим модули агрегаторы новостей (RSS каналы, YouTube top и т.д.)
    5. Настраиваем OpenVpn в режиме port-share 443. т.е. шарит один порт с другими программами
    6. Покупаем (или можно использовать let’s encrypt) сертификат и всё это дело настраиваем в Nginx и stunel

    Что получим на выходе вы спросите?? А вот что. Есть сайт. На нём какая-то популярная инфа (таких сейчас тысячи). Если ваш трафик начнут слушать, то первое что они увидят что вы ходите на какой-то сайт смотреть новости, а не просто заходите шлёте на некий безымянный IP SSL трафик как в данной статье =).

  10. JollyDog

    16.05.2018 at 08:27

    Спасибо, вроде настроил все как в статье, использую tunnelblick на mac os, соединение устанавливается, но после этого пропадает интернет. В чем может быть проблема? Куда копать? Спасибо.

  11. JollyDog

    16.05.2018 at 08:37

    Разобрался, неверно описал настройки в openvpn-server.conf.

    • Pumbaa

      02.06.2018 at 20:01

      @JollyDog, а можно по-подробней, в чём ошибка? Спасибо

      • Pumbaa

        02.06.2018 at 21:55

        проблема, как выяснилось, не в настройках openvpn-server.conf, а в том, что сервер не на 443 порту, потому что 443 занят https и не пускает туда ))). Спасибо @dimas9009 за мысль >>Настраиваем OpenVpn в режиме port-share 443. т.е. шарит один порт с другими программами

  12. p.r0phe.t

    28.05.2018 at 08:12

    А как быть с дисконнектом? Чтобы трафик не шел открытый при обрыве соединения?

  13. AnRoN

    04.07.2018 at 17:52

    Возможно глупый вопрос, но я не сталкивался с подобными задачами. С недавних пор решил создать ВПН, данная статья очень заинтересовала. Но по глупости при покупке и создании VPS мною в качестве ОС была выбрана Windows Server 2012 R2 (для меня Windows все-таки единственно знакомая ОС). Может кто сможет объяснить (для чайников), как то же самое развернуть под Windows?

  14. Esachello

    07.09.2018 at 15:55

    Статья хороша, но надо упомянуть что в CentOS установка stunnel должна делаться из исходников, это обезопасит от проблем с с версией openssl. Также сервис для stunnel необходимо будет добавить вручную после установки из исходников. Моя проблема решилась, я использовал связку свой VPN с stunnel и сервера для хостинга сайтов, на которых были компоненты, которые попадали под несанкционированную блокировку РКН (банили по IP запрещены ресурсы, а на этих IP размещаются еще куча ничем не повинных). Делал тунель на сервере только для этих ресурсов, основной трафик идет через провайдера. Некий симбиоз для тех кто со стороны страдает из-за блокировок.

    • skycheg

      21.09.2018 at 12:02

      А какие могуть быть проблемы с openssl? в момент генерирования ключей и сертификатов, или после?

  15. skycheg

    20.09.2018 at 13:07

    2018.09.20 16:05:38 LOG5[22]: Service [openvpn] accepted connection from 127.0.0.1:3491
    2018.09.20 16:05:38 LOG5[22]: s_connect: connected ip_address_server:443
    2018.09.20 16:05:38 LOG5[22]: Service [openvpn] connected remote server from ip_addrr_client:3492
    2018.09.20 16:05:38 LOG4[22]: CERT: Pre-verification error: self signed certificate
    2018.09.20 16:05:38 LOG4[22]: Rejected by CERT at depth=0: CN=stunnel-server
    2018.09.20 16:05:38 LOG3[22]: SSL_connect: 14090086: error:14090086:SSL routines:ssl3_get_server_certificate:certificate verify failed
    2018.09.20 16:05:38 LOG5[22]: Connection reset: 0 byte(s) sent to TLS, 0 byte(s) sent to socket

Оставить мнение

Check Also

Эхо кибервойны. Как NotPetya чуть не потопил крупнейшего морского перевозчика грузов

Российское кибероружие, построенное на утекших у АНБ эксплоитах, маскировалось под вирус-в…