What's new

FlexQoS FlexQoS 1.2.5 - Flexible QoS Enhancement Script for Adaptive QoS

  • SNBForums Code of Conduct

    SNBForums is a community for everyone, no matter what their level of experience.

    Please be tolerant and patient of others, especially newcomers. We are all here to share and learn!

    The rules are simple: Be patient, be nice, be helpful or be gone!

Today, my family and I were streaming a program and I was disappointed to see it was being classified as Web Surfing, despite my custom rule for all traffic from the streaming device to be classified as Streaming.

After some analysis of the Tracked Connections from the device, I determined that the stream was happening over IPv6, so it eluded my IPv4-based iptables rule for the device. Sad.

After reviewing my old notes and posts from the FreshJR thread I was reminded of the difficulty creating iptables rules for local IPv6 addresses because in most cases, the addresses are random and change frequently for privacy. Hence, any iptables rule in FlexQoS that includes a local or remote IPv4 address isn’t applied to IPv6 traffic.

So I’m on a bit of a quest to solve this puzzle. Since we cannot rely on a stable, predictable IPv6 address, we need to figure out what we have to work with. MAC address is the obvious missing link, but not available in the POSTROUTING table.

I found a clever post at OpenWRT that has put me on an interesting track using ipsets. I’m only experimenting with manual commands at this point, but this is the approach I’m pursuing (it’s a work-in-progress so not necessarily efficient or fully thought through yet):
  • We know the local IPv4 address for a device. Derive the MAC address of the IPv4 address.
  • Create a hash:mac ipset to hold the MAC address for up to 1 day (my lease duration). ipset create firestick-mac hash:mac timeout 86400
  • Create an iptables rule to capture the MAC address when the known IPv4 address initiates a new connection anywhere. iptables -t mangle -I PREROUTING -m conntrack --ctstate NEW -s 192.168.50.7 -j SET --add-set firestick-mac src --exist
  • Create a hash:ip ipset for IPv6 address for the device to hold the temporary IPv6 addresses as they change, for up to 1 hour. ipset create firestick hash:ip family inet6 timeout 3600
  • Create an ip6tables rule to capture the local IPv6 address when the MAC address initiates a connection. ip6tables -t mangle -I PREROUTING -m conntrack --ctstate NEW -m set --match-set firestick-mac src -j SET --add-set firestick src --exist
  • As the device initiates connections, the firestick ipset should always contain the most recent IPv6 addresses it has been assigned. Now we can use that firestick ipset in an ip6tables rule to capture my streaming traffic.
  • Create ip6tables rules to mimic the IPv4 rule I setup in the FlexQoS GUI. ip6tables -t mangle -A FlexQoS -o br0 -m set --match-set firestick dst -p tcp -j MARK --set-xmark 0x8004ffff/0xc03fffff ip6tables -t mangle -A FlexQoS -o eth0 -m set --match-set firestick src -p tcp -j MARK --set-xmark 0x4004ffff/0xc03fffff
It remains to be seen if this is workable for every situation involving local IPs. But so far it seems to be capturing the idle phone home traffic that the Amazon Firestick is doing while I type this.
Code:
# ip6tables -t mangle -nvL FlexQoS
Chain FlexQoS (1 references)
pkts bytes target     prot opt in     out     source               destination       
    0     0 MARK       udp      *      br0     ::/0                 ::/0                 multiport dports 500,4500 multiport sports 500,4500 MARK xset 0x8006ffff/0xc03fffff
    0     0 MARK       udp      *      eth0    ::/0                 ::/0                 multiport sports 500,4500 multiport dports 500,4500 MARK xset 0x4006ffff/0xc03fffff
    0     0 MARK       udp      *      br0     ::/0                 ::/0                 multiport sports 3478:3481 mark match 0x80000000/0xc03fffff MARK xset 0x8006ffff/0xc03fffff
    0     0 MARK       udp      *      eth0    ::/0                 ::/0                 multiport dports 3478:3481 mark match 0x40000000/0xc03fffff MARK xset 0x4006ffff/0xc03fffff
   40  4060 MARK       tcp      *      br0     ::/0                 ::/0                 match-set firestick dst MARK xset 0x8004ffff/0xc03fffff
  149 12608 MARK       tcp      *      eth0    ::/0                 ::/0                 match-set firestick src MARK xset 0x4004ffff/0xc03fffff
There’s no reward for keeping this half-baked idea to myself, so I post it for anyone to comment on or test themselves if they follow the logic. FreshJR always said he had some ideas how to solve this, but never elaborated.
Yes I remember the headches with the FreshJR script while running IPV6.

