Iptables

Aus SchnallIchNet
Wechseln zu: Navigation, Suche

Chain order

IPTables/EBTables Packet Flow
		mangle: PREROUTING
		         |
		         Y
		nat: PREROUTING
		|               \
		Y                \
	mangle: INPUT             \
	      |			   \
	      Y			   |
	filter: INPUT		   Y
-----------------------       mangle: FORWARD
	mangle: OUTPUT		   |
	      |			   Y
	      Y			filter: FORWARD
	nat: OUTPUT		   |
	      |			   |
	      Y			   Y
	filter: OUTPUT ------>	mangle: POSTROUTING
-- 				   |
				   Y
				nat: POSTROUTING
				   |
				   Y
				NETWORK-CARD


Snippets

some snippets to do useful things ;-)


INVALID

drop all traffic with an "INVALID" state match

iptables -A INPUT -m conntrack --ctstate INVALID -j DROP
Achtung.jpeg rule will drop all packets with invalid headers or checksums, invalid TCP flags, invalid ICMP messages (such as a port unreachable when we did not send anything to the host), and out of sequence packets which can be caused by sequence prediction or other similar attacks.
Achtung.jpeg ICMPv6 Neighbor Discovery packets remain untracked, and will always be classified "INVALID" though they are not corrupted or thelike. Keep this in mind, and accept them before this rule! iptables -A INPUT -p 41 -j ACCEPT


Block APNIC/CN completely

block the whole CN-iplist for port 22
perhaps integrate some caching...

wget -O- ftp://ftp.apnic.net/apnic/stats/apnic/delegated-apnic-extended-latest | awk -F'|' '$2 == "CN" && $3 == "ipv4" { print $4" "$5 }' | \
   while read line; do
      IP=`echo $line | awk '{print $1}'`;
      HOSTS=`echo $line | awk '{print $2}'`;
      HLP=`echo "obase=2;ibase=10;$HOSTS" | bc | wc -c`;
      MASK=`echo "32-($HLP-2)" | bc`;
      $IPTABLES -A INPUT -i $EXT_IF -s $IP/$MASK -p tcp --dport 22 -j nirwana;
   done

explanation:
========================

  1. wget the APNIC delegated ip's from APNIC-FTP-Server
  2. print only spec. lines:
    1. that match country 'CN' ($2) AND
    2. that match IP version 4 'ipv4' ($3)
  3. print network-address ($4) and number of hosts ($5)
  4. pipe values to while-loop
  5. put IP and number of HOSTS into variables
  6. calculate BitMask of network (MASK)
  7. run iptables-command ...

modify the iptables command to your needs...
for me blocking of port 22 is enough...


Skeleton

#!/bin/bash
#
# firewall-script mit iptables
# By Christoph Steidl - (c) 1999
#

# iptables binary
IPTABLES=/sbin/iptables
# iptables with Layer7-Patch
#IPTABLES=/usr/local/sbin/iptables
# iproute2
IP_BIN=/sbin/ip

# netzwerke
NETWORK=123.123.123.0/24
LAN=10.10.10.0/24

### Interfaces
EXT_IF=eth0
IPSEC_IF=$EXT_IF
#IPSEC_IF=ipsec0
INT_IF=eth1

### Hosts

### Marks (be sure to use like bitmask: 1,2,4,8,16)
# ipsec-mark if something comes from ipsec-tunnel
IPSEC_MARK=1
NoMASQ=2
ANYTHING_MARK=4
ANYTHING2_MARK=8

