Avanti Indietro Indice

3. Packet Filtering

3.1 A Simple Scenario

Single machine with no forwarding: PPP interface

Only ident requests to come in from outside

3.2 A Simple Solution



iptables -A INPUT -i lo -j ACCEPT
iptables -P INPUT DROP

iptables -N LOGDROP
iptables -A LOGDROP --m limit --limit 5/hour -j LOG
iptables -A LOGDROP -j DROP

iptables -N ppp-incoming
iptables -A ppp-incoming -p ! tcp -f -j LOGDROP
iptables -A ppp-incoming -p tcp --dport ident -j ACCEPT
iptables -A ppp-incoming -p tcp ! --syn -j ACCEPT
iptables -A ppp-incoming -p udp --dport 53 -j ACCEPT
iptables -A ppp-incoming -p icmp --icmp-type destination-unreachable -j ACCEPT
iptables -A ppp-incoming -p icmp --icmp-type pong -j ACCEPT
iptables -A ppp-incoming -j LOGDROP

In ip-up script:

iptables -A INPUT -i $1 -j ppp-incoming

3.3 A More Realistic Scenario

Internal Network, DMZ

We have the following requirements:

Packet Filter box:

DMZ:

Mail server

Name server

Web server

Internal:

3.4 A Solution



for f in /proc/sys/net/ipv4/conf/*/rp_filter; do echo 1 > $f; done

iptables -A INPUT -i ! lo -j DROP
iptables -A OUTPUT -i ! lo -j DROP
iptables -A FORWARD -j DROP

ifconfig eth0 192.84.219.0 netmask 255.255.255.0
ifconfig eth1 192.168.1.0 netmask 255.255.255.0
pppd

route add default ppp0





iptables -N internal-dmz
iptables -N external-dmz
iptables -N internal-external
iptables -N dmz-internal
iptables -N dmz-external
iptables -N external-internal
iptables -N icmp-accept
iptables -N NEVER
iptables -N LOGDROP

iptables -A NEVER -j LOG --log-level alert --log-prefix "filter ERROR: "
iptables -A NEVER -j DROP

iptables -A LOGDROP -m limit -j LOG --log-prefix "filter: "
iptables -A LOGDROP -j DROP

iptables -A FORWARD -i eth1 -o eth0 -j internal-dmz
iptables -A FORWARD -i eth1 -o ppp0 -j internal-external
iptables -A FORWARD -i eth0 -o ppp0 -j dmz-external
iptables -A FORWARD -i eth0 -o eth1 -j dmz-internal
iptables -A FORWARD -i ppp0 -o eth0 -j external-dmz
iptables -A FORWARD -i ppp0 -o eth1 -j external-internal
iptables -A FORWARD -j NEVER

Define the icmp-accept chain:


iptables -A icmp-accept -p icmp --icmp-type destination-unreachable -j ACCEPT
iptables -A icmp-accept -p icmp --icmp-type source-quench -j ACCEPT
iptables -A icmp-accept -p icmp --icmp-type time-exceeded -j ACCEPT
iptables -A icmp-accept -p icmp --icmp-type parameter-problem -j ACCEPT

iptables -A internal-dmz -p tcp -d $MAILSERVER --dport smtp -j ACCEPT
iptables -A internal-dmz -p tcp -d $MAILSERVER --dport pop-3 -j ACCEPT
iptables -A internal-dmz -p udp -d $NAMESERVER --dport domain -j ACCEPT
iptables -A internal-dmz -p tcp -d $NAMESERVER --dport domain -j ACCEPT
iptables -A internal-dmz -p tcp -d $WEBSERVER --dport www -j ACCEPT
iptables -A internal-dmz -p tcp -d $WEBSERVER --dport rsync -j ACCEPT
iptables -A internal-dmz -p icmp -j icmp-accept
iptables -A internal-dmz -j LOGDROP

iptables -A external-dmz -p tcp -d $MAILSERVER --dport smtp -j ACCEPT
iptables -A external-dmz -p udp -d $NAMESERVER --dport domain -j ACCEPT
iptables -A external-dmz -p tcp -d $NAMESERVER --dport domain -j ACCEPT
iptables -A external-dmz -p tcp -d $WEBSERVER --dport www -j ACCEPT
iptables -A external-dmz -p icmp -j icmp-accept
iptables -A external-dmz -j DROP

iptables -A internal-external -p tcp --dport www -j ACCEPT
iptables -A internal-external -p tcp --dport ssh -j ACCEPT
iptables -A internal-external -p udp --dport 33434:33500 -j ACCEPT
iptables -A internal-external -p tcp --dport ftp -j ACCEPT
iptables -A internal-external -p tcp --dport 1024:65535 -j ACCEPT
iptables -A internal-external -p icmp --icmp-type ping -j ACCEPT
iptables -A internal-external -j LOG
iptables -A internal-external -j REJECT

iptables -A dmz-internal -p tcp ! --syn -s $MAILSERVER smtp -j ACCEPT
iptables -A dmz-internal -p udp -s $NAMESERVER domain -j ACCEPT
iptables -A dmz-internal -p tcp ! --syn -s $NAMESERVER domain -j ACCEPT
iptables -A dmz-internal -p tcp ! --syn -s $WEBSERVER www -j ACCEPT
iptables -A dmz-internal -p tcp ! --syn -s $WEBSERVER rsync -j ACCEPT
iptables -A dmz-internal -p icmp -j icmp-accept
iptables -A dmz-internal -j NEVER

iptables -A dmz-external -p tcp -s $MAILSERVER smtp -j ACCEPT
iptables -A dmz-external -p udp -s $NAMESERVER domain -j ACCEPT
iptables -A dmz-external -p tcp -s $NAMESERVER domain -j ACCEPT
iptables -A dmz-external -p tcp ! --syn -s $WEBSERVER www -j ACCEPT
iptables -A dmz-external -p icmp -j icmp-accept
iptables -A dmz-external -j NEVER

iptables -A external-internal -p tcp ! --syn --sport www -j ACCEPT
iptables -A external-internal -p tcp ! --syn --sport ssh -j ACCEPT
iptables -A external-internal -p tcp ! --syn --sport ftp -j ACCEPT
iptables -A external-internal -p tcp ! --syn --sport 1024:65535 -j ACCEPT
iptables -A external-internal -p icmp --icmp-type pong -j ACCEPT
iptables -A external-internal -j DROP




iptables -N external-if
iptables -N dmz-if
iptables -N internal-if

iptables -A INPUT -i ppp0 -j external-if
iptables -A INPUT -i eth0 -j dmz-if
iptables -A INPUT -i eth1 -j internal-if

iptables -A external-if -p icmp --icmp-type pong -j ACCEPT
iptables -A external-if -j icmp-accept
iptables -A external-if -j DROP

iptables -A dmz-if -p tcp ! --syn -s $NAMESERVER 53 -j ACCEPT
iptables -A dmz-if -p udp -s $NAMESERVER 53 -j ACCEPT
iptables -A dmz-if -p icmp --icmp-type pong -j ACCEPT
iptables -A dmz-if -j icmp-accept
iptables -A dmz-if -j NEVER

iptables -A internal-if -p icmp --icmp-type ping -j ACCEPT
iptables -A internal-if -p icmp --icmp-type pong -j ACCEPT
iptables -A internal-if -j icmp-accept
iptables -A internal-if -j LOGDROP

iptables -D 1 input
iptables -D 1 forward
iptables -D 1 output

3.5 Summary

Packet filtering this way is logical, but painful

Use routing's source verification

Define your allowed set thoroughly

Always limit external logging

Correct placement of LOG rules can help with problems


Avanti Indietro Indice                                 LINUXCARE