I eventually just disabled IPV6 since the gaming rules would also not apply. Guess it's the same for streaming.

I see your currently testing the possibility of workaround with IPV6....will you include this in a future beta Flex script test or it has to de done manually at this time?

Thanks!
 
Just for sayin i also use ipv6

Also with the flexqos didnt work tge post before i also had the problems at the beginning when i dont enter the right wan paket overhead, after this all worked normal because i saw that you didnt put any in it?
 
is it good to set all the other devices in the bandwith priority tap to verly low when i want to have no ping fluctating and so on while gaming ?
 
Hi @dave14305 , can you please remind me how to mark all traffic from an IP as "Streaming" or whatever I want?
I want to mark my TV's IP as Streaming no matter what traffic is, and a couple of devices mor the same way.

Thanks!!!
 
Hi @dave14305 , can you please remind me how to mark all traffic from an IP as "Streaming" or whatever I want?
I want to mark my TV's IP as Streaming no matter what traffic is, and a couple of devices mor the same way.

Thanks!!!
Create a rule with the device’s Local IP and the Class as Streaming.
 
Create a rule with the device’s Local IP and the Class as Streaming.
With no Mark at all? Like this?

Update: Thanks, didn't thought about adding them without marking
 

Attachments

  • Screenshot_20210828-102501_Chrome.jpg
    Screenshot_20210828-102501_Chrome.jpg
    17.2 KB · Views: 158
Last edited:
Today, my family and I were streaming a program and I was disappointed to see it was being classified as Web Surfing, despite my custom rule for all traffic from the streaming device to be classified as Streaming.

After some analysis of the Tracked Connections from the device, I determined that the stream was happening over IPv6, so it eluded my IPv4-based iptables rule for the device. Sad.

After reviewing my old notes and posts from the FreshJR thread I was reminded of the difficulty creating iptables rules for local IPv6 addresses because in most cases, the addresses are random and change frequently for privacy. Hence, any iptables rule in FlexQoS that includes a local or remote IPv4 address isn’t applied to IPv6 traffic.

So I’m on a bit of a quest to solve this puzzle. Since we cannot rely on a stable, predictable IPv6 address, we need to figure out what we have to work with. MAC address is the obvious missing link, but not available in the POSTROUTING table.

I found a clever post at OpenWRT that has put me on an interesting track using ipsets. I’m only experimenting with manual commands at this point, but this is the approach I’m pursuing (it’s a work-in-progress so not necessarily efficient or fully thought through yet):
  • We know the local IPv4 address for a device. Derive the MAC address of the IPv4 address.
  • Create a hash:mac ipset to hold the MAC address for up to 1 day (my lease duration). ipset create firestick-mac hash:mac timeout 86400
  • Create an iptables rule to capture the MAC address when the known IPv4 address initiates a new connection anywhere. iptables -t mangle -I PREROUTING -m conntrack --ctstate NEW -s 192.168.50.7 -j SET --add-set firestick-mac src --exist
  • Create a hash:ip ipset for IPv6 address for the device to hold the temporary IPv6 addresses as they change, for up to 1 hour. ipset create firestick hash:ip family inet6 timeout 3600
  • Create an ip6tables rule to capture the local IPv6 address when the MAC address initiates a connection. ip6tables -t mangle -I PREROUTING -m conntrack --ctstate NEW -m set --match-set firestick-mac src -j SET --add-set firestick src --exist
  • As the device initiates connections, the firestick ipset should always contain the most recent IPv6 addresses it has been assigned. Now we can use that firestick ipset in an ip6tables rule to capture my streaming traffic.
  • Create ip6tables rules to mimic the IPv4 rule I setup in the FlexQoS GUI. ip6tables -t mangle -A FlexQoS -o br0 -m set --match-set firestick dst -p tcp -j MARK --set-xmark 0x8004ffff/0xc03fffff ip6tables -t mangle -A FlexQoS -o eth0 -m set --match-set firestick src -p tcp -j MARK --set-xmark 0x4004ffff/0xc03fffff
