}
}
+/*
+ * Utility to determine whether a candidate nexthop is useable. We make this
+ * check in a couple of places, so this is a single home for the logic we
+ * use.
+ */
+static bool rnh_nexthop_valid(const struct nexthop *nh)
+{
+ return ((CHECK_FLAG(nh->flags, NEXTHOP_FLAG_FIB)
+ || CHECK_FLAG(nh->flags, NEXTHOP_FLAG_RECURSIVE))
+ && CHECK_FLAG(nh->flags, NEXTHOP_FLAG_ACTIVE));
+}
+
/*
* Determine appropriate route (route entry) resolving a tracked
* nexthop.
struct route_table *route_table;
struct route_node *rn;
struct route_entry *re;
+ struct nexthop *nexthop;
*prn = NULL;
if (!CHECK_FLAG(re->flags, ZEBRA_FLAG_SELECTED))
continue;
+ /* Just being SELECTED isn't quite enough - must
+ * have an installed nexthop to be useful.
+ */
+ for (nexthop = re->ng.nexthop; nexthop;
+ nexthop = nexthop->next) {
+ if (rnh_nexthop_valid(nexthop))
+ break;
+ }
+
+ if (nexthop == NULL)
+ continue;
+
if (CHECK_FLAG(rnh->flags, ZEBRA_NHT_CONNECTED)) {
if ((re->type == ZEBRA_ROUTE_CONNECT)
|| (re->type == ZEBRA_ROUTE_STATIC))
break;
if (re->type == ZEBRA_ROUTE_NHRP) {
- struct nexthop *nexthop;
for (nexthop = re->ng.nexthop; nexthop;
nexthop = nexthop->next)
nump = stream_get_endp(s);
stream_putc(s, 0);
for (nh = re->ng.nexthop; nh; nh = nh->next)
- if ((CHECK_FLAG(nh->flags, NEXTHOP_FLAG_FIB)
- || CHECK_FLAG(nh->flags, NEXTHOP_FLAG_RECURSIVE))
- && CHECK_FLAG(nh->flags, NEXTHOP_FLAG_ACTIVE)) {
+ if (rnh_nexthop_valid(nh)) {
+ stream_putl(s, nh->vrf_id);
stream_putc(s, nh->type);
switch (nh->type) {
case NEXTHOP_TYPE_IPV4: