Difference between revisions of "Firewall basics"
(Created page with "Category:Linux =Set IP preference= If you enable IPv6 then that will be the default. You can override that and '''set IPv4 as the default protocol''': <syntaxhighli...") |
(→FTP client) |
||
(21 intermediate revisions by the same user not shown) | |||
Line 6: | Line 6: | ||
If you enable IPv6 then that will be the default. | If you enable IPv6 then that will be the default. | ||
+ | |||
+ | |||
+ | [[File:Ipv6logo.jpg|64px|caption|IPv6]] | ||
+ | '''Recommended solution''' : IPv6 is now available in a lot of places. It's time to use it! | ||
+ | |||
+ | |||
+ | [[File:Ipv4.jpg|64px|caption|IPv4 only]] | ||
+ | If you don't want to use IPv6 you can force IPv4 mode. This is not recommended any-more! IPv6 is becoming bigger and bigger, you need to switch. | ||
Line 25: | Line 33: | ||
+ | =Global networking configuration= | ||
− | =Enable modules= | + | ==Enable modules== |
First things first! Before writing any rule you have to enable the required modules in your current O.S. | First things first! Before writing any rule you have to enable the required modules in your current O.S. | ||
Line 38: | Line 47: | ||
<syntaxhighlight lang="bash"> | <syntaxhighlight lang="bash"> | ||
MODPROBE=`which modprobe` | MODPROBE=`which modprobe` | ||
− | |||
echo -e " " | echo -e " " | ||
Line 45: | Line 53: | ||
echo -e "-----------------------------" | echo -e "-----------------------------" | ||
− | # IPv4 | + | ##### IPv4 |
− | |||
$MODPROBE ip_tables | $MODPROBE ip_tables | ||
$MODPROBE iptable_filter | $MODPROBE iptable_filter | ||
Line 52: | Line 59: | ||
# Allow to use state match | # Allow to use state match | ||
$MODPROBE ip_conntrack | $MODPROBE ip_conntrack | ||
+ | # Allow NAT | ||
+ | $MODPROBE iptable_nat | ||
− | # IPv6 | + | ##### IPv6 |
− | |||
$MODPROBE ip6_tables | $MODPROBE ip6_tables | ||
$MODPROBE ip6table_filter | $MODPROBE ip6table_filter | ||
$MODPROBE ip6table_mangle | $MODPROBE ip6table_mangle | ||
− | # | + | ##### Allow active / passive FTP |
− | |||
− | |||
− | |||
− | # Allow active / passive FTP | ||
− | |||
$MODPROBE ip_conntrack_ftp | $MODPROBE ip_conntrack_ftp | ||
$MODPROBE ip_nat_ftp | $MODPROBE ip_nat_ftp | ||
− | # Allow log limits | + | ##### Allow log limits |
echo " ... burst limit" | echo " ... burst limit" | ||
$MODPROBE ipt_limit | $MODPROBE ipt_limit | ||
Line 76: | Line 79: | ||
− | = | + | ==Set network features== |
− | Now that you've enable some modules, you need to choose which | + | Now that you've enable some modules, you need to choose which network features you're gonna use or not. |
Line 106: | Line 109: | ||
echo 0 > /proc/sys/net/ipv4/conf/all/accept_source_route | echo 0 > /proc/sys/net/ipv4/conf/all/accept_source_route | ||
echo 0 > /proc/sys/net/ipv6/conf/all/accept_source_route | echo 0 > /proc/sys/net/ipv6/conf/all/accept_source_route | ||
− | |||
## Check TCP window | ## Check TCP window | ||
echo 1 > /proc/sys/net/ipv4/tcp_window_scaling | echo 1 > /proc/sys/net/ipv4/tcp_window_scaling | ||
Line 116: | Line 118: | ||
− | # | + | # Enable port forwarding in general |
− | + | # (i) Some might argue that it should only be done by routers... | |
+ | # Since I'm using a VPN, I like to access both networks and exchange data between them. | ||
+ | # That's why port forwarding is enable. | ||
echo 1 > /proc/sys/net/ipv4/ip_forward | echo 1 > /proc/sys/net/ipv4/ip_forward | ||
+ | |||
+ | echo 2 > /proc/sys/net/ipv6/conf/all/use_tempaddr | ||
+ | echo 2 > /proc/sys/net/ipv6/conf/default/use_tempaddr | ||
+ | echo 2 > /proc/sys/net/ipv6/conf/eth0/use_tempaddr | ||
echo 1 > /proc/sys/net/ipv6/conf/all/forwarding | echo 1 > /proc/sys/net/ipv6/conf/all/forwarding | ||
− | + | echo 0 > /proc/sys/net/ipv6/conf/default/forwarding | |
+ | echo 0 > /proc/sys/net/ipv6/conf/eth0/forwarding | ||
</syntaxhighlight> | </syntaxhighlight> | ||
Line 143: | Line 152: | ||
− | == | + | ==Set default policies== |
This is how you defined a default policy. | This is how you defined a default policy. | ||
+ | [[File:Best-pratice-icon.png|64px|caption|Best practice]] '''Recommendations''' : | ||
+ | * You should set all policies in ''ACCEPT'' ; and ''DROP'' the packets at the end of your firewall. By doing so you'll probably not be locked away from your server in case of firewall change. | ||
+ | * You should keep the ''RELATED'' and ''ESTABLISHED'' connections | ||
− | |||
− | |||
− | |||
Line 163: | Line 172: | ||
echo -e "------------------------" | echo -e "------------------------" | ||
+ | # Delete GENERIC rules | ||
$IP6TABLES -F | $IP6TABLES -F | ||
+ | $IP6TABLES -X | ||
+ | $IPTABLES -F | ||
+ | $IPTABLES -X | ||
+ | # delete FILTER rule (in/out) | ||
$IPTABLES -t filter -F | $IPTABLES -t filter -F | ||
$IPTABLES -t filter -X | $IPTABLES -t filter -X | ||
+ | $IP6TABLES -t filter -F | ||
+ | $IP6TABLES -t filter -X | ||
+ | |||
+ | # delete MANGLE rules (packets modifications) | ||
+ | $IPTABLES -t mangle -F | ||
+ | $IPTABLES -t mangle -X | ||
+ | $IP6TABLES -t mangle -F | ||
+ | $IP6TABLES -t mangle -X | ||
− | # delete NAT rules | + | # delete NAT rules [IPv4 only] |
$IPTABLES -t nat -F | $IPTABLES -t nat -F | ||
$IPTABLES -t nat -X | $IPTABLES -t nat -X | ||
− | |||
− | |||
− | |||
echo -e " " | echo -e " " | ||
Line 180: | Line 199: | ||
echo -e " Default policy" | echo -e " Default policy" | ||
echo -e "------------------------" | echo -e "------------------------" | ||
− | echo -e " | + | $IPTABLES -P INPUT ACCEPT |
− | echo -e " | + | $IPTABLES -P FORWARD ACCEPT |
− | + | $IPTABLES -P OUTPUT ACCEPT | |
+ | |||
+ | $IP6TABLES -P INPUT ACCEPT | ||
+ | $IP6TABLES -P FORWARD ACCEPT | ||
+ | $IP6TABLES -P OUTPUT ACCEPT | ||
+ | |||
+ | |||
+ | echo -e " " | ||
+ | echo -e "------------------------" | ||
+ | echo -e " Keep connections" | ||
+ | echo -e "------------------------" | ||
+ | $IPTABLES -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT | ||
+ | $IPTABLES -A FORWARD -m state --state ESTABLISHED,RELATED -j ACCEPT | ||
+ | $IPTABLES -A OUTPUT -m state --state ESTABLISHED,RELATED -j ACCEPT | ||
+ | |||
+ | $IP6TABLES -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT | ||
+ | $IP6TABLES -A FORWARD -m state --state ESTABLISHED,RELATED -j ACCEPT | ||
+ | $IP6TABLES -A OUTPUT -m state --state ESTABLISHED,RELATED -j ACCEPT | ||
+ | |||
+ | |||
+ | [...] | ||
+ | |||
+ | |||
+ | # End of script (optional) | ||
+ | $IPTABLES -A INPUT -j DROP | ||
+ | $IP6TABLES -A INPUT -j DROP | ||
+ | |||
+ | $IPTABLES -A OUTPUT -j DROP | ||
+ | $IP6TABLES -A OUTPUT -j DROP | ||
+ | |||
+ | </syntaxhighlight> | ||
+ | |||
+ | |||
+ | |||
+ | =Basic protection and protocol(s) enforcement= | ||
+ | |||
+ | |||
+ | ==Basic (minimal) protection== | ||
+ | |||
+ | You should put some minimal protection. This layer relies on your O.S and its internal checks. Most of the time that's enough to block malformed and suspicious packets. | ||
+ | |||
+ | |||
+ | <syntaxhighlight lang="bash"> | ||
+ | IPTABLES=`which iptables` | ||
+ | IP6TABLES=`which ip6tables` | ||
+ | |||
+ | |||
+ | ##################### | ||
+ | ### All protocols ### | ||
+ | ##################### | ||
+ | # Reject invalid packets | ||
+ | $IPTABLES -A INPUT -m state --state INVALID -m comment --comment "Invalid input" -j DROP | ||
+ | $IPTABLES -A OUTPUT -m state --state INVALID -m comment --comment "Invalid input" -j DROP | ||
+ | $IPTABLES -A FORWARD -m state --state INVALID -m comment --comment "Invalid forward" -j DROP | ||
+ | |||
+ | $IP6TABLES -A INPUT -m state --state INVALID -m comment --comment "Invalid input" -j DROP | ||
+ | $IP6TABLES -A OUTPUT -m state --state INVALID -m comment --comment "Invalid input" -j DROP | ||
+ | $IP6TABLES -A FORWARD -m state --state INVALID -m comment --comment "Invalid forward" -j DROP | ||
+ | |||
+ | # Ensure TCP connection requests start with SYN flag | ||
+ | $IPTABLES -A INPUT -p tcp -m state --state NEW ! --syn -m comment --comment "Invalid conn request" -j DROP | ||
+ | $IPTABLES -A OUTPUT -p tcp -m state --state NEW ! --syn -m comment --comment "Invalid conn request" -j DROP | ||
+ | |||
+ | $IP6TABLES -A INPUT -p tcp -m state --state NEW ! --syn -m comment --comment "Invalid conn request" -j DROP | ||
+ | $IP6TABLES -A OUTPUT -p tcp -m state --state NEW ! --syn -m comment --comment "Invalid conn request" -j DROP | ||
+ | |||
+ | |||
+ | ############ | ||
+ | ### IPv4 ### | ||
+ | ############ | ||
+ | ## Localhost | ||
+ | $IPTABLES -A INPUT ! -i lo -s 127.0.0.0/24 -m comment --comment "Reject none loopback on 'lo'" -j DROP | ||
+ | $IPTABLES -A OUTPUT ! -o lo -d 127.0.0.0/24 -m comment --comment "Reject none loopback on 'lo'" -j DROP | ||
+ | # Accept all local packets | ||
+ | $IPTABLES -A INPUT -i lo -m comment --comment "Accept localhost packets" -j ACCEPT | ||
+ | $IPTABLES -A OUTPUT -o lo -m comment --comment "Accept localhost packets" -j ACCEPT | ||
+ | |||
+ | |||
+ | ############ | ||
+ | ### IPv6 ### | ||
+ | ############ | ||
+ | # Allow localhost traffic. These rules are for all protocols. | ||
+ | $IP6TABLES -A INPUT -s ::1 -d ::1 -j ACCEPT | ||
+ | $IP6TABLES -A INPUT ! -i lo -s ::1 -m comment --comment "Reject none loopback on 'lo'" -j DROP | ||
+ | $IP6TABLES -A OUTPUT ! -o lo -d ::1 -m comment --comment "Reject none loopback on 'lo'" -j DROP | ||
+ | |||
+ | # Allow Link-Local addresses | ||
+ | $IP6TABLES -A INPUT -s fe80::/10 -j ACCEPT | ||
+ | $IP6TABLES -A OUTPUT -s fe80::/10 -j ACCEPT | ||
− | # | + | # Normally, link-local packets should NOT be forwarded and don't need an entry in the FORWARD rule. |
− | # | + | # However, when bridging in Linux (e.g. in Xen or OpenWRT), the FORWARD rule is needed: |
− | $ | + | $IP6TABLES -A FORWARD -s fe80::/10 -j ACCEPT |
− | |||
− | |||
− | $ | + | ################# |
− | + | ### Multicast ### | |
− | $ | + | ################# |
+ | $IPTABLES -A INPUT -m comment --comment "Multicast auto-configuration" -d 224.0.0.0/24 -j ACCEPT | ||
+ | $IPTABLES -A OUTPUT -m comment --comment "Multicast request" -d 224.0.0.0/24 -j ACCEPT | ||
− | + | $IP6TABLES -A INPUT -d ff00::/8 -j ACCEPT | |
− | + | $IP6TABLES -A INPUT -s ff00::/8 -j ACCEPT | |
− | $ | + | $IP6TABLES -A OUTPUT -d ff00::/8 -j ACCEPT |
− | $ | + | $IP6TABLES -A OUTPUT -s ff00::/8 -j ACCEPT |
− | |||
− | $ | ||
− | $ | ||
− | |||
− | |||
− | + | </syntaxhighlight> | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | ==Block IPv4 in IPv6 tunnels== | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | If your ISP delivers you a native IPv6 connection then you don't need to use IPv4 tunneling! Just use either IPv4 or IPv6 native mode. | |
− | + | ||
− | + | ||
− | + | <syntaxhighlight lang="bash"> | |
− | + | IPTABLES=`which iptables` | |
+ | IP6TABLES=`which ip6tables` | ||
## IPv6 security | ## IPv6 security | ||
# No IPv4 -> IPv6 tunneling | # No IPv4 -> IPv6 tunneling | ||
− | + | $IP6TABLES -A INPUT -s 2002::/16 -m comment --comment "Reject 6to4 tunnels" -j DROP | |
− | $IP6TABLES -A INPUT -s 2002::/16 -j DROP | + | $IP6TABLES -A FORWARD -s 2002::/16 -m comment --comment "Reject 6to4 tunnels" -j DROP |
− | $IP6TABLES -A FORWARD -s 2002::/16 -j DROP | + | $IP6TABLES -A INPUT -s 2001:0::/32 -m comment --comment "Reject Teredo tunnels" -j DROP |
− | $IP6TABLES -A INPUT -s 2001:0::/32 -j DROP | + | $IP6TABLES -A FORWARD -s 2001:0::/32 -m comment --comment "Reject Teredo tunnels" -j DROP |
− | $IP6TABLES -A FORWARD -s 2001:0::/32 -j DROP | + | |
− | |||
# Block IPv6 protocol in IPv4 frames | # Block IPv6 protocol in IPv4 frames | ||
− | + | $IPTABLES -A INPUT -p 41 -m comment --comment "Block IPv6 protocol in IPv4 frames" -j DROP | |
− | + | $IPTABLES -A OUTPUT -p 41 -m comment --comment "Block IPv6 protocol in IPv4 frames" -j DROP | |
− | $IPTABLES -A OUTPUT -p 41 -j DROP | + | $IPTABLES -A FORWARD -p 41 -m comment --comment "Block IPv6 protocol in IPv4 frames" -j DROP |
− | $IPTABLES -A FORWARD -p 41 -j DROP | ||
+ | </syntaxhighlight> | ||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
+ | ==Block IPv6 routing headers== | ||
+ | <syntaxhighlight lang="bash"> | ||
+ | # Filter all packets that have RH0 headers: | ||
+ | $IP6TABLES -A INPUT -m rt --rt-type 0 -j DROP | ||
+ | $IP6TABLES -A FORWARD -m rt --rt-type 0 -j DROP | ||
+ | $IP6TABLES -A OUTPUT -m rt --rt-type 0 -j DROP | ||
</syntaxhighlight> | </syntaxhighlight> | ||
+ | ==Protocol(s) enforcement== | ||
− | + | You can even push the standard protection a bit higher by checking some protocols flags. | |
<syntaxhighlight lang="bash"> | <syntaxhighlight lang="bash"> | ||
Line 281: | Line 357: | ||
echo -e " Protocols enforcement" | echo -e " Protocols enforcement" | ||
echo -e "------------------------" | echo -e "------------------------" | ||
− | echo | + | |
+ | ####### IPv4 ####### | ||
+ | echo " ... Layer 2: ICMP v4" | ||
# ICMP packets should not be fragmented | # ICMP packets should not be fragmented | ||
− | $IPTABLES -A INPUT --fragment -p icmp -j DROP | + | $IPTABLES -A INPUT --fragment -p icmp -m comment --comment "no ICMP fragments" -j DROP |
− | + | # SMURF attack protection | |
+ | $IPTABLES -A INPUT -p icmp -m icmp --icmp-type address-mask-request -m comment --comment "address-mask-request" -j DROP | ||
+ | $IPTABLES -A INPUT -p icmp -m icmp --icmp-type timestamp-request -m comment --comment "timestamp-request" -j DROP | ||
# Limit ICMP Flood | # Limit ICMP Flood | ||
− | $IPTABLES -A INPUT -p icmp -m limit --limit 1/s --limit-burst 1 -j ACCEPT | + | $IPTABLES -A INPUT -p icmp -m limit --limit 1/s --limit-burst 1 -m comment --comment "ICMP flood protection" -j ACCEPT |
− | $IPTABLES -A OUTPUT -p icmp --icmp-type 0 -j ACCEPT | + | $IPTABLES -A OUTPUT -p icmp --icmp-type 0 -m comment --comment "echo reply" -j ACCEPT |
− | $IPTABLES -A OUTPUT -p icmp --icmp-type 3 -j ACCEPT | + | $IPTABLES -A OUTPUT -p icmp --icmp-type 3 -m comment --comment "destination unreachable" -j ACCEPT |
− | $IPTABLES -A OUTPUT -p icmp --icmp-type 8 - | + | $IPTABLES -A OUTPUT -p icmp --icmp-type 8 -m comment --comment "echo request" -j ACCEPT |
− | |||
− | |||
− | |||
− | |||
− | echo | + | ####### IPv6 ####### |
− | # | + | echo " ... Layer 2: ICMP v6 " |
− | $IP6TABLES -A INPUT | + | # Don't DROP ICMP6 a lot of things are happening over there! It might completly block the connection if you DROP icmp6 |
− | $IP6TABLES -A | + | $IP6TABLES -A INPUT -j ACCEPT |
− | $IP6TABLES -A | + | $IP6TABLES -A OUTPUT -p icmpv6 -j ACCEPT |
− | + | $IP6TABLES -A FORWARD -p icmpv6 -j ACCEPT | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | + | ####### TCP IPv4 ####### | |
echo " ... Layer 4: TCP # check packets conformity" | echo " ... Layer 4: TCP # check packets conformity" | ||
# INCOMING packets check | # INCOMING packets check | ||
# All new incoming TCP should be SYN first | # All new incoming TCP should be SYN first | ||
− | $IPTABLES -A INPUT -p tcp ! --syn -m state --state NEW -j DROP | + | $IPTABLES -A INPUT -p tcp ! --syn -m state --state NEW -m comment --comment "new TCP connection check" -j DROP |
# Avoid SYN Flood (max 3 SYN packets / second. Then Drop all requests !!) | # Avoid SYN Flood (max 3 SYN packets / second. Then Drop all requests !!) | ||
− | $IPTABLES -A INPUT -p tcp --syn -m limit --limit 1/s --limit-burst 3 -j ACCEPT | + | $IPTABLES -A INPUT -p tcp --syn -m limit --limit 1/s --limit-burst 3 -m comment --comment "avoid TCP SYN flood" -j ACCEPT |
# Avoid fragment packets | # Avoid fragment packets | ||
− | $IPTABLES -A INPUT -f -j DROP | + | $IPTABLES -A INPUT -f -m comment --comment "no fragments" -j DROP |
# Check TCP flags -- flag 64, 128 = bogues | # Check TCP flags -- flag 64, 128 = bogues | ||
− | $IPTABLES -A INPUT -p tcp --tcp-option 64 -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-option 64 -m comment --comment "ECE flag" -j DROP |
− | $IPTABLES -A INPUT -p tcp --tcp-option 128 -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-option 128 -m comment --comment "CWR flag" -j DROP |
+ | |||
+ | |||
echo " ... Layer 4: TCP # Avoid NMAP Scans" | echo " ... Layer 4: TCP # Avoid NMAP Scans" | ||
# XMAS-NULL | # XMAS-NULL | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags ALL NONE -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags ALL NONE -m comment --comment "attack XMAS-NULL" -j DROP |
# XMAS-TREE | # XMAS-TREE | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags ALL ALL -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags ALL ALL -m comment --comment "attack XMAS-tree" -j DROP |
+ | # Stealth XMAS Scan | ||
+ | $IPTABLES -A INPUT -p tcp --tcp-flags ALL FIN,PSH,URG -m comment --comment "attack XMAS stealth" -j DROP | ||
# SYN/RST Scan | # SYN/RST Scan | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags SYN,RST SYN,RST -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags SYN,RST SYN,RST -m comment --comment "scan SYN/RST" -j DROP |
# SYN/FIN Scan | # SYN/FIN Scan | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags SYN,FIN SYN,FIN -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags SYN,FIN SYN,FIN -m comment --comment "scan SYN/FIN" -j DROP |
# SYN/ACK Scan | # SYN/ACK Scan | ||
− | + | $IPTABLES -A INPUT -p tcp --tcp-flags SYN,ACK SYN,ACK -m comment --comment "scan SYN/ACK" -j DROP | |
− | |||
# FIN/RST Scan | # FIN/RST Scan | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags FIN,RST FIN,RST -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags FIN,RST FIN,RST -m comment --comment "scan FIN/RST" -j DROP |
# FIN/ACK Scan | # FIN/ACK Scan | ||
− | $IPTABLES -A INPUT -p tcp -m tcp --tcp-flags FIN,ACK FIN -j DROP | + | $IPTABLES -A INPUT -p tcp -m tcp --tcp-flags FIN,ACK FIN -m comment --comment "scan FIN/ACK" -j DROP |
# ACK/URG Scan | # ACK/URG Scan | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags ACK,URG URG -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags ACK,URG URG -m comment --comment "scan ACK/URG" -j DROP |
# FIN/URG/PSH Scan | # FIN/URG/PSH Scan | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags FIN,URG,PSH FIN,URG,PSH - | + | $IPTABLES -A INPUT -p tcp --tcp-flags FIN,URG,PSH FIN,URG,PSH -m comment --comment "scan FIN/URG/PSH" -j DROP |
− | |||
− | |||
# XMAS-PSH Scan | # XMAS-PSH Scan | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags ALL SYN,RST,ACK,FIN,URG -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags ALL SYN,RST,ACK,FIN,URG -m comment --comment "scan XMAS/PSH" -j DROP |
# End TCP connection | # End TCP connection | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags ALL FIN -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags ALL FIN -m comment --comment "end TCP connection flag" -j DROP |
# Ports scans | # Ports scans | ||
− | $IPTABLES -A INPUT -p tcp --tcp-flags FIN,SYN,RST,ACK SYN -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags FIN,SYN,RST,ACK SYN -m comment --comment "common scan FIN/SYN/RST/ACK SYN" -j DROP |
− | $IPTABLES -A INPUT -p tcp --tcp-flags FIN,SYN,RST,PSH,ACK,URG NONE -j DROP | + | $IPTABLES -A INPUT -p tcp --tcp-flags FIN,SYN,RST,PSH,ACK,URG NONE -m comment --comment "common scan FIN/SYN/RST/ACK/PSH/URG NONE" -j DROP |
</syntaxhighlight> | </syntaxhighlight> | ||
Line 373: | Line 436: | ||
<syntaxhighlight lang="bash"> | <syntaxhighlight lang="bash"> | ||
IPTABLES=`which iptables` | IPTABLES=`which iptables` | ||
+ | IP6TABLES=`which ip6tables` | ||
# DHCP client >> Broadcast IP request | # DHCP client >> Broadcast IP request | ||
− | $IPTABLES -A | + | $IPTABLES -A INPUT -p udp --sport 67:68 --dport 67:68 -m comment --comment "DHCP" -j ACCEPT |
− | $IPTABLES -A | + | $IPTABLES -A OUTPUT -p udp --sport 67:68 --dport 67:68 -m comment --comment "DHCP" -j ACCEPT |
− | $ | + | |
− | $ | + | $IP6TABLES -A INPUT -p udp --sport 67:68 --dport 67:68 -m comment --comment "DHCP" -j ACCEPT |
+ | $IP6TABLES -A OUTPUT -p udp --sport 67:68 --dport 67:68 -m comment --comment "DHCP" -j ACCEPT | ||
</syntaxhighlight> | </syntaxhighlight> | ||
Line 390: | Line 455: | ||
IPTABLES=`which iptables` | IPTABLES=`which iptables` | ||
IP6TABLES=`which ip6tables` | IP6TABLES=`which ip6tables` | ||
+ | |||
+ | # DNS | ||
+ | $IPTABLES -A INPUT -p udp --sport 53 -m comment --comment "DNS UDP sPort" -j ACCEPT | ||
+ | $IPTABLES -A OUTPUT -p udp --sport 53 -m comment --comment "DNS UDP sPort" -j ACCEPT | ||
+ | |||
+ | $IPTABLES -A INPUT -p udp --dport 53 -m comment --comment "DNS UDP dPort" -j ACCEPT | ||
+ | $IPTABLES -A OUTPUT -p udp --dport 53 -m comment --comment "DNS UDP dPort" -j ACCEPT | ||
+ | |||
+ | |||
+ | $IP6TABLES -A INPUT -p udp --sport 53 -m comment --comment "DNS UDP sPort" -j ACCEPT | ||
+ | $IP6TABLES -A OUTPUT -p udp --sport 53 -m comment --comment "DNS UDP sPort" -j ACCEPT | ||
+ | |||
+ | $IP6TABLES -A INPUT -p udp --dport 53 -m comment --comment "DNS UDP dPort" -j ACCEPT | ||
+ | $IP6TABLES -A OUTPUT -p udp --dport 53 -m comment --comment "DNS UDP dPort" -j ACCEPT | ||
− | + | # DNS SEC | |
− | $IPTABLES -A OUTPUT -p | + | # Established, related input are already accepted earlier |
− | $IPTABLES -A | + | $IPTABLES -A OUTPUT -p tcp --sport 53 -m comment --comment "DNS Sec TCP sPort" -j ACCEPT |
− | + | $IPTABLES -A OUTPUT -p tcp --dport 53 -m comment --comment "DNS Sec TCP dPort" -j ACCEPT | |
+ | $IP6TABLES -A OUTPUT -p tcp --sport 53 -m comment --comment "DNS Sec TCP sPort" -j ACCEPT | ||
+ | $IP6TABLES -A OUTPUT -p tcp --dport 53 -m comment --comment "DNS Sec TCP dPort" -j ACCEPT | ||
− | |||
− | |||
− | |||
− | |||
</syntaxhighlight> | </syntaxhighlight> | ||
+ | |||
+ | |||
+ | <big>!! IMPORTANT !!! </big> | ||
+ | |||
+ | If you ever loose Internet access after that you need to check your <code>/etc/resolv.conf</code> configuration and make sure you're using a valid DNS server. | ||
+ | |||
Line 447: | Line 530: | ||
# NTP client | # NTP client | ||
echo -e " ... Allow NTP time sync" | echo -e " ... Allow NTP time sync" | ||
− | $IPTABLES -A OUTPUT -p udp --dport 123 -j ACCEPT | + | $IPTABLES -A INPUT -p udp --sport 123 -m state --state ESTABLISHED -m comment --comment "NTP (UDP)" -j ACCEPT |
− | $IPTABLES -A | + | $IPTABLES -A INPUT -p tcp --sport 123 -m state --state ESTABLISHED -m comment --comment "NTP (TCP)" -j ACCEPT |
+ | |||
+ | $IPTABLES -A OUTPUT -p udp --dport 123 -m state --state NEW,ESTABLISHED -m comment --comment "NTP (UDP)" -j ACCEPT | ||
+ | $IPTABLES -A OUTPUT -p tcp --dport 123 -m state --state NEW,ESTABLISHED -m comment --comment "NTP (TCP)" -j ACCEPT | ||
− | |||
− | |||
</syntaxhighlight> | </syntaxhighlight> | ||
Line 459: | Line 543: | ||
<syntaxhighlight lang="bash"> | <syntaxhighlight lang="bash"> | ||
IPTABLES=`which iptables` | IPTABLES=`which iptables` | ||
− | |||
# SAMBA share | # SAMBA share | ||
# Access filtering is done in /etc/samba/smb.conf | # Access filtering is done in /etc/samba/smb.conf | ||
− | $IPTABLES -A INPUT -p | + | $IPTABLES -A INPUT -p tcp --dport 135 -m comment --comment "DCE endpoint resolution" -j ACCEPT |
− | $IPTABLES -A INPUT -p udp --dport | + | $IPTABLES -A INPUT -p udp --dport 137 -m comment --comment "NetBIOS Name Service" -j ACCEPT |
− | + | $IPTABLES -A INPUT -p udp --dport 138 -m comment --comment "NetBIOS Datagram" -j ACCEPT | |
− | $IPTABLES -A INPUT -p | + | $IPTABLES -A INPUT -p tcp --dport 139 -m comment --comment "NetBIOS Session" -j ACCEPT |
− | + | $IPTABLES -A INPUT -p tcp --dport 445 -m comment --comment "SMB over TCP" -j ACCEPT | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | $IPTABLES -A INPUT -p tcp -- | ||
− | $IPTABLES -A | ||
− | + | $IPTABLES -A OUTPUT -p tcp --sport 135 -m state --state ESTABLISHED -m comment --comment "DCE endpoint resolution" -j ACCEPT | |
− | $IPTABLES -A | + | $IPTABLES -A OUTPUT -p udp --dport 137 -m comment --comment "NetBios Name Service" -j ACCEPT |
− | $IPTABLES -A OUTPUT -p tcp --dport | + | $IPTABLES -A OUTPUT -p udp --dport 138 -m comment --comment "NetBios Data Exchange" -j ACCEPT |
+ | $IPTABLES -A OUTPUT -p tcp --dport 139 -m comment --comment "NetBios Session + Samba" -j ACCEPT | ||
+ | $IPTABLES -A OUTPUT -p tcp --dport 445 -m comment --comment "CIFS - Partage Win2K and more" -j ACCEPT | ||
+ | $IPTABLES -A OUTPUT -p tcp --dport 548 -m comment --comment "Apple file sharing" -j ACCEPT | ||
− | |||
− | |||
− | |||
</syntaxhighlight> | </syntaxhighlight> | ||
− | == | + | ==FTP client== |
− | |||
− | |||
<syntaxhighlight lang="bash"> | <syntaxhighlight lang="bash"> | ||
IPTABLES=`which iptables` | IPTABLES=`which iptables` | ||
− | + | # FTP | |
− | + | # FTP INPUT (Client <--from-- Server) | |
− | + | $IPTABLES -A INPUT -p tcp --dport 21 -m conntrack --ctstate NEW,ESTABLISHED -m comment --comment "FTP command: allow FTP connections" -j ACCEPT | |
− | + | $IPTABLES -A INPUT -p tcp --dport 20 -m conntrack --ctstate NEW,ESTABLISHED,RELATED -m comment --comment "FTP data (active)" -j ACCEPT | |
− | + | $IPTABLES -A INPUT -p tcp --sport 1024:65535 --dport 1024:65535 -m conntrack --ctstate NEW,ESTABLISHED -m comment --comment "FTP data (passive)" -j ACCEPT | |
− | + | $IPTABLES -A INPUT -p tcp -m state --state ESTABLISHED -m comment --comment "FTP established connections" -j ACCEPT | |
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | |||
− | $IPTABLES -A INPUT -p | ||
− | |||
− | |||
− | |||
− | |||
− | $IPTABLES -A | ||
− | |||
− | + | # FTP OUTPUT (Client --to--> Server) | |
− | $IPTABLES -A | + | $IPTABLES -A OUTPUT -p tcp --dport 21 -m conntrack --ctstate NEW,ESTABLISHED -m comment --comment "FTP command: allow FTP connections" -j ACCEPT |
− | $IPTABLES -A OUTPUT - | + | $IPTABLES -A OUTPUT -p tcp --dport 20 -m conntrack --ctstate NEW,ESTABLISHED -m comment --comment "FTP data (active)" -j ACCEPT |
+ | $IPTABLES -A OUTPUT -p tcp --sport 1024:65535 --dport 1024:65535 -m conntrack --ctstate NEW,ESTABLISHED,RELATED -m comment --comment "FTP data (passive)" -j ACCEPT | ||
</syntaxhighlight> | </syntaxhighlight> |
Latest revision as of 18:33, 22 April 2017
Contents
Set IP preference
If you enable IPv6 then that will be the default.
Recommended solution : IPv6 is now available in a lot of places. It's time to use it!
If you don't want to use IPv6 you can force IPv4 mode. This is not recommended any-more! IPv6 is becoming bigger and bigger, you need to switch.
You can override that and set IPv4 as the default protocol:
vim /etc/gai.conf
About line 54, un-comment the following line:
#
# For sites which prefer IPv4 connections change the last line to
#
precedence ::ffff:0:0/96 100
Global networking configuration
Enable modules
First things first! Before writing any rule you have to enable the required modules in your current O.S.
- Note -
If your server is hosted over Internet then you're probably using a custom Kernel (such as OVH, Tripnet, ...). In that case most modules are already enabled.
MODPROBE=`which modprobe`
echo -e " "
echo -e "-----------------------------"
echo -e " Enable networking modules"
echo -e "-----------------------------"
##### IPv4
$MODPROBE ip_tables
$MODPROBE iptable_filter
$MODPROBE iptable_mangle
# Allow to use state match
$MODPROBE ip_conntrack
# Allow NAT
$MODPROBE iptable_nat
##### IPv6
$MODPROBE ip6_tables
$MODPROBE ip6table_filter
$MODPROBE ip6table_mangle
##### Allow active / passive FTP
$MODPROBE ip_conntrack_ftp
$MODPROBE ip_nat_ftp
##### Allow log limits
echo " ... burst limit"
$MODPROBE ipt_limit
Set network features
Now that you've enable some modules, you need to choose which network features you're gonna use or not.
IPTABLES=`which iptables`
IP6TABLES=`which ip6tables`
echo -e " "
echo -e "------------------------"
echo -e " Set network features"
echo -e "------------------------"
echo " ... Enable common Linux protections"
# Avoid broadcast echo
echo 1 > /proc/sys/net/ipv4/icmp_echo_ignore_broadcasts
# avoid TCP SYN Cookie
echo 1 > /proc/sys/net/ipv4/tcp_syncookies
# protection against bogus responses
echo 1 > /proc/sys/net/ipv4/icmp_ignore_bogus_error_responses
# Avoid IP Spoofing (discard non routable IP@)
for f in /proc/sys/net/ipv4/conf/*/rp_filter; do echo 1 > $f; done
# Avoid ICMP redirect
echo 0 > /proc/sys/net/ipv4/conf/all/accept_redirects
echo 0 > /proc/sys/net/ipv4/conf/all/send_redirects
echo 0 > /proc/sys/net/ipv6/conf/all/accept_redirects
# Avoid Source Routed
echo 0 > /proc/sys/net/ipv4/conf/all/accept_source_route
echo 0 > /proc/sys/net/ipv6/conf/all/accept_source_route
## Check TCP window
echo 1 > /proc/sys/net/ipv4/tcp_window_scaling
## Avoid DoS
echo 30 > /proc/sys/net/ipv4/tcp_fin_timeout
echo 1800 > /proc/sys/net/ipv4/tcp_keepalive_time
## Adjust TTL value
echo 64 > /proc/sys/net/ipv4/ip_default_ttl
# Enable port forwarding in general
# (i) Some might argue that it should only be done by routers...
# Since I'm using a VPN, I like to access both networks and exchange data between them.
# That's why port forwarding is enable.
echo 1 > /proc/sys/net/ipv4/ip_forward
echo 2 > /proc/sys/net/ipv6/conf/all/use_tempaddr
echo 2 > /proc/sys/net/ipv6/conf/default/use_tempaddr
echo 2 > /proc/sys/net/ipv6/conf/eth0/use_tempaddr
echo 1 > /proc/sys/net/ipv6/conf/all/forwarding
echo 0 > /proc/sys/net/ipv6/conf/default/forwarding
echo 0 > /proc/sys/net/ipv6/conf/eth0/forwarding
Default policy
Attacks types
As a reminder, there are 3 different kind of attacks:
- INPUT = intrusion. Someone want something from your computer, NOW.
- OUTPUT = disclosure. Someone want something from your computer or network - and you might give it LATER.
- FORWARD = get access. someone want something from your network. ... Or even worse: they will use your computer to perform attacks on your behalf!
You can read more about each attack over Internet.
Set default policies
This is how you defined a default policy.
- You should set all policies in ACCEPT ; and DROP the packets at the end of your firewall. By doing so you'll probably not be locked away from your server in case of firewall change.
- You should keep the RELATED and ESTABLISHED connections
IPTABLES=`which iptables`
IP6TABLES=`which ip6tables`
echo -e " "
echo -e "------------------------"
echo -e " Flush existing rules "
echo -e "------------------------"
# Delete GENERIC rules
$IP6TABLES -F
$IP6TABLES -X
$IPTABLES -F
$IPTABLES -X
# delete FILTER rule (in/out)
$IPTABLES -t filter -F
$IPTABLES -t filter -X
$IP6TABLES -t filter -F
$IP6TABLES -t filter -X
# delete MANGLE rules (packets modifications)
$IPTABLES -t mangle -F
$IPTABLES -t mangle -X
$IP6TABLES -t mangle -F
$IP6TABLES -t mangle -X
# delete NAT rules [IPv4 only]
$IPTABLES -t nat -F
$IPTABLES -t nat -X
echo -e " "
echo -e "------------------------"
echo -e " Default policy"
echo -e "------------------------"
$IPTABLES -P INPUT ACCEPT
$IPTABLES -P FORWARD ACCEPT
$IPTABLES -P OUTPUT ACCEPT
$IP6TABLES -P INPUT ACCEPT
$IP6TABLES -P FORWARD ACCEPT
$IP6TABLES -P OUTPUT ACCEPT
echo -e " "
echo -e "------------------------"
echo -e " Keep connections"
echo -e "------------------------"
$IPTABLES -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
$IPTABLES -A FORWARD -m state --state ESTABLISHED,RELATED -j ACCEPT
$IPTABLES -A OUTPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
$IP6TABLES -A INPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
$IP6TABLES -A FORWARD -m state --state ESTABLISHED,RELATED -j ACCEPT
$IP6TABLES -A OUTPUT -m state --state ESTABLISHED,RELATED -j ACCEPT
[...]
# End of script (optional)
$IPTABLES -A INPUT -j DROP
$IP6TABLES -A INPUT -j DROP
$IPTABLES -A OUTPUT -j DROP
$IP6TABLES -A OUTPUT -j DROP
Basic protection and protocol(s) enforcement
Basic (minimal) protection
You should put some minimal protection. This layer relies on your O.S and its internal checks. Most of the time that's enough to block malformed and suspicious packets.
IPTABLES=`which iptables`
IP6TABLES=`which ip6tables`
#####################
### All protocols ###
#####################
# Reject invalid packets
$IPTABLES -A INPUT -m state --state INVALID -m comment --comment "Invalid input" -j DROP
$IPTABLES -A OUTPUT -m state --state INVALID -m comment --comment "Invalid input" -j DROP
$IPTABLES -A FORWARD -m state --state INVALID -m comment --comment "Invalid forward" -j DROP
$IP6TABLES -A INPUT -m state --state INVALID -m comment --comment "Invalid input" -j DROP
$IP6TABLES -A OUTPUT -m state --state INVALID -m comment --comment "Invalid input" -j DROP
$IP6TABLES -A FORWARD -m state --state INVALID -m comment --comment "Invalid forward" -j DROP
# Ensure TCP connection requests start with SYN flag
$IPTABLES -A INPUT -p tcp -m state --state NEW ! --syn -m comment --comment "Invalid conn request" -j DROP
$IPTABLES -A OUTPUT -p tcp -m state --state NEW ! --syn -m comment --comment "Invalid conn request" -j DROP
$IP6TABLES -A INPUT -p tcp -m state --state NEW ! --syn -m comment --comment "Invalid conn request" -j DROP
$IP6TABLES -A OUTPUT -p tcp -m state --state NEW ! --syn -m comment --comment "Invalid conn request" -j DROP
############
### IPv4 ###
############
## Localhost
$IPTABLES -A INPUT ! -i lo -s 127.0.0.0/24 -m comment --comment "Reject none loopback on 'lo'" -j DROP
$IPTABLES -A OUTPUT ! -o lo -d 127.0.0.0/24 -m comment --comment "Reject none loopback on 'lo'" -j DROP
# Accept all local packets
$IPTABLES -A INPUT -i lo -m comment --comment "Accept localhost packets" -j ACCEPT
$IPTABLES -A OUTPUT -o lo -m comment --comment "Accept localhost packets" -j ACCEPT
############
### IPv6 ###
############
# Allow localhost traffic. These rules are for all protocols.
$IP6TABLES -A INPUT -s ::1 -d ::1 -j ACCEPT
$IP6TABLES -A INPUT ! -i lo -s ::1 -m comment --comment "Reject none loopback on 'lo'" -j DROP
$IP6TABLES -A OUTPUT ! -o lo -d ::1 -m comment --comment "Reject none loopback on 'lo'" -j DROP
# Allow Link-Local addresses
$IP6TABLES -A INPUT -s fe80::/10 -j ACCEPT
$IP6TABLES -A OUTPUT -s fe80::/10 -j ACCEPT
# Normally, link-local packets should NOT be forwarded and don't need an entry in the FORWARD rule.
# However, when bridging in Linux (e.g. in Xen or OpenWRT), the FORWARD rule is needed:
$IP6TABLES -A FORWARD -s fe80::/10 -j ACCEPT
#################
### Multicast ###
#################
$IPTABLES -A INPUT -m comment --comment "Multicast auto-configuration" -d 224.0.0.0/24 -j ACCEPT
$IPTABLES -A OUTPUT -m comment --comment "Multicast request" -d 224.0.0.0/24 -j ACCEPT
$IP6TABLES -A INPUT -d ff00::/8 -j ACCEPT
$IP6TABLES -A INPUT -s ff00::/8 -j ACCEPT
$IP6TABLES -A OUTPUT -d ff00::/8 -j ACCEPT
$IP6TABLES -A OUTPUT -s ff00::/8 -j ACCEPT
Block IPv4 in IPv6 tunnels
If your ISP delivers you a native IPv6 connection then you don't need to use IPv4 tunneling! Just use either IPv4 or IPv6 native mode.
IPTABLES=`which iptables`
IP6TABLES=`which ip6tables`
## IPv6 security
# No IPv4 -> IPv6 tunneling
$IP6TABLES -A INPUT -s 2002::/16 -m comment --comment "Reject 6to4 tunnels" -j DROP
$IP6TABLES -A FORWARD -s 2002::/16 -m comment --comment "Reject 6to4 tunnels" -j DROP
$IP6TABLES -A INPUT -s 2001:0::/32 -m comment --comment "Reject Teredo tunnels" -j DROP
$IP6TABLES -A FORWARD -s 2001:0::/32 -m comment --comment "Reject Teredo tunnels" -j DROP
# Block IPv6 protocol in IPv4 frames
$IPTABLES -A INPUT -p 41 -m comment --comment "Block IPv6 protocol in IPv4 frames" -j DROP
$IPTABLES -A OUTPUT -p 41 -m comment --comment "Block IPv6 protocol in IPv4 frames" -j DROP
$IPTABLES -A FORWARD -p 41 -m comment --comment "Block IPv6 protocol in IPv4 frames" -j DROP
Block IPv6 routing headers
# Filter all packets that have RH0 headers:
$IP6TABLES -A INPUT -m rt --rt-type 0 -j DROP
$IP6TABLES -A FORWARD -m rt --rt-type 0 -j DROP
$IP6TABLES -A OUTPUT -m rt --rt-type 0 -j DROP
Protocol(s) enforcement
You can even push the standard protection a bit higher by checking some protocols flags.
IPTABLES=`which iptables`
IP6TABLES=`which ip6tables`
echo -e " "
echo -e "------------------------"
echo -e " Protocols enforcement"
echo -e "------------------------"
####### IPv4 #######
echo " ... Layer 2: ICMP v4"
# ICMP packets should not be fragmented
$IPTABLES -A INPUT --fragment -p icmp -m comment --comment "no ICMP fragments" -j DROP
# SMURF attack protection
$IPTABLES -A INPUT -p icmp -m icmp --icmp-type address-mask-request -m comment --comment "address-mask-request" -j DROP
$IPTABLES -A INPUT -p icmp -m icmp --icmp-type timestamp-request -m comment --comment "timestamp-request" -j DROP
# Limit ICMP Flood
$IPTABLES -A INPUT -p icmp -m limit --limit 1/s --limit-burst 1 -m comment --comment "ICMP flood protection" -j ACCEPT
$IPTABLES -A OUTPUT -p icmp --icmp-type 0 -m comment --comment "echo reply" -j ACCEPT
$IPTABLES -A OUTPUT -p icmp --icmp-type 3 -m comment --comment "destination unreachable" -j ACCEPT
$IPTABLES -A OUTPUT -p icmp --icmp-type 8 -m comment --comment "echo request" -j ACCEPT
####### IPv6 #######
echo " ... Layer 2: ICMP v6 "
# Don't DROP ICMP6 a lot of things are happening over there! It might completly block the connection if you DROP icmp6
$IP6TABLES -A INPUT -j ACCEPT
$IP6TABLES -A OUTPUT -p icmpv6 -j ACCEPT
$IP6TABLES -A FORWARD -p icmpv6 -j ACCEPT
####### TCP IPv4 #######
echo " ... Layer 4: TCP # check packets conformity"
# INCOMING packets check
# All new incoming TCP should be SYN first
$IPTABLES -A INPUT -p tcp ! --syn -m state --state NEW -m comment --comment "new TCP connection check" -j DROP
# Avoid SYN Flood (max 3 SYN packets / second. Then Drop all requests !!)
$IPTABLES -A INPUT -p tcp --syn -m limit --limit 1/s --limit-burst 3 -m comment --comment "avoid TCP SYN flood" -j ACCEPT
# Avoid fragment packets
$IPTABLES -A INPUT -f -m comment --comment "no fragments" -j DROP
# Check TCP flags -- flag 64, 128 = bogues
$IPTABLES -A INPUT -p tcp --tcp-option 64 -m comment --comment "ECE flag" -j DROP
$IPTABLES -A INPUT -p tcp --tcp-option 128 -m comment --comment "CWR flag" -j DROP
echo " ... Layer 4: TCP # Avoid NMAP Scans"
# XMAS-NULL
$IPTABLES -A INPUT -p tcp --tcp-flags ALL NONE -m comment --comment "attack XMAS-NULL" -j DROP
# XMAS-TREE
$IPTABLES -A INPUT -p tcp --tcp-flags ALL ALL -m comment --comment "attack XMAS-tree" -j DROP
# Stealth XMAS Scan
$IPTABLES -A INPUT -p tcp --tcp-flags ALL FIN,PSH,URG -m comment --comment "attack XMAS stealth" -j DROP
# SYN/RST Scan
$IPTABLES -A INPUT -p tcp --tcp-flags SYN,RST SYN,RST -m comment --comment "scan SYN/RST" -j DROP
# SYN/FIN Scan
$IPTABLES -A INPUT -p tcp --tcp-flags SYN,FIN SYN,FIN -m comment --comment "scan SYN/FIN" -j DROP
# SYN/ACK Scan
$IPTABLES -A INPUT -p tcp --tcp-flags SYN,ACK SYN,ACK -m comment --comment "scan SYN/ACK" -j DROP
# FIN/RST Scan
$IPTABLES -A INPUT -p tcp --tcp-flags FIN,RST FIN,RST -m comment --comment "scan FIN/RST" -j DROP
# FIN/ACK Scan
$IPTABLES -A INPUT -p tcp -m tcp --tcp-flags FIN,ACK FIN -m comment --comment "scan FIN/ACK" -j DROP
# ACK/URG Scan
$IPTABLES -A INPUT -p tcp --tcp-flags ACK,URG URG -m comment --comment "scan ACK/URG" -j DROP
# FIN/URG/PSH Scan
$IPTABLES -A INPUT -p tcp --tcp-flags FIN,URG,PSH FIN,URG,PSH -m comment --comment "scan FIN/URG/PSH" -j DROP
# XMAS-PSH Scan
$IPTABLES -A INPUT -p tcp --tcp-flags ALL SYN,RST,ACK,FIN,URG -m comment --comment "scan XMAS/PSH" -j DROP
# End TCP connection
$IPTABLES -A INPUT -p tcp --tcp-flags ALL FIN -m comment --comment "end TCP connection flag" -j DROP
# Ports scans
$IPTABLES -A INPUT -p tcp --tcp-flags FIN,SYN,RST,ACK SYN -m comment --comment "common scan FIN/SYN/RST/ACK SYN" -j DROP
$IPTABLES -A INPUT -p tcp --tcp-flags FIN,SYN,RST,PSH,ACK,URG NONE -m comment --comment "common scan FIN/SYN/RST/ACK/PSH/URG NONE" -j DROP
Allow services and network protocols
DHCP
DHCP client:
IPTABLES=`which iptables`
IP6TABLES=`which ip6tables`
# DHCP client >> Broadcast IP request
$IPTABLES -A INPUT -p udp --sport 67:68 --dport 67:68 -m comment --comment "DHCP" -j ACCEPT
$IPTABLES -A OUTPUT -p udp --sport 67:68 --dport 67:68 -m comment --comment "DHCP" -j ACCEPT
$IP6TABLES -A INPUT -p udp --sport 67:68 --dport 67:68 -m comment --comment "DHCP" -j ACCEPT
$IP6TABLES -A OUTPUT -p udp --sport 67:68 --dport 67:68 -m comment --comment "DHCP" -j ACCEPT
DNS
This will allow your computer to perform DNS requests:
IPTABLES=`which iptables`
IP6TABLES=`which ip6tables`
# DNS
$IPTABLES -A INPUT -p udp --sport 53 -m comment --comment "DNS UDP sPort" -j ACCEPT
$IPTABLES -A OUTPUT -p udp --sport 53 -m comment --comment "DNS UDP sPort" -j ACCEPT
$IPTABLES -A INPUT -p udp --dport 53 -m comment --comment "DNS UDP dPort" -j ACCEPT
$IPTABLES -A OUTPUT -p udp --dport 53 -m comment --comment "DNS UDP dPort" -j ACCEPT
$IP6TABLES -A INPUT -p udp --sport 53 -m comment --comment "DNS UDP sPort" -j ACCEPT
$IP6TABLES -A OUTPUT -p udp --sport 53 -m comment --comment "DNS UDP sPort" -j ACCEPT
$IP6TABLES -A INPUT -p udp --dport 53 -m comment --comment "DNS UDP dPort" -j ACCEPT
$IP6TABLES -A OUTPUT -p udp --dport 53 -m comment --comment "DNS UDP dPort" -j ACCEPT
# DNS SEC
# Established, related input are already accepted earlier
$IPTABLES -A OUTPUT -p tcp --sport 53 -m comment --comment "DNS Sec TCP sPort" -j ACCEPT
$IPTABLES -A OUTPUT -p tcp --dport 53 -m comment --comment "DNS Sec TCP dPort" -j ACCEPT
$IP6TABLES -A OUTPUT -p tcp --sport 53 -m comment --comment "DNS Sec TCP sPort" -j ACCEPT
$IP6TABLES -A OUTPUT -p tcp --dport 53 -m comment --comment "DNS Sec TCP dPort" -j ACCEPT
!! IMPORTANT !!!
If you ever loose Internet access after that you need to check your /etc/resolv.conf
configuration and make sure you're using a valid DNS server.
LAN communication
To allow communication in the local network, without any restrictions:
IPTABLES=`which iptables`
IP_LAN_V4="172.16.50.0/24"
IP_LAN_V6="2001:DB8:1::1"
# Allow LAN communication
if [ ! -z "$IP_LAN_V4" ]
then
echo -e " ... Allow LAN communication - IP v4"
$IPTABLES -A INPUT -s $IP_LAN_V4 -d $IP_LAN_V4 -j ACCEPT
$IPTABLES -A OUTPUT -s $IP_LAN_V4 -d $IP_LAN_V4 -j ACCEPT
# Allow forwarding within the LAN
$IPTABLES -A FORWARD -s $IP_LAN_V4 -j ACCEPT
fi
if [ ! -z "$IP_LAN_V6" ]
then
echo -e " ... Allow LAN communication - IP v6"
$IP6TABLES -A INPUT -s $IP_LAN_V6 -d $IP_LAN_V6 -j ACCEPT
$IP6TABLES -A OUTPUT -s $IP_LAN_V6 -d $IP_LAN_V6 -j ACCEPT
# Allow forwarding within the LAN
$IP6TABLES -A FORWARD -s $IP_LAN_V6 -j ACCEPT
fi
Note: thanks to the ! -z operator if the variable is not set or "" then the rule will be skipped.
NTP (time syncronization) client
IPTABLES=`which iptables`
# NTP client
echo -e " ... Allow NTP time sync"
$IPTABLES -A INPUT -p udp --sport 123 -m state --state ESTABLISHED -m comment --comment "NTP (UDP)" -j ACCEPT
$IPTABLES -A INPUT -p tcp --sport 123 -m state --state ESTABLISHED -m comment --comment "NTP (TCP)" -j ACCEPT
$IPTABLES -A OUTPUT -p udp --dport 123 -m state --state NEW,ESTABLISHED -m comment --comment "NTP (UDP)" -j ACCEPT
$IPTABLES -A OUTPUT -p tcp --dport 123 -m state --state NEW,ESTABLISHED -m comment --comment "NTP (TCP)" -j ACCEPT
IPTABLES=`which iptables`
# SAMBA share
# Access filtering is done in /etc/samba/smb.conf
$IPTABLES -A INPUT -p tcp --dport 135 -m comment --comment "DCE endpoint resolution" -j ACCEPT
$IPTABLES -A INPUT -p udp --dport 137 -m comment --comment "NetBIOS Name Service" -j ACCEPT
$IPTABLES -A INPUT -p udp --dport 138 -m comment --comment "NetBIOS Datagram" -j ACCEPT
$IPTABLES -A INPUT -p tcp --dport 139 -m comment --comment "NetBIOS Session" -j ACCEPT
$IPTABLES -A INPUT -p tcp --dport 445 -m comment --comment "SMB over TCP" -j ACCEPT
$IPTABLES -A OUTPUT -p tcp --sport 135 -m state --state ESTABLISHED -m comment --comment "DCE endpoint resolution" -j ACCEPT
$IPTABLES -A OUTPUT -p udp --dport 137 -m comment --comment "NetBios Name Service" -j ACCEPT
$IPTABLES -A OUTPUT -p udp --dport 138 -m comment --comment "NetBios Data Exchange" -j ACCEPT
$IPTABLES -A OUTPUT -p tcp --dport 139 -m comment --comment "NetBios Session + Samba" -j ACCEPT
$IPTABLES -A OUTPUT -p tcp --dport 445 -m comment --comment "CIFS - Partage Win2K and more" -j ACCEPT
$IPTABLES -A OUTPUT -p tcp --dport 548 -m comment --comment "Apple file sharing" -j ACCEPT
FTP client
IPTABLES=`which iptables`
# FTP
# FTP INPUT (Client <--from-- Server)
$IPTABLES -A INPUT -p tcp --dport 21 -m conntrack --ctstate NEW,ESTABLISHED -m comment --comment "FTP command: allow FTP connections" -j ACCEPT
$IPTABLES -A INPUT -p tcp --dport 20 -m conntrack --ctstate NEW,ESTABLISHED,RELATED -m comment --comment "FTP data (active)" -j ACCEPT
$IPTABLES -A INPUT -p tcp --sport 1024:65535 --dport 1024:65535 -m conntrack --ctstate NEW,ESTABLISHED -m comment --comment "FTP data (passive)" -j ACCEPT
$IPTABLES -A INPUT -p tcp -m state --state ESTABLISHED -m comment --comment "FTP established connections" -j ACCEPT
# FTP OUTPUT (Client --to--> Server)
$IPTABLES -A OUTPUT -p tcp --dport 21 -m conntrack --ctstate NEW,ESTABLISHED -m comment --comment "FTP command: allow FTP connections" -j ACCEPT
$IPTABLES -A OUTPUT -p tcp --dport 20 -m conntrack --ctstate NEW,ESTABLISHED -m comment --comment "FTP data (active)" -j ACCEPT
$IPTABLES -A OUTPUT -p tcp --sport 1024:65535 --dport 1024:65535 -m conntrack --ctstate NEW,ESTABLISHED,RELATED -m comment --comment "FTP data (passive)" -j ACCEPT