Что не так с этим исходящим файерволом iptables?

Вопрос или проблема

У меня есть почтовый сервер, который я хотел бы защитить, разрешив только исходящие соединения на различных портах, которые он использует. Входящие правила работают нормально – они обрабатываются хостом ВМ.

Мне не удалось найти много информации об этом, и хотя скрипт ниже почти работает, он отбрасывает пакеты, например, для порта 993:

Mar 25 16:08:11 lorina kernel: [200590.714226] IPTables-Dropped: IN= OUT=ens18 SRC=[локальный IP здесь] DST=[удаленный IP здесь] LEN=148 TOS=0x00 PREC=0x00 TTL=64 ID=37253 DF PROTO=TCP SPT=993 DPT=14826 WINDOW=243 RES=0x00 ACK PSH FIN URGP=0

Вот скрипт. Обратите внимание, что ens19 — это интерфейс LAN (который я хотел бы оставить открытым), а ens18 — это WAN.

iptables -A OUTPUT -o lo -p all -j ACCEPT
iptables -A OUTPUT -o ens19 -p all -j ACCEPT
iptables -A OUTPUT -p icmp -j ACCEPT
iptables -A OUTPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
iptables -A OUTPUT -p tcp --dport 53 -j ACCEPT
iptables -A OUTPUT -p udp --dport 53 -j ACCEPT
iptables -A OUTPUT -p udp -m owner --uid-owner systemd-timesync -j ACCEPT

ip6tables -A OUTPUT -o lo -p all -j ACCEPT
ip6tables -A OUTPUT -p icmpv6 -j ACCEPT
ip6tables -A OUTPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
ip6tables -A OUTPUT -p tcp --dport 53 -j ACCEPT
ip6tables -A OUTPUT -p udp --dport 53 -j ACCEPT
ip6tables -A OUTPUT -p udp -m owner --uid-owner systemd-timesync -j ACCEPT

while read h; do
        ip6tables -A OUTPUT -m conntrack --ctstate NEW -d $h -j ACCEPT &> /dev/null
        iptables -A OUTPUT -m conntrack --ctstate NEW -d $h -j ACCEPT
done < /usr/local/etc/hosts-to-allow.list

while read p; do
        ip6tables -A OUTPUT -m conntrack --ctstate NEW -p tcp --dport $p -j ACCEPT
        iptables -A OUTPUT -m conntrack --ctstate NEW -p tcp --dport $p -j ACCEPT
done < /usr/local/etc/ports-to-allow.list

ip6tables -A OUTPUT -o ens18 -j LOGGING
ip6tables -A LOGGING -m limit --limit 2/min -j LOG --log-prefix "IPTables-Dropped: " --log-level 4
iptables -A OUTPUT -o ens18 -j LOGGING
iptables -A LOGGING -m limit --limit 2/min -j LOG --log-prefix "IPTables-Dropped: " --log-level 4

iptables -A OUTPUT -o ens18 -j REJECT
ip6tables -A OUTPUT -o ens18 -j REJECT

Интересная примечание

Отброшенные пакеты из этих правил могут быть нормальными, и я все еще вижу их время от времени. Объяснение этому дал пользователь Даг С на форумах поддержки Ubuntu:

Ваш пример строки журнала относится к пакету, который не является “NEW”. Вы можете определить это по флагам TCP в конце строки.

Моя лучшая догадка, что это застарелый пакет из уже закрытой и забытой TCP-сессии, иначе он бы прошел по пути RELATED,ESTABLISHED.

Это происходит довольно часто с iptables, в зависимости от вашего маршрутизатора и/или других факторов, влияющих на путешествие пакетов. Почему? Потому что для TCP соединений Linux имеет тенденцию использовать последовательность закрытия “полудуплексного” соединения, при которой любая сторона сессии может инициировать завершение соединения с помощью одной двухсторонней FIN-ACK рукопожатия (что переводит соединение в состояние CLOSE_WAIT), вместо полного четырехстороннего FIN-ACK рукопожатия.

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

На данный момент в сегодняшнем файле /var/log/syslog у меня 115 записей, заканчивающихся “RES=0x00 ACK FIN URGP=0”, и 93 из них来自我的局域网.

Я предполагаю, что ваш файл ports-to-allow.list содержит порт 993, и поэтому вы не ожидали записи журнала, которую вы процитировали. Однако обратите внимание, что вы, похоже, используете список портов для белого списка целевого порта, тогда как ваш журнал показывает 993 как исходный порт заблокированного пакета.

Ответ или решение

Вопрос об ошибках в вашем исходящем файерволе, созданном с помощью iptables, поднимает несколько важных моментов, касающихся конфигурации и назначения правил. Рассмотрим проблемы, которые могли бы вызвать сброс пакетов, а также предложим пути их устранения.

1. Структура ваших правил iptables

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

2. Логирование и анализ сбросов

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

  • Проблема с состоянием соединений: Логируемый пакет имеет флаги FIN и ACK, что говорит о попытке завершения существующего соединения. Это может означать, что ваше правило с -m conntrack --ctstate RELATED,ESTABLISHED не срабатывает, потому что пакет не соответствует условиям для установки соединения как "новое" или "связанное".

  • Порты назначения и источники: Из логов видно, что 993 — это порт источника. Вы упоминаете, что ожидаете разрешенный исходящий трафик на порты, указанные в списке, но в этом случае речь идет о трафике с порта 993 на случайный порт (14826). Поэтому рекомендуется пересмотреть список разрешенных портов и точно указать, какие порты должны быть разрешены.

3. Уявление правил

На основе представленного скрипта, несколько моментов могут быть улучшены:

  • Порядок правил: Убедитесь, что правило для установления разрешений на выходящие соединения должно располагаться прежде любых блокирующих правил. Правило с -A OUTPUT -o ens18 -j REJECT должно быть последним в вашей конфигурации, чтобы не блокировать разрешенные соединения.

  • Тест по конкретным протоколам: Убедитесь, что в вашем файле ports-to-allow.list действительно перечислены все необходимые порты, включая 993, и что в списке указаны как tcp, так и udp, если это необходимо.

4. Перепроверка netstat или ss

Чтобы понять, какие соединения активны и откуда могут приходить пакеты, используйте команды netstat или ss. Это может помочь вам диагностировать, откуда именно приходят ваши сбрасываемые пакеты и каковы их состояния.

Рекомендации по конфигурации

В результате, вам стоит учесть следующее в вашей конфигурации iptables:

# Разрешаем локалу и LAN
iptables -A OUTPUT -o lo -j ACCEPT
iptables -A OUTPUT -o ens19 -j ACCEPT

# Разрешаем ICMP
iptables -A OUTPUT -p icmp -j ACCEPT

# Установленные соединения
iptables -A OUTPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT

# Разрешаем порты DNS
iptables -A OUTPUT -p {tcp,udp} --dport 53 -j ACCEPT

# Другие необходимые порты
while read p; do
    iptables -A OUTPUT -p tcp --dport $p -j ACCEPT
done < /usr/local/etc/ports-to-allow.list

# Разрешайте необходимые диапазоны IP
while read h; do
    iptables -A OUTPUT -d $h -j ACCEPT
done < /usr/local/etc/hosts-to-allow.list

# Логирование сбросов
iptables -A OUTPUT -o ens18 -j LOG --log-prefix "IPTables-Dropped: "

# Теперь блокируем все остальное
iptables -A OUTPUT -o ens18 -j REJECT

Заключение

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

Оцените материал
Добавить комментарий

Капча загружается...