Change the code to use less goto and instead use a while loop.
I think the result is easier to understand.

OK?
-- 
:wq Claudio

Index: rde_update.c
===================================================================
RCS file: /cvs/src/usr.sbin/bgpd/rde_update.c,v
retrieving revision 1.138
diff -u -p -r1.138 rde_update.c
--- rde_update.c        22 Mar 2022 10:53:08 -0000      1.138
+++ rde_update.c        30 Mar 2022 09:42:37 -0000
@@ -117,12 +117,7 @@ up_generate_updates(struct filter_head *
                prefixlen = new->pt->prefixlen;
        }
 
-again:
-       if (new == NULL) {
-               /* withdraw prefix */
-               if ((p = prefix_adjout_get(peer, 0, &addr, prefixlen)) != NULL)
-                       prefix_adjout_withdraw(p);
-       } else {
+       while (new != NULL) {
                need_withdraw = 0;
                /*
                 * up_test_update() needs to run before the output filters
@@ -144,7 +139,7 @@ again:
                if (need_withdraw &&
                    !(peer->flags & PEERFLAG_EVALUATE_ALL)) {
                        new = NULL;
-                       goto again;
+                       continue;
                }
 
                rde_filterstate_prep(&state, prefix_aspath(new),
@@ -159,14 +154,17 @@ again:
                                new = NULL;
                        if (new != NULL && !prefix_eligible(new))
                                new = NULL;
-                       goto again;
+                       continue;
                }
 
+               /* check if this was actually a withdraw */
                if (need_withdraw) {
                        new = NULL;
-                       goto again;
+                       continue;
                }
 
+               /* from here on we know this is an update */
+
                up_prep_adjout(peer, &state, addr.aid);
                prefix_adjout_update(peer, &state, &addr,
                    new->pt->prefixlen, prefix_vstate(new));
@@ -181,7 +179,13 @@ again:
                        rde_update_err(peer, ERR_CEASE,
                            ERR_CEASE_MAX_SENT_PREFIX, NULL, 0);
                }
+
+               return;
        }
+
+       /* withdraw prefix */
+       if ((p = prefix_adjout_get(peer, 0, &addr, prefixlen)) != NULL)
+               prefix_adjout_withdraw(p);
 }
 
 struct rib_entry *rib_add(struct rib *, struct bgpd_addr *, int);

Reply via email to