Разговоры о iptables. Настройка NAT.

В этом видео я продолжу рассказ о утилите iptables.
Сегодня речь пойдёт о том:
– Как настроить NAT на вашем ubuntu сервере.
– Плюсы и минусы NAT.
– Какие проблемы есть у ipv4 адресов.
– Как решаются данные проблемы.
– Как настроить статический маршрут в Linux.
– Немного теории.

Сегодня я продолжаю рассказ о возможностях iptables в Linux. Речь сегодня пойдёт о достаточно простом в настройке, но не всегда простом в понимании механизме под названием NAT. Этот механизм встречается повсеместно. Если среди зрителей есть такие люди которые никогда не слышали о NAT, то вот пользовались им точно все. Если у вас дома есть ромашний роутер для подключения к провайдеру, то там есть NAT.
Из Википедии – NAT (от англ. Network Address Translation — «преобразование сетевых адресов») — это механизм в сетях TCP/IP, позволяющий преобразовывать IP-адреса транзитных пакетов.
Также имеет названия IP Masquerading, Network Masquerading и Native Address Translation.
По сути это замена одного ip-address’a на другой. В подавляющем большинстве случает производит подмену приватных адресов локальной сети, на публичный адрес выданный провайдером предоставляющим доступ в Интернет. Тут не обойтись без дополнительного разъяснения о том что такое приватные и публичные Ip-address. У меня же видео для начинающих специалистов! По этому об этом нужно рассказать.
Опять же цитата из Википедии – “IPv4 использует 32-битные (четырёхбайтные) адреса, ограничивающие адресное пространство 4 294 967 296 (232) возможными уникальными адресами.”

Как можно легко понять – количество этих адресов очень не велико, даже если всем жителям земли раздать по одному адресу, то всем не хватит. В настоящее время население Земли составляет более 7,3 миллиардов человек. Конечно не все пользуются Интернетом на Земле, но Ip адреса привязаны не к человеку, а к оборудованию – смартфону, компьютеру, планшету и тп. У многих особенно молодых людей всяких гаджетов больше одного – каждому нужен Ip-address. Я уже не говорю о всяком сетевом оборудование и серверах, систем “умный дом”, умные холодильники и носки – всем устройством нужен ip-address для доступа в Интернет и взаимодействия друг с другом. Плюс среди указанных адресов есть диапазоны которые зарезервированы для всяких служб или для тестов и не могут быть использованы.
В итоге у нас нет даже тех самых 4 миллиардов адресов, адресов мало. Нужно было что-то с этим делать, переходить на ipv6 народ был не готов (не всё оборудование и сейчас поддерживает ipv6). Для обычного пользователя сидящего дома или где-то в офисе, пользующего браузер для просмотра страничек, почтовый клиент и вконтактик совсем не обязательно иметь публичный ip-address. Публичные ip-address-а очень важны для работы серверов – чтобы все знали как к ним доступаться. Конечно, иметь публичный ip-address гораздо удобнее чем приватный, как-минимум проблем с настройкой NAT нету и любые приложения будут работать лучше (некоторые приложения не могу работать через NAT). Например, если вы сидите дома за своим роутером с приватным адресом, поднять веб сервер не получится (или если сказать уж совсем точно, то нужно будет делать доп. настройки, следить чтобы они не сбились, нигде не поменялись вдруг адреса и тп, что очень не удобно). В общем в условия ограниченного количества ip-address был придуман NAT.
Как я уже говорил – В подавляющем большинстве случает производит подмену приватных адресов локальной сети, на публичный адрес выданный провайдером предоставляющим доступ в Интернет. Таблица преобразований хранится в устройстве осуществляющем NAT. Дополнительно хочу сказать, что в этой таблице хранится информация о TCP/UDP портах для того чтобы точнее определять к какой сессии и каким адресам относится каждая трансляция.

В общем случае топология, схема сети в которой настраивают NAT выглядит следующим образом:
0-home internet connection and NAT
Есть роутер(пусть у нас будет сервер с двумя интерфейсами). Один интерфейс роутера смотрит в локальную сеть (Ethernet и WiFi), второй интерфейс подключён к Интернет провайдеру. В локальной сети (например, вашей домашней сети или сети вашей компании) у нас приватные адреса.
Например, из диапазона 192.168.0.0/16 . На интерфейсе смотрящем в сторону провайдера у нас какой-то публичный адрес, он всего один.
Для настройки NAT в данном случае нужно указать что адресам локальной сети при прохождении роутера в сторону Интернета нужно заменить source адрес на публичный адрес интерфейса подключённого к провайдеру.
Далее необходимо на роутере-сервере разрешить маршрутизацию – пересылку пакетов с одного интерфейса на другой.
Так же данный сервер-роутер должен иметь маршрут по-умолчанию. Обычно это маршрут в сторону провайдера Интернета.
… Конечно, тут можно придумать множество оговорок, но наиболее общая схема выглядит именно так. Если у вас есть вопросы или что-то не понятно – пиши в комментариях.

