Schuby
Occasional Visitor
I modified @Adamm 's script (http://www.snbforums.com/threads/ho...ious-ips-using-ipset-firewall-addition.16798/) and with the help of @Maude I was able to use iptables to forward ports to my web server and still have blacklisted users banned as needed.
In regards to the original script, I removed the 'dynamic' portion of it (i.e. searching for 'DROP' packets in the firewall log and auto-banning them) as well as added a 'checkban' feature to see if a provided IP address is either banned or not banned. Furthermore I used 'ShellCheck' to cleanup code and bring it up to shell standards.
Here is the full edit: FIXED script:
As of this moment, this passes ShellCheck 100%!
Many thanks to @Neurophile , @Fitz Mutch , and @barzot for helping me fix the code.
To-do:
In regards to the original script, I removed the 'dynamic' portion of it (i.e. searching for 'DROP' packets in the firewall log and auto-banning them) as well as added a 'checkban' feature to see if a provided IP address is either banned or not banned. Furthermore I used 'ShellCheck' to cleanup code and bring it up to shell standards.
Here is the full edit: FIXED script:
Code:
#!/bin/sh
#################################################################################################
############################## 06/02/2016 - Firewall Addition v3.1 ##############################
#################################################################################################
########################----- Make Sure To Edit The Following Files -----########################
### /jffs/scripts/firewall-start <-- Sets up cronjob/iptables rules #
### /jffs/scripts/firewall <-- Blacklists IP's From /jffs/scripts/ipset.txt #
### /jffs/scripts/ipset.txt <-- Banned IP List/IPSet Rules #
#################################################################################################
#####Commands / Variables#####
UNBANSINGLE="unban" # <-- Remove Single IP From Blacklist i.e. ./Firewall.sh unban 123.45.6.7
UNBANALL="unbanall" # <-- Unbans All IPs In Blacklist i.e. ./Firewall.sh unbanall
REMOVEBANS="removeall" # <-- Remove All Entries From Blacklist i.e. ./Firewall.sh removeall
SAVEIPSET="save" # <-- Save Blacklists to /jffs/scripts/ipset.txt i.e. ./Firewall.sh save
BANSINGLE="ban" # <-- Adds Entry To Blacklist i.e. ./Firewall.sh ban 123.45.6.7
BANCOUNTRYSINGLE="country" # <-- Adds entire country to blacklist i.e. ./Firewall.sh country ca
BANCOUNTRYLIST="bancountry" # <-- Bans specified countries in this file i.e. ./Firewall.sh bancountry
WHITELIST="whitelist" # <-- Add IPs from path to Whitelist i.e. ./Firewall.sh whitelist /jffs/scripts/whitelist.txt
NEWLIST="new" # <-- Create new IPSet Blacklist i.e. ./Firewall.sh new
CHECKBAN="check" # <-- Check if an IP is banned. i.e. ./Firewall.sh check 123.45.6.7
##############################
start_time=$(date +%s)
if [ "$1" = "$UNBANSINGLE" ]
then
logger -t Firewall "[Unbanning And Removing $2 From Blacklist] ... ... ..."
ipset -D Blacklist "$2"
printf "%s" "$(sed "/$2/d" /jffs/scripts/ipset.txt > unbantmpfile && mv unbantmpfile ipset.txt)"
echo "$2 Is Now Unbanned"
elif [ "1" = "$UNBANALL" ]
then
echo "[Unbanning All IP's] ... ... ..."
logger -t Firewall "[Unbanning All IP's] ... ... ..."
ipset --flush Blacklist
ipset --flush BlockedCountries
elif [ "$1" = "$REMOVEBANS" ]
then
nvram set Blacklist="$(printf "%s" "$(ipset -L Blacklist | wc -l)")"
echo "[Deleting All $(nvram get Blacklist) Entries From Blacklist] ... ... ..."
logger -t Firewall "[Deleting All $(nvram get Blacklist) Entries From Blacklist] ... ... ..."
ipset --flush Blacklist
ipset --flush BlockedCountries
ipset --save > /jffs/scripts/ipset.txt
elif [ "$1" = "$SAVEIPSET" ]
then
echo "[Saving Blacklists] ... ... ..."
ipset --save > /jffs/scripts/ipset.txt
printf "%s" "$(sed "/crond: USER admin/d" /tmp/syslog.log > saveiptmpfile && mv saveiptmpfile /tmp/syslog.log)"
elif [ "$1" = "$BANSINGLE" ]
then
logger -t Firewall "[Adding $2 To Blacklist] ... ... ..."
ipset -q -A Blacklist "$2"
echo "$2 Is Now Banned"
elif [ "$1" = "$BANCOUNTRYSINGLE" ]
then
echo "Input Country Abbreviation"
read -r country
for IP in $(wget -q -O - http://www.ipdeny.com/ipblocks/data/countries/"$country".zone)
do
ipset -q -A BlockedCountries "$IP"
done
elif [ "$1" = "$BANCOUNTRYLIST" ]
then
echo "[Banning Spam Countries] ... ... ..."
for country in pk cn in jp ru sa
do
for IP in $(wget -q -O - http://www.ipdeny.com/ipblocks/data/countries/"$country".zone)
do
ipset -q -A BlockedCountries "$IP"
done
done
elif [ "$1" = "$WHITELIST" ]
then
echo "Input file location"
read -r WHITELISTFILE
grep -v '^ *#' < "$WHITELISTFILE" | while IFS= read -r IP
do
ipset -q -A Whitelist "$IP"
echo "$IP"
done
ipset --save > /jffs/scripts/ipset.txt
elif [ "$1" = "$NEWLIST" ]
then
echo "Does The Blacklist Need To Be Downloaded? yes/no"
read -r ENABLEDOWNLOAD
if [ X"$ENABLEDOWNLOAD" = X"yes" ]; then
echo "Input URL For IPSet Blacklist"
read -r DOWNLOADURL
wget -O /jffs/scripts/ipset2.txt "$DOWNLOADURL"
fi
echo "Input New Set Name"
read -r SETNAME
sed -i "s/Blacklist/$SETNAME/g" /jffs/scripts/ipset2.txt
ipset -q -R < /jffs/scripts/ipset2.txt
echo "Successfully Added New Set"
elif [ "$1" = "$CHECKBAN" ]
then
checkip=$(ipset -L | grep "$2")
if test -n "$checkip"; then
echo "$2" is banned.
exit
else
echo "$2" is not banned.
exit
fi
fi
### Main ban script function
printf "%s" "$(sed "/IP Banning Started/d" /tmp/syslog.log > baniptmpfile && mv baniptmpfile /tmp/syslog.log)"
echo "[IP Banning Started] ... ... ..."
logger -t Firewall "[IP Banning Started] ... ... ..."
ipset -q -R < /jffs/scripts/ipset.txt
ipset -q -N Whitelist nethash
ipset -q -N Blacklist iphash
ipset -q -N BlockedCountries nethash
### Add webserver forwards
iptables -t nat -I PREROUTING -d "$(nvram get wan0_ipaddr)"/32 -p tcp -m tcp --dport 80 -j DNAT --to-destination "$(nvram get WWW)":80
iptables -t nat -I PREROUTING -d "$(nvram get wan0_ipaddr)"/32 -p tcp -m tcp --dport 443 -j DNAT --to-destination "$(nvram get WWW)":443
iptables -t nat -I PREROUTING -d "$(nvram get wan0_ipaddr)"/32 -p tcp -m tcp --dport 80 -m set --match-set Whitelist src -j DNAT --to-destination "$(nvram get WWW)":80
iptables -t nat -I PREROUTING -d "$(nvram get wan0_ipaddr)"/32 -p tcp -m tcp --dport 443 -m set --match-set Whitelist src -j DNAT --to-destination "$(nvram get WWW)":443
iptables -I FORWARD -m conntrack --ctstate DNAT -j ACCEPT
iptables -I FORWARD -m conntrack --ctstate DNAT -m set --match-set BlockedCountries src -j DROP
iptables -I FORWARD -m conntrack --ctstate DNAT -m set --match-set Blacklist src -j DROP
### Standard blocking rules based on lists.
iptables -I INPUT -m set --match-set Blacklist src -j DROP
iptables -I INPUT -m set --match-set BlockedCountries src -j DROP
iptables -I INPUT -m set --match-set Whitelist src -j ACCEPT
ipset -q -A Whitelist 192.168.1.0/24
ipset -q -A Whitelist "$(nvram get lan_ipaddr)"/24
###############
# - Logging - #
###############
OLDAMOUNT="$(nvram get Blacklist)"
nvram set Blacklist=$(($(ipset -L Blacklist | wc -l) - 6))
NEWAMOUNT="$(nvram get Blacklist)"
nvram set BlacklistTotal=$(($(ipset -L | wc -l) - 26))
current_time=$(date +%s)
start_time=$((current_time - start_time))
echo "[Complete] $NEWAMOUNT IPs currently banned. $((NEWAMOUNT - OLDAMOUNT)) New IP's Banned. $(nvram get BlacklistTotal) Banned Overall ($start_time s)"
logger -t Firewall "[Complete] $NEWAMOUNT IPs currently banned. $((NEWAMOUNT - OLDAMOUNT)) New IP's Banned. $(nvram get BlacklistTotal) Banned Overall ($start_time s)"
As of this moment, this passes ShellCheck 100%!
Many thanks to @Neurophile , @Fitz Mutch , and @barzot for helping me fix the code.
To-do:
- Allow users to specify webserver IP at top of script instead of expecting them to set WWW in nvram.
- Use printf instead of echo.
- Incorporate the updated malware code by @Neurophile and @swetoast
- Allow users to specify ports wanted (if any) at the start of the script.
- Remove any unused/unwanted arguments.
- Allow users to specify countries in a separate file.
- Put everything on github.
Last edited: