What's new

Selective Routing with Asuswrt-Merlin

  • 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!

By default using this version of the selective routing script nothing goes via the VPN unless explicitly defined.

So if you were to remove ALL three of the tagging rules this this should be the case...if it isn't then you will need to look at the log to see if there are any errors.

However

iptables -t mangle -A PREROUTING -i br0 -m iprange --src-range 10.10.1.100 -j MARK 0

shouldn't this be in the same format as the two rules below?

i.e.

iptables -t mangle -A PREROUTING -i br0 -m iprange --src-range 10.10.1.100 -j MARK --set-mark 0

although it should be tagged to the WAN by default anyway.

I suggest you dump the tables/rules using

ip rule

iptables -t mangle -L -nv --line

ip route show table 101

Ok so i'm doing something totally wrong because all my traffic is going out to the VPN.

EDIT: ok made that correction you pointed out. updating the info below with the new stuff.

here are the ip rules, tables and routes...
Code:
dubwize@RouteBox:/jffs/scripts# ip rule
0:      from all lookup local
32765:  from all fwmark 0x1 lookup 101
32766:  from all lookup main
32767:  from all lookup default

dubwize@RouteBox:/jffs/scripts# iptables -t mangle -L -nv --line
Chain PREROUTING (policy ACCEPT 3662 packets, 2253K bytes)
num   pkts bytes target     prot opt in     out     source               destination
1      308 43136 MARK       all  --  br0    *       0.0.0.0/0            0.0.0.0/0            source IP range 10.10.1.100-10.10.1.100 MARK and 0x0
2        2   690 MARK       all  --  br0    *       0.0.0.0/0            0.0.0.0/0            source IP range 10.10.1.2-10.10.1.99 MARK set 0x1
3      738 66478 MARK       all  --  br0    *       0.0.0.0/0            0.0.0.0/0            source IP range 10.10.1.101-10.10.1.254 MARK set 0x1

Chain INPUT (policy ACCEPT 1545 packets, 1136K bytes)
num   pkts bytes target     prot opt in     out     source               destination

Chain FORWARD (policy ACCEPT 2047 packets, 1107K bytes)
num   pkts bytes target     prot opt in     out     source               destination

Chain OUTPUT (policy ACCEPT 1138 packets, 231K bytes)
num   pkts bytes target     prot opt in     out     source               destination

Chain POSTROUTING (policy ACCEPT 3188 packets, 1338K bytes)
num   pkts bytes target     prot opt in     out     source               destination

dubwize@RouteBox:/jffs/scripts# ip route show table 101
default via 10.149.1.6 dev tun11


these are the only errors in my log that i can find, and these are normal afaik.
Code:
Mar  4 19:42:00 openvpn[2821]: Options error: option 'redirect-gateway' cannot be used in this context ([PUSH-OPTIONS])
Mar  4 19:42:00 openvpn[2821]: Options error: option 'dhcp-option' cannot be used in this context ([PUSH-OPTIONS])
Mar  4 19:42:00 openvpn[2821]: Options error: option 'dhcp-option' cannot be used in this context ([PUSH-OPTIONS])
Mar  4 19:42:00 openvpn[2821]: Options error: option 'route' cannot be used in this context ([PUSH-OPTIONS])
 
Last edited:
Ok so i'm doing something totally wrong because all my traffic is going out to the VPN.

EDIT: ok made that correction you pointed out. updating the info below with the new stuff.

here are the ip rules, tables and routes...
Code:
dubwize@RouteBox:/jffs/scripts# ip rule
0:      from all lookup local
32765:  from all fwmark 0x1 lookup 101
32766:  from all lookup main
32767:  from all lookup default

dubwize@RouteBox:/jffs/scripts# iptables -t mangle -L -nv --line
Chain PREROUTING (policy ACCEPT 3662 packets, 2253K bytes)
num   pkts bytes target     prot opt in     out     source               destination
1      308 43136 MARK       all  --  br0    *       0.0.0.0/0            0.0.0.0/0            source IP range 10.10.1.100-10.10.1.100 MARK and 0x0
2        2   690 MARK       all  --  br0    *       0.0.0.0/0            0.0.0.0/0            source IP range 10.10.1.2-10.10.1.99 MARK set 0x1
3      738 66478 MARK       all  --  br0    *       0.0.0.0/0            0.0.0.0/0            source IP range 10.10.1.101-10.10.1.254 MARK set 0x1