It remains to be seen if this is workable for every situation involving local IPs. But so far it seems to be capturing the idle phone home traffic that the Amazon Firestick is doing while I type this.
Code:
# ip6tables -t mangle -nvL FlexQoS
Chain FlexQoS (1 references)
pkts bytes target     prot opt in     out     source               destination        
    0     0 MARK       udp      *      br0     ::/0                 ::/0                 multiport dports 500,4500 multiport sports 500,4500 MARK xset 0x8006ffff/0xc03fffff
    0     0 MARK       udp      *      eth0    ::/0                 ::/0                 multiport sports 500,4500 multiport dports 500,4500 MARK xset 0x4006ffff/0xc03fffff
    0     0 MARK       udp      *      br0     ::/0                 ::/0                 multiport sports 3478:3481 mark match 0x80000000/0xc03fffff MARK xset 0x8006ffff/0xc03fffff
    0     0 MARK       udp      *      eth0    ::/0                 ::/0                 multiport dports 3478:3481 mark match 0x40000000/0xc03fffff MARK xset 0x4006ffff/0xc03fffff
   40  4060 MARK       tcp      *      br0     ::/0                 ::/0                 match-set firestick dst MARK xset 0x8004ffff/0xc03fffff
  149 12608 MARK       tcp      *      eth0    ::/0                 ::/0                 match-set firestick src MARK xset 0x4004ffff/0xc03fffff
There’s no reward for keeping this half-baked idea to myself, so I post it for anyone to comment on or test themselves if they follow the logic. FreshJR always said he had some ideas how to solve this, but never elaborated.
There's a 1.2.6 beta on the develop channel to see if this works for others using IPv6. It seems to work for me in my initial tests.

If you don't use IPv6, the only other change in this version is a change to classify outbound DNS, DoT and NTP as Net Control. Previously, these bypassed QoS completely.

In case you forgot how, you can switch to the develop branch using flexqos develop

This only works with Local IPs in rules. If an IPv4 Remote IP is also present in the rule, the IPv6 rule support won't work.

I haven't coded in weeks, so this beta could be rough around the edges.
 
@dave14305

I would like to try the beta. I had a couple of questions.

Off course I will 1st enabled IPV6 on the router.

Do I need to do anything on any of my devices specifically for my gaming devices once they get an IPV6 IP?

Do I go to my devices and see what IP (IPV6) they're using to add to current the gaming rule or even for devices that are streaming?

Thanks.
 
@dave14305

I would like to try the beta. I had a couple of questions.

Off course I will 1st enabled IPV6 on the router.

Do I need to do anything on any of my devices specifically for my gaming devices once they get an IPV6 IP?

Do I go to my devices and see what IP (IPV6) they're using to add to current the gaming rule or even for devices that are streaming?

Thanks.
No, there is no need to do anything. FlexQoS will figure out which IPv6 traffic matches the IPv4 IPs or CIDRs in your existing rules. You cannot input IPv6 addresses into the GUI at all.

If you use stateless, native IPv6 like me, the IPv6 addresses will change every 10 minutes, so it’s useless trying to track them directly in a rule.

If your games or applications don’t use IPv6, it won’t be of much benefit. But those that do will no longer be ignored in FlexQoS when using a local IP in your rule.

Edit: my test case is to set a rule for the IPv4 address of my iPad and put any traffic with Mark 04**** into File Transfers. Then I run a speedtest on fast.com which will gladly use IPv6.
 
Last edited:
Awesome job!!! You're a GENIUS :)

Everything seems to be working as it should:

Code:
admin@GT-AX11000-xxxx:/tmp/home/root# ip6tables -t mangle -nvL FlexQoS
Chain FlexQoS (1 references)
pkts bytes target     prot opt in     out     source               destination       
    0     0 MARK       udp      *      br0     ::/0                 ::/0                 multiport sports 500,4500 MARK xset 0x8006ffff/0xc03fffff
    0     0 MARK       udp      *      eth0    ::/0                 ::/0                 multiport dports 500,4500 MARK xset 0x4006ffff/0xc03fffff
    4   658 MARK       udp      *      br0     ::/0                 ::/0                 multiport dports 16384:16415 MARK xset 0x8006ffff/0xc03fffff
    5   479 MARK       udp      *      eth0    ::/0                 ::/0                 multiport sports 16384:16415 MARK xset 0x4006ffff/0xc03fffff
    0     0 MARK       tcp      *      br0     ::/0                 ::/0                 multiport sports 119,563 MARK xset 0x8003ffff/0xc03fffff
    0     0 MARK       tcp      *      eth0    ::/0                 ::/0                 multiport dports 119,563 MARK xset 0x4003ffff/0xc03fffff
    0     0 MARK       tcp      *      br0     ::/0                 ::/0                 multiport sports 80,443 mark match 0x80080000/0xc03f0000 MARK xset 0x8003ffff/0xc03fffff
    0     0 MARK       tcp      *      eth0    ::/0                 ::/0                 multiport dports 80,443 mark match 0x40080000/0xc03f0000 MARK xset 0x4003ffff/0xc03fffff
