Debian: настройка и управление IPTABLES

By | 04/02/2013
 

debian-logo_lenny2Тут приводятся примеры настройки для различных ситуаций. Про структуру IPTABLES, управление, архитектуру и прочее – смотрите в цикле Linux: IPTABLES — руководство: часть 1 — основы IPTABLES.

Настройка осуществляется на:

# lsb_release -a
No LSB modules are available.
Distributor ID: Debian
Description:    Debian GNU/Linux 6.0.7 (squeeze)
Release:        6.0.7
Codename:       squeeze

Создаём файл настроек для IPTABLES:

# touch /etc/network/if-up.d/iptables.conf

Разрешаем его запуск:

# chmod +x /etc/network/if-up.d/iptables.conf

ВАЖНО: некоторые опции указываются с двумя тире — хотя в примерах они отображаются как одно! Учтите это, если копируете правила прямо из блога:

– – state
– – dport
– – tcp-flags
– – reject-with

В него добавляем:

#!/bin/bash

# Задаём путь к исполняемому файлу IPTABLES
IPTABLES=’/sbin/iptables’

# Сбрасываем существующие правила для всех таблиц и цепочек
$IPTABLES -F
$IPTABLES -X

# Задаём правила по-умолчанию (если не сработало не одно правило из цепочки – сработает правило отсюда)
$IPTABLES -P INPUT DROP
$IPTABLES -P OUTPUT ACCEPT
$IPTABLES -P FORWARD ACCEPT

# Разрешаем весь трафик по loopback интерфейсу lo0
$IPTABLES -A INPUT -i lo -j ACCEPT

# Разрешаем трафик уже установленным и создающим новые подключения соединениям:
$IPTABLES -A INPUT -m state –state RELATED,ESTABLISHED -j ACCEPT

# Разрешаем входящий SSH через интерфейс eth0
$IPTABLES -A INPUT -p tcp -i eth0 –dport 22 -j ACCEPT

Теперь разберём созданные правила подробнее.

В IPTABLES используется три вида таблиц:

  1. Mangle – обычно эта цепочка используется для внесения изменений в заголовок пакета, например для изменения битов TOS и пр.
  2. Nat – эта цепочка используется для трансляции сетевых адресов (Destination Network Address Translation). Source Network Address Translation выполняется позднее, в другой цепочке. Любого рода фильтрация в этой цепочке может производиться только в исключительных случаях.
  3. Filter – здесь производится фильтрация трафика. Помните, что все входящие пакеты, адресованные нам, проходят через эту цепочку, независимо от того с какого интерфейса они поступили.

Соответственно, нас интересует третья таблица Filter. В этой таблицы имеются три встроенные цепочки:

  1. INPUT – для входящих пакетов.
  2. FORWARD – для проходящих через данную машину к другой.
  3. OUTPUT – для исходящих.

Пакет, проходящий через эти цепочки, исходя из правила может быть пропущен (ACCEPT) или отброшен (DROP):

  • ACCEPT – пропустить пакет; просмотр таблицы завершается
  • DROP – выбросить молча; просмотр завершается не только для текущей цепочки, но и для других таблиц
  • REJECT – выбросить, известив отправителя (–reject-with тип-извещения)

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

$IPTABLES  -P INPUT DROP

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

То же самое касается “транзитных” пакетов:

$IPTABLES  -P OUTPUT ACCEPT

Следующее правило:

$IPTABLES  -A INPUT -i lo -j ACCEPT

Задаёт пользовательское правило (-A) в фильтр INPUT для пакетов, проходящих через интерфейс (-i) loopback (lo) и выполняет цель (-j) “принять” (ACCEPT).

В следующем правиле используется модуль (-m) state, который проверяет состояние устанавливаемого соединения – RELATED или ESTABLISHED и если соединение подходит под это правило – разрешает его:

$IPTABLES -A INPUT -m state –state RELATED,ESTABLISHED -j ACCEPT

Возможные состояния: INVALID – пакет не связан с каким-либо известным соединением, ESTABLISHED – пакет связан с соединением, по которому уже проходили пакеты в обоих направлениях, NEW – пакет инициирует новое соединение, либо связан с соединением, по которому ещё не проходили пакеты в обоих направлениях , RELATED – пакет инициирует новое соединение, но также связан с уже существующим соединением, например при передаче данных по FTP или сообщении об ошибке ICMP, SNAT – виртуальное состояние, положительный результат выдаётся если исходный адрес источника отличен от адреса, который должен получить ответ, DNAT – виртуальное состояние, положительный результат выдаётся если исходный адрес получателя отличен от адреса отправителя ответа.

В следующем правиле для фильтра входящих соединений INPUT мы указываем:

$IPTABLES -A INPUT -p tcp -i eth0 –dport 22 -j ACCEPT

Протокол (-p) TCP, интерфейс (-i) eth0, и порт назначения, т.е. порт на нашем сервере, к которому устанавливается соединение (–dport) 22.

Добавим ещё несколько правил:

