e = *extra;
if (e->damp_info)
- bgp_damp_info_free(e->damp_info, 0);
+ bgp_damp_info_free(e->damp_info, 0, e->damp_info->afi,
+ e->damp_info->safi);
e->damp_info = NULL;
if (e->parent) {
static int bgp_input_modifier(struct peer *peer, struct prefix *p,
struct attr *attr, afi_t afi, safi_t safi,
const char *rmap_name, mpls_label_t *label,
- uint32_t num_labels)
+ uint32_t num_labels, struct bgp_node *rn)
{
struct bgp_filter *filter;
struct bgp_path_info rmap_path = { 0 };
rmap_path.peer = peer;
rmap_path.attr = attr;
rmap_path.extra = &extra;
+ rmap_path.net = rn;
+
extra.num_labels = num_labels;
if (label && num_labels && num_labels <= BGP_MAX_LABELS)
memcpy(extra.label, label,
memset(&rmap_path, 0, sizeof(struct bgp_path_info));
rmap_path.peer = peer;
rmap_path.attr = attr;
+ rmap_path.net = rn;
if (pi->extra) {
memcpy(&dummy_rmap_path_extra, pi->extra,
__func__, family2str(family));
subgroup_announce_reset_nhop(family, attr);
}
+ }
- /* If IPv6/MP and nexthop does not have any override and happens
- * to
- * be a link-local address, reset it so that we don't pass along
- * the
- * source's link-local IPv6 address to recipients who may not be
- * on
- * the same interface.
- */
- if (p->family == AF_INET6 || peer_cap_enhe(peer, afi, safi)) {
- if (IN6_IS_ADDR_LINKLOCAL(&attr->mp_nexthop_global))
- subgroup_announce_reset_nhop(AF_INET6, attr);
- }
+ /* If IPv6/MP and nexthop does not have any override and happens
+ * to
+ * be a link-local address, reset it so that we don't pass along
+ * the
+ * source's link-local IPv6 address to recipients who may not be
+ * on
+ * the same interface.
+ */
+ if (p->family == AF_INET6 || peer_cap_enhe(peer, afi, safi)) {
+ if (IN6_IS_ADDR_LINKLOCAL(&attr->mp_nexthop_global))
+ subgroup_announce_reset_nhop(AF_INET6, attr);
}
return 1;
int connected = 0;
int do_loop_check = 1;
int has_valid_label = 0;
+ afi_t nh_afi;
#if ENABLE_BGP_VNC
int vnc_implicit_withdraw = 0;
#endif
* intern
* the attr (which takes over the memory references) */
if (bgp_input_modifier(peer, p, &new_attr, afi, safi, NULL,
- label, num_labels) == RMAP_DENY) {
+ label, num_labels, rn) == RMAP_DENY) {
peer->stat_pfx_filter++;
reason = "route-map;";
bgp_attr_flush(&new_attr);
/* Nexthop reachability check - for unicast and
* labeled-unicast.. */
- if ((afi == AFI_IP || afi == AFI_IP6)
- && (safi == SAFI_UNICAST || safi == SAFI_LABELED_UNICAST)) {
+ if (((afi == AFI_IP || afi == AFI_IP6)
+ && (safi == SAFI_UNICAST || safi == SAFI_LABELED_UNICAST))
+ || (safi == SAFI_EVPN &&
+ bgp_evpn_is_prefix_nht_supported(p))) {
if (peer->sort == BGP_PEER_EBGP && peer->ttl == 1
&& !CHECK_FLAG(peer->flags,
PEER_FLAG_DISABLE_CONNECTED_CHECK)
if (pi->extra && pi->extra->bgp_orig)
bgp_nexthop = pi->extra->bgp_orig;
- if (bgp_find_or_add_nexthop(bgp, bgp_nexthop, afi, pi,
- NULL, connected)
+ nh_afi = BGP_ATTR_NH_AFI(afi, pi->attr);
+
+ if (bgp_find_or_add_nexthop(bgp, bgp_nexthop, nh_afi,
+ pi, NULL, connected)
|| CHECK_FLAG(peer->flags, PEER_FLAG_IS_RFAPI_HD))
bgp_path_info_set_flag(rn, pi, BGP_PATH_VALID);
else {
* updating
* the attributes for the route in the VNI(s).
*/
- if (safi == SAFI_EVPN && !same_attr)
+ if (safi == SAFI_EVPN && !same_attr &&
+ CHECK_FLAG(pi->flags, BGP_PATH_VALID))
bgp_evpn_import_route(bgp, afi, safi, p, pi);
/* Process change. */
evpn == NULL ? NULL : &evpn->gw_ip);
}
/* Nexthop reachability check. */
- if ((afi == AFI_IP || afi == AFI_IP6)
- && (safi == SAFI_UNICAST || safi == SAFI_LABELED_UNICAST)) {
+ if (((afi == AFI_IP || afi == AFI_IP6)
+ && (safi == SAFI_UNICAST || safi == SAFI_LABELED_UNICAST))
+ || (safi == SAFI_EVPN && bgp_evpn_is_prefix_nht_supported(p))) {
if (peer->sort == BGP_PEER_EBGP && peer->ttl == 1
&& !CHECK_FLAG(peer->flags,
PEER_FLAG_DISABLE_CONNECTED_CHECK)
else
connected = 0;
- if (bgp_find_or_add_nexthop(bgp, bgp, afi, new, NULL, connected)
+ nh_afi = BGP_ATTR_NH_AFI(afi, new->attr);
+
+ if (bgp_find_or_add_nexthop(bgp, bgp, nh_afi, new, NULL,
+ connected)
|| CHECK_FLAG(peer->flags, PEER_FLAG_IS_RFAPI_HD))
bgp_path_info_set_flag(rn, new, BGP_PATH_VALID);
else {
return -1;
/* If this is an EVPN route, process for import. */
- if (safi == SAFI_EVPN)
+ if (safi == SAFI_EVPN && CHECK_FLAG(new->flags, BGP_PATH_VALID))
bgp_evpn_import_route(bgp, afi, safi, p, new);
hook_call(bgp_process, bgp, afi, safi, rn, peer, false);
/* dampening route */
static void damp_route_vty_out(struct vty *vty, struct prefix *p,
- struct bgp_path_info *path, int display,
+ struct bgp_path_info *path, int display, afi_t afi,
safi_t safi, bool use_json, json_object *json)
{
struct attr *attr;
}
if (use_json)
- bgp_damp_reuse_time_vty(vty, path, timebuf, BGP_UPTIME_LEN,
- use_json, json);
+ bgp_damp_reuse_time_vty(vty, path, timebuf, BGP_UPTIME_LEN, afi,
+ safi, use_json, json);
else
vty_out(vty, "%s ",
bgp_damp_reuse_time_vty(vty, path, timebuf,
- BGP_UPTIME_LEN, use_json,
- json));
+ BGP_UPTIME_LEN, afi, safi,
+ use_json, json));
/* Print attribute */
attr = path->attr;
/* flap route */
static void flap_route_vty_out(struct vty *vty, struct prefix *p,
- struct bgp_path_info *path, int display,
+ struct bgp_path_info *path, int display, afi_t afi,
safi_t safi, bool use_json, json_object *json)
{
struct attr *attr;
&& !CHECK_FLAG(path->flags, BGP_PATH_HISTORY)) {
if (use_json)
bgp_damp_reuse_time_vty(vty, path, timebuf,
- BGP_UPTIME_LEN, use_json, json);
+ BGP_UPTIME_LEN, afi, safi,
+ use_json, json);
else
vty_out(vty, "%s ",
bgp_damp_reuse_time_vty(vty, path, timebuf,
- BGP_UPTIME_LEN,
- use_json, json));
+ BGP_UPTIME_LEN, afi,
+ safi, use_json, json));
} else {
if (!use_json)
vty_out(vty, "%*s ", 8, " ");
}
if (path->extra && path->extra->damp_info)
- bgp_damp_info_vty(vty, path, json_path);
+ bgp_damp_info_vty(vty, path, afi, safi, json_path);
/* Remote Label */
if (path->extra && bgp_is_valid_label(&path->extra->label[0])
}
if (type == bgp_show_type_dampend_paths
|| type == bgp_show_type_damp_neighbor)
- damp_route_vty_out(vty, &rn->p, pi, display,
+ damp_route_vty_out(vty, &rn->p, pi, display, AFI_IP,
safi, use_json, json_paths);
else if (type == bgp_show_type_flap_statistics
|| type == bgp_show_type_flap_neighbor)
- flap_route_vty_out(vty, &rn->p, pi, display,
+ flap_route_vty_out(vty, &rn->p, pi, display, AFI_IP,
safi, use_json, json_paths);
else
route_vty_out(vty, &rn->p, pi, display, safi,
}
ret = bgp_show(vty, bgp, afi, safi, type, p, 0);
- prefix_free(p);
+ prefix_free(&p);
return ret;
}
argv_find(argv, argc, "X:X::X:X", &idx))
network = argv[idx]->arg;
else if (argv_find(argv, argc, "A.B.C.D/M", &idx) ||
- argv_find(argv, argc, "A.B.C.D/M", &idx)) {
+ argv_find(argv, argc, "X:X::X:X/M", &idx)) {
network = argv[idx]->arg;
prefix_check = 1;
} else {
/* Filter prefix using route-map */
ret = bgp_input_modifier(peer, &rn->p, &attr,
- afi, safi, rmap_name, NULL, 0);
+ afi, safi, rmap_name, NULL, 0,
+ NULL);
if (type == bgp_show_adj_route_filtered &&
!route_filtered && ret != RMAP_DENY) {
pi_temp = pi->next;
bgp_damp_info_free(
pi->extra->damp_info,
- 1);
+ 1, afi, safi);
pi = pi_temp;
} else
pi = pi->next;
pi_temp = pi->next;
bgp_damp_info_free(
pi->extra->damp_info,
- 1);
+ 1, afi, safi);
pi = pi_temp;
} else
pi = pi->next;
BGP_STR
"Clear route flap dampening information\n")
{
- bgp_damp_info_clean();
+ bgp_damp_info_clean(AFI_IP, SAFI_UNICAST);
return CMD_SUCCESS;
}