summaryrefslogtreecommitdiff
path: root/ripd/rip_interface.c
diff options
context:
space:
mode:
authorLu Feng <lu.feng@6wind.com>2014-07-18 06:13:18 +0000
committerDaniel Walton <dwalton@cumulusnetworks.com>2016-05-26 17:11:05 +0000
commitbce8e8681a4874fe6e5e126a25f4286563bf930b (patch)
tree3ffa9d41c17e11f5e21a53d2b4542e0ee097f350 /ripd/rip_interface.c
parent9bc6875ad65c22b4008dca0b572ae5b192f2bf91 (diff)
ripd: add ECMP support
* Each node in the routing table is changed into a list, holding the multiple equal-cost paths. * If one of the multiple entries gets less-preferred (greater metric or greater distance), it will be directly deleted instead of starting a garbage-collection timer for it. The garbage-collection timer is started only when the last entry in the list gets INFINITY. * Some new functions are used to maintain the ECMP list. And hence rip_rte_process(), rip_redistribute_add() and rip_timeout() are significantly simplified. * rip_zebra_ipv4_add() and rip_zebra_ipv4_delete() now can share the common code. The common part is moved to rip_zebra_ipv4_send(). Signed-off-by: Feng Lu <lu.feng@6wind.com> Reviewed-by: Alain Ritoux <alain.ritoux@6wind.com> Signed-off-by: David Lamparter <equinox@opensourcerouting.org> (cherry picked from commit b397cf4f0fc484c5ebfc8a680090055c8e6cbe32) Conflicts: ripd/rip_zebra.c
Diffstat (limited to 'ripd/rip_interface.c')
-rw-r--r--ripd/rip_interface.c38
1 files changed, 8 insertions, 30 deletions
diff --git a/ripd/rip_interface.c b/ripd/rip_interface.c
index 23d90a616d..6748e197da 100644
--- a/ripd/rip_interface.c
+++ b/ripd/rip_interface.c
@@ -580,37 +580,15 @@ rip_if_down(struct interface *ifp)
struct route_node *rp;
struct rip_info *rinfo;
struct rip_interface *ri = NULL;
+ struct list *list = NULL;
+ struct listnode *listnode = NULL, *nextnode = NULL;
if (rip)
- {
- for (rp = route_top (rip->table); rp; rp = route_next (rp))
- if ((rinfo = rp->info) != NULL)
- {
- /* Routes got through this interface. */
- if (rinfo->ifindex == ifp->ifindex &&
- rinfo->type == ZEBRA_ROUTE_RIP &&
- rinfo->sub_type == RIP_ROUTE_RTE)
- {
- rip_zebra_ipv4_delete ((struct prefix_ipv4 *) &rp->p,
- &rinfo->nexthop,
- rinfo->metric);
-
- rip_redistribute_delete (rinfo->type,rinfo->sub_type,
- (struct prefix_ipv4 *)&rp->p,
- rinfo->ifindex);
- }
- else
- {
- /* All redistributed routes but static and system */
- if ((rinfo->ifindex == ifp->ifindex) &&
- /* (rinfo->type != ZEBRA_ROUTE_STATIC) && */
- (rinfo->type != ZEBRA_ROUTE_SYSTEM))
- rip_redistribute_delete (rinfo->type,rinfo->sub_type,
- (struct prefix_ipv4 *)&rp->p,
- rinfo->ifindex);
- }
- }
- }
-
+ for (rp = route_top (rip->table); rp; rp = route_next (rp))
+ if ((list = rp->info) != NULL)
+ for (ALL_LIST_ELEMENTS (list, listnode, nextnode, rinfo))
+ if (rinfo->ifindex == ifp->ifindex)
+ rip_ecmp_delete (rinfo);
+
ri = ifp->info;
if (ri->running)