v38-my topology
Для сегодняшнего видео я собрал вот такую тестовую схему из трёх серверов (Сервера А, В и С).
Сервер В стоит, как видно на изображении, в центре. Он соединён с сервером А и С. Сервера А и С соединены напрямую только с В. По этому для доступа с сервера А к серверу С трафику придётся пройти через сервер В. Все указанные сервера конечно имеют ещё интерфейс по которому они подключены к виртуальному Виртуальному Хосту, но в данном случае это не повлияет на работу, так как сети 192.168.57.0/24 и 192.168.58/24 не имеют подключения к Виртуальному Хосту.
Сервер А – играет роль сервера, компьютера в локальной сети, сервер В играет роль маршрутизатора между локальной сетью с сервером А и Интернетом, в качестве Интернета выступает сервер С.

Теперь необходимо произвести настройки о которых я рассказывал ранее.
(1)- настроить маршрутизацию (маршрут по умолчанию) на локальной машине (А) и маршрутизаторе (В), если требуется;
(2)- разреришить маршрутизацию между интерфейсами на маршрутизаторе (В);
(3)- настроить NAT для адресов из локальной сети в адрес Интернет подключения(В).

Как вы могли заметить – все настройки производятся по большей части на сервере В, совсем немного на А. На сервере С настройки не производятся. Никто в Интернете не будет ничего настраивать для вас. Это важно понимать.

Итак. Для начала необходимо на локальной машине настроить маршрут по умолчанию – обычно это делать не нужно – настройки компьютеры получают по DHCP. В данном случае я добавлю статический маршрут на сеть 192.168.57.0 через сервер В, так как эта сеть доступна только через него. За одно покажу вам как производится настойки статических маршрутов.
В самом начале необходимо показать вам, что сервер С с адресом с 192.168.57.5 не доступен без доп. настроек – он не доступен.
А как показывает утилита tcpdump (смотри в видео) – на сервер не приходят пакеты от сервера А, а также вообще какие-либо icmp пакеты. О утилите tcpdump я ещё как-нибудь расскажу. Пока скажу, что данной утилитой можно отслеживать приходящие на сервер пакеты (от кого, какой пакет, на какой порт и тп) и много чего ещё.

(1)
Теперь добавим статический маршрут на сервере А:

sudo route add -net 192.168.57.0 netmask 255.255.255.0 gw 192.168.58.2 dev eth2
Данный маршрут если всё правильно будет занесён в текущую таблицу машрутизации и будет храниться там до перезагрузки или до удаления.
Посмотреть текущую таблицу маршрутизации можно командой:
netstat -rn
~$ netstat -rn
Kernel IP routing table
Destination Gateway Genmask Flags MSS Window irtt Iface
0.0.0.0 10.0.2.2 0.0.0.0 UG 0 0 0 eth0
10.0.2.0 0.0.0.0 255.255.255.0 U 0 0 0 eth0
169.254.0.0 0.0.0.0 255.255.0.0 U 0 0 0 eth1
192.168.56.0 0.0.0.0 255.255.255.0 U 0 0 0 eth1
192.168.57.0 192.168.58.2 255.255.255.0 UG 0 0 0 eth2 <<<<<<<<<<<<<<<<<<<< 192.168.58.0 0.0.0.0 255.255.255.0 U 0 0 0 eth2

Для сохранения маршрута на постоянной основе, его необходимо добавить в файл /etc/network/interfaces

Но сервер С по прежнему не доступен.

(2)
Теперь необходимо разрешить на сервере В маршрутизацию.
На текущий момент сервер В получает пакеты от сервера А, сервер В знает куда их нужно отправлять, но не переправляет, ему это делать пока нельзя.
:~$ sysctl net.ipv4.ip_forward
net.ipv4.ip_forward = 0

Теперь разрешим ему это делать:
Если вы работаете от root, то команда выглядит так:
echo 1 > /proc/sys/net/ipv4/ip_forward
Если нет, что более безопасно и правильно:
sudo sh -c "iptables-save > /etc/iptables.rules"
Теперь ему пересылать пакеты можно:
:~$ sysctl net.ipv4.ip_forward
net.ipv4.ip_forward = 1

Чтобы форвардинг автоматически включался при запуске системы
Открываем файл:
sudo nano /etc/sysctl.conf
и добавляем в него строчку:
net.ipv4.ip_forward = 1