#Делаем защиту от DOS атак:
$IPTABLES -A INPUT -p tcp -m tcp –tcp-flags SYN,ACK,FIN,RST RST -m limit –limit 1/s -j ACCEPT

# Разрешаем FTP
$IPTABLES -A INPUT -i eth0 -p tcp –dport 21 -j ACCEPT

# Разрешаем HTTP
$IPTABLES -A INPUT -i eth0 -p tcp –dport 80 -j ACCEPT

# Разрешаем HTTPS
$IPTABLES -A INPUT -i eth0 -p tcp –dport 443 -j ACCEPT

# Разрешаем SMTP только из сети 77.120.***.1/24
$IPTABLES -A INPUT -s 77.120.***.1/24 -i eth0 -p tcp –dport 25 -j ACCEPT

# Разрешаем SMTP всем, но запрещаем отправку для адреса 77.120.***.46
$IPTABLES -A INPUT -s ! 77.120.***.46 -i eth0 -p tcp –dport 25 -j ACCEPT

# РазрешаемPOP3 только с IP 77.120.***.46
$IPTABLES -A INPUT -s 77.120.***.46 -i eth0 -p tcp –dport 110 -j ACCEPT

# Разрешаем DNS
$IPTABLES -A INPUT -i eth0 -p udp –sport 53 -j ACCEPT

# Доступ к портам 8081 и 8082 разрешаем только из сетей 91.***.**.0/24, 195.***.***.0/23 и IP 37.***.**.174
for net in 91.***.**.0/24 195.***.***.0/23 37.***.**.174; do
$IPTABLES -A INPUT -p tcp -m tcp -s $net -m multiport –dports 8081,8082 -j ACCEPT
done
$IPTABLES -A INPUT -p tcp -m tcp -m multiport –dports 8081,8082 -j DROP

# Разрешаем ping
$IPTABLES -A INPUT -p icmp -j ACCEPT

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

# /etc/network/if-up.d/iptables.conf reload

В случае ошибок – будет указано в какой строке какая ошибка. Например:

