Line 109: |
Line 109: |
| == Other == | | == Other == |
| Any other information that doesn't fit elsewhere. | | Any other information that doesn't fit elsewhere. |
| + | |
| + | = Firewall = |
| + | Information regarding firewall setup as related to the VPN configs above. |
| + | |
| + | == Linux == |
| + | The following script can be used to setup a basic firewall on a Linux based system using iptables. |
| + | |
| + | Supports IPv4 and IPv6. Comment out the parts that are not need with a # or optionally delete them. |
| + | |
| + | #!/bin/bash |
| + | |
| + | #Modify to match your network interface |
| + | INET_IF=eth0 |
| + | |
| + | #Edit IP address below to match the IP and netmask of the system or subnet you want to allow access to |
| + | #"Management only" services. You modify and add or remove as needed. Make sure to update the ManagementFilterV4 with |
| + | #the changes |
| + | System1="XX.XX.XX.XX/YY" |
| + | System2="XX.XX.XX.XX/YY" |
| + | |
| + | ManagementFilterV4=$System1,$System2 |
| + | |
| + | #Flush and zero all tables |
| + | modprobe ip_tables |
| + | modprobe ipt_limit |
| + | modprobe iptable_mangle |
| + | modprobe ipt_state |
| + | modprobe ipt_LOG |
| + | modprobe iptable_filter |
| + | modprobe ipv6 |
| + | |
| + | iptables -F INPUT |
| + | iptables -F FORWARD |
| + | iptables -t nat -F POSTROUTING |
| + | iptables -t nat -F PREROUTING |
| + | |
| + | ip6tables -F INPUT |
| + | ip6tables -F FORWARD |
| + | |
| + | #init the log-and-drop chain |
| + | iptables -F log-and-drop |
| + | iptables -X log-and-drop |
| + | iptables -N log-and-drop |
| + | |
| + | ip6tables -F log-and-drop |
| + | ip6tables -X log-and-drop |
| + | ip6tables -N log-and-drop |
| + | |
| + | iptables -F log-and-reject |
| + | iptables -X log-and-reject |
| + | iptables -N log-and-reject |
| + | |
| + | ip6tables -F log-and-reject |
| + | ip6tables -X log-and-reject |
| + | ip6tables -N log-and-reject |
| + | |
| + | #Now add in rules to affect DOCKER containers - uncomment if using Docker |
| + | #See https://unrouted.io/2017/08/15/docker-firewall/ |
| + | #iptables -F DOCKER-USER |
| + | #iptables -X DOCKER-USER |
| + | #iptables -N DOCKER-USER |
| + | |
| + | #ip6tables -F DOCKER-USER |
| + | #ip6tables -X DOCKER-USER |
| + | #ip6tables -N DOCKER-USER |
| + | |
| + | #iptables -F FILTERS |
| + | #iptables -X FILTERS |
| + | #iptables -N FILTERS |
| + | |
| + | #ip6tables -F FILTERS |
| + | #ip6tables -X FILTERS |
| + | #ip6tables -N FILTERS |
| + | |
| + | echo "all tables flushed and dropped" |
| + | # Specific chain used for logging packets before blocking them |
| + | iptables -A log-and-drop -j LOG --log-prefix "[IPTables] Drop " |
| + | iptables -A log-and-drop -j DROP |
| + | |
| + | ip6tables -A log-and-drop -j LOG --log-prefix "[IPTables] Drop " |
| + | ip6tables -A log-and-drop -j DROP |
| + | |
| + | # Specific chain used for logging packets before blocking them |
| + | iptables -A log-and-reject -j LOG --log-prefix "[IPTables] Reject " |
| + | iptables -A log-and-reject -j REJECT |
| + | |
| + | ip6tables -A log-and-reject -j LOG --log-prefix "[IPTables] Reject " |
| + | ip6tables -A log-and-reject -j REJECT |
| + | |
| + | echo "logging chains setup" |
| + | |
| + | # The packets having the TCP flags activated are dropped |
| + | # and so for the ones with no flag at all (often used with Nmap scans) |
| + | iptables -A FORWARD -p tcp --tcp-flags ALL ALL -j log-and-drop |
| + | iptables -A FORWARD -p tcp --tcp-flags ALL NONE -j log-and-drop |
| + | |
| + | ip6tables -A FORWARD -p tcp --tcp-flags ALL ALL -j log-and-drop |
| + | ip6tables -A FORWARD -p tcp --tcp-flags ALL NONE -j log-and-drop |
| + | |
| + | #setup DOCKER-USER related rules - uncomment if using Docker |
| + | #iptables -A DOCKER-USER -i $INET_IF -j FILTERS |
| + | |
| + | #Now add any rules you want Docker to abide by for containers to -A FILTERS |
| + | |
| + | #limit traffic to 80 an 443 |
| + | #DCQ="2" #max requests in 1 second |
| + | #DCH="25" #max requests over 7 seconds |
| + | |
| + | #iptables -A FILTERS -p tcp --dport 80 -m state --state NEW -m recent --set --name P80QF --rsource |
| + | #iptables -A FILTERS -p tcp --dport 80 -m state --state NEW -m recent --update --second 1 --hitcount ${DCQ} --name P80QF --rsource -j log-and-drop |
| + | #iptables -A FILTERS -p tcp --dport 80 -m state --state NEW -m recent --set --name P80HF --rsource |
| + | #iptables -A FILTERS -p tcp --dport 80 -m state --state NEW -m recent --update --second 7 --hitcount ${DCH} --name P80HF --rsource -j log-and-drop |
| + | |
| + | #iptables -A FILTERS -p tcp --dport 443 -m state --state NEW -m recent --set --name P443QF --rsource |
| + | #iptables -A FILTERS -p tcp --dport 443 -m state --state NEW -m recent --update --second 1 --hitcount ${DCQ} --name P443QF --rsource -j log-and-drop |
| + | #iptables -A FILTERS -p tcp --dport 443 -m state --state NEW -m recent --set --name P443HF --rsource |
| + | #iptables -A FILTERS -p tcp --dport 443 -m state --state NEW -m recent --update --second 7 --hitcount ${DCH} --name P443HF --rsource -j log-and-drop |
| + | |
| + | #default return chain |
| + | #iptables -A FILTERS -j RETURN |
| + | |
| + | #Global blocks |
| + | #iptables -t filter -A INPUT -j DROP -s 12.34.56.78/32 |
| + | |
| + | #Limit DNS requests to prevent flood attacks - use if you are running a DNS server on the system this is installed on. |
| + | # Requests per second |
| + | #RQS="15" |
| + | # Requests per 7 seconds |
| + | #RQH="35" |
| + | |
| + | #iptables -A INPUT -p udp --dport 53 -m state --state NEW -m recent --set --name DNSQF --rsource |
| + | #iptables -A INPUT -p udp --dport 53 -m state --state NEW -m recent --update --seconds 1 --hitcount ${RQS} --name DNSQF --rsource -j DROP |
| + | #iptables -A INPUT -p udp --dport 53 -m state --state NEW -m recent --set --name DNSHF --rsource |
| + | #iptables -A INPUT -p udp --dport 53 -m state --state NEW -m recent --update --seconds 7 --hitcount ${RQH} --name DNSHF --rsource -j DROP |
| + | |
| + | #Uncomment the next sections if using IPSEC |
| + | #Clamp MSS on IPSEC tunnels |
| + | #iptables -t mangle -A FORWARD -m policy --pol ipsec --dir in -p tcp -m tcp --tcp-flags SYN,RST SYN -m tcpmss --mss 1361:1536 -j TCPMSS --set-mss 1360 |
| + | #iptables -t mangle -A FORWARD -m policy --pol ipsec --dir out -p tcp -m tcp --tcp-flags SYN,RST SYN -m tcpmss --mss 1361:1536 -j TCPMSS --set-mss 1360 |
| + | |
| + | # allow IPSEC from other boxes |
| + | #IPSECsrc='XX.XX.XX.XX/YY' # Put in the form of XX.XX.XX.XX = IP address you want to allow IPSEC in from and YY is the netmask. |
| + | |
| + | #Technically the next two are not needed as we have the policy |
| + | #iptables -A INPUT -i $INET_IF -p 50 -j ACCEPT --src "$IPSECsrc" |
| + | #iptables -A INPUT -i $INET_IF -p 51 -j ACCEPT --src "$IPSECsrc" |
| + | #iptables -A INPUT -i $INET_IF -p udp --dport 500 -j ACCEPT --src "$IPSECsrc" |
| + | #iptables -A INPUT -i $INET_IF -p udp --dport 4500 -j ACCEPT --src "$IPSECsrc" |
| + | # this is needed to allow all ipsec packets when it's host to host |
| + | #iptables -A INPUT -m policy --dir in --pol ipsec -j ACCEPT --src "$IPSECsrc" |
| + | |
| + | #allow DNS in |
| + | #iptables -t filter -A INPUT -j ACCEPT --protocol tcp --dport 53 |
| + | #iptables -t filter -A INPUT -j ACCEPT --protocol udp --dport 53 |
| + | |
| + | #ip6tables -t filter -A INPUT -j ACCEPT --protocol tcp --dport 53 |
| + | #ip6tables -t filter -A INPUT -j ACCEPT --protocol udp --dport 53 |
| + | |
| + | #allow port 80 in |
| + | #iptables -t filter -A INPUT -j ACCEPT --protocol tcp --dport 80 |
| + | #ip6tables -t filter -A INPUT -j ACCEPT --protocol tcp --dport 80 |
| + | |
| + | #allow port 443 in |
| + | #iptables -t filter -A INPUT -j ACCEPT --protocol tcp --dport 443 |
| + | #ip6tables -t filter -A INPUT -j ACCEPT --protocol tcp --dport 443 |
| + | |
| + | # allow all ssh in - uncomment ManagemetnFilterV4 and comment out the two lines below to restrict SSH access on port 22 |
| + | #iptables -t filter -A INPUT -j ACCEPT --protocol tcp --dport 22 --src $ManagementFilterV4 |
| + | iptables -t filter -A INPUT -j ACCEPT --protocol tcp --dport 22 |
| + | ip6tables -t filter -A INPUT -j ACCEPT --protocol tcp --dport 22 |
| + | |
| + | echo "end of services" |
| + | # allow ping at 2 per sec |
| + | iptables -t filter -A INPUT -j ACCEPT --in-interface $INET_IF --protocol icmp --icmp-type echo-request --match limit --limit 4/s --limit-burst 3 |
| + | iptables -t filter -A INPUT -j log-and-drop --in-interface $INET_IF --protocol icmp --icmp-type echo-request |
| + | |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type destination-unreachable -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type packet-too-big -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type time-exceeded -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type parameter-problem -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type echo-request -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type echo-reply -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type router-solicitation -m hl --hl-eq 255 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type router-advertisement -m hl --hl-eq 255 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-solicitation -m hl --hl-eq 255 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type neighbor-advertisement -m hl --hl-eq 255 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 141 -m hl --hl-eq 255 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 142 -m hl --hl-eq 255 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 130 -s fe80::/10 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 131 -s fe80::/10 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 132 -s fe80::/10 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 143 -s fe80::/10 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 148 -m hl --hl-eq 255 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 149 -m hl --hl-eq 255 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 151 -s fe80::/10 -m hl --hl-eq 1 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 152 -s fe80::/10 -m hl --hl-eq 1 -j ACCEPT |
| + | ip6tables -A INPUT -p icmpv6 --icmpv6-type 153 -s fe80::/10 -m hl --hl-eq 1 -j ACCEPT |
| + | |
| + | # allow responces to local initated connections |
| + | #iptables -A INPUT -i $INET_IF --match state --state NEW,INVALID -j log-and-drop |
| + | #iptables -A FORWARD -i $INET_IF --match state --state NEW,INVALID -j log-and-drop |
| + | iptables -t filter -A INPUT -j ACCEPT --match state --state RELATED,ESTABLISHED |
| + | ip6tables -t filter -A INPUT -j ACCEPT --match state --state RELATED,ESTABLISHED |
| + | |
| + | # Set rp_filter to 2 |
| + | for i in `find /proc/sys/net/ipv*/conf -name rp_filter` |
| + | do |
| + | echo "2" >$i |
| + | done |
| + | # setup a default deny rule for outside traffic |
| + | iptables -t filter -A INPUT --in-interface $INET_IF -j log-and-drop |
| + | ip6tables -t filter -A INPUT --in-interface $INET_IF -j log-and-drop |
| + | |
| + | #uncomment if you are using Docker |
| + | #echo "Restarting Docker" |
| + | #systemctl restart docker |
| + | |
| + | #uncomment the next two lines if fail2ban is installed |
| + | #echo "Restarting fail2ban" |
| + | #systemctl restart fail2ban |