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

Почему некоторые правила DNAT iptables не работают до перезагрузки?

Мои правила DNAT для iptables не работают до перезагрузки. Если я перезагружаю свой сервер, все правила работают.

Описание архитектуры:

Десятки хостов (отправителей) отправляют некоторые UDP-пакеты (в одну сторону на определенный порт 9999) на мой маршрутизатор Linux. Этот маршрутизатор Linux использует iptables для пересылки этих пакетов на несколько хостов (получателей).

senderX 10.0.0.X ====> Linux-роутер с iptables ====> ReceiverY 10.0.1.Y

Маршрутизатор linux имеет две сетевые карты: eth1 10.0.0.1/24 (сторона отправителя) и eth0 10.0.1.1/24 (сторона получателя).

Настройка iptables:

iptables -t nat -A PREROUTING -s 10.0.0.2 -i eth1 -j DNAT --to-destination 10.0.1.123

Настройка сети :

ip addr show :

1: lo: <LOOPBACK,UP,LOWER_UP> mtu 16436 qdisc noqueue state UNKNOWN
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
    inet6 ::1/128 scope host
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP qlen 1000
    link/ether 54:9f:35:0a:16:38 brd ff:ff:ff:ff:ff:ff
    inet 10.0.1.1/24 brd 10.0.1.255 scope global eth0
    inet6 fe80::569f:35ff:fe0a:1638/64 scope link
       valid_lft forever preferred_lft forever
3: eth1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc mq state UP qlen 1000
    link/ether 54:9f:35:0a:16:3a brd ff:ff:ff:ff:ff:ff
    inet 10.0.0.1/24 brd 10.0.0.255 scope global eth1
    inet6 fe80::569f:35ff:fe0a:163a/64 scope link
       valid_lft forever preferred_lft forever

Симптом:

После добавления набора правил некоторые из них не работают. И с помощью tcpdump я вижу, что UDP-пакеты больше не маршрутизируются, а пакеты отклоняются.

tcpdump -n -i eth1 host 10.0.0.2
tcpdump: verbose output suppressed, use -v or -vv for full protocol decode
listening on eth1, link-type EN10MB (Ethernet), capture size 65535 bytes
16:12:58.241225 IP 10.0.0.2.56859 > 10.0.0.1.9999: UDP, length 1464
16:12:58.241285 IP 10.0.0.1 > 10.0.0.2: ICMP 10.0.0.1 udp port 9999 unreachable, length 556

Сделан анализ:

Я добавил правило для регистрации определенного отправителя, который не работает:

iptables -t nat -A PREROUTING -s 10.0.0.2 -i eth1 -j LOG --log-prefix='PREROUTING LOG :'

Но это правило ничего не регистрирует. Пакеты приходят, потому что я вижу их в tcpdump, но они не регистрируются. Также с -v в iptables, я не вижу увеличения счетчиков для этого правила.

Если я применю то же правило до того, как оно перестанет работать, у меня появятся журналы.

Вопрос:

Описанные вами симптомы соответствуют тем, которые наблюдаются при конфликте между правилом NAT и записью отслеживания соединения.

Например, когда пакет соответствует

-A PREROUTING -s 10.0.0.2 -i eth1 -j DNAT --to-destination 10.0.1.123

необходимо создать новую запись отслеживания подключения. Это сопоставит кортеж IP-адреса источника и назначения и порта на входящей стороне с аналогичным кортежем на исходящей стороне.

Не может быть существующей записи отслеживания соединения, соответствующей входящей стороне, потому что, если бы она была, она использовалась бы вместо правила. Однако после того, как IP-адрес назначения кортежа был заменен для создания кортежа для исходящей стороны, кортеж может конфликтовать с существующей записью отслеживания соединения.

Если вы установите conntrack утилита, вы можете ввести conntrack -L чтобы увидеть список существующих записей отслеживания подключений. Эта утилита также имеет функции для перечисления только записей отслеживания соединений, соответствующих определенным критериям, а также для удаления выбранных записей.

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