Enhance IPv6 ban functionality: add dynamic mask handling and prevent banning own addresses
This commit is contained in:
@@ -73,6 +73,54 @@ containsElement () {
|
||||
return 1
|
||||
}
|
||||
|
||||
## - Expand a given IPv6 address (parameter 1) to 32 hex digits without colons.
|
||||
## - Returns 1 if the address cannot be parsed.
|
||||
## -
|
||||
ipv6_expand() {
|
||||
local _addr="${1,,}"
|
||||
local _head _tail _group _n _out=""
|
||||
local -a _h=() _t=()
|
||||
|
||||
if [[ "$_addr" == *::* ]] ; then
|
||||
_head="${_addr%%::*}"
|
||||
_tail="${_addr#*::}"
|
||||
[[ "$_tail" == *::* ]] && return 1
|
||||
[[ -n "$_head" ]] && IFS=':' read -ra _h <<< "$_head"
|
||||
[[ -n "$_tail" ]] && IFS=':' read -ra _t <<< "$_tail"
|
||||
_n=$(( 8 - ${#_h[@]} - ${#_t[@]} ))
|
||||
[[ $_n -lt 1 ]] && return 1
|
||||
for (( ; _n > 0; _n-- )) ; do
|
||||
_h+=("0")
|
||||
done
|
||||
_h+=("${_t[@]}")
|
||||
else
|
||||
IFS=':' read -ra _h <<< "$_addr"
|
||||
fi
|
||||
|
||||
[[ ${#_h[@]} -eq 8 ]] || return 1
|
||||
for _group in "${_h[@]}" ; do
|
||||
[[ "$_group" =~ ^[0-9a-f]{1,4}$ ]] || return 1
|
||||
_out+="$(printf '%04x' "0x$_group")"
|
||||
done
|
||||
|
||||
echo "$_out"
|
||||
}
|
||||
|
||||
## - Check if a given IPv6 address (parameter 1) lies within the network
|
||||
## - given by address (parameter 2) and prefix length (parameter 3).
|
||||
## -
|
||||
ipv6_in_net() {
|
||||
local _a _n _full _rest
|
||||
_a="$(ipv6_expand "$1")" || return 1
|
||||
_n="$(ipv6_expand "$2")" || return 1
|
||||
_full=$(( $3 / 4 ))
|
||||
_rest=$(( $3 % 4 ))
|
||||
|
||||
[[ "${_a:0:_full}" == "${_n:0:_full}" ]] || return 1
|
||||
[[ $_rest -eq 0 ]] && return 0
|
||||
(( (0x${_a:_full:1} >> (4 - _rest)) == (0x${_n:_full:1} >> (4 - _rest)) ))
|
||||
}
|
||||
|
||||
is_number() {
|
||||
|
||||
return $(test ! -z "${1##*[!0-9]*}" > /dev/null 2>&1);
|
||||
|
||||
Reference in New Issue
Block a user