Chain INPUT (policy ACCEPT 1545 packets, 1136K bytes)
num   pkts bytes target     prot opt in     out     source               destination

Chain FORWARD (policy ACCEPT 2047 packets, 1107K bytes)
num   pkts bytes target     prot opt in     out     source               destination

Chain OUTPUT (policy ACCEPT 1138 packets, 231K bytes)
num   pkts bytes target     prot opt in     out     source               destination

Chain POSTROUTING (policy ACCEPT 3188 packets, 1338K bytes)
num   pkts bytes target     prot opt in     out     source               destination

dubwize@RouteBox:/jffs/scripts# ip route show table 101
default via 10.149.1.6 dev tun11


these are the only errors in my log that i can find, and these are normal afaik.
Code:
Mar  4 19:42:00 openvpn[2821]: Options error: option 'redirect-gateway' cannot be used in this context ([PUSH-OPTIONS])
Mar  4 19:42:00 openvpn[2821]: Options error: option 'dhcp-option' cannot be used in this context ([PUSH-OPTIONS])
Mar  4 19:42:00 openvpn[2821]: Options error: option 'dhcp-option' cannot be used in this context ([PUSH-OPTIONS])
Mar  4 19:42:00 openvpn[2821]: Options error: option 'route' cannot be used in this context ([PUSH-OPTIONS])

So although in this case the 'syntax' error is irrelevant, see how easy it is to introduce simple typos when cut'n'pasting - PEBKAC!:D

..and yes the 'Options error:' messages that you have quoted are informational.

The info iptables/rules dump information looks fine with hits being recorded for the 3 rules. Now if there is indeed a bug in the fwmark processing on MIPS routers then if the Kernel did not honour/implement the fwmark tagging correctly, then the route-nopull directive should still force all of the packets via the WAN?.

I assume you have defnitely checked that 10.10.1.100 has been been correctly (statically) assigned to the device you wish to bypass the VPN and that the 10.149.1.6 is truly the VPN assigned to you when the script is invoked.

I suppose you could try with different table numbers and fwmark values in the script - edit them to other random values just in case they are now considered invalid.

But again, I stress that the whole point of of this version of the script is that with route no-pull VPN option in force, and with all 3 of the rules removed ALL traffic should be routed via the WAN.

So if the VPN is UP and connected, what happens if you manually issue

iptables -t mangle -F PREROUTING

....do all of your devices still go via the VPN?

I suggest you check your routes, alternatively, reboot and then immediately start the VPN without specifying the selective routing script to test WAN ONLY routing.

The last resort would be to use the original version of the selective routing script which uses 2 tables (and copies routing tables info that may or may not be 'valid'), extracts NVRAM values etc. which in my pesonal view may be even more problematic.
 
Last edited:
So I have checked and tried a number of things.

- The IPs are correct (the 10.10.1.100 is static/mac bound)
- tried different fwmark and table numbers (no change)
- # escaped the 3 iptable line at the end of the scripted. (everything still routes through the vpn)
- if I manually add an iptable prerouting entry it does nothing, I can see it with (iptables -t mangle -L -nv --line) and the pkts count goes up so I know it's sending data through it.

I'll try the original script as this is not working at all for me. Thanks for the all help, i'm sure i'll have more questions at some point.
 
So I have checked and tried a number of things.

- The IPs are correct (the 10.10.1.100 is static/mac bound)
- tried different fwmark and table numbers (no change)
- # escaped the 3 iptable line at the end of the scripted. (everything still routes through the vpn)
- if I manually add an iptable prerouting entry it does nothing, I can see it with (iptables -t mangle -L -nv --line) and the pkts count goes up so I know it's sending data through it.