Теперь, я запущу пинг с сервера А на сервер С.
Как видно, ответов по прежнему нет, но! На сервер С теперь приходят icmp request от сервера А. Мы видим что source ip-address у пакетов принадлежит серверу А. Всё по тому, что NAT у меня ещё не насроен на сервере В.
Ответы я не получаю, так как сервер С не знает правильный маршрут до сервера А (192.168.58.7).

(3)
Следующим шагом будет настройка NAT на сервере В.
Для этого нужно добавить следующее правило:
iptables -t nat -A POSTROUTING -s 192.168.58.0/24 -d 192.168.57.0/24 -o eth2 -j MASQUERADE

Этим правилом и по сути единственным производится настройка NAT для описанной в начале задачи(доп.инфо о iptables).
Этим правилом я добавляю в таблицу NAT, в цепочку POSTROUTING (структуру iptables см тут).

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

В этом правиле я могу указать какие конкретно адреса должны быть обработаны NAT (часто адреса не указывают, если у вас просто NAT для доступа в Интернет - то указывать конкретные адреса особого смысла нет).
Действие (-j) Masquerade работает только с таблицей NAT.
Из мануала

MASQUERADE
This target is only valid in the nat table, in the POSTROUTING chain. It should only be used with dynamically assigned IP (dialup) connections: if you have a static IP address, you should use the SNAT target. Masquerading is equivalent to specifying a mapping to the IP address of the interface the packet is going out, but also has the effect that connections are forgotten when the interface goes down. This is the correct behavior when the next dialup is unlikely to have the same interface address (and hence any established connections are lost anyway). It takes one option:
--to-ports port[-port]
This specifies a range of source ports to use, overriding the default SNAT source port-selection heuristics (see above). This is only valid if the rule also specifies -p tcp or -p udp.

Теперь нужно проверить, что всё работает.
Как мы видим, я могу пинговать сервер С с сервера А. На сервере С, в tcpdump мы видим входящие и! исходящие пакеты.
Но! Как мы видим source ip-address изменился, теперь это адрес сервера В.

За счёт подмены source ip-address, не пришлось ничего менять на сервере С. Сервер А получил доступ к серверу С с использованием адреса сервера В, а ip-address сервера B известен серверу С и он знает куда отправлять ответные пакеты.

После настройки и проверки, что всё работает, нужно сохранить настройки iptables.
sudo sh -c "iptables-save > /etc/iptables.rules"
Подробнее смотрите в моём посте - 'Как закрыть доступ к ssh с помощью iptables.'

На этом с настройкой всё. Настройки простые, но нужно точно понимать, что и зачем нужно.

Теперь хочу рассказать о дополнительных особенностях NAT, которые как мне думается особенно важны для понимания.
----------------------
Если вы вдруг занимаетесь настройкой сетевого оборудования, то советую обратиться к комментариям, описаниям процесса NAT на оборудовании вашего вендора. Это полезно знать - в какой момент происходит NAT, фильтрация, маршрутизация и тп:
Вот как это выглядит на оборудовании Cisco в IOS: NAT Order of Operation

С использованием NAT можно менять не только source ip-address, но и destination. Наиболее часто это используется для доступа к серверам находящимся за firewall, когда у компании нет свободных публичных адресов. Схема работы такая - Пакет из Интернета приходит на граничный сервер, на его публичный адрес настроенный на интерфейсе смотрящем в сторону Интернет провайдера, на определённый tcp-udp порт и преобразуется в приватный адрес одного из серверов в локальной сети, после чего отправляется непосредственно этому серверу.

Так же NAT может использоваться для настройки доступа в чужие сети с одного какого-то ip-address или изменение source, если в сети партнёра есть уже адреса source как и в вашей сети, если например подключаетесь через vpn в чужую сеть.
Такая ситуация может возникнуть в случае, если, например, происходит объединение локальных- корпоративных сетей каких-либо компаний. Или удалённый доступ в сети заказчиков (в ряде случаев доступ через терминательный сервер невозможен по причине несовместимости протоколов или его просто нет).

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

И последнее. NAT, не по основной задумке, а просто по факту повышает безопасность пользователей. Особенно тех кто ничего не понимает в работе компьютеров. У многих пользователей установлена какая-нибудь ОС, он её не настраивает, просто пользуется. Есть много запущенных служб - удалённый доступ, синхронизация, обмен файлами, печать и тп. Если у вас стоит домашний роутер, все компьютеры подключены за ним. Входящие соединения не разрешены по умолчанию - домашний NAT не пропускает входящие подключения в локальную сеть... Это огромный плюс и наверное ситуация с вирусами, ddos атаками была бы сильно хуже, если бы все повально не видели за NAT.
Различные умники могли бы пользоваться открытыми портами, простыми пользовательскими логин-паролями и делать разные нехорошие вещи.
----------------------
На этом всё.
Спасибо за внимание. Подписывайтесь на канал, задавайте вопросы в комментариях.
Удачи!