Assalam-u-alaikum,
I have been receiving many mails for few years now to provide with a firewall script. Lately I received one such mail and I decided to publish, what I replied him with. The names and email are changed for privacy reasons. I hope this firewall script will be helpful to many.

The Scenario:

[Internet]—[DSLRouter/DialUp Modem]—[LinuxFirewall]—[LAN switch/users]

First, the mail from one of the community members:

A.o.A
My name is Farrukh Irfan.I am facing one problem, which I want to discuss with you. In my office different developers using different ports like pop,smtp,ftp,imap etc. by default all the ports are block,no entry in iptables.
When i use one rule iptables -t nat -A POSTROUTING -j MASQUERADE this will open every port,so many users also using p2p software,p2p software using different ports and changing port every time,soo i need your help how to i block this p2p software.also some times when some one open any site,the problem occours like this “not to resolve request”,please tell me why its come.
Thanx
Waiting ur reply
Allah Hafiz

Here is my reply and the firewall script I have attached below it.

Wa-alaikum “A.o.A”,
Alhumdulillah. Nice to know you.

The solution to your problem is simple. Block all traffic and allow only interested ports to be forwarded. That way you can easily stop P2P traffic.

I am attaching a sample firewall. You can customize it and use it for yourself. This will work 100%, InshaAllah. This firewall needs some adjustment as per your setup, such as the name of your PUBLIC and LOCAL interfaces and their IPs. Any way, this is currently in place, at one of the offices somewhere in the city. Feel free to use it for your setup.

Ma’ ssalama,
Kamran

Now, the (much awaited) actual firewall script:


#!/bin/bash
#Author: Muhammad Kamran Azeem (kamran@wbitt.com)
#Disclaimer: Use this firewall script on your own risk !
#Revision History :- 20080702, 20080622, 20080222, 20070314

#If you have fixed IP from your ISP, you should provide PUBLICIP below,
#and use SNAT instead of MASQUERADE.

#If you have dynamic IP (on dialup) (or changing everytime, for some reason),
#then you should comment the PUBLICIP below and use MASQUERADE instead of SNAT.

#Define interfaces. Please specify your interfaces carefully.
#On a dial up connection, the PUBLICIF would most likely be ppp0.
#On a DSL connection, the PUBLICIF may be eth0 or eth1,
#depending on what you use for your internal LAN.
#Also specify your PUBLICIP, if you have a static IP given to you from your ISP.


PUBLICIF=eth0
PUBLICIP=202.203.103.211

LOCALIF=eth1
LOCALIP=192.168.0.254

IPTABLES=/sbin/iptables

############ Load Modules - Start ###################################################
#Load FTP connection tracking module. Without it, FTP to this server will NOT work
modprobe ip_conntrack_ftp
modprobe ip_conntrack

############# Load Modules - End ###################################################

###################### Kernel Parameters - Start ########################

#Various Kernel parameters which you can (also) setup in /etc/sysctl.conf

#This following enables source address verification,
#, which is inbuilt into Linux kernel itself.
#net.ipv4.conf.all.rp_filter = 1
echo 1 > /proc/sys/net/ipv4/conf/all/rp_filter
echo 1 > /proc/sys/net/ipv4/ip_forward

###################### Kernel Parameters - End ########################

########################## Main firewall engine (Start) ######################

First clear the tables:

$IPTABLES -t nat -F
$IPTABLES -F

Block spoofing

$IPTABLES -A INPUT -s 127.0.0.0/8 -i ! lo -j DROP

#OR more sophisticated / wide ranged method is below. USE CAREFULLY:-

#Let it remain commented if you do not understand this:-
#Add your IP range/IPs here,
#Yes, I am sure that the last address has 16 bit subnet for a VALID reason
#SPOOFLIST=”0.0.0.0/8 127.0.0.0/8 10.0.0.0/8 172.16.0.0/16 192.168.0.0/16 224.0.0.0/3”
#for ip in $SPOOFLIST
#do

