Скрипт проброса портов: OpenVZ + iptables

Один из механизмов автоматизации, когда на твоем сервере очень много OpenVZ-контейнеров с серыми IP, чаще всего им требуется не только доступ к интернет, но и проброс портов, чтобы извне заходить в сами контейнеры по SSH / FTP или любому другому протоколу, не важно. Конечно, как вариант, подходит ручная правка /etc/sysconfig/iptables и reload сервиса, но это не очень удобно и все-таки допускает «человеческий фактор», в данному случае скрипты автоматизации помогают нам.
Недавно наткнулся на интересную реализацию скрипта iptables, который смотрит запущенные контейнеры OpenVZ и автоматически пробрасывает порты на каждый контейнер, это очень удобно!

Рассмотрим его работу на примере, допустим у нас есть 3 контейнера OpenVZ:

# vzlist
      CTID      NPROC STATUS    IP_ADDR         HOSTNAME
        20         11 running   10.11.0.20      test1
        21         11 running   10.11.0.21      test2
        22         11 running   10.11.0.22      test3

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

# iptables -t nat -nvL
Chain PREROUTING (policy ACCEPT 19 packets, 1451 bytes)
 pkts bytes target     prot opt in     out     source               destination         

Chain POSTROUTING (policy ACCEPT 12 packets, 947 bytes)
 pkts bytes target     prot opt in     out     source               destination         

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

Однако бывают и проблемы, после установки ядра OpenVZ NAT на физической машине не работает, видим ошибку:

iptables v1.4.7: can't initialize iptables table `nat': Table does not exist (do you need to insmod?)

Исправить ситуацию можно без перезагрузки, если повезет :)

vi /etc/modprobe.d/openvz.conf
options nf_conntrack ip_conntrack_disable_ve0=1

меняем на

options nf_conntrack ip_conntrack_disable_ve0=0

Выгружаем модули:

rmmod iptable_nat
rmmod nf_nat
rmmod nf_conntrack_ipv4
rmmod nf_conntrack

Проверяем. Если не помогло, тогда требуется перезагрузка, увы!
Теперь настроим наш скрипт:

vi /etc/init.d/iptables.nat

#!/bin/bash
#
# iptables.ssh    This shell script enables ssh access from whitelist
#
# chkconfig:    - 99 12
#
# description:  Enable execution of SSH whitelist access
# processname   iptables.ssh
# config:       /etc/iptables.ssh
#

# source function library
. /etc/rc.d/init.d/functions

HN=`hostname`
IPTABLES=/sbin/iptables
ETH0_IP=`ifconfig eth0 2>/dev/null|awk '/inet addr:/ {print $2}'|sed 's/addr://'`
LANNET=10.11.0.0/24
VPNNET=172.16.10.0/24

start() {
$IPTABLES -t nat -N iptables.nat
reload

 $IPTABLES -t nat -A PREROUTING -i eth0 -j iptables.nat
 # exclude network from NAT (it's may be a problem when you use VPN)
 $IPTABLES -t nat -A POSTROUTING -d $VPNNET -o eth0 -j RETURN
 $IPTABLES -t nat -A POSTROUTING -s $LANNET -o eth0 -j SNAT --to-source $ETH0_IP
}

reload() {
$IPTABLES -t nat -F iptables.nat
VZL=`vzlist | grep running | grep 10.`
while read -r CTID T1 T2 CTIP T5  ; do
  PORT=`expr 2400 + $CTID`
  echo $CTIP
 $IPTABLES -t nat -A iptables.nat -i eth0 -p tcp -m tcp --dport $PORT -j DNAT --to-destination $CTIP:22
done <<< "$VZL"
}

stop() {
read -p "All rules will be removed! Are you sure (y/n)? " -n 1 -r
echo
if [[ ! $REPLY =~ ^[Yy]$ ]]
then
    echo "The action was canceled."
    exit 1
fi
  $IPTABLES -t nat -D PREROUTING -i eth0 -j iptables.nat
  $IPTABLES -t nat -D POSTROUTING -d $VPNNET -o eth0 -j RETURN
  $IPTABLES -t nat -D POSTROUTING -s $LANNET -o eth0 -j SNAT --to-source $ETH0_IP
  $IPTABLES -t nat -F iptables.nat
  $IPTABLES -t nat -X iptables.nat 

}

case "$1" in
  start)
        start
        ;;
  stop)
        stop
        ;;
  restart|force-reload)
        reload
        ;;
  reload)
	reload
        ;;
  *)
        echo $"Usage: $0 {start|stop|restart|reload|force-reload}"
        exit 1
esac

exit $RETVAL

Даем права на исполнение:

chmod +x /etc/init.d/iptables.nat

Запускаем и видим:

# /etc/init.d/iptables.nat start
10.11.0.20
10.11.0.21
10.11.0.22

Скрипт отработал и открыл доступ в интернет всем хостам, а также пробросил на каждый свой порт SSH, исключил из НАТ подсеть VPN (172.16.10.0/24):

# iptables -t nat -nvL
Chain PREROUTING (policy ACCEPT 12 packets, 812 bytes)
 pkts bytes target     prot opt in     out     source               destination
    7   452 iptables.nat  all  --  eth0   *       0.0.0.0/0            0.0.0.0/0           

Chain POSTROUTING (policy ACCEPT 12 packets, 812 bytes)
 pkts bytes target     prot opt in     out     source               destination
    0     0 RETURN     all  --  *      eth0    0.0.0.0/0            172.16.10.0/24
    0     0 SNAT       all  --  *      eth0    10.11.0.0/24         0.0.0.0/0           to:X.X.X.X

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

Chain iptables.nat (1 references)
 pkts bytes target     prot opt in     out     source               destination
    0     0 DNAT       tcp  --  eth0   *       0.0.0.0/0            0.0.0.0/0           tcp dpt:2420 to:10.11.0.20:22
    0     0 DNAT       tcp  --  eth0   *       0.0.0.0/0            0.0.0.0/0           tcp dpt:2421 to:10.11.0.21:22
    0     0 DNAT       tcp  --  eth0   *       0.0.0.0/0            0.0.0.0/0           tcp dpt:2422 to:10.11.0.22:22 

Пользуйтесь!

Related posts:

  1. Linux PPTP подключение IPTABLES и ошибка 619 Вот такая пара у нас образовалась. При подключении через Iptables...
  2. Скрипт сканирования портов для Linux Вопрос безопасности обычно встает очень остро по факту взлома системы,...
  3. НАШИ СКРИПТЫ: DHCP LINUX Скрипт dhcp.pl используется для передачи опции DHCP ‘classless static routes’...
  4. Flood скрипт, проверка защиты Вашего оборудования У каждого администратора по сетевой безопасности обязательно имеется свой набор...
  5. Asterisk – установка Fail2Ban Очень часто мы сталкиваемся с атаками на SIP-серверы, особенно когда...
You can leave a response, or trackback from your own site.

Оставить комментарий

*