mirror of
https://github.com/openwrt/packages.git
synced 2025-12-10 12:41:22 +00:00
@@ -5,7 +5,7 @@ include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=pbr
|
||||
PKG_VERSION:=1.2.0
|
||||
PKG_RELEASE:=2
|
||||
PKG_RELEASE:=6
|
||||
PKG_LICENSE:=AGPL-3.0-or-later
|
||||
PKG_MAINTAINER:=Stan Grishin <stangri@melmac.ca>
|
||||
|
||||
|
||||
@@ -286,10 +286,11 @@ is_supported_protocol(){ grep -qi "^${1:--}" /etc/protocols;}
|
||||
is_pptp() { local p; network_get_protocol p "$1"; [ "${p:0:4}" = "pptp" ]; }
|
||||
is_softether() { local d; network_get_device d "$1"; [ "${d:0:4}" = "vpn_" ]; }
|
||||
is_supported_interface() { { is_lan "$1" || is_disabled_interface "$1"; } && return 1; str_contains_word "$supported_interface" "$1" || { ! is_ignored_interface "$1" && { is_wan "$1" || is_wan6 "$1" || is_tunnel "$1"; }; } || is_ignore_target "$1" || is_xray "$1"; }
|
||||
is_netbird() { local d; network_get_device d "$1"; [ "${d:0:2}" = "wt" ]; }
|
||||
is_tailscale() { local d; network_get_device d "$1"; [ "${d:0:9}" = "tailscale" ]; }
|
||||
is_tor() { [ "$(str_to_lower "$1")" = "tor" ]; }
|
||||
is_tor_running() { ! is_ignored_interface 'tor' && [ -s "$torConfigFile" ] && str_contains "$(ubus call service list "{ 'name': 'tor' }" | jsonfilter -e '@.tor.instances.*.running')" 'true' && return 0 || return 1; }
|
||||
is_tunnel() { is_dslite "$1" || is_l2tp "$1" || is_oc "$1" || is_ovpn "$1" || is_pptp "$1" || is_softether "$1" || is_tailscale "$1" || is_tor "$1" || is_wg "$1"; }
|
||||
is_tunnel() { is_dslite "$1" || is_l2tp "$1" || is_oc "$1" || is_ovpn "$1" || is_pptp "$1" || is_softether "$1" || is_netbird "$1" || is_tailscale "$1" || is_tor "$1" || is_wg "$1"; }
|
||||
is_url() { is_url_file "$1" || is_url_dl "$1"; }
|
||||
is_url_dl() { is_url_ftp "$1" || is_url_http "$1" || is_url_https "$1"; }
|
||||
is_url_file() { [ "$1" != "${1#file://}" ]; }
|
||||
|
||||
@@ -1,87 +1,106 @@
|
||||
#!/bin/sh
|
||||
# When using pbr with dnsmasq's nft set support, a domain-based policy will not take effect until
|
||||
# the remote domain name has been resolved by dnsmasq. Resolve all domain names in pbr policies in advance.
|
||||
# shellcheck disable=SC3043
|
||||
|
||||
(
|
||||
timeout_nft='10'
|
||||
timeout_dnsmasq='20'
|
||||
pipe_ubus="/tmp/pipe.ubus.$$"
|
||||
pipe_nslookup="/tmp/pipe.nslookup.$$"
|
||||
log_abort='domain names in policies not resolved'
|
||||
pipe_nslookup="/var/run/${packageName}.nslookup.$$"
|
||||
|
||||
# shellcheck disable=SC2154
|
||||
output()
|
||||
{
|
||||
msg="$*"
|
||||
msg=$(printf '%b' "$msg" | sed 's/\x1b\[[0-9;]*m//g')
|
||||
output() {
|
||||
local msg="$*"
|
||||
|
||||
msg="$(printf '%b' "$msg" | sed 's/\x1b\[[0-9;]*m//g')"
|
||||
# shellcheck disable=SC2154
|
||||
logger -t "$packageName [$$]" "$(printf '%b' "$msg")"
|
||||
}
|
||||
|
||||
nft_ready()
|
||||
{
|
||||
nft_ready() {
|
||||
local timeout_nft='10'
|
||||
|
||||
while ! /usr/sbin/nft list sets 'inet' | grep -q "pbr"; do
|
||||
[ "$timeout_nft" -eq '0' ] && {
|
||||
output "Pbr's nft sets not found, $log_abort $__FAIL__"
|
||||
return 1
|
||||
}
|
||||
sleep '1' && timeout_nft=$((timeout_nft - 1))
|
||||
sleep '1' && timeout_nft="$((timeout_nft - 1))"
|
||||
done
|
||||
}
|
||||
|
||||
run_nslookup()
|
||||
{
|
||||
output=$(nslookup "$1" 127.0.0.1) && { echo '0' > "$pipe_nslookup"; return; }
|
||||
reason=$(printf '%s' "$output" | grep -Eo -m 1 'NXDOMAIN|SERVFAIL|timed out') && \
|
||||
run_nslookup() {
|
||||
local output reason
|
||||
|
||||
output="$(nslookup "$1" 127.0.0.1)" && { echo '0' > "$pipe_nslookup"; return; }
|
||||
reason="$(printf '%s' "$output" | grep -Eo -m 1 'NXDOMAIN|SERVFAIL|timed out')" && \
|
||||
output "$_WARNING_ Lookup failed for $domain ($reason)"
|
||||
echo '1' > "$pipe_nslookup"
|
||||
}
|
||||
|
||||
# shellcheck disable=SC2162
|
||||
nslookup_tracker()
|
||||
{
|
||||
while read ec; do
|
||||
entries=$((entries + 1))
|
||||
[ "$ec" -eq '1' ] && errors=$((errors + 1))
|
||||
nslookup_tracker() {
|
||||
local entries errors
|
||||
|
||||
while read -r rc; do
|
||||
entries="$((entries + 1))"
|
||||
[ "$rc" -eq '1' ] && errors="$((errors + 1))"
|
||||
done < "$pipe_nslookup"
|
||||
|
||||
output "Finished resolving $entries domain names in policies (${errors:-0} failed) $__OK__"
|
||||
}
|
||||
|
||||
[ -n "$resolverSetSupported" ] || {
|
||||
output "Resolver set support disabled, $log_abort $__FAIL__"
|
||||
exit
|
||||
}
|
||||
mkfifo "$pipe_ubus"
|
||||
mkfifo "$pipe_nslookup"
|
||||
ubus listen -m 'ubus.object.add' > "$pipe_ubus" & ubus_listen_pid=$!
|
||||
main() {
|
||||
local pipe_ubus="/var/run/${packageName}.ubus.$$"
|
||||
local timeout_dnsmasq='20'
|
||||
local msg_abort='domain names in policies not resolved'
|
||||
local dnsmasq_restarted ubus_listen_pid event domain entries
|
||||
local rc='0'
|
||||
|
||||
# shellcheck disable=SC3045
|
||||
while read -t "$timeout_dnsmasq" -r event; do
|
||||
echo "$event" | grep -q "dnsmasq.dns" || continue
|
||||
dnsmasq_restarted='1'
|
||||
# shellcheck disable=SC2154
|
||||
[ -f "$packageDnsmasqFile" ] || {
|
||||
output "File $packageDnsmasqFile not found, $log_abort $__FAIL__"
|
||||
break
|
||||
[ -n "$resolverSetSupported" ] || {
|
||||
output "Resolver set support disabled, $msg_abort $__FAIL__"
|
||||
rc='1'
|
||||
return "$rc"
|
||||
}
|
||||
nft_ready || break
|
||||
nslookup_tracker & exec 3>"$pipe_nslookup"
|
||||
mkfifo "$pipe_ubus"
|
||||
mkfifo "$pipe_nslookup"
|
||||
# The subshell may be necessary for "$!" to expand to a correct value
|
||||
( exec ubus listen -m 'ubus.object.add' > "$pipe_ubus" ) &
|
||||
ubus_listen_pid="$!"
|
||||
|
||||
(
|
||||
output "Resolving domain names in policies..."
|
||||
while IFS='/' read -r _ domain _; do
|
||||
[ -n "$domain" ] && run_nslookup "$domain" &
|
||||
entries=$((entries + 1))
|
||||
done < "$packageDnsmasqFile"
|
||||
wait
|
||||
)
|
||||
# shellcheck disable=SC3045
|
||||
while read -t "$timeout_dnsmasq" -r event; do
|
||||
echo "$event" | grep -q "dnsmasq.dns" || continue
|
||||
dnsmasq_restarted='1'
|
||||
# shellcheck disable=SC2154
|
||||
[ -f "$packageDnsmasqFile" ] || {
|
||||
output "File $packageDnsmasqFile not found, $msg_abort $__FAIL__"
|
||||
rc='1'
|
||||
break
|
||||
}
|
||||
nft_ready || {
|
||||
output "Pbr's nft sets not found, $msg_abort $__FAIL__"
|
||||
rc='1'
|
||||
break
|
||||
}
|
||||
nslookup_tracker & exec 3>"$pipe_nslookup"
|
||||
(
|
||||
output "Resolving domain names in policies..."
|
||||
while IFS='/' read -r _ domain _; do
|
||||
[ -n "$domain" ] && run_nslookup "$domain" &
|
||||
entries="$((entries + 1))"
|
||||
done < "$packageDnsmasqFile"
|
||||
wait
|
||||
)
|
||||
exec 3>&-
|
||||
break
|
||||
done < "$pipe_ubus"
|
||||
|
||||
exec 3>&-
|
||||
break
|
||||
done < "$pipe_ubus"
|
||||
|
||||
[ -n "$dnsmasq_restarted" ] || output "Dnsmasq hasn't restarted, $log_abort $__FAIL__"
|
||||
kill "$ubus_listen_pid"
|
||||
rm "$pipe_ubus"
|
||||
rm "$pipe_nslookup"
|
||||
[ -n "$dnsmasq_restarted" ] || {
|
||||
output "Dnsmasq hasn't restarted, $msg_abort $__FAIL__"
|
||||
rc='1'
|
||||
}
|
||||
kill "$ubus_listen_pid"
|
||||
rm -f "$pipe_ubus"
|
||||
rm -f "$pipe_nslookup"
|
||||
return "$rc"
|
||||
}
|
||||
|
||||
main
|
||||
return "$?"
|
||||
) &
|
||||
|
||||
Reference in New Issue
Block a user