Настройка фаервола

Материал из Wiki МИАЦ ВО
Перейти к навигации Перейти к поиску

Описание скрипта фаервола

Вообще, прежде чем пытаться настроить фаервол, очень рекомендую прочитать Руководство по iptables (Iptables Tutorial 1.1.19). Также можно почитать сайт посвященный iptables.
Тут я приведу свой скрипт настройки фаервола, который почти целиком взят из этого описания, и может быть использован как основа для вашей системы. Если Вы найдете какие то замечания, прошу сообщить мне.

Немножкко о задаче.

  1. Есть сервер с двумя интерфейсами (eth0 и eth1)
    eth0 смотрит в интернет и его адрес 213.54.25.11
    eth1 смотрит в локальную сеть и его адрес 172.16.130.8
  2. Для доступа в интернет на сервере поднят VPN сервер с с адресом 192.168.5.1 и диаппазоном выдаваемых адресов 192.168.10.0/24
  3. Необходимо защитить сервер и с наружи и изнутри

Сам скрипт.

#!/bin/sh
#
#
# Этот скрипт для свободного распостранения. Вы можете его менять по своему
# усмотрению
# Он распостраняетяс под GNU General Public License.
# Никаких ГАРАНТИЙ нет, что он будет правильно работать
# Вы устанавливаете его на свой страх и риск.
#
# Сначала сбросим все правила, которые были до этого
/etc/init.d/iptables stop

###########################################################################
#
# 1. Configuration options.
#

#
# 1.1 Internet Configuration.
#


INET_IP="213.54.25.11"          # Арес интерфейса, который смотрит в интернет
INET_IFACE="eth0"               # Имя интерфейса
INET_BROADCAST="192.168.10.255"
LAN_VPN_RANGE="192.168.10.0/24" # Диапазон адресов VPN сети, имеющей доступ
                                # в инет
LAN_VPN="192.168.5.1"           # Адрес VPN сервера

#
# 1.1.1 DHCP
#

#
# 1.1.2 PPPoE
#

#
# 1.2 Local Area Network configuration.
#
# your LAN's IP range and localhost IP. /24 means to only use the first 24
# bits of the 32 bit IP address. the same as netmask 255.255.255.0
#

LAN_IP="172.16.130.8"           # Ip адрес интерфейса локальной сети
LAN_IP_RANGE="172.16.130.0/24"  # Диапазон адресов локальной сети
LAN_IFACE="eth1"                # Имя интерфейса локальной сети

#
# 1.3 DMZ Configuration.
#

#
# 1.4 Localhost Configuration.
#

LO_IFACE="lo"
LO_IP="127.0.0.1"

#
# 1.5 IPTables Configuration.
#
# Путь, где находится iptables.
IPTABLES="/usr/local/sbin/iptables"

#
# 1.6 Other Configuration.
#

###########################################################################
#
# 2. Module loading.
#

#
# Needed to initially load modules
#

/sbin/depmod -a

#
# 2.1 Загружаем необходимые модули
#

/sbin/modprobe ip_tables
/sbin/modprobe ip_conntrack
/sbin/modprobe iptable_filter
/sbin/modprobe iptable_mangle
/sbin/modprobe iptable_nat
/sbin/modprobe ipt_LOG
/sbin/modprobe ipt_limit
/sbin/modprobe ipt_state
/sbin/modprobe ipt_owner
/sbin/modprobe ipt_REJECT
/sbin/modprobe ipt_MASQUERADE
/sbin/modprobe ip_conntrack_ftp
/sbin/modprobe ip_conntrack_irc
/sbin/modprobe ip_nat_ftp
/sbin/modprobe ip_nat_irc
# Модули для работы pptp
/sbin/modprobe ip_conntrack_pptp
/sbin/modprobe ip_nat_pptp
/sbin/modprobe ip_gre



#
# 2.2 Non-Required modules
#

###########################################################################
#
# 3. /proc set up.
#

#
# 3.1 Required proc configuration
#

# активация TCP SYN Cookie Protection
echo "1" > /proc/sys/net/ipv4/tcp_syncookies

# отключение IP Source Routing
echo "0" > /proc/sys/net/ipv4/conf/all/accept_source_route

# отключение ICMP Redirect
#echo 0 > /proc/sys/net/ipv4/conf/all/accept_redirects

# активация IP Spoofing Protection
echo "1" >  /proc/sys/net/ipv4/conf/all/rp_filter

# игнорирование Broadcast Request
echo "1" > /proc/sys/net/ipv4/icmp_echo_ignore_broadcasts

# сообщения о Bad Error Message
echo "1" >  /proc/sys/net/ipv4/icmp_ignore_bogus_error_responses

