Skip to content
maurerr edited this page Jul 12, 2022 · 26 revisions

Debugging openfortivpn

  • Run openfortivpn in verbose mode using command line option -v (or even -v -v for very verbose output).
  • Retrieve the pppd log using command line option --pppd-log. Some issues are related to pppd which is forked by openfortivpn.

Reporting issues

  • Create a new ticket under Issues instead of adding comments to existing issues. Similar symptoms do not necessarily mean identical causes.
  • Specify the versions of the operating system and openfortivpn.
  • Provide the verbose openfortivpn output obtained with command line option -v and the pppd log obtained with command line option --pppd-log. Remember to redact confidential information such as IP addresses.

Starting openfortivpn as a system service

  • StandardOutput= should redirect the output of openfortivpn to a file.
  • With Type=simple the PID of openfortivpn should be known to systemd. Or use Type=notify support which was added in #370.
  • Restart= can be used instead of --persistent.
  • see also #623 and #633 for integration with systemd

Using pppd ip-up / ip-down scripts

pppd sets a couple of environment variables (see man pppd). ipparam is currently passed through openfortivpn, but inside the ip-up / ip-down scripts one can replace variables in this string as follows:

ipparam_raw=$6
ipparam=$(eval echo $ipparam_raw)

and invoke with openfortivpn --pppd-ipparam='device=$DEVICE' Note the single quotes to prevent from variable expansion by the calling shell where $DEVICE is not yet set. Expansion is done inside the script by the execution of eval echo $ipparam_raw when the environment variables are made available by pppd.

One application is to manage the update of /etc/resolv.conf using openresolv. When calling openfortivpn --no-dns -v with the following scripts present on the system /etc/ppp/ip-down.d/000resolvconf:

#!/bin/sh
 
[ -x /sbin/resolvconf ] || exit 0
/sbin/resolvconf -f -d "$PPP_IFACE"

and /etc/ppp/ip-up.d/000resolvconf:

#!/bin/sh

[ -x /sbin/resolvconf ] || exit 0

if [ -n "$DNS1" -o -n "$DNS2" ]; then
        conf="# Generated by ppp.ip-up for $PPP_IFACE\n"
        [ -n "$DNS1" ] && conf="${conf}nameserver $DNS1\n"
        [ -n "$DNS2" ] && conf="${conf}nameserver $DNS2\n"
        printf "$conf" | /sbin/resolvconf -a "$PPP_IFACE"
fi

See also pppd ip-up scripts and option --pppd-ipparam in the openfortivpn man page.

How to add specific routes using pppd

method one - short version - pass routes by pppd-ipparam

assign routes to pppd-ipparam in your config file eg.

set-routes=0
pppd-ipparam=192.168.77.88 192.168.77.233 192.168.77.205

Then put this into /etc/ppp/ip-up.d/openfortivpn

#!/bin/sh -e   

logger "forticlient connection is up $PPP_IFACE connection ip routes: ${6}"
IPS="${6}"
for IP in ${IPS}
do
  ip route add ${IP} dev $PPP_IFACE
done

Don't forget to make it executable: sudo chmod a+x /etc/ppp/ip-up.d/openfortivpn

method two - extended version

  1. run openfortivpn with --no-routes flag, or add set-routes = 0 in your configuration file
  2. create a ppp script when link is up: sudo touch /etc/ppp/ip-up.d/fortivpn
  3. make it executable: sudo chmod a+x /etc/ppp/ip-up.d/fortivpn
  4. add your own routes, either by look up of their name or by adding specific ip addresses:
#!/bin/bash
#
# Example script for /etc/ppp/ip-up.d/openfortivpn
#
# Can be used to make internet work as usual having VPN running and only route Traffic
# for specified Networks to the VPN
#
# To use this, you may disable routing in /etc/openfortivpn/config like that:
#set-routes = 0
#half-internet-routes = 0
#
# Whitelist here all domains and ips (may be masked) that need to go through FortiVPN
# Domains are separated by a space
#
DOMAINS='example.com example.org'
IPS='10.0.0.0/8'

BASENAME=${0##*/}
INTERFACE=$1
DEVICE=$2
SPEED=$3
LOCALIP=$4
REMOTEIP=$5
IPPARAM=$6
ACTION=${0#/etc/ppp/}

let RESOLVED
for DOMAIN in $DOMAINS; do
  RESOLVED=`dig +short $DOMAIN | tail -n1`
  IPS="$IPS $RESOLVED"
done

for IP in $IPS; do
  ip route add $IP dev $INTERFACE
done
  1. check the created routes:
    $ route
    Kernel IP routing table
    Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
    default         192.168.10.254  0.0.0.0         UG    600    0        0 wlp3s0
    one.one.one.one *               255.255.255.255 UH    0      0        0 ppp0
    IP-OF-FIRST-DOMAIN *               255.255.255.255 UH    0      0        0 ppp0
    IP-OF-SECOND-DOMAIN *               255.255.255.255 UH    0      0        0 ppp0
    link-local      *               255.255.0.0     U     1000   0        0 br-cc6b09fa8986
    172.16.238.0    *               255.255.255.0   U     0      0        0 br-30ec352ff3e1
    172.17.0.0      *               255.255.0.0     U     0      0        0 docker0
    172.18.0.0      *               255.255.0.0     U     0      0        0 br-44b22a74e13d
    172.19.0.0      *               255.255.0.0     U     0      0        0 br-cc6b09fa8986
    172.20.0.0      *               255.255.0.0     U     0      0        0 br-2718c069c2ed
    192.168.10.0    *               255.255.255.0   U     600    0        0 wlp3s0
  1. check your IP: https://duckduckgo.com/?q=what%27s+my+ip&t=lm&atb=v110-5_h&ia=answer It should be your regular IP, while you should have access to white-listed domains through the VPN.

Server certificate

If the VPN gateway certificate is signed by a certification authority (CA) that is now known by the system, we suggest you add that CA to the system certificate store. See for example How to import CA root certificates on Linux and Windows.

As a last resort, you may retrieve the certificate from the VPN gateway and use the --trusted-certoption of openfortivpn. However, this implies a much higher risk of man-in-the-middle (MITM) attack. To retrieve the certificate, see openfortivpn#946 (comment).

Clone this wiki locally