76481   72M MARK       tcp      *      br0     ::/0                 ::/0                 match-set 192.168.1.100/28 dst multiport sports 80,443 mark match ! 0x80040000/0xc03f0000 MARK xset 0x8004ffff/0xc03fffff
44847 6189K MARK       tcp      *      eth0    ::/0                 ::/0                 match-set 192.168.1.100/28 src multiport dports 80,443 mark match ! 0x40040000/0xc03f0000 MARK xset 0x4004ffff/0xc03fffff
    0     0 MARK       tcp      *      br0     ::/0                 ::/0                 match-set 192.168.1.11 dst multiport sports 80,443 mark match ! 0x80040000/0xc03f0000 MARK xset 0x8004ffff/0xc03fffff
    0     0 MARK       tcp      *      eth0    ::/0                 ::/0                 match-set 192.168.1.11 src multiport dports 80,443 mark match ! 0x40040000/0xc03f0000 MARK xset 0x4004ffff/0xc03fffff
    0     0 MARK       tcp      *      br0     ::/0                 ::/0                 match-set 192.168.1.16/28 dst multiport sports  !80,443 mark match 0x80000000/0xc03fffff MARK xset 0x8008ffff/0xc03fffff
    0     0 MARK       tcp      *      eth0    ::/0                 ::/0                 match-set 192.168.1.16/28 src multiport dports  !80,443 mark match 0x40000000/0xc03fffff MARK xset 0x4008ffff/0xc03fffff
    0     0 MARK       udp      *      br0     ::/0                 ::/0                 match-set 192.168.1.16/28 dst multiport sports  !80,443 mark match 0x80000000/0xc03fffff MARK xset 0x8008ffff/0xc03fffff
    0     0 MARK       udp      *      eth0    ::/0                 ::/0                 match-set 192.168.1.16/28 src multiport dports  !80,443 mark match 0x40000000/0xc03fffff MARK xset 0x4008ffff/0xc03fffff
 
Last edited:
Everything is working 100% for me - my testing is somewhat limited as I notice that all the heavy traffic that needs to be handled properly is IPv4. But I see both being used and everything is great!
Thank you for keeping my home router QoSing like a $1000 machine ;)
 
If you don't use IPv6, the only other change in this version is a change to classify outbound DNS, DoT and NTP as Net Control. Previously, these bypassed QoS completely.

I've been using the beta script without any issues.

I did have a question...

I noticed I see alot more traffic categorize as "DNS" as top priority from certain devices i.e. printer, Alexa, Google Nest mini, certain cell phones, my firestick. I'm assuming this is normal behaviour due to the version change in regards to the proper classification of outbound DNS/DoT and NTP as Net Control, correct?

Other than that, I disabled IPV6 temporarily due to using a full-time VPN which leaks when IPV6 is on, but everything was working flawlessly.
 
Last edited:
I noticed I see alot more traffic categorize as "DNS" as top priority from certain devices i.e. printer, Alexa, Google Nest mini, certain cell phones, my firestick. I'm assuming this is normal behaviour due to the version change in regards to the proper classification of outbound DNS/DoT and NTP as Net Control, correct?
The change in the develop version would not explain more DNS connections from clients starting to appear in the Tracked Connections list. Perhaps if you had disabled DNSFilter and more clients were bypassing the router as DNS, that might explain it. What is the destination IP for those connections?

My recent change for DNS would result in more Net Control traffic in the charts, but not in Tracked Connections.
 
The change in the develop version would not explain more DNS connections from clients starting to appear in the Tracked Connections list. Perhaps if you had disabled DNSFilter and more clients were bypassing the router as DNS, that might explain it. What is the destination IP for those connections?

My recent change for DNS would result in more Net Control traffic in the charts, but not in Tracked Connections.
I do have a static IP address and specific rule on certain devices for either gaming or streaming. DNSFilter has remained on and set to Router.

This is what the FlexQoS traffic is showing....not sure if this would answer the question.

I wonder if it has to do with the Swinson script and using a fulltime VPN that's reflecting this info. It's only for port 53.
Screenshot_20210910-154225_Samsung Internet.jpg
 
Last edited:
I do have a static IP address and specific rule on certain devices for either gaming or streaming. DNSFilter has remained on and set to Router.

This is what the FlexQoS traffic is showing....not sure if this would answer the question.

I wonder if it has to do with the Swinson script and using a fulltime VPN that's reflecting this info. It's only for port 53.
View attachment 36217
What is 10.200.0.1 in your setup?
 
What is 10.200.0.1 in your setup?
Thanks for the assist.