I'll try the original script as this is not working at all for me. Thanks for the all help, i'm sure i'll have more questions at some point.

If you removed every trace of the script, and with route-nopull defined traffic still stubbornly uses the VPN, then there must be something wrong with the default route

ip route

xxx.xxx.xxx.xxx dev eth0 scope link
<>snip
default via xxx.xxx.xxx.xxx dev eth0

so if the default is the same as your VPN then that is where the issue lies

1. Disable VPN client
2. Reboot
3. Execute ip route command
4. Start VPN Client with route-nopull
5 .Execute ip route command again and compare the defaults.

Although technically the script documented on the WiKi incorrectly uses NVRAM variable

wan_gateway rather than wan0_gateway

it comprehensively covers the selective routing problem, and the author deserves recognition as the solution proposed no doubt works for his environment.

# https://github.com/RMerl/asuswrt-merlin/wiki/How-to-Direct-Traffic-over-VPN-and-Drop-connections-if-VPN-goes-down
 
Last edited:
Disabled the vpn and removed start with WAN then rebooted
Code:
dubwize@RouteBox:/tmp/home/root# ip route
108.170.161.129 dev eth0  scope link
108.170.161.128/25 dev eth0  proto kernel  scope link  src 108.170.161.194
10.0.0.0/8 dev br0  proto kernel  scope link  src 10.10.1.1
127.0.0.0/8 dev lo  scope link
default via 108.170.161.129 dev eth0

Started the VPN
Code:
64.237.37.117 via 108.170.161.129 dev eth0
10.115.1.9 dev tun11  proto kernel  scope link  src 10.115.1.10
108.170.161.129 dev eth0  scope link
108.170.161.128/25 dev eth0  proto kernel  scope link  src 108.170.161.194
10.0.0.0/8 dev br0  proto kernel  scope link  src 10.10.1.1
127.0.0.0/8 dev lo  scope link
0.0.0.0/1 via 10.115.1.9 dev tun11
128.0.0.0/1 via 10.115.1.9 dev tun11
default via 108.170.161.129 dev eth0

then thought to myself maybe i'll remove all the VPN extra options and leave only route-nopull
Code:
10.152.1.9 dev tun11  proto kernel  scope link  src 10.152.1.10
108.170.161.129 dev eth0  scope link
108.170.161.128/25 dev eth0  proto kernel  scope link  src 108.170.161.194
10.0.0.0/8 dev br0  proto kernel  scope link  src 10.10.1.1
127.0.0.0/8 dev lo  scope link
default via 108.170.161.129 dev eth0

and just to be clear I did remove the script completely from the VPN settings.
 
With your help Martineau I have I made it all work. So thank you for everything.

I guess i need to look into the kill switch now, since this sends everything through the WAN if it goes down. I'm sure there is a way to make everything go through the VPN by default except the one machine, and then if it had issues it would send the one machine through the VPN also.

Either way i'm happy with it now and i'll poke around at it later on if it it has issues.

Thanks again Martineau. :cool:
 
With your help Martineau I have I made it all work. So thank you for everything.

I guess i need to look into the kill switch now, since this sends everything through the WAN if it goes down. I'm sure there is a way to make everything go through the VPN by default except the one machine, and then if it had issues it would send the one machine through the VPN also.

Either way i'm happy with it now and i'll poke around at it later on if it it has issues.

Thanks again Martineau. :cool:

So something in the VPN Client Configuraton options was preventing route-nopull from being honoured? -- weird :eek:

To ensure that nothing gets out via the WAN you can enable only the first rule, or you could elect to allow HTTP/S through by enabling all three...simply add the clause to wan-start

Code:
# Here we can block ALL WAN access except http/https traffic until the VPN Client1 is physically started
#LANIP=$(nvram get lan_ipaddr)
#SUBNET_PREFIX=`echo $LANIP | awk 'BEGIN { FS = "." } {print $1"."$2"."$3}'`    # Extract first three octets of I/P
#iptables -I FORWARD -i br0 -s $SUBNET_PREFIX.0/24 -o eth0 -j DROP
#iptables -I FORWARD -s $SUBNET_PREFIX.0/24 -o ! tun11 -p tcp --dport 80 -j ACCEPT
#iptables -I FORWARD -s $SUBNET_PREFIX.0/24 -o ! tun11 -p tcp --dport 443 -j ACCEPT
 
