V roce 2001 jsme publikovali seriál článků „Stavíme firewall“, který inspiroval překvapivé množství linuxových administrátorů ke tvorbě vlastního firewallu. Součástí článků byl i ukázkový script, který doporučoval mj. zablokovat adresní rozsah 96.0.0.0/4, který v té době byl rezervovaný. Protože nyní při nedostatku IPv4 adresního prostoru došlo k přerozdělování i těchto rozsahů může dojít k problémům, pokud jej váš firewall stále blokuje. Pokud jste tedy uvedený skript použili jako základ pro váš firewall, ujistěte se, že neblokujete nyní korektní rozsahy adres.
Kromě filtrovací tabulky, jejíž fungování jsme si ozřejmili minule, má linuxové jádro ještě další tabulku, kterou procházejí pakety a sice NAT (Network Adres Translation). Stejně jako filtrovací tabulka, i ona obsahuje tři řetězce, které se však tentokrát nepoužívají k filtrování paketů (i když i to je možné), ale jak už její název napovídá, ke změnám adresy datagramu. Funguje to tak, že pokud paket při průchodu vyhoví zadanému pravidlu, tak mu je podle určeného vzoru změněna adresa jeho odesílatele resp. příjemce podle určeného vzoru. Podle toho hovoříme buď o překladu adres odesílatele (SNAT – Source NAT) nebo překladu adres příjemce (DNAT – Destination NAT).
Podobně, jako jsme si minule ukázali strukturu filtrovací tabulky, tak si dnes naznačíme jak vypadá pouť datagramu NAT tabulkou:
- Příchozí pakety, ať už jejich destinace jakákoliv, prochází řetězcem PREROUTING, kde jim můžeme měnit adresu příjemce, tedy DNAT.
- Odchozí pakety, bez ohledu na odesílatele zase mohou být SNATovány (zamaskování adresy odesílatele) v řetězci POSTROUTING.
- Zvláštním případem je odchozí řetězec OUTPUT, který lze použít k DNATování paketů vzniklých pouze na lokálním počítači. V praxi se však OUTPUT DNAT používá jen zřídka.
SNAT
Příkladem použití SNATu je IP maškaráda, nebo-li zamaskování IP adresy routovaných paketů adresou routeru. Zní to komplikovaně, ale je to docela prosté. Představme si, že máme od poskytovatele připojení k dispozici jednu veřejnou IP adresu, ale potřebujeme k síti připojit větší množství počítačů. Proto veřejnou adresu přidělíme routeru, ostatním počítačům přidělíme privátní IP adresy, které jsou k tomuto účelu rezervovány podle RFC xxxx a do NAT tabulky routeru vložíme následující pravidlo:
iptables -t nat -A POSTROUTING -o eth0 -j SNAT --to 1.2.3.4
Pravidlo způsobí, že pokud ze sítě (řekněme z adresy 192.168.0.2) přijde paket, který má v úmyslu opustit router přes vnější rozhraní eth0, tak dojde k nahrazení jeho původní IP adresy za adresu 1.2.3.4. To znamená, že příjemce datagramu bude mít „pocit“ jako kdyby s ním nekomunikovala stanice s nesměrovatelnou adresou 192.168.0.2, ale přímo router 1.2.3.4, který stejně tak zajistí, aby se pakety v opačném směru dostaly zpátky k 192.168.0.2.
Na uvedeném příkaze si povšimněme, určení „-t nat“, což znamená, že pravidlo je určené k zapsání do NAT tabulky. Podobně bychom mohli pravidla do filtrovací tabulky uvádět příkazem „-t filter“, ovšem není to nutné, neboť „-t filter“ je implicitní příkaz, jak ostatně víme z předchozího článku.
Minule jsme si také uvedli jiný příklad definice maškarády:
iptables -t nat -A POSTROUTING -o eth0 -j MASQUERADE
Jaký je tedy v těchto dvou přístupech vlastně rozdíl? Oba dva fungují téměř stejně ovšem u druhého způsobu nemusíme při deklaraci uvádět maskovanou adresu. To je výhodné tehdy, když ji v okamžiku zavádění pravidla ještě neznáme, například pro to, že ji teprve získáme z DHCP serveru. První způsob naopak přináší možnost specifikovat ne jednu, ale rozsah adres, to když má náš router k dispozici několik veřejných adres:
iptables -t nat -A POSTROUTING -o eth0 -j SNAT --to 1.2.3.4-1.2.3.8
DNAT
Naopak DNAT použijeme tehdy, když potřebujeme měnit IP adresu adresáta datagramu. Používá se to při přesměrovávání datagramů na jiného adresáta. V dobách kernelů 2.0 a 2.2 jsme namísto DNATu používali různé speciální programy pro přesměrování portů, jako třeba ipmasqadm, ipfwd, portfwd, apod. Zkusme si uvést častý příklad, kdy máme někde v síti umístěný WWW server a rádi bychom na něj přesměrovali všechny požadavky směřující přes náš router:
iptables -t nat -A PREROUTING -p tcp --dport 80 -i eth0 \ -j DNAT --to 192.168.0.2:80
Tímto zápisem jsme zařídili, že pokud se na našem routeru objeví TCP segment určený pro port 80 (WWW server), tak se jeho cílová adresa přepíše na 192.168.0.2.i
Tím čím je „-j MASQUARADE“ pro SNAT je výraz „-j REDIRECT“ pro DNAT, tedy dává nám možnost přesměrovat datagram na jiný port bez znalosti přesné IP adresy. Chceme-li například použít program Squid na portu 3128 v režimu transparentní proxy přesměrujeme všechny HTTP požadavky na port 3128:
iptables -t nat -A PREROUTING -p tcp --dport 80 -i eth1 \ -j REDIRECT --to-port 3128
Poznámky
Nesmíme zapomínat na skutečnost, že když nějaký paket vyhověl pravidlu v NAT tabulce ještě neznamená, že má volný průchod paketovým filtrem. Vždy je třeba ještě povolit dané spojení ještě ve filtrovací tabulce, zejména pokud ji máme inicializovanou pro implicitní zákaz (DROP). Tak například pro výše uvedené přesměrování WWW serveru DNATem by bylo zapotřebí:
iptables -A FORWARD -i eth0 -p tcp -d 192.168.0.2 --dport 80 \ -m state --state NEW,ESTABLISHED,RELATED -j ACCEPT
Stejně tak pro správné fungování maškárady (SNATu) je nezbytné uvolnit směrování paketů a to oběma směry:
iptables -A FORWARD -i eth0 -o eth1 -m state \ --state ESTABLISHED,RELATED -k ACCEPT iptables -A FORWARD -i eth0 -o eth1 -j ACCEPT
V těchto příkladech, jsem tak trochu předběhl a použil další novinku v jádrech 2.4 – stavový firewall. Více o něm se dozvíme příště.
Rozdíl mezi filtrovací tabulkou a NAT tabulkou je také v tom, že zatímco filtrovací tabulkou prochází každý paket bez rozdílu, tak NAT tabulka je aktivní pouze pro první paket nového spojení. Proto tedy není vhodné používat NAT tabulku pro nějaké složité filtrování a když, tak pouze s podporou stavového firewallu (příště). S výhodou můžeme zahazování paketů v NAT tabulce použít jako ochranu před IP spoofingem z nesmyslných IP adres, prostě proto, že pravidla stačí jednou zapsat do PREROUTINGu a nemusíme je zdvojovat v INPUTu a FORWARDu:
iptables -t nat -A PREROUTING -i eth0 -s 192.168.0.0/16 -j DROP iptables -t nat -A PREROUTING -i eth0 -s 172.16.0.0/12 -j DROP iptables -t nat -A PREROUTING -i eth0 -s 10.0.0.0/8 -j DROP
Související odkazy