mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-06-14 16:29:32 +00:00
bgpd: Reformat bpacket_reformat_for_peer
This function was heavily indented, reformat to reduce indentation levels a bit. Signed-off-by: Donald Sharp <sharpd@cumulusnetworks.com>
This commit is contained in:
parent
4b08a72ed1
commit
f041034e44
@ -397,253 +397,243 @@ struct stream *bpacket_reformat_for_peer(struct bpacket *pkt,
|
|||||||
peer = PAF_PEER(paf);
|
peer = PAF_PEER(paf);
|
||||||
|
|
||||||
vec = &pkt->arr.entries[BGP_ATTR_VEC_NH];
|
vec = &pkt->arr.entries[BGP_ATTR_VEC_NH];
|
||||||
if (CHECK_FLAG(vec->flags, BPKT_ATTRVEC_FLAGS_UPDATED)) {
|
|
||||||
uint8_t nhlen;
|
|
||||||
afi_t nhafi;
|
|
||||||
int route_map_sets_nh;
|
|
||||||
nhlen = stream_getc_from(s, vec->offset);
|
|
||||||
filter = &peer->filter[paf->afi][paf->safi];
|
|
||||||
|
|
||||||
if (peer_cap_enhe(peer, paf->afi, paf->safi))
|
if (!CHECK_FLAG(vec->flags, BPKT_ATTRVEC_FLAGS_UPDATED))
|
||||||
nhafi = AFI_IP6;
|
return s;
|
||||||
else
|
|
||||||
nhafi = BGP_NEXTHOP_AFI_FROM_NHLEN(nhlen);
|
|
||||||
|
|
||||||
if (nhafi == AFI_IP) {
|
uint8_t nhlen;
|
||||||
struct in_addr v4nh, *mod_v4nh;
|
afi_t nhafi;
|
||||||
int nh_modified = 0;
|
int route_map_sets_nh;
|
||||||
size_t offset_nh = vec->offset + 1;
|
|
||||||
|
|
||||||
route_map_sets_nh =
|
nhlen = stream_getc_from(s, vec->offset);
|
||||||
(CHECK_FLAG(
|
filter = &peer->filter[paf->afi][paf->safi];
|
||||||
vec->flags,
|
|
||||||
BPKT_ATTRVEC_FLAGS_RMAP_IPV4_NH_CHANGED)
|
|
||||||
|| CHECK_FLAG(
|
|
||||||
vec->flags,
|
|
||||||
BPKT_ATTRVEC_FLAGS_RMAP_NH_PEER_ADDRESS));
|
|
||||||
|
|
||||||
switch (nhlen) {
|
if (peer_cap_enhe(peer, paf->afi, paf->safi))
|
||||||
case BGP_ATTR_NHLEN_IPV4:
|
nhafi = AFI_IP6;
|
||||||
break;
|
else
|
||||||
case BGP_ATTR_NHLEN_VPNV4:
|
nhafi = BGP_NEXTHOP_AFI_FROM_NHLEN(nhlen);
|
||||||
offset_nh += 8;
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
/* TODO: handle IPv6 nexthops */
|
|
||||||
flog_warn(
|
|
||||||
EC_BGP_INVALID_NEXTHOP_LENGTH,
|
|
||||||
"%s: %s: invalid MP nexthop length (AFI IP): %u",
|
|
||||||
__func__, peer->host, nhlen);
|
|
||||||
stream_free(s);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
stream_get_from(&v4nh, s, offset_nh, IPV4_MAX_BYTELEN);
|
if (nhafi == AFI_IP) {
|
||||||
mod_v4nh = &v4nh;
|
struct in_addr v4nh, *mod_v4nh;
|
||||||
|
int nh_modified = 0;
|
||||||
|
size_t offset_nh = vec->offset + 1;
|
||||||
|
|
||||||
/*
|
route_map_sets_nh =
|
||||||
* If route-map has set the nexthop, that is normally
|
(CHECK_FLAG(vec->flags,
|
||||||
* used; if it is specified as peer-address, the peering
|
BPKT_ATTRVEC_FLAGS_RMAP_IPV4_NH_CHANGED)
|
||||||
* address is picked up. Otherwise, if NH is unavailable
|
|| CHECK_FLAG(
|
||||||
* from attribute, the peering addr is picked up; the
|
vec->flags,
|
||||||
* "NH unavailable" case also covers next-hop-self and
|
BPKT_ATTRVEC_FLAGS_RMAP_NH_PEER_ADDRESS));
|
||||||
* some other scenarios - see subgroup_announce_check().
|
|
||||||
* In all other cases, use the nexthop carried in the
|
|
||||||
* attribute unless it is EBGP non-multiaccess and there
|
|
||||||
* is no next-hop-unchanged setting or the peer is EBGP
|
|
||||||
* and the route-map that changed the next-hop value
|
|
||||||
* was applied inbound rather than outbound. Updates to
|
|
||||||
* an EBGP peer should only modify the next-hop if it
|
|
||||||
* was set in an outbound route-map to that peer.
|
|
||||||
* Note: It is assumed route-map cannot set the nexthop
|
|
||||||
* to an invalid value.
|
|
||||||
*/
|
|
||||||
if (route_map_sets_nh
|
|
||||||
&& ((peer->sort != BGP_PEER_EBGP)
|
|
||||||
|| ROUTE_MAP_OUT(filter))) {
|
|
||||||
if (CHECK_FLAG(
|
|
||||||
vec->flags,
|
|
||||||
BPKT_ATTRVEC_FLAGS_RMAP_NH_PEER_ADDRESS)) {
|
|
||||||
mod_v4nh = &peer->nexthop.v4;
|
|
||||||
nh_modified = 1;
|
|
||||||
}
|
|
||||||
} else if (v4nh.s_addr == INADDR_ANY) {
|
|
||||||
mod_v4nh = &peer->nexthop.v4;
|
|
||||||
nh_modified = 1;
|
|
||||||
} else if (peer->sort == BGP_PEER_EBGP
|
|
||||||
&& (bgp_multiaccess_check_v4(v4nh, peer)
|
|
||||||
== 0)
|
|
||||||
&& !CHECK_FLAG(
|
|
||||||
vec->flags,
|
|
||||||
BPKT_ATTRVEC_FLAGS_RMAP_NH_UNCHANGED)
|
|
||||||
&& !peer_af_flag_check(
|
|
||||||
peer, paf->afi, paf->safi,
|
|
||||||
PEER_FLAG_NEXTHOP_UNCHANGED)) {
|
|
||||||
/* NOTE: not handling case where NH has new AFI
|
|
||||||
*/
|
|
||||||
mod_v4nh = &peer->nexthop.v4;
|
|
||||||
nh_modified = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (nh_modified) /* allow for VPN RD */
|
switch (nhlen) {
|
||||||
stream_put_in_addr_at(s, offset_nh, mod_v4nh);
|
case BGP_ATTR_NHLEN_IPV4:
|
||||||
|
break;
|
||||||
if (bgp_debug_update(peer, NULL, NULL, 0))
|
case BGP_ATTR_NHLEN_VPNV4:
|
||||||
zlog_debug("u%" PRIu64 ":s%" PRIu64
|
offset_nh += 8;
|
||||||
" %s send UPDATE w/ nexthop %s%s",
|
break;
|
||||||
PAF_SUBGRP(paf)->update_group->id,
|
default:
|
||||||
PAF_SUBGRP(paf)->id, peer->host,
|
/* TODO: handle IPv6 nexthops */
|
||||||
inet_ntoa(*mod_v4nh),
|
flog_warn(
|
||||||
(nhlen == 12 ? " and RD" : ""));
|
EC_BGP_INVALID_NEXTHOP_LENGTH,
|
||||||
} else if (nhafi == AFI_IP6) {
|
"%s: %s: invalid MP nexthop length (AFI IP): %u",
|
||||||
struct in6_addr v6nhglobal, *mod_v6nhg;
|
__func__, peer->host, nhlen);
|
||||||
struct in6_addr v6nhlocal, *mod_v6nhl;
|
stream_free(s);
|
||||||
int gnh_modified, lnh_modified;
|
return NULL;
|
||||||
size_t offset_nhglobal = vec->offset + 1;
|
|
||||||
size_t offset_nhlocal = vec->offset + 1;
|
|
||||||
|
|
||||||
gnh_modified = lnh_modified = 0;
|
|
||||||
mod_v6nhg = &v6nhglobal;
|
|
||||||
mod_v6nhl = &v6nhlocal;
|
|
||||||
|
|
||||||
route_map_sets_nh =
|
|
||||||
(CHECK_FLAG(
|
|
||||||
vec->flags,
|
|
||||||
BPKT_ATTRVEC_FLAGS_RMAP_IPV6_GNH_CHANGED)
|
|
||||||
|| CHECK_FLAG(
|
|
||||||
vec->flags,
|
|
||||||
BPKT_ATTRVEC_FLAGS_RMAP_NH_PEER_ADDRESS));
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The logic here is rather similar to that for IPv4,
|
|
||||||
* the
|
|
||||||
* additional work being to handle 1 or 2 nexthops.
|
|
||||||
* Also, 3rd
|
|
||||||
* party nexthop is not propagated for EBGP right now.
|
|
||||||
*/
|
|
||||||
switch (nhlen) {
|
|
||||||
case BGP_ATTR_NHLEN_IPV6_GLOBAL:
|
|
||||||
break;
|
|
||||||
case BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL:
|
|
||||||
offset_nhlocal += IPV6_MAX_BYTELEN;
|
|
||||||
break;
|
|
||||||
case BGP_ATTR_NHLEN_VPNV6_GLOBAL:
|
|
||||||
offset_nhglobal += 8;
|
|
||||||
break;
|
|
||||||
case BGP_ATTR_NHLEN_VPNV6_GLOBAL_AND_LL:
|
|
||||||
offset_nhglobal += 8;
|
|
||||||
offset_nhlocal += 8 * 2 + IPV6_MAX_BYTELEN;
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
/* TODO: handle IPv4 nexthops */
|
|
||||||
flog_warn(
|
|
||||||
EC_BGP_INVALID_NEXTHOP_LENGTH,
|
|
||||||
"%s: %s: invalid MP nexthop length (AFI IP6): %u",
|
|
||||||
__func__, peer->host, nhlen);
|
|
||||||
stream_free(s);
|
|
||||||
return NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
stream_get_from(&v6nhglobal, s, offset_nhglobal,
|
|
||||||
IPV6_MAX_BYTELEN);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Updates to an EBGP peer should only modify the
|
|
||||||
* next-hop if it was set in an outbound route-map
|
|
||||||
* to that peer.
|
|
||||||
*/
|
|
||||||
if (route_map_sets_nh
|
|
||||||
&& ((peer->sort != BGP_PEER_EBGP)
|
|
||||||
|| ROUTE_MAP_OUT(filter))) {
|
|
||||||
if (CHECK_FLAG(
|
|
||||||
vec->flags,
|
|
||||||
BPKT_ATTRVEC_FLAGS_RMAP_NH_PEER_ADDRESS)) {
|
|
||||||
mod_v6nhg = &peer->nexthop.v6_global;
|
|
||||||
gnh_modified = 1;
|
|
||||||
}
|
|
||||||
} else if (IN6_IS_ADDR_UNSPECIFIED(&v6nhglobal)) {
|
|
||||||
mod_v6nhg = &peer->nexthop.v6_global;
|
|
||||||
gnh_modified = 1;
|
|
||||||
} else if (
|
|
||||||
(peer->sort == BGP_PEER_EBGP)
|
|
||||||
&& (!bgp_multiaccess_check_v6(v6nhglobal, peer))
|
|
||||||
&& !CHECK_FLAG(vec->flags,
|
|
||||||
BPKT_ATTRVEC_FLAGS_RMAP_NH_UNCHANGED)
|
|
||||||
&& !peer_af_flag_check(
|
|
||||||
peer, nhafi, paf->safi,
|
|
||||||
PEER_FLAG_NEXTHOP_UNCHANGED)) {
|
|
||||||
/* NOTE: not handling case where NH has new AFI
|
|
||||||
*/
|
|
||||||
mod_v6nhg = &peer->nexthop.v6_global;
|
|
||||||
gnh_modified = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
if (nhlen == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL
|
|
||||||
|| nhlen == BGP_ATTR_NHLEN_VPNV6_GLOBAL_AND_LL) {
|
|
||||||
stream_get_from(&v6nhlocal, s, offset_nhlocal,
|
|
||||||
IPV6_MAX_BYTELEN);
|
|
||||||
if (IN6_IS_ADDR_UNSPECIFIED(&v6nhlocal)) {
|
|
||||||
mod_v6nhl = &peer->nexthop.v6_local;
|
|
||||||
lnh_modified = 1;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (gnh_modified)
|
|
||||||
stream_put_in6_addr_at(s, offset_nhglobal,
|
|
||||||
mod_v6nhg);
|
|
||||||
if (lnh_modified)
|
|
||||||
stream_put_in6_addr_at(s, offset_nhlocal,
|
|
||||||
mod_v6nhl);
|
|
||||||
|
|
||||||
if (bgp_debug_update(peer, NULL, NULL, 0)) {
|
|
||||||
if (nhlen == 32 || nhlen == 48)
|
|
||||||
zlog_debug(
|
|
||||||
"u%" PRIu64 ":s%" PRIu64
|
|
||||||
" %s send UPDATE w/ mp_nexthops %s, %s%s",
|
|
||||||
PAF_SUBGRP(paf)
|
|
||||||
->update_group->id,
|
|
||||||
PAF_SUBGRP(paf)->id, peer->host,
|
|
||||||
inet_ntop(AF_INET6, mod_v6nhg,
|
|
||||||
buf, BUFSIZ),
|
|
||||||
inet_ntop(AF_INET6, mod_v6nhl,
|
|
||||||
buf2, BUFSIZ),
|
|
||||||
(nhlen == 48 ? " and RD" : ""));
|
|
||||||
else
|
|
||||||
zlog_debug(
|
|
||||||
"u%" PRIu64 ":s%" PRIu64
|
|
||||||
" %s send UPDATE w/ mp_nexthop %s%s",
|
|
||||||
PAF_SUBGRP(paf)
|
|
||||||
->update_group->id,
|
|
||||||
PAF_SUBGRP(paf)->id, peer->host,
|
|
||||||
inet_ntop(AF_INET6, mod_v6nhg,
|
|
||||||
buf, BUFSIZ),
|
|
||||||
(nhlen == 24 ? " and RD" : ""));
|
|
||||||
}
|
|
||||||
} else if (paf->afi == AFI_L2VPN) {
|
|
||||||
struct in_addr v4nh, *mod_v4nh;
|
|
||||||
int nh_modified = 0;
|
|
||||||
|
|
||||||
stream_get_from(&v4nh, s, vec->offset + 1, 4);
|
|
||||||
mod_v4nh = &v4nh;
|
|
||||||
|
|
||||||
/* No route-map changes allowed for EVPN nexthops. */
|
|
||||||
if (v4nh.s_addr == INADDR_ANY) {
|
|
||||||
mod_v4nh = &peer->nexthop.v4;
|
|
||||||
nh_modified = 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (nh_modified)
|
|
||||||
stream_put_in_addr_at(s, vec->offset + 1,
|
|
||||||
mod_v4nh);
|
|
||||||
|
|
||||||
if (bgp_debug_update(peer, NULL, NULL, 0))
|
|
||||||
zlog_debug("u%" PRIu64 ":s%" PRIu64
|
|
||||||
" %s send UPDATE w/ nexthop %s",
|
|
||||||
PAF_SUBGRP(paf)->update_group->id,
|
|
||||||
PAF_SUBGRP(paf)->id, peer->host,
|
|
||||||
inet_ntoa(*mod_v4nh));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
stream_get_from(&v4nh, s, offset_nh, IPV4_MAX_BYTELEN);
|
||||||
|
mod_v4nh = &v4nh;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* If route-map has set the nexthop, that is normally
|
||||||
|
* used; if it is specified as peer-address, the peering
|
||||||
|
* address is picked up. Otherwise, if NH is unavailable
|
||||||
|
* from attribute, the peering addr is picked up; the
|
||||||
|
* "NH unavailable" case also covers next-hop-self and
|
||||||
|
* some other scenarios - see subgroup_announce_check().
|
||||||
|
* In all other cases, use the nexthop carried in the
|
||||||
|
* attribute unless it is EBGP non-multiaccess and there
|
||||||
|
* is no next-hop-unchanged setting or the peer is EBGP
|
||||||
|
* and the route-map that changed the next-hop value
|
||||||
|
* was applied inbound rather than outbound. Updates to
|
||||||
|
* an EBGP peer should only modify the next-hop if it
|
||||||
|
* was set in an outbound route-map to that peer.
|
||||||
|
* Note: It is assumed route-map cannot set the nexthop
|
||||||
|
* to an invalid value.
|
||||||
|
*/
|
||||||
|
if (route_map_sets_nh
|
||||||
|
&& ((peer->sort != BGP_PEER_EBGP)
|
||||||
|
|| ROUTE_MAP_OUT(filter))) {
|
||||||
|
if (CHECK_FLAG(
|
||||||
|
vec->flags,
|
||||||
|
BPKT_ATTRVEC_FLAGS_RMAP_NH_PEER_ADDRESS)) {
|
||||||
|
mod_v4nh = &peer->nexthop.v4;
|
||||||
|
nh_modified = 1;
|
||||||
|
}
|
||||||
|
} else if (v4nh.s_addr == INADDR_ANY) {
|
||||||
|
mod_v4nh = &peer->nexthop.v4;
|
||||||
|
nh_modified = 1;
|
||||||
|
} else if (peer->sort == BGP_PEER_EBGP
|
||||||
|
&& (bgp_multiaccess_check_v4(v4nh, peer) == 0)
|
||||||
|
&& !CHECK_FLAG(vec->flags,
|
||||||
|
BPKT_ATTRVEC_FLAGS_RMAP_NH_UNCHANGED)
|
||||||
|
&& !peer_af_flag_check(
|
||||||
|
peer, paf->afi, paf->safi,
|
||||||
|
PEER_FLAG_NEXTHOP_UNCHANGED)) {
|
||||||
|
/* NOTE: not handling case where NH has new AFI
|
||||||
|
*/
|
||||||
|
mod_v4nh = &peer->nexthop.v4;
|
||||||
|
nh_modified = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (nh_modified) /* allow for VPN RD */
|
||||||
|
stream_put_in_addr_at(s, offset_nh, mod_v4nh);
|
||||||
|
|
||||||
|
if (bgp_debug_update(peer, NULL, NULL, 0))
|
||||||
|
zlog_debug("u%" PRIu64 ":s%" PRIu64
|
||||||
|
" %s send UPDATE w/ nexthop %s%s",
|
||||||
|
PAF_SUBGRP(paf)->update_group->id,
|
||||||
|
PAF_SUBGRP(paf)->id, peer->host,
|
||||||
|
inet_ntoa(*mod_v4nh),
|
||||||
|
(nhlen == 12 ? " and RD" : ""));
|
||||||
|
} else if (nhafi == AFI_IP6) {
|
||||||
|
struct in6_addr v6nhglobal, *mod_v6nhg;
|
||||||
|
struct in6_addr v6nhlocal, *mod_v6nhl;
|
||||||
|
int gnh_modified, lnh_modified;
|
||||||
|
size_t offset_nhglobal = vec->offset + 1;
|
||||||
|
size_t offset_nhlocal = vec->offset + 1;
|
||||||
|
|
||||||
|
gnh_modified = lnh_modified = 0;
|
||||||
|
mod_v6nhg = &v6nhglobal;
|
||||||
|
mod_v6nhl = &v6nhlocal;
|
||||||
|
|
||||||
|
route_map_sets_nh =
|
||||||
|
(CHECK_FLAG(vec->flags,
|
||||||
|
BPKT_ATTRVEC_FLAGS_RMAP_IPV6_GNH_CHANGED)
|
||||||
|
|| CHECK_FLAG(
|
||||||
|
vec->flags,
|
||||||
|
BPKT_ATTRVEC_FLAGS_RMAP_NH_PEER_ADDRESS));
|
||||||
|
|
||||||
|
/*
|
||||||
|
* The logic here is rather similar to that for IPv4, the
|
||||||
|
* additional work being to handle 1 or 2 nexthops.
|
||||||
|
* Also, 3rd party nexthop is not propagated for EBGP
|
||||||
|
* right now.
|
||||||
|
*/
|
||||||
|
switch (nhlen) {
|
||||||
|
case BGP_ATTR_NHLEN_IPV6_GLOBAL:
|
||||||
|
break;
|
||||||
|
case BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL:
|
||||||
|
offset_nhlocal += IPV6_MAX_BYTELEN;
|
||||||
|
break;
|
||||||
|
case BGP_ATTR_NHLEN_VPNV6_GLOBAL:
|
||||||
|
offset_nhglobal += 8;
|
||||||
|
break;
|
||||||
|
case BGP_ATTR_NHLEN_VPNV6_GLOBAL_AND_LL:
|
||||||
|
offset_nhglobal += 8;
|
||||||
|
offset_nhlocal += 8 * 2 + IPV6_MAX_BYTELEN;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
/* TODO: handle IPv4 nexthops */
|
||||||
|
flog_warn(
|
||||||
|
EC_BGP_INVALID_NEXTHOP_LENGTH,
|
||||||
|
"%s: %s: invalid MP nexthop length (AFI IP6): %u",
|
||||||
|
__func__, peer->host, nhlen);
|
||||||
|
stream_free(s);
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
stream_get_from(&v6nhglobal, s, offset_nhglobal,
|
||||||
|
IPV6_MAX_BYTELEN);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Updates to an EBGP peer should only modify the
|
||||||
|
* next-hop if it was set in an outbound route-map
|
||||||
|
* to that peer.
|
||||||
|
*/
|
||||||
|
if (route_map_sets_nh
|
||||||
|
&& ((peer->sort != BGP_PEER_EBGP)
|
||||||
|
|| ROUTE_MAP_OUT(filter))) {
|
||||||
|
if (CHECK_FLAG(
|
||||||
|
vec->flags,
|
||||||
|
BPKT_ATTRVEC_FLAGS_RMAP_NH_PEER_ADDRESS)) {
|
||||||
|
mod_v6nhg = &peer->nexthop.v6_global;
|
||||||
|
gnh_modified = 1;
|
||||||
|
}
|
||||||
|
} else if (IN6_IS_ADDR_UNSPECIFIED(&v6nhglobal)) {
|
||||||
|
mod_v6nhg = &peer->nexthop.v6_global;
|
||||||
|
gnh_modified = 1;
|
||||||
|
} else if ((peer->sort == BGP_PEER_EBGP)
|
||||||
|
&& (!bgp_multiaccess_check_v6(v6nhglobal, peer))
|
||||||
|
&& !CHECK_FLAG(vec->flags,
|
||||||
|
BPKT_ATTRVEC_FLAGS_RMAP_NH_UNCHANGED)
|
||||||
|
&& !peer_af_flag_check(
|
||||||
|
peer, nhafi, paf->safi,
|
||||||
|
PEER_FLAG_NEXTHOP_UNCHANGED)) {
|
||||||
|
/* NOTE: not handling case where NH has new AFI
|
||||||
|
*/
|
||||||
|
mod_v6nhg = &peer->nexthop.v6_global;
|
||||||
|
gnh_modified = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (nhlen == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL
|
||||||
|
|| nhlen == BGP_ATTR_NHLEN_VPNV6_GLOBAL_AND_LL) {
|
||||||
|
stream_get_from(&v6nhlocal, s, offset_nhlocal,
|
||||||
|
IPV6_MAX_BYTELEN);
|
||||||
|
if (IN6_IS_ADDR_UNSPECIFIED(&v6nhlocal)) {
|
||||||
|
mod_v6nhl = &peer->nexthop.v6_local;
|
||||||
|
lnh_modified = 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (gnh_modified)
|
||||||
|
stream_put_in6_addr_at(s, offset_nhglobal, mod_v6nhg);
|
||||||
|
if (lnh_modified)
|
||||||
|
stream_put_in6_addr_at(s, offset_nhlocal, mod_v6nhl);
|
||||||
|
|
||||||
|
if (bgp_debug_update(peer, NULL, NULL, 0)) {
|
||||||
|
if (nhlen == 32 || nhlen == 48)
|
||||||
|
zlog_debug(
|
||||||
|
"u%" PRIu64 ":s%" PRIu64
|
||||||
|
" %s send UPDATE w/ mp_nexthops %s, %s%s",
|
||||||
|
PAF_SUBGRP(paf)->update_group->id,
|
||||||
|
PAF_SUBGRP(paf)->id, peer->host,
|
||||||
|
inet_ntop(AF_INET6, mod_v6nhg, buf,
|
||||||
|
BUFSIZ),
|
||||||
|
inet_ntop(AF_INET6, mod_v6nhl, buf2,
|
||||||
|
BUFSIZ),
|
||||||
|
(nhlen == 48 ? " and RD" : ""));
|
||||||
|
else
|
||||||
|
zlog_debug("u%" PRIu64 ":s%" PRIu64
|
||||||
|
" %s send UPDATE w/ mp_nexthop %s%s",
|
||||||
|
PAF_SUBGRP(paf)->update_group->id,
|
||||||
|
PAF_SUBGRP(paf)->id, peer->host,
|
||||||
|
inet_ntop(AF_INET6, mod_v6nhg, buf,
|
||||||
|
BUFSIZ),
|
||||||
|
(nhlen == 24 ? " and RD" : ""));
|
||||||
|
}
|
||||||
|
} else if (paf->afi == AFI_L2VPN) {
|
||||||
|
struct in_addr v4nh, *mod_v4nh;
|
||||||
|
int nh_modified = 0;
|
||||||
|
|
||||||
|
stream_get_from(&v4nh, s, vec->offset + 1, 4);
|
||||||
|
mod_v4nh = &v4nh;
|
||||||
|
|
||||||
|
/* No route-map changes allowed for EVPN nexthops. */
|
||||||
|
if (v4nh.s_addr == INADDR_ANY) {
|
||||||
|
mod_v4nh = &peer->nexthop.v4;
|
||||||
|
nh_modified = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (nh_modified)
|
||||||
|
stream_put_in_addr_at(s, vec->offset + 1, mod_v4nh);
|
||||||
|
|
||||||
|
if (bgp_debug_update(peer, NULL, NULL, 0))
|
||||||
|
zlog_debug("u%" PRIu64 ":s%" PRIu64
|
||||||
|
" %s send UPDATE w/ nexthop %s",
|
||||||
|
PAF_SUBGRP(paf)->update_group->id,
|
||||||
|
PAF_SUBGRP(paf)->id, peer->host,
|
||||||
|
inet_ntoa(*mod_v4nh));
|
||||||
}
|
}
|
||||||
|
|
||||||
return s;
|
return s;
|
||||||
|
Loading…
Reference in New Issue
Block a user