From 26cc29d8fb3ff73dac3b602308079a95f6f315d2 Mon Sep 17 00:00:00 2001 From: ajs Date: Tue, 8 Jan 2008 20:12:46 +0000 Subject: [link-detect] Static interface routes should behave properly with link-detect. 2008-01-08 Michael Larson * zebra_rib.c: (nexthop_active_check) Replace if_is_up with if_is_operative to solve problems with static interface routes not behaving properly with link-detect. --- zebra/zebra_rib.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'zebra/zebra_rib.c') diff --git a/zebra/zebra_rib.c b/zebra/zebra_rib.c index 37b84a66..e27c63bf 100644 --- a/zebra/zebra_rib.c +++ b/zebra/zebra_rib.c @@ -795,7 +795,7 @@ nexthop_active_check (struct route_node *rn, struct rib *rib, { case NEXTHOP_TYPE_IFINDEX: ifp = if_lookup_by_index (nexthop->ifindex); - if (ifp && if_is_up (ifp)) + if (ifp && if_is_operative(ifp)) SET_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE); else UNSET_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE); @@ -804,7 +804,7 @@ nexthop_active_check (struct route_node *rn, struct rib *rib, family = AFI_IP6; case NEXTHOP_TYPE_IFNAME: ifp = if_lookup_by_name (nexthop->ifname); - if (ifp && if_is_up (ifp)) + if (ifp && if_is_operative(ifp)) { if (set) nexthop->ifindex = ifp->ifindex; @@ -838,7 +838,7 @@ nexthop_active_check (struct route_node *rn, struct rib *rib, if (IN6_IS_ADDR_LINKLOCAL (&nexthop->gate.ipv6)) { ifp = if_lookup_by_index (nexthop->ifindex); - if (ifp && if_is_up (ifp)) + if (ifp && if_is_operative(ifp)) SET_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE); else UNSET_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE); -- cgit v1.2.3 From c3c92461eb41baadaac3549ad5a99646b3184999 Mon Sep 17 00:00:00 2001 From: pilot Date: Tue, 26 Feb 2008 14:02:24 +0000 Subject: + fix bug#326 by rib_lookup_and_pushup() --- zebra/zebra_rib.c | 56 +++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 56 insertions(+) (limited to 'zebra/zebra_rib.c') diff --git a/zebra/zebra_rib.c b/zebra/zebra_rib.c index e27c63bf..c6af3290 100644 --- a/zebra/zebra_rib.c +++ b/zebra/zebra_rib.c @@ -1614,6 +1614,62 @@ void rib_lookup_and_dump (struct prefix_ipv4 * p) } } +/* Check if requested address assignment will fail due to another + * route being installed by zebra in FIB already. Take necessary + * actions, if needed: remove such a route from FIB and deSELECT + * corresponding RIB entry. Then put affected RN into RIBQ head. + */ +void rib_lookup_and_pushup (struct prefix_ipv4 * p) +{ + struct route_table *table; + struct route_node *rn; + struct rib *rib; + unsigned changed = 0; + + if (NULL == (table = vrf_table (AFI_IP, SAFI_UNICAST, 0))) + { + zlog_err ("%s: vrf_table() returned NULL", __func__); + return; + } + + /* No matches would be the simplest case. */ + if (NULL == (rn = route_node_lookup (table, (struct prefix *) p))) + return; + + /* Unlock node. */ + route_unlock_node (rn); + + /* Check all RIB entries. In case any changes have to be done, requeue + * the RN into RIBQ head. If the routing message about the new connected + * route (generated by the IP address we are going to assign very soon) + * comes before the RIBQ is processed, the new RIB entry will join + * RIBQ record already on head. This is necessary for proper revalidation + * of the rest of the RIB. + */ + for (rib = rn->info; rib; rib = rib->next) + { + if (CHECK_FLAG (rib->flags, ZEBRA_FLAG_SELECTED) && + ! RIB_SYSTEM_ROUTE (rib)) + { + changed = 1; + if (IS_ZEBRA_DEBUG_RIB) + { + char buf[INET_ADDRSTRLEN]; + inet_ntop (rn->p.family, &p->prefix, buf, INET_ADDRSTRLEN); + zlog_debug ("%s: freeing way for connected prefix %s/%d", __func__, buf, p->prefixlen); + rib_dump (__func__, (struct prefix_ipv4 *)&rn->p, rib); + } + rib_uninstall (rn, rib); + } + } + if (changed) + { + work_queue_aim_head (zebrad.ribq, 1); + rib_queue_add (&zebrad, rn); + work_queue_aim_head (zebrad.ribq, 0); + } +} + int rib_add_ipv4_multipath (struct prefix_ipv4 *p, struct rib *rib) { -- cgit v1.2.3