В прошлой статье мы разбирали, как анонимизировать весь Интернет-трафик одного хоста. Теперь давайте повысим уровень безопасности, обернув всю локальную сеть VPN-ом. При этом мы избавимся от опасности выйти в интернет с еще не настроенного девайса и ассоциировать адрес своего провайдера с этим устройством.

Для этой цели можно просто настроить VPN-клиент на шлюзе, если это позволяет роутер. Но такое решение черевато последствиями в виде уменьшения скорости работы Интернета, повышенной нагрузки на роутер, к тому же некоторые клиенты отправляют весь трафик через основное соединение сразу же в случае отключения от VPN. Не стоит забывать, что даже ведущие VPN-провайдеры не могут обеспечить 100% аптайм своих серверов.

Итак, каковы наши цели:

  • пропускать через VPN весь без исключения исходящий трафик
  • делать это с максимально возможной скоростью
  • не зависеть от временных неполадок VPN-провайдера
  • максимум анонимности в Интернете

Подготовка


Нам нужен мощный роутер, способный шифровать трафик на высокой скорости. Он будет выступать в роли VPN-шлюза. Мы нашли замечательные мини-ПК на AliExpress, которые подошли под эту задачу: четырехъядерный Intel Celeron, нативная поддержка AES-CBC, AES-XTS, AES-GCM, AES-ICM и аж четыре RJ-45 порта. И по умолчанию на них была установлена pfSense. С ней и будем работать.

Если ваш Интернет-провайдер требует особой настройки соединения, вы можете взять еще два роутера и разделить доступ к интернету и локальную сеть, а между ними поставить VPN-шлюз. В другом случае, можете напрямую подключить провод провайдера к VPN-шлюзу, а за ним разместить ваш домашний роутер с локальной сетью. Первоначальная настройка Интернет-соединения на pfSense выходит за рамки этой статьи.

Настройка


Статья предполагает, что интернет подключен к первому порту, ваш ПК или домашняя сеть — ко второму, и что до настройки VPN вы смогли выйти в интернет.

Во избежание дальнейших проблем давайте авторизуемся у любимого VPN-провайдера и найдем инструкцию по настройке pfSense. Если ваш провайдер не предоставляет инструкцию по ручной настройке в pfSense, можно воспользоваться вот этой от моего любимого провайдера: www.expressvpn.com/support/vpn-setup/pfsense-with-expressvpn-openvpn — основная суть не изменится. Приведенная статья с картинками расписывает, как полностью настроить только что купленный роутер с pfSense.

Вот краткий чеклист настройки нового VPN-а:

  • System — Cert. Manager — CAs. Добавляем сертификат VPN CA
  • System — Cert. Manager — Certificates. Добавляем сертификат VPN сервера
  • VPN — OpenVPN — Clients. Создаем нового клиента по инструкции от VPN-провайдера
  • Interfaces — Assignment. Добавляем клиентов как интерфейсы
  • System — Routing. Проверяем что появился шлюз.
  • Firewall — NAT. Добавляем правила NAT для каждого клиента
  • Firewall — Rules — LAN. Добавляем перенаправление всего трафика из сети через Gateway
  • System — Routing. Для активного VPN-a в настройках шлюза указываем Monitor IP, пингом до которого будет проверяться работоспособность VPN-а

Перезагрузка VPN-ов осуществляется в Status — OpenVPN. Просмотр логов в Status — Package Logs — OpenVPN.

На этом этапе останавливаемся и проверяем, что доступ в интернет через VPN есть, и что при отключении от VPN доступ пропадает вовсе. Если интернета нет — где-то ошиблись, смотрим логи VPN, проверяем настройки заново. Если после отключения VPN трафик начинает идти через основной шлюз, значит накосячили в Firewall — Rules — LAN.

Теперь интересная часть. Если ваш провайдер выдает 20 Мбит в секунду, и то ночью — то на этом этапе вы уже получили локальную сеть, полностью закрытую VPN-ом, который работает с максимально возможной скоростью. Но что, если у вас канал пошире?

Масштабируемся


Настраиваем еще пару-тройку VPN клиентов для разных серверов по инструкции выше. Добавлять сертификаты CA и сервера не нужно, выбираем уже добавленные. Также не выполняем шаг с Firewall — Rules — LAN, его мы сделаем позже. Необходимое количество клиентов устанавливается эмпирическим путем по результатам замеров скорости через каждый отдельный сервер.

После того как завершили, у нас должна быть следующая картина:

— В VPN — OpenVPN — Clients созданы и активированы клиенты

VPN - OpenVPN - Clients

— В Interfaces — Assignment созданы и активированы интерфейсы для каждого клиента

Interfaces - Assignment

— В Status — OpenVPN все клиенты находятся в состоянии «up»

Status - OpenVPN

