У вас есть роутер Keenetic, поднят внешний сервер VPN и стандартными средствами Keenetic к нему подключен тунель. Статья про перенаправление трафика в зависимости от домена, а не про настройку VPN. Тем не менее, рекомендую использовать Wireguard, как самый быстрый и безопасный.
Максимально будем использовать встроенные средства Keenetic, а именно - политики доступа в интернет. Это позволит нам гибко контроллировать как способ выхода в интернет через VPN: например, для смены OpenVPN на Wireguard не придется лезть в консоль, все можно будет сделать из интерфейса, так и контроллировать какие именно устройства получат возможность использовать перенаправление в зависимости от доменного имени. В случае каких-то проблем, можно будет отключить не лазая в консоль.
-
Установить Entware, лучше во внутреннюю память роутера, но можно и на флешку. Все пакеты в памяти займут не больше 16Мб, такой объем есть на всех роутерах Keenetic. Инструкция
ВАЖНО! При маунте storage с папкой Install начинается процесс установки. Он может занять время, надо смотреть логи в "Диагностика" в интерфейсе. После установки будет доступен SSH с параметрами из логов.
Получили доступ к SSH с Entware, заходим туда.
-
opkg update opkg install mc dnsmasq-full ipset iptables
С первого раза может не установится из-за ограниченной памяти и скачивания всего сразу, можно выполнить второй раз.
Настраиваем dnsmasq в точности как описано тут:
Будем максимально использовать возможность Keenetic, доступные из интерфейса. Переходим в "Приоритеты подключений" в интерфейсе. Нам нужно создать 2 новые политики доступа. Одна будет использоваться для реального выхода в интернет через VPN, вторая - для включения перенаправления в зависимости от домена.
- Первую назовем "VPN". И настроим ее так, чтобы все устройства, подключенные к этой политике, всегда выходили в интернет только через VPN соединение. Для этого оставляем галочку только у VPN соединения.
- Вторую назовем "Domain VPN". Настроим выход в интернет как по умолчанию, через основного провайдера. В дальнейшем все устройства, которые будут подключены к этой политике будут на самом деле использовать политику "VPN" для подключения к адресам, доменные имена которых указаны в настройках dnsmasq. При подключении ко всем остальным будет использоваться стандартная политика, настроенная в "Domain VPN"
Keenetic маркирует трафик в зависимости от того, в какой группе находится устройство. Нам нужно выяснить значения маркера для групп "VPN" и "Domain VPN". Сделать это можно, добавив какие-либо устройства в эти группы (нужно знать IP адреса устройст) и посмотреть командой iptables-save | grep MARK
каким IP адресам какой -j MARK
присваивается. Например, для политики "VPN" мы увидим -j MARK --set-xmark 0xffffd00/0xffffffff
, а для "Domain VPN" -j MARK --set-xmark 0xffffd02/0xffffffff
. Запомним.
Базовые принципы работы iptables Описаны тут. Хотя есть один нюанс, не описанный в этой статье. После цепочки OUTPUT (локальный трафик) будет произведен re-routing, если были изменения в метках MARK пакета.
Создаем файл /opt/root/iptables_mangle_vpn.sh
. После создания конечно даем права на исполнение, про это не буду далее напоминать.
[ -n "$(iptables-save | grep DOMAIN_VPN)" ] && exit 0
iptables -t mangle -N DOMAIN_VPN
iptables -t mangle -A DOMAIN_VPN -j MARK --set-mark 0xffffd00
iptables -t mangle -A DOMAIN_VPN -j CONNMARK --save-mark --nfmask 0xffffffff --ctmask 0xffffffff
iptables -t mangle -A PREROUTING -p all -m mark --mark 0xffffd02 -m set --match-set unblock dst -j DOMAIN_VPN
iptables -t mangle -A OUTPUT -p udp -d 1.1.1.1 --dport 53 -j DOMAIN_VPN
iptables -t mangle -A OUTPUT -p udp -d 8.8.8.8 --dport 53 -j DOMAIN_VPN
Давайте разберемся. Скрипт будет запускаться многократно из-за нюансов работы Keenetic, он очень часто сбрасывает iptables таблицы к исходному состоянию по своим внутренним причинам. Поэтому проверяем, существует ли наша цепочка в правилах. Меняем таблицу mangle. Наша задача - пометить пакеты, которые в группе "Domain VPN" и которые идут по указанному в настройках dnsmasq доменному имени, меткой от группы "VPN", чтобы роутинг таких пакетов пошел по пути "VPN". Итак, ловим пакеты, которые
-p all
- любой протокол-m mark --mark 0xffffd02
- инициатор пакета находится в группе "Domain VPN"-m set --match-set unblock dst
- IP адрес назначения соответствует списку IP адресов "unblock". Этот ipset будет постоянно обновляться нашим DNS сервером на лету.- Дополнительно ловим DNS запросы из
OUTPUT
. Это локально сгенерированные DNS запросы от dnsmasq. Транзитные DNS запросы, например, если у клиента используется DNS сервер8.8.8.8
- пойдут без VPN.
Все пакеты, соответствующие этим условиям помечаем меткой от группы "VPN". Соответственно, на этапе роутинга эти пакеты пойдут по пути, определенному политикой "VPN", то есть через наше VPN подключение.
Теперь этот скрипт можно запустить вручную и проверить работу. Если что-то не так - можно перезагрузить роутер. В автозагрузку добавлять только после того как все протестировано! Для добавления в автозагрузку (формально это не совсем автозагрузка, скрипт вызывается роутером в момент очистки и перезагрузки определенной таблицы iptables, таблица nat и mangle перезагружается роутером многократно) создадим файл /opt/etc/ndm/netfilter.d/iptables_mangle_vpn_reload.sh
с содержимым:
#!/bin/sh
[ "$type" == "ip6tables" ] && exit 0 # check the protocol type in backward-compatible way
[ "$table" == "mangle" ] || exit 0 # check the table name
logger "iptables $table reloaded: load /opt/root/iptables_mangle_vpn.sh"
/opt/root/iptables_mangle_vpn.sh
Полезное для диагностики:
iptables-save | grep DOMAIN_VPN
- покажет все добавленные вами правила