echo "1" > /proc/sys/net/ipv4/ip_forward

# Если сильно достают неправильные пакеты (martian source)в логах
# отключаем лог martian source на всех интерфейсах
#echo "0" > /proc/sys/net/ipv4/conf/all/log_martians



#
# 3.2 Non-Required proc configuration
#

#echo "1" > /proc/sys/net/ipv4/conf/all/rp_filter
#echo "1" > /proc/sys/net/ipv4/conf/all/proxy_arp
#echo "1" > /proc/sys/net/ipv4/ip_dynaddr

###########################################################################
#
# 4. rules set up.
#

######
# 4.1 Filter table
#

#
# 4.1.1 Установка политики по умолчанию
#
#set -x
$IPTABLES -P INPUT DROP
$IPTABLES -P OUTPUT DROP
$IPTABLES -P FORWARD DROP
#$IPTABLES -P INPUT ACCEPT
#$IPTABLES -P OUTPUT ACCEPT
#$IPTABLES -P FORWARD ACCEPT
# По умолчанию все запретить
#
# 4.1.2 Создание пользовательских цепочек, которые будут использоваться
# позже.

#
# Цепочка для  bad tcp packets
#

$IPTABLES -N bad_tcp_packets

#
# Создание раздельных цепочек для прохождения ICMP, TCP and UDP пакетов
#

$IPTABLES -N allowed
$IPTABLES -N tcp_packets
$IPTABLES -N udp_packets
$IPTABLES -N icmp_packets

#
# 4.1.3 Create content in userspecified chains
#

#
# bad_tcp_packets chain
#

$IPTABLES -A bad_tcp_packets -p tcp --tcp-flags SYN,ACK SYN,ACK \
-m state --state NEW -j REJECT --reject-with tcp-reset
$IPTABLES -A bad_tcp_packets -p tcp ! --syn -m state --state NEW -j LOG \
--log-prefix "New not syn:"
$IPTABLES -A bad_tcp_packets -p tcp ! --syn -m state --state NEW -j DROP

#
# allowed chain
#

$IPTABLES -A allowed -p TCP --syn -j ACCEPT
$IPTABLES -A allowed -p TCP -m state --state ESTABLISHED,RELATED -j ACCEPT
$IPTABLES -A allowed -p TCP -j DROP

#
# TCP rules
#
# Создаем правила для TCP пакетов ( ту мы открываем общие порты для внутренней
# и внешней сети)
for i in 21 22 25 53 80 110 113 123 443 465 1723 5190 10000
     do
        $IPTABLES -A tcp_packets -p TCP -s 0/0 --dport $i -j allowed
done
# 21 - ftp порт
# 22 - ssh порт
# 25 - smtp
# 53 - DNS
# 80 - http
# 110 - pop3
# 113 - INETTD
# 123 - NTP служба точного времени
# 445 - SMB
# 443 - HTTPS
# 465 - SMTPS
# 24537 - Torrent agent
# 6667- Интернет reley chat
# 1194 - openVPN
# 1723 - VPN
# 5190 - ICQ
# 10000 - WEBMIN
# 16384-16394- Голосовая почта


# 3128- squid только для внутренней  VPN сети
#
$IPTABLES -A tcp_packets -p TCP -s $LAN_VPN_RANGE --dport 3128 -j allowed
# Открываем порты для Samba только для внутренней сети
#$IPTABLES -A INPUT -p TCP -s $LAN_IP_RANGE  --dport 137:139 -j ACCEPT
#$IPTABLES -A INPUT -p UDP -s $LAN_IP_RANGE  --destination-port 137:139 -j ACCEPT

#
# UDP ports
#
for i in 53 123 1000:1060 4000
    do
        $IPTABLES -A udp_packets -p UDP -s 0/0 --dport $i -j ACCEPT
done
# 53 DNS
# 123 NTP служба точного времени
# 2074 передача голоса
#
# 1000:1060 - при проблемах с DNS
# На клиенте (в винде) запускаем ipconfig /all и видим dns, скажем, 1.2.3.4 
# С клиента же делаем пинг 1.2.3.4 - он есть
# С клиента же делаем пинг ya.ru - пинга нет
#
# 4000 ICQ
# 1194 - openVPN


#
# In Microsoft Networks you will be swamped by broadcasts. These lines
# will prevent them from showing up in the logs.
#

#$IPTABLES -A udp_packets -p UDP -i $INET_IFACE -d $INET_BROADCAST \
#--destination-port 135:139 -j DROP

#
# If we get DHCP requests from the Outside of our network, our logs will
# be swamped as well. This rule will block them from getting logged.
#

#$IPTABLES -A udp_packets -p UDP -i $INET_IFACE -d 255.255.255.255 \
#--destination-port 67:68 -j DROP