iptables v1.4.8: unknown protocol `tcp–dport’ specified

Пропущен пробел после tcp.

Посмотреть текущие правила можно с помощью опции –list:

# iptables –list
Chain INPUT (policy DROP)
target     prot opt source               destination
ACCEPT     all  —  anywhere             anywhere
ACCEPT     all  —  anywhere             anywhere            state RELATED,ESTABLISHED
ACCEPT     tcp  —  anywhere             anywhere            tcp dpt:ssh
ACCEPT     tcp  —  anywhere             anywhere            tcp flags:FIN,SYN,RST,ACK/RST limit: avg 1/sec burst 5
ACCEPT     tcp  —  anywhere             anywhere            tcp dpt:ftp
ACCEPT     tcp  —  anywhere             anywhere            tcp dpt:www
ACCEPT     tcp  —  anywhere             anywhere            tcp dpt:https
ACCEPT     tcp  —  0.***.***.77.colo.static.dc.volia.com/24  anywhere            tcp dpt:smtp
ACCEPT     tcp  — !0.***.***.77.colo.static.dc.volia.com/24  anywhere            tcp dpt:smtp
ACCEPT     tcp  —  46.***.***.77.colo.static.dc.volia.com  anywhere            tcp dpt:pop3
ACCEPT     udp  —  anywhere             anywhere            udp spt:domain
ACCEPT     tcp  —  91.***.**.0/24  anywhere            tcp multiport dports tproxy,8082
ACCEPT     tcp  —  195.***.***.0/23     anywhere            tcp multiport dports tproxy,8082
ACCEPT     tcp  —  37.***.***.174       anywhere            tcp multiport dports tproxy,8082
DROP       tcp  —  anywhere             anywhere            tcp multiport dports tproxy,8082
ACCEPT     icmp —  anywhere             anywhere            icmp echo-request

Chain FORWARD (policy ACCEPT)
target     prot opt source               destination

Chain OUTPUT (policy ACCEPT)
target     prot opt source               destination

Ещё несколько примеров использования.

Проверить статус IPTABLES:

# iptables -L -n -v
Chain INPUT (policy DROP 176 packets, 36734 bytes)
pkts bytes target     prot opt in     out     source               destination
0     0 ACCEPT     all  —  lo     *       0.0.0.0/0            0.0.0.0/0
179K   40M ACCEPT     all  —  *      *       0.0.0.0/0            0.0.0.0/0           state RELATED,ESTABLISHED
1   100 ACCEPT     tcp  —  eth0   *       0.0.0.0/0            0.0.0.0/0           tcp dpt:22
0     0 ACCEPT     tcp  —  eth0   *       0.0.0.0/0            0.0.0.0/0           tcp dpt:21
3   180 ACCEPT     tcp  —  eth0   *       0.0.0.0/0            0.0.0.0/0           tcp dpt:80
1    28 ACCEPT     icmp —  *      *       0.0.0.0/0            0.0.0.0/0
1    60 ACCEPT     tcp  —  *      *       195.191.226.102      0.0.0.0/0           tcp dpt:514
0     0 ACCEPT     tcp  —  *      *       91.218.228.236       0.0.0.0/0           tcp dpt:514

Chain FORWARD (policy ACCEPT 0 packets, 0 bytes)
pkts bytes target     prot opt in     out     source               destination

Chain OUTPUT (policy ACCEPT 180K packets, 12M bytes)
pkts bytes target     prot opt in     out     source               destination

Ключи:

-L: показать список правил;
-v: выводить дополнительную информацию;
-n: отображать ip адрес и порт числами, а не перобразовывать в FQDN-имя.

Вывести текущие правила, только INPUT:

# iptables -L INPUT -n -v

Или только OUTPUT:

# iptables -L OUTPUT -n -v

Добавление и удаление правил.

Вывести текущие правила INPUT с указанием строк (номеров правил):

# iptables -L INPUT -n –line-numbers
Chain INPUT (policy DROP)
num  target     prot opt source               destination
1    ACCEPT     all  —  0.0.0.0/0            0.0.0.0/0
2    ACCEPT     all  —  0.0.0.0/0            0.0.0.0/0           state RELATED,ESTABLISHED
3    ACCEPT     tcp  —  0.0.0.0/0            0.0.0.0/0           tcp dpt:22
4    ACCEPT     tcp  —  0.0.0.0/0            0.0.0.0/0           tcp dpt:21
5    ACCEPT     tcp  —  0.0.0.0/0            0.0.0.0/0           tcp dpt:80
6    ACCEPT     icmp —  0.0.0.0/0            0.0.0.0/0
7    ACCEPT     tcp  —  195.191.226.102      0.0.0.0/0           tcp dpt:514
8    ACCEPT     tcp  —  91.218.228.236       0.0.0.0/0           tcp dpt:514

Что бы добавить правило перед 5:

# iptables -I INPUT 5 -i eth0 -p tcp –dport 8080 -j ACCEPT

Проверяем:

# iptables -L INPUT -n –line-numbers | grep 80
5    ACCEPT     tcp  —  0.0.0.0/0            0.0.0.0/0           tcp dpt:8080
6    ACCEPT     tcp  —  0.0.0.0/0            0.0.0.0/0           tcp dpt:80

Старое правло “подвинулось” на 6 строку, новое – стало 5.

Заблокировать входящие соединения для IP 8.8.8.8:

# iptables -I INPUT 7 -s 8.8.8.8 -j DROP

Проверяем:

# iptables -L INPUT -n –line-numbers | grep 8.8.8.8
7    DROP       all  —  8.8.8.8              0.0.0.0/0

Заблокировать исходящий ICMP на facebook.com:

# iptables -A OUTPUT -p icmp -d www.facebook.com -j DROP

Пробуем:

# ping 173.252.101.26
PING 173.252.101.26 (173.252.101.26) 56(84) bytes of data.
ping: sendmsg: Operation not permitted
ping: sendmsg: Operation not permitted

Посмотрим в правилах:

# iptables -L OUTPUT -n –line-numbers
Chain OUTPUT (policy ACCEPT)
num  target     prot opt source               destination
1    DROP       tcp  —  0.0.0.0/0            173.252.101.26

Использование MAC-адреса в правилах – разрешаем SSH только с MAC 00:60:ef:0b:f6:1a:

# iptables -A INPUT -p tcp –destination-port 22 -m mac –mac-source 00:60:ef:0b:f6:1a -j ACCEPT

Разрешить SSH с адресов начиная от 10.0.0.5 и до 10.0.0.10 включительно:

# iptables -A INPUT -p tcp –destination-port 22 -m iprange –src-range 10.0.0.5-10.0.0.10 -j ACCEPT

Ограничить количество параллельных соединений к серверу для одного адреса

Для ограничений используется connlimit модуль. Чтобы разрешить только 3 SSH соединения на одного клиента:

# iptables -A INPUT -p tcp –syn –dport 22 -m connlimit –connlimit-above 3 -j REJECT

Установить количество запросов HTTP до 20:

# iptables -p tcp –syn –dport 80 -m connlimit –connlimit-above 20 –connlimit-mask 24 -j DROP

Опции:

–connlimit-above 3: указывает, что правило действует только если количество соединений превышает 3;

–connlimit-mask
24: указывает маску сети.

Ссылки по теме:

http://konungr.ru

http://www.doless.ru

http://nikmy.ru

http://www.iptables.ru

http://www.opennet.ru

http://www.opennet.ru

http://rus-linux.net

http://cartmanees.blogspot.com

http://rusua.org.ua

http://www.fullautomatic.ru


  • Sergey
     

    > # Разрешаем SMTP но запрещаем отправку для адреса 77.120.***.46

    > $IPTABLES-A INPUT -s ! 77.120.***.1/24 -i eth0 -p tcp —dport 25 -j ACCEPT

    Это опечатка ? Или так должно быть ??

    •  

      Да, опечатка – копировал адрес из предыдущего примера 🙂 Спасибо, поправил.