[SOLVED] Restart OpenVPN w/ modified openvpn.conf breaks PBR

Post new topic   Reply to topic    DD-WRT Forum Forum Index -> Advanced Networking
Author Message
anointer-unsolved-steersm
DD-WRT Novice


Joined: 27 Jul 2021
Posts: 2

PostPosted: Tue Jul 27, 2021 22:57    Post subject: [SOLVED] Restart OpenVPN w/ modified openvpn.conf breaks PBR Reply with quote
Router Model: Netgear R7800
Build Number: v3.0-r47090 std (07/26/21)
Kernel Version: Linux 4.9.276 #336 SMP Mon Jul 26 01:18:52 +07 2021 armv7l

Question:
How can I restart OpenVPN using a modified openvpn.conf while still preserving GUI-configured PBR rules?

Context:
I am trying to use a script from here that dynamically updates openvpn.conf with a more optimal VPN remote. However, the current method of restarting OpenVPN seems to break any PBR rules applied in the GUI.

Specifically, this line does reconnect OpenVPN to the new remote successfully, however the GUI-configured PBR rules are not applied.

Code:

# restart openvpn
openvpn --config /tmp/openvpncl/openvpn.conf --route-up /tmp/openvpncl/route-up.sh --route-pre-down /tmp/openvpncl/route-down.sh --daemon


I had tried something like below instead as this watchdog script suggests, however this approach does not use my modified openvpn.conf with the new "remote" config.

Code:
restart_f openvpn


Any suggestions or pointers would be greatly welcomed. Thanks!

Full Script:
Code:

#!/bin/sh

# specify PATH to run from cron
PATH=/bin:/usr/bin:/sbin:/usr/sbin:/jffs/sbin:/jffs/bin:/jffs/usr/sbin:/jffs/usr/bin:/mmc/sbin:/mmc/bin:/mmc/usr/sbin:/mmc/usr/bin:/opt/sbin:/opt/bin:/opt/usr/sbin:/opt/

# kill openvpn
PID=$(pidof openvpn)
kill -s SIGTERM "$PID"
while $(kill -0 "$PID" 2>/dev/null); do
  sleep 1
done