#
# ICMP rules
#

$IPTABLES -A icmp_packets -p ICMP -s 0/0 --icmp-type 8 -j ACCEPT
$IPTABLES -A icmp_packets -p ICMP -s 0/0 --icmp-type 11 -j ACCEPT

# разрешаем gre траффик
$IPTABLES -A INPUT -s 0/0 -d 0/0  -p gre -j ACCEPT


#
# 4.1.4 INPUT chain
#

#
# Bad TCP packets we don't want.
#

$IPTABLES -A INPUT -p tcp -j bad_tcp_packets

#
# Тут мы разрешаем пакеты со спец сети  not part of the Internet
#

$IPTABLES -A INPUT -p ALL -i $LO_IFACE -s $LO_IP -j ACCEPT


# Данным IP адресам полностью доверяем
#$IPTABLES -A INPUT -p ALL -s 172.16.130.1   -j ACCEPT
#$IPTABLES -A INPUT -p ALL -s 172.16.130.101   -j ACCEPT
#$IPTABLES -A INPUT -p ALL -s 172.16.130.102   -j ACCEPT

#
# Правила для входящих пакетов с любой сети.
#

$IPTABLES -A INPUT -p ALL -d $INET_IP -m state --state ESTABLISHED,RELATED -j ACCEPT
$IPTABLES -A INPUT -p ALL -d $LAN_IP -m state --state ESTABLISHED,RELATED -j ACCEPT
$IPTABLES -A INPUT -p ALL -d $LAN_VPN -m state --state ESTABLISHED,RELATED -j ACCEPT
$IPTABLES -A INPUT -p TCP -j tcp_packets
$IPTABLES -A INPUT -p UDP -j udp_packets
$IPTABLES -A INPUT -p ICMP -j icmp_packets


#Anti-ssh-bruteforce
# После 3 попыток подключиться в течение 60 секунд, робот блокируется и отваливает :)
# и прочти нет мусора в логах, а главное - лишнего траффика, в отличие от pam_abl.
# По желанию можно увеличить параметры --hitcount и --seconds.
$IPTABLES -A INPUT -p tcp --syn --dport 22 -m recent --name radiator --set
$IPTABLES -A INPUT -p tcp --syn --dport 22 -m recent --name radiator --update --seconds 60 --hitcount 3 -j DROP

#
# If you have a Microsoft Network on the outside of your firewall, you may
# also get flooded by Multicasts. We drop them so we do not get flooded by
# logs
#

#$IPTABLES -A INPUT -i $INET_IFACE -d 224.0.0.0/8 -j DROP

#
# Log weird packets that don't match the above.
#

$IPTABLES -A INPUT -m limit --limit 3/minute --limit-burst 3 -j LOG \
--log-level DEBUG --log-prefix "IPT INPUT packet died: "

#
# 4.1.5 Правила для проходящих пакетов
#

#
# Bad TCP packets we don't want
#

$IPTABLES -A FORWARD -p tcp -j bad_tcp_packets

#
# Accept the packets we actually want to forward
#

$IPTABLES -A FORWARD -p TCP -j  tcp_packets
$IPTABLES -A FORWARD -p UDP -j udp_packets
$IPTABLES -A FORWARD -p ICMP -j icmp_packets


$IPTABLES -A FORWARD -m state --state ESTABLISHED,RELATED -j ACCEPT

#
# Log weird packets that don't match the above.
#

$IPTABLES -A FORWARD -m limit --limit 3/minute --limit-burst 3 -j LOG \
--log-level DEBUG --log-prefix "IPT FORWARD packet died: "

#
# 4.1.6 Правила для исходящих пакетов
#

#
# Bad TCP packets we don't want.
#

$IPTABLES -A OUTPUT -p tcp -j bad_tcp_packets

#
# Special OUTPUT rules to decide which IP's to allow.
#

$IPTABLES -A OUTPUT -p ALL -s $LO_IP -j ACCEPT
$IPTABLES -A OUTPUT -p ALL -s $LAN_IP -j ACCEPT
$IPTABLES -A OUTPUT -p ALL -s $INET_IP -j ACCEPT
$IPTABLES -A OUTPUT -p ALL -s $LAN_VPN   -j ACCEPT
#
# Log weird packets that don't match the above.
#

$IPTABLES -A OUTPUT -m limit --limit 3/minute --limit-burst 3 -j LOG \
--log-level DEBUG --log-prefix "IPT OUTPUT packet died: "

######
# 4.2 nat table
#

#
# 4.2.1 Set policies
#

#
# 4.2.2 Create user specified chains
#

#
# 4.2.3 Create content in user specified chains
#

