У меня есть сервер с 1 интерфейсом, подключенным к tap0
. Также клиент с 2 интерфейсами, которые имеют общедоступное подключение к Интернету (eth1
и eth2
) и туннель для интерфейса 2, чтобы я мог отправлять трафик через tap0
и будет отправлять данные через eth2
.
если я сделаю
curl ifconfig.co
Я получаю публичный IP eth1
. Если я сделаю
curl ifconfig.co --interface eth2
Я получаю публичный IP eth2
, и если я сделаю
curl ifconfig.co --interface tap0
Я получаю публичный IP сервера (он прошел через туннель, так что все в порядке).
tap0
в 192.168.0.0/24
подсеть (остальные 192.168.1.0/24
и 192.168.3.0/24
, так что никакого конфликта здесь) и я могу правильно подключиться к 192.168.0.1
, 192.168.0.22
(который является локальным IP-адресом сервера) и т. д.
Я установил в сервере роутер (192.168.0.1
) перенаправление портов, которые мне нужны, на машину по адресу 192.168.0.22
(iperf3, 80, OpenVPN и тому подобное).
Короче думаю, что до этого момента у меня все работает правильно.
Проблема возникает, когда я хочу подключиться к общедоступному IP-адресу сервера. Допустим, публичный IP-адрес 1.2.3.4
через VPN. Если я сделаю
curl 1.2.3.4
Я получаю всю необходимую информацию по мере подключения eth1
к маршрутизатору сервера, который перенаправляет его на локальный компьютер, на котором находится сервер. Но если я сделаю
curl 1.2.3.4 --interface tap0
НИЧЕГО НЕ ПРОИЗОШЛО!
Проверка клиента tap0
с tcpdump я вижу, что запрос создан
Но этот запрос никогда не достигает tap0
на сервере (проверено eth0 на сервере на предмет входящих UDP-пакетов OpenVPN, и никаких новых пакетов не поступает, когда этот создается в клиенте tap0
). Это eth0
на сервере при подключении к чему-либо еще от клиента:
Это становится расшифрованным пакетом на tap0
и само собой разумеется, что расшифрованный пакет не появляется на tap0
когда пакет UDP не появляется.
Я не знаю, что здесь происходит. Я думал, что все пакеты, которые проходят tap0
на клиенте будет отправлено на сервер без ограничений, но, похоже, это не так.
Кроме того, если я пойду на серверную машину 192.168.0.22
и выполняю curl для общедоступного IP-адреса, я снова подключаюсь к веб-серверу, и curl получает результат, поэтому у сервера нет проблем с подключением к самому себе.
Диаграмма (Не убивай меня):
Что я могу сделать, чтобы подключения к общедоступному IP-адресу моего сервера работали при пересылке tap0
?
Понял! Я думаю, что это скорее обходной путь, чем что-то другое, но он сработал так, как ожидалось.
Просто нужно было создать iptables
правило, которое изменит пункт назначения пакетов, если источник и пункт назначения соответствуют IP-адресу общедоступного сервера и IP-адресу туннеля:
iptables -t nat -A OUTPUT -s [client tap0 IP] -d [server public IP] -j DNAT --to-destination [server local IP]
И готово! Прекрасно работает с MP-TCP.
Сначала вы должны согласиться с тем, что для того, чтобы VPN оставалась подключенной, соединения от VPN-клиента к VPN-серверу должны происходить за пределами VPN.
Во-вторых, вы должны понять, что curl 1.2.3.4 --interface tap0
ничего не меняет о маршрутизации на вашем клиенте. Все, что он делает, это контролирует исходный IP-адрес пакета. Если вы подключаетесь к внешнему IP-адресу VPN-сервера, он все равно будет выходить напрямую, а не волшебным образом попасть в туннель.
Тем не мение внимательно посмотрите на свою таблицу маршрутизации, который сообщает вам, как будут проходить пакеты.
Что я могу сделать, чтобы подключения к общедоступному IP-адресу моего сервера работали при отправке через tap0?
Стандартный ответ: нет. Используйте разделенный DNS или что-то еще, чтобы, когда ваша VPN работает, вы использовали внутренние адреса.
Сложный / хакерский ответ: если все ваши клиенты основаны на Linux, вы могли бы что-то сделать с маршрутизацией и настройкой политик, чтобы трафик OpenVPN по-прежнему проходил через общедоступную сеть, а трафик не OpenVPN использовал туннель. Но это почти наверняка будет чрезвычайно сложно настроить и потребует некоторых странных сценариев. Я этого не делал и не знаю ни одного учебника.