Назад | Перейти на главную страницу

DNAT от localhost (127.0.0.1)

Я хотел бы настроить TCP DNAT с 127.0.0.1, порт 4242 на 11.22.33.44, порт 5353 в Linux 3.x (в настоящее время 3.2.52, но при необходимости я могу обновить).

Похоже, простая настройка правила DNAT не работает, telnet 127.0.0.1 4242 висит на минуту в Trying 127.0.0.1..., а затем истекает время ожидания. Возможно, это потому, что ядро ​​отбрасывает возвращаемые пакеты (например, SYN + ACK), потому что считает их марсианскими. Мне не нужно объяснять, почему простое решение не работает, мне нужно решение, даже если оно сложное (например, оно связано с созданием правил майских правил).

Я мог бы настроить обычный DNAT с другого локального IP-адреса за пределами 127.0.0.0/8 сеть, но теперь мне нужно 127.0.0.1 в качестве адреса назначения. Я знаю, что могу настроить процесс переадресации портов на уровне пользователя, но теперь мне нужно решение, которое можно настроить с помощью iptables и не требует вспомогательных процессов.

Я гуглил об этом в течение часа. Его спрашивали несколько раз, но я не мог найти никаких рабочих решений.

Также есть много вопросов по DNAT to 127.0.0.1, но мне это не нужно, мне нужно наоборот.

Обратите внимание, что сингл iptables -j REDIRECT правило не сработает, потому что мне нужно изменить IP-адрес исходящего пакета с 127.0.0.1 на 11.22.33.44, и -j REDIRECT не может изменить IP-адрес.

Это работает для меня, маршрутизация трафика от localhost:8081 к 172.17.0.1:80, где 172.17.0.1 это veth за интерфейсом моста с именем docker0.

sysctl -w net.ipv4.conf.docker0.route_localnet=1
iptables -t nat -A OUTPUT -o lo -p tcp -m tcp --dport 8081 -j DNAT --to-destination 172.17.0.1:80
iptables -t nat -A POSTROUTING -o docker0 -m addrtype --src-type LOCAL --dst-type UNICAST -j MASQUERADE

Ключевым элементом головоломки является MASQUERADE правило.

Дальнейшее вдохновение:

Вам нужно будет запустить следующие три команды, чтобы он заработал:

iptables -t nat -A OUTPUT -p tcp -d 127.0.0.1 --dport 4242 -j DNAT --to 11.22.33.44:5353
sysctl -w net.ipv4.conf.eth0.route_localnet=1
iptables -t nat -A POSTROUTING -p tcp -s 127.0.0.1 -d 11.22.33.44 --dport 5353 -j SNAT --to $your-eth0-ip

Вот подробное объяснение.

Первая команда выполнит DNAT, как ожидалось. Однако, если вы попытаетесь захватить пакет только с этим набором правил, вы ничего не получите:

tcpdump -i any -n port 5353

Это связано с тем, что ядро ​​linux по умолчанию отбрасывает этот тип пакета, если пакет имеет 127.0.0.0/8 как один конец, и внешний IP-адрес как другой конец.

Вторая команда изменяет параметр ядра, чтобы этот тип пакета проходил (конечно, вы должны изменить eth0 соответственно). После этого, когда вы захватите пакет на eth0, вы увидите отправленные пакеты, но с адресом источника 127.0.0.1 и адрес назначения 11.22.33.44. Независимо от того, сможет ли этот пакет достичь целевого сервера или нет (промежуточные маршрутизаторы сбросят этот пакет), этот пакет не может вернуться. Итак, вы должны добавить SNAT правило, чтобы изменить исходный адрес на ваш eth0. И теперь должно работать.

Вам это нужно? Перенаправление порта iptables не работает для localhost

iptables -t nat -I OUTPUT -p tcp -d 127.0.0.1 --dport 443 -j REDIRECT --to-ports 8080

Адриан