— В System — Routing появились шлюзы, и для них указаны пингуемые IP-адреса.
(Если не можете придумать, кого попинговать — откройте shodan.io и найдите все IP google)

System - Routing

Теперь зайдем в System — Routing — Gateway Groups. Нажмите Add. Укажите запоминающееся имя в Group Name.

System - Routing - Gateway Groups

Теперь обратите внимание на таблицу Gateway Priority. Группы шлюзов работают следующим образом: failover по уровням, балансировка внутри уровня. Столбец Tier указывает, в каком уровне будет использоваться данный шлюз. Простейший вариант — указываем все активные VPN-шлюзы в первом уровне. Вариант для медленного интернета — создаем двух клиентов и размещаем их на первом и втором уровне, но в этом случае будет только отказоустойчивость.

Ниже найдите Trigger Level. Это условие, при котором произойдет временное исключение шлюза из группы. Варианты кроме Member Down позволяют перестать отправлять пакеты шлюзу чуть раньше, чем он упадет полностью — по превышению порога потери пакетов и/или по высокому пингу. Пороги потерь и пинга задаются для каждого шлюза индивидуально в System — Routing — Gateway.

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

Пришло время направить трафик в новую группу шлюзов. Идем в Firewall — Rules — LAN, открываем созданное ранее правило перенаправления, спускаемся до списка со шлюзами и видим в этом списке созданную нами группу. Выбираем её, сохраняем правило и применяем изменения. Всё, теперь каждое новое соединение будет идти через новый VPN-клиент в группе.

Время тестирования: открываем api.ipify.me, отключаем кэш и keep-alive, и перезагружаем страницу. Если вы единственный пользователь в сети, на каждое обновление страницы вы должны видеть новый IP адрес, отличающийся от вашего домашнего. Если вы видите один и тот же адрес, полностью обновите страницу при помощи Ctrl+F5 (Command+Shift+R на маках), или откройте новую приватную вкладку. Если не помогло — значит где-то ошиблись в настройках группы, или не сменили шлюз в правилах фаерволла.

Теперь о плохом. К сожалению, у данного решения есть небольшой трудноуловимый баг, если использовать его перед роутером локальной сети (а не коммутатором). Рано или поздно у вас отваливается один из VPN-клиентов, срабатывает исключение его из группы, и всё хорошо до того момента, пока VPN не поднимется обратно. Так как все пользователи находятся за NAT, а VPN-роутер видит только один IP-адрес и 65 тысяч портов, со временем он ассоциирует все порты с теми VPN-клиентами, которые никогда не падали. Соответственно, как только VPN-клиент поднимается, через него не идет никакой трафик. Клиент полностью жив, через него идут пинги и некоторое стабильное количество служебного трафика, но через него не идет трафик клиентов. По идее это решалось бы сбросом таблицы соединений, и для этого даже есть галочка в настройках pfSense, но в моих исследованиях эта галочка напрочь блокировала всякий доступ к роутеру, так как клиенты начинали валиться циклично, при этом роняя только-только установленные соединения с веб-интерфейсом, что сильно затрудняло исправление проблемы. Без этой галочки при наличии более двух VPN-ов они уравновешивали себя, так что доступ хотя бы через один всегда был. В конце концов я настроил в мониторинге условие «если пять минут на интерфейсе было меньше 1000 байт трафика в секунду, сообщить мне», и в особо запущенных случаях перезагружаю зомби-VPN-клиента вручную с целью сбросить таблицу соединений.

Итак, мы получили сеть, полностью пропускаемую через несколько распределенных VPN-ов. За счет сочетания нескольких разных VPN-серверов мы не зависим от доступности каждого из них в отдельности, а скорость сети ограничена только вашим каналом за вычетом шифрования. Если вдруг вам не хватит одного роутера — их тоже можно масштабировать, но это тема для отдельной статьи.

