From: Donald Sharp Date: Thu, 11 Jun 2015 16:11:12 +0000 (-0700) Subject: Zebra: Don't resolve nexthops over default route unless explicitly allowed. X-Git-Tag: frr-2.0-rc1~1352 X-Git-Url: https://git.puffer.fish/?a=commitdiff_plain;h=18ff3eddccd3b024677bb9b2f9c5aac8df8ecc35;p=matthieu%2Ffrr.git Zebra: Don't resolve nexthops over default route unless explicitly allowed. Ensure that resolution of a nexthop using a default route is not done in the nexthop validation/update code in zebra_rib.c also. This is an addition to the zebra-nht-no-default.patch which made the checks only in the NHT code. In the case of scenarios like interface down, this nexthop update code will kick in first to update the route before the NHT code comes into play; without the additional fix, this code could incorrectly resolve the nexthop over a default route, even when disallowed by the administrator. --- diff --git a/lib/nexthop.h b/lib/nexthop.h index b375c55b95..e92d97262c 100644 --- a/lib/nexthop.h +++ b/lib/nexthop.h @@ -85,6 +85,20 @@ struct nexthop n; \ }) + +extern int zebra_rnh_ip_default_route; +extern int zebra_rnh_ipv6_default_route; + +static inline int +nh_resolve_via_default(int family) +{ + if (((family == AF_INET) && zebra_rnh_ip_default_route) || + ((family == AF_INET6) && zebra_rnh_ipv6_default_route)) + return 1; + else + return 0; +} + extern const char *nexthop_type_to_str (enum nexthop_types_t nh_type); extern int nexthop_same_no_recurse (struct nexthop *next1, struct nexthop *next2); diff --git a/lib/prefix.h b/lib/prefix.h index c02317a587..30fdaed3cf 100644 --- a/lib/prefix.h +++ b/lib/prefix.h @@ -247,4 +247,18 @@ static inline int ipv4_martian (struct in_addr *addr) return 0; } +static inline int +is_default_prefix (struct prefix *p) +{ + if (!p) + return 0; + + if (((p->family == AF_INET) && (p->u.prefix4.s_addr == INADDR_ANY)) + || ((p->family == AF_INET6) && + !memcmp(&p->u.prefix6, &in6addr_any, sizeof (struct in6_addr)))) + return 1; + + return 0; +} + #endif /* _ZEBRA_PREFIX_H */ diff --git a/zebra/zebra_rib.c b/zebra/zebra_rib.c index 3886e220b8..99db3a264e 100644 --- a/zebra/zebra_rib.c +++ b/zebra/zebra_rib.c @@ -570,6 +570,11 @@ nexthop_active_ipv4 (struct rib *rib, struct nexthop *nexthop, int set, return 0; /* Pick up selected route. */ + /* However, do not resolve over default route unless explicitly allowed. */ + if (is_default_prefix (&rn->p) && + !nh_resolve_via_default (p.family)) + return 0; + RNODE_FOREACH_RIB (rn, match) { if (CHECK_FLAG (match->status, RIB_ENTRY_REMOVED)) @@ -774,6 +779,11 @@ nexthop_active_ipv6 (struct rib *rib, struct nexthop *nexthop, int set, return 0; /* Pick up selected route. */ + /* However, do not resolve over default route unless explicitly allowed. */ + if (is_default_prefix (&rn->p) && + !nh_resolve_via_default (p.family)) + return 0; + RNODE_FOREACH_RIB (rn, match) { if (CHECK_FLAG (match->status, RIB_ENTRY_REMOVED)) diff --git a/zebra/zebra_rnh.c b/zebra/zebra_rnh.c index 16f5dac40e..f5bd1463aa 100644 --- a/zebra/zebra_rnh.c +++ b/zebra/zebra_rnh.c @@ -230,30 +230,6 @@ zebra_deregister_rnh_static_nh(struct prefix *nh, struct route_node *static_rn) zebra_delete_rnh(rnh, RNH_NEXTHOP_TYPE); } -static inline int -zebra_rnh_is_default_route(struct prefix *p) -{ - if (!p) - return 0; - - if (((p->family == AF_INET) && (p->u.prefix4.s_addr == INADDR_ANY)) - || ((p->family == AF_INET6) && - !memcmp(&p->u.prefix6, &in6addr_any, sizeof (struct in6_addr)))) - return 1; - - return 0; -} - -static inline int -zebra_rnh_resolve_via_default(int family) -{ - if (((family == AF_INET) && zebra_rnh_ip_default_route) || - ((family == AF_INET6) && zebra_rnh_ipv6_default_route)) - return 1; - else - return 0; -} - static int zebra_evaluate_rnh_nexthops(int family, struct rib *rib, struct route_node *prn, int proto) @@ -345,11 +321,11 @@ zebra_evaluate_rnh (int vrfid, int family, int force, rnh_type_t type, if (!prn) rib = NULL; else if ((type == RNH_NEXTHOP_TYPE) && - (zebra_rnh_is_default_route(&prn->p) && - !zebra_rnh_resolve_via_default(prn->p.family))) + (is_default_prefix (&prn->p) && + !nh_resolve_via_default(prn->p.family))) rib = NULL; else if ((type == RNH_IMPORT_CHECK_TYPE) && - ((zebra_rnh_is_default_route(&prn->p)) || + ((is_default_prefix(&prn->p)) || ((CHECK_FLAG(rnh->flags, ZEBRA_NHT_EXACT_MATCH)) && !prefix_same(&nrn->p, &prn->p)))) rib = NULL;