|
|
@ -143,6 +143,10 @@ IPT_DEL() |
|
|
|
{ |
|
|
|
$IPTABLES -C "$@" >/dev/null 2>/dev/null && $IPTABLES -D "$@" |
|
|
|
} |
|
|
|
IPT_ADD_DEL() |
|
|
|
{ |
|
|
|
on_off_function IPT IPT_DEL "$@" |
|
|
|
} |
|
|
|
IPFW_ADD() |
|
|
|
{ |
|
|
|
ipfw -qf add $IPFW_RULE_NUM "$@" |
|
|
@ -199,7 +203,6 @@ check_system() |
|
|
|
Linux) |
|
|
|
PKTWS="$NFQWS" |
|
|
|
PKTWSD=nfqws |
|
|
|
LO_IFACE=lo |
|
|
|
linux_fwtype |
|
|
|
[ "$FWTYPE" = iptables -o "$FWTYPE" = nftables ] || { |
|
|
|
echo firewall type $FWTYPE not supported in $UNAME |
|
|
@ -210,20 +213,17 @@ check_system() |
|
|
|
PKTWS="$DVTWS" |
|
|
|
PKTWSD=dvtws |
|
|
|
FWTYPE=ipfw |
|
|
|
LO_IFACE=lo0 |
|
|
|
[ -f /etc/platform ] && read SUBSYS </etc/platform |
|
|
|
;; |
|
|
|
OpenBSD) |
|
|
|
PKTWS="$DVTWS" |
|
|
|
PKTWSD=dvtws |
|
|
|
FWTYPE=opf |
|
|
|
LO_IFACE=lo0 |
|
|
|
;; |
|
|
|
Darwin) |
|
|
|
PKTWS="$DVTWS" |
|
|
|
PKTWSD=dvtws |
|
|
|
FWTYPE=mpf |
|
|
|
LO_IFACE=lo0 |
|
|
|
;; |
|
|
|
*) |
|
|
|
echo $UNAME not supported |
|
|
@ -497,76 +497,70 @@ curl_test_http3() |
|
|
|
curl_with_dig $1 $2 -ISs -A "$USER_AGENT" --max-time $CURL_MAX_TIME --http3-only $CURL_OPT "https://$2" -o /dev/null 2>&1 |
|
|
|
} |
|
|
|
|
|
|
|
pktws_ipt_prepare_tcp() |
|
|
|
ipt_scheme() |
|
|
|
{ |
|
|
|
# $1 - port |
|
|
|
# $1 - 1 - add , 0 - del |
|
|
|
# $2 - tcp/udp |
|
|
|
# $3 - port |
|
|
|
|
|
|
|
IPT_ADD_DEL $1 OUTPUT -t mangle -p $2 --dport $3 -m mark ! --mark $DESYNC_MARK/$DESYNC_MARK -j NFQUEUE --queue-num $QNUM |
|
|
|
# to avoid possible INVALID state drop |
|
|
|
[ "$2" = tcp ] && IPT_ADD_DEL $1 INPUT -p $2 --sport $3 ! --syn -j ACCEPT |
|
|
|
# for strategies with incoming packets involved (autottl) |
|
|
|
IPT_ADD_DEL $1 OUTPUT -p $2 --dport $3 -m conntrack --ctstate INVALID -j ACCEPT |
|
|
|
if [ "$IPV" = 6 -a -n "$IP6_DEFRAG_DISABLE" ]; then |
|
|
|
# the only way to reliable disable ipv6 defrag. works only in 4.16+ kernels |
|
|
|
IPT_ADD_DEL $1 OUTPUT -t raw -p $2 -m frag -j CT --notrack |
|
|
|
elif [ "$IPV" = 4 ]; then |
|
|
|
# enable fragments |
|
|
|
IPT_ADD_DEL $1 OUTPUT -f -j ACCEPT |
|
|
|
fi |
|
|
|
# enable everything generated by nfqws (works only in OUTPUT, not in FORWARD) |
|
|
|
# raw table may not be present |
|
|
|
IPT_ADD_DEL $1 OUTPUT -t raw -m mark --mark $DESYNC_MARK/$DESYNC_MARK -j CT --notrack |
|
|
|
} |
|
|
|
nft_scheme() |
|
|
|
{ |
|
|
|
# $1 - tcp/udp |
|
|
|
# $2 - port |
|
|
|
nft add table inet $NFT_TABLE |
|
|
|
nft "add chain inet $NFT_TABLE postnat { type filter hook output priority 102; }" |
|
|
|
nft "add rule inet $NFT_TABLE postnat meta nfproto ipv${IPV} $1 dport $2 mark and $DESYNC_MARK != $DESYNC_MARK queue num $QNUM" |
|
|
|
# for strategies with incoming packets involved (autottl) |
|
|
|
nft "add chain inet $NFT_TABLE prenat { type filter hook prerouting priority -102; }" |
|
|
|
# enable everything generated by nfqws (works only in OUTPUT, not in FORWARD) |
|
|
|
nft "add chain inet $NFT_TABLE predefrag { type filter hook output priority -402; }" |
|
|
|
nft "add rule inet $NFT_TABLE predefrag meta nfproto ipv${IPV} mark and $DESYNC_MARK !=0 notrack" |
|
|
|
} |
|
|
|
|
|
|
|
pktws_ipt_prepare() |
|
|
|
{ |
|
|
|
# $1 - tcp/udp |
|
|
|
# $2 - port |
|
|
|
case "$FWTYPE" in |
|
|
|
iptables) |
|
|
|
# to avoid possible INVALID state drop |
|
|
|
IPT INPUT -p tcp --sport $1 ! --syn -j ACCEPT |
|
|
|
IPT OUTPUT -p tcp --dport $1 -m conntrack --ctstate INVALID -j ACCEPT |
|
|
|
if [ "$IPV" = 6 -a -n "$IP6_DEFRAG_DISABLE" ]; then |
|
|
|
# the only way to reliable disable ipv6 defrag. works only in 4.16+ kernels |
|
|
|
IPT OUTPUT -t raw -p tcp -m frag -j CT --notrack |
|
|
|
elif [ "$IPV" = 4 ]; then |
|
|
|
# enable fragments |
|
|
|
IPT OUTPUT -f -j ACCEPT |
|
|
|
fi |
|
|
|
IPT OUTPUT -t mangle -p tcp --dport $1 -m mark ! --mark $DESYNC_MARK/$DESYNC_MARK -j NFQUEUE --queue-num $QNUM |
|
|
|
IPT INPUT -t mangle -p tcp --sport $1 -m connbytes --connbytes-dir=original --connbytes-mode=packets --connbytes 1:1 -j NFQUEUE --queue-num $QNUM |
|
|
|
# enable everything generated by nfqws (works only in OUTPUT, not in FORWARD) |
|
|
|
# raw table may not be present |
|
|
|
IPT OUTPUT -t raw -m mark --mark $DESYNC_MARK/$DESYNC_MARK -j CT --notrack |
|
|
|
ipt_scheme 1 $1 $2 |
|
|
|
;; |
|
|
|
nftables) |
|
|
|
nft add table inet $NFT_TABLE |
|
|
|
# prenat |
|
|
|
# [ "$IPV" = 6 -a -n "$IP6_DEFRAG_DISABLE" ] && { |
|
|
|
# nft "add chain inet $NFT_TABLE predefrag { type filter hook output priority -402; }" |
|
|
|
# nft "add rule inet $NFT_TABLE predefrag meta nfproto ipv${IPV} exthdr frag exists notrack" |
|
|
|
# } |
|
|
|
# nft "add chain inet $NFT_TABLE premangle { type filter hook output priority -152; }" |
|
|
|
# nft "add rule inet $NFT_TABLE premangle meta nfproto ipv${IPV} tcp dport $1 mark and 0x40000000 != 0x40000000 queue num $QNUM" |
|
|
|
# postnat. this is good because we need only output traffic |
|
|
|
nft "add chain inet $NFT_TABLE postnat { type filter hook output priority 102; }" |
|
|
|
nft "add rule inet $NFT_TABLE postnat meta nfproto ipv${IPV} tcp dport $1 mark and 0x40000000 != 0x40000000 queue num $QNUM" |
|
|
|
# for strategies with incoming packets involved (autottl) |
|
|
|
nft "add chain inet $NFT_TABLE prenat { type filter hook prerouting priority -102; }" |
|
|
|
nft "add rule inet $NFT_TABLE prenat meta nfproto ipv${IPV} tcp sport $1 ct original packets 1 queue num $QNUM" |
|
|
|
# enable everything generated by nfqws (works only in OUTPUT, not in FORWARD) |
|
|
|
nft "add chain inet $NFT_TABLE predefrag { type filter hook output priority -402; }" |
|
|
|
nft "add rule inet $NFT_TABLE predefrag meta nfproto ipv${IPV} mark and $DESYNC_MARK !=0 notrack" |
|
|
|
nft_scheme $1 $2 |
|
|
|
;; |
|
|
|
ipfw) |
|
|
|
# disable PF to avoid interferences |
|
|
|
pf_is_avail && pfctl -qd |
|
|
|
|
|
|
|
IPFW_ADD divert $IPFW_DIVERT_PORT tcp from me to any $1 proto ip${IPV} out not diverted not sockarg |
|
|
|
# for autottl mode |
|
|
|
IPFW_ADD divert $IPFW_DIVERT_PORT tcp from any $1 to me proto ip${IPV} tcpflags syn,ack in not diverted not sockarg |
|
|
|
IPFW_ADD divert $IPFW_DIVERT_PORT $1 from me to any $2 proto ip${IPV} out not diverted not sockarg |
|
|
|
;; |
|
|
|
opf) |
|
|
|
opf_prepare_dvtws tcp $1 |
|
|
|
opf_prepare_dvtws $1 $2 |
|
|
|
;; |
|
|
|
esac |
|
|
|
} |
|
|
|
pktws_ipt_unprepare_tcp() |
|
|
|
pktws_ipt_unprepare() |
|
|
|
{ |
|
|
|
# $1 - port |
|
|
|
# $1 - tcp/udp |
|
|
|
# $2 - port |
|
|
|
case "$FWTYPE" in |
|
|
|
iptables) |
|
|
|
IPT_DEL OUTPUT -t mangle -p tcp --dport $1 -m mark ! --mark $DESYNC_MARK/$DESYNC_MARK -j NFQUEUE --queue-num $QNUM |
|
|
|
IPT_DEL INPUT -t mangle -p tcp --sport $1 -m connbytes --connbytes-dir=original --connbytes-mode=packets --connbytes 1:1 -j NFQUEUE --queue-num $QNUM |
|
|
|
|
|
|
|
IPT_DEL INPUT -p tcp --sport $1 ! --syn -j ACCEPT |
|
|
|
IPT_DEL OUTPUT -p tcp --dport $1 -m conntrack --ctstate INVALID -j ACCEPT |
|
|
|
if [ "$IPV" = 6 -a -n "$IP6_DEFRAG_DISABLE" ]; then |
|
|
|
IPT_DEL OUTPUT -t raw -p tcp -m frag -j CT --notrack |
|
|
|
elif [ "$IPV" = 4 ]; then |
|
|
|
IPT_DEL OUTPUT -f -j ACCEPT |
|
|
|
fi |
|
|
|
# raw table may not be present |
|
|
|
IPT_DEL OUTPUT -t raw -m mark --mark $DESYNC_MARK/$DESYNC_MARK -j CT --notrack |
|
|
|
ipt_scheme 0 $1 $2 |
|
|
|
;; |
|
|
|
nftables) |
|
|
|
nft delete table inet $NFT_TABLE 2>/dev/null |
|
|
@ -580,48 +574,52 @@ pktws_ipt_unprepare_tcp() |
|
|
|
;; |
|
|
|
esac |
|
|
|
} |
|
|
|
pktws_ipt_prepare_udp() |
|
|
|
|
|
|
|
pktws_ipt_prepare_tcp() |
|
|
|
{ |
|
|
|
# $1 - port |
|
|
|
|
|
|
|
pktws_ipt_prepare tcp $1 |
|
|
|
|
|
|
|
case "$FWTYPE" in |
|
|
|
iptables) |
|
|
|
IPT OUTPUT -t mangle -p udp --dport $1 -m mark ! --mark $DESYNC_MARK/$DESYNC_MARK -j NFQUEUE --queue-num $QNUM |
|
|
|
# for autottl |
|
|
|
IPT INPUT -t mangle -p tcp --sport $1 -m connbytes --connbytes-dir=original --connbytes-mode=packets --connbytes 1:1 -j NFQUEUE --queue-num $QNUM |
|
|
|
;; |
|
|
|
nftables) |
|
|
|
nft add table inet $NFT_TABLE |
|
|
|
nft "add chain inet $NFT_TABLE premangle { type filter hook output priority -152; }" |
|
|
|
nft "add rule inet $NFT_TABLE premangle meta nfproto ipv${IPV} udp dport $1 mark and 0x40000000 != 0x40000000 queue num $QNUM" |
|
|
|
# for autottl |
|
|
|
nft "add rule inet $NFT_TABLE prenat meta nfproto ipv${IPV} tcp sport $1 ct original packets 1 queue num $QNUM" |
|
|
|
;; |
|
|
|
ipfw) |
|
|
|
# disable PF to avoid interferences |
|
|
|
pf_is_avail && pfctl -qd |
|
|
|
|
|
|
|
IPFW_ADD divert $IPFW_DIVERT_PORT udp from me to any $1 proto ip${IPV} out not diverted not sockarg |
|
|
|
;; |
|
|
|
opf) |
|
|
|
opf_prepare_dvtws udp $1 |
|
|
|
# for autottl mode |
|
|
|
IPFW_ADD divert $IPFW_DIVERT_PORT tcp from any $1 to me proto ip${IPV} tcpflags syn,ack in not diverted not sockarg |
|
|
|
;; |
|
|
|
esac |
|
|
|
} |
|
|
|
pktws_ipt_unprepare_udp() |
|
|
|
pktws_ipt_unprepare_tcp() |
|
|
|
{ |
|
|
|
# $1 - port |
|
|
|
|
|
|
|
pktws_ipt_unprepare tcp $1 |
|
|
|
|
|
|
|
case "$FWTYPE" in |
|
|
|
iptables) |
|
|
|
IPT_DEL OUTPUT -t mangle -p udp --dport $1 -m mark ! --mark $DESYNC_MARK/$DESYNC_MARK -j NFQUEUE --queue-num $QNUM |
|
|
|
;; |
|
|
|
nftables) |
|
|
|
nft delete table inet $NFT_TABLE 2>/dev/null |
|
|
|
;; |
|
|
|
ipfw) |
|
|
|
IPFW_DEL |
|
|
|
pf_is_avail && pf_restore |
|
|
|
;; |
|
|
|
opf) |
|
|
|
pf_restore |
|
|
|
IPT_DEL INPUT -t mangle -p tcp --sport $1 -m connbytes --connbytes-dir=original --connbytes-mode=packets --connbytes 1:1 -j NFQUEUE --queue-num $QNUM |
|
|
|
;; |
|
|
|
esac |
|
|
|
} |
|
|
|
pktws_ipt_prepare_udp() |
|
|
|
{ |
|
|
|
# $1 - port |
|
|
|
|
|
|
|
pktws_ipt_prepare udp $1 |
|
|
|
} |
|
|
|
pktws_ipt_unprepare_udp() |
|
|
|
{ |
|
|
|
# $1 - port |
|
|
|
|
|
|
|
pktws_ipt_unprepare udp $1 |
|
|
|
} |
|
|
|
|
|
|
|
pktws_start() |
|
|
|
{ |
|
|
@ -882,13 +880,23 @@ pktws_check_domain_http3_bypass() |
|
|
|
local f desync frag tests |
|
|
|
|
|
|
|
pktws_curl_test_update $1 $2 --dpi-desync=fake |
|
|
|
|
|
|
|
|
|
|
|
[ "$IPV" = 6 ] && { |
|
|
|
f="hopbyhop destopt" |
|
|
|
[ -n "$IP6_DEFRAG_DISABLE" ] && f="$f ipfrag1" |
|
|
|
for desync in $f; do |
|
|
|
pktws_curl_test_update $1 $2 --dpi-desync=$desync |
|
|
|
done |
|
|
|
} |
|
|
|
[ "$IPV" = 4 -o -n "$IP6_DEFRAG_DISABLE" ] && { |
|
|
|
for frag in 8 16 24 32 40 64; do |
|
|
|
tests="ipfrag2" |
|
|
|
[ "$IPV" = 6 ] && tests="$tests hopbyhop,ipfrag2 destopt,ipfrag2" |
|
|
|
for desync in $tests; do |
|
|
|
pktws_curl_test_update $1 $2 --dpi-desync=$desync --dpi-desync-ipfrag-pos-udp=$frag |
|
|
|
done |
|
|
|
done |
|
|
|
} |
|
|
|
|
|
|
|
report_strategy $1 $2 $PKTWSD |
|
|
|
} |
|
|
|