case "$1" in
	start)
		echo " "
		echo "Starting Firewall..."
		echo "Enabling IP-Forward..."
		echo " "
		# /proc setup
		#
		# Das Paket-Forwarding aktivieren
		echo "1" > /proc/sys/net/ipv4/ip_forward
		
		# Support für dynamische IP-Adressen von
		# Dial-Up-Interfaces aktivieren.
		echo "0" > /proc/sys/net/ipv4/ip_dynaddr
		
		for iface in /proc/sys/net/ipv4/conf/*; do
			# IP spoofing-Schutz aktivieren
			echo "0" > $iface/rp_filter
			echo "0" > $iface/accept_redirects
			# Ungültige IP-Pakete loggen
			echo "1" > $iface/log_martians
			# icmp-redirect ausschalten (ipsec)
			if [ $iface != "eth0" ]; then
				echo 0 > $iface/send_redirects
			fi
		done
		
		# SYN cookie protection aktivieren
		echo "1" > /proc/sys/net/ipv4/tcp_syncookies
		
		# Keine ungültigen ICMP-Pakete loggen, da davon
		# sehr viele auftreten können
		echo "1" > /proc/sys/net/ipv4/icmp_ignore_bogus_error_responses
		
		# Keine ICMP-Packete akzeptieren,
		# sprich keine Pings mehr beantworten
		#echo "1" > /proc/sys/net/ipv4/icmp_echo_ignore_all
		echo "1" > /proc/sys/net/ipv4/icmp_echo_ignore_broadcasts
		
		##########################
		# FIREWALL CONFIGURATION #
		##########################
		# Alle Tables leeren
		$IPTABLES -F                    #Flush Filter-Chains
		$IPTABLES -t nat -F             #Fulsh NAT-Chains
		$IPTABLES -t mangle -F          #Fulsh Mangle-Chains
		$IPTABLES -X                    #Loesche alle Non-Buildin Chains
		
		# Alle default-Policies auf DROP, damit keine Lücken beim Aufbau
		# der Firewall entstehen
		$IPTABLES -P INPUT DROP
		$IPTABLES -P OUTPUT DROP
		$IPTABLES -P FORWARD DROP
		
		# Die NAT-/MANGLE-Chains bleiben auf ACCEPT, Pakete werden nur im
		# Filter-Table verworfen.
		$IPTABLES -t nat -P PREROUTING ACCEPT
		$IPTABLES -t nat -P POSTROUTING ACCEPT
		$IPTABLES -t nat -P OUTPUT ACCEPT
                $IPTABLES -t mangle -P PREROUTING ACCEPT
		$IPTABLES -t mangle -P POSTROUTING ACCEPT
		$IPTABLES -t mangle -P OUTPUT ACCEPT
		
		###################
		# IP TABLES rules #
		###################
		
		### MY Chains
		
		# neue kette namens nirwana anlegen und fuers logging definieren
		$IPTABLES -N nirwana
		$IPTABLES -A nirwana -p TCP -j LOG --log-prefix "NIRWANA_TCP: "
		$IPTABLES -A nirwana -p TCP -j DROP 
		$IPTABLES -A nirwana -p UDP -j LOG --log-prefix "NIRWANA_UDP: "
		$IPTABLES -A nirwana -p UDP -j DROP
		$IPTABLES -A nirwana -p ICMP -j LOG --log-prefix "NIRWANA_ICMP: "
		$IPTABLES -A nirwana -p ICMP -j DROP 
		$IPTABLES -A nirwana -p 50 -j LOG --log-prefix "NIRWANA_ESP: "
		$IPTABLES -A nirwana -p 50 -j DROP
		$IPTABLES -A nirwana -p 51 -j LOG --log-prefix "NIRWANA_AH: "
		$IPTABLES -A nirwana -p 51 -j DROP
		$IPTABLES -A nirwana -j LOG --log-prefix "NIRWANA_UNKNOWN: "
		$IPTABLES -A nirwana -j DROP
		
		
		###
		### MANGLE --> PREROUTING
		###
		
		### ipsec
		# mark incomming packets
		$IPTABLES -t mangle -A PREROUTING -i $IPSEC_IF -p 50 -j MARK --set-mark $IPSEC_MARK
		$IPTABLES -t mangle -A PREROUTING -i $IPSEC_IF -p 50 -m esp --espspi 500:520 -j MARK --set-mark $IPSEC_MARK
		
		# Change Routing -- TODO: PATCH NEEDED???? plz check it!!!
		#$IPTABLES -t mangle -A PREROUTING -i $INT_IF -d 10.11.0.0/18 -j ROUTE --gw 10.10.11.4
		#$IPTABLES -t mangle -A PREROUTING -i $INT_IF -d 10.12.0.0/24 -j ROUTE --gw 10.10.11.4
		#$IPTABLES -t mangle -A PREROUTING -i $INT_IF -d 10.12.1.0/24 -j ROUTE --gw 10.10.11.4
		
		###
		### NAT --> PREROUTING
		###
		
		
		###
		### MANGLE --> INPUT / OUTPUT / FORWARD
		###
		
		#
		##
		#### Should be done in PRE- / POST-ROUTING
		#### try to put your rules there!!
		#### NO RULES HERE if possible
		##
		#
		
		
		
		###
		### NAT --> OUTPUT
		###
		
		
		
		###
		### FILTER --> INPUT / OUTPUT / FORWARD
		###
		
		##### DROP-Zone #####
		
		# temporary block for testing
		#$IPTABLES -A FORWARD -i $INT_IF -o $EXT_IF -p tcp --dport 7001:7002 -j DROP
		
		##### End DROP-Zone #####

		# set MTU to path mtu
		$IPTABLES -A FORWARD -p tcp --tcp-flags SYN,RST SYN -j TCPMSS --clamp-mss-to-pmtu

		### EXTERNE Verbindungen gestatten z.B. SMTP, DNS, IMAPs  oder SSH-Connections
		### Locale Dienste
		# erlaube alles von trusted IPs
		$IPTABLES -A INPUT -i $EXT_IF -s $TRUSTED_SOURCE_IP -j ACCEPT
		$IPTABLES -A FORWARD -i $EXT_IF -s $TRUSTED_SOURCE_IP -j ACCEPT
		# limit ssh from non-trusted ip's
		$IPTABLES -A INPUT -p tcp --dport 22 -m state --state NEW -m recent --set --name SSH
		$IPTABLES -A INPUT -p tcp --dport 22 -m state --state NEW -m recent --update --seconds 60 --hitcount 4 --rttl --name SSH -j nirwana
		$IPTABLES -A INPUT -i $EXT_IF -p tcp --dport 22 -j ACCEPT
		
		# erlaube ipsec
		$IPTABLES -A INPUT -p udp --dport 500 -j ACCEPT			# IPSec
		$IPTABLES -A INPUT -p udp --dport 4500 -j ACCEPT		# NAT-Traversal
		$IPTABLES -A FORWARD -p udp --dport 4500 -j ACCEPT		# NAT-Traversal
		$IPTABLES -A INPUT -p 50 -j ACCEPT							# ESP
		$IPTABLES -A INPUT -p 51 -j ACCEPT							# AH
		
		# ipsec-rules ()
		# if any ipsec-network is untrusted add the following for
		# all or the specific rule:
		# -m state --state ESTABLISHED,RELATED
		$IPTABLES -A FORWARD -i $IPSEC_IF -s 192.168.0.0/16 -m mark --mark $IPSEC_MARK -j ACCEPT
		$IPTABLES -A INPUT -i $IPSEC_IF -s 192.168.0.0/16 -m mark --mark $IPSEC_MARK -j ACCEPT
		$IPTABLES -A FORWARD -i $IPSEC_IF -s 172.16.0.0/12 -m mark --mark $IPSEC_MARK -j ACCEPT
		$IPTABLES -A INPUT -i $IPSEC_IF -s 172.16.0.0/12 -m mark --mark $IPSEC_MARK -j ACCEPT
		$IPTABLES -A FORWARD -i $IPSEC_IF -s 10.0.0.0/8 -m mark --mark $IPSEC_MARK -j ACCEPT
		$IPTABLES -A INPUT -i $IPSEC_IF -s 10.0.0.0/8 -m mark --mark $IPSEC_MARK -j ACCEPT
		
		# Aktive FTP-Data-Connections auch für Hosts hinter
		# der Firewall zulassen
		$IPTABLES -A FORWARD -p tcp --sport 20 -m state --state ESTABLISHED,RELATED -j ACCEPT
		$IPTABLES -A FORWARD -p tcp --dport 20 -m state --state ESTABLISHED,RELATED -j ACCEPT
		$IPTABLES -A INPUT   -p tcp --sport 20 -m state --state ESTABLISHED,RELATED -j ACCEPT
		$IPTABLES -A INPUT   -p tcp --dport 20 -m state --state ESTABLISHED,RELATED -j ACCEPT
		$IPTABLES -A OUTPUT  -p tcp --sport 20 -m state --state ESTABLISHED,RELATED -j ACCEPT
		$IPTABLES -A OUTPUT  -p tcp --dport 20 -m state --state ESTABLISHED,RELATED -j ACCEPT

		# Pakete, die zu einer lokal aufgebauten Verbindung gehoeren,
		# werden akzeptiert.
		$IPTABLES -A INPUT   -i $EXT_IF -m state --state ESTABLISHED,RELATED -j ACCEPT
		$IPTABLES -A FORWARD -i $EXT_IF -m state --state ESTABLISHED,RELATED -j ACCEPT
		
		# Lokal generierte Pakete dürfen verschickt werden
		$IPTABLES -A OUTPUT -o $EXT_IF -j ACCEPT
		$IPTABLES -A OUTPUT -o $INT_IF -j ACCEPT
		$IPTABLES -A OUTPUT -o $DMZ_IF -j ACCEPT
		
		# Über das Local-Loopback-Device darf alles verschickt
		# werden
		$IPTABLES -A INPUT -i lo -j ACCEPT
		$IPTABLES -A OUTPUT -o lo -j ACCEPT
			
		# Aus dem internen Netz werden alle Pakete angenommen,
		# weiterhin werden alle Pakete nach draussen weitergeschickt.
		$IPTABLES -A INPUT -i $INT_IF -s $NETWORK -j ACCEPT
		$IPTABLES -A OUTPUT -o $INT_IF -d $NETWORK -j ACCEPT
		$IPTABLES -A FORWARD -i $INT_IF -s $NETWORK -j ACCEPT

		# alle packete der input- und forwardkette werden als letztes
		# in die kette nirwana geleitet (LOG and DROP all)
		$IPTABLES -A FORWARD -j nirwana
		$IPTABLES -A INPUT -j nirwana
		$IPTABLES -A OUTPUT -j nirwana
		
		
		###
		### MANGLE --> POSTROUTING
		###
		
		# Alle Pakete, die vom Internen Netzwerk ins Internet gehen, 
		# werden maskiert 
		# ATTENTION!!! IPSec is not longer interface ipsec0, its ppp0 now which is the external, too!
		# For this reason we had to check destination before masquerading!!
		$IPTABLES -t mangle -A POSTROUTING -o $EXT_IF -s $NETWORK -d 172.16.0.0/12 -j MARK --or-mark $NoMASQ
		$IPTABLES -t mangle -A POSTROUTING -o $EXT_IF -s $NETWORK -d 192.168.0.0/16 -j MARK --or-mark $NoMASQ
		$IPTABLES -t mangle -A POSTROUTING -o $EXT_IF -s $NETWORK -d 10.0.0.0/8 -j MARK --or-mark $NoMASQ
		
		
		###
		### NAT --> POSTROUTING
		###
		
		# dont masq if NoMASQ-Mark is set
		$IPTABLES -t nat -A POSTROUTING -o $EXT_IF -m mark ! --mark $NoMASQ/$NoMASQ -j MASQUERADE
		

	;;
	stop)
		echo " "
		echo "Shutting down Firewall..."
		echo "Disabling IP-Forward..."
		echo " "
		
		$IPTABLES -P INPUT ACCEPT
		$IPTABLES -P OUTPUT ACCEPT
		$IPTABLES -P FORWARD ACCEPT
		$IPTABLES -P POSTROUTING ACCEPT -t nat
		$IPTABLES -P PREROUTING ACCEPT -t nat
		$IPTABLES -P OUTPUT ACCEPT -t nat

		$IPTABLES -F
		$IPTABLES -F -t nat
		$IPTABLES -F -t mangle
		$IPTABLES -X
			
		# neue kette namens nirwana anlegen und fuers logging definieren
		$IPTABLES -N nirwana
		$IPTABLES -A nirwana -p TCP -j LOG --log-prefix "NIRWANA_TCP: "
		$IPTABLES -A nirwana -p UDP -j LOG --log-prefix "NIRWANA_UDP: "
		$IPTABLES -A nirwana -p ICMP -j LOG --log-prefix "NIRWANA_ICMP: "
		$IPTABLES -A nirwana -p TCP -j DROP
		$IPTABLES -A nirwana -p UDP -j DROP
		$IPTABLES -A nirwana -p ICMP -j DROP
		$IPTABLES -A nirwana -j LOG --log-prefix "NIRWANA_UNKNOWN: "
		$IPTABLES -A nirwana -j DROP
		

		# disable forwarding
		echo 0 > /proc/sys/net/ipv4/ip_forward

		# allow trusted ip's only for INPUT
		$IPTABLES -A INPUT -s $TRUSTED_SOURCE_IP -j ACCEPT
		$IPTABLES -A FORWARD -s $TRUSTED_SOURCE_IP -j ACCEPT
		$IPTABLES -A OUTPUT -d $TRUSTED_SOURCE_IP -j ACCEPT
		# drop all the rest
		$IPTABLES -A INPUT   -i $EXT_IF -j nirwana
		$IPTABLES -A FORWARD -i $EXT_IF -j nirwana
		#echo 1 > /proc/sys/net/ipv4/ip_forward
		#$IPTABLES -t nat -A POSTROUTING -o $EXT_IF -s $NETWORK -j MASQUERADE
	
	
	;;
	restart)
		$0 stop
		$0 start
	
	
	;;
	status)
		echo;
		echo "\[\033[31m\]======================> FILTER-RULES: <======================\[\033[0m\]"
		$IPTABLES -nvL 
		echo; echo; echo; echo "\[\033[31m\]======================> MANGLE-RULES: <======================\[\033[0m\]"
		$IPTABLES -t mangle -nvL
		echo; echo; echo; echo "\[\033[31m\]======================> NAT-RULES: <======================\[\033[0m\]"
		$IPTABLES -t nat -nvL
		echo;
	
	
	;;
	tcstatus)
		echo; echo;
		DEVICES="ppp0 imq0";
		for d in $DEVICES; do
			echo "/------------------------- TC-Config $d -------------------------------/"
			$TC -s qdisc ls dev $d
			$TC -s class ls dev $d
			echo; echo;
		done
	;;
	*)
		echo "Usage: $0 {start|status|tcstatus|restart|stop}"
		exit 1
	
	
	;;
esac

exit 0