I think this might be the cause due to my setup with a VPN and running Unbound.

I'm using unbound and have enabled it to run with a VPN and swinson script below:

Code:
E:Option ==> ?

    Version=3.22                    (Change Log: https://github.com/MartineauUK/Unbound-Asuswrt-Merlin/commits/master/unbound_manager.sh)
    Local                        md5=6b4a500c071bcbb3f4a6e9596a178d43
    Github                        md5=6b4a500c071bcbb3f4a6e9596a178d43
    /jffs/addons/unbound/unbound_manager.md5    md5=6b4a500c071bcbb3f4a6e9596a178d43

    Router Configuration recommended pre-reqs status:

    [✔] Swapfile=2097148 kB
    [✔] DNS Filter=ON
    [✔] DNS Filter=ROUTER
    [✔] WAN: Use local caching DNS server as system resolver=NO
    [✔] Enable local NTP server=YES
    [✔] Enable DNS Rebind protection=NO
    [✔] Enable DNSSEC support=NO

    Options:

    [✔] unbound CPU/Memory Performance tweaks
    [✔] Firefox DNS-over-HTTPS (DoH) DISABLE/Blocker
    [✔] Router Graphical GUI statistics TAB installed
    [✔] unbound-control FAST response ENABLED
    [✔] unbound requests via VPN Client 1 (10.200.0.26) tunnel ENABLED

At the same time, I'm using the Swinson script which allows DNS packets appear to originate off in VPN host provider and not the WAN ISP host provider. The router should resolve through the DNS provided in the WAN settings & everything else should resolve through unbound with your VPNs IP.

So when running an ipleak test and/or dnsleaktest, everything shows from the VPN IP versus the WAN IP.

This is the code within the script:

Code:
#!/bin/sh
Check_Tun11_Con() {
ping -c1 -w1 -I tun11 9.9.9.9
}
Delete_Rules() {
iptables-save | grep "unbound_rule" | sed 's/^-A/iptables -t mangle -D/' | while read CMD;do $CMD;done
}
Add_Rules(){
Delete_Rules
iptables -t mangle -A OUTPUT -d "${wan0_dns##*.*.*.* }"/32 -p udp --dport 53 -m comment --comment unbound_rule -j MARK --set-mark 0x8000/0x8000
iptables -t mangle -A OUTPUT -d "${wan0_dns%% *.*.*.*}"/32 -p udp --dport 53 -m comment --comment unbound_rule -j MARK --set-mark 0x8000/0x8000
iptables -t mangle -A OUTPUT -d "${wan0_dns##*.*.*.* }"/32 -p tcp --dport 53 -m comment --comment unbound_rule -j MARK --set-mark 0x8000/0x8000
iptables -t mangle -A OUTPUT -d "${wan0_dns%% *.*.*.*}"/32 -p tcp --dport 53 -m comment --comment unbound_rule -j MARK --set-mark 0x8000/0x8000
iptables -t mangle -A OUTPUT -p tcp --dport 53 -m comment --comment unbound_rule -j MARK --set-mark 0x1000/0x1000
iptables -t mangle -A OUTPUT -p udp --dport 53 -m comment --comment unbound_rule -j MARK --set-mark 0x1000/0x1000
}
Call_unbound_manager() {
/jffs/addons/unbound/unbound_manager.sh vpn="$1"
}
Poll_Tun11() {
timer=$1
[ -z $timer ] && Post_log "Error Timeout" && exit 1 || sleep 2
Check_Tun11_Con && Add_Rules && Call_unbound_manager "1" || Poll_Tun11 "$((timer--))"
}
Post_log() {
$(logger -st "($(basename "$0"))" $$ "$1")
}
[ -z "$1" ] && Post_log "Script Arg Missing" && exit 1 || Post_log "Starting Script Execution"
wan0_dns="$(nvram get wan0_dns)"
Delete_Rules
case "$1" in
start)
Poll_Tun11 "150" && Post_log "Ending Script Execution" && exit 0;;
stop)
Call_unbound_manager "disable" && Post_log "Ending Script Execution" && exit 0;;
*)
Post_log "Script Arg Invalid" && exit 1;;
esac

I believe the code is putting all VPN traffic as DNS (port 53) but I'm not sure if I can resolved that or if I should. Thanks again!
 
Last edited:

Support SNBForums w/ Amazon

If you'd like to support SNBForums, just use this link and buy anything on Amazon. Thanks!

Sign Up For SNBForums Daily Digest

Get an update of what's new every day delivered to your mailbox. Sign up here!
Top