Filename: Private: No Yes Filetype: Auto ABAP Sophia Apex Azure CLI Batch Bicep C Cameligo Clojure CoffeeScript C++ C# CSP CSS Cypher Dart Dockerfile ECL Elixir Flow9 FreeMarker2 FreeMarker2 (Angle/Bracket) FreeMarker2 (Angle/Dollar) FreeMarker2 (Auto/Bracket) FreeMarker2 (Auto/Dollar) FreeMarker2 (Bracket/Bracket) FreeMarker2 (Bracket/Dollar) F# Go GraphQL Handlebars Terraform HTML Ini Java JavaScript Julia Kotlin Less Lexon Liquid Lua Modula-3 Markdown MDX MIPS DAX MySQL Objective-C Pascal Pascaligo Perl PostgreSQL PHP Plain text ATS PQ PowerShell Protobuf Pug Python Q# R Razor Redis Redshift ReStructuredText Ruby Rust Small Basic Scala Scheme Sass Shell Solidity SPARQL SQL StructuredText Swift SV Tcl Twig TypeScript TypeSpec Visual Basic V WebGPU Shading Language XML YAML Indentation: Spaces Tabs 1 2 3 4 5 6 7 8 Clone #!/bin/bash # vim:ts=2:sts=2:sw=2:et set -e # # global defaults # DB="${DB:-/var/db/bandb/bandb.txt}" TABLE="${TABLE:-bandb}" IP6TABLES="${IP6TABLES:-ip6tables}" IPTABLES="${IPTABLES:-iptables}" # # iptables helper # ipxtables() { local quiet=false local addr="${1}" shift if [[ "$addr" = '-q' ]]; then quiet=true addr="${1}" shift fi case "${addr}" in *:*) "${quiet}" || echo "# ${IP6TABLES}" "${@}" "${IP6TABLES}" "${@}" ;; *) "${quiet}" || echo "# ${IPTABLES}" "${@}" "${IPTABLES}" "${@}" ;; esac } # # usage # do_usage() { case "${1}" in start) echo 'Usage:' echo " ${0} start [options]" echo echo 'Starts bandb.' echo 'This command has no command-specific options.' echo "See \`${0} -h\` for a list of global options." ;; stop) echo 'Usage:' echo " ${0} stop [options]" echo echo 'Stops bandb.' echo 'This command has no command-specific options.' echo "See \`${0} -h\` for a list of global options." ;; flush) echo 'Usage:' echo " ${0} flush [options]" echo echo 'Flushes bandb.' echo 'This command has no command-specific options.' echo "See \`${0} -h\` for a list of global options." ;; list) echo 'Usage:' echo " ${0} list [options]" echo echo 'Lists banned addresses.' echo 'This command has no command-specific options.' echo "See \`${0} -h\` for a list of global options." ;; ban) echo 'Usage:' echo " ${0} ban [options] <addr...>" echo echo 'Bans one or more addresses.' echo 'This command has no command-specific options.' echo "See \`${0} -h\` for a list of global options." ;; unban) echo 'Usage:' echo " ${0} unban [options] <addr.>" echo echo 'Unbans one or more addresses.' echo 'This command has no command-specific options.' echo "See \`${0} -h\` for a list of global options." ;; *) echo 'Usage:' echo " ${0} <command> [options] [args...]" echo echo 'Commands:' echo ' start [options] Starts bandb' echo ' stop [options] Stops bandb' echo ' flush [options] Flushes bandb' echo ' list [options] Lists banned addresses' echo ' ban [options] <addr...> Bans one or more addresses' echo ' unban [options] <addr...> Unbans one or more addresses' echo echo 'Global options:' echo " -d DB, --db=DB Set database path (default: ${DB})" echo " -t TBL, --table=TBL Set chain name (default: ${TABLE})" echo " -4 CMD, --iptables=CMD Set iptables command (default: ${IPTABLES})" echo " -6 CMD, --ip6tables=CMD Set ip6tables command (default: ${IP6TABLES})" ;; esac exit "${2:0}" } # # start # do_start() { touch "${DB}" ipxtables :: -F "${TABLE}" ipxtables 0.0.0.0 -F "${TABLE}" while read -r addr; do ipxtables "${addr}" -A "${TABLE}" -s "${addr}" -j DROP done <"${DB}" } # # stop # do_stop() { ipxtables :: -F "${TABLE}" ipxtables 0.0.0.0 -F "${TABLE}" } # # flush # do_flush() { : >"${DB}" ipxtables :: -F "${TABLE}" ipxtables 0.0.0.0 -F "${TABLE}" } # # list # do_list() { sort -V < "${DB}" } # # ban # do_ban() { local result=0 local addr for addr; do local re="${addr//./\\.}" if ! grep -q "^${re}$" "${DB}"; then cp "${DB}" "${DB}.tmp" echo "${addr}" >>"${DB}.tmp" sort -V "${DB}.tmp" >"${DB}" rm -f "${DB}.tmp" ipxtables "${addr}" -A "${TABLE}" -s "${addr}" -j DROP else result=$((result+1)) fi done return "${result}" } # # unban # do_unban() { local result=0 local addr for addr; do local re="${addr//./\\.}" if grep -q "^${re}$" "${DB}"; then grep -v "^${re}$" "${DB}" >"${DB}.tmp" mv "${DB}.tmp" "${DB}" ipxtables -q "${addr}" --line-numbers -nvL "${TABLE}" | awk "/ ${re} / { print \$1 }" | while read -r rule_no; do ipxtables "${addr}" -D "${TABLE}" "${rule_no}" done else result=$((result+1)) fi done return "${result}" } # # go! # ARGS=() PARSE=true DO_HELP=false while [[ -n "${1}" ]]; do if ${PARSE}; then case "${1}" in -d|--db) DB="${2}"; shift;; --db=*) DB="${1:5}";; -d*) DB="${1:2}";; -t|--table) TABLE="${2}"; shift;; --table=*) TABLE="${1:8}";; -t*) TABLE="${1:2}";; -6|--ip6tabpes) IP6TABLES="${2}"; shift;; --ip6tables=*) IP6TABLES="${1:12}";; -6*) IP6TABLES="${1:2}";; -4|--iptabpes) IPTABLES="${2}"; shift;; --iptables=*) IPTABLES="${1:11}";; -4*) IPTABLES="${1:2}";; -h|--help) DO_HELP=true;; *) ARGS+=("${1}");; esac else ARGS+=("${1}") fi shift done set -- "${ARGS[@]}" if $DO_HELP; then do_usage "${1:-main}" 0 >&1 elif [[ -z "${1}" ]]; then do_usage main 1 >&2 fi case "${1}" in start) do_start "${@:2}";; stop) do_stop "${@:2}";; flush) do_flush "${@:2}";; ls|list) do_list "${@:2}";; b|ban) do_ban "${@:2}";; u|unban) do_unban "${@:2}";; *) echo "${0}: unknown command: ${1}" >&2; echo >&2; do_usage main 1 >&2;; esac Paste