Среда виртуального хостинга (KVM):
Гость:
Ubuntu 14.04.5 LTS \n \l
Linux ari 3.8.0-29-generic #42~precise1-Ubuntu SMP Wed Aug 14 15:31:16 UTC 2013 i686 i686 i686 GNU/Linux
Хост:
Ubuntu 14.04.3 LTS \n \l
Linux host 3.13.0-74-generic #118-Ubuntu SMP Thu Dec 17 22:52:10 UTC 2015 x86_64 x86_64 x86_64 GNU/Linux
Сеть:
eth0 |----------| virbr63 eth0 |----------|
---------------| HOST |---------------------------------| ari |
11.22.33.44 |----------| 192.168.63.1 192.168.63.2 |----------|
11.22.33.44
публичный IP-адресari
это виртуальная машина (гость)HOST
это физическая машина (хост виртуальной машины)eth0
это физическая сетевая карта в HOST
virbr63
это виртуальный сетевой адаптерНа HOST есть правило iptables:
-I PREROUTING -p tcp -d 11.22.33.44 --dport 80 -j DNAT --to 192.168.63.2:8888
Скажем mydomain.com
разрешается до 11.22.33.44. ari обслуживает все HTTP-запросы, поступающие на 11.22.33.44. Вьющийся mydomain.com
работает из любого места в Интернете.
Когда я пытаюсь получить доступ mydomain.com
через HTTP от ari
, не работает (зависает curl).
Вот как выглядит неудачная попытка завивки в tcpdump (на хосте):
host$ sudo tcpdump -i virbr63 port 8888
22:03:15.541155 IP 192.168.63.2.42740 > 192.168.63.2.8888: Flags [S], seq 786111635, win 14600, options [mss1460,sackOK,TS val 1662005624 ecr 0,nop,wscale 5], length 0
22:03:15.541173 IP 192.168.63.2.42740 > 192.168.63.2.8888: Flags [S], seq 786111635, win 14600, options [mss1460,sackOK,TS val 1662005624 ecr 0,nop,wscale 5], length 0
Это повторяется каждые несколько секунд.
Вот как выглядит успешная попытка завивки (извне) в tcpdump (на хосте):
host$ sudo tcpdump -i virbr63 port 8888
21:59:10.924031 IP external.xxx.47812 > 192.168.63.2.8888: Flags [S], seq 2881442181, win 29200, options [mss 1420,sackOK,TS val 4022859071 ecr 0,nop,wscale 7], length 0
21:59:10.924339 IP 192.168.63.2.8888 > external.xxx.47812: Flags [S.], seq 1044842547, ack 2881442182, win 14480, options [mss 1460,sackOK,TS val 1661944471 ecr 4022859071,nop,wscale 5], length 0
21:59:10.968371 IP external.xxx.47812 > 192.168.63.2.8888: Flags [.], ack 1, win 229, options [nop,nop,TS val 4022859117 ecr 1661944471], length 0
21:59:10.976415 IP external.xxx.47812 > 192.168.63.2.8888: Flags [P.], seq 1:72, ack 1, win 229, options [nop,nop,TS val 4022859117 ecr 1661944471], length 71
21:59:10.976683 IP 192.168.63.2.8888 > external.xxx.47812: Flags [.], ack 72, win 453, options [nop,nop,TS val 1661944484 ecr 4022859117], length 0
21:59:10.977985 IP 192.168.63.2.8888 > external.xxx.47812: Flags [P.], seq 1:909, ack 72, win 453, options [nop,nop,TS val 1661944484 ecr 4022859117], length 908
21:59:11.025271 IP external.xxx.47812 > 192.168.63.2.8888: Flags [.], ack 909, win 243, options [nop,nop,TS val 4022859175 ecr 1661944484], length 0
21:59:11.030033 IP external.xxx.47812 > 192.168.63.2.8888: Flags [F.], seq 72, ack 909, win 243, options [nop,nop,TS val 4022859175 ecr 1661944484], length 0
21:59:11.030375 IP 192.168.63.2.8888 > external.xxx.47812: Flags [F.], seq 909, ack 73, win 453, options [nop,nop,TS val 1661944497 ecr 4022859175], length 0
21:59:11.075205 IP external.xxx.47812 > 192.168.63.2.8888: Flags [.], ack 910, win 243, options [nop,nop,TS val 4022859223 ecr 1661944497], length 0
external.xxx
это обратный DNS IP-адреса, который делает запросЭто настройка мониторинга, поэтому я ищу решение с минимальными изменениями на host
насколько возможно. Желательно без изменений на хосте, просто убедительно ari
(гость) для приема пакетов и маршрутизации ответов по сети.
Это не помогает, потому что это настройка мониторинга, и вся ее цель - проверить, работает ли 11.22.33.44:80.
Он работает (также из той же сети, 192.168.63.0/24
), но это не решает проблемы.
Я рассмотрел следующие вопросы и ответы:
Гость KVM не может подключиться к хосту, но работает наоборот
ari$ sudo sysctl -w net.ipv4.conf.eth0.accept_local=1
Это не решает проблему, не меняет вывод tcpdump.
ari$ sudo sysctl -w net.ipv4.conf.eth0.route_localnet=1
Это не решает проблему, не меняет вывод tcpdump.
ari$ sudo sysctl -w net.ipv4.conf.eth0.rp_filter=0
Это не решает проблему, не меняет вывод tcpdump.
ari
Я пробовал добавить второй сетевой интерфейс eth0:1
с IP-адресом 192.168.63.200
. Доступ 192.168.63.2:8888
из 192.168.63.200
не работает точно так же:
17:42:08.746328 IP 192.168.63.200.41676 > 192.168.63.2.8888: Flags [S], seq 3211292625, win 14600, options [mss 1460,sackOK,TS val 1744488483 ecr 0,nop,wscale 5], length 0
17:42:08.746351 IP 192.168.63.200.41676 > 192.168.63.2.8888: Flags [S], seq 3211292625, win 14600, options [mss 1460,sackOK,TS val 1744488483 ecr 0,nop,wscale 5], length 0
После ответа Купсона я нашел здесь очень похожее решение:
http://idallen.com/dnat.txt (ищите «Много клиентов - слишком много SNAT»). Оно имеет:
iptables -t nat -A POSTROUTING -s 172.16.0.0/24 -d 172.16.0.0/24 -m conntrack --ctstate DNAT -j SNAT --to 172.16.0.254
Одно из возможных решений - использовать SNAT на ХОСТЕ, чтобы изменить исходный адрес пакетов и перенаправить их обратно на виртуальную машину "ari". Это не самое производительное решение, но оно простое и достаточно хорошее для многих настроек.
# fixup chain
iptables -t nat -N fixup-snat
iptables -t nat -A fixup-snat -m conntrack --ctstate DNAT -j MASQUERADE
# please select proper network ranges and NIC names below
iptables -t nat -I POSTROUTING -s 192.168.63.0/24 -d 192.168.63.0/24 -o virbr63 -j fixup-snat
Вы можете объединить это в один iptables
Правило, для ясности предпочитаю отдельную цепочку.
Вы также должны отключить обработку пакетов iptables на интерфейсе моста:
sysctl -w net.bridge.bridge-nf-call-arptables=0
sysctl -w net.bridge.bridge-nf-call-ip6tables=0
sysctl -w net.bridge.bridge-nf-call-iptables=0
Чтобы они выжили после перезагрузки в системах Debian, отредактируйте /etc/sysctl.conf
файл или создать новый файл в /etc/sysctl.d/
каталог.