Last edited:
Hi folks,

I hope you'll bear with me, I've been reading through this thread and I'm a little overwhelmed. There's some simple selective routing I'd like to accomplish. I think I understand what to do but I thought I'd ask a few basic questions first, as I'm a relative novice at this stuff.

The problem
I'd like to enable a Private Internet Access OpenVPN client connection on my router so all network traffic goes through it and I don't have to run specific clients on specific machines. The problem is when I do this a few key services (my VOIP lines for example) go down. So basically, I need to exclude the IP of the VOIP box from the VPN tunnel, which seems to be what this thread is all about.

My understanding of the solution
From my initial read of this thread, it appears that the answer lies in post #64 of this thread, from DJR747, linked here:
http://www.snbforums.com/threads/selective-routing-with-asuswrt-merlin.9311/page-4#post-101202

As I understand it, all I should theoretically need to do is the following:
  1. Replace the IP range in the original code with the one(s) I want to exclude from the VPN
  2. Save the code as a .sh file and upload it to the router
  3. Add route-nopull and script calling lines to the Custom Configuration area of my OpenVPN Client connection.
And I think that should be it.

My questions
All that having been said, I'm wondering the following:
  1. How do I upload the .sh file to my router and where is the best place to put it?
  2. If I want to exclude multiple unique IPs rather than a range, do I need to include a line for each IP address?
  3. I see a lot of talk about the code actually needing to start with "#!/bin/sh". Does that hold in this case? Do I need to include that? I'm assuming I do.
  4. I already have some simple entries in custom configuration. How do those settings live with this new entries? Do I just paste it above? Below? Does it matter? FYI, those settings can be seen in this guide for PIA and ASUSWRT-Merlin: http://i.imgur.com/tUr32fz.png
  5. What things am I fundamentally misunderstanding? (I'm sure I've got this all wrong)
In conclusion
Thanks in advance for any assistance. I feel a little in over my head here, so any help is greatly appreciated!
 
Last edited:
My questions
All that having been said, I'm wondering the following:
  1. How do I upload the .sh file to my router and where is the best place to put it?
  2. If I want to exclude multiple unique IPs rather than a range, do I need to include a line for each IP address?
  3. I see a lot of talk about the code actually needing to start with "#!/bin/sh". Does that hold in this case? Do I need to include that? I'm assuming I do.
  4. I already have some simple entries in custom configuration. How do those settings live with this new entries? Do I just paste it above? Below? Does it matter? FYI, those settings can be seen in this guide for PIA and ASUSWRT-Merlin: http://i.imgur.com/tUr32fz.png
  5. What things am I fundamentally misunderstanding? (I'm sure I've got this all wrong)
I'm a bit of a newbie myself but hopefully this is correct.
1) You need to upload the scripts to the router using ssh. This can be done using PuTTY, make sure you enable ssh in the web interface. Scripts are uploaded to /jffs/scripts, make sure you enable this in the web interface.
2) You can specify a range, here is an example
Code:
iptables -t mangle -A PREROUTING -i br0 -m iprange --src-range 192.168.10.2-192.168.10.254 -j MARK --set-mark 10
This means that all IPs (from .2 to .254) go through the VPN client (--set-mark 10)
3) You need the "#!/bin/sh". It's called a shebang https://en.wikipedia.org/wiki/Shebang_(Unix)
4) You can use openvpn-event as your script (See https://github.com/RMerl/asuswrt-merlin/wiki/User-scripts) or write your own shell script. openvpn-event runs each time the server starts/stops.

Hopefully that's clear but if not just ask away :)
 
Found this thread, which covers exactly what I want to achieve. I want to achieve the following:

1) All devices connect over my US VPN to selected sites (e.g., facebook, google, youtube)
2) All devices connect over my EU VPN to selected streaming services (e.g., Tunein, Zattoo, Netflix)
3) One devices always connects over VPN

