]> git.puffer.fish Git - matthieu/frr.git/commitdiff
bfdd: change vrf name with bypassing nb api
authorPhilippe Guibert <philippe.guibert@6wind.com>
Tue, 27 Aug 2019 14:58:47 +0000 (16:58 +0200)
committerPhilippe Guibert <philippe.guibert@6wind.com>
Tue, 27 Aug 2019 14:58:47 +0000 (16:58 +0200)
bfd operational & config data may already applied and available, while
an external event requests for changing the vrf name. this change
updates the config and operational context of yang.

Signed-off-by: Philippe Guibert <philippe.guibert@6wind.com>
bfdd/bfd.c

index 0b157ddafcae0502d7a554ed34533c75beb844de..44589566ba7c3ab23ed03dafae3101011682b572 100644 (file)
@@ -1756,6 +1756,51 @@ void bfd_session_update_vrf_name(struct bfd_session *bs, struct vrf *vrf)
                return;
        /* update key */
        hash_release(bfd_key_hash, bs);
+       /*
+        * HACK: Change the BFD VRF in the running configuration directly,
+        * bypassing the northbound layer. This is necessary to avoid deleting
+        * the BFD and readding it in the new VRF, which would have
+        * several implications.
+        */
+       if (yang_module_find("frr-bfdd") && bs->key.vrfname[0]) {
+               struct lyd_node *bfd_dnode;
+               char xpath[XPATH_MAXLEN], xpath_srcaddr[XPATH_MAXLEN + 32];
+               char addr_buf[INET6_ADDRSTRLEN];
+               int slen;
+
+               /* build xpath */
+               if (bs->key.mhop) {
+                       inet_ntop(bs->key.family, &bs->key.local, addr_buf, sizeof(addr_buf));
+                       snprintf(xpath_srcaddr, sizeof(xpath_srcaddr), "[source-addr='%s']",
+                                addr_buf);
+               } else
+                       xpath_srcaddr[0] = 0;
+               inet_ntop(bs->key.family, &bs->key.peer, addr_buf, sizeof(addr_buf));
+               slen = snprintf(xpath, sizeof(xpath),
+                               "/frr-bfdd:bfdd/bfd/sessions/%s%s[dest-addr='%s']",
+                               bs->key.mhop ? "multi-hop" : "single-hop", xpath_srcaddr,
+                               addr_buf);
+               if (bs->key.ifname[0])
+                       slen += snprintf(xpath + slen, sizeof(xpath) - slen,
+                                        "[interface='%s']", bs->key.ifname);
+               else
+                       slen += snprintf(xpath + slen, sizeof(xpath) - slen,
+                                        "[interface='']");
+               snprintf(xpath + slen, sizeof(xpath) - slen, "[vrf='%s']/vrf",
+                        bs->key.vrfname);
+
+               pthread_rwlock_wrlock(&running_config->lock);
+               {
+                       bfd_dnode = yang_dnode_get(
+                                                  running_config->dnode,
+                                                  xpath, bs->key.vrfname);
+                       if (bfd_dnode) {
+                               yang_dnode_change_leaf(bfd_dnode, vrf->name);
+                               running_config->version++;
+                       }
+                       pthread_rwlock_unlock(&running_config->lock);
+               }
+       }
        memset(bs->key.vrfname, 0, sizeof(bs->key.vrfname));
        strlcpy(bs->key.vrfname, vrf->name, sizeof(bs->key.vrfname));
        hash_get(bfd_key_hash, bs, hash_alloc_intern);