Основные понятия iptables в Linux

27 декабря, 2011 Рубрики: Linux, netfilter/iptables, основы Linux

фаервол в LinuxДоброго времени, читатели и гости моего блога. C этой статьи начну серию статей о подсистеме Netfilter/iptables в Linux. В данной статье приведу основные понятия работы netfilter в Linux. Для понимания данной темы, обязательно советую ознакомиться со статьями Основные понятия сетей, Настройка сети в Linux, диагностика и мониторинг и Настройка и управление сетевой подсистемой Linux (iproute2).

Введение и история

Netfilter — межсетевой экран (он же, брандмауэр, он же файерволл, он же firewall…) встроен в ядро Linux с версии 2.4. Netfilter управляется утилитой iptables (Для IPv6 — ip6tables). До netfilter/iptables был Ipchains, который входил в состав ядер Linux 2.2. До ipchains в Linux был так называемый ipfw (IPV4 firewal), перенесенный из BSD. Утилита управления – ipfwadm. Проект netfilter/iptables был основан в 1998. Автором является Расти Расселл (он же руководил и прошлыми разработками). В 1999 г. образовалась команда Netfilter Core Team (сокращено coreteam). Разработанный межсетевой экран получил официальное название netfilter. В августе 2003 руководителем coreteam стал Харальд Вельте (Harald Welte).

Проекты ipchains и ipfwadm изменяли работу стека протоколов ядра Linux, поскольку до появления netfilter в архитектуре ядра не существовало возможностей для подключения дополнительных модулей управления пакетами. iptables сохранил основную идею ipfwadm — список правил, состоящих из критериев и действия, которое выполняется если пакет соответствует критериям. В ipchains была представлена новая концепция — возможность создавать новые цепочки правил и переход пакетов между цепочками, а в iptables концепция была расширена до четырёх таблиц (в современных netfilter – более четырех), разграничивающих цепочки правил по задачам: фильтрация, NAT, и модификация пакетов. Также iptables расширил возможности Linux в области определения состояний, позволяя создавать межсетевые экраны работающие на сеансовом уровне.

Архитектура Netfilter/iptables

Предварительные требования (с)

Как уже говорилось выше, для работы Netfilter необходимо ядро версии 2.6 (ну или хотя бы 2.3.15). Кроме того, при сборке и настройке ядра необходимо наличие настроек CONFIG_NETFILTER, CONFIG_IP_NF_IPTABLES, CONFIG_IP_NF_FILTER (таблица filter), CONFIG_IP_NF_NAT (таблица nat), CONFIG_BRIDGE_NETFILTER, а также многочисленные дополнительные модули: CONFIG_IP_NF_CONNTRACK (отслеживание соединений), CONFIG_IP_NF_FTP (вспомогательный модуль для отслеживания FTP соединений), CONFIG_IP_NF_MATCH_* (дополнительные типы шаблонов соответствия пакетов: LIMIT, MAC, MARK, MULTIPORT, TOS, TCPMSS, STATE, UNCLEAN, OWNER), CONFIG_IP_NF_TARGET_* (дополнительные действия в правилах: REJECT, MASQUERADE, REDIRECT, LOG, TCPMSS), CONFIG_IP_NF_COMPAT_IPCHAINS для совместимости с ipchains, CONFIG_BRIDGE_NF_EBTABLES и CONFIG_BRIDGE_EBT_* для работы в режиме моста, прочие CONFIG_IP_NF_* и CONFIG_IP6_NF_*. Полезно также указать CONFIG_PACKET.

