From 927c98f23a6317e2e3565032023d68b753d71037 Mon Sep 17 00:00:00 2001 From: Christian Poessinger Date: Fri, 10 Apr 2020 13:28:46 +0200 Subject: pppoe: T2248: connect-on-demand and vrf are mutually exclusive As PPP can be used to establish a connection on-demand it manages the Kernel default route. This can not be used when using VRFs which are managed by the ip-up.d and ip-down.d scripts - thus those options are now mutially exclusive. The best fix would be adding support for VRFs into PPP. --- data/templates/pppoe/ip-down.script.tmpl | 6 ++++-- data/templates/pppoe/ip-up.script.tmpl | 12 ++++++------ data/templates/pppoe/peer.tmpl | 9 +++++++++ src/conf_mode/interfaces-pppoe.py | 3 +++ 4 files changed, 22 insertions(+), 8 deletions(-) diff --git a/data/templates/pppoe/ip-down.script.tmpl b/data/templates/pppoe/ip-down.script.tmpl index e76875f12..a68fc099c 100644 --- a/data/templates/pppoe/ip-down.script.tmpl +++ b/data/templates/pppoe/ip-down.script.tmpl @@ -10,8 +10,9 @@ fi DIALER_PID=$(cat /var/run/{{ intf }}.pid) logger -t pppd[$DIALER_PID] "executing $0" -# Determine if we are enslaved to a VRF, this is needed to properly insert -# the default route +{% if not on_demand %} +# See https://phabricator.vyos.net/T2248. Determine if we are enslaved to a +# VRF, this is needed to properly insert the default route. VRF_NAME="" if [ -d /sys/class/net/{{ intf }}/upper_* ]; then # Determine upper (VRF) interface @@ -24,3 +25,4 @@ fi # Always delete default route when interface goes down vtysh -c "conf t" ${VRF_NAME} -c "no ip route 0.0.0.0/0 {{ intf }} ${VRF_NAME}" +{% endif %} diff --git a/data/templates/pppoe/ip-up.script.tmpl b/data/templates/pppoe/ip-up.script.tmpl index 4cc779914..697ebcc20 100644 --- a/data/templates/pppoe/ip-up.script.tmpl +++ b/data/templates/pppoe/ip-up.script.tmpl @@ -6,13 +6,15 @@ if [ "$6" != "{{ intf }}" ]; then exit fi -set -x +{% if not on_demand %} +# See https://phabricator.vyos.net/T2248 & T2220. Determine if we are enslaved +# to a VRF, this is needed to properly insert the default route. # add some info to syslog DIALER_PID=$(cat /var/run/{{ intf }}.pid) logger -t pppd[$DIALER_PID] "executing $0" -SED_OPT="ip route" +SED_OPT="^ip route" VRF_NAME="" if [ -d /sys/class/net/{{ intf }}/upper_* ]; then # Determine upper (VRF) interface @@ -25,10 +27,8 @@ if [ -d /sys/class/net/{{ intf }}/upper_* ]; then VRF_NAME="vrf ${VRF}" fi -# Debian PPP version has no support for replacing an existing default route -# thus we emulate this ba an ip-up script https://phabricator.vyos.net/T2220. {% if 'auto' in default_route -%} -# only insert a new default route if there is no default route configured +# Only insert a new default route if there is no default route configured routes=$(vtysh -c "show running-config" | sed -n "/${SED_OPT}/,/!/p" | grep 0.0.0.0/0 | wc -l) if [ "$routes" -ne 0 ]; then exit 1 @@ -44,4 +44,4 @@ done # Add default route to default or VRF routing table vtysh -c "conf t" ${VTY_OPT} -c "ip route 0.0.0.0/0 {{ intf }} ${VRF_NAME}" logger -t pppd[$DIALER_PID] "added default route via {{ intf }} ${VRF_NAME}" - +{% endif %} diff --git a/data/templates/pppoe/peer.tmpl b/data/templates/pppoe/peer.tmpl index 8651f12a5..36d108cee 100644 --- a/data/templates/pppoe/peer.tmpl +++ b/data/templates/pppoe/peer.tmpl @@ -60,4 +60,13 @@ rp_pppoe_service "{{ service_name }}" {% endif %} {% if on_demand %} demand +# See T2249. PPP default route options should only be set when in on-demand +# mode. As soon as we are not in on-demand mode the default-route handling is +# passed to the ip-up.d/ip-down.s scripts which is required for VRF support. +{% if 'auto' in default_route -%} +defaultroute +{% elif 'force' in default_route -%} +defaultroute +replacedefaultroute +{% endif %} {% endif %} diff --git a/src/conf_mode/interfaces-pppoe.py b/src/conf_mode/interfaces-pppoe.py index 5f073dac6..353a5a12c 100755 --- a/src/conf_mode/interfaces-pppoe.py +++ b/src/conf_mode/interfaces-pppoe.py @@ -155,6 +155,9 @@ def verify(pppoe): if vrf_name and vrf_name not in interfaces(): raise ConfigError(f'VRF {vrf_name} does not exist') + if pppoe['on_demand'] and pppoe['vrf']: + raise ConfigError('On-demand dialing and VRF can not be used at the same time') + return None def generate(pppoe): -- cgit v1.2.3