$IPTABLES -A INPUT -i $PUBLICIF -s $ip -j DROP

#done

Stop bad packets

$IPTABLES -A INPUT -m state –state INVALID -j DROP

#NMAP FIN/URG/PSH
$IPTABLES -A INPUT -p tcp –tcp-flags ALL FIN,URG,PSH -j DROP

stop Xmas Tree type scanning

$IPTABLES -A INPUT -p tcp –tcp-flags ALL ALL -j DROP
$IPTABLES -A INPUT -p tcp –tcp-flags ALL SYN,RST,ACK,FIN,URG -j DROP

stop null scanning

$IPTABLES -A INPUT -p tcp –tcp-flags ALL NONE -j DROP

#SYN/RST
$IPTABLES -A INPUT -p tcp –tcp-flags SYN,RST SYN,RST -j DROP

#SYN/FIN
$IPTABLES -A INPUT -p tcp –tcp-flags SYN,FIN SYN,FIN -j DROP

#If the incoming SYN packets are not NEW, we need to DROP them:-
$IPTABLES -A INPUT -p tcp ! –syn -m state –state NEW -j DROP

In case of dynamic IP, use this on your public interface:-

$IPTABLES -t nat -A POSTROUTING -o $PUBLICIF -j MASQUERADE

In case of static IP, use this on your public interface:-

$IPTABLES -t nat -A POSTROUTING -o $PUBLICIF -j SNAT –to-source $PUBLICIP

echo -n “Enabling Transparent Proxying (SQUID on same machine) …”

$IPTABLES -t nat -A PREROUTING -i $LOCALIF -p tcp -d ! $LOCALIP –dport 80 -j REDIRECT –to-port 3128

123 TCP/UDP is Network Time Protocol

Allow diagnostic/admin ports, i.e SSH, web from internet (and NTP). .

$IPTABLES -A INPUT -i $PUBLICIF -p tcp -m multiport –dport 22,80,123 -j ACCEPT
$IPTABLES -A INPUT -i $PUBLICIF -p udp -m multiport –dport 123 -j ACCEPT

#TCP/UDP 123 is NTP
#Yahoo messenger needs 5050 (and 443 as well)
#Lets allow traffic for outgoing 20,21,80,1863 MSN ,5050 yahoo,
#1433 MS SQL server
#51215 is web2SMS for mobilink
#5001:5020 TCP PalTalk
#2091 UDP Paltalk incoming control
#1025-2500 UDP Paltalk out control
#TCP 5222, 443 to anywhere GoogleTalk
#TCP 1111, 1935 Flash Communications ports
#GMAIL - POP - 995
#GMAIL - IMAP - 993
#4080 / TCP - MLNET
#11999 is yahoo games MSN needs both 1863 and 443,

#set default FORWARD policy to drop.

$IPTABLES -P FORWARD DROP

#We will only allow specific connections.

$IPTABLES -A FORWARD -i $LOCALIF -o $PUBLICIF -p tcp
-m multiport –dports 21,22,80,110,143,443,1863,5050 -j ACCEPT

$IPTABLES -A FORWARD -m state –state RELATED,ESTABLISHED -j ACCEPT

#Stop ping flood attack

$IPTABLES -A INPUT -p icmp –icmp-type echo-request -m length
–length 85: -j REJECT –reject-with icmp-host-prohibited

Allow maximum two incoming ICMP packets per second

$IPTABLES -A INPUT -p icmp –icmp-type echo-request -m limit –limit 1/s -j ACCEPT

#The following DROPS icmp packets coming from internet
$IPTABLES -A INPUT -i $PUBLICIF -p icmp -j DROP #Drop all connections, by default, from internet, which are destined for public interface of this machine.

This will serve as default policy. :-

$IPTABLES -A INPUT -i $PUBLICIF -j DROP That should be all.