Комментарии (21)


  1. Bonio
    09.11.2019 18:58
    +1

    Обожаю pfsense. Тоже его использую в такой связке с vpn, только без Gateway Groups.


  1. KonstantinSpb
    09.11.2019 19:08

    Обернули бы в Wireguard скорость бы была еще больше.


    1. chupasaurus
      09.11.2019 07:43

      Именно. Оптимизированная под x86_64 реализация Salsa20 вдвое быстрее RC4, что какбы намекает.


      1. Tangeman
        09.11.2019 16:18

        Основной выигрыш там за счёт того что он не user-space, а не за счёт скорости шифрования.


        1. chupasaurus
          10.11.2019 06:46

          В Windows, Android и iOS?
          От того, что в Linux он работает в виде модуля ядра — снижаются задержки, но потоковое вместо блочного шифрования даёт основную разницу, можете на вполне юзерспейсном SSH проверить.


          1. Tangeman
            10.11.2019 18:17
            +1

            Я говорил про Linux. Как дела обстоят в Windows я не в курсе, а в Android WG точно не в ядре (если без рута).

            Несколько некорректно сравнивать ssh с туннелем — потому что ssh может себе позволить шифровать длинные блоки и отправлять их одним syscall, в то время как для туннеля приходится каждый блок (обычно один пакет) обрабатывать и собирать отдельно (речь про туннель поверх UDP).

            Если очень грубо — OpenVPN вынужден каждый (почти) пакет получать из ядра (а это переключение контекста), потому что-то с ним делать и отдавать обратно в ядро (tun/tap) — итого имеем минимум два syscall на пакет не считая дополнительного копирования данных (в память процесса и из неё). Можно оптимизировать вторую часть, т.е. накапливать принятые пакеты и отдавать в tun/tap пачками после обработки, но это не всегда оптимально и возможно. Можно даже оптимизировать первую часть, получая пакеты пачками (есть для этого фишки в линухе), но всё равно оверхед будет ощутим.

            Таким образом, нагрузка на процессор очень сильно возрастает, и мы получаем естественное ограничение скорости передачи с привязкой к мощности процессора — дополнительно к скорости шифрования.

            Wireguard может позволить себе делать всё это в самом ядре, без переключения контекста, сильно сокращая накладные расходы — никаких лишних копий, никаких переключений контекста в процессе обработки потоков, не говоря уже о прямом доступе к буферам сокетов/адаптеров, таким образом значительно более эффективно используя процессор.

            Проверьте скорость шифрования AES256 (openssl speed aes) и сравните со скоростью передачи openvpn с этим же шифром — первый покажет явно не меньше 100MB/s даже на средненьком интеле (даже RPi4 дает > 60 MB/s), а вот второй загнется где-то уже в районе 10-20 MB/s (т.е. выдаст не больше 100-200 мегабит на гигабитном линке, при этом загружая процессор на 100%).


            1. mkll
              10.11.2019 21:55

              Заплюсовал бы, да увы.


  1. enzain
    09.11.2019 20:03

    и как же решается обращение к одному ресурсу с разных ипов? некоторые ресурсы ведь этого не любят


  1. fessmage
    09.11.2019 21:39

    Нераскрыт вопрос сохранения сессии при переключении по разным соединениям. Как реагируют на такое ресурсы с авторизацией, с мультимедиа, SPA сайты, интернет банки?


    Если dest адрес привязывается к конкретному соединению — то должно быть всё хорошо, но без ускорения. А без привязки — быстро и с багами на сайтах.


  1. pprometey
    09.11.2019 11:03
    +1

    Зачем pfSense, когда есть OPNsense?


    1. pprometey
      09.11.2019 11:04

      Это решение на мой взгляд предпочтительнее использовать дня таких целей


      1. anatol_pustivahili
        11.11.2019 20:31

        Вообще на мой взгяд лучше всего использовать голый пакетный фильтр PF в OpenBSD, без гуев вида pfsense.


        1. pprometey
          12.11.2019 05:03

          Лучше — с какой точки зрения?


          1. anatol_pustivahili
            12.11.2019 11:05

            Когда настраиваешь pf то начинаешь понимать как все работает, что где запрещено — разрешено, меньше риска что все поломается из за какого то обновления для гуев потому что их нет, рулить двумя или тремя текстовыми конфигами гораздо проще чем перемещаться по 10 вклдакам и еще 10 подвкладкам. Вообще каждому удобнее так как требует ситуация, для быстрого старта работы конечно pfsense или opnsense подойдут лучше всего, но если не пожалеть время и подготовить брандмауэр построенный на pf в ручную, то это время не пройдет зря точно, совсем по другому посмотришь на гуевы решения. В общем нужно только попробовать а понимание что удобнее, безопаснее, стабильнее придет.


  1. mxms
    09.11.2019 13:39
    +1

    OpenVPN и "без ограничения скорости" это взаимоисключающие параграфы. Промчались годы, а он до сих пор может только в один поток данные обрабатывать.


    1. mkll
      10.11.2019 18:41

      Вижу заголовок статьи, ну-ка ну-ка, лезу внутрь — бац, а там OpenVPN. Ну что ты будешь делать. :))


      1. mxms
        10.11.2019 21:33

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


        1. mkll
          10.11.2019 21:46

          Соглашусь. Я именно про это.


      1. Duss
        11.11.2019 09:09

        Вот таже реакция, только после ну-ка ну-ка я полез сразу в комменты, а не в статью.
        Спасибо, все понятно, можно не читать)


  1. loltrol
    10.11.2019 09:46

    Хм… Это же и на сидбокс поставить можно...


  1. Darka
    10.11.2019 13:25

    Я просто сотавлю это здесь:
    multipath-tcp.org/data/MultipathTCP-netsys.pdf
    www.openmptcprouter.com