diff options
Diffstat (limited to 'ospfd/ospf_zebra.c')
| -rw-r--r-- | ospfd/ospf_zebra.c | 369 |
1 files changed, 237 insertions, 132 deletions
diff --git a/ospfd/ospf_zebra.c b/ospfd/ospf_zebra.c index dc8a8dccd2..fd965e8f21 100644 --- a/ospfd/ospf_zebra.c +++ b/ospfd/ospf_zebra.c @@ -73,12 +73,9 @@ static int ospf_router_id_update_zebra(ZAPI_CALLBACK_ARGS) struct prefix router_id; zebra_router_id_update_read(zclient->ibuf, &router_id); - if (IS_DEBUG_OSPF(zebra, ZEBRA_INTERFACE)) { - char buf[PREFIX2STR_BUFFER]; - prefix2str(&router_id, buf, sizeof(buf)); - zlog_debug("Zebra rcvd: router id update %s vrf %s id %u", buf, - ospf_vrf_id_to_name(vrf_id), vrf_id); - } + if (IS_DEBUG_OSPF(zebra, ZEBRA_INTERFACE)) + zlog_debug("Zebra rcvd: router id update %pFX vrf %s id %u", + &router_id, ospf_vrf_id_to_name(vrf_id), vrf_id); ospf = ospf_lookup_by_vrf_id(vrf_id); @@ -86,15 +83,11 @@ static int ospf_router_id_update_zebra(ZAPI_CALLBACK_ARGS) ospf->router_id_zebra = router_id.u.prefix4; ospf_router_id_update(ospf); } else { - if (IS_DEBUG_OSPF_EVENT) { - char buf[PREFIX2STR_BUFFER]; - - prefix2str(&router_id, buf, sizeof(buf)); + if (IS_DEBUG_OSPF_EVENT) zlog_debug( - "%s: ospf instance not found for vrf %s id %u router_id %s", + "%s: ospf instance not found for vrf %s id %u router_id %pFX", __func__, ospf_vrf_id_to_name(vrf_id), vrf_id, - buf); - } + &router_id); } return 0; } @@ -110,13 +103,10 @@ static int ospf_interface_address_add(ZAPI_CALLBACK_ARGS) if (c == NULL) return 0; - if (IS_DEBUG_OSPF(zebra, ZEBRA_INTERFACE)) { - char buf[PREFIX2STR_BUFFER]; - prefix2str(c->address, buf, sizeof(buf)); - zlog_debug("Zebra: interface %s address add %s vrf %s id %u", - c->ifp->name, buf, ospf_vrf_id_to_name(vrf_id), - vrf_id); - } + if (IS_DEBUG_OSPF(zebra, ZEBRA_INTERFACE)) + zlog_debug("Zebra: interface %s address add %pFX vrf %s id %u", + c->ifp->name, c->address, + ospf_vrf_id_to_name(vrf_id), vrf_id); ospf = ospf_lookup_by_vrf_id(vrf_id); if (!ospf) @@ -142,12 +132,9 @@ static int ospf_interface_address_delete(ZAPI_CALLBACK_ARGS) if (c == NULL) return 0; - if (IS_DEBUG_OSPF(zebra, ZEBRA_INTERFACE)) { - char buf[PREFIX2STR_BUFFER]; - prefix2str(c->address, buf, sizeof(buf)); - zlog_debug("Zebra: interface %s address delete %s", - c->ifp->name, buf); - } + if (IS_DEBUG_OSPF(zebra, ZEBRA_INTERFACE)) + zlog_debug("Zebra: interface %s address delete %pFX", + c->ifp->name, c->address); ifp = c->ifp; p = *c->address; @@ -279,17 +266,14 @@ void ospf_zebra_add(struct ospf *ospf, struct prefix_ipv4 *p, count++; if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) { - char buf[2][PREFIX2STR_BUFFER]; struct interface *ifp; ifp = if_lookup_by_index(path->ifindex, ospf->vrf_id); zlog_debug( - "Zebra: Route add %s nexthop %s, ifindex=%d %s", - prefix2str(p, buf[0], sizeof(buf[0])), - inet_ntop(AF_INET, &path->nexthop, - buf[1], sizeof(buf[1])), - path->ifindex, ifp ? ifp->name : " "); + "Zebra: Route add %pFX nexthop %pI4, ifindex=%d %s", + p, &path->nexthop, path->ifindex, + ifp ? ifp->name : " "); } } api.nexthop_num = count; @@ -309,11 +293,8 @@ void ospf_zebra_delete(struct ospf *ospf, struct prefix_ipv4 *p, api.safi = SAFI_UNICAST; memcpy(&api.prefix, p, sizeof(*p)); - if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) { - char buf[PREFIX2STR_BUFFER]; - zlog_debug("Zebra: Route delete %s", - prefix2str(p, buf, sizeof(buf))); - } + if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) + zlog_debug("Zebra: Route delete %pFX", p); zclient_route_send(ZEBRA_ROUTE_DELETE, zclient, &api); } @@ -332,11 +313,8 @@ void ospf_zebra_add_discard(struct ospf *ospf, struct prefix_ipv4 *p) zclient_route_send(ZEBRA_ROUTE_ADD, zclient, &api); - if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) { - char buf[PREFIX2STR_BUFFER]; - zlog_debug("Zebra: Route add discard %s", - prefix2str(p, buf, sizeof(buf))); - } + if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) + zlog_debug("Zebra: Route add discard %pFX", p); } void ospf_zebra_delete_discard(struct ospf *ospf, struct prefix_ipv4 *p) @@ -353,11 +331,8 @@ void ospf_zebra_delete_discard(struct ospf *ospf, struct prefix_ipv4 *p) zclient_route_send(ZEBRA_ROUTE_DELETE, zclient, &api); - if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) { - char buf[PREFIX2STR_BUFFER]; - zlog_debug("Zebra: Route delete discard %s", - prefix2str(p, buf, sizeof(buf))); - } + if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) + zlog_debug("Zebra: Route delete discard %pFX", p); } struct ospf_external *ospf_external_lookup(struct ospf *ospf, uint8_t type, @@ -433,8 +408,8 @@ bool ospf_external_default_routemap_apply_walk(struct ospf *ospf, if (ret && ei) { if (IS_DEBUG_OSPF_DEFAULT_INFO) - zlog_debug("Default originate routemap permit ei: %s", - inet_ntoa(ei->p.prefix)); + zlog_debug("Default originate routemap permit ei: %pI4", + &ei->p.prefix); return true; } @@ -488,7 +463,7 @@ static int ospf_external_lsa_default_routemap_timer(struct thread *thread) if (ret && !lsa) ospf_external_lsa_originate(ospf, default_ei); else if (ret && lsa && IS_LSA_MAXAGE(lsa)) - ospf_external_lsa_refresh(ospf, lsa, default_ei, true); + ospf_external_lsa_refresh(ospf, lsa, default_ei, true, false); else if (!ret && lsa) ospf_external_lsa_flush(ospf, DEFAULT_ROUTE, &default_ei->p, 0); @@ -875,8 +850,8 @@ static int ospf_external_lsa_originate_check(struct ospf *ospf, /* If prefix is multicast, then do not originate LSA. */ if (IN_MULTICAST(htonl(ei->p.prefix.s_addr))) { zlog_info( - "LSA[Type5:%s]: Not originate AS-external-LSA, Prefix belongs multicast", - inet_ntoa(ei->p.prefix)); + "LSA[Type5:%pI4]: Not originate AS-external-LSA, Prefix belongs multicast", + &ei->p.prefix); return 0; } @@ -968,16 +943,16 @@ static bool ospf_external_lsa_default_routemap_apply(struct ospf *ospf, } if (IS_DEBUG_OSPF_DEFAULT_INFO) - zlog_debug("Apply default originate routemap on ei: %s cmd: %d", - inet_ntoa(ei->p.prefix), cmd); + zlog_debug("Apply default originate routemap on ei: %pI4 cmd: %d", + &ei->p.prefix, cmd); ret = ospf_external_info_apply_default_routemap(ospf, ei, default_ei); /* If deny then nothing to be done both in add and del case. */ if (!ret) { if (IS_DEBUG_OSPF_DEFAULT_INFO) - zlog_debug("Default originte routemap deny for ei: %s", - inet_ntoa(ei->p.prefix)); + zlog_debug("Default originte routemap deny for ei: %pI4", + &ei->p.prefix); return false; } @@ -989,7 +964,7 @@ static bool ospf_external_lsa_default_routemap_apply(struct ospf *ospf, /* If permit and default already advertise then return. */ if (lsa && !IS_LSA_MAXAGE(lsa)) { if (IS_DEBUG_OSPF_DEFAULT_INFO) - zlog_debug("Defult lsa already originated"); + zlog_debug("Default lsa already originated"); return true; } @@ -998,7 +973,8 @@ static bool ospf_external_lsa_default_routemap_apply(struct ospf *ospf, if (lsa && IS_LSA_MAXAGE(lsa)) /* Refresh lsa.*/ - ospf_external_lsa_refresh(ospf, lsa, default_ei, true); + ospf_external_lsa_refresh(ospf, lsa, default_ei, true, + false); else /* If permit and default not advertised then advertise. */ @@ -1015,8 +991,8 @@ static bool ospf_external_lsa_default_routemap_apply(struct ospf *ospf, if (IS_DEBUG_OSPF_DEFAULT_INFO) zlog_debug( - "Running default route-map again as ei: %s deleted", - inet_ntoa(ei->p.prefix)); + "Running default route-map again as ei: %pI4 deleted", + &ei->p.prefix); /* * if this route delete was permitted then we need to check * there are any other external info which can still trigger @@ -1061,13 +1037,10 @@ int ospf_redistribute_check(struct ospf *ospf, struct external_info *ei, if (DISTRIBUTE_LIST(ospf, type)) if (access_list_apply(DISTRIBUTE_LIST(ospf, type), p) == FILTER_DENY) { - if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) { - char buf[PREFIX2STR_BUFFER]; + if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) zlog_debug( - "Redistribute[%s]: %s filtered by distribute-list.", - ospf_redist_string(type), - prefix2str(p, buf, sizeof(buf))); - } + "Redistribute[%s]: %pFX filtered by distribute-list.", + ospf_redist_string(type), p); return 0; } @@ -1088,13 +1061,10 @@ int ospf_redistribute_check(struct ospf *ospf, struct external_info *ei, if (ret == RMAP_DENYMATCH) { ei->route_map_set = save_values; - if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) { - char buf[PREFIX2STR_BUFFER]; + if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) zlog_debug( - "Redistribute[%s]: %s filtered by route-map.", - ospf_redist_string(type), - prefix2str(p, buf, sizeof(buf))); - } + "Redistribute[%s]: %pFX filtered by route-map.", + ospf_redist_string(type), p); return 0; } @@ -1171,14 +1141,10 @@ static int ospf_zebra_read_route(ZAPI_CALLBACK_ARGS) if (is_prefix_default(&p)) rt_type = DEFAULT_ROUTE; - if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) { - char buf_prefix[PREFIX_STRLEN]; - prefix2str(&api.prefix, buf_prefix, sizeof(buf_prefix)); - - zlog_debug("%s: cmd %s from client %s: vrf_id %d, p %s", + if (IS_DEBUG_OSPF(zebra, ZEBRA_REDISTRIBUTE)) + zlog_debug("%s: cmd %s from client %s: vrf_id %d, p %pFX", __func__, zserv_command_string(cmd), - zebra_route_string(api.type), vrf_id, buf_prefix); - } + zebra_route_string(api.type), vrf_id, &api.prefix); if (cmd == ZEBRA_REDISTRIBUTE_ROUTE_ADD) { /* XXX|HACK|TODO|FIXME: @@ -1215,24 +1181,100 @@ static int ospf_zebra_read_route(ZAPI_CALLBACK_ARGS) if (is_prefix_default(&p)) ospf_external_lsa_refresh_default(ospf); else { - struct ospf_lsa *current; + struct ospf_external_aggr_rt *aggr; + struct as_external_lsa *al; + struct ospf_lsa *lsa = NULL; + struct in_addr mask; + + aggr = ospf_external_aggr_match(ospf, + &ei->p); + + if (aggr) { + /* Check the AS-external-LSA + * should be originated. + */ + if (!ospf_redistribute_check( + ospf, ei, NULL)) + return 0; - current = ospf_external_info_find_lsa( - ospf, &ei->p); - if (!current) - ospf_external_lsa_originate( - ospf, ei); - else { if (IS_DEBUG_OSPF( - zebra, - ZEBRA_REDISTRIBUTE)) + lsa, + EXTNL_LSA_AGGR)) zlog_debug( - "ospf_zebra_read_route() : %s refreshing LSA", - inet_ntoa( - p.prefix)); - ospf_external_lsa_refresh( - ospf, current, ei, - LSA_REFRESH_FORCE); + "%s: Send Aggreate LSA (%pI4/%d)", + __func__, + &aggr->p.prefix, + aggr->p.prefixlen); + + ospf_originate_summary_lsa( + ospf, aggr, ei); + + /* Handling the case where the + * external route prefix + * and aggegate prefix is same + * If same dont flush the + * originated + * external LSA. + */ + if (prefix_same( + (struct prefix + *)&aggr->p, + (struct prefix *)&ei + ->p)) + return 0; + + lsa = ospf_external_info_find_lsa( + ospf, &ei->p); + + if (lsa) { + al = (struct + as_external_lsa *) + lsa->data; + masklen2ip( + ei->p.prefixlen, + &mask); + + if (mask.s_addr + != al->mask.s_addr) + return 0; + + ospf_external_lsa_flush( + ospf, ei->type, + &ei->p, 0); + } + } else { + struct ospf_lsa *current; + + current = + ospf_external_info_find_lsa( + ospf, &ei->p); + if (!current) { + /* Check the + * AS-external-LSA + * should be + * originated. + */ + if (!ospf_redistribute_check( + ospf, ei, + NULL)) + return 0; + + ospf_external_lsa_originate( + ospf, ei); + } else { + if (IS_DEBUG_OSPF( + zebra, + ZEBRA_REDISTRIBUTE)) + zlog_debug( + "%s: %pI4 refreshing LSA", + __func__, + &p.prefix); + ospf_external_lsa_refresh( + ospf, current, + ei, + LSA_REFRESH_FORCE, + false); + } } } } @@ -1246,21 +1288,36 @@ static int ospf_zebra_read_route(ZAPI_CALLBACK_ARGS) } else /* if (cmd == ZEBRA_REDISTRIBUTE_ROUTE_DEL) */ { - /* - * Check if default-information originate is - * with some routemap prefix/access list match. - * Apply before ei is deleted. - */ + struct ospf_external_aggr_rt *aggr; + ei = ospf_external_info_lookup(ospf, rt_type, api.instance, &p); - if (ei) + if (ei == NULL) + return 0; + else + /* + * Check if default-information originate i + * with some routemap prefix/access list match. + * Apply before ei is deleted. + */ ospf_external_lsa_default_routemap_apply(ospf, ei, cmd); - ospf_external_info_delete(ospf, rt_type, api.instance, p); - if (is_prefix_default(&p)) - ospf_external_lsa_refresh_default(ospf); - else - ospf_external_lsa_flush(ospf, rt_type, &p, - ifindex /*, nexthop */); + aggr = ospf_external_aggr_match(ospf, &ei->p); + + if (aggr && (ei->aggr_route == aggr)) { + ospf_unlink_ei_from_aggr(ospf, aggr, ei); + + ospf_external_info_delete(ospf, rt_type, api.instance, + p); + } else { + ospf_external_info_delete(ospf, rt_type, api.instance, + p); + + if (is_prefix_default(&p)) + ospf_external_lsa_refresh_default(ospf); + else + ospf_external_lsa_flush(ospf, rt_type, &p, + ifindex /*, nexthop */); + } } @@ -1352,32 +1409,80 @@ static int ospf_distribute_list_update_timer(struct thread *thread) if ((ei = rn->info) != NULL) { if (is_prefix_default(&ei->p)) default_refresh = 1; - else if ( - (lsa = ospf_external_info_find_lsa( - ospf, &ei->p))) { - int force = - LSA_REFRESH_IF_CHANGED; - /* If this is a MaxAge LSA, we - * need to force refresh it - * because distribute settings - * might have changed and now, - * this LSA needs to be - * originated, not be removed. - * If we don't force refresh it, - * it will remain a MaxAge LSA - * because it will look like it - * hasn't changed. Neighbors - * will not receive updates for - * this LSA. - */ - if (IS_LSA_MAXAGE(lsa)) - force = LSA_REFRESH_FORCE; - - ospf_external_lsa_refresh( - ospf, lsa, ei, force); - } else - ospf_external_lsa_originate( - ospf, ei); + else { + struct ospf_external_aggr_rt + *aggr; + aggr = ospf_external_aggr_match( + ospf, &ei->p); + if (aggr) { + /* Check the + * AS-external-LSA + * should be originated. + */ + if (!ospf_redistribute_check( + ospf, ei, + NULL)) { + + ospf_unlink_ei_from_aggr( + ospf, + aggr, + ei); + continue; + } + + if (IS_DEBUG_OSPF( + lsa, + EXTNL_LSA_AGGR)) + zlog_debug( + "%s: Send Aggregate LSA (%pI4/%d)", + __func__, + &aggr->p.prefix, + aggr->p.prefixlen); + + /* Originate Aggregate + * LSA + */ + ospf_originate_summary_lsa( + ospf, aggr, ei); + } else if ( + (lsa = ospf_external_info_find_lsa( + ospf, + &ei->p))) { + int force = + LSA_REFRESH_IF_CHANGED; + /* If this is a MaxAge + * LSA, we need to + * force refresh it + * because distribute + * settings might have + * changed and now, + * this LSA needs to be + * originated, not be + * removed. + * If we don't force + * refresh it, it will + * remain a MaxAge LSA + * because it will look + * like it hasn't + * changed. Neighbors + * will not receive + * updates for this LSA. + */ + if (IS_LSA_MAXAGE(lsa)) + force = LSA_REFRESH_FORCE; + + ospf_external_lsa_refresh( + ospf, lsa, ei, + force, false); + } else { + if (!ospf_redistribute_check( + ospf, ei, + NULL)) + continue; + ospf_external_lsa_originate( + ospf, ei); + } + } } } } |