Файлы в каталоге /proc, отображающие информацию о работе netfilter (о некоторых из них – ниже по тексту):

  • /proc/net/ip_tables_names – список используемых таблиц
  • /proc/net/ip_tables_targets – список используемых действий
  • /proc/net/ip_tables_matches – список используемых протоколов
  • /proc/net/nf_conntrack (или /proc/net/ip_conntrack) – список установленных соединений и их состояний
  • /proc/sys/net/ipv4/netfilter/* – cодержит множество настроек системы conntrack, например:
    • ip_conntrack_tcp_be_liberal
      • 0 – все пакеты, не попадающие в окно, считаются INVALID
      • 1 – только RST пакеты, не попадающие в окно, считаются INVALID (пришлось поставить)
    • ip_conntrack_log_invalid – выводить в журнал INVALID пакеты
    • ip_conntrack_tcp_loose – при “подхватывании” уже установленного соединения сколько пакетов требуется в обоих направлениях для подтверждения; если 0, то установленное соединение не подхватывается вовсе; по умолчанию – 3
    • ip_conntrack_max_retrans – число повторных пакетов без подтверждения ACK, которое требуется для удаления соединения из таблицы после дополнительного ожидания ip_conntrack_timeout_max_retrans секунд; по умолчанию – 3

Функциональность netfilter может расширяться с помощью модулей ядра. Головной модуль ядра называется iptable_filter, модуль поддержки утилиты iptables называется ip_tables, вспомогательные модули обычно имеют префикс “ipt_” (например: ipt_state, ipt_REJECT, ipt_LOG; хотя – ip_conntrack/nf_conntrack). Большинство модулей загружается автомагически, но некоторые всё же приходиться загружать вручную (ip_conntrack_ftp – иначе может не работать в режиме Active; ip_conntrack_irc – иначе может не работать отсылка файлов по DCC; ip_nat_ftp; ip_nat_irc; ip_conntrack_tftp/nf_conntrack_tftp на клиенте – иначе не будет работать TFTP).

Схема работы

Для начального понимания архитектуры Netfilter/iptables отлично подойдет иллюстрация из википедии, которую я несколько модифицировал для большей прозрачности и понимания материала:

Архитектура netfiler/iptables в схеме

Ахтунг, ниже в трех абзацах изложена основная мысль статьи и принцип работы сетевого фильтра, поэтому желательно вчитаться как можно внимательнее!

Итак, давайте разберем данную схему работы netfilter. Сетевые пакеты поступают в сетевой интерфейс, настроенный на стек TCP/IP и после некоторых простых проверок ядром (например, контрольная сумма) проходят  последовательность цепочек (chain) (обозначены пунктиром). Пакет обязательно проходит первоначальную цепочку PREROUTING. После цепочки PREROUTING, в соответствии с таблицей маршрутизации, проверяется кому принадлежит пакет и, в зависимости от назначения пакета, определяется куда он дальше попадет (в какую цепочку). Если пакет НЕ адресован (в IP пакете поле адрес получателя – НЕ локальная система) локальной системе, то он направляется в цепочку FORWARD, если пакет адресован локальной системе, то направляется в цепочку INPUT и после прохождения INPUT отдается локальным демонам/процессам. После обработки локальной программой, при необходимости формируется ответ. Ответный пакет пакет отправляемый локальной системой в соответствии с правилами маршрутизации направляется на соответствующий маршрут (хост из локальной сети или адрес маршрутизатора) и направляется в цепочку OUTPUT. После цепочки OUTPUT (или FORWARD, если пакет был проходящий) пакет снова сверяется с правилами маршрутизации и отправляется в цепочку POSTROUTING. Может возникнуть резонный вопрос: почему несколько раз пакет проходит через таблицу маршрутизации? (об этом – ниже).

Каждая цепочка, которую проходит пакет состоит из набора таблиц (table) (обозначены овалами). Таблицы в разных цепочках имеют одинаковое наименование, но тем не менее никак между собой не связаны. Например таблица nat в цепочке PREROUTING никак не связана с таблицей nat в цепочке POSTROUTING. Каждая таблица состоит из упорядоченного  набора (списка) правил. Каждое правило содержит условие, которому должен соответствовать проходящий пакет и действия к пакету, подходящему данному условию.

Проходя через серию цепочек пакет последовательно проходит каждую таблицу (в указанном на иллюстрации порядке) и в каждой таблице последовательно сверяется с каждым правилом (точнее сказать – с каждым набором условий/критериев в правиле), и если пакет соответствует какому-либо критерию, то выполняется заданное действие над пакетом. При этом, в каждой таблице (кроме пользовательских) существует заданная по-умолчанию политика. Данная политика определяет действие над пакетом, в случае, если пакет не соответствует ни одному из правил в таблице. Чаще всего – это действие ACCEPT, чтобы принять пакет и передать в следующую таблицу или DROP – чтобы отбросить пакет. В случае, если пакет не был отброшен, он завершает свое путешествие по ядру системы и отправляется в сетевую карту сетевой интерфейс, которая подходит по правилам маршрутизации.

Очень часто о таблицах и цепочках говорят в плоскости “таблицы содержат  в себе наборы цепочек”, но я считаю, что это неудобно и непонятно.

Цепочки netfilter:

  • PREROUTING — для изначальной обработки входящих пакетов
  • INPUT — для входящих пакетов, адресованных непосредственно локальному компьютеру
  • FORWARD — для проходящих (маршрутизируемых) пакетов
  • OUTPUT — для пакетов, создаваемых локальным компьютером (исходящих)
  • POSTROUTING— для окончательной обработки исходящих пакетов
  • Также можно создавать и уничтожать собственные цепочки при помощи утилиты iptables.

Цепочки организованны в 4 таблицы:

  • raw — пакет проходит данную таблицу до передачи системе определения состояний. Используется редко, например для маркировки пакетов, которые НЕ должны обрабатываться системой определения состояний. Для этого в правиле указывается действие NOTRACK. Содержитcя в цепочках PREROUTING и OUTPUT.
  • mangle — содержит правила модификации (обычно полей заголовка) IP‐пакетов. Среди прочего, поддерживает действия TTLTOS, и MARK (для изменения полей TTL и TOS, и для изменения маркеров пакета). Редко необходима и может быть опасна. Содержится во всех пяти стандартных цепочках.
  • nat — предназначена для подмены адреса отправителя или получателя. Данную таблицу проходят только первый пакет из потока, трансляция адресов или маскировка (подмена адреса отправителя или получателя) применяются ко всем последующим пакетам в потоке автоматически. Поддерживает действия DNATSNATMASQUERADE, REDIRECT. Содержится в цепочках PREROUTINGOUTPUT, и POSTROUTING.
  • filter — основная таблица, используется по умолчанию если название таблицы не указано. Используется для фильтрации пакетов. Содержится в цепочках INPUTFORWARD, и OUTPUT.

Как я уже отметил, непосредственно для фильтрации пакетов используются таблицЫ filter. Поэтому в рамках данной темы важно понимать, что для пакетов, предназначенных данному узлу необходимо модифицировать таблицу filter цепочки INPUT, для проходящих пакетов — цепочки FORWARD, для пакетов, созданных данным узлом — OUTPUT.

Примеры прохождения цепочек

Последовательность обработки входящего пакета, предназначенного для локального процесса:

  1. Просматривается цепочка PREROUTING
    1. Просматривается таблица raw
    2. Просматривается  таблица mangle, далее происходит отслеживание соединений
    3. Просматривается таблица nat (используется для DNAT – модификация адреса получателя)
  2. маршрутизация: если пакет надо маршрутизовать мимо локального хоста, то переходим к обработке проходящего пакета, если для он предназначен локальному хосту, то обрабатывается как локальный
  3. Просматривается цепочка INPUT 
    1. Просматривается таблица mangle
    2. Просматривается таблица filter

Последовательность обработки пакета, уходящего с нашего хоста:

  1. Маршрутизация: определение исходящего адреса, адреса назначения, используемого интерфейса; если пакет маршрутизируется внутрь (для локального хоста), то переходим к предыдущей процедуре
  2. Просматривается цепочка OUTPUT
    1. Просматривается таблица raw
    2. Просматривается таблица mangle, фильтровать здесь не стоит, здесь же происходит отслеживание локально создаваемых соединений
    3. Просматривается таблица nat (NAT для локально сгенерированных пакетов)
    4. Просматривается таблица filter
  3. Повторная маршрутизация, т.к. в таблицах mangle и nat пакет мог быть изменён; если пакет маршрутизируется внутрь (для локального хоста), то переходим к предыдущей процедуре
  4. Просматривается цепочка POSTROUTING 
    1. Просматривается таблица mangle
    2. Просматривается таблица nat (используется для SNAT – модификация адреса источника, фильтровать здесь не стоит)

Последовательность обработки проходящего пакета (начинается от п.2 первой процедуры):

  1. Просматривается цепочка FORWARD
    1. Просматривается таблица mangle
    2. Просматривается таблица filter
  2. повторная маршрутизация, т.к. в таблице mangle пакет мог быть изменён; если пакет маршрутизируется внутрь (для локального хоста), то переходим к первой процедуре
  3. Просматривается цепочка POSTROUTING
    1. Просматривается таблица mangle
    2. Просматривается таблица nat (используется для SNAT и Masquerading, фильтровать здесь не стоит)

Как видно, таблица nat и mangle может модифицировать получателя или отправителя сетевого пакета. Именно поэтому сетевой пакет несколько раз сверяется с таблицей маршрутизации.

Механизм определения состояний (conntrack)

Выше в тексте несколько раз указывалось понятие “определение состояний”, оно заслуживает отдельной темы для обсуждения, но тем не менее я кратко затрону данный вопрос в текущем посте. В общем, механизм определения состояний (он же state machine, он же connection tracking, он же conntrack) является частью пакетного фильтра и позволяет определить определить к какому соединению/сеансу принадлежит пакет. Conntrack анализирует состояние всех пакетов, кроме тех, которые помечены как NOTRACK в таблице raw. На основе этого состояния определяется принадлежит пакет новому соединению (состояние NEW), уже установленному соединению (состояние ESTABLISHED), дополнительному к уже существующему (RELATED), либо к “другому” (неопределяемому) соединению (состояние INVALID). Состояние пакета определяется на основе анализа заголовков передаваемого TCP-пакета. Модуль conntrack позволяет реализовать межсетевой экран сеансового уровня (пятого уровня модели OSI). Для управления данным механизмом используется утилита conntrack, а так же параметр утилиты iptables: -m conntrack или -m state (устарел). Состояния текущих соединений conntrack хранит в ядре. Их можно просмотреть в файле /proc/net/nf_conntrack (или /proc/net/ip_conntrack).

Чтобы мысли не превратились в кашу, думаю данной краткой информации для понимания дальнейшего материала будет достаточно.

Управление правилами сетевой фильтрации Netfilter (использование команды iptables)

Утилита iptables является интерфейсом для управления сетевым экраном netfilter. Данная команда позволяет редактировать правила таблиц, таблицы и цепочки. Как я уже говорил – каждое правило представляет собой запись/строку, содержащую в себе критерии отбора сетевых пакетов и действие над пакетами, которые соответствуют заданному правилу. Команда iptables требует для своей работы прав root.

В общем случае формат команды следующий:

iptables [-t таблица] команда [критерии] [действие]

Все параметры в квадратных скобках – необязательны. По умолчанию используется таблица filter, если же необходимо указать другую таблицу, то следует использовать ключ -t с указанием имени таблицы. После имени таблицы указывается команда, определяющая действие (например: вставить правило, или добавить правило в конец цепочки, или удалить правило). “критерии” задает параметры отбора. “действие” указывает, какое действие должно быть выполнено при условии совпадения критериев отбора в правиле (например: передать пакет в другую цепочку правил, “сбросить” пакет, выдать на источник сообщение об ошибке…).

Ниже приведены команды и параметры утилиты iptables:

Параметр Описание Пример
Команды
–append (-A) Добавить в указанную цепочку и указанную таблицу заданное правило в КОНЕЦ списка. iptables -A FORWARD критерии -j действие
–delete (-D) Удаляет заданное номером(ами) или правилом(ами) правило(а). Первый пример удаляет все правила с номерами 10,12 во всех цепочках, в таблицах filter, второй пример удаляет заданное правило из таблицы mangle в цепочке PREROUTING. iptables -D 10,12
iptables -t mangle -D PREROUTING критерии -j действие
–rename-chain (-E) Изменить имя цепочки. iptables -E OLD_CHAIN NEW_CHAIN
–flush (-F) Очистка всех правил текущей таблицы. Ко всем пакетам, которые относятся к уже установленным соединениям, применяем терминальное действие ACCEPT — пропустить iptables -F
–insert (-I) Вставляет заданное правило в место, заданное номером. iptables -I FORWARD 5 критерии -j действие
–list (сокр. -L) Просмотр существующих правил (без явного указания таблицы – отображается таблица filter всех цепочек). iptables -L
–policy (-P) Устанавливает стандартную политику для заданной цепочки. iptables -t mangle -P PREROUTING DROP
–replace (-R) Заменяет заданное номером правило на заданное в критериях. iptables -R POSROUTING 7 | критерии -j действие
–delete-chain (-X) Удалить ВСЕ созданные вручную цепочки (оставить только стандартные INPUT, OUTPUT, FORWARD, PREROUTING и POSTROUTING). iptables -X
–zero (-Z) Обнуляет счетчики переданных данных в цепочке. iptables -Z INPUT
Параметры
–numeric (-n) Не резолвит адреса и протоколы при выводе.
–line-numbers Указывать номера правил при выводе (может использоваться совместно с -L). iptables -L –line-numbers
–help (-h) куда же без нее :)
-t таблица Задает название таблицы, над которой необходимо совершить действие. В примере сбрасывается таблица nat во всех цепочках. iptables -t nat -F
–verbose (-v) Детальный вывод. iptables -L -v

Критерии (параметры) отбора сетевых пакетов команды iptables

Критерии отбора сетевых пакетов негласно делятся на несколько групп: Общие критерии, Неявные критерии, Явные критерии. Общие критерии допустимо употреблять в любых правилах, они не зависят от типа протокола и не требуют подгрузки модулей расширения. Неявные критерии (я бы из назвал необщие),  те критерии, которые подгружаются неявно и становятся доступны, например при указании общего критерия –protocol tcp|udp|icmp. Перед использованием Явных критериев, необходимо подключить дополнительное расширение (это своеобразные плагины для netfilter). Дополнительные расширения подгружаются с помощью параметра -m или –match. Так, например, если мы собираемся использовать критерии state, то мы должны явно указать это в строке правила: -m state левее используемого критерия. Отличие между явными и неявными необщими критериями заключается в том, что явные нужно подгружать явно, а неявные подгружаются автоматически.

Во всех критериях можно использовать знак ! перед значением критерия. Это будет означать, что под данное правило подпадают все пакеты, которые не соответствуют данному параметру. Например: критерий –protocol ! tcp будет обозначать, что все пакеты, которые не являются TCP-протоколом подходят под действие правила. Однако последние версии iptables (в частности, 1.4.3.2 и выше), уже не поддерживают этот синтаксис и требуют использования не –protocol ! tcp, а ! –protocol tcp,  выдавая следующую ошибку:

Using intrapositioned negation (`--option ! this`) is deprecated in favor of extrapositioned (`! --option this`).

Ниже в виде таблицы приведены часто используемые параметры отбора пакетов:

Параметр Описание Пример
Общие параметры
–protocol
(сокр. -p)
Определяет протокол транспортного уровня. Опции tcp, udp, icmp, all или любой другой протокол определенный в /etc/protocols iptables -A INPUT -p tcp
–source
(-s, –src)
IP адрес источника пакета. Может быть определен несколькими путями:

  • Одиночный хост: host.domain.tld, или IP адрес: 10.10.10.3
  • Пул-адресов (подсеть): 10.10.10.3/24 или 10.10.10.3/255.255.255.0
Настойчиво не рекомендуется использовать доменные имена, для разрешения (резольва) которых требуются DNS-запросы, так как на этапе конфигурирования netfilter DNS может работать некорректно. Также, заметим, имена резольвятся всего один раз — при добавлении правила в цепочку. Впоследствии соответствующий этому имени IP-адрес может измениться, но на уже записанные правила это никак не повлияет (в них останется старый адрес). Если указать доменное имя, которое резольвится в несколько IP-адресов, то для каждого адреса будет добавлено отдельное правило.
iptables -A INPUT -s 10.10.10.3
–destination
(-d)
IP адрес назначения пакета. Может быть определен несколькими путями (см. –source). iptables -A INPUT –destination 192.168.1.0/24
–in-interface
(-i)
Определяет интерфейс, на который прибыл пакет. Полезно для NAT и машин с несколькими сетевыми интерфейсами. Применяется в цепочках INPUT, FORWARD и PREROUTING. Возможно использование знака “+”, тогда подразумевается использование всех интерфейсов, начинающихся на имя+ (например eth+ – все интерфейсы eth). iptables -t nat -A PREROUTING –in-interface eth0
–out-interface
(-o)
Определяет интерфейс, с которого уйдет пакет. Полезно для NAT и машин с несколькими сетевыми интерфейсами. Применяется в цепочках OUTPUT, FORWARD и POSTROUTING. Возможно использование знака “+”. iptables -t nat -A POSTROUTING –in-interface eth1
Неявные (необщие) параметры
-p proto -h вывод справки по неявным параметрам протокола proto. iptables -p icmp -h
–source-port
(–sport)
Порт источник, возможно только для протоколов –protocol tcp, или –protocol udp iptables -A INPUT –protocol tcp –source-port 25
–destination-port
(–dport)
Порт назначения, возможно только для протоколов –protocol tcp, или –protemocol udp iptables -A INPUT –protocol udp –destination-port 67
Явные параметры
-m state –state (устарел)
он же
-m conntrack –ctstate

Состояние соединения. Доступные опции:

  • NEW (Все пакеты устанавливающие новое соединение)
  • ESTABLISHED (Все пакеты, принадлежащие установленному соединению)
  • RELATED (Пакеты, не принадлежащие установленному соединению, но связанные с ним. Например – FTP в активном режиме использует разные соединения для передачи данных. Эти соединения связаны.)
  • INVALID (Пакеты, которые не могут быть по тем или иным причинам идентифицированы. Например, ICMP ошибки не принадлежащие существующим соединениям)
  • и др. (более подробно в документации)
iptables -A INPUT -m state –state NEW,ESTABLISHEDiptables -A INPUT -m conntrack –ctstate NEW,ESTABLISHED
-m mac –mac-source Задает MAC адрес сетевого узла, передавшего пакет. MAC адрес должен указываться в форме XX:XX:XX:XX:XX:XX. -m mac –mac-source 00:00:00:00:00:0

Действия над пакетами

Данный заголовок правильнее будет перефразировать в “Действия над пакетами, которые совпали с критериями отбора“. Итак, для совершения какого-либо действия над пакетами, необходимо задать ключ -j (–jump) и указать, какое конкретно действие совершить.

Действия над пакетами могут принимать следующие значения:

  • ACCEPT – пакет покидает данную цепочку и передается в следующую (дословно – ПРИНЯТЬ).
  • DROP – отбросить удовлетворяющий условию пакет, при этом пакет не передается в другие таблицы/цепочки.
  • REJECT – отбросить пакет, отправив отправителю ICMP-сообщение, при этом пакет не передается в другие таблицы/цепочки.
  • RETURN – возвратить пакет в предыдущую цепочку и продолжить ее прохождение начиная со следующего правила.
  • SNAT – применить трансляцию адреса источника в пакете. Может использоваться только в цепочках POSTROUTING и OUTPUT в таблицах nat.
  • DNAT – применить трансляцию адреса назначения в пакете. Может использоваться в цепочке PREROUTING в таблице nat. (в исключительных случаях – в цепочке OUTPUT)
  • LOG – протоколировать пакет (отправляется демону syslog) и обработать остальными правилами.
  • MASQUERADE — используется вместо SNAT при наличии соединения с динамическим IP (допускается указывать только в цепочке POSTROUTING таблицы nat).
  • MARK — используется для установки меток на пакеты, передается для обработки дальнейшим правилам.
  • и др.

Кроме указанных действий, существуют и другие, с которыми можно ознакомиться в документации (возможно, в скором времени я дополню статью в ходе освоения темы). У некоторых действий есть дополнительные параметры.

В таблице ниже приведены примеры и описания дополнительных параметров:

Параметр Описание Пример
DNAT (Destination Network Address Translation)
–to-destination указывает, какой IP адрес должен быть подставлен в качестве адреса места назначения. В примере во всех пакетах протокола tcp, пришедших на адрес 1.2.3.4, данный адрес будет заменен на 4.3.2.1. iptables -t nat -A PREROUTING -p tcp -d 1.2.3.4 -j DNAT –to-destination 4.3.2.1
LOG
–log-level Используется для задания уровня журналирования (log level). В примере установлен максимальный уровень логирования для всех tcp пакетов в таблице filter цепочки FORWARD. iptables -A FORWARD -p tcp -j LOG –log-level debug
–log-prefix Задает текст (префикс), которым будут предваряться все сообщения iptables. (очень удобно для дальнейшего парсинга) Префикс может содержать до 29 символов, включая и пробелы. В примере отправляются в syslog все tcp пакеты в таблице filter цепочки INPUT с префиксом INRUT-filter. iptables -A INPUT -p tcp -j LOG –log-prefix “INRUT-filter”
–log-ip-options Позволяет заносить в системный журнал различные сведения из заголовка IP пакета. iptables -A FORWARD -p tcp -j LOG –log-ip-options
и др…

На этом закончим теорию о сетевом фильтре netfilter/iptables. В следующей статье я приведу практические примеры для усвоения данной теории.

Резюме

В данной статье мы рассмотрели очень кратко основные понятия сетевого фильтра в Linux. Итак, подсистема netfilter/iptables является частью ядра Linux и используется для организации различных схем фильтрации и манипуляции с сетевыми пакетами. При этом, каждый пакет проходит от сетевого интерфейса, в который он прибыл и далее по определенному маршруту цепочек, в зависимости от того, предназначен он локальной системе или “нелокальной”. Каждая цепочка состоит из набора таблиц, содержащих последовательный набор правил. Каждое правило состоит из определенного критерия/критериев отбора сетевого пакета и какого-то действия с пакетом, соответствующего данным критериям. В соответствии с заданными правилами над пакетом может быть совершено какое-либо действие (Например, передача следующей/другой цепочке, сброс пакета, модификация содержимого или заголовков и др.).  Каждая цепочка и каждая таблица имеет свое назначение, функциональность и место в пути следования пакета. Например для фильтрации пакетов используется таблица filter, которая содержится в трех стандартных цепочках и может содержаться в цепочках, заданных пользователем. Завершается путь пакета либо в выходящем сетевом интерфейсе, либо доставкой локальному процессу/приложению.

Литература

Довольно много интересной информации на русском содержится тут:

  • http://www.opennet.ru/docs/RUS/iptables/
  • http://ru.wikibooks.org/wiki/Iptables
Более глубоко материал доступен на буржуйском вот тут:
  • http://www.frozentux.net/documents/ipsysctl-tutorial/
  • http://www.netfilter.org/documentation/index.html

 С Уважением, Mc.Sim!




Теги: , , , ,

54 комментария к “Основные понятия iptables в Linux”

  1. Денис
    19 марта, 2012 at 22:08
    1

    Вот еще неплохая картинка по структуре –

    http://mdsh.com/wiki/Wiki?action=action_view_attachment&attachment=20100309110057767-0-IPTables.png

    • 21 марта, 2012 at 13:14
      2

      Да. Хороший рисунок. Его я использую в статье про OpenVPN.

  2. monkey-alex
    9 июня, 2012 at 11:58
    3

    Спасибо за статью!!! Очень толковая и небольшая )).

  3. PowerMonger
    13 июля, 2012 at 10:27
    4

    Статья очень хорошая и понятная, автору отдельное спасибо!!!

    • 14 июля, 2012 at 01:27
      5

      пожалуйста! Приходите еще!

  4. Аноним
    23 октября, 2012 at 12:43
    6

    Хорошая статья! Я систематизировал знания свои по таблицам сетевым с помощью этой статьи. Спасибо.

    • 23 октября, 2012 at 22:31
      7

      На здоровье, приходите еще.

  5. Николай
    28 ноября, 2012 at 15:49
    8

    Благодарю,хорошая статья,помогла разобраться

  6. apelmon
    14 декабря, 2012 at 00:01
    9

    “DNAT – применить трансляцию адреса назначения в пакете. Может использоваться только в цепочке POSTROUTING в таблице nat.”

    Я, конечно, только начал изучать iptables, но помойму, dnat может использоваться только в цепочке PREROUTING, или я – неправ? Иначе, как перенаправлять входящие пакеты?..

    • 19 декабря, 2012 at 17:32
      10

      apelmon, спасибо.
      Конечно же PREROUTING. Это опечатка. А еще в исключительных случаях -в OUTPUT.

  7. John
    16 января, 2013 at 10:51
    11

    Чувак, зачетная статья, молодец! А продолжение когда будет?:)

    • 22 января, 2013 at 19:35
      12

      Спасибо за отзыв. Про продолжение пока не могу назвать сроков…

  8. Alexey_SL
    23 января, 2013 at 12:51
    13

    Очень часто о таблицах и цепочках говорят в плоскости “таблицы содержат в себе наборы цепочек”, но я считаю, что это неудобно и непонятно.

    Эта фраза породила во мне когнитивный диссонанс такой силы, что я решил открыть исходники и посмотреть, что же там во что входит. Таблицы описаны в файлах “linux-src/net/ipv4/netfilter/table_таблица.c” (linux-src – это каталог с исходниками ядра). Таблицы имеют тип struct xt_table, который описан в linux-src/include/linux/netfilter/x_tables.h:

    struct xt_table {
    struct list_head list;

    /* What hooks you will enter on */
    unsigned int valid_hooks;

    /* Man behind the curtain... */
    struct xt_table_info *private;

    /* Set this to THIS_MODULE if you are a module, otherwise NULL */
    struct module *me;

    u_int8_t af; /* address/protocol family */
    int priority; /* hook order */

    /* A unique name... */
    const char name[XT_TABLE_MAXNAMELEN];
    };

    valid_hooks – это какие-то “хуки”, применимые к таблице. Возможные значения valid_hooks описаны в описаны в файле linux-src/include/uapi/linux/netfilter.h в структуре enum nf_inet_hooks:

    enum nf_inet_hooks {
    NF_INET_PRE_ROUTING,
    NF_INET_LOCAL_IN,
    NF_INET_FORWARD,
    NF_INET_LOCAL_OUT,
    NF_INET_POST_ROUTING,
    NF_INET_NUMHOOKS
    };

    В принципе, думаю, понятно какой хук к какой цепочке относится (кстати, можно заметить, что эти хуки перечислены в порядке следования). Например, для таблицы filter:

    #define FILTER_VALID_HOOKS ((1 << NF_INET_LOCAL_IN) | \
    (1 << NF_INET_FORWARD) | \
    (1 << NF_INET_LOCAL_OUT))

    static const struct xt_table packet_filter = {
    .name = "filter",
    .valid_hooks = FILTER_VALID_HOOKS,
    .me = THIS_MODULE,
    .af = NFPROTO_IPV4,
    .priority = NF_IP_PRI_FILTER,
    };

    Видно, что для таблицы filter применимы действия цепочек INPUT, FORWARD и OUTPUT. Таким образом, “by design” ни таблицы ни цепочки не входят друг в друга. Netfilter работает с таблицами, в таблицы входят действия, которые реализуются в цепочках. Интересна таблица nat:

    static const struct xt_table nf_nat_ipv4_table = {
    .name = "nat",
    .valid_hooks = (1 << NF_INET_PRE_ROUTING) |
    (1 << NF_INET_POST_ROUTING) |
    (1 << NF_INET_LOCAL_OUT) |
    (1 << NF_INET_LOCAL_IN),
    .me = THIS_MODULE,
    .af = NFPROTO_IPV4,
    };

    Можно увидеть, что таблица nat может применяться в цепочке INPUT. Видимо, это какой-то старый код (даже хуки объявлены не через define). Сами разработчики в комментариях в файле пишут так:

    /* After packet filtering, change source */
    {
    .hook = nf_nat_ipv4_fn,
    .owner = THIS_MODULE,
    .pf = NFPROTO_IPV4,
    .hooknum = NF_INET_LOCAL_IN,
    .priority = NF_IP_PRI_NAT_SRC,
    },

    Видимо, в цепочке INPUT заложена возможность изменить source пакета после применения фильтра.

    И немного по схеме фильтрации. С учетом всего вышеизложенного запомнить схему не так уж и сложно. Достаточно помнить 2 вещи:
    1. Порядок цепочек (есть в схеме).
    2. Помнить, что таблицы в цепочках всегда (!) применяются в одном и том же порядке: raw, mangle, nat, filter (за исключением теоретической возможности с таблицей nat, описанной выше). Про новую security пока не говорю, поскольку не знаю, где она применяется (скорее всего, после filter). Вот список таблиц и цепочек, в которых они могут применяться (без security, в порядке следования соответственно).

    raw: PREROUTING
    OUTPUT

    mangle: PREROUTING
    INPUT
    FORWARD
    OUTPUT
    POSTROUTING

    nat: PREROUTING
    INPUT
    OUTPUT
    POSTROUTING

    filter: INPUT
    FORWARD
    OUTPUT

    Спасибо за внимание.

    P.S. Чуть позже нарисую свою схему с комментариями и оставлю ссылку.

    • 28 января, 2013 at 22:45
      14

      Молодец, Алексей.
      Я в сях не силен, но разъяснения довольно убедительны )))
      Как появиться схема – допилю статью )))

      Спасибо за коммент.

      • Alexey_SL
        17 февраля, 2013 at 21:14
        15

        Хм, не понял, смог ли я отправить комментарий или нет. На всякий случай еще раз оставлю ссылки. Схемка в pdf: http://yadi.sk/d/qKLD0pje2Ep1m и odf: http://yadi.sk/d/tFP-gvbc2Ep1a. Совместил описание таблиц и схему работы. Постарался изобразить только то, что имеет отношение к iptables. Жирным шрифтом в схеме выделил таблицы, которые чаще всего задействуют в правилах, остальные обозначил маленьким.

        • 18 февраля, 2013 at 01:16
          16

          Спасибо, Alexey_SL
          Где-то я уже аналогичную схему встречал… Толи на опеннете, то ли еще где-то…
          Остановился я все же именно на той, которую вставил в статью. По причине того, что она проще поддается описанию и объяснению и более наглядна…
          В Ваших схемах еще не хватает роутинга на выходе из Local Process / Socket и перед цепочкой построутинг, что тоже важный момент для понимания “перемещения” пакетов в ядре )
          В целом, спасибо за проделанную работу, Ваша схема, разбор ядра и сделанные выводы мне помогли убедиться, что не капаясь в ядре, я (и википедия )) ) достаточно верно изобразили основные аспекты прохождения трафика через нетфильтр.

  9. Grol
    1 февраля, 2013 at 15:16
    17

    Отличная статья! Благодаря ей избавился от каши в голове по iptables.

  10. Rawlik
    12 февраля, 2013 at 17:41
    18

    Если пакет НЕ принадлежит (в TCP пакете поле адрес получателя – не локальная система) локальной системе, то он направляется в цепочку FORWARD, если пакет принадлежит локальной системе, то направляется в цепочку INPUT и после прохождения INPUT отдается локальным демонам/процессам.

    Возможно проще сразу написать адресован, ‘принадлежит’ можно понять и как пакет, источник которого сам хост маршрутизатора (конечно в скобках написано но, тогда это пояснение будет уже и не нужно).

    • 18 февраля, 2013 at 01:04
      19

      Rawlik,
      Спасибо за замечание. Так действительно будет понятнее. Подправил.

  11. Alex
    8 апреля, 2014 at 11:06
    20

    Ищу описание как использовать -j TRACE в таблице raw, для отладки правил, но тщетно. Вы не встречали такого в сети?

    • 24 июня, 2014 at 19:36
      21

      А зачем там trace?
      Можно ж tcpdump использовать для ловли пакетов, он вроде как собирает “до” сетевого фильтра (если можно так сказать – “до”)..

  12. Stoner
    3 сентября, 2014 at 14:03
    22

    Здравствуйте. Всё же, не разобрался с синтаксисом. Вот, к примеру, есть такое правило:
    “root@debian-gateway:~# iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE”.
    Я так понял, что цепочка – это набор таблиц, включая nat и проч. Тогда как понимать параметр -А для цепочки? Или без явного указания таблицы (-t nat) он применяется для всех таблиц цепочки?

    • 17 декабря, 2014 at 20:44
      23

      Нет, если таблица не задана, то правило применяется к таблице filter. Цитата из статьи:

      filter — основная таблица, используется по умолчанию если название таблицы не указано. Используется для фильтрации пакетов.

      В вашем случае, если не указать ключ -t, то скорей всего будет ошибка, т.к. в POSTROUTING нет таблицы filter.

  13. Женя
    2 октября, 2014 at 13:17
    24

    Прошу помощи найти способ связать web сессию c iptables.

    Есть вэб форма авторизации пользователей, при авторизации в которой (установлении сессии) необходимо в фаерволе itables включать правило на пропуск пакетов – другими словами необходимо строить правило по web сессии (если сессия есть то правило включается).

    Пытаюсь сделать это на ОС Debian.

    В данном вопросе как и куда и какие пакеты ходят не принципиально. Важно понять как можно построить проверку в фаерволе при web сессии?
    Может кто реализовывал подобное на других системах, буду благодарен за пример.
    Я пытаюсь реализовать на связке Debian + iptables+apache2+php5

    Спасибо за любую помощь!
    http://toster.ru/q/136253

    • 18 декабря, 2014 at 00:08
      25

      Направление для мысли на тостер.ру дали правиьное. )

  14. зина
    20 ноября, 2014 at 02:32
    26

    Уберите тракинг кликов в метрике, невозможно читать когда он при каждом клике чтото там снизу подгружает ) бесит…

    • 18 декабря, 2014 at 15:09
      27

      убрал )

  15. Thund3r
    29 декабря, 2014 at 01:02
    28

    Благодарю за хорошую статью! Но возник вопрос, например мы в цепочке POSTROUTING в таблице mangle ставить route mark, как же эта метка обработается, если больше не будет маршрутизации. Возможно логика на картинке не полная?

    • Thund3r
      29 декабря, 2014 at 21:09
      29

      Прошу прощения! В POSTROUTING в таблице mangle невозможно mark route

    • 9 апреля, 2015 at 16:37
      30

      Все верно, в цепочке POSTROUTING бессмыслено маркировать пакеты, т.к. это пакеты, которые вот-вот вылетят из сетевого интерфейса. Маркировку нужно производить для входящего пакета, либо для пакета, отправляемого каким-то локальным сервисом.

  16. depeche
    31 июля, 2015 at 00:46
    31

    >> если пакет маршрутизируется внутрь, то переходим к предыдущей процедуре

    Во внутрь – это как? Опять на локальный интерфейс? Тогда в этом случае не правильнее будет сказать, что пакет выходит с цепочки построутинг и идет опять на цепочку инпут?

    Спасибо.

    • 10 октября, 2015 at 13:41
      32

      Да, действительно каламбур получился.
      Подправил текст. Теперь более понятно значение.

  17. Андрей
    20 сентября, 2015 at 19:08
    33

    В цепочке INPUT тоже есть NAT.

    Добавьте в схемку)

    • 10 октября, 2015 at 14:13
      34

      Откуда такая информация?

      • Алексей
        10 ноября, 2015 at 22:14
        35

        На Debian 7.9 пишу: iptables -t nat -L и среди прочего получаю Chain INPUT…
        А в целом – статью в избранное, автору медаль (размером как кремлёвские часы)

        • 24 июля, 2016 at 15:26
          36

          Спасибо.
          Да, действительно, в ядре с версии 2.6.35 структура обновилась (пруф)

  18. 12 ноября, 2015 at 18:56
    37

    Большое пасиб за статью. Все очень доходчиво и кратко.

  19. Дмитрий
    13 июля, 2017 at 21:15
    38

    Спасибо, статья помогла разобраться в теме.

  20. Drentul
    14 сентября, 2018 at 18:19
    39

    Спасибо вам, добрый человек! Картинки то мне и не хватало, чтобы расставить точки над “ё”. Вы мне очень помогли.

  21. Влад
    27 февраля, 2019 at 09:56
    40

    Thanks! *IN LOVE*

  22. Paragor
    22 сентября, 2019 at 13:34
    41

    Уже 2019 год, а статья еще актуальна. Спасибо за труд! *IN LOVE* *IN LOVE* *IN LOVE*

  23. Alex
    20 января, 2020 at 02:02
    42

    Актуально и в 2020 :)
    Однако вопрос имеется. Если мне нужно заблокировать 22й порт как для сервиса локальной машины, так и для стоящих за ней, получается, это нужно сделать в двух местах (FORWARD filter + INPUT filter). Нет ли в этом архитектурного недостатка?

    • 2 февраля, 2020 at 17:00
      43

      Думаю, что нет.
      Это 2 разных цепочки для двух разных задач.

  24. AlexG
    16 апреля, 2020 at 11:13
    44

    Благодарю за статью!

    Пожалуйста, подскажите, а для docker настраивали iptables? Интересует как совладать с его динамическим прописыванием правил в iptables. А если точнее, то как заблокировать порт в docker к mysql от внешнего интерфейса, чтобы при этом можно было достучаться изнутри…

    • 16 апреля, 2020 at 20:19
      45

      До докера, к сожалению, не довелось добраться.
      Можно попробовать включить интуицию.
      Полагаю, что сетевая подсистема докера устроена как у KVM, к примеру?
      Можно понять, какие потоки соединений и куда идут и дальше – разобраться с правилами.

  25. putin
    7 октября, 2020 at 12:02
    46

    в TCP пакете поле адрес получателя – НЕ локальная система

    Адрес в IP, не в TCP. И так по

  26. 30 октября, 2020 at 06:43
    47

    Это самая понятная статья из всех, которые я видел в интернете на эту тему. Спасибо. Никогда не мог понять логику этих всех таблиц и цепочек. А статью нашел через поиск по картинкам.

    Если вы ищете правила iptables для docker, то я во всем разобрался и написал статью: https://codepoetry.ru/post/docker-user-iptables/
    – там как раз о том, как фильтровать трафик и закрыть/открыть доступ к определенным портам в контейнерах

    • 3 ноября, 2020 at 09:10
      48

      Дмитрий, спасибо за статью :)

  27. XF13
    4 ноября, 2020 at 15:18
    49

    Как я понимаю iptabes и nftables основаны на одном и том же netfilter. Но все же, актуальны ли представленные схемы для nftables в 2020?

    • 13 января, 2021 at 14:52
      50

      К сожалению, я пока не готов ответить на этот вопрос.
      Пока с nftables я не сталкивался.

    • Tux
      31 июля, 2021 at 13:24
      51

      nftables eto i est iptables, raxnitsa tolko v tom shto v iptables ukazyvaem “iptables, arptables i e.t.c” a v nftables vsyu etu dvizhuhu zamenili na “nftables”. eto dve odinakovye sistemy upravleniya v toy zhe utilite

  28. Tux
    31 июля, 2021 at 13:20
    52

    Mne kajetsa koe kto zabyl tablitsu “SECURE” ukazat ili ya ne prav?

    • 2 марта, 2024 at 15:04
      53

      В целом, да там есть больше таблиц. В том числе security, srcnat, и др. Но это в основном специфичные для дистрибутива таблицы. Например, Security – это там, где есть SElinux. Если я правильно помню

  29. Константин
    16 марта, 2022 at 14:22
    54

    Спасибо! *THUMBS UP*

Написать комментарий