# fetch ProtonVPN server info
LOGICALS=$(curl -sk -H "Cache-Control: no-cache" -H "Accept: application/json" https://api.protonmail.ch/vpn/logicals)

# query for optimal server
IPSTRING=$(echo "$LOGICALS" | jq '.LogicalServers | map(select(.Status == 1 and .Tier == 2 and (.Name | (startswith("US-TX#") or startswith("US-GA#")) and (endswith("TOR") | not)))) | [sort_by(.Score, .Load)[]][0] | .Servers[0].EntryIP')

# update openvpn config
if [ -n "$IPSTRING" ]
then
  sed -i '/^remote/d' /tmp/openvpncl/openvpn.conf
  IPSTRING="${IPSTRING%\"}"
  IP="${IPSTRING#\"}"
  echo "Connecting to $IP..."
  REMOTE="remote ${IP} 443"
  echo $REMOTE >> /tmp/openvpncl/openvpn.conf
fi

# restart openvpn
openvpn --config /tmp/openvpncl/openvpn.conf --route-up /tmp/openvpncl/route-up.sh --route-pre-down /tmp/openvpncl/route-down.sh --daemon


Last edited by anointer-unsolved-steersm on Wed Jul 28, 2021 13:17; edited 1 time in total
Sponsor
eibgrad
DD-WRT Guru


Joined: 18 Sep 2010
Posts: 8784

PostPosted: Wed Jul 28, 2021 1:20    Post subject: Reply with quote
On the face of it, it's not obvious why PBR would fail to work under such circumstances. But there's been a lot of changes in how the OpenVPN client works over the past couple years, particularly recently, so I decided to take a closer look for myself.

From my own testing, it appears if you have the killswitch OFF, PBR will fail on the restart. At least when I dump the ip rules database, I don't see the rules anymore.

Code:
ip rule show


However, if I turn ON the killswitch, PBR works on the restart. And that's because as part of the killswitch logic, it preserves the ip rules database. IOW, after the openvpn process is killed, you can still dump the ip rules database again and see your rules.

IIRC, before the killswitch was implemented, PBR used to be managed within the route-up/route-down scripts. But that logic was moved into the firmware to make this and some other data structures persistent should the openvpn process fail. And perhaps that change in logic explains why simply restarting the OpenVPN client doesn't preserve PBR, at least w/ the killswitch OFF.

Btw, there's no need to include the --route-up or --route-pre-down options on the command line. Another one of the many changes to the OpenVPN client is the router now includes these directives in the config file (so they can be overridden in the Additional Config field should anyone find it necessary). IOW, the following will suffice.

Code:
openvpn --config /tmp/openvpncl/openvpn.conf --daemon

_________________
ddwrt-ovpn-split-basic.sh * ddwrt-ovpn-split-advanced.sh * ddwrt-ovpn-kill-switch.sh (new) * ddwrt-ovpn-watchdog.sh (new) * ddwrt-ovpn-remote-access.sh * ddwrt-ovpn-client-backup.sh * ddwrt-mount-usb-drives.sh
egc
DD-WRT Guru


Joined: 18 Mar 2014
Posts: 8180
Location: Netherlands

PostPosted: Wed Jul 28, 2021 7:02    Post subject: Reply with quote
It is like @eibgrad said the PBR has been moved to the code logic so either do your own PBR (I can send examples if you want) but easier is this (have not tried it)

Code:
stopservice openvpn
#replace your remote ip address/port in the nvram parameter:
nvram set openvpncl_remoteip="<my_new_server_address>"
nvram set openvpncl_remoteport="<my_new_port>"
nvram commit
startservice openvpn

_________________
Routers:Netgear R7800, R6400v1, R6400v2, Linksys EA8500, EA6900 (XvortexCFE), E2000 (converted WRT320N), WRT54GS v1.
WireGuard Documents & Guides:https://forum.dd-wrt.com/phpBB2/viewtopic.php?t=327397
OpenVPN Documents & Guides: https://forum.dd-wrt.com/phpBB2/viewtopic.php?t=327398
IPSET: https://forum.dd-wrt.com/phpBB2/viewtopic.php?t=327261
Install guide R6400v2:http://forum.dd-wrt.com/phpBB2/viewtopic.php?t=316399
Install guide R7800: https://forum.dd-wrt.com/phpBB2/viewtopic.php?t=320614
Forum Guide Lines (important read):https://forum.dd-wrt.com/phpBB2/viewtopic.php?t=324087
anointer-unsolved-steersm
DD-WRT Novice


Joined: 27 Jul 2021
Posts: 2

PostPosted: Wed Jul 28, 2021 13:15    Post subject: It works! Reply with quote
Thanks, @eibgrad and @egc . I tried @egc 's approach, and it seems to work well, and simpler to boot!

Updated code:

Code:

#!/bin/sh

# specify PATH to run from cron
PATH=/bin:/usr/bin:/sbin:/usr/sbin:/jffs/sbin:/jffs/bin:/jffs/usr/sbin:/jffs/usr/bin:/mmc/sbin:/mmc/bin:/mmc/usr/sbin:/mmc/usr/bin:/opt/sbin:/opt/bin:/opt/usr/sbin:/opt/

# stop openvpn
stopservice openvpn

# fetch ProtonVPN server info
LOGICALS=$(curl -sk -H "Cache-Control: no-cache" -H "Accept: application/json" https://api.protonmail.ch/vpn/logicals)

# query for optimal server
IPSTRING=$(echo "$LOGICALS" | jq '.LogicalServers | map(select(.Status == 1 and .Tier == 2 and (.Name | (startswith("US-TX#") or startswith("US-GA#")) and (endswith("TOR") | not)))) | [sort_by(.Score, .Load)[]][0] | .Servers[0].EntryIP')

# update openvpn config
if [ -n "$IPSTRING" ]
then
  IPSTRING="${IPSTRING%\"}"
  IP="${IPSTRING#\"}"
  echo "Connecting to $IP..."
  nvram set openvpncl_remoteip="${IP}"
  nvram commit
fi

# start openvpn
startservice openvpn
Display posts from previous:    Page 1 of 1
Post new topic   Reply to topic    DD-WRT Forum Forum Index -> Advanced Networking All times are GMT

Navigation

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
You cannot attach files in this forum
You cannot download files in this forum