]> git.puffer.fish Git - matthieu/frr.git/commitdiff
zebra: Combine meta_queue_free and meta_queue_vrf_free functions
authorDonald Sharp <sharpd@nvidia.com>
Tue, 9 Aug 2022 17:09:16 +0000 (13:09 -0400)
committerDonald Sharp <sharpd@nvidia.com>
Wed, 10 Aug 2022 11:14:43 +0000 (07:14 -0400)
These functions essentially do the same thing.  Combine them
for the goodness of mankind.

Signed-off-by: Donald Sharp <sharpd@nvidia.com>
zebra/rib.h
zebra/zebra_rib.c
zebra/zebra_router.c
zebra/zebra_vrf.c

index 60092c9632e619ced30a6a36acfff35c6379fbc6..a40843e27f479b287fab78a1716cc3b4f49dd97e 100644 (file)
@@ -454,9 +454,7 @@ int zebra_rib_queue_evpn_rem_vtep_add(vrf_id_t vrf_id, vni_t vni,
 int zebra_rib_queue_evpn_rem_vtep_del(vrf_id_t vrf_id, vni_t vni,
                                      struct in_addr vtep_ip);
 
-extern void meta_queue_free(struct meta_queue *mq);
-extern void rib_meta_queue_free_vrf(struct meta_queue *mq,
-                                   struct zebra_vrf *zvrf);
+extern void meta_queue_free(struct meta_queue *mq, struct zebra_vrf *zvrf);
 extern int zebra_rib_labeled_unicast(struct route_entry *re);
 extern struct route_table *rib_table_ipv6;
 
index 2651eab164248ef532d55d1c022b9d01db6e30dd..79eb99ddf9448252641e678af8d9cb5b54dc73b4 100644 (file)
@@ -2958,64 +2958,103 @@ int zebra_rib_queue_evpn_rem_vtep_del(vrf_id_t vrf_id, vni_t vni,
        return mq_add_handler(w, rib_meta_queue_evpn_add);
 }
 
+
+/* Create new meta queue.
+   A destructor function doesn't seem to be necessary here.
+ */
+static struct meta_queue *meta_queue_new(void)
+{
+       struct meta_queue *new;
+       unsigned i;
+
+       new = XCALLOC(MTYPE_WORK_QUEUE, sizeof(struct meta_queue));
+
+       for (i = 0; i < MQ_SIZE; i++) {
+               new->subq[i] = list_new();
+               assert(new->subq[i]);
+       }
+
+       return new;
+}
+
 /* Clean up the EVPN meta-queue list */
-static void evpn_meta_queue_free(struct list *l)
+static void evpn_meta_queue_free(struct meta_queue *mq, struct list *l,
+                                struct zebra_vrf *zvrf)
 {
-       struct listnode *node;
+       struct listnode *node, *nnode;
        struct wq_evpn_wrapper *w;
 
        /* Free the node wrapper object, and the struct it wraps */
-       while ((node = listhead(l)) != NULL) {
-               w = node->data;
+       for (ALL_LIST_ELEMENTS(l, node, nnode, w)) {
+               if (zvrf) {
+                       vrf_id_t vrf_id = zvrf->vrf->vrf_id;
+
+                       if (w->vrf_id != vrf_id)
+                               continue;
+               }
+
                node->data = NULL;
 
                XFREE(MTYPE_WQ_WRAPPER, w);
 
                list_delete_node(l, node);
+               mq->size--;
        }
 }
 
 /* Clean up the nhg meta-queue list */
-static void nhg_meta_queue_free(struct list *l)
+static void nhg_meta_queue_free(struct meta_queue *mq, struct list *l,
+                               struct zebra_vrf *zvrf)
 {
        struct wq_nhg_wrapper *w;
-       struct listnode *node;
+       struct listnode *node, *nnode;
 
        /* Free the node wrapper object, and the struct it wraps */
-       while ((node = listhead(l)) != NULL) {
-               w = node->data;
-               node->data = NULL;
+       for (ALL_LIST_ELEMENTS(l, node, nnode, w)) {
+               if (zvrf) {
+                       vrf_id_t vrf_id = zvrf->vrf->vrf_id;
 
+                       if (w->type == WQ_NHG_WRAPPER_TYPE_CTX &&
+                           w->u.ctx->vrf_id != vrf_id)
+                               continue;
+                       else if (w->type == WQ_NHG_WRAPPER_TYPE_NHG &&
+                                w->u.nhe->vrf_id != vrf_id)
+                               continue;
+               }
                if (w->type == WQ_NHG_WRAPPER_TYPE_CTX)
                        nhg_ctx_free(&w->u.ctx);
                else if (w->type == WQ_NHG_WRAPPER_TYPE_NHG)
                        zebra_nhg_free(w->u.nhe);
 
+               node->data = NULL;
                XFREE(MTYPE_WQ_WRAPPER, w);
 
                list_delete_node(l, node);
+               mq->size--;
        }
 }
 
-/* Create new meta queue.
-   A destructor function doesn't seem to be necessary here.
- */
-static struct meta_queue *meta_queue_new(void)
+static void rib_meta_queue_free(struct meta_queue *mq, struct list *l,
+                               struct zebra_vrf *zvrf)
 {
-       struct meta_queue *new;
-       unsigned i;
+       struct route_node *rnode;
+       struct listnode *node, *nnode;
 
-       new = XCALLOC(MTYPE_WORK_QUEUE, sizeof(struct meta_queue));
+       for (ALL_LIST_ELEMENTS(l, node, nnode, rnode)) {
+               rib_dest_t *dest = rib_dest_from_rnode(rnode);
 
-       for (i = 0; i < MQ_SIZE; i++) {
-               new->subq[i] = list_new();
-               assert(new->subq[i]);
-       }
+               if (dest && rib_dest_vrf(dest) != zvrf)
+                       continue;
 
-       return new;
+               route_unlock_node(rnode);
+               node->data = NULL;
+               list_delete_node(l, node);
+               mq->size--;
+       }
 }
 
-void meta_queue_free(struct meta_queue *mq)
+
+void meta_queue_free(struct meta_queue *mq, struct zebra_vrf *zvrf)
 {
        enum meta_queue_indexes i;
 
@@ -3023,10 +3062,10 @@ void meta_queue_free(struct meta_queue *mq)
                /* Some subqueues may need cleanup - nhgs for example */
                switch (i) {
                case META_QUEUE_NHG:
-                       nhg_meta_queue_free(mq->subq[i]);
+                       nhg_meta_queue_free(mq, mq->subq[i], zvrf);
                        break;
                case META_QUEUE_EVPN:
-                       evpn_meta_queue_free(mq->subq[i]);
+                       evpn_meta_queue_free(mq, mq->subq[i], zvrf);
                        break;
                case META_QUEUE_CONNECTED:
                case META_QUEUE_KERNEL:
@@ -3034,76 +3073,15 @@ void meta_queue_free(struct meta_queue *mq)
                case META_QUEUE_NOTBGP:
                case META_QUEUE_BGP:
                case META_QUEUE_OTHER:
+                       rib_meta_queue_free(mq, mq->subq[i], zvrf);
                        break;
                }
-               list_delete(&mq->subq[i]);
+               if (!zvrf)
+                       list_delete(&mq->subq[i]);
        }
 
-       XFREE(MTYPE_WORK_QUEUE, mq);
-}
-
-void rib_meta_queue_free_vrf(struct meta_queue *mq, struct zebra_vrf *zvrf)
-{
-       vrf_id_t vrf_id = zvrf->vrf->vrf_id;
-       enum meta_queue_indexes i;
-
-       for (i = 0; i < MQ_SIZE; i++) {
-               struct listnode *lnode, *nnode;
-               void *data;
-               bool del;
-
-               for (ALL_LIST_ELEMENTS(mq->subq[i], lnode, nnode, data)) {
-                       del = false;
-
-                       switch (i) {
-                       case META_QUEUE_EVPN: {
-                               struct wq_evpn_wrapper *w = data;
-
-                               if (w->vrf_id == vrf_id) {
-                                       XFREE(MTYPE_WQ_WRAPPER, w);
-                                       del = true;
-                               }
-                               break;
-                       }
-                       case META_QUEUE_NHG: {
-                               struct wq_nhg_wrapper *w = data;
-
-                               if (w->type == WQ_NHG_WRAPPER_TYPE_CTX &&
-                                   w->u.ctx->vrf_id == vrf_id) {
-                                       nhg_ctx_free(&w->u.ctx);
-                                       XFREE(MTYPE_WQ_WRAPPER, w);
-                                       del = true;
-                               } else if (w->type == WQ_NHG_WRAPPER_TYPE_NHG &&
-                                          w->u.nhe->vrf_id == vrf_id) {
-                                       zebra_nhg_free(w->u.nhe);
-                                       XFREE(MTYPE_WQ_WRAPPER, w);
-                                       del = true;
-                               }
-                               break;
-                       }
-                       case META_QUEUE_CONNECTED:
-                       case META_QUEUE_KERNEL:
-                       case META_QUEUE_STATIC:
-                       case META_QUEUE_NOTBGP:
-                       case META_QUEUE_BGP:
-                       case META_QUEUE_OTHER: {
-                               struct route_node *rnode = data;
-                               rib_dest_t *dest = rib_dest_from_rnode(rnode);
-
-                               if (dest && rib_dest_vrf(dest) == zvrf) {
-                                       route_unlock_node(rnode);
-                                       del = true;
-                               }
-                               break;
-                       }
-                       }
-
-                       if (del) {
-                               list_delete_node(mq->subq[i], lnode);
-                               mq->size--;
-                       }
-               }
-       }
+       if (!zvrf)
+               XFREE(MTYPE_WORK_QUEUE, mq);
 }
 
 /* initialise zebra rib work queue */
index 24e71b4a8b8266d31a676147a0e9e86eecddbd38..c66849863e86b14c4584ba1014420fa03835f2ed 100644 (file)
@@ -239,7 +239,7 @@ void zebra_router_terminate(void)
                zebra_router_free_table(zrt);
 
        work_queue_free_and_null(&zrouter.ribq);
-       meta_queue_free(zrouter.mq);
+       meta_queue_free(zrouter.mq, NULL);
 
        zebra_vxlan_disable();
        zebra_mlag_terminate();
index 553864d089e2c17cc32a4c2b20c2ca50fc568c97..6624f0beb993913543ed8645fd47e73e9ac571b7 100644 (file)
@@ -218,7 +218,7 @@ static int zebra_vrf_disable(struct vrf *vrf)
                if_nbr_ipv6ll_to_ipv4ll_neigh_del_all(ifp);
 
        /* clean-up work queues */
-       rib_meta_queue_free_vrf(zrouter.mq, zvrf);
+       meta_queue_free(zrouter.mq, zvrf);
 
        /* Cleanup (free) routing tables and NHT tables. */
        for (afi = AFI_IP; afi <= AFI_IP6; afi++) {
@@ -253,7 +253,7 @@ static int zebra_vrf_delete(struct vrf *vrf)
        table_manager_disable(zvrf);
 
        /* clean-up work queues */
-       rib_meta_queue_free_vrf(zrouter.mq, zvrf);
+       meta_queue_free(zrouter.mq, zvrf);
 
        /* Free Vxlan and MPLS. */
        zebra_vxlan_close_tables(zvrf);