summaryrefslogtreecommitdiffstats
path: root/bgpd/bgp_vty.c
diff options
context:
space:
mode:
authorDonatas Abraitis <donatas@opensourcerouting.org>2022-10-24 16:30:10 +0200
committerGitHub <noreply@github.com>2022-10-24 16:30:10 +0200
commit695f387ed872c1bc55ad4149ede95465b48697b9 (patch)
tree0f53707776371ae9b36134b3fe6638d6cf9c76a2 /bgpd/bgp_vty.c
parentMerge pull request #12026 from kuldeepkash/bgp_local_asn (diff)
parentzebra: Do not allow SRv6 func_bit_len > 20 (diff)
downloadfrr-695f387ed872c1bc55ad4149ede95465b48697b9.tar.xz
frr-695f387ed872c1bc55ad4149ede95465b48697b9.zip
Merge pull request #11673 from cscarpitta/srv6-per-vrf-sid
bgpd: add support for SRv6 L3VPN for IPv4 and IPv6 address families using a single SID
Diffstat (limited to 'bgpd/bgp_vty.c')
-rw-r--r--bgpd/bgp_vty.c128
1 files changed, 127 insertions, 1 deletions
diff --git a/bgpd/bgp_vty.c b/bgpd/bgp_vty.c
index e574ae780..f380460a9 100644
--- a/bgpd/bgp_vty.c
+++ b/bgpd/bgp_vty.c
@@ -331,6 +331,9 @@ static int bgp_srv6_locator_unset(struct bgp *bgp)
/* refresh vpnv6 tovpn_sid */
XFREE(MTYPE_BGP_SRV6_SID,
bgp_vrf->vpn_policy[AFI_IP6].tovpn_sid);
+
+ /* refresh per-vrf tovpn_sid */
+ XFREE(MTYPE_BGP_SRV6_SID, bgp_vrf->tovpn_sid);
}
/* update vpn bgp processes */
@@ -356,6 +359,9 @@ static int bgp_srv6_locator_unset(struct bgp *bgp)
srv6_locator_chunk_free(tovpn_sid_locator);
bgp_vrf->vpn_policy[AFI_IP6].tovpn_sid_locator = NULL;
}
+
+ /* refresh per-vrf tovpn_sid_locator */
+ srv6_locator_chunk_free(bgp_vrf->tovpn_sid_locator);
}
/* clear locator name */
@@ -8995,6 +9001,14 @@ DEFPY (af_sid_vpn_export,
return CMD_WARNING_CONFIG_FAILED;
}
+ if (bgp->tovpn_sid_index != 0 ||
+ CHECK_FLAG(bgp->vrf_flags, BGP_VRF_TOVPN_SID_AUTO)) {
+ vty_out(vty,
+ "per-vrf sid and per-af sid are mutually exclusive\n"
+ "Failed: per-vrf sid is configured. Remove per-vrf sid before configuring per-af sid\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
/* skip when it's already configured */
if ((sid_idx != 0 && bgp->vpn_policy[afi].tovpn_sid_index != 0)
|| (sid_auto && CHECK_FLAG(bgp->vpn_policy[afi].flags,
@@ -9036,6 +9050,92 @@ DEFPY (af_sid_vpn_export,
return CMD_SUCCESS;
}
+DEFPY (bgp_sid_vpn_export,
+ bgp_sid_vpn_export_cmd,
+ "[no] sid vpn per-vrf export <(1-255)$sid_idx|auto$sid_auto>",
+ NO_STR
+ "sid value for VRF\n"
+ "Between current vrf and vpn\n"
+ "sid per-VRF (both IPv4 and IPv6 address families)\n"
+ "For routes leaked from current vrf to vpn\n"
+ "Sid allocation index\n"
+ "Automatically assign a label\n")
+{
+ VTY_DECLVAR_CONTEXT(bgp, bgp);
+ int debug;
+
+ debug = (BGP_DEBUG(vpn, VPN_LEAK_TO_VRF) |
+ BGP_DEBUG(vpn, VPN_LEAK_FROM_VRF));
+
+ if (no) {
+ /* when per-VRF SID is not set, do nothing */
+ if (bgp->tovpn_sid_index == 0 &&
+ !CHECK_FLAG(bgp->vrf_flags, BGP_VRF_TOVPN_SID_AUTO))
+ return CMD_SUCCESS;
+
+ sid_idx = 0;
+ sid_auto = false;
+ bgp->tovpn_sid_index = 0;
+ UNSET_FLAG(bgp->vrf_flags, BGP_VRF_TOVPN_SID_AUTO);
+ }
+
+ if (bgp->vpn_policy[AFI_IP].tovpn_sid_index != 0 ||
+ CHECK_FLAG(bgp->vpn_policy[AFI_IP].flags,
+ BGP_VPN_POLICY_TOVPN_SID_AUTO) ||
+ bgp->vpn_policy[AFI_IP6].tovpn_sid_index != 0 ||
+ CHECK_FLAG(bgp->vpn_policy[AFI_IP6].flags,
+ BGP_VPN_POLICY_TOVPN_SID_AUTO)) {
+ vty_out(vty,
+ "per-vrf sid and per-af sid are mutually exclusive\n"
+ "Failed: per-af sid is configured. Remove per-af sid before configuring per-vrf sid\n");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
+ /* skip when it's already configured */
+ if ((sid_idx != 0 && bgp->tovpn_sid_index != 0) ||
+ (sid_auto && CHECK_FLAG(bgp->vrf_flags, BGP_VRF_TOVPN_SID_AUTO)))
+ return CMD_SUCCESS;
+
+ /*
+ * mode change between sid_idx and sid_auto isn't supported.
+ * user must negate sid vpn export when they want to change the mode
+ */
+ if ((sid_auto && bgp->tovpn_sid_index != 0) ||
+ (sid_idx != 0 &&
+ CHECK_FLAG(bgp->vrf_flags, BGP_VRF_TOVPN_SID_AUTO))) {
+ vty_out(vty, "it's already configured as %s.\n",
+ sid_auto ? "auto-mode" : "idx-mode");
+ return CMD_WARNING_CONFIG_FAILED;
+ }
+
+ /* pre-change */
+ vpn_leak_prechange(BGP_VPN_POLICY_DIR_TOVPN, AFI_IP, bgp_get_default(),
+ bgp);
+ vpn_leak_prechange(BGP_VPN_POLICY_DIR_TOVPN, AFI_IP6, bgp_get_default(),
+ bgp);
+
+ if (sid_auto) {
+ /* SID allocation auto-mode */
+ if (debug)
+ zlog_debug("%s: auto per-vrf sid alloc.", __func__);
+ SET_FLAG(bgp->vrf_flags, BGP_VRF_TOVPN_SID_AUTO);
+ } else if (sid_idx != 0) {
+ /* SID allocation index-mode */
+ if (debug)
+ zlog_debug("%s: idx %ld per-vrf sid alloc.", __func__,
+ sid_idx);
+ bgp->tovpn_sid_index = sid_idx;
+ }
+
+ /* post-change */
+ vpn_leak_postchange(BGP_VPN_POLICY_DIR_TOVPN, AFI_IP, bgp_get_default(),
+ bgp);
+ vpn_leak_postchange(BGP_VPN_POLICY_DIR_TOVPN, AFI_IP6,
+ bgp_get_default(), bgp);
+
+ return CMD_SUCCESS;
+}
+
ALIAS (af_label_vpn_export,
af_no_label_vpn_export_cmd,
"no label vpn export",
@@ -9044,6 +9144,15 @@ ALIAS (af_label_vpn_export,
"Between current address-family and vpn\n"
"For routes leaked from current address-family to vpn\n")
+ALIAS (bgp_sid_vpn_export,
+ no_bgp_sid_vpn_export_cmd,
+ "no$no sid vpn per-vrf export",
+ NO_STR
+ "sid value for VRF\n"
+ "Between current vrf and vpn\n"
+ "sid per-VRF (both IPv4 and IPv6 address families)\n"
+ "For routes leaked from current vrf to vpn\n")
+
DEFPY (af_nexthop_vpn_export,
af_nexthop_vpn_export_cmd,
"[no] nexthop vpn export [<A.B.C.D|X:X::X:X>$nexthop_su]",
@@ -9751,8 +9860,14 @@ DEFPY (show_bgp_srv6,
vty_out(vty, "locator_name: %s\n", bgp->srv6_locator_name);
vty_out(vty, "locator_chunks:\n");
- for (ALL_LIST_ELEMENTS_RO(bgp->srv6_locator_chunks, node, chunk))
+ for (ALL_LIST_ELEMENTS_RO(bgp->srv6_locator_chunks, node, chunk)) {
vty_out(vty, "- %pFX\n", &chunk->prefix);
+ vty_out(vty, " block-length: %d\n", chunk->block_bits_length);
+ vty_out(vty, " node-length: %d\n", chunk->node_bits_length);
+ vty_out(vty, " func-length: %d\n",
+ chunk->function_bits_length);
+ vty_out(vty, " arg-length: %d\n", chunk->argument_bits_length);
+ }
vty_out(vty, "functions:\n");
for (ALL_LIST_ELEMENTS_RO(bgp->srv6_functions, node, func)) {
@@ -9770,6 +9885,7 @@ DEFPY (show_bgp_srv6,
bgp->vpn_policy[AFI_IP].tovpn_sid);
vty_out(vty, " vpn_policy[AFI_IP6].tovpn_sid: %pI6\n",
bgp->vpn_policy[AFI_IP6].tovpn_sid);
+ vty_out(vty, " per-vrf tovpn_sid: %pI6\n", bgp->tovpn_sid);
}
return CMD_SUCCESS;
@@ -17566,6 +17682,7 @@ int bgp_config_write(struct vty *vty)
struct listnode *mnode, *mnnode;
afi_t afi;
safi_t safi;
+ uint32_t tovpn_sid_index = 0;
if (bm->rmap_update_timer != RMAP_DEFAULT_UPDATE_TIMER)
vty_out(vty, "bgp route-map delay-timer %u\n",
@@ -17950,6 +18067,13 @@ int bgp_config_write(struct vty *vty)
vty_endframe(vty, " exit\n");
}
+ tovpn_sid_index = bgp->tovpn_sid_index;
+ if (CHECK_FLAG(bgp->vrf_flags, BGP_VRF_TOVPN_SID_AUTO)) {
+ vty_out(vty, " sid vpn per-vrf export auto\n");
+ } else if (tovpn_sid_index != 0) {
+ vty_out(vty, " sid vpn per-vrf export %d\n",
+ tovpn_sid_index);
+ }
/* IPv4 unicast configuration. */
bgp_config_write_family(vty, bgp, AFI_IP, SAFI_UNICAST);
@@ -19803,6 +19927,8 @@ void bgp_vty_init(void)
install_element(BGP_SRV6_NODE, &no_bgp_srv6_locator_cmd);
install_element(BGP_IPV4_NODE, &af_sid_vpn_export_cmd);
install_element(BGP_IPV6_NODE, &af_sid_vpn_export_cmd);
+ install_element(BGP_NODE, &bgp_sid_vpn_export_cmd);
+ install_element(BGP_NODE, &no_bgp_sid_vpn_export_cmd);
bgp_vty_if_init();
}