I am open to using either Openvpn or PPTP and always wanted to get guidance what is actually the better way? From reading on the forums, it appears openvpn, but would also love to get your thoughts.

I have read through the whole thread, but am not knowledgeable enough to figure out how I can get this working and whether what I am trying to achieve is basic or something particularly difficult?

Any easy 101 guidance would be hugely appreciated!!! Thanks!
 
Thanks heaps for this. I'm a bit of a linux noob, but studied this script to try and figure out what's going on. As I understand it, you're creating two custom routing tables, 10 (vpn) and 12 (normal wan).

I guess you're then adding rules to the 'mangle' table to set a mark on each packet as either 10 or 12 to direct it to one of those predefined routes.

I think that I understand the IP range pointing packets to table 10, what I don't understand is this line.
> iptables -t mangle -A PREROUTING -i br0 -p tcp --dport 563 -j MARK --set-mark 12

I assume it directs everything not in the pre-defined ip range to table 12? Would someone mind pointing me in the right direction? Is this just a catch all? Do the tables process in order, so, anything not handled by '10' falls through to '12'? I don't understand what the 563 is.

Thanks for your help! :)


 
I think that line means that anything destined for port 563 (--dport 563) will be set as mark 12, so it should bypass the VPN.
 
I am using PPTP for my VPN. Got the script working fine but I wonder how to start it. ppp5 doesn't appear to exist during services-start and wan-start and I dont' get openvpn-event.

Thanks in advance.
 
I am using PPTP for my VPN. Got the script working fine but I wonder how to start it. ppp5 doesn't appear to exist during services-start and wan-start and I dont' get openvpn-event.

Thanks in advance.

Well clearly if you are not using OpenVPN then why would you expect PPTP to trigger the execution of the openvpn-event script?

The following post shows how to start the PPTP client from wan-start (In leiu of the missing 'Start with WAN' GUI toggle for the PPTP client)

http://forums.smallnetbuilder.com/showpost.php?p=106381&postcount=1
 
Just because I like to tease you guys:
ovpn-routing.png
 
Just because I like to tease you guys:
View attachment 3623

...and then you will be inundated with thankless punters asking why the selective routing doesn't allow more flexible criteria such as by traffic i.e. BitTorrents or http/https to a specific site!! :p
 
...and then you will be inundated with thankless punters asking why the selective routing doesn't allow more flexible criteria such as by traffic i.e. BitTorrents or http/https to a specific site!! :p

Eh. They will still be free to keep relying on user scripts if they really need more flexibility. I've always made sure to leave as many doors open as possible for more advanced tweaking by expert users.

My implementation is entirely done at the kernel routing table level (no packet marking involved). Anything that's based around protocol-based policies require iptable-level code, which will interfere with a lot of things, starting with the DPI engine. That means there's no way for me to implement it in a reliable enough way to be implemented in the firmware itself.

I haven't committed the code to Github yet because the implementation has been through multiple major changes over the past few days. I'm pretty close to a final implementation now, at which point I'll be able to push it to Github.
 
Eh. They will still be free to keep relying on user scripts if they really need more flexibility. I've always made sure to leave as many doors open as possible for more advanced tweaking by expert users.

My implementation is entirely done at the kernel routing table level (no packet marking involved). Anything that's based around protocol-based policies require iptable-level code, which will interfere with a lot of things, starting with the DPI engine. That means there's no way for me to implement it in a reliable enough way to be implemented in the firmware itself.

I haven't committed the code to Github yet because the implementation has been through multiple major changes over the past few days. I'm pretty close to a final implementation now, at which point I'll be able to push it to Github.

For the majority of users this will be a very welcome GUI feature addition with what sounds like an elegant (performance aware?) technical solution that we have come to expect from your firmware.

I guess my .BAT/AutoIT.au3 scripts (exploiting plink.exe) on Wintel platforms will still be around for a while allow to allow dynamic selective OpenVPN routing by device! :D
 

Latest threads

Sign Up For SNBForums Daily Digest

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