A little script that can be handy when you arent using any automated blocking strategy. Maintaining a secure system is a proactive process. Every once in a while you will need to do stuff manually, this script can help out when fail2ban cant be install or you just need something temporary.

Breaking Down the Script

  • create_chain: This function creates a new chain and adds each IP from the blocklist to the chain. All packets from these IPs will be dropped.

  • remove_chain: This function removes the chain from IPtables, effectively unblocking all the IPs that were in the chain.

  • add_ip: This function adds a specific IP to the chain and the blocklist, effectively blocking it.

  • remove_ip: This function removes a specific IP from the chain and the blocklist, effectively unblocking it.

  • start: This function starts the blocking operation by inserting the custom chain to the INPUT chain of IPtables.

  • stop: This function stops the blocking operation by flushing the custom chain and removing it from the INPUT chain.

  • watch: This function allows you to keep an eye on the chain and its effect on the IPtables.

How to Use the Script

  1. Create the Chain and Block IPs

    Run the script with the create-chain argument. This will create a new chain in IPtables and block all IPs in your blocklist.

    ./script.sh create-chain
    
  2. Add an IP to the Blocklist

    To block an additional IP, run the script with the add-ip argument followed by the IP.

    ./script.sh add-ip 192.168.0.1
    
  3. Remove an IP from the Blocklist

    To unblock an IP, use the remove-ip argument followed by the IP.

    ./script.sh remove-ip 192.168.0.1
    
  4. Start the Blocking Operation

    Once your blocklist is ready, use the start argument to commence the blocking operation.

    ./script.sh start
    
  5. Stop the Blocking Operation

    If you need to stop the operation, use the stop argument.

    ./script.sh stop
    
  6. Watch the Chain

    To monitor the chain and its effects on the IPtables, use the watch argument.

    ./script.sh watch
    

Script


#!/bin/bash

# Define the file that contains the blocklist
SCRIPT_DIR="$(dirname "$(readlink -f "$0")")"
BLOCKLIST="${SCRIPT_DIR}/blocklist.txt"
IPTABLES="/sbin/iptables"
CHAIN_NAME="BadActors"

function create_chain() {
    # Create new chain
    $IPTABLES -N "$CHAIN_NAME"

    # Loop through the blocklist file and add each IP to the BadActors chain
    while read -r IP; do
        # $IPTABLES -A "$CHAIN_NAME" -s $IP -j LOG -log-prefix "IPTables-BadActors-Dropped: " --log-level 4
        $IPTABLES -A "$CHAIN_NAME" -s $IP -j DROP
    done < "$BLOCKLIST"
}

function remove_chain() {
    if $IPTABLES -L "$CHAIN_NAME" >/dev/null 2>&1; then
        # Remove reference in INPUT chain
        $IPTABLES -D INPUT -j "$CHAIN_NAME"

        # Flush the chain to remove all rules
        $IPTABLES -F "$CHAIN_NAME"

        # Delete the chain
        $IPTABLES -X "$CHAIN_NAME"

        echo "Chain "$CHAIN_NAME" removed successfully."
    else
        echo "Chain "$CHAIN_NAME" does not exist."
    fi
}

function add_ip() {
    IP=$1

    # Check if the BadActors chain exists
    if $IPTABLES -L "$CHAIN_NAME" >/dev/null 2>&1; then
        # Add the IP to the BadActors chain
        # $IPTABLES -A "$CHAIN_NAME" -s $IP -j LOG -log-prefix "IPTables-BadActors-Dropped: " --log-level 4
        $IPTABLES -A "$CHAIN_NAME" -s $IP -j DROP
        echo $IP >> $BLOCKLIST
        echo "IP $IP added to BadActors chain."
    else
        echo "BadActors chain does not exist. Please create it first."
    fi
}

function remove_ip() {
    IP=$1

    # Check if the BadActors chain exists
    if $IPTABLES -L "$CHAIN_NAME" >/dev/null 2>&1; then
        # Remove the IP from the BadActors chain
        # $IPTABLES -D $CHAIN_NAME -s $IP -j LOG --log-prefix "IPTables-BadActors-Dropped: " --log-level 4
        $IPTABLES -D "$CHAIN_NAME" -s $IP -j DROP
        sed -i "/$IP/d" $BLOCKLIST
        echo "IP $IP removed from BadActors chain."
    else
        echo "BadActors chain does not exist. Please create it first."
    fi
}

function start() {
    # Check if the BadActors chain exists
    if $IPTABLES -L "$CHAIN_NAME" >/dev/null 2>&1; then
        # Add the BadActors chain to the INPUT chain
        $IPTABLES -I INPUT -j "$CHAIN_NAME"
    else
        echo "BadActors chain does not exist. Please create it first."
    fi
}


function stop() {
    # Flush the BadActors chain to remove all rules
    $IPTABLES -F "$CHAIN_NAME"

    # Remove reference in INPUT chain
    $IPTABLES -D INPUT -j "$CHAIN_NAME"

    # Delete the chain
    $IPTABLES -X "$CHAIN_NAME"
}

function watch() {
    echo "Start Watching"
    /usr/bin/watch '$IPTABLES -L "'$CHAIN_NAME'" -n -v'
}

# Check the command line argument
case "$1" in
    create-chain)
        create_chain
        ;;
    remove-chain)
        remove_chain
        ;;
    add-ip)
        add_ip $2
        ;;
    remove-ip)
        remove_ip $2
        ;;
    watch)
        watch
        ;;
    start)
        start
        ;;
    stop)
        stop
        ;;
    *)
        echo "Usage: $0 {create-chain|remove-chain|add-ip|remove-ip|start|stop|watch}"
        exit 1
esac

Remember, to make this persistent, you will need to install iptables-persistent and do a iptables-save > /etc/iptables/rules.v4



Buy Me a Coffee