#
# 4.2.4 PREROUTING chain
#
# Организуем празрачный прокси

$IPTABLES -t nat -A PREROUTING  -s $LAN_VPN_RANGE -p tcp -m tcp --dport 80 -j REDIRECT --to-ports 3128

#
# 4.2.5 POSTROUTING chain
#

#
# Enable simple IP Forwarding and Network Address Translation
#
# Делаем NAT
$IPTABLES -t nat -A POSTROUTING  -s $LAN_VPN_RANGE -j SNAT --to-source $INET_IP
#
# 4.2.6 OUTPUT chain
#

######
# 4.3 mangle table
#

#
# 4.3.1 Set policies
#

#
# 4.3.2 Create user specified chains
#
# 4.3.3 Create content in user specified chains
#

#
# 4.3.4 PREROUTING chain
#

#
# 4.3.5 INPUT chain
#

#
# 4.3.6 FORWARD chain
#

#
# 4.3.7 OUTPUT chain
#

#
# 4.3.8 POSTROUTING chain
#

Ошибки при работе DNS

Вобщем столкнулся с такой проблемой.
На клиенте (в винде) запускаем ipconfig /all и видим dns, скажем, 1.2.3.4
С клиента же делаем пинг 1.2.3.4 - он есть
С клиента же делаем пинг ya.ru - пинга нет
Решилось откритием портов UDP c 1000 по 1060.
В скрипте это отражено.

При использовании VPN подключения к провайдеру

Тут оказалось не все так просто.

  1. VPN соединение к провайдеру может подняться не сразу, а через некоторое время, поэтому могут быть проблемы с default route.
Вот одно из решений данной проблемы.

Подключение к провайдеру через VPN канал

  1. Сначала установим пакет pptp-command*.rpm
  2. Настроим соединение
  3. Далее в /etc/rc.d/rc.local добавляем строки
# Поднимаем VPN соединение до провайдера с именем navb
pptp-command start navb
# Удаляем default route
route del default
# Поднимаем defaut route
route add default ppp0
# Запускаем фаервол
/etc/sysconfig/iptables.sh

Скрипт по проверке и поднятию default route

Тк соединение может установиться не сразу, то команда

route add default ppp0

может не сработать.

Для последующего поднятия default route делаем следующий скрипт (/etc/scripts/route_exist.sh).
В этом же скрипте запускаем службу VPN сервера (pptpd), что бы не было захвата интерфейса ppp0, запускаем фаервол - после определения внешнего ip VPN соединения и запуск службы динамического DNS.

#!/bin/bash
# set -x
# Если соединение есть, но нет default route, то
if [ -z "`ip route| grep ppp0 | grep default`" ]; then
    route del default
    route add default ppp0
    # Запускаем фаервол
    /etc/sysconfig/iptables.sh
    echo "$date1        $IP_BL" >> file.int
fi
# Если пинг не проходит - потеря 100%, то перезапускаем соединение
if [ -n "`ping  -w5 -W2 -q www.ru | grep 100%`" ]; then
    pptp-command stop
fi
# Проверяем поднят ли интерфейс ppp0
if [ -z "`ip route | grep ppp0`" ]; then
    # Если нет, то поднять
    pptp-command start navb
    # Находим ip адрес нового соединения
    IP_BL=`ifconfig  ppp0 | grep -A 1 ppp0| grep inet |cut -d ":" -f2 |cut -d " " -f1`
    #echo 2
    date1=`date`
    #set -x
    route del default
    route add default ppp0
    # Если сервис pptpd не запущен, то запускаем
    service pptpd start
    # Запускаем фаервол
    /etc/sysconfig/iptables.sh
    # Send new ip address to no-ip.com
    /usr/local/bin/noip2 -i $IP_BL
    # Запускаем програму динамического имени
    /etc/init.d/noip2 start
    echo "$date1        $IP_BL" >> file.int
fi

И запускаем его из cron каждые 5 минут. Для этого добавляем следующие строки в /etc/crontab

# Проверка и поднятие default route
*/5 *  *  *  *   root    /etc/scripts/route_exist.sh

Изменения в файле фаервола /etc/sysconfig/iptables.sh

Оперделения интерфейса VPN подключения к провайдеру (при динамическом ip).
# Арес интерфейса, который смотрит в интернет
INET_IP=`ifconfig | grep -A 1 ppp0| grep inet |cut -d ":" -f2 |cut -d " " -f1`
И все строчки, где есть переменная $INET_IP проверяем на наличие этого ip адреса
Например:
if [ -n "$INET_IP" ]; then
    $IPTABLES -A INPUT -p ALL -i $LO_IFACE -s $INET_IP -j ACCEPT
fi