Merge pull request #3032 from donaldsharp/bgp_info

`struct bgp_info` to `struct bgp_path_info`
This commit is contained in:
Lou Berger 2018-10-11 09:17:31 -04:00 committed by GitHub
commit b3c8d34291
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
55 changed files with 3501 additions and 3484 deletions

View File

@ -104,8 +104,8 @@ bgp_route.[hc]:
looking for data in hash table, and putting there if missing, refcnt looking for data in hash table, and putting there if missing, refcnt
using pointer to existing data using pointer to existing data
many validity checks many validity checks
get new struct bgp_info (10 words/40 bytes) get new struct bgp_path_info
call bgp_info_add with rn and bgp_info call bgp_path_info_add with rn and bgp_path_info
call bgp_process call bgp_process
bgp_routemap.c bgp_routemap.c
@ -149,7 +149,7 @@ bgpd.c
Question: How much memory does quagga's bgpd use as a function of Question: How much memory does quagga's bgpd use as a function of
state received from peers? state received from peers?
It seems that a struct bgp_info is kept for each prefix. The "struct It seems that a struct bgp_path_info is kept for each prefix. The "struct
attr *" is interned, and variables within that are interned. So, 40 attr *" is interned, and variables within that are interned. So, 40
bytes are kept per received prefix, plus interned shared values. This bytes are kept per received prefix, plus interned shared values. This
could be 36 if 'int suppress' where changed to a u_char and moved to could be 36 if 'int suppress' where changed to a u_char and moved to

View File

@ -90,9 +90,9 @@ struct bgp_advertise *bgp_advertise_new(void)
void bgp_advertise_free(struct bgp_advertise *adv) void bgp_advertise_free(struct bgp_advertise *adv)
{ {
if (adv->binfo) if (adv->pathi)
bgp_info_unlock( /* bgp_advertise bgp_path_info reference */
adv->binfo); /* bgp_advertise bgp_info reference */ bgp_path_info_unlock(adv->pathi);
XFREE(MTYPE_BGP_ADVERTISE, adv); XFREE(MTYPE_BGP_ADVERTISE, adv);
} }

View File

@ -62,7 +62,7 @@ struct bgp_advertise {
struct bgp_advertise_attr *baa; struct bgp_advertise_attr *baa;
/* BGP info. */ /* BGP info. */
struct bgp_info *binfo; struct bgp_path_info *pathi;
}; };
/* BGP adjacency out. */ /* BGP adjacency out. */
@ -113,7 +113,7 @@ struct bgp_synchronize {
}; };
/* BGP adjacency linked list. */ /* BGP adjacency linked list. */
#define BGP_INFO_ADD(N, A, TYPE) \ #define BGP_PATH_INFO_ADD(N, A, TYPE) \
do { \ do { \
(A)->prev = NULL; \ (A)->prev = NULL; \
(A)->next = (N)->TYPE; \ (A)->next = (N)->TYPE; \
@ -122,7 +122,7 @@ struct bgp_synchronize {
(N)->TYPE = (A); \ (N)->TYPE = (A); \
} while (0) } while (0)
#define BGP_INFO_DEL(N, A, TYPE) \ #define BGP_PATH_INFO_DEL(N, A, TYPE) \
do { \ do { \
if ((A)->next) \ if ((A)->next) \
(A)->next->prev = (A)->prev; \ (A)->next->prev = (A)->prev; \
@ -132,10 +132,10 @@ struct bgp_synchronize {
(N)->TYPE = (A)->next; \ (N)->TYPE = (A)->next; \
} while (0) } while (0)
#define BGP_ADJ_IN_ADD(N,A) BGP_INFO_ADD(N,A,adj_in) #define BGP_ADJ_IN_ADD(N, A) BGP_PATH_INFO_ADD(N, A, adj_in)
#define BGP_ADJ_IN_DEL(N,A) BGP_INFO_DEL(N,A,adj_in) #define BGP_ADJ_IN_DEL(N, A) BGP_PATH_INFO_DEL(N, A, adj_in)
#define BGP_ADJ_OUT_ADD(N,A) BGP_INFO_ADD(N,A,adj_out) #define BGP_ADJ_OUT_ADD(N, A) BGP_PATH_INFO_ADD(N, A, adj_out)
#define BGP_ADJ_OUT_DEL(N,A) BGP_INFO_DEL(N,A,adj_out) #define BGP_ADJ_OUT_DEL(N, A) BGP_PATH_INFO_DEL(N, A, adj_out)
#define BGP_ADV_FIFO_ADD(F, N) \ #define BGP_ADV_FIFO_ADD(F, N) \
do { \ do { \

View File

@ -42,8 +42,8 @@ static struct bgp_damp_config *damp = &bgp_damp_cfg;
/* Utility macro to add and delete BGP dampening information to no /* Utility macro to add and delete BGP dampening information to no
used list. */ used list. */
#define BGP_DAMP_LIST_ADD(N,A) BGP_INFO_ADD(N,A,no_reuse_list) #define BGP_DAMP_LIST_ADD(N, A) BGP_PATH_INFO_ADD(N, A, no_reuse_list)
#define BGP_DAMP_LIST_DEL(N,A) BGP_INFO_DEL(N,A,no_reuse_list) #define BGP_DAMP_LIST_DEL(N, A) BGP_PATH_INFO_DEL(N, A, no_reuse_list)
/* Calculate reuse list index by penalty value. */ /* Calculate reuse list index by penalty value. */
static int bgp_reuse_index(int penalty) static int bgp_reuse_index(int penalty)
@ -128,7 +128,7 @@ static int bgp_reuse_timer(struct thread *t)
/* 3. if ( the saved list head pointer is non-empty ) */ /* 3. if ( the saved list head pointer is non-empty ) */
for (; bdi; bdi = next) { for (; bdi; bdi = next) {
struct bgp *bgp = bdi->binfo->peer->bgp; struct bgp *bgp = bdi->path->peer->bgp;
next = bdi->next; next = bdi->next;
@ -145,15 +145,15 @@ static int bgp_reuse_timer(struct thread *t)
/* if (figure-of-merit < reuse). */ /* if (figure-of-merit < reuse). */
if (bdi->penalty < damp->reuse_limit) { if (bdi->penalty < damp->reuse_limit) {
/* Reuse the route. */ /* Reuse the route. */
bgp_info_unset_flag(bdi->rn, bdi->binfo, bgp_path_info_unset_flag(bdi->rn, bdi->path,
BGP_INFO_DAMPED); BGP_PATH_DAMPED);
bdi->suppress_time = 0; bdi->suppress_time = 0;
if (bdi->lastrecord == BGP_RECORD_UPDATE) { if (bdi->lastrecord == BGP_RECORD_UPDATE) {
bgp_info_unset_flag(bdi->rn, bdi->binfo, bgp_path_info_unset_flag(bdi->rn, bdi->path,
BGP_INFO_HISTORY); BGP_PATH_HISTORY);
bgp_aggregate_increment(bgp, &bdi->rn->p, bgp_aggregate_increment(bgp, &bdi->rn->p,
bdi->binfo, bdi->afi, bdi->path, bdi->afi,
bdi->safi); bdi->safi);
bgp_process(bgp, bdi->rn, bdi->afi, bdi->safi); bgp_process(bgp, bdi->rn, bdi->afi, bdi->safi);
} }
@ -172,8 +172,8 @@ static int bgp_reuse_timer(struct thread *t)
} }
/* A route becomes unreachable (RFC2439 Section 4.8.2). */ /* A route becomes unreachable (RFC2439 Section 4.8.2). */
int bgp_damp_withdraw(struct bgp_info *binfo, struct bgp_node *rn, afi_t afi, int bgp_damp_withdraw(struct bgp_path_info *path, struct bgp_node *rn,
safi_t safi, int attr_change) afi_t afi, safi_t safi, int attr_change)
{ {
time_t t_now; time_t t_now;
struct bgp_damp_info *bdi = NULL; struct bgp_damp_info *bdi = NULL;
@ -182,8 +182,8 @@ int bgp_damp_withdraw(struct bgp_info *binfo, struct bgp_node *rn, afi_t afi,
t_now = bgp_clock(); t_now = bgp_clock();
/* Processing Unreachable Messages. */ /* Processing Unreachable Messages. */
if (binfo->extra) if (path->extra)
bdi = binfo->extra->damp_info; bdi = path->extra->damp_info;
if (bdi == NULL) { if (bdi == NULL) {
/* If there is no previous stability history. */ /* If there is no previous stability history. */
@ -195,7 +195,7 @@ int bgp_damp_withdraw(struct bgp_info *binfo, struct bgp_node *rn, afi_t afi,
bdi = XCALLOC(MTYPE_BGP_DAMP_INFO, bdi = XCALLOC(MTYPE_BGP_DAMP_INFO,
sizeof(struct bgp_damp_info)); sizeof(struct bgp_damp_info));
bdi->binfo = binfo; bdi->path = path;
bdi->rn = rn; bdi->rn = rn;
bdi->penalty = bdi->penalty =
(attr_change ? DEFAULT_PENALTY / 2 : DEFAULT_PENALTY); (attr_change ? DEFAULT_PENALTY / 2 : DEFAULT_PENALTY);
@ -205,7 +205,7 @@ int bgp_damp_withdraw(struct bgp_info *binfo, struct bgp_node *rn, afi_t afi,
bdi->index = -1; bdi->index = -1;
bdi->afi = afi; bdi->afi = afi;
bdi->safi = safi; bdi->safi = safi;
(bgp_info_extra_get(binfo))->damp_info = bdi; (bgp_path_info_extra_get(path))->damp_info = bdi;
BGP_DAMP_LIST_ADD(damp, bdi); BGP_DAMP_LIST_ADD(damp, bdi);
} else { } else {
last_penalty = bdi->penalty; last_penalty = bdi->penalty;
@ -222,16 +222,16 @@ int bgp_damp_withdraw(struct bgp_info *binfo, struct bgp_node *rn, afi_t afi,
bdi->flap++; bdi->flap++;
} }
assert((rn == bdi->rn) && (binfo == bdi->binfo)); assert((rn == bdi->rn) && (path == bdi->path));
bdi->lastrecord = BGP_RECORD_WITHDRAW; bdi->lastrecord = BGP_RECORD_WITHDRAW;
bdi->t_updated = t_now; bdi->t_updated = t_now;
/* Make this route as historical status. */ /* Make this route as historical status. */
bgp_info_set_flag(rn, binfo, BGP_INFO_HISTORY); bgp_path_info_set_flag(rn, path, BGP_PATH_HISTORY);
/* Remove the route from a reuse list if it is on one. */ /* Remove the route from a reuse list if it is on one. */
if (CHECK_FLAG(bdi->binfo->flags, BGP_INFO_DAMPED)) { if (CHECK_FLAG(bdi->path->flags, BGP_PATH_DAMPED)) {
/* If decay rate isn't equal to 0, reinsert brn. */ /* If decay rate isn't equal to 0, reinsert brn. */
if (bdi->penalty != last_penalty && bdi->index >= 0) { if (bdi->penalty != last_penalty && bdi->index >= 0) {
bgp_reuse_list_delete(bdi); bgp_reuse_list_delete(bdi);
@ -243,7 +243,7 @@ int bgp_damp_withdraw(struct bgp_info *binfo, struct bgp_node *rn, afi_t afi,
/* If not suppressed before, do annonunce this withdraw and /* If not suppressed before, do annonunce this withdraw and
insert into reuse_list. */ insert into reuse_list. */
if (bdi->penalty >= damp->suppress_value) { if (bdi->penalty >= damp->suppress_value) {
bgp_info_set_flag(rn, binfo, BGP_INFO_DAMPED); bgp_path_info_set_flag(rn, path, BGP_PATH_DAMPED);
bdi->suppress_time = t_now; bdi->suppress_time = t_now;
BGP_DAMP_LIST_DEL(damp, bdi); BGP_DAMP_LIST_DEL(damp, bdi);
bgp_reuse_list_add(bdi); bgp_reuse_list_add(bdi);
@ -252,28 +252,28 @@ int bgp_damp_withdraw(struct bgp_info *binfo, struct bgp_node *rn, afi_t afi,
return BGP_DAMP_USED; return BGP_DAMP_USED;
} }
int bgp_damp_update(struct bgp_info *binfo, struct bgp_node *rn, afi_t afi, int bgp_damp_update(struct bgp_path_info *path, struct bgp_node *rn, afi_t afi,
safi_t safi) safi_t safi)
{ {
time_t t_now; time_t t_now;
struct bgp_damp_info *bdi; struct bgp_damp_info *bdi;
int status; int status;
if (!binfo->extra || !((bdi = binfo->extra->damp_info))) if (!path->extra || !((bdi = path->extra->damp_info)))
return BGP_DAMP_USED; return BGP_DAMP_USED;
t_now = bgp_clock(); t_now = bgp_clock();
bgp_info_unset_flag(rn, binfo, BGP_INFO_HISTORY); bgp_path_info_unset_flag(rn, path, BGP_PATH_HISTORY);
bdi->lastrecord = BGP_RECORD_UPDATE; bdi->lastrecord = BGP_RECORD_UPDATE;
bdi->penalty = bgp_damp_decay(t_now - bdi->t_updated, bdi->penalty); bdi->penalty = bgp_damp_decay(t_now - bdi->t_updated, bdi->penalty);
if (!CHECK_FLAG(bdi->binfo->flags, BGP_INFO_DAMPED) if (!CHECK_FLAG(bdi->path->flags, BGP_PATH_DAMPED)
&& (bdi->penalty < damp->suppress_value)) && (bdi->penalty < damp->suppress_value))
status = BGP_DAMP_USED; status = BGP_DAMP_USED;
else if (CHECK_FLAG(bdi->binfo->flags, BGP_INFO_DAMPED) else if (CHECK_FLAG(bdi->path->flags, BGP_PATH_DAMPED)
&& (bdi->penalty < damp->reuse_limit)) { && (bdi->penalty < damp->reuse_limit)) {
bgp_info_unset_flag(rn, binfo, BGP_INFO_DAMPED); bgp_path_info_unset_flag(rn, path, BGP_PATH_DAMPED);
bgp_reuse_list_delete(bdi); bgp_reuse_list_delete(bdi);
BGP_DAMP_LIST_ADD(damp, bdi); BGP_DAMP_LIST_ADD(damp, bdi);
bdi->suppress_time = 0; bdi->suppress_time = 0;
@ -290,28 +290,29 @@ int bgp_damp_update(struct bgp_info *binfo, struct bgp_node *rn, afi_t afi,
} }
/* Remove dampening information and history route. */ /* Remove dampening information and history route. */
int bgp_damp_scan(struct bgp_info *binfo, afi_t afi, safi_t safi) int bgp_damp_scan(struct bgp_path_info *path, afi_t afi, safi_t safi)
{ {
time_t t_now, t_diff; time_t t_now, t_diff;
struct bgp_damp_info *bdi; struct bgp_damp_info *bdi;
assert(binfo->extra && binfo->extra->damp_info); assert(path->extra && path->extra->damp_info);
t_now = bgp_clock(); t_now = bgp_clock();
bdi = binfo->extra->damp_info; bdi = path->extra->damp_info;
if (CHECK_FLAG(binfo->flags, BGP_INFO_DAMPED)) { if (CHECK_FLAG(path->flags, BGP_PATH_DAMPED)) {
t_diff = t_now - bdi->suppress_time; t_diff = t_now - bdi->suppress_time;
if (t_diff >= damp->max_suppress_time) { if (t_diff >= damp->max_suppress_time) {
bgp_info_unset_flag(bdi->rn, binfo, BGP_INFO_DAMPED); bgp_path_info_unset_flag(bdi->rn, path,
BGP_PATH_DAMPED);
bgp_reuse_list_delete(bdi); bgp_reuse_list_delete(bdi);
BGP_DAMP_LIST_ADD(damp, bdi); BGP_DAMP_LIST_ADD(damp, bdi);
bdi->penalty = damp->reuse_limit; bdi->penalty = damp->reuse_limit;
bdi->suppress_time = 0; bdi->suppress_time = 0;
bdi->t_updated = t_now; bdi->t_updated = t_now;
/* Need to announce UPDATE once this binfo is usable /* Need to announce UPDATE once this path is usable
* again. */ * again. */
if (bdi->lastrecord == BGP_RECORD_UPDATE) if (bdi->lastrecord == BGP_RECORD_UPDATE)
return 1; return 1;
@ -323,7 +324,7 @@ int bgp_damp_scan(struct bgp_info *binfo, afi_t afi, safi_t safi)
bdi->penalty = bgp_damp_decay(t_diff, bdi->penalty); bdi->penalty = bgp_damp_decay(t_diff, bdi->penalty);
if (bdi->penalty <= damp->reuse_limit / 2.0) { if (bdi->penalty <= damp->reuse_limit / 2.0) {
/* release the bdi, bdi->binfo. */ /* release the bdi, bdi->path. */
bgp_damp_info_free(bdi, 1); bgp_damp_info_free(bdi, 1);
return 0; return 0;
} else } else
@ -334,23 +335,24 @@ int bgp_damp_scan(struct bgp_info *binfo, afi_t afi, safi_t safi)
void bgp_damp_info_free(struct bgp_damp_info *bdi, int withdraw) void bgp_damp_info_free(struct bgp_damp_info *bdi, int withdraw)
{ {
struct bgp_info *binfo; struct bgp_path_info *path;
if (!bdi) if (!bdi)
return; return;
binfo = bdi->binfo; path = bdi->path;
binfo->extra->damp_info = NULL; path->extra->damp_info = NULL;
if (CHECK_FLAG(binfo->flags, BGP_INFO_DAMPED)) if (CHECK_FLAG(path->flags, BGP_PATH_DAMPED))
bgp_reuse_list_delete(bdi); bgp_reuse_list_delete(bdi);
else else
BGP_DAMP_LIST_DEL(damp, bdi); BGP_DAMP_LIST_DEL(damp, bdi);
bgp_info_unset_flag(bdi->rn, binfo, BGP_INFO_HISTORY | BGP_INFO_DAMPED); bgp_path_info_unset_flag(bdi->rn, path,
BGP_PATH_HISTORY | BGP_PATH_DAMPED);
if (bdi->lastrecord == BGP_RECORD_WITHDRAW && withdraw) if (bdi->lastrecord == BGP_RECORD_WITHDRAW && withdraw)
bgp_info_delete(bdi->rn, binfo); bgp_path_info_delete(bdi->rn, path);
XFREE(MTYPE_BGP_DAMP_INFO, bdi); XFREE(MTYPE_BGP_DAMP_INFO, bdi);
} }
@ -588,7 +590,7 @@ static const char *bgp_get_reuse_time(unsigned int penalty, char *buf,
return buf; return buf;
} }
void bgp_damp_info_vty(struct vty *vty, struct bgp_info *binfo, void bgp_damp_info_vty(struct vty *vty, struct bgp_path_info *path,
json_object *json_path) json_object *json_path)
{ {
struct bgp_damp_info *bdi; struct bgp_damp_info *bdi;
@ -596,11 +598,11 @@ void bgp_damp_info_vty(struct vty *vty, struct bgp_info *binfo,
char timebuf[BGP_UPTIME_LEN]; char timebuf[BGP_UPTIME_LEN];
int penalty; int penalty;
if (!binfo->extra) if (!path->extra)
return; return;
/* BGP dampening information. */ /* BGP dampening information. */
bdi = binfo->extra->damp_info; bdi = path->extra->damp_info;
/* If dampening is not enabled or there is no dampening information, /* If dampening is not enabled or there is no dampening information,
return immediately. */ return immediately. */
@ -618,8 +620,8 @@ void bgp_damp_info_vty(struct vty *vty, struct bgp_info *binfo,
peer_uptime(bdi->start_time, timebuf, BGP_UPTIME_LEN, 1, peer_uptime(bdi->start_time, timebuf, BGP_UPTIME_LEN, 1,
json_path); json_path);
if (CHECK_FLAG(binfo->flags, BGP_INFO_DAMPED) if (CHECK_FLAG(path->flags, BGP_PATH_DAMPED)
&& !CHECK_FLAG(binfo->flags, BGP_INFO_HISTORY)) && !CHECK_FLAG(path->flags, BGP_PATH_HISTORY))
bgp_get_reuse_time(penalty, timebuf, BGP_UPTIME_LEN, 1, bgp_get_reuse_time(penalty, timebuf, BGP_UPTIME_LEN, 1,
json_path); json_path);
} else { } else {
@ -629,8 +631,8 @@ void bgp_damp_info_vty(struct vty *vty, struct bgp_info *binfo,
peer_uptime(bdi->start_time, timebuf, BGP_UPTIME_LEN, 0, peer_uptime(bdi->start_time, timebuf, BGP_UPTIME_LEN, 0,
json_path)); json_path));
if (CHECK_FLAG(binfo->flags, BGP_INFO_DAMPED) if (CHECK_FLAG(path->flags, BGP_PATH_DAMPED)
&& !CHECK_FLAG(binfo->flags, BGP_INFO_HISTORY)) && !CHECK_FLAG(path->flags, BGP_PATH_HISTORY))
vty_out(vty, ", reuse in %s", vty_out(vty, ", reuse in %s",
bgp_get_reuse_time(penalty, timebuf, bgp_get_reuse_time(penalty, timebuf,
BGP_UPTIME_LEN, 0, BGP_UPTIME_LEN, 0,
@ -640,7 +642,7 @@ void bgp_damp_info_vty(struct vty *vty, struct bgp_info *binfo,
} }
} }
const char *bgp_damp_reuse_time_vty(struct vty *vty, struct bgp_info *binfo, const char *bgp_damp_reuse_time_vty(struct vty *vty, struct bgp_path_info *path,
char *timebuf, size_t len, bool use_json, char *timebuf, size_t len, bool use_json,
json_object *json) json_object *json)
{ {
@ -648,11 +650,11 @@ const char *bgp_damp_reuse_time_vty(struct vty *vty, struct bgp_info *binfo,
time_t t_now, t_diff; time_t t_now, t_diff;
int penalty; int penalty;
if (!binfo->extra) if (!path->extra)
return NULL; return NULL;
/* BGP dampening information. */ /* BGP dampening information. */
bdi = binfo->extra->damp_info; bdi = path->extra->damp_info;
/* If dampening is not enabled or there is no dampening information, /* If dampening is not enabled or there is no dampening information,
return immediately. */ return immediately. */

View File

@ -43,8 +43,8 @@ struct bgp_damp_info {
/* Time of route start to be suppressed. */ /* Time of route start to be suppressed. */
time_t suppress_time; time_t suppress_time;
/* Back reference to bgp_info. */ /* Back reference to bgp_path_info. */
struct bgp_info *binfo; struct bgp_path_info *path;
/* Back reference to bgp_node. */ /* Back reference to bgp_node. */
struct bgp_node *rn; struct bgp_node *rn;
@ -130,18 +130,19 @@ struct bgp_damp_config {
extern int bgp_damp_enable(struct bgp *, afi_t, safi_t, time_t, unsigned int, extern int bgp_damp_enable(struct bgp *, afi_t, safi_t, time_t, unsigned int,
unsigned int, time_t); unsigned int, time_t);
extern int bgp_damp_disable(struct bgp *, afi_t, safi_t); extern int bgp_damp_disable(struct bgp *, afi_t, safi_t);
extern int bgp_damp_withdraw(struct bgp_info *, struct bgp_node *, afi_t, extern int bgp_damp_withdraw(struct bgp_path_info *path, struct bgp_node *rn,
safi_t, int); afi_t afi, safi_t safi, int attr_change);
extern int bgp_damp_update(struct bgp_info *, struct bgp_node *, afi_t, safi_t); extern int bgp_damp_update(struct bgp_path_info *path, struct bgp_node *rn,
extern int bgp_damp_scan(struct bgp_info *, afi_t, safi_t); afi_t afi, safi_t saff);
extern void bgp_damp_info_free(struct bgp_damp_info *, int); extern int bgp_damp_scan(struct bgp_path_info *path, afi_t afi, safi_t safi);
extern void bgp_damp_info_free(struct bgp_damp_info *path, int withdraw);
extern void bgp_damp_info_clean(void); extern void bgp_damp_info_clean(void);
extern int bgp_damp_decay(time_t, int); extern int bgp_damp_decay(time_t, int);
extern void bgp_config_write_damp(struct vty *); extern void bgp_config_write_damp(struct vty *);
extern void bgp_damp_info_vty(struct vty *, struct bgp_info *, extern void bgp_damp_info_vty(struct vty *vty, struct bgp_path_info *path,
json_object *json_path); json_object *json_path);
extern const char *bgp_damp_reuse_time_vty(struct vty *vty, extern const char *bgp_damp_reuse_time_vty(struct vty *vty,
struct bgp_info *binfo, struct bgp_path_info *path,
char *timebuf, size_t len, char *timebuf, size_t len,
bool use_json, json_object *json); bool use_json, json_object *json);
extern int bgp_show_dampening_parameters(struct vty *vty, afi_t, safi_t); extern int bgp_show_dampening_parameters(struct vty *vty, afi_t, safi_t);

View File

@ -299,9 +299,9 @@ static void bgp_dump_routes_index_table(struct bgp *bgp)
} }
static struct bgp_info *bgp_dump_route_node_record(int afi, struct bgp_node *rn, static struct bgp_path_info *
struct bgp_info *info, bgp_dump_route_node_record(int afi, struct bgp_node *rn,
unsigned int seq) struct bgp_path_info *path, unsigned int seq)
{ {
struct stream *obuf; struct stream *obuf;
size_t sizep; size_t sizep;
@ -349,18 +349,18 @@ static struct bgp_info *bgp_dump_route_node_record(int afi, struct bgp_node *rn,
stream_putw(obuf, 0); stream_putw(obuf, 0);
endp = stream_get_endp(obuf); endp = stream_get_endp(obuf);
for (; info; info = info->next) { for (; path; path = path->next) {
size_t cur_endp; size_t cur_endp;
/* Peer index */ /* Peer index */
stream_putw(obuf, info->peer->table_dump_index); stream_putw(obuf, path->peer->table_dump_index);
/* Originated */ /* Originated */
stream_putl(obuf, time(NULL) - (bgp_clock() - info->uptime)); stream_putl(obuf, time(NULL) - (bgp_clock() - path->uptime));
/* Dump attribute. */ /* Dump attribute. */
/* Skip prefix & AFI/SAFI for MP_NLRI */ /* Skip prefix & AFI/SAFI for MP_NLRI */
bgp_dump_routes_attr(obuf, info->attr, &rn->p); bgp_dump_routes_attr(obuf, path->attr, &rn->p);
cur_endp = stream_get_endp(obuf); cur_endp = stream_get_endp(obuf);
if (cur_endp > BGP_MAX_PACKET_SIZE + BGP_DUMP_MSG_HEADER if (cur_endp > BGP_MAX_PACKET_SIZE + BGP_DUMP_MSG_HEADER
@ -379,7 +379,7 @@ static struct bgp_info *bgp_dump_route_node_record(int afi, struct bgp_node *rn,
bgp_dump_set_size(obuf, MSG_TABLE_DUMP_V2); bgp_dump_set_size(obuf, MSG_TABLE_DUMP_V2);
fwrite(STREAM_DATA(obuf), stream_get_endp(obuf), 1, bgp_dump_routes.fp); fwrite(STREAM_DATA(obuf), stream_get_endp(obuf), 1, bgp_dump_routes.fp);
return info; return path;
} }
@ -387,7 +387,7 @@ static struct bgp_info *bgp_dump_route_node_record(int afi, struct bgp_node *rn,
static unsigned int bgp_dump_routes_func(int afi, int first_run, static unsigned int bgp_dump_routes_func(int afi, int first_run,
unsigned int seq) unsigned int seq)
{ {
struct bgp_info *info; struct bgp_path_info *path;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp *bgp; struct bgp *bgp;
struct bgp_table *table; struct bgp_table *table;
@ -410,9 +410,9 @@ static unsigned int bgp_dump_routes_func(int afi, int first_run,
table = bgp->rib[afi][SAFI_UNICAST]; table = bgp->rib[afi][SAFI_UNICAST];
for (rn = bgp_table_top(table); rn; rn = bgp_route_next(rn)) { for (rn = bgp_table_top(table); rn; rn = bgp_route_next(rn)) {
info = rn->info; path = rn->info;
while (info) { while (path) {
info = bgp_dump_route_node_record(afi, rn, info, seq); path = bgp_dump_route_node_record(afi, rn, path, seq);
seq++; seq++;
} }
} }

File diff suppressed because it is too large Load Diff

View File

@ -76,9 +76,9 @@ static inline int advertise_type5_routes(struct bgp *bgp_vrf,
} }
/* Flag if the route's parent is a EVPN route. */ /* Flag if the route's parent is a EVPN route. */
static inline int is_route_parent_evpn(struct bgp_info *ri) static inline int is_route_parent_evpn(struct bgp_path_info *ri)
{ {
struct bgp_info *parent_ri; struct bgp_path_info *parent_ri;
struct bgp_table *table; struct bgp_table *table;
struct bgp_node *rn; struct bgp_node *rn;
@ -89,7 +89,7 @@ static inline int is_route_parent_evpn(struct bgp_info *ri)
return 0; return 0;
/* See if the parent is of family L2VPN/EVPN */ /* See if the parent is of family L2VPN/EVPN */
parent_ri = (struct bgp_info *)ri->extra->parent; parent_ri = (struct bgp_path_info *)ri->extra->parent;
rn = parent_ri->net; rn = parent_ri->net;
if (!rn) if (!rn)
return 0; return 0;
@ -124,9 +124,9 @@ extern void bgp_evpn_encode_prefix(struct stream *s, struct prefix *p,
extern int bgp_nlri_parse_evpn(struct peer *peer, struct attr *attr, extern int bgp_nlri_parse_evpn(struct peer *peer, struct attr *attr,
struct bgp_nlri *packet, int withdraw); struct bgp_nlri *packet, int withdraw);
extern int bgp_evpn_import_route(struct bgp *bgp, afi_t afi, safi_t safi, extern int bgp_evpn_import_route(struct bgp *bgp, afi_t afi, safi_t safi,
struct prefix *p, struct bgp_info *ri); struct prefix *p, struct bgp_path_info *ri);
extern int bgp_evpn_unimport_route(struct bgp *bgp, afi_t afi, safi_t safi, extern int bgp_evpn_unimport_route(struct bgp *bgp, afi_t afi, safi_t safi,
struct prefix *p, struct bgp_info *ri); struct prefix *p, struct bgp_path_info *ri);
extern int bgp_filter_evpn_routes_upon_martian_nh_change(struct bgp *bgp); extern int bgp_filter_evpn_routes_upon_martian_nh_change(struct bgp *bgp);
extern int bgp_evpn_local_macip_del(struct bgp *bgp, vni_t vni, extern int bgp_evpn_local_macip_del(struct bgp *bgp, vni_t vni,
struct ethaddr *mac, struct ipaddr *ip); struct ethaddr *mac, struct ipaddr *ip);

View File

@ -536,7 +536,7 @@ static void show_esi_routes(struct bgp *bgp,
{ {
int header = 1; int header = 1;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *pi;
uint32_t prefix_cnt, path_cnt; uint32_t prefix_cnt, path_cnt;
uint64_t tbl_ver; uint64_t tbl_ver;
@ -573,13 +573,13 @@ static void show_esi_routes(struct bgp *bgp,
/* For EVPN, the prefix is displayed for each path (to fit in /* For EVPN, the prefix is displayed for each path (to fit in
* with code that already exists). * with code that already exists).
*/ */
for (ri = rn->info; ri; ri = ri->next) { for (pi = rn->info; pi; pi = pi->next) {
json_object *json_path = NULL; json_object *json_path = NULL;
if (json) if (json)
json_path = json_object_new_array(); json_path = json_object_new_array();
route_vty_out(vty, &rn->p, ri, 0, SAFI_EVPN, json_path); route_vty_out(vty, &rn->p, pi, 0, SAFI_EVPN, json_path);
if (json) if (json)
json_object_array_add(json_paths, json_path); json_object_array_add(json_paths, json_path);
@ -616,7 +616,7 @@ static void show_vni_routes(struct bgp *bgp, struct bgpevpn *vpn, int type,
json_object *json) json_object *json)
{ {
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *pi;
struct bgp_table *table; struct bgp_table *table;
int header = 1; int header = 1;
uint64_t tbl_ver; uint64_t tbl_ver;
@ -660,18 +660,18 @@ static void show_vni_routes(struct bgp *bgp, struct bgpevpn *vpn, int type,
/* For EVPN, the prefix is displayed for each path (to fit in /* For EVPN, the prefix is displayed for each path (to fit in
* with code that already exists). * with code that already exists).
*/ */
for (ri = rn->info; ri; ri = ri->next) { for (pi = rn->info; pi; pi = pi->next) {
json_object *json_path = NULL; json_object *json_path = NULL;
if (vtep_ip.s_addr if (vtep_ip.s_addr
&& !IPV4_ADDR_SAME(&(vtep_ip), && !IPV4_ADDR_SAME(&(vtep_ip),
&(ri->attr->nexthop))) &(pi->attr->nexthop)))
continue; continue;
if (json) if (json)
json_path = json_object_new_array(); json_path = json_object_new_array();
route_vty_out(vty, &rn->p, ri, 0, SAFI_EVPN, json_path); route_vty_out(vty, &rn->p, pi, 0, SAFI_EVPN, json_path);
if (json) if (json)
json_object_array_add(json_paths, json_path); json_object_array_add(json_paths, json_path);
@ -990,7 +990,7 @@ static int bgp_show_ethernet_vpn(struct vty *vty, struct prefix_rd *prd,
struct bgp_table *table; struct bgp_table *table;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_node *rm; struct bgp_node *rm;
struct bgp_info *ri; struct bgp_path_info *pi;
int rd_header; int rd_header;
int header = 1; int header = 1;
@ -1046,14 +1046,14 @@ static int bgp_show_ethernet_vpn(struct vty *vty, struct prefix_rd *prd,
tbl_ver = table->version; tbl_ver = table->version;
for (rm = bgp_table_top(table); rm; rm = bgp_route_next(rm)) for (rm = bgp_table_top(table); rm; rm = bgp_route_next(rm))
for (ri = rm->info; ri; ri = ri->next) { for (pi = rm->info; pi; pi = pi->next) {
total_count++; total_count++;
if (type == bgp_show_type_neighbor) { if (type == bgp_show_type_neighbor) {
union sockunion *su = output_arg; union sockunion *su = output_arg;
if (ri->peer->su_remote == NULL if (pi->peer->su_remote == NULL
|| !sockunion_same( || !sockunion_same(
ri->peer->su_remote, su)) pi->peer->su_remote, su))
continue; continue;
} }
if (header == 0) { if (header == 0) {
@ -1162,14 +1162,14 @@ static int bgp_show_ethernet_vpn(struct vty *vty, struct prefix_rd *prd,
else else
json_array = NULL; json_array = NULL;
if (option == SHOW_DISPLAY_TAGS) if (option == SHOW_DISPLAY_TAGS)
route_vty_out_tag(vty, &rm->p, ri, 0, route_vty_out_tag(vty, &rm->p, pi, 0,
SAFI_EVPN, SAFI_EVPN,
json_array); json_array);
else if (option == SHOW_DISPLAY_OVERLAY) else if (option == SHOW_DISPLAY_OVERLAY)
route_vty_out_overlay(vty, &rm->p, ri, route_vty_out_overlay(vty, &rm->p, pi,
0, json_array); 0, json_array);
else else
route_vty_out(vty, &rm->p, ri, 0, route_vty_out(vty, &rm->p, pi, 0,
SAFI_EVPN, json_array); SAFI_EVPN, json_array);
output_count++; output_count++;
} }
@ -2017,7 +2017,7 @@ static void evpn_show_route_vni_multicast(struct vty *vty, struct bgp *bgp,
struct bgpevpn *vpn; struct bgpevpn *vpn;
struct prefix_evpn p; struct prefix_evpn p;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *pi;
uint32_t path_cnt = 0; uint32_t path_cnt = 0;
afi_t afi; afi_t afi;
safi_t safi; safi_t safi;
@ -2049,13 +2049,13 @@ static void evpn_show_route_vni_multicast(struct vty *vty, struct bgp *bgp,
route_vty_out_detail_header(vty, bgp, rn, NULL, afi, safi, json); route_vty_out_detail_header(vty, bgp, rn, NULL, afi, safi, json);
/* Display each path for this prefix. */ /* Display each path for this prefix. */
for (ri = rn->info; ri; ri = ri->next) { for (pi = rn->info; pi; pi = pi->next) {
json_object *json_path = NULL; json_object *json_path = NULL;
if (json) if (json)
json_path = json_object_new_array(); json_path = json_object_new_array();
route_vty_out_detail(vty, bgp, &rn->p, ri, afi, safi, route_vty_out_detail(vty, bgp, &rn->p, pi, afi, safi,
json_path); json_path);
if (json) if (json)
@ -2086,7 +2086,7 @@ static void evpn_show_route_vni_macip(struct vty *vty, struct bgp *bgp,
struct bgpevpn *vpn; struct bgpevpn *vpn;
struct prefix_evpn p; struct prefix_evpn p;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *pi;
uint32_t path_cnt = 0; uint32_t path_cnt = 0;
afi_t afi; afi_t afi;
safi_t safi; safi_t safi;
@ -2119,13 +2119,13 @@ static void evpn_show_route_vni_macip(struct vty *vty, struct bgp *bgp,
route_vty_out_detail_header(vty, bgp, rn, NULL, afi, safi, json); route_vty_out_detail_header(vty, bgp, rn, NULL, afi, safi, json);
/* Display each path for this prefix. */ /* Display each path for this prefix. */
for (ri = rn->info; ri; ri = ri->next) { for (pi = rn->info; pi; pi = pi->next) {
json_object *json_path = NULL; json_object *json_path = NULL;
if (json) if (json)
json_path = json_object_new_array(); json_path = json_object_new_array();
route_vty_out_detail(vty, bgp, &rn->p, ri, afi, safi, route_vty_out_detail(vty, bgp, &rn->p, pi, afi, safi,
json_path); json_path);
if (json) if (json)
@ -2196,7 +2196,7 @@ static void evpn_show_route_rd_macip(struct vty *vty, struct bgp *bgp,
{ {
struct prefix_evpn p; struct prefix_evpn p;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *pi;
afi_t afi; afi_t afi;
safi_t safi; safi_t safi;
uint32_t path_cnt = 0; uint32_t path_cnt = 0;
@ -2226,13 +2226,13 @@ static void evpn_show_route_rd_macip(struct vty *vty, struct bgp *bgp,
json_paths = json_object_new_array(); json_paths = json_object_new_array();
/* Display each path for this prefix. */ /* Display each path for this prefix. */
for (ri = rn->info; ri; ri = ri->next) { for (pi = rn->info; pi; pi = pi->next) {
json_object *json_path = NULL; json_object *json_path = NULL;
if (json) if (json)
json_path = json_object_new_array(); json_path = json_object_new_array();
route_vty_out_detail(vty, bgp, &rn->p, ri, afi, safi, route_vty_out_detail(vty, bgp, &rn->p, pi, afi, safi,
json_path); json_path);
if (json) if (json)
@ -2262,7 +2262,7 @@ static void evpn_show_route_rd(struct vty *vty, struct bgp *bgp,
struct bgp_node *rd_rn; struct bgp_node *rd_rn;
struct bgp_table *table; struct bgp_table *table;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *pi;
int rd_header = 1; int rd_header = 1;
afi_t afi; afi_t afi;
safi_t safi; safi_t safi;
@ -2330,13 +2330,13 @@ static void evpn_show_route_rd(struct vty *vty, struct bgp *bgp,
json_paths = json_object_new_array(); json_paths = json_object_new_array();
/* Display each path for this prefix. */ /* Display each path for this prefix. */
for (ri = rn->info; ri; ri = ri->next) { for (pi = rn->info; pi; pi = pi->next) {
json_object *json_path = NULL; json_object *json_path = NULL;
if (json) if (json)
json_path = json_object_new_array(); json_path = json_object_new_array();
route_vty_out_detail(vty, bgp, &rn->p, ri, afi, safi, route_vty_out_detail(vty, bgp, &rn->p, pi, afi, safi,
json_path); json_path);
if (json) if (json)
@ -2383,7 +2383,7 @@ static void evpn_show_all_routes(struct vty *vty, struct bgp *bgp, int type,
struct bgp_node *rd_rn; struct bgp_node *rd_rn;
struct bgp_table *table; struct bgp_table *table;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *pi;
int header = 1; int header = 1;
int rd_header; int rd_header;
afi_t afi; afi_t afi;
@ -2467,7 +2467,7 @@ static void evpn_show_all_routes(struct vty *vty, struct bgp *bgp, int type,
* fit in * fit in
* with code that already exists). * with code that already exists).
*/ */
for (ri = rn->info; ri; ri = ri->next) { for (pi = rn->info; pi; pi = pi->next) {
json_object *json_path = NULL; json_object *json_path = NULL;
path_cnt++; path_cnt++;
add_prefix_to_json = 1; add_prefix_to_json = 1;
@ -2476,7 +2476,7 @@ static void evpn_show_all_routes(struct vty *vty, struct bgp *bgp, int type,
if (json) if (json)
json_path = json_object_new_array(); json_path = json_object_new_array();
route_vty_out(vty, &rn->p, ri, 0, SAFI_EVPN, route_vty_out(vty, &rn->p, pi, 0, SAFI_EVPN,
json_path); json_path);
if (json) if (json)

View File

@ -44,8 +44,8 @@ extern void bgp_fs_nlri_get_string(unsigned char *nlri_content, size_t len,
json_object *json_path); json_object *json_path);
extern void route_vty_out_flowspec(struct vty *vty, struct prefix *p, extern void route_vty_out_flowspec(struct vty *vty, struct prefix *p,
struct bgp_info *binfo, struct bgp_path_info *path, int display,
int display, json_object *json_paths); json_object *json_paths);
extern int bgp_fs_config_write_pbr(struct vty *vty, struct bgp *bgp, extern int bgp_fs_config_write_pbr(struct vty *vty, struct bgp *bgp,
afi_t afi, safi_t safi); afi_t afi, safi_t safi);

View File

@ -253,8 +253,8 @@ void bgp_fs_nlri_get_string(unsigned char *nlri_content, size_t len,
} }
void route_vty_out_flowspec(struct vty *vty, struct prefix *p, void route_vty_out_flowspec(struct vty *vty, struct prefix *p,
struct bgp_info *binfo, struct bgp_path_info *path, int display,
int display, json_object *json_paths) json_object *json_paths)
{ {
struct attr *attr; struct attr *attr;
char return_string[BGP_FLOWSPEC_STRING_DISPLAY_MAX]; char return_string[BGP_FLOWSPEC_STRING_DISPLAY_MAX];
@ -274,9 +274,9 @@ void route_vty_out_flowspec(struct vty *vty, struct prefix *p,
else else
json_nlri_path = json_paths; json_nlri_path = json_paths;
} }
if (display == NLRI_STRING_FORMAT_LARGE && binfo) if (display == NLRI_STRING_FORMAT_LARGE && path)
vty_out(vty, "BGP flowspec entry: (flags 0x%x)\n", vty_out(vty, "BGP flowspec entry: (flags 0x%x)\n",
binfo->flags); path->flags);
bgp_fs_nlri_get_string((unsigned char *) bgp_fs_nlri_get_string((unsigned char *)
p->u.prefix_flowspec.ptr, p->u.prefix_flowspec.ptr,
p->u.prefix_flowspec.prefixlen, p->u.prefix_flowspec.prefixlen,
@ -292,11 +292,11 @@ void route_vty_out_flowspec(struct vty *vty, struct prefix *p,
else if (json_paths && display == NLRI_STRING_FORMAT_JSON) else if (json_paths && display == NLRI_STRING_FORMAT_JSON)
json_object_array_add(json_paths, json_nlri_path); json_object_array_add(json_paths, json_nlri_path);
} }
if (!binfo) if (!path)
return; return;
if (binfo->attr && binfo->attr->ecommunity) { if (path->attr && path->attr->ecommunity) {
/* Print attribute */ /* Print attribute */
attr = binfo->attr; attr = path->attr;
s = ecommunity_ecom2str(attr->ecommunity, s = ecommunity_ecom2str(attr->ecommunity,
ECOMMUNITY_FORMAT_ROUTE_MAP, 0); ECOMMUNITY_FORMAT_ROUTE_MAP, 0);
if (!s) if (!s)
@ -318,7 +318,7 @@ void route_vty_out_flowspec(struct vty *vty, struct prefix *p,
vty_out(vty, "\tNH %-16s\n", inet_ntoa(attr->nexthop)); vty_out(vty, "\tNH %-16s\n", inet_ntoa(attr->nexthop));
XFREE(MTYPE_ECOMMUNITY_STR, s); XFREE(MTYPE_ECOMMUNITY_STR, s);
} }
peer_uptime(binfo->uptime, timebuf, BGP_UPTIME_LEN, 0, NULL); peer_uptime(path->uptime, timebuf, BGP_UPTIME_LEN, 0, NULL);
if (display == NLRI_STRING_FORMAT_LARGE) { if (display == NLRI_STRING_FORMAT_LARGE) {
vty_out(vty, "\treceived for %8s\n", timebuf); vty_out(vty, "\treceived for %8s\n", timebuf);
} else if (json_paths) { } else if (json_paths) {
@ -329,7 +329,8 @@ void route_vty_out_flowspec(struct vty *vty, struct prefix *p,
json_object_array_add(json_paths, json_time_path); json_object_array_add(json_paths, json_time_path);
} }
if (display == NLRI_STRING_FORMAT_LARGE) { if (display == NLRI_STRING_FORMAT_LARGE) {
struct bgp_info_extra *extra = bgp_info_extra_get(binfo); struct bgp_path_info_extra *extra =
bgp_path_info_extra_get(path);
if (extra->bgp_fs_pbr) { if (extra->bgp_fs_pbr) {
struct listnode *node; struct listnode *node;
@ -368,7 +369,7 @@ int bgp_show_table_flowspec(struct vty *vty, struct bgp *bgp, afi_t afi,
void *output_arg, bool use_json, int is_last, void *output_arg, bool use_json, int is_last,
unsigned long *output_cum, unsigned long *total_cum) unsigned long *output_cum, unsigned long *total_cum)
{ {
struct bgp_info *ri; struct bgp_path_info *pi;
struct bgp_node *rn; struct bgp_node *rn;
unsigned long total_count = 0; unsigned long total_count = 0;
json_object *json_paths = NULL; json_object *json_paths = NULL;
@ -384,12 +385,10 @@ int bgp_show_table_flowspec(struct vty *vty, struct bgp *bgp, afi_t afi,
json_paths = json_object_new_array(); json_paths = json_object_new_array();
display = NLRI_STRING_FORMAT_JSON; display = NLRI_STRING_FORMAT_JSON;
} }
for (ri = rn->info; ri; ri = ri->next) { for (pi = rn->info; pi; pi = pi->next) {
total_count++; total_count++;
route_vty_out_flowspec(vty, &rn->p, route_vty_out_flowspec(vty, &rn->p, pi, display,
ri, display,
json_paths); json_paths);
} }
if (use_json) { if (use_json) {
vty_out(vty, "%s\n", vty_out(vty, "%s\n",

View File

@ -94,18 +94,18 @@ int bgp_parse_fec_update(void)
return 1; return 1;
} }
mpls_label_t bgp_adv_label(struct bgp_node *rn, struct bgp_info *ri, mpls_label_t bgp_adv_label(struct bgp_node *rn, struct bgp_path_info *pi,
struct peer *to, afi_t afi, safi_t safi) struct peer *to, afi_t afi, safi_t safi)
{ {
struct peer *from; struct peer *from;
mpls_label_t remote_label; mpls_label_t remote_label;
int reflect; int reflect;
if (!rn || !ri || !to) if (!rn || !pi || !to)
return MPLS_INVALID_LABEL; return MPLS_INVALID_LABEL;
remote_label = ri->extra ? ri->extra->label[0] : MPLS_INVALID_LABEL; remote_label = pi->extra ? pi->extra->label[0] : MPLS_INVALID_LABEL;
from = ri->peer; from = pi->peer;
reflect = reflect =
((from->sort == BGP_PEER_IBGP) && (to->sort == BGP_PEER_IBGP)); ((from->sort == BGP_PEER_IBGP) && (to->sort == BGP_PEER_IBGP));
@ -120,7 +120,8 @@ mpls_label_t bgp_adv_label(struct bgp_node *rn, struct bgp_info *ri,
return rn->local_label; return rn->local_label;
} }
void bgp_reg_dereg_for_label(struct bgp_node *rn, struct bgp_info *ri, int reg) void bgp_reg_dereg_for_label(struct bgp_node *rn, struct bgp_path_info *pi,
int reg)
{ {
struct stream *s; struct stream *s;
struct prefix *p; struct prefix *p;
@ -142,11 +143,11 @@ void bgp_reg_dereg_for_label(struct bgp_node *rn, struct bgp_info *ri, int reg)
stream_putw(s, PREFIX_FAMILY(p)); stream_putw(s, PREFIX_FAMILY(p));
stream_put_prefix(s, p); stream_put_prefix(s, p);
if (reg) { if (reg) {
assert(ri); assert(pi);
if (ri->attr->flag & ATTR_FLAG_BIT(BGP_ATTR_PREFIX_SID)) { if (pi->attr->flag & ATTR_FLAG_BIT(BGP_ATTR_PREFIX_SID)) {
if (ri->attr->label_index != BGP_INVALID_LABEL_INDEX) { if (pi->attr->label_index != BGP_INVALID_LABEL_INDEX) {
flags |= ZEBRA_FEC_REGISTER_LABEL_INDEX; flags |= ZEBRA_FEC_REGISTER_LABEL_INDEX;
stream_putl(s, ri->attr->label_index); stream_putl(s, pi->attr->label_index);
} }
} }
SET_FLAG(rn->flags, BGP_NODE_REGISTERED_FOR_LABEL); SET_FLAG(rn->flags, BGP_NODE_REGISTERED_FOR_LABEL);

View File

@ -27,13 +27,13 @@
#define BGP_PREVENT_VRF_2_VRF_LEAK 0xFFFFFFFE #define BGP_PREVENT_VRF_2_VRF_LEAK 0xFFFFFFFE
struct bgp_node; struct bgp_node;
struct bgp_info; struct bgp_path_info;
struct peer; struct peer;
extern void bgp_reg_dereg_for_label(struct bgp_node *rn, struct bgp_info *ri, extern void bgp_reg_dereg_for_label(struct bgp_node *rn,
int reg); struct bgp_path_info *pi, int reg);
extern int bgp_parse_fec_update(void); extern int bgp_parse_fec_update(void);
extern mpls_label_t bgp_adv_label(struct bgp_node *rn, struct bgp_info *ri, extern mpls_label_t bgp_adv_label(struct bgp_node *rn, struct bgp_path_info *pi,
struct peer *to, afi_t afi, safi_t safi); struct peer *to, afi_t afi, safi_t safi);
extern int bgp_nlri_parse_label(struct peer *peer, struct attr *attr, extern int bgp_nlri_parse_label(struct peer *peer, struct attr *attr,
@ -85,9 +85,9 @@ static inline void bgp_unset_valid_label(mpls_label_t *label)
} }
static inline void bgp_register_for_label(struct bgp_node *rn, static inline void bgp_register_for_label(struct bgp_node *rn,
struct bgp_info *ri) struct bgp_path_info *pi)
{ {
bgp_reg_dereg_for_label(rn, ri, 1); bgp_reg_dereg_for_label(rn, pi, 1);
} }
static inline void bgp_unregister_for_label(struct bgp_node *rn) static inline void bgp_unregister_for_label(struct bgp_node *rn)

View File

@ -113,45 +113,47 @@ static int bgp_interface_same(struct interface *ifp1, struct interface *ifp2)
/* /*
* bgp_info_nexthop_cmp * bgp_path_info_nexthop_cmp
* *
* Compare the nexthops of two paths. Return value is less than, equal to, * Compare the nexthops of two paths. Return value is less than, equal to,
* or greater than zero if bi1 is respectively less than, equal to, * or greater than zero if bpi1 is respectively less than, equal to,
* or greater than bi2. * or greater than bpi2.
*/ */
int bgp_info_nexthop_cmp(struct bgp_info *bi1, struct bgp_info *bi2) int bgp_path_info_nexthop_cmp(struct bgp_path_info *bpi1,
struct bgp_path_info *bpi2)
{ {
int compare; int compare;
struct in6_addr addr1, addr2; struct in6_addr addr1, addr2;
compare = IPV4_ADDR_CMP(&bi1->attr->nexthop, &bi2->attr->nexthop); compare = IPV4_ADDR_CMP(&bpi1->attr->nexthop, &bpi2->attr->nexthop);
if (!compare) { if (!compare) {
if (bi1->attr->mp_nexthop_len == bi2->attr->mp_nexthop_len) { if (bpi1->attr->mp_nexthop_len == bpi2->attr->mp_nexthop_len) {
switch (bi1->attr->mp_nexthop_len) { switch (bpi1->attr->mp_nexthop_len) {
case BGP_ATTR_NHLEN_IPV4: case BGP_ATTR_NHLEN_IPV4:
case BGP_ATTR_NHLEN_VPNV4: case BGP_ATTR_NHLEN_VPNV4:
compare = IPV4_ADDR_CMP( compare = IPV4_ADDR_CMP(
&bi1->attr->mp_nexthop_global_in, &bpi1->attr->mp_nexthop_global_in,
&bi2->attr->mp_nexthop_global_in); &bpi2->attr->mp_nexthop_global_in);
break; break;
case BGP_ATTR_NHLEN_IPV6_GLOBAL: case BGP_ATTR_NHLEN_IPV6_GLOBAL:
case BGP_ATTR_NHLEN_VPNV6_GLOBAL: case BGP_ATTR_NHLEN_VPNV6_GLOBAL:
compare = IPV6_ADDR_CMP( compare = IPV6_ADDR_CMP(
&bi1->attr->mp_nexthop_global, &bpi1->attr->mp_nexthop_global,
&bi2->attr->mp_nexthop_global); &bpi2->attr->mp_nexthop_global);
break; break;
case BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL: case BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL:
addr1 = (bi1->attr->mp_nexthop_prefer_global) addr1 = (bpi1->attr->mp_nexthop_prefer_global)
? bi1->attr->mp_nexthop_global ? bpi1->attr->mp_nexthop_global
: bi1->attr->mp_nexthop_local; : bpi1->attr->mp_nexthop_local;
addr2 = (bi2->attr->mp_nexthop_prefer_global) addr2 = (bpi2->attr->mp_nexthop_prefer_global)
? bi2->attr->mp_nexthop_global ? bpi2->attr->mp_nexthop_global
: bi2->attr->mp_nexthop_local; : bpi2->attr->mp_nexthop_local;
if (!bi1->attr->mp_nexthop_prefer_global if (!bpi1->attr->mp_nexthop_prefer_global
&& !bi2->attr->mp_nexthop_prefer_global) && !bpi2->attr->mp_nexthop_prefer_global)
compare = !bgp_interface_same( compare = !bgp_interface_same(
bi1->peer->ifp, bi2->peer->ifp); bpi1->peer->ifp,
bpi2->peer->ifp);
if (!compare) if (!compare)
compare = IPV6_ADDR_CMP(&addr1, &addr2); compare = IPV6_ADDR_CMP(&addr1, &addr2);
@ -163,14 +165,15 @@ int bgp_info_nexthop_cmp(struct bgp_info *bi1, struct bgp_info *bi2)
* link-local * link-local
* nexthops but another IPv6 peer only sends you global * nexthops but another IPv6 peer only sends you global
*/ */
else if (bi1->attr->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL else if (bpi1->attr->mp_nexthop_len
|| bi1->attr->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL
|| bpi1->attr->mp_nexthop_len
== BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL) { == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL) {
compare = IPV6_ADDR_CMP(&bi1->attr->mp_nexthop_global, compare = IPV6_ADDR_CMP(&bpi1->attr->mp_nexthop_global,
&bi2->attr->mp_nexthop_global); &bpi2->attr->mp_nexthop_global);
if (!compare) { if (!compare) {
if (bi1->attr->mp_nexthop_len if (bpi1->attr->mp_nexthop_len
< bi2->attr->mp_nexthop_len) < bpi2->attr->mp_nexthop_len)
compare = -1; compare = -1;
else else
compare = 1; compare = 1;
@ -182,7 +185,7 @@ int bgp_info_nexthop_cmp(struct bgp_info *bi1, struct bgp_info *bi2)
} }
/* /*
* bgp_info_mpath_cmp * bgp_path_info_mpath_cmp
* *
* This function determines our multipath list ordering. By ordering * This function determines our multipath list ordering. By ordering
* the list we can deterministically select which paths are included * the list we can deterministically select which paths are included
@ -193,26 +196,26 @@ int bgp_info_nexthop_cmp(struct bgp_info *bi1, struct bgp_info *bi2)
* The order of paths is determined first by received nexthop, and then * The order of paths is determined first by received nexthop, and then
* by peer address if the nexthops are the same. * by peer address if the nexthops are the same.
*/ */
static int bgp_info_mpath_cmp(void *val1, void *val2) static int bgp_path_info_mpath_cmp(void *val1, void *val2)
{ {
struct bgp_info *bi1, *bi2; struct bgp_path_info *bpi1, *bpi2;
int compare; int compare;
bi1 = val1; bpi1 = val1;
bi2 = val2; bpi2 = val2;
compare = bgp_info_nexthop_cmp(bi1, bi2); compare = bgp_path_info_nexthop_cmp(bpi1, bpi2);
if (!compare) { if (!compare) {
if (!bi1->peer->su_remote && !bi2->peer->su_remote) if (!bpi1->peer->su_remote && !bpi2->peer->su_remote)
compare = 0; compare = 0;
else if (!bi1->peer->su_remote) else if (!bpi1->peer->su_remote)
compare = 1; compare = 1;
else if (!bi2->peer->su_remote) else if (!bpi2->peer->su_remote)
compare = -1; compare = -1;
else else
compare = sockunion_cmp(bi1->peer->su_remote, compare = sockunion_cmp(bpi1->peer->su_remote,
bi2->peer->su_remote); bpi2->peer->su_remote);
} }
return compare; return compare;
@ -228,7 +231,7 @@ void bgp_mp_list_init(struct list *mp_list)
{ {
assert(mp_list); assert(mp_list);
memset(mp_list, 0, sizeof(struct list)); memset(mp_list, 0, sizeof(struct list));
mp_list->cmp = bgp_info_mpath_cmp; mp_list->cmp = bgp_path_info_mpath_cmp;
} }
/* /*
@ -247,31 +250,31 @@ void bgp_mp_list_clear(struct list *mp_list)
* *
* Adds a multipath entry to the mp_list * Adds a multipath entry to the mp_list
*/ */
void bgp_mp_list_add(struct list *mp_list, struct bgp_info *mpinfo) void bgp_mp_list_add(struct list *mp_list, struct bgp_path_info *mpinfo)
{ {
assert(mp_list && mpinfo); assert(mp_list && mpinfo);
listnode_add_sort(mp_list, mpinfo); listnode_add_sort(mp_list, mpinfo);
} }
/* /*
* bgp_info_mpath_new * bgp_path_info_mpath_new
* *
* Allocate and zero memory for a new bgp_info_mpath element * Allocate and zero memory for a new bgp_path_info_mpath element
*/ */
static struct bgp_info_mpath *bgp_info_mpath_new(void) static struct bgp_path_info_mpath *bgp_path_info_mpath_new(void)
{ {
struct bgp_info_mpath *new_mpath; struct bgp_path_info_mpath *new_mpath;
new_mpath = new_mpath = XCALLOC(MTYPE_BGP_MPATH_INFO,
XCALLOC(MTYPE_BGP_MPATH_INFO, sizeof(struct bgp_info_mpath)); sizeof(struct bgp_path_info_mpath));
return new_mpath; return new_mpath;
} }
/* /*
* bgp_info_mpath_free * bgp_path_info_mpath_free
* *
* Release resources for a bgp_info_mpath element and zero out pointer * Release resources for a bgp_path_info_mpath element and zero out pointer
*/ */
void bgp_info_mpath_free(struct bgp_info_mpath **mpath) void bgp_path_info_mpath_free(struct bgp_path_info_mpath **mpath)
{ {
if (mpath && *mpath) { if (mpath && *mpath) {
if ((*mpath)->mp_attr) if ((*mpath)->mp_attr)
@ -282,37 +285,38 @@ void bgp_info_mpath_free(struct bgp_info_mpath **mpath)
} }
/* /*
* bgp_info_mpath_get * bgp_path_info_mpath_get
* *
* Fetch the mpath element for the given bgp_info. Used for * Fetch the mpath element for the given bgp_path_info. Used for
* doing lazy allocation. * doing lazy allocation.
*/ */
static struct bgp_info_mpath *bgp_info_mpath_get(struct bgp_info *binfo) static struct bgp_path_info_mpath *
bgp_path_info_mpath_get(struct bgp_path_info *path)
{ {
struct bgp_info_mpath *mpath; struct bgp_path_info_mpath *mpath;
if (!binfo->mpath) { if (!path->mpath) {
mpath = bgp_info_mpath_new(); mpath = bgp_path_info_mpath_new();
if (!mpath) if (!mpath)
return NULL; return NULL;
binfo->mpath = mpath; path->mpath = mpath;
mpath->mp_info = binfo; mpath->mp_info = path;
} }
return binfo->mpath; return path->mpath;
} }
/* /*
* bgp_info_mpath_enqueue * bgp_path_info_mpath_enqueue
* *
* Enqueue a path onto the multipath list given the previous multipath * Enqueue a path onto the multipath list given the previous multipath
* list entry * list entry
*/ */
static void bgp_info_mpath_enqueue(struct bgp_info *prev_info, static void bgp_path_info_mpath_enqueue(struct bgp_path_info *prev_info,
struct bgp_info *binfo) struct bgp_path_info *path)
{ {
struct bgp_info_mpath *prev, *mpath; struct bgp_path_info_mpath *prev, *mpath;
prev = bgp_info_mpath_get(prev_info); prev = bgp_path_info_mpath_get(prev_info);
mpath = bgp_info_mpath_get(binfo); mpath = bgp_path_info_mpath_get(path);
if (!prev || !mpath) if (!prev || !mpath)
return; return;
@ -322,17 +326,17 @@ static void bgp_info_mpath_enqueue(struct bgp_info *prev_info,
prev->mp_next->mp_prev = mpath; prev->mp_next->mp_prev = mpath;
prev->mp_next = mpath; prev->mp_next = mpath;
SET_FLAG(binfo->flags, BGP_INFO_MULTIPATH); SET_FLAG(path->flags, BGP_PATH_MULTIPATH);
} }
/* /*
* bgp_info_mpath_dequeue * bgp_path_info_mpath_dequeue
* *
* Remove a path from the multipath list * Remove a path from the multipath list
*/ */
void bgp_info_mpath_dequeue(struct bgp_info *binfo) void bgp_path_info_mpath_dequeue(struct bgp_path_info *path)
{ {
struct bgp_info_mpath *mpath = binfo->mpath; struct bgp_path_info_mpath *mpath = path->mpath;
if (!mpath) if (!mpath)
return; return;
if (mpath->mp_prev) if (mpath->mp_prev)
@ -340,101 +344,105 @@ void bgp_info_mpath_dequeue(struct bgp_info *binfo)
if (mpath->mp_next) if (mpath->mp_next)
mpath->mp_next->mp_prev = mpath->mp_prev; mpath->mp_next->mp_prev = mpath->mp_prev;
mpath->mp_next = mpath->mp_prev = NULL; mpath->mp_next = mpath->mp_prev = NULL;
UNSET_FLAG(binfo->flags, BGP_INFO_MULTIPATH); UNSET_FLAG(path->flags, BGP_PATH_MULTIPATH);
} }
/* /*
* bgp_info_mpath_next * bgp_path_info_mpath_next
* *
* Given a bgp_info, return the next multipath entry * Given a bgp_path_info, return the next multipath entry
*/ */
struct bgp_info *bgp_info_mpath_next(struct bgp_info *binfo) struct bgp_path_info *bgp_path_info_mpath_next(struct bgp_path_info *path)
{ {
if (!binfo->mpath || !binfo->mpath->mp_next) if (!path->mpath || !path->mpath->mp_next)
return NULL; return NULL;
return binfo->mpath->mp_next->mp_info; return path->mpath->mp_next->mp_info;
} }
/* /*
* bgp_info_mpath_first * bgp_path_info_mpath_first
* *
* Given bestpath bgp_info, return the first multipath entry. * Given bestpath bgp_path_info, return the first multipath entry.
*/ */
struct bgp_info *bgp_info_mpath_first(struct bgp_info *binfo) struct bgp_path_info *bgp_path_info_mpath_first(struct bgp_path_info *path)
{ {
return bgp_info_mpath_next(binfo); return bgp_path_info_mpath_next(path);
} }
/* /*
* bgp_info_mpath_count * bgp_path_info_mpath_count
* *
* Given the bestpath bgp_info, return the number of multipath entries * Given the bestpath bgp_path_info, return the number of multipath entries
*/ */
uint32_t bgp_info_mpath_count(struct bgp_info *binfo) uint32_t bgp_path_info_mpath_count(struct bgp_path_info *path)
{ {
if (!binfo->mpath) if (!path->mpath)
return 0; return 0;
return binfo->mpath->mp_count; return path->mpath->mp_count;
} }
/* /*
* bgp_info_mpath_count_set * bgp_path_info_mpath_count_set
* *
* Sets the count of multipaths into bestpath's mpath element * Sets the count of multipaths into bestpath's mpath element
*/ */
static void bgp_info_mpath_count_set(struct bgp_info *binfo, uint32_t count) static void bgp_path_info_mpath_count_set(struct bgp_path_info *path,
uint32_t count)
{ {
struct bgp_info_mpath *mpath; struct bgp_path_info_mpath *mpath;
if (!count && !binfo->mpath) if (!count && !path->mpath)
return; return;
mpath = bgp_info_mpath_get(binfo); mpath = bgp_path_info_mpath_get(path);
if (!mpath) if (!mpath)
return; return;
mpath->mp_count = count; mpath->mp_count = count;
} }
/* /*
* bgp_info_mpath_attr * bgp_path_info_mpath_attr
* *
* Given bestpath bgp_info, return aggregated attribute set used * Given bestpath bgp_path_info, return aggregated attribute set used
* for advertising the multipath route * for advertising the multipath route
*/ */
struct attr *bgp_info_mpath_attr(struct bgp_info *binfo) struct attr *bgp_path_info_mpath_attr(struct bgp_path_info *path)
{ {
if (!binfo->mpath) if (!path->mpath)
return NULL; return NULL;
return binfo->mpath->mp_attr; return path->mpath->mp_attr;
} }
/* /*
* bgp_info_mpath_attr_set * bgp_path_info_mpath_attr_set
* *
* Sets the aggregated attribute into bestpath's mpath element * Sets the aggregated attribute into bestpath's mpath element
*/ */
static void bgp_info_mpath_attr_set(struct bgp_info *binfo, struct attr *attr) static void bgp_path_info_mpath_attr_set(struct bgp_path_info *path,
struct attr *attr)
{ {
struct bgp_info_mpath *mpath; struct bgp_path_info_mpath *mpath;
if (!attr && !binfo->mpath) if (!attr && !path->mpath)
return; return;
mpath = bgp_info_mpath_get(binfo); mpath = bgp_path_info_mpath_get(path);
if (!mpath) if (!mpath)
return; return;
mpath->mp_attr = attr; mpath->mp_attr = attr;
} }
/* /*
* bgp_info_mpath_update * bgp_path_info_mpath_update
* *
* Compare and sync up the multipath list with the mp_list generated by * Compare and sync up the multipath list with the mp_list generated by
* bgp_best_selection * bgp_best_selection
*/ */
void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best, void bgp_path_info_mpath_update(struct bgp_node *rn,
struct bgp_info *old_best, struct list *mp_list, struct bgp_path_info *new_best,
struct bgp_path_info *old_best,
struct list *mp_list,
struct bgp_maxpaths_cfg *mpath_cfg) struct bgp_maxpaths_cfg *mpath_cfg)
{ {
uint16_t maxpaths, mpath_count, old_mpath_count; uint16_t maxpaths, mpath_count, old_mpath_count;
struct listnode *mp_node, *mp_next_node; struct listnode *mp_node, *mp_next_node;
struct bgp_info *cur_mpath, *new_mpath, *next_mpath, *prev_mpath; struct bgp_path_info *cur_mpath, *new_mpath, *next_mpath, *prev_mpath;
int mpath_changed, debug; int mpath_changed, debug;
char pfx_buf[PREFIX2STR_BUFFER], nh_buf[2][INET6_ADDRSTRLEN]; char pfx_buf[PREFIX2STR_BUFFER], nh_buf[2][INET6_ADDRSTRLEN];
char path_buf[PATH_ADDPATH_STR_BUFFER]; char path_buf[PATH_ADDPATH_STR_BUFFER];
@ -454,17 +462,17 @@ void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best,
if (new_best) { if (new_best) {
mpath_count++; mpath_count++;
if (new_best != old_best) if (new_best != old_best)
bgp_info_mpath_dequeue(new_best); bgp_path_info_mpath_dequeue(new_best);
maxpaths = (new_best->peer->sort == BGP_PEER_IBGP) maxpaths = (new_best->peer->sort == BGP_PEER_IBGP)
? mpath_cfg->maxpaths_ibgp ? mpath_cfg->maxpaths_ibgp
: mpath_cfg->maxpaths_ebgp; : mpath_cfg->maxpaths_ebgp;
} }
if (old_best) { if (old_best) {
cur_mpath = bgp_info_mpath_first(old_best); cur_mpath = bgp_path_info_mpath_first(old_best);
old_mpath_count = bgp_info_mpath_count(old_best); old_mpath_count = bgp_path_info_mpath_count(old_best);
bgp_info_mpath_count_set(old_best, 0); bgp_path_info_mpath_count_set(old_best, 0);
bgp_info_mpath_dequeue(old_best); bgp_path_info_mpath_dequeue(old_best);
} }
if (debug) if (debug)
@ -485,7 +493,7 @@ void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best,
* to skip over it * to skip over it
*/ */
while (mp_node || cur_mpath) { while (mp_node || cur_mpath) {
struct bgp_info *tmp_info; struct bgp_path_info *tmp_info;
/* /*
* We can bail out of this loop if all existing paths on the * We can bail out of this loop if all existing paths on the
@ -496,7 +504,8 @@ void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best,
break; break;
mp_next_node = mp_node ? listnextnode(mp_node) : NULL; mp_next_node = mp_node ? listnextnode(mp_node) : NULL;
next_mpath = cur_mpath ? bgp_info_mpath_next(cur_mpath) : NULL; next_mpath =
cur_mpath ? bgp_path_info_mpath_next(cur_mpath) : NULL;
tmp_info = mp_node ? listgetdata(mp_node) : NULL; tmp_info = mp_node ? listgetdata(mp_node) : NULL;
if (debug) if (debug)
@ -512,14 +521,16 @@ void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best,
*/ */
if (mp_node && (listgetdata(mp_node) == cur_mpath)) { if (mp_node && (listgetdata(mp_node) == cur_mpath)) {
list_delete_node(mp_list, mp_node); list_delete_node(mp_list, mp_node);
bgp_info_mpath_dequeue(cur_mpath); bgp_path_info_mpath_dequeue(cur_mpath);
if ((mpath_count < maxpaths) if ((mpath_count < maxpaths)
&& bgp_info_nexthop_cmp(prev_mpath, cur_mpath)) { && bgp_path_info_nexthop_cmp(prev_mpath,
bgp_info_mpath_enqueue(prev_mpath, cur_mpath); cur_mpath)) {
bgp_path_info_mpath_enqueue(prev_mpath,
cur_mpath);
prev_mpath = cur_mpath; prev_mpath = cur_mpath;
mpath_count++; mpath_count++;
if (debug) { if (debug) {
bgp_info_path_with_addpath_rx_str( bgp_path_info_path_with_addpath_rx_str(
cur_mpath, path_buf); cur_mpath, path_buf);
zlog_debug( zlog_debug(
"%s: %s is still multipath, cur count %d", "%s: %s is still multipath, cur count %d",
@ -528,7 +539,7 @@ void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best,
} else { } else {
mpath_changed = 1; mpath_changed = 1;
if (debug) { if (debug) {
bgp_info_path_with_addpath_rx_str( bgp_path_info_path_with_addpath_rx_str(
cur_mpath, path_buf); cur_mpath, path_buf);
zlog_debug( zlog_debug(
"%s: remove mpath %s nexthop %s, cur count %d", "%s: remove mpath %s nexthop %s, cur count %d",
@ -548,7 +559,8 @@ void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best,
if (cur_mpath if (cur_mpath
&& (!mp_node && (!mp_node
|| (bgp_info_mpath_cmp(cur_mpath, listgetdata(mp_node)) || (bgp_path_info_mpath_cmp(cur_mpath,
listgetdata(mp_node))
< 0))) { < 0))) {
/* /*
* If here, we have an old multipath and either the * If here, we have an old multipath and either the
@ -557,11 +569,11 @@ void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best,
* multipath, so we need to purge this path from the * multipath, so we need to purge this path from the
* multipath list * multipath list
*/ */
bgp_info_mpath_dequeue(cur_mpath); bgp_path_info_mpath_dequeue(cur_mpath);
mpath_changed = 1; mpath_changed = 1;
if (debug) { if (debug) {
bgp_info_path_with_addpath_rx_str(cur_mpath, bgp_path_info_path_with_addpath_rx_str(
path_buf); cur_mpath, path_buf);
zlog_debug( zlog_debug(
"%s: remove mpath %s nexthop %s, cur count %d", "%s: remove mpath %s nexthop %s, cur count %d",
pfx_buf, path_buf, pfx_buf, path_buf,
@ -595,17 +607,19 @@ void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best,
assert(new_mpath); assert(new_mpath);
assert(prev_mpath); assert(prev_mpath);
if ((mpath_count < maxpaths) && (new_mpath != new_best) if ((mpath_count < maxpaths) && (new_mpath != new_best)
&& bgp_info_nexthop_cmp(prev_mpath, new_mpath)) { && bgp_path_info_nexthop_cmp(prev_mpath,
new_mpath)) {
if (new_mpath == next_mpath) if (new_mpath == next_mpath)
bgp_info_mpath_next(new_mpath); bgp_path_info_mpath_next(new_mpath);
bgp_info_mpath_dequeue(new_mpath); bgp_path_info_mpath_dequeue(new_mpath);
bgp_info_mpath_enqueue(prev_mpath, new_mpath); bgp_path_info_mpath_enqueue(prev_mpath,
new_mpath);
prev_mpath = new_mpath; prev_mpath = new_mpath;
mpath_changed = 1; mpath_changed = 1;
mpath_count++; mpath_count++;
if (debug) { if (debug) {
bgp_info_path_with_addpath_rx_str( bgp_path_info_path_with_addpath_rx_str(
new_mpath, path_buf); new_mpath, path_buf);
zlog_debug( zlog_debug(
"%s: add mpath %s nexthop %s, cur count %d", "%s: add mpath %s nexthop %s, cur count %d",
@ -629,39 +643,39 @@ void bgp_info_mpath_update(struct bgp_node *rn, struct bgp_info *new_best,
pfx_buf, mpath_count, pfx_buf, mpath_count,
mpath_changed ? "YES" : "NO"); mpath_changed ? "YES" : "NO");
bgp_info_mpath_count_set(new_best, mpath_count - 1); bgp_path_info_mpath_count_set(new_best, mpath_count - 1);
if (mpath_changed if (mpath_changed
|| (bgp_info_mpath_count(new_best) != old_mpath_count)) || (bgp_path_info_mpath_count(new_best) != old_mpath_count))
SET_FLAG(new_best->flags, BGP_INFO_MULTIPATH_CHG); SET_FLAG(new_best->flags, BGP_PATH_MULTIPATH_CHG);
} }
} }
/* /*
* bgp_mp_dmed_deselect * bgp_mp_dmed_deselect
* *
* Clean up multipath information for BGP_INFO_DMED_SELECTED path that * Clean up multipath information for BGP_PATH_DMED_SELECTED path that
* is not selected as best path * is not selected as best path
*/ */
void bgp_mp_dmed_deselect(struct bgp_info *dmed_best) void bgp_mp_dmed_deselect(struct bgp_path_info *dmed_best)
{ {
struct bgp_info *mpinfo, *mpnext; struct bgp_path_info *mpinfo, *mpnext;
if (!dmed_best) if (!dmed_best)
return; return;
for (mpinfo = bgp_info_mpath_first(dmed_best); mpinfo; for (mpinfo = bgp_path_info_mpath_first(dmed_best); mpinfo;
mpinfo = mpnext) { mpinfo = mpnext) {
mpnext = bgp_info_mpath_next(mpinfo); mpnext = bgp_path_info_mpath_next(mpinfo);
bgp_info_mpath_dequeue(mpinfo); bgp_path_info_mpath_dequeue(mpinfo);
} }
bgp_info_mpath_count_set(dmed_best, 0); bgp_path_info_mpath_count_set(dmed_best, 0);
UNSET_FLAG(dmed_best->flags, BGP_INFO_MULTIPATH_CHG); UNSET_FLAG(dmed_best->flags, BGP_PATH_MULTIPATH_CHG);
assert(bgp_info_mpath_first(dmed_best) == 0); assert(bgp_path_info_mpath_first(dmed_best) == 0);
} }
/* /*
* bgp_info_mpath_aggregate_update * bgp_path_info_mpath_aggregate_update
* *
* Set the multipath aggregate attribute. We need to see if the * Set the multipath aggregate attribute. We need to see if the
* aggregate has changed and then set the ATTR_CHANGED flag on the * aggregate has changed and then set the ATTR_CHANGED flag on the
@ -672,10 +686,10 @@ void bgp_mp_dmed_deselect(struct bgp_info *dmed_best)
* is no change in multipath selection and no attribute change in * is no change in multipath selection and no attribute change in
* any multipath. * any multipath.
*/ */
void bgp_info_mpath_aggregate_update(struct bgp_info *new_best, void bgp_path_info_mpath_aggregate_update(struct bgp_path_info *new_best,
struct bgp_info *old_best) struct bgp_path_info *old_best)
{ {
struct bgp_info *mpinfo; struct bgp_path_info *mpinfo;
struct aspath *aspath; struct aspath *aspath;
struct aspath *asmerge; struct aspath *asmerge;
struct attr *new_attr, *old_attr; struct attr *new_attr, *old_attr;
@ -686,19 +700,19 @@ void bgp_info_mpath_aggregate_update(struct bgp_info *new_best,
struct attr attr = {0}; struct attr attr = {0};
if (old_best && (old_best != new_best) if (old_best && (old_best != new_best)
&& (old_attr = bgp_info_mpath_attr(old_best))) { && (old_attr = bgp_path_info_mpath_attr(old_best))) {
bgp_attr_unintern(&old_attr); bgp_attr_unintern(&old_attr);
bgp_info_mpath_attr_set(old_best, NULL); bgp_path_info_mpath_attr_set(old_best, NULL);
} }
if (!new_best) if (!new_best)
return; return;
if (!bgp_info_mpath_count(new_best)) { if (!bgp_path_info_mpath_count(new_best)) {
if ((new_attr = bgp_info_mpath_attr(new_best))) { if ((new_attr = bgp_path_info_mpath_attr(new_best))) {
bgp_attr_unintern(&new_attr); bgp_attr_unintern(&new_attr);
bgp_info_mpath_attr_set(new_best, NULL); bgp_path_info_mpath_attr_set(new_best, NULL);
SET_FLAG(new_best->flags, BGP_INFO_ATTR_CHANGED); SET_FLAG(new_best->flags, BGP_PATH_ATTR_CHANGED);
} }
return; return;
} }
@ -718,8 +732,8 @@ void bgp_info_mpath_aggregate_update(struct bgp_info *new_best,
lcomm = (attr.lcommunity) ? lcommunity_dup(attr.lcommunity) lcomm = (attr.lcommunity) ? lcommunity_dup(attr.lcommunity)
: NULL; : NULL;
for (mpinfo = bgp_info_mpath_first(new_best); mpinfo; for (mpinfo = bgp_path_info_mpath_first(new_best); mpinfo;
mpinfo = bgp_info_mpath_next(mpinfo)) { mpinfo = bgp_path_info_mpath_next(mpinfo)) {
asmerge = asmerge =
aspath_aggregate(aspath, mpinfo->attr->aspath); aspath_aggregate(aspath, mpinfo->attr->aspath);
aspath_free(aspath); aspath_free(aspath);
@ -789,11 +803,11 @@ void bgp_info_mpath_aggregate_update(struct bgp_info *new_best,
new_attr = bgp_attr_intern(&attr); new_attr = bgp_attr_intern(&attr);
if (new_attr != bgp_info_mpath_attr(new_best)) { if (new_attr != bgp_path_info_mpath_attr(new_best)) {
if ((old_attr = bgp_info_mpath_attr(new_best))) if ((old_attr = bgp_path_info_mpath_attr(new_best)))
bgp_attr_unintern(&old_attr); bgp_attr_unintern(&old_attr);
bgp_info_mpath_attr_set(new_best, new_attr); bgp_path_info_mpath_attr_set(new_best, new_attr);
SET_FLAG(new_best->flags, BGP_INFO_ATTR_CHANGED); SET_FLAG(new_best->flags, BGP_PATH_ATTR_CHANGED);
} else } else
bgp_attr_unintern(&new_attr); bgp_attr_unintern(&new_attr);
} }

View File

@ -22,18 +22,18 @@
#ifndef _QUAGGA_BGP_MPATH_H #ifndef _QUAGGA_BGP_MPATH_H
#define _QUAGGA_BGP_MPATH_H #define _QUAGGA_BGP_MPATH_H
/* Supplemental information linked to bgp_info for keeping track of /* Supplemental information linked to bgp_path_info for keeping track of
* multipath selections, lazily allocated to save memory * multipath selections, lazily allocated to save memory
*/ */
struct bgp_info_mpath { struct bgp_path_info_mpath {
/* Points to the first multipath (on bestpath) or the next multipath */ /* Points to the first multipath (on bestpath) or the next multipath */
struct bgp_info_mpath *mp_next; struct bgp_path_info_mpath *mp_next;
/* Points to the previous multipath or NULL on bestpath */ /* Points to the previous multipath or NULL on bestpath */
struct bgp_info_mpath *mp_prev; struct bgp_path_info_mpath *mp_prev;
/* Points to bgp_info associated with this multipath info */ /* Points to bgp_path_info associated with this multipath info */
struct bgp_info *mp_info; struct bgp_path_info *mp_info;
/* When attached to best path, the number of selected multipaths */ /* When attached to best path, the number of selected multipaths */
uint32_t mp_count; uint32_t mp_count;
@ -50,27 +50,33 @@ extern int bgp_maximum_paths_unset(struct bgp *, afi_t, safi_t, int);
/* Functions used by bgp_best_selection to record current /* Functions used by bgp_best_selection to record current
* multipath selections * multipath selections
*/ */
extern int bgp_info_nexthop_cmp(struct bgp_info *bi1, struct bgp_info *bi2); extern int bgp_path_info_nexthop_cmp(struct bgp_path_info *bpi1,
struct bgp_path_info *bpi2);
extern void bgp_mp_list_init(struct list *); extern void bgp_mp_list_init(struct list *);
extern void bgp_mp_list_clear(struct list *); extern void bgp_mp_list_clear(struct list *);
extern void bgp_mp_list_add(struct list *, struct bgp_info *); extern void bgp_mp_list_add(struct list *mp_list, struct bgp_path_info *mpinfo);
extern void bgp_mp_dmed_deselect(struct bgp_info *); extern void bgp_mp_dmed_deselect(struct bgp_path_info *dmed_best);
extern void bgp_info_mpath_update(struct bgp_node *, struct bgp_info *, extern void bgp_path_info_mpath_update(struct bgp_node *rn,
struct bgp_info *, struct list *, struct bgp_path_info *new_best,
struct bgp_maxpaths_cfg *); struct bgp_path_info *old_best,
extern void bgp_info_mpath_aggregate_update(struct bgp_info *, struct list *mp_list,
struct bgp_info *); struct bgp_maxpaths_cfg *mpath_cfg);
extern void
bgp_path_info_mpath_aggregate_update(struct bgp_path_info *new_best,
struct bgp_path_info *old_best);
/* Unlink and free multipath information associated with a bgp_info */ /* Unlink and free multipath information associated with a bgp_path_info */
extern void bgp_info_mpath_dequeue(struct bgp_info *); extern void bgp_path_info_mpath_dequeue(struct bgp_path_info *path);
extern void bgp_info_mpath_free(struct bgp_info_mpath **); extern void bgp_path_info_mpath_free(struct bgp_path_info_mpath **mpath);
/* Walk list of multipaths associated with a best path */ /* Walk list of multipaths associated with a best path */
extern struct bgp_info *bgp_info_mpath_first(struct bgp_info *); extern struct bgp_path_info *
extern struct bgp_info *bgp_info_mpath_next(struct bgp_info *); bgp_path_info_mpath_first(struct bgp_path_info *path);
extern struct bgp_path_info *
bgp_path_info_mpath_next(struct bgp_path_info *path);
/* Accessors for multipath information */ /* Accessors for multipath information */
extern uint32_t bgp_info_mpath_count(struct bgp_info *); extern uint32_t bgp_path_info_mpath_count(struct bgp_path_info *path);
extern struct attr *bgp_info_mpath_attr(struct bgp_info *); extern struct attr *bgp_path_info_mpath_attr(struct bgp_path_info *path);
#endif /* _QUAGGA_BGP_MPATH_H */ #endif /* _QUAGGA_BGP_MPATH_H */

View File

@ -402,22 +402,23 @@ static int ecom_intersect(struct ecommunity *e1, struct ecommunity *e2)
return 0; return 0;
} }
static bool labels_same(struct bgp_info *bi, mpls_label_t *label, uint32_t n) static bool labels_same(struct bgp_path_info *bpi, mpls_label_t *label,
uint32_t n)
{ {
uint32_t i; uint32_t i;
if (!bi->extra) { if (!bpi->extra) {
if (!n) if (!n)
return true; return true;
else else
return false; return false;
} }
if (n != bi->extra->num_labels) if (n != bpi->extra->num_labels)
return false; return false;
for (i = 0; i < n; ++i) { for (i = 0; i < n; ++i) {
if (label[i] != bi->extra->label[i]) if (label[i] != bpi->extra->label[i])
return false; return false;
} }
return true; return true;
@ -426,8 +427,7 @@ static bool labels_same(struct bgp_info *bi, mpls_label_t *label, uint32_t n)
/* /*
* make encoded route labels match specified encoded label set * make encoded route labels match specified encoded label set
*/ */
static void setlabels( static void setlabels(struct bgp_path_info *bpi,
struct bgp_info *bi,
mpls_label_t *label, /* array of labels */ mpls_label_t *label, /* array of labels */
uint32_t num_labels) uint32_t num_labels)
{ {
@ -436,12 +436,12 @@ static void setlabels(
assert(num_labels <= BGP_MAX_LABELS); assert(num_labels <= BGP_MAX_LABELS);
if (!num_labels) { if (!num_labels) {
if (bi->extra) if (bpi->extra)
bi->extra->num_labels = 0; bpi->extra->num_labels = 0;
return; return;
} }
struct bgp_info_extra *extra = bgp_info_extra_get(bi); struct bgp_path_info_extra *extra = bgp_path_info_extra_get(bpi);
uint32_t i; uint32_t i;
for (i = 0; i < num_labels; ++i) { for (i = 0; i < num_labels; ++i) {
@ -454,35 +454,27 @@ static void setlabels(
} }
/* /*
* returns pointer to new bgp_info upon success * returns pointer to new bgp_path_info upon success
*/ */
static struct bgp_info * static struct bgp_path_info *
leak_update( leak_update(struct bgp *bgp, /* destination bgp instance */
struct bgp *bgp, /* destination bgp instance */ struct bgp_node *bn, struct attr *new_attr, /* already interned */
struct bgp_node *bn, afi_t afi, safi_t safi, struct bgp_path_info *source_bpi,
struct attr *new_attr, /* already interned */ mpls_label_t *label, uint32_t num_labels, void *parent,
afi_t afi, struct bgp *bgp_orig, struct prefix *nexthop_orig,
safi_t safi, int nexthop_self_flag, int debug)
struct bgp_info *source_bi,
mpls_label_t *label,
uint32_t num_labels,
void *parent,
struct bgp *bgp_orig,
struct prefix *nexthop_orig,
int nexthop_self_flag,
int debug)
{ {
struct prefix *p = &bn->p; struct prefix *p = &bn->p;
struct bgp_info *bi; struct bgp_path_info *bpi;
struct bgp_info *bi_ultimate; struct bgp_path_info *bpi_ultimate;
struct bgp_info *new; struct bgp_path_info *new;
char buf_prefix[PREFIX_STRLEN]; char buf_prefix[PREFIX_STRLEN];
if (debug) { if (debug) {
prefix2str(&bn->p, buf_prefix, sizeof(buf_prefix)); prefix2str(&bn->p, buf_prefix, sizeof(buf_prefix));
zlog_debug("%s: entry: leak-to=%s, p=%s, type=%d, sub_type=%d", zlog_debug("%s: entry: leak-to=%s, p=%s, type=%d, sub_type=%d",
__func__, bgp->name_pretty, buf_prefix, __func__, bgp->name_pretty, buf_prefix,
source_bi->type, source_bi->sub_type); source_bpi->type, source_bpi->sub_type);
} }
/* /*
@ -494,31 +486,30 @@ leak_update(
* should have nexthop tracking, we must find the ultimate * should have nexthop tracking, we must find the ultimate
* parent so we can check its sub_type. * parent so we can check its sub_type.
* *
* As of now, source_bi may at most be a second-generation route * As of now, source_bpi may at most be a second-generation route
* (only one hop back to ultimate parent for vrf-vpn-vrf scheme). * (only one hop back to ultimate parent for vrf-vpn-vrf scheme).
* Using a loop here supports more complex intra-bgp import-export * Using a loop here supports more complex intra-bgp import-export
* schemes that could be implemented in the future. * schemes that could be implemented in the future.
* *
*/ */
for (bi_ultimate = source_bi; for (bpi_ultimate = source_bpi;
bi_ultimate->extra && bi_ultimate->extra->parent; bpi_ultimate->extra && bpi_ultimate->extra->parent;
bi_ultimate = bi_ultimate->extra->parent) bpi_ultimate = bpi_ultimate->extra->parent)
; ;
/* /*
* match parent * match parent
*/ */
for (bi = bn->info; bi; bi = bi->next) { for (bpi = bn->info; bpi; bpi = bpi->next) {
if (bi->extra && bi->extra->parent == parent) if (bpi->extra && bpi->extra->parent == parent)
break; break;
} }
if (bi) { if (bpi) {
bool labelssame = labels_same(bi, label, num_labels); bool labelssame = labels_same(bpi, label, num_labels);
if (attrhash_cmp(bi->attr, new_attr) if (attrhash_cmp(bpi->attr, new_attr) && labelssame
&& labelssame && !CHECK_FLAG(bpi->flags, BGP_PATH_REMOVED)) {
&& !CHECK_FLAG(bi->flags, BGP_INFO_REMOVED)) {
bgp_attr_unintern(&new_attr); bgp_attr_unintern(&new_attr);
if (debug) if (debug)
@ -530,43 +521,42 @@ leak_update(
} }
/* attr is changed */ /* attr is changed */
bgp_info_set_flag(bn, bi, BGP_INFO_ATTR_CHANGED); bgp_path_info_set_flag(bn, bpi, BGP_PATH_ATTR_CHANGED);
/* Rewrite BGP route information. */ /* Rewrite BGP route information. */
if (CHECK_FLAG(bi->flags, BGP_INFO_REMOVED)) if (CHECK_FLAG(bpi->flags, BGP_PATH_REMOVED))
bgp_info_restore(bn, bi); bgp_path_info_restore(bn, bpi);
else else
bgp_aggregate_decrement(bgp, p, bi, afi, safi); bgp_aggregate_decrement(bgp, p, bpi, afi, safi);
bgp_attr_unintern(&bi->attr); bgp_attr_unintern(&bpi->attr);
bi->attr = new_attr; bpi->attr = new_attr;
bi->uptime = bgp_clock(); bpi->uptime = bgp_clock();
/* /*
* rewrite labels * rewrite labels
*/ */
if (!labelssame) if (!labelssame)
setlabels(bi, label, num_labels); setlabels(bpi, label, num_labels);
if (nexthop_self_flag) if (nexthop_self_flag)
bgp_info_set_flag(bn, bi, BGP_INFO_ANNC_NH_SELF); bgp_path_info_set_flag(bn, bpi, BGP_PATH_ANNC_NH_SELF);
struct bgp *bgp_nexthop = bgp; struct bgp *bgp_nexthop = bgp;
int nh_valid; int nh_valid;
if (bi->extra && bi->extra->bgp_orig) if (bpi->extra && bpi->extra->bgp_orig)
bgp_nexthop = bi->extra->bgp_orig; bgp_nexthop = bpi->extra->bgp_orig;
/* No nexthop tracking for redistributed routes */ /* No nexthop tracking for redistributed routes */
if (bi_ultimate->sub_type == BGP_ROUTE_REDISTRIBUTE) if (bpi_ultimate->sub_type == BGP_ROUTE_REDISTRIBUTE)
nh_valid = 1; nh_valid = 1;
else else
/* /*
* TBD do we need to do anything about the * TBD do we need to do anything about the
* 'connected' parameter? * 'connected' parameter?
*/ */
nh_valid = bgp_find_or_add_nexthop( nh_valid = bgp_find_or_add_nexthop(bgp, bgp_nexthop,
bgp, bgp_nexthop, afi, bpi, NULL, 0);
afi, bi, NULL, 0);
if (debug) if (debug)
zlog_debug("%s: nexthop is %svalid (in vrf %s)", zlog_debug("%s: nexthop is %svalid (in vrf %s)",
@ -574,10 +564,10 @@ leak_update(
bgp_nexthop->name_pretty); bgp_nexthop->name_pretty);
if (nh_valid) if (nh_valid)
bgp_info_set_flag(bn, bi, BGP_INFO_VALID); bgp_path_info_set_flag(bn, bpi, BGP_PATH_VALID);
/* Process change. */ /* Process change. */
bgp_aggregate_increment(bgp, p, bi, afi, safi); bgp_aggregate_increment(bgp, p, bpi, afi, safi);
bgp_process(bgp, bn, afi, safi); bgp_process(bgp, bn, afi, safi);
bgp_unlock_node(bn); bgp_unlock_node(bn);
@ -585,22 +575,22 @@ leak_update(
zlog_debug("%s: ->%s: %s Found route, changed attr", zlog_debug("%s: ->%s: %s Found route, changed attr",
__func__, bgp->name_pretty, buf_prefix); __func__, bgp->name_pretty, buf_prefix);
return bi; return bpi;
} }
new = info_make(ZEBRA_ROUTE_BGP, BGP_ROUTE_IMPORTED, 0, new = info_make(ZEBRA_ROUTE_BGP, BGP_ROUTE_IMPORTED, 0,
bgp->peer_self, new_attr, bn); bgp->peer_self, new_attr, bn);
if (nexthop_self_flag) if (nexthop_self_flag)
bgp_info_set_flag(bn, new, BGP_INFO_ANNC_NH_SELF); bgp_path_info_set_flag(bn, new, BGP_PATH_ANNC_NH_SELF);
bgp_info_extra_get(new); bgp_path_info_extra_get(new);
if (num_labels) if (num_labels)
setlabels(new, label, num_labels); setlabels(new, label, num_labels);
new->extra->parent = bgp_info_lock(parent); new->extra->parent = bgp_path_info_lock(parent);
bgp_lock_node((struct bgp_node *)((struct bgp_info *)parent)->net); bgp_lock_node((struct bgp_node *)((struct bgp_path_info *)parent)->net);
if (bgp_orig) if (bgp_orig)
new->extra->bgp_orig = bgp_lock(bgp_orig); new->extra->bgp_orig = bgp_lock(bgp_orig);
if (nexthop_orig) if (nexthop_orig)
@ -620,7 +610,7 @@ leak_update(
* their originating protocols will do the tracking and * their originating protocols will do the tracking and
* withdraw those routes if the nexthops become unreachable * withdraw those routes if the nexthops become unreachable
*/ */
if (bi_ultimate->sub_type == BGP_ROUTE_REDISTRIBUTE) if (bpi_ultimate->sub_type == BGP_ROUTE_REDISTRIBUTE)
nh_valid = 1; nh_valid = 1;
else else
/* /*
@ -635,10 +625,10 @@ leak_update(
__func__, (nh_valid ? "" : "not "), __func__, (nh_valid ? "" : "not "),
bgp_nexthop->name_pretty); bgp_nexthop->name_pretty);
if (nh_valid) if (nh_valid)
bgp_info_set_flag(bn, new, BGP_INFO_VALID); bgp_path_info_set_flag(bn, new, BGP_PATH_VALID);
bgp_aggregate_increment(bgp, p, new, afi, safi); bgp_aggregate_increment(bgp, p, new, afi, safi);
bgp_info_add(bn, new); bgp_path_info_add(bn, new);
bgp_unlock_node(bn); bgp_unlock_node(bn);
bgp_process(bgp, bn, afi, safi); bgp_process(bgp, bn, afi, safi);
@ -653,10 +643,10 @@ leak_update(
/* cf vnc_import_bgp_add_route_mode_nvegroup() and add_vnc_route() */ /* cf vnc_import_bgp_add_route_mode_nvegroup() and add_vnc_route() */
void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, /* to */ void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, /* to */
struct bgp *bgp_vrf, /* from */ struct bgp *bgp_vrf, /* from */
struct bgp_info *info_vrf) /* route */ struct bgp_path_info *path_vrf) /* route */
{ {
int debug = BGP_DEBUG(vpn, VPN_LEAK_FROM_VRF); int debug = BGP_DEBUG(vpn, VPN_LEAK_FROM_VRF);
struct prefix *p = &info_vrf->net->p; struct prefix *p = &path_vrf->net->p;
afi_t afi = family2afi(p->family); afi_t afi = family2afi(p->family);
struct attr static_attr = {0}; struct attr static_attr = {0};
struct attr *new_attr = NULL; struct attr *new_attr = NULL;
@ -670,12 +660,12 @@ void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, /* to */
if (debug) if (debug)
zlog_debug("%s: from vrf %s", __func__, bgp_vrf->name_pretty); zlog_debug("%s: from vrf %s", __func__, bgp_vrf->name_pretty);
if (debug && info_vrf->attr->ecommunity) { if (debug && path_vrf->attr->ecommunity) {
char *s = ecommunity_ecom2str(info_vrf->attr->ecommunity, char *s = ecommunity_ecom2str(path_vrf->attr->ecommunity,
ECOMMUNITY_FORMAT_ROUTE_MAP, 0); ECOMMUNITY_FORMAT_ROUTE_MAP, 0);
zlog_debug("%s: %s info_vrf->type=%d, EC{%s}", __func__, zlog_debug("%s: %s path_vrf->type=%d, EC{%s}", __func__,
bgp_vrf->name, info_vrf->type, s); bgp_vrf->name, path_vrf->type, s);
XFREE(MTYPE_ECOMMUNITY_STR, s); XFREE(MTYPE_ECOMMUNITY_STR, s);
} }
@ -689,7 +679,7 @@ void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, /* to */
} }
/* loop check - should not be an imported route. */ /* loop check - should not be an imported route. */
if (info_vrf->extra && info_vrf->extra->bgp_orig) if (path_vrf->extra && path_vrf->extra->bgp_orig)
return; return;
@ -700,13 +690,13 @@ void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, /* to */
return; return;
} }
bgp_attr_dup(&static_attr, info_vrf->attr); /* shallow copy */ bgp_attr_dup(&static_attr, path_vrf->attr); /* shallow copy */
/* /*
* route map handling * route map handling
*/ */
if (bgp_vrf->vpn_policy[afi].rmap[BGP_VPN_POLICY_DIR_TOVPN]) { if (bgp_vrf->vpn_policy[afi].rmap[BGP_VPN_POLICY_DIR_TOVPN]) {
struct bgp_info info; struct bgp_path_info info;
route_map_result_t ret; route_map_result_t ret;
memset(&info, 0, sizeof(info)); memset(&info, 0, sizeof(info));
@ -818,8 +808,8 @@ void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, /* to */
* IPv4 nexthops as the attr has been copied * IPv4 nexthops as the attr has been copied
* otherwise. * otherwise.
*/ */
if (afi == AFI_IP && if (afi == AFI_IP
!BGP_ATTR_NEXTHOP_AFI_IP6(info_vrf->attr)) { && !BGP_ATTR_NEXTHOP_AFI_IP6(path_vrf->attr)) {
static_attr.mp_nexthop_global_in.s_addr = static_attr.mp_nexthop_global_in.s_addr =
static_attr.nexthop.s_addr; static_attr.nexthop.s_addr;
static_attr.mp_nexthop_len = 4; static_attr.mp_nexthop_len = 4;
@ -859,10 +849,10 @@ void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, /* to */
bn = bgp_afi_node_get(bgp_vpn->rib[afi][safi], afi, safi, p, bn = bgp_afi_node_get(bgp_vpn->rib[afi][safi], afi, safi, p,
&(bgp_vrf->vpn_policy[afi].tovpn_rd)); &(bgp_vrf->vpn_policy[afi].tovpn_rd));
struct bgp_info *new_info; struct bgp_path_info *new_info;
new_info = leak_update(bgp_vpn, bn, new_attr, afi, safi, info_vrf, new_info = leak_update(bgp_vpn, bn, new_attr, afi, safi, path_vrf,
&label, 1, info_vrf, bgp_vrf, NULL, &label, 1, path_vrf, bgp_vrf, NULL,
nexthop_self_flag, debug); nexthop_self_flag, debug);
/* /*
@ -880,13 +870,13 @@ void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, /* to */
void vpn_leak_from_vrf_withdraw(struct bgp *bgp_vpn, /* to */ void vpn_leak_from_vrf_withdraw(struct bgp *bgp_vpn, /* to */
struct bgp *bgp_vrf, /* from */ struct bgp *bgp_vrf, /* from */
struct bgp_info *info_vrf) /* route */ struct bgp_path_info *path_vrf) /* route */
{ {
int debug = BGP_DEBUG(vpn, VPN_LEAK_FROM_VRF); int debug = BGP_DEBUG(vpn, VPN_LEAK_FROM_VRF);
struct prefix *p = &info_vrf->net->p; struct prefix *p = &path_vrf->net->p;
afi_t afi = family2afi(p->family); afi_t afi = family2afi(p->family);
safi_t safi = SAFI_MPLS_VPN; safi_t safi = SAFI_MPLS_VPN;
struct bgp_info *bi; struct bgp_path_info *bpi;
struct bgp_node *bn; struct bgp_node *bn;
const char *debugmsg; const char *debugmsg;
char buf_prefix[PREFIX_STRLEN]; char buf_prefix[PREFIX_STRLEN];
@ -896,16 +886,16 @@ void vpn_leak_from_vrf_withdraw(struct bgp *bgp_vpn, /* to */
zlog_debug( zlog_debug(
"%s: entry: leak-from=%s, p=%s, type=%d, sub_type=%d", "%s: entry: leak-from=%s, p=%s, type=%d, sub_type=%d",
__func__, bgp_vrf->name_pretty, buf_prefix, __func__, bgp_vrf->name_pretty, buf_prefix,
info_vrf->type, info_vrf->sub_type); path_vrf->type, path_vrf->sub_type);
} }
if (info_vrf->sub_type != BGP_ROUTE_NORMAL if (path_vrf->sub_type != BGP_ROUTE_NORMAL
&& info_vrf->sub_type != BGP_ROUTE_STATIC && path_vrf->sub_type != BGP_ROUTE_STATIC
&& info_vrf->sub_type != BGP_ROUTE_REDISTRIBUTE) { && path_vrf->sub_type != BGP_ROUTE_REDISTRIBUTE) {
if (debug) if (debug)
zlog_debug("%s: wrong sub_type %d", __func__, zlog_debug("%s: wrong sub_type %d", __func__,
info_vrf->sub_type); path_vrf->sub_type);
return; return;
} }
if (!bgp_vpn) if (!bgp_vpn)
@ -924,27 +914,27 @@ void vpn_leak_from_vrf_withdraw(struct bgp *bgp_vpn, /* to */
} }
if (debug) if (debug)
zlog_debug("%s: withdrawing (info_vrf=%p)", __func__, info_vrf); zlog_debug("%s: withdrawing (path_vrf=%p)", __func__, path_vrf);
bn = bgp_afi_node_get(bgp_vpn->rib[afi][safi], afi, safi, p, bn = bgp_afi_node_get(bgp_vpn->rib[afi][safi], afi, safi, p,
&(bgp_vrf->vpn_policy[afi].tovpn_rd)); &(bgp_vrf->vpn_policy[afi].tovpn_rd));
/* /*
* vrf -> vpn * vrf -> vpn
* match original bi imported from * match original bpi imported from
*/ */
for (bi = (bn ? bn->info : NULL); bi; bi = bi->next) { for (bpi = (bn ? bn->info : NULL); bpi; bpi = bpi->next) {
if (bi->extra && bi->extra->parent == info_vrf) { if (bpi->extra && bpi->extra->parent == path_vrf) {
break; break;
} }
} }
if (bi) { if (bpi) {
/* withdraw from looped vrfs as well */ /* withdraw from looped vrfs as well */
vpn_leak_to_vrf_withdraw(bgp_vpn, bi); vpn_leak_to_vrf_withdraw(bgp_vpn, bpi);
bgp_aggregate_decrement(bgp_vpn, p, bi, afi, safi); bgp_aggregate_decrement(bgp_vpn, p, bpi, afi, safi);
bgp_info_delete(bn, bi); bgp_path_info_delete(bn, bpi);
bgp_process(bgp_vpn, bn, afi, safi); bgp_process(bgp_vpn, bn, afi, safi);
} }
bgp_unlock_node(bn); bgp_unlock_node(bn);
@ -959,14 +949,14 @@ void vpn_leak_from_vrf_withdraw_all(struct bgp *bgp_vpn, /* to */
safi_t safi = SAFI_MPLS_VPN; safi_t safi = SAFI_MPLS_VPN;
/* /*
* Walk vpn table, delete bi with bgp_orig == bgp_vrf * Walk vpn table, delete bpi with bgp_orig == bgp_vrf
*/ */
for (prn = bgp_table_top(bgp_vpn->rib[afi][safi]); prn; for (prn = bgp_table_top(bgp_vpn->rib[afi][safi]); prn;
prn = bgp_route_next(prn)) { prn = bgp_route_next(prn)) {
struct bgp_table *table; struct bgp_table *table;
struct bgp_node *bn; struct bgp_node *bn;
struct bgp_info *bi; struct bgp_path_info *bpi;
/* This is the per-RD table of prefixes */ /* This is the per-RD table of prefixes */
table = prn->info; table = prn->info;
@ -984,24 +974,24 @@ void vpn_leak_from_vrf_withdraw_all(struct bgp *bgp_vpn, /* to */
prefix2str(&bn->p, buf, sizeof(buf))); prefix2str(&bn->p, buf, sizeof(buf)));
} }
for (bi = bn->info; bi; bi = bi->next) { for (bpi = bn->info; bpi; bpi = bpi->next) {
if (debug) if (debug)
zlog_debug("%s: type %d, sub_type %d", zlog_debug("%s: type %d, sub_type %d",
__func__, bi->type, __func__, bpi->type,
bi->sub_type); bpi->sub_type);
if (bi->sub_type != BGP_ROUTE_IMPORTED) if (bpi->sub_type != BGP_ROUTE_IMPORTED)
continue; continue;
if (!bi->extra) if (!bpi->extra)
continue; continue;
if ((struct bgp *)bi->extra->bgp_orig if ((struct bgp *)bpi->extra->bgp_orig
== bgp_vrf) { == bgp_vrf) {
/* delete route */ /* delete route */
if (debug) if (debug)
zlog_debug("%s: deleting it\n", zlog_debug("%s: deleting it\n",
__func__); __func__);
bgp_aggregate_decrement(bgp_vpn, &bn->p, bgp_aggregate_decrement(bgp_vpn, &bn->p,
bi, afi, safi); bpi, afi, safi);
bgp_info_delete(bn, bi); bgp_path_info_delete(bn, bpi);
bgp_process(bgp_vpn, bn, afi, safi); bgp_process(bgp_vpn, bn, afi, safi);
} }
} }
@ -1014,7 +1004,7 @@ void vpn_leak_from_vrf_update_all(struct bgp *bgp_vpn, /* to */
afi_t afi) afi_t afi)
{ {
struct bgp_node *bn; struct bgp_node *bn;
struct bgp_info *bi; struct bgp_path_info *bpi;
int debug = BGP_DEBUG(vpn, VPN_LEAK_FROM_VRF); int debug = BGP_DEBUG(vpn, VPN_LEAK_FROM_VRF);
if (debug) if (debug)
@ -1027,21 +1017,22 @@ void vpn_leak_from_vrf_update_all(struct bgp *bgp_vpn, /* to */
if (debug) if (debug)
zlog_debug("%s: node=%p", __func__, bn); zlog_debug("%s: node=%p", __func__, bn);
for (bi = bn->info; bi; bi = bi->next) { for (bpi = bn->info; bpi; bpi = bpi->next) {
if (debug) if (debug)
zlog_debug( zlog_debug(
"%s: calling vpn_leak_from_vrf_update", "%s: calling vpn_leak_from_vrf_update",
__func__); __func__);
vpn_leak_from_vrf_update(bgp_vpn, bgp_vrf, bi); vpn_leak_from_vrf_update(bgp_vpn, bgp_vrf, bpi);
} }
} }
} }
static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */ static void
vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
struct bgp *bgp_vpn, /* from */ struct bgp *bgp_vpn, /* from */
struct bgp_info *info_vpn) /* route */ struct bgp_path_info *path_vpn) /* route */
{ {
struct prefix *p = &info_vpn->net->p; struct prefix *p = &path_vpn->net->p;
afi_t afi = family2afi(p->family); afi_t afi = family2afi(p->family);
struct attr static_attr = {0}; struct attr static_attr = {0};
@ -1053,7 +1044,7 @@ static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
mpls_label_t *pLabels = NULL; mpls_label_t *pLabels = NULL;
uint32_t num_labels = 0; uint32_t num_labels = 0;
int nexthop_self_flag = 1; int nexthop_self_flag = 1;
struct bgp_info *bi_ultimate = NULL; struct bgp_path_info *bpi_ultimate = NULL;
int origin_local = 0; int origin_local = 0;
struct bgp *src_vrf; struct bgp *src_vrf;
@ -1068,7 +1059,7 @@ static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
/* Check for intersection of route targets */ /* Check for intersection of route targets */
if (!ecom_intersect( if (!ecom_intersect(
bgp_vrf->vpn_policy[afi].rtlist[BGP_VPN_POLICY_DIR_FROMVPN], bgp_vrf->vpn_policy[afi].rtlist[BGP_VPN_POLICY_DIR_FROMVPN],
info_vpn->attr->ecommunity)) { path_vpn->attr->ecommunity)) {
return; return;
} }
@ -1077,7 +1068,7 @@ static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
zlog_debug("%s: updating to vrf %s", __func__, zlog_debug("%s: updating to vrf %s", __func__,
bgp_vrf->name_pretty); bgp_vrf->name_pretty);
bgp_attr_dup(&static_attr, info_vpn->attr); /* shallow copy */ bgp_attr_dup(&static_attr, path_vpn->attr); /* shallow copy */
/* /*
* Nexthop: stash and clear * Nexthop: stash and clear
@ -1086,7 +1077,7 @@ static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
* Stash it for later label resolution by vrf ingress path and then * Stash it for later label resolution by vrf ingress path and then
* overwrite with 0, i.e., "me", for the sake of vrf advertisement. * overwrite with 0, i.e., "me", for the sake of vrf advertisement.
*/ */
uint8_t nhfamily = NEXTHOP_FAMILY(info_vpn->attr->mp_nexthop_len); uint8_t nhfamily = NEXTHOP_FAMILY(path_vpn->attr->mp_nexthop_len);
if (nhfamily != AF_UNSPEC) if (nhfamily != AF_UNSPEC)
static_attr.flag |= ATTR_FLAG_BIT(BGP_ATTR_NEXT_HOP); static_attr.flag |= ATTR_FLAG_BIT(BGP_ATTR_NEXT_HOP);
@ -1096,7 +1087,7 @@ static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
switch (nhfamily) { switch (nhfamily) {
case AF_INET: case AF_INET:
/* save */ /* save */
nexthop_orig.u.prefix4 = info_vpn->attr->mp_nexthop_global_in; nexthop_orig.u.prefix4 = path_vpn->attr->mp_nexthop_global_in;
nexthop_orig.prefixlen = 32; nexthop_orig.prefixlen = 32;
if (CHECK_FLAG(bgp_vrf->af_flags[afi][safi], if (CHECK_FLAG(bgp_vrf->af_flags[afi][safi],
@ -1105,14 +1096,14 @@ static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
nexthop_orig.u.prefix4.s_addr; nexthop_orig.u.prefix4.s_addr;
static_attr.mp_nexthop_global_in = static_attr.mp_nexthop_global_in =
info_vpn->attr->mp_nexthop_global_in; path_vpn->attr->mp_nexthop_global_in;
static_attr.mp_nexthop_len = static_attr.mp_nexthop_len =
info_vpn->attr->mp_nexthop_len; path_vpn->attr->mp_nexthop_len;
} }
break; break;
case AF_INET6: case AF_INET6:
/* save */ /* save */
nexthop_orig.u.prefix6 = info_vpn->attr->mp_nexthop_global; nexthop_orig.u.prefix6 = path_vpn->attr->mp_nexthop_global;
nexthop_orig.prefixlen = 128; nexthop_orig.prefixlen = 128;
if (CHECK_FLAG(bgp_vrf->af_flags[afi][safi], if (CHECK_FLAG(bgp_vrf->af_flags[afi][safi],
@ -1126,7 +1117,7 @@ static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
* route map handling * route map handling
*/ */
if (bgp_vrf->vpn_policy[afi].rmap[BGP_VPN_POLICY_DIR_FROMVPN]) { if (bgp_vrf->vpn_policy[afi].rmap[BGP_VPN_POLICY_DIR_FROMVPN]) {
struct bgp_info info; struct bgp_path_info info;
route_map_result_t ret; route_map_result_t ret;
memset(&info, 0, sizeof(info)); memset(&info, 0, sizeof(info));
@ -1174,30 +1165,30 @@ static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
if (!CHECK_FLAG(bgp_vrf->af_flags[afi][safi], if (!CHECK_FLAG(bgp_vrf->af_flags[afi][safi],
BGP_CONFIG_VRF_TO_VRF_IMPORT)) { BGP_CONFIG_VRF_TO_VRF_IMPORT)) {
/* work back to original route */ /* work back to original route */
for (bi_ultimate = info_vpn; for (bpi_ultimate = path_vpn;
bi_ultimate->extra && bi_ultimate->extra->parent; bpi_ultimate->extra && bpi_ultimate->extra->parent;
bi_ultimate = bi_ultimate->extra->parent) bpi_ultimate = bpi_ultimate->extra->parent)
; ;
/* /*
* if original route was unicast, * if original route was unicast,
* then it did not arrive over vpn * then it did not arrive over vpn
*/ */
if (bi_ultimate->net) { if (bpi_ultimate->net) {
struct bgp_table *table; struct bgp_table *table;
table = bgp_node_table(bi_ultimate->net); table = bgp_node_table(bpi_ultimate->net);
if (table && (table->safi == SAFI_UNICAST)) if (table && (table->safi == SAFI_UNICAST))
origin_local = 1; origin_local = 1;
} }
/* copy labels */ /* copy labels */
if (!origin_local && if (!origin_local && path_vpn->extra
info_vpn->extra && info_vpn->extra->num_labels) { && path_vpn->extra->num_labels) {
num_labels = info_vpn->extra->num_labels; num_labels = path_vpn->extra->num_labels;
if (num_labels > BGP_MAX_LABELS) if (num_labels > BGP_MAX_LABELS)
num_labels = BGP_MAX_LABELS; num_labels = BGP_MAX_LABELS;
pLabels = info_vpn->extra->label; pLabels = path_vpn->extra->label;
} }
} }
@ -1212,19 +1203,18 @@ static void vpn_leak_to_vrf_update_onevrf(struct bgp *bgp_vrf, /* to */
* For VRF-2-VRF route-leaking, * For VRF-2-VRF route-leaking,
* the source will be the originating VRF. * the source will be the originating VRF.
*/ */
if (info_vpn->extra && info_vpn->extra->bgp_orig) if (path_vpn->extra && path_vpn->extra->bgp_orig)
src_vrf = info_vpn->extra->bgp_orig; src_vrf = path_vpn->extra->bgp_orig;
else else
src_vrf = bgp_vpn; src_vrf = bgp_vpn;
leak_update(bgp_vrf, bn, new_attr, afi, safi, info_vpn, leak_update(bgp_vrf, bn, new_attr, afi, safi, path_vpn, pLabels,
pLabels, num_labels, num_labels, path_vpn, /* parent */
info_vpn, /* parent */
src_vrf, &nexthop_orig, nexthop_self_flag, debug); src_vrf, &nexthop_orig, nexthop_self_flag, debug);
} }
void vpn_leak_to_vrf_update(struct bgp *bgp_vpn, /* from */ void vpn_leak_to_vrf_update(struct bgp *bgp_vpn, /* from */
struct bgp_info *info_vpn) /* route */ struct bgp_path_info *path_vpn) /* route */
{ {
struct listnode *mnode, *mnnode; struct listnode *mnode, *mnnode;
struct bgp *bgp; struct bgp *bgp;
@ -1232,20 +1222,20 @@ void vpn_leak_to_vrf_update(struct bgp *bgp_vpn, /* from */
int debug = BGP_DEBUG(vpn, VPN_LEAK_TO_VRF); int debug = BGP_DEBUG(vpn, VPN_LEAK_TO_VRF);
if (debug) if (debug)
zlog_debug("%s: start (info_vpn=%p)", __func__, info_vpn); zlog_debug("%s: start (path_vpn=%p)", __func__, path_vpn);
/* Loop over VRFs */ /* Loop over VRFs */
for (ALL_LIST_ELEMENTS(bm->bgp, mnode, mnnode, bgp)) { for (ALL_LIST_ELEMENTS(bm->bgp, mnode, mnnode, bgp)) {
if (!info_vpn->extra if (!path_vpn->extra
|| info_vpn->extra->bgp_orig != bgp) { /* no loop */ || path_vpn->extra->bgp_orig != bgp) { /* no loop */
vpn_leak_to_vrf_update_onevrf(bgp, bgp_vpn, info_vpn); vpn_leak_to_vrf_update_onevrf(bgp, bgp_vpn, path_vpn);
} }
} }
} }
void vpn_leak_to_vrf_withdraw(struct bgp *bgp_vpn, /* from */ void vpn_leak_to_vrf_withdraw(struct bgp *bgp_vpn, /* from */
struct bgp_info *info_vpn) /* route */ struct bgp_path_info *path_vpn) /* route */
{ {
struct prefix *p; struct prefix *p;
afi_t afi; afi_t afi;
@ -1253,38 +1243,38 @@ void vpn_leak_to_vrf_withdraw(struct bgp *bgp_vpn, /* from */
struct bgp *bgp; struct bgp *bgp;
struct listnode *mnode, *mnnode; struct listnode *mnode, *mnnode;
struct bgp_node *bn; struct bgp_node *bn;
struct bgp_info *bi; struct bgp_path_info *bpi;
const char *debugmsg; const char *debugmsg;
char buf_prefix[PREFIX_STRLEN]; char buf_prefix[PREFIX_STRLEN];
int debug = BGP_DEBUG(vpn, VPN_LEAK_TO_VRF); int debug = BGP_DEBUG(vpn, VPN_LEAK_TO_VRF);
if (debug) { if (debug) {
prefix2str(&info_vpn->net->p, buf_prefix, sizeof(buf_prefix)); prefix2str(&path_vpn->net->p, buf_prefix, sizeof(buf_prefix));
zlog_debug("%s: entry: p=%s, type=%d, sub_type=%d", zlog_debug("%s: entry: p=%s, type=%d, sub_type=%d", __func__,
__func__, buf_prefix, buf_prefix, path_vpn->type, path_vpn->sub_type);
info_vpn->type, info_vpn->sub_type);
} }
if (debug) if (debug)
zlog_debug("%s: start (info_vpn=%p)", __func__, info_vpn); zlog_debug("%s: start (path_vpn=%p)", __func__, path_vpn);
if (!info_vpn->net) { if (!path_vpn->net) {
#if ENABLE_BGP_VNC #if ENABLE_BGP_VNC
/* BGP_ROUTE_RFP routes do not have info_vpn->net set (yet) */ /* BGP_ROUTE_RFP routes do not have path_vpn->net set (yet) */
if (info_vpn->type == ZEBRA_ROUTE_BGP && if (path_vpn->type == ZEBRA_ROUTE_BGP
info_vpn->sub_type == BGP_ROUTE_RFP) { && path_vpn->sub_type == BGP_ROUTE_RFP) {
return; return;
} }
#endif #endif
if (debug) if (debug)
zlog_debug("%s: info_vpn->net unexpectedly NULL, no prefix, bailing", zlog_debug(
"%s: path_vpn->net unexpectedly NULL, no prefix, bailing",
__func__); __func__);
return; return;
} }
p = &info_vpn->net->p; p = &path_vpn->net->p;
afi = family2afi(p->family); afi = family2afi(p->family);
/* Loop over VRFs */ /* Loop over VRFs */
@ -1299,7 +1289,7 @@ void vpn_leak_to_vrf_withdraw(struct bgp *bgp_vpn, /* from */
/* Check for intersection of route targets */ /* Check for intersection of route targets */
if (!ecom_intersect(bgp->vpn_policy[afi] if (!ecom_intersect(bgp->vpn_policy[afi]
.rtlist[BGP_VPN_POLICY_DIR_FROMVPN], .rtlist[BGP_VPN_POLICY_DIR_FROMVPN],
info_vpn->attr->ecommunity)) { path_vpn->attr->ecommunity)) {
continue; continue;
} }
@ -1309,19 +1299,20 @@ void vpn_leak_to_vrf_withdraw(struct bgp *bgp_vpn, /* from */
bgp->name_pretty); bgp->name_pretty);
bn = bgp_afi_node_get(bgp->rib[afi][safi], afi, safi, p, NULL); bn = bgp_afi_node_get(bgp->rib[afi][safi], afi, safi, p, NULL);
for (bi = (bn ? bn->info : NULL); bi; bi = bi->next) { for (bpi = (bn ? bn->info : NULL); bpi; bpi = bpi->next) {
if (bi->extra if (bpi->extra
&& (struct bgp_info *)bi->extra->parent && (struct bgp_path_info *)bpi->extra->parent
== info_vpn) { == path_vpn) {
break; break;
} }
} }
if (bi) { if (bpi) {
if (debug) if (debug)
zlog_debug("%s: deleting bi %p", __func__, bi); zlog_debug("%s: deleting bpi %p", __func__,
bgp_aggregate_decrement(bgp, p, bi, afi, safi); bpi);
bgp_info_delete(bn, bi); bgp_aggregate_decrement(bgp, p, bpi, afi, safi);
bgp_path_info_delete(bn, bpi);
bgp_process(bgp, bn, afi, safi); bgp_process(bgp, bn, afi, safi);
} }
bgp_unlock_node(bn); bgp_unlock_node(bn);
@ -1332,25 +1323,25 @@ void vpn_leak_to_vrf_withdraw_all(struct bgp *bgp_vrf, /* to */
afi_t afi) afi_t afi)
{ {
struct bgp_node *bn; struct bgp_node *bn;
struct bgp_info *bi; struct bgp_path_info *bpi;
safi_t safi = SAFI_UNICAST; safi_t safi = SAFI_UNICAST;
int debug = BGP_DEBUG(vpn, VPN_LEAK_TO_VRF); int debug = BGP_DEBUG(vpn, VPN_LEAK_TO_VRF);
if (debug) if (debug)
zlog_debug("%s: entry", __func__); zlog_debug("%s: entry", __func__);
/* /*
* Walk vrf table, delete bi with bgp_orig in a different vrf * Walk vrf table, delete bpi with bgp_orig in a different vrf
*/ */
for (bn = bgp_table_top(bgp_vrf->rib[afi][safi]); bn; for (bn = bgp_table_top(bgp_vrf->rib[afi][safi]); bn;
bn = bgp_route_next(bn)) { bn = bgp_route_next(bn)) {
for (bi = bn->info; bi; bi = bi->next) { for (bpi = bn->info; bpi; bpi = bpi->next) {
if (bi->extra && bi->extra->bgp_orig != bgp_vrf) { if (bpi->extra && bpi->extra->bgp_orig != bgp_vrf) {
/* delete route */ /* delete route */
bgp_aggregate_decrement(bgp_vrf, &bn->p, bi, bgp_aggregate_decrement(bgp_vrf, &bn->p, bpi,
afi, safi); afi, safi);
bgp_info_delete(bn, bi); bgp_path_info_delete(bn, bpi);
bgp_process(bgp_vrf, bn, afi, safi); bgp_process(bgp_vrf, bn, afi, safi);
} }
} }
@ -1375,7 +1366,7 @@ void vpn_leak_to_vrf_update_all(struct bgp *bgp_vrf, /* to */
struct bgp_table *table; struct bgp_table *table;
struct bgp_node *bn; struct bgp_node *bn;
struct bgp_info *bi; struct bgp_path_info *bpi;
memset(&prd, 0, sizeof(prd)); memset(&prd, 0, sizeof(prd));
prd.family = AF_UNSPEC; prd.family = AF_UNSPEC;
@ -1390,13 +1381,14 @@ void vpn_leak_to_vrf_update_all(struct bgp *bgp_vrf, /* to */
for (bn = bgp_table_top(table); bn; bn = bgp_route_next(bn)) { for (bn = bgp_table_top(table); bn; bn = bgp_route_next(bn)) {
for (bi = bn->info; bi; bi = bi->next) { for (bpi = bn->info; bpi; bpi = bpi->next) {
if (bi->extra && bi->extra->bgp_orig == bgp_vrf) if (bpi->extra
&& bpi->extra->bgp_orig == bgp_vrf)
continue; continue;
vpn_leak_to_vrf_update_onevrf(bgp_vrf, bgp_vpn, vpn_leak_to_vrf_update_onevrf(bgp_vrf, bgp_vpn,
bi); bpi);
} }
} }
} }

View File

@ -53,10 +53,10 @@ extern int bgp_show_mpls_vpn(struct vty *vty, afi_t afi, struct prefix_rd *prd,
int tags, bool use_json); int tags, bool use_json);
extern void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, struct bgp *bgp_vrf, extern void vpn_leak_from_vrf_update(struct bgp *bgp_vpn, struct bgp *bgp_vrf,
struct bgp_info *info_vrf); struct bgp_path_info *path_vrf);
extern void vpn_leak_from_vrf_withdraw(struct bgp *bgp_vpn, struct bgp *bgp_vrf, extern void vpn_leak_from_vrf_withdraw(struct bgp *bgp_vpn, struct bgp *bgp_vrf,
struct bgp_info *info_vrf); struct bgp_path_info *path_vrf);
extern void vpn_leak_from_vrf_withdraw_all(struct bgp *bgp_vpn, extern void vpn_leak_from_vrf_withdraw_all(struct bgp *bgp_vpn,
struct bgp *bgp_vrf, afi_t afi); struct bgp *bgp_vrf, afi_t afi);
@ -70,10 +70,10 @@ extern void vpn_leak_to_vrf_update_all(struct bgp *bgp_vrf, struct bgp *bgp_vpn,
afi_t afi); afi_t afi);
extern void vpn_leak_to_vrf_update(struct bgp *bgp_vpn, extern void vpn_leak_to_vrf_update(struct bgp *bgp_vpn,
struct bgp_info *info_vpn); struct bgp_path_info *path_vpn);
extern void vpn_leak_to_vrf_withdraw(struct bgp *bgp_vpn, extern void vpn_leak_to_vrf_withdraw(struct bgp *bgp_vpn,
struct bgp_info *info_vpn); struct bgp_path_info *path_vpn);
extern void vpn_leak_zebra_vrf_label_update(struct bgp *bgp, afi_t afi); extern void vpn_leak_zebra_vrf_label_update(struct bgp *bgp, afi_t afi);
extern void vpn_leak_zebra_vrf_label_withdraw(struct bgp *bgp, afi_t afi); extern void vpn_leak_zebra_vrf_label_withdraw(struct bgp *bgp, afi_t afi);

View File

@ -63,7 +63,7 @@ struct bgp_nexthop_cache {
struct bgp_node *node; struct bgp_node *node;
void *nht_info; /* In BGP, peer session */ void *nht_info; /* In BGP, peer session */
LIST_HEAD(path_list, bgp_info) paths; LIST_HEAD(path_list, bgp_path_info) paths;
unsigned int path_count; unsigned int path_count;
struct bgp *bgp; struct bgp *bgp;
}; };
@ -74,8 +74,6 @@ struct tip_addr {
int refcnt; int refcnt;
}; };
extern int bgp_nexthop_lookup(afi_t, struct peer *peer, struct bgp_info *,
int *, int *);
extern void bgp_connected_add(struct bgp *bgp, struct connected *c); extern void bgp_connected_add(struct bgp *bgp, struct connected *c);
extern void bgp_connected_delete(struct bgp *bgp, struct connected *c); extern void bgp_connected_delete(struct bgp *bgp, struct connected *c);
extern int bgp_subgrp_multiaccess_check_v4(struct in_addr nexthop, extern int bgp_subgrp_multiaccess_check_v4(struct in_addr nexthop,

View File

@ -50,9 +50,9 @@ static void register_zebra_rnh(struct bgp_nexthop_cache *bnc,
static void unregister_zebra_rnh(struct bgp_nexthop_cache *bnc, static void unregister_zebra_rnh(struct bgp_nexthop_cache *bnc,
int is_bgp_static_route); int is_bgp_static_route);
static void evaluate_paths(struct bgp_nexthop_cache *bnc); static void evaluate_paths(struct bgp_nexthop_cache *bnc);
static int make_prefix(int afi, struct bgp_info *ri, struct prefix *p); static int make_prefix(int afi, struct bgp_path_info *pi, struct prefix *p);
static void path_nh_map(struct bgp_info *path, struct bgp_nexthop_cache *bnc, static void path_nh_map(struct bgp_path_info *path,
int keep); struct bgp_nexthop_cache *bnc, int keep);
static int bgp_isvalid_nexthop(struct bgp_nexthop_cache *bnc) static int bgp_isvalid_nexthop(struct bgp_nexthop_cache *bnc)
{ {
@ -66,7 +66,7 @@ static int bgp_isvalid_labeled_nexthop(struct bgp_nexthop_cache *bnc)
|| (bnc && CHECK_FLAG(bnc->flags, BGP_NEXTHOP_LABELED_VALID))); || (bnc && CHECK_FLAG(bnc->flags, BGP_NEXTHOP_LABELED_VALID)));
} }
int bgp_find_nexthop(struct bgp_info *path, int connected) int bgp_find_nexthop(struct bgp_path_info *path, int connected)
{ {
struct bgp_nexthop_cache *bnc = path->nexthop; struct bgp_nexthop_cache *bnc = path->nexthop;
@ -104,7 +104,7 @@ static void bgp_unlink_nexthop_check(struct bgp_nexthop_cache *bnc)
} }
} }
void bgp_unlink_nexthop(struct bgp_info *path) void bgp_unlink_nexthop(struct bgp_path_info *path)
{ {
struct bgp_nexthop_cache *bnc = path->nexthop; struct bgp_nexthop_cache *bnc = path->nexthop;
@ -143,7 +143,7 @@ void bgp_unlink_nexthop_by_peer(struct peer *peer)
* we need both the bgp_route and bgp_nexthop pointers. * we need both the bgp_route and bgp_nexthop pointers.
*/ */
int bgp_find_or_add_nexthop(struct bgp *bgp_route, struct bgp *bgp_nexthop, int bgp_find_or_add_nexthop(struct bgp *bgp_route, struct bgp *bgp_nexthop,
afi_t afi, struct bgp_info *ri, afi_t afi, struct bgp_path_info *pi,
struct peer *peer, int connected) struct peer *peer, int connected)
{ {
struct bgp_node *rn; struct bgp_node *rn;
@ -151,9 +151,9 @@ int bgp_find_or_add_nexthop(struct bgp *bgp_route, struct bgp *bgp_nexthop,
struct prefix p; struct prefix p;
int is_bgp_static_route = 0; int is_bgp_static_route = 0;
if (ri) { if (pi) {
is_bgp_static_route = ((ri->type == ZEBRA_ROUTE_BGP) is_bgp_static_route = ((pi->type == ZEBRA_ROUTE_BGP)
&& (ri->sub_type == BGP_ROUTE_STATIC)) && (pi->sub_type == BGP_ROUTE_STATIC))
? 1 ? 1
: 0; : 0;
@ -161,12 +161,12 @@ int bgp_find_or_add_nexthop(struct bgp *bgp_route, struct bgp *bgp_nexthop,
to derive to derive
address-family from the next-hop. */ address-family from the next-hop. */
if (!is_bgp_static_route) if (!is_bgp_static_route)
afi = BGP_ATTR_NEXTHOP_AFI_IP6(ri->attr) ? AFI_IP6 afi = BGP_ATTR_NEXTHOP_AFI_IP6(pi->attr) ? AFI_IP6
: AFI_IP; : AFI_IP;
/* This will return TRUE if the global IPv6 NH is a link local /* This will return TRUE if the global IPv6 NH is a link local
* addr */ * addr */
if (make_prefix(afi, ri, &p) < 0) if (make_prefix(afi, pi, &p) < 0)
return 1; return 1;
} else if (peer) { } else if (peer) {
if (!sockunion2hostprefix(&peer->su, &p)) { if (!sockunion2hostprefix(&peer->su, &p)) {
@ -246,19 +246,19 @@ int bgp_find_or_add_nexthop(struct bgp *bgp_route, struct bgp *bgp_nexthop,
bnc->flags |= BGP_NEXTHOP_VALID; bnc->flags |= BGP_NEXTHOP_VALID;
} else if (!CHECK_FLAG(bnc->flags, BGP_NEXTHOP_REGISTERED)) } else if (!CHECK_FLAG(bnc->flags, BGP_NEXTHOP_REGISTERED))
register_zebra_rnh(bnc, is_bgp_static_route); register_zebra_rnh(bnc, is_bgp_static_route);
if (ri && ri->nexthop != bnc) { if (pi && pi->nexthop != bnc) {
/* Unlink from existing nexthop cache, if any. This will also /* Unlink from existing nexthop cache, if any. This will also
* free * free
* the nexthop cache entry, if appropriate. * the nexthop cache entry, if appropriate.
*/ */
bgp_unlink_nexthop(ri); bgp_unlink_nexthop(pi);
path_nh_map(ri, bnc, 1); /* updates NHT ri list reference */ path_nh_map(pi, bnc, 1); /* updates NHT pi list reference */
if (CHECK_FLAG(bnc->flags, BGP_NEXTHOP_VALID) && bnc->metric) if (CHECK_FLAG(bnc->flags, BGP_NEXTHOP_VALID) && bnc->metric)
(bgp_info_extra_get(ri))->igpmetric = bnc->metric; (bgp_path_info_extra_get(pi))->igpmetric = bnc->metric;
else if (ri->extra) else if (pi->extra)
ri->extra->igpmetric = 0; pi->extra->igpmetric = 0;
} else if (peer) } else if (peer)
bnc->nht_info = (void *)peer; /* NHT peer reference */ bnc->nht_info = (void *)peer; /* NHT peer reference */
@ -527,11 +527,11 @@ void bgp_cleanup_nexthops(struct bgp *bgp)
* make_prefix - make a prefix structure from the path (essentially * make_prefix - make a prefix structure from the path (essentially
* path's node. * path's node.
*/ */
static int make_prefix(int afi, struct bgp_info *ri, struct prefix *p) static int make_prefix(int afi, struct bgp_path_info *pi, struct prefix *p)
{ {
int is_bgp_static = ((ri->type == ZEBRA_ROUTE_BGP) int is_bgp_static = ((pi->type == ZEBRA_ROUTE_BGP)
&& (ri->sub_type == BGP_ROUTE_STATIC)) && (pi->sub_type == BGP_ROUTE_STATIC))
? 1 ? 1
: 0; : 0;
@ -540,10 +540,10 @@ static int make_prefix(int afi, struct bgp_info *ri, struct prefix *p)
case AFI_IP: case AFI_IP:
p->family = AF_INET; p->family = AF_INET;
if (is_bgp_static) { if (is_bgp_static) {
p->u.prefix4 = ri->net->p.u.prefix4; p->u.prefix4 = pi->net->p.u.prefix4;
p->prefixlen = ri->net->p.prefixlen; p->prefixlen = pi->net->p.prefixlen;
} else { } else {
p->u.prefix4 = ri->attr->nexthop; p->u.prefix4 = pi->attr->nexthop;
p->prefixlen = IPV4_MAX_BITLEN; p->prefixlen = IPV4_MAX_BITLEN;
} }
break; break;
@ -551,10 +551,10 @@ static int make_prefix(int afi, struct bgp_info *ri, struct prefix *p)
p->family = AF_INET6; p->family = AF_INET6;
if (is_bgp_static) { if (is_bgp_static) {
p->u.prefix6 = ri->net->p.u.prefix6; p->u.prefix6 = pi->net->p.u.prefix6;
p->prefixlen = ri->net->p.prefixlen; p->prefixlen = pi->net->p.prefixlen;
} else { } else {
p->u.prefix6 = ri->attr->mp_nexthop_global; p->u.prefix6 = pi->attr->mp_nexthop_global;
p->prefixlen = IPV6_MAX_BITLEN; p->prefixlen = IPV6_MAX_BITLEN;
} }
break; break;
@ -673,7 +673,7 @@ static void unregister_zebra_rnh(struct bgp_nexthop_cache *bnc,
static void evaluate_paths(struct bgp_nexthop_cache *bnc) static void evaluate_paths(struct bgp_nexthop_cache *bnc)
{ {
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *path; struct bgp_path_info *path;
int afi; int afi;
struct peer *peer = (struct peer *)bnc->nht_info; struct peer *peer = (struct peer *)bnc->nht_info;
struct bgp_table *table; struct bgp_table *table;
@ -740,14 +740,16 @@ static void evaluate_paths(struct bgp_nexthop_cache *bnc)
(bnc_is_valid_nexthop ? "" : "not ")); (bnc_is_valid_nexthop ? "" : "not "));
} }
if ((CHECK_FLAG(path->flags, BGP_INFO_VALID) ? 1 : 0) if ((CHECK_FLAG(path->flags, BGP_PATH_VALID) ? 1 : 0)
!= bnc_is_valid_nexthop) { != bnc_is_valid_nexthop) {
if (CHECK_FLAG(path->flags, BGP_INFO_VALID)) { if (CHECK_FLAG(path->flags, BGP_PATH_VALID)) {
bgp_aggregate_decrement(bgp_path, &rn->p, bgp_aggregate_decrement(bgp_path, &rn->p,
path, afi, safi); path, afi, safi);
bgp_info_unset_flag(rn, path, BGP_INFO_VALID); bgp_path_info_unset_flag(rn, path,
BGP_PATH_VALID);
} else { } else {
bgp_info_set_flag(rn, path, BGP_INFO_VALID); bgp_path_info_set_flag(rn, path,
BGP_PATH_VALID);
bgp_aggregate_increment(bgp_path, &rn->p, bgp_aggregate_increment(bgp_path, &rn->p,
path, afi, safi); path, afi, safi);
} }
@ -756,13 +758,14 @@ static void evaluate_paths(struct bgp_nexthop_cache *bnc)
/* Copy the metric to the path. Will be used for bestpath /* Copy the metric to the path. Will be used for bestpath
* computation */ * computation */
if (bgp_isvalid_nexthop(bnc) && bnc->metric) if (bgp_isvalid_nexthop(bnc) && bnc->metric)
(bgp_info_extra_get(path))->igpmetric = bnc->metric; (bgp_path_info_extra_get(path))->igpmetric =
bnc->metric;
else if (path->extra) else if (path->extra)
path->extra->igpmetric = 0; path->extra->igpmetric = 0;
if (CHECK_FLAG(bnc->change_flags, BGP_NEXTHOP_METRIC_CHANGED) if (CHECK_FLAG(bnc->change_flags, BGP_NEXTHOP_METRIC_CHANGED)
|| CHECK_FLAG(bnc->change_flags, BGP_NEXTHOP_CHANGED)) || CHECK_FLAG(bnc->change_flags, BGP_NEXTHOP_CHANGED))
SET_FLAG(path->flags, BGP_INFO_IGP_CHANGED); SET_FLAG(path->flags, BGP_PATH_IGP_CHANGED);
bgp_process(bgp_path, rn, afi, safi); bgp_process(bgp_path, rn, afi, safi);
} }
@ -786,8 +789,8 @@ static void evaluate_paths(struct bgp_nexthop_cache *bnc)
* make - if set, make the association. if unset, just break the existing * make - if set, make the association. if unset, just break the existing
* association. * association.
*/ */
static void path_nh_map(struct bgp_info *path, struct bgp_nexthop_cache *bnc, static void path_nh_map(struct bgp_path_info *path,
int make) struct bgp_nexthop_cache *bnc, int make)
{ {
if (path->nexthop) { if (path->nexthop) {
LIST_REMOVE(path, nh_thread); LIST_REMOVE(path, nh_thread);

View File

@ -32,7 +32,7 @@ extern void bgp_parse_nexthop_update(int command, vrf_id_t vrf_id);
* p - path for which the nexthop object is being looked up * p - path for which the nexthop object is being looked up
* connected - True if NH MUST be a connected route * connected - True if NH MUST be a connected route
*/ */
extern int bgp_find_nexthop(struct bgp_info *p, int connected); extern int bgp_find_nexthop(struct bgp_path_info *p, int connected);
/** /**
* bgp_find_or_add_nexthop() - lookup the nexthop cache table for the bnc * bgp_find_or_add_nexthop() - lookup the nexthop cache table for the bnc
@ -47,16 +47,17 @@ extern int bgp_find_nexthop(struct bgp_info *p, int connected);
* connected - True if NH MUST be a connected route * connected - True if NH MUST be a connected route
*/ */
extern int bgp_find_or_add_nexthop(struct bgp *bgp_route, extern int bgp_find_or_add_nexthop(struct bgp *bgp_route,
struct bgp *bgp_nexthop, afi_t a, struct bgp_info *p, struct bgp *bgp_nexthop, afi_t a,
struct peer *peer, int connected); struct bgp_path_info *p, struct peer *peer,
int connected);
/** /**
* bgp_unlink_nexthop() - Unlink the nexthop object from the path structure. * bgp_unlink_nexthop() - Unlink the nexthop object from the path structure.
* ARGUMENTS: * ARGUMENTS:
* p - path structure. * p - path structure.
*/ */
extern void bgp_unlink_nexthop(struct bgp_info *p); extern void bgp_unlink_nexthop(struct bgp_path_info *p);
void bgp_unlink_nexthop_by_peer(struct peer *); void bgp_unlink_nexthop_by_peer(struct peer *peer);
/** /**
* bgp_delete_connected_nexthop() - Reset the 'peer' pointer for a connected * bgp_delete_connected_nexthop() - Reset the 'peer' pointer for a connected

View File

@ -227,7 +227,7 @@ struct bgp_pbr_or_filter {
}; };
static void bgp_pbr_policyroute_add_to_zebra_unit(struct bgp *bgp, static void bgp_pbr_policyroute_add_to_zebra_unit(struct bgp *bgp,
struct bgp_info *binfo, struct bgp_path_info *path,
struct bgp_pbr_filter *bpf, struct bgp_pbr_filter *bpf,
struct nexthop *nh, struct nexthop *nh,
float *rate); float *rate);
@ -627,7 +627,7 @@ static int bgp_pbr_validate_policy_route(struct bgp_pbr_entry_main *api)
/* return -1 if build or validation failed */ /* return -1 if build or validation failed */
static int bgp_pbr_build_and_validate_entry(struct prefix *p, static int bgp_pbr_build_and_validate_entry(struct prefix *p,
struct bgp_info *info, struct bgp_path_info *path,
struct bgp_pbr_entry_main *api) struct bgp_pbr_entry_main *api)
{ {
int ret; int ret;
@ -645,8 +645,8 @@ static int bgp_pbr_build_and_validate_entry(struct prefix *p,
if (ret < 0) if (ret < 0)
return -1; return -1;
/* extract actiosn from flowspec ecom list */ /* extract actiosn from flowspec ecom list */
if (info && info->attr && info->attr->ecommunity) { if (path && path->attr && path->attr->ecommunity) {
ecom = info->attr->ecommunity; ecom = path->attr->ecommunity;
for (i = 0; i < ecom->size; i++) { for (i = 0; i < ecom->size; i++) {
ecom_eval = (struct ecommunity_val *) ecom_eval = (struct ecommunity_val *)
(ecom->val + (i * ECOMMUNITY_SIZE)); (ecom->val + (i * ECOMMUNITY_SIZE));
@ -690,7 +690,7 @@ static int bgp_pbr_build_and_validate_entry(struct prefix *p,
(char)ECOMMUNITY_REDIRECT_IP_NH)) { (char)ECOMMUNITY_REDIRECT_IP_NH)) {
api_action->action = ACTION_REDIRECT_IP; api_action->action = ACTION_REDIRECT_IP;
api_action->u.zr.redirect_ip_v4.s_addr = api_action->u.zr.redirect_ip_v4.s_addr =
info->attr->nexthop.s_addr; path->attr->nexthop.s_addr;
api_action->u.zr.duplicate = ecom_eval->val[7]; api_action->u.zr.duplicate = ecom_eval->val[7];
} else { } else {
if (ecom_eval->val[0] != if (ecom_eval->val[0] !=
@ -1223,16 +1223,16 @@ static void bgp_pbr_flush_entry(struct bgp *bgp, struct bgp_pbr_action *bpa,
bgp_send_pbr_ipset_entry_match(bpme, false); bgp_send_pbr_ipset_entry_match(bpme, false);
bpme->installed = false; bpme->installed = false;
bpme->backpointer = NULL; bpme->backpointer = NULL;
if (bpme->bgp_info) { if (bpme->path) {
struct bgp_info *bgp_info; struct bgp_path_info *path;
struct bgp_info_extra *extra; struct bgp_path_info_extra *extra;
/* unlink bgp_info to bpme */ /* unlink bgp_path_info to bpme */
bgp_info = (struct bgp_info *)bpme->bgp_info; path = (struct bgp_path_info *)bpme->path;
extra = bgp_info_extra_get(bgp_info); extra = bgp_path_info_extra_get(path);
if (extra->bgp_fs_pbr) if (extra->bgp_fs_pbr)
listnode_delete(extra->bgp_fs_pbr, bpme); listnode_delete(extra->bgp_fs_pbr, bpme);
bpme->bgp_info = NULL; bpme->path = NULL;
} }
} }
hash_release(bpm->entry_hash, bpme); hash_release(bpm->entry_hash, bpme);
@ -1304,9 +1304,8 @@ static int bgp_pbr_get_remaining_entry(struct hash_backet *backet, void *arg)
return HASHWALK_ABORT; return HASHWALK_ABORT;
} }
static void bgp_pbr_policyroute_remove_from_zebra_unit(struct bgp *bgp, static void bgp_pbr_policyroute_remove_from_zebra_unit(
struct bgp_info *binfo, struct bgp *bgp, struct bgp_path_info *path, struct bgp_pbr_filter *bpf)
struct bgp_pbr_filter *bpf)
{ {
struct bgp_pbr_match temp; struct bgp_pbr_match temp;
struct bgp_pbr_match_entry temp2; struct bgp_pbr_match_entry temp2;
@ -1438,13 +1437,10 @@ static uint8_t bgp_pbr_next_type_entry(uint8_t type_entry)
return 0; return 0;
} }
static void bgp_pbr_icmp_action(struct bgp *bgp, static void bgp_pbr_icmp_action(struct bgp *bgp, struct bgp_path_info *path,
struct bgp_info *binfo,
struct bgp_pbr_filter *bpf, struct bgp_pbr_filter *bpf,
struct bgp_pbr_or_filter *bpof, struct bgp_pbr_or_filter *bpof, bool add,
bool add, struct nexthop *nh, float *rate)
struct nexthop *nh,
float *rate)
{ {
struct bgp_pbr_range_port srcp, dstp; struct bgp_pbr_range_port srcp, dstp;
struct bgp_pbr_val_mask *icmp_type, *icmp_code; struct bgp_pbr_val_mask *icmp_type, *icmp_code;
@ -1466,11 +1462,11 @@ static void bgp_pbr_icmp_action(struct bgp *bgp,
for (ALL_LIST_ELEMENTS_RO(bpof->icmp_code, cnode, icmp_code)) { for (ALL_LIST_ELEMENTS_RO(bpof->icmp_code, cnode, icmp_code)) {
dstp.min_port = icmp_code->val; dstp.min_port = icmp_code->val;
if (add) if (add)
bgp_pbr_policyroute_add_to_zebra_unit(bgp, binfo, bgp_pbr_policyroute_add_to_zebra_unit(
bpf, nh, rate); bgp, path, bpf, nh, rate);
else else
bgp_pbr_policyroute_remove_from_zebra_unit( bgp_pbr_policyroute_remove_from_zebra_unit(
bgp, binfo, bpf); bgp, path, bpf);
} }
return; return;
} }
@ -1487,31 +1483,27 @@ static void bgp_pbr_icmp_action(struct bgp *bgp,
dstp.max_port = 255; dstp.max_port = 255;
if (add) if (add)
bgp_pbr_policyroute_add_to_zebra_unit( bgp_pbr_policyroute_add_to_zebra_unit(
bgp, binfo, bgp, path, bpf, nh, rate);
bpf, nh, rate);
else else
bgp_pbr_policyroute_remove_from_zebra_unit(bgp, bgp_pbr_policyroute_remove_from_zebra_unit(
binfo, bpf); bgp, path, bpf);
continue; continue;
} }
for (ALL_LIST_ELEMENTS_RO(bpof->icmp_code, cnode, icmp_code)) { for (ALL_LIST_ELEMENTS_RO(bpof->icmp_code, cnode, icmp_code)) {
dstp.min_port = icmp_code->val; dstp.min_port = icmp_code->val;
if (add) if (add)
bgp_pbr_policyroute_add_to_zebra_unit( bgp_pbr_policyroute_add_to_zebra_unit(
bgp, binfo, bgp, path, bpf, nh, rate);
bpf, nh, rate);
else else
bgp_pbr_policyroute_remove_from_zebra_unit( bgp_pbr_policyroute_remove_from_zebra_unit(
bgp, binfo, bpf); bgp, path, bpf);
} }
} }
} }
static void bgp_pbr_policyroute_remove_from_zebra_recursive(struct bgp *bgp, static void bgp_pbr_policyroute_remove_from_zebra_recursive(
struct bgp_info *binfo, struct bgp *bgp, struct bgp_path_info *path, struct bgp_pbr_filter *bpf,
struct bgp_pbr_filter *bpf, struct bgp_pbr_or_filter *bpof, uint8_t type_entry)
struct bgp_pbr_or_filter *bpof,
uint8_t type_entry)
{ {
struct listnode *node, *nnode; struct listnode *node, *nnode;
struct bgp_pbr_val_mask *valmask; struct bgp_pbr_val_mask *valmask;
@ -1520,8 +1512,8 @@ static void bgp_pbr_policyroute_remove_from_zebra_recursive(struct bgp *bgp,
struct bgp_pbr_val_mask **target_val; struct bgp_pbr_val_mask **target_val;
if (type_entry == 0) if (type_entry == 0)
return bgp_pbr_policyroute_remove_from_zebra_unit(bgp, return bgp_pbr_policyroute_remove_from_zebra_unit(bgp, path,
binfo, bpf); bpf);
next_type_entry = bgp_pbr_next_type_entry(type_entry); next_type_entry = bgp_pbr_next_type_entry(type_entry);
if (type_entry == FLOWSPEC_TCP_FLAGS && bpof->tcpflags) { if (type_entry == FLOWSPEC_TCP_FLAGS && bpof->tcpflags) {
orig_list = bpof->tcpflags; orig_list = bpof->tcpflags;
@ -1538,53 +1530,43 @@ static void bgp_pbr_policyroute_remove_from_zebra_recursive(struct bgp *bgp,
} else if (type_entry == FLOWSPEC_ICMP_TYPE && } else if (type_entry == FLOWSPEC_ICMP_TYPE &&
(bpof->icmp_type || bpof->icmp_code)) { (bpof->icmp_type || bpof->icmp_code)) {
/* enumerate list for icmp - must be last one */ /* enumerate list for icmp - must be last one */
bgp_pbr_icmp_action(bgp, binfo, bpf, bpof, false, NULL, NULL); bgp_pbr_icmp_action(bgp, path, bpf, bpof, false, NULL, NULL);
return; return;
} else { } else {
return bgp_pbr_policyroute_remove_from_zebra_recursive(bgp, return bgp_pbr_policyroute_remove_from_zebra_recursive(
binfo, bgp, path, bpf, bpof, next_type_entry);
bpf, bpof,
next_type_entry);
} }
for (ALL_LIST_ELEMENTS(orig_list, node, nnode, valmask)) { for (ALL_LIST_ELEMENTS(orig_list, node, nnode, valmask)) {
*target_val = valmask; *target_val = valmask;
bgp_pbr_policyroute_remove_from_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_remove_from_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, next_type_entry);
next_type_entry);
} }
} }
static void bgp_pbr_policyroute_remove_from_zebra(struct bgp *bgp, static void bgp_pbr_policyroute_remove_from_zebra(
struct bgp_info *binfo, struct bgp *bgp, struct bgp_path_info *path, struct bgp_pbr_filter *bpf,
struct bgp_pbr_filter *bpf,
struct bgp_pbr_or_filter *bpof) struct bgp_pbr_or_filter *bpof)
{ {
if (!bpof) if (!bpof)
return bgp_pbr_policyroute_remove_from_zebra_unit(bgp, return bgp_pbr_policyroute_remove_from_zebra_unit(bgp, path,
binfo,
bpf); bpf);
if (bpof->tcpflags) if (bpof->tcpflags)
bgp_pbr_policyroute_remove_from_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_remove_from_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, FLOWSPEC_TCP_FLAGS);
FLOWSPEC_TCP_FLAGS);
else if (bpof->dscp) else if (bpof->dscp)
bgp_pbr_policyroute_remove_from_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_remove_from_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, FLOWSPEC_DSCP);
FLOWSPEC_DSCP);
else if (bpof->pkt_len) else if (bpof->pkt_len)
bgp_pbr_policyroute_remove_from_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_remove_from_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, FLOWSPEC_PKT_LEN);
FLOWSPEC_PKT_LEN);
else if (bpof->fragment) else if (bpof->fragment)
bgp_pbr_policyroute_remove_from_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_remove_from_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, FLOWSPEC_FRAGMENT);
FLOWSPEC_FRAGMENT);
else if (bpof->icmp_type || bpof->icmp_code) else if (bpof->icmp_type || bpof->icmp_code)
bgp_pbr_policyroute_remove_from_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_remove_from_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, FLOWSPEC_ICMP_TYPE);
FLOWSPEC_ICMP_TYPE);
else else
bgp_pbr_policyroute_remove_from_zebra_unit(bgp, binfo, bpf); bgp_pbr_policyroute_remove_from_zebra_unit(bgp, path, bpf);
/* flush bpof */ /* flush bpof */
if (bpof->tcpflags) if (bpof->tcpflags)
list_delete_all_node(bpof->tcpflags); list_delete_all_node(bpof->tcpflags);
@ -1692,7 +1674,7 @@ static void bgp_pbr_dump_entry(struct bgp_pbr_filter *bpf, bool add)
} }
static void bgp_pbr_policyroute_add_to_zebra_unit(struct bgp *bgp, static void bgp_pbr_policyroute_add_to_zebra_unit(struct bgp *bgp,
struct bgp_info *binfo, struct bgp_path_info *path,
struct bgp_pbr_filter *bpf, struct bgp_pbr_filter *bpf,
struct nexthop *nh, struct nexthop *nh,
float *rate) float *rate)
@ -1848,19 +1830,21 @@ static void bgp_pbr_policyroute_add_to_zebra_unit(struct bgp *bgp,
bpme->installed = false; bpme->installed = false;
bpme->install_in_progress = false; bpme->install_in_progress = false;
/* link bgp info to bpme */ /* link bgp info to bpme */
bpme->bgp_info = (void *)binfo; bpme->path = (void *)path;
} else } else
bpme_found = true; bpme_found = true;
/* already installed */ /* already installed */
if (bpme_found) { if (bpme_found) {
struct bgp_info_extra *extra = bgp_info_extra_get(binfo); struct bgp_path_info_extra *extra =
bgp_path_info_extra_get(path);
if (extra && extra->bgp_fs_pbr && if (extra && extra->bgp_fs_pbr &&
listnode_lookup(extra->bgp_fs_pbr, bpme)) { listnode_lookup(extra->bgp_fs_pbr, bpme)) {
if (BGP_DEBUG(pbr, PBR_ERROR)) if (BGP_DEBUG(pbr, PBR_ERROR))
zlog_err("%s: entry %p/%p already installed in bgp pbr", zlog_err(
__func__, binfo, bpme); "%s: entry %p/%p already installed in bgp pbr",
__func__, path, bpme);
return; return;
} }
} }
@ -1911,12 +1895,9 @@ static void bgp_pbr_policyroute_add_to_zebra_unit(struct bgp *bgp,
} }
static void bgp_pbr_policyroute_add_to_zebra_recursive(struct bgp *bgp, static void bgp_pbr_policyroute_add_to_zebra_recursive(
struct bgp_info *binfo, struct bgp *bgp, struct bgp_path_info *path, struct bgp_pbr_filter *bpf,
struct bgp_pbr_filter *bpf, struct bgp_pbr_or_filter *bpof, struct nexthop *nh, float *rate,
struct bgp_pbr_or_filter *bpof,
struct nexthop *nh,
float *rate,
uint8_t type_entry) uint8_t type_entry)
{ {
struct listnode *node, *nnode; struct listnode *node, *nnode;
@ -1926,8 +1907,8 @@ static void bgp_pbr_policyroute_add_to_zebra_recursive(struct bgp *bgp,
struct bgp_pbr_val_mask **target_val; struct bgp_pbr_val_mask **target_val;
if (type_entry == 0) if (type_entry == 0)
return bgp_pbr_policyroute_add_to_zebra_unit(bgp, binfo, bpf, return bgp_pbr_policyroute_add_to_zebra_unit(bgp, path, bpf, nh,
nh, rate); rate);
next_type_entry = bgp_pbr_next_type_entry(type_entry); next_type_entry = bgp_pbr_next_type_entry(type_entry);
if (type_entry == FLOWSPEC_TCP_FLAGS && bpof->tcpflags) { if (type_entry == FLOWSPEC_TCP_FLAGS && bpof->tcpflags) {
orig_list = bpof->tcpflags; orig_list = bpof->tcpflags;
@ -1944,59 +1925,45 @@ static void bgp_pbr_policyroute_add_to_zebra_recursive(struct bgp *bgp,
} else if (type_entry == FLOWSPEC_ICMP_TYPE && } else if (type_entry == FLOWSPEC_ICMP_TYPE &&
(bpof->icmp_type || bpof->icmp_code)) { (bpof->icmp_type || bpof->icmp_code)) {
/* enumerate list for icmp - must be last one */ /* enumerate list for icmp - must be last one */
bgp_pbr_icmp_action(bgp, binfo, bpf, bpof, true, nh, rate); bgp_pbr_icmp_action(bgp, path, bpf, bpof, true, nh, rate);
return; return;
} else { } else {
return bgp_pbr_policyroute_add_to_zebra_recursive(bgp, binfo, return bgp_pbr_policyroute_add_to_zebra_recursive(
bpf, bpof, nh, rate, bgp, path, bpf, bpof, nh, rate, next_type_entry);
next_type_entry);
} }
for (ALL_LIST_ELEMENTS(orig_list, node, nnode, valmask)) { for (ALL_LIST_ELEMENTS(orig_list, node, nnode, valmask)) {
*target_val = valmask; *target_val = valmask;
bgp_pbr_policyroute_add_to_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_add_to_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, nh, rate, next_type_entry);
nh, rate,
next_type_entry);
} }
} }
static void bgp_pbr_policyroute_add_to_zebra(struct bgp *bgp, static void bgp_pbr_policyroute_add_to_zebra(struct bgp *bgp,
struct bgp_info *binfo, struct bgp_path_info *path,
struct bgp_pbr_filter *bpf, struct bgp_pbr_filter *bpf,
struct bgp_pbr_or_filter *bpof, struct bgp_pbr_or_filter *bpof,
struct nexthop *nh, struct nexthop *nh, float *rate)
float *rate)
{ {
if (!bpof) if (!bpof)
return bgp_pbr_policyroute_add_to_zebra_unit(bgp, binfo, return bgp_pbr_policyroute_add_to_zebra_unit(bgp, path, bpf, nh,
bpf, nh, rate); rate);
if (bpof->tcpflags) if (bpof->tcpflags)
bgp_pbr_policyroute_add_to_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_add_to_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, nh, rate, FLOWSPEC_TCP_FLAGS);
nh, rate,
FLOWSPEC_TCP_FLAGS);
else if (bpof->dscp) else if (bpof->dscp)
bgp_pbr_policyroute_add_to_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_add_to_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, nh, rate, FLOWSPEC_DSCP);
nh, rate,
FLOWSPEC_DSCP);
else if (bpof->pkt_len) else if (bpof->pkt_len)
bgp_pbr_policyroute_add_to_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_add_to_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, nh, rate, FLOWSPEC_PKT_LEN);
nh, rate,
FLOWSPEC_PKT_LEN);
else if (bpof->fragment) else if (bpof->fragment)
bgp_pbr_policyroute_add_to_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_add_to_zebra_recursive(
bpf, bpof, bgp, path, bpf, bpof, nh, rate, FLOWSPEC_FRAGMENT);
nh, rate,
FLOWSPEC_FRAGMENT);
else if (bpof->icmp_type || bpof->icmp_code) else if (bpof->icmp_type || bpof->icmp_code)
bgp_pbr_policyroute_add_to_zebra_recursive(bgp, binfo, bgp_pbr_policyroute_add_to_zebra_recursive(
bpf, bpof, nh, rate, bgp, path, bpf, bpof, nh, rate, FLOWSPEC_ICMP_TYPE);
FLOWSPEC_ICMP_TYPE);
else else
bgp_pbr_policyroute_add_to_zebra_unit(bgp, binfo, bpf, bgp_pbr_policyroute_add_to_zebra_unit(bgp, path, bpf, nh, rate);
nh, rate);
/* flush bpof */ /* flush bpof */
if (bpof->tcpflags) if (bpof->tcpflags)
list_delete_all_node(bpof->tcpflags); list_delete_all_node(bpof->tcpflags);
@ -2012,10 +1979,8 @@ static void bgp_pbr_policyroute_add_to_zebra(struct bgp *bgp,
list_delete_all_node(bpof->icmp_code); list_delete_all_node(bpof->icmp_code);
} }
static void bgp_pbr_handle_entry(struct bgp *bgp, static void bgp_pbr_handle_entry(struct bgp *bgp, struct bgp_path_info *path,
struct bgp_info *binfo, struct bgp_pbr_entry_main *api, bool add)
struct bgp_pbr_entry_main *api,
bool add)
{ {
struct nexthop nh; struct nexthop nh;
int i = 0; int i = 0;
@ -2151,9 +2116,8 @@ static void bgp_pbr_handle_entry(struct bgp *bgp,
bpf.src_port = srcp; bpf.src_port = srcp;
bpf.dst_port = dstp; bpf.dst_port = dstp;
if (!add) if (!add)
return bgp_pbr_policyroute_remove_from_zebra(bgp, return bgp_pbr_policyroute_remove_from_zebra(bgp, path, &bpf,
binfo, &bpof);
&bpf, &bpof);
/* no action for add = true */ /* no action for add = true */
for (i = 0; i < api->action_num; i++) { for (i = 0; i < api->action_num; i++) {
switch (api->actions[i].action) { switch (api->actions[i].action) {
@ -2162,9 +2126,8 @@ static void bgp_pbr_handle_entry(struct bgp *bgp,
if (api->actions[i].u.r.rate == 0) { if (api->actions[i].u.r.rate == 0) {
nh.vrf_id = api->vrf_id; nh.vrf_id = api->vrf_id;
nh.type = NEXTHOP_TYPE_BLACKHOLE; nh.type = NEXTHOP_TYPE_BLACKHOLE;
bgp_pbr_policyroute_add_to_zebra(bgp, binfo, bgp_pbr_policyroute_add_to_zebra(
&bpf, &bpof, bgp, path, &bpf, &bpof, &nh, &rate);
&nh, &rate);
} else { } else {
/* update rate. can be reentrant */ /* update rate. can be reentrant */
rate = api->actions[i].u.r.rate; rate = api->actions[i].u.r.rate;
@ -2204,8 +2167,7 @@ static void bgp_pbr_handle_entry(struct bgp *bgp,
nh.gate.ipv4.s_addr = nh.gate.ipv4.s_addr =
api->actions[i].u.zr.redirect_ip_v4.s_addr; api->actions[i].u.zr.redirect_ip_v4.s_addr;
nh.vrf_id = api->vrf_id; nh.vrf_id = api->vrf_id;
bgp_pbr_policyroute_add_to_zebra(bgp, binfo, bgp_pbr_policyroute_add_to_zebra(bgp, path, &bpf, &bpof,
&bpf, &bpof,
&nh, &rate); &nh, &rate);
/* XXX combination with REDIRECT_VRF /* XXX combination with REDIRECT_VRF
* + REDIRECT_NH_IP not done * + REDIRECT_NH_IP not done
@ -2215,8 +2177,7 @@ static void bgp_pbr_handle_entry(struct bgp *bgp,
case ACTION_REDIRECT: case ACTION_REDIRECT:
nh.vrf_id = api->actions[i].u.redirect_vrf; nh.vrf_id = api->actions[i].u.redirect_vrf;
nh.type = NEXTHOP_TYPE_IPV4; nh.type = NEXTHOP_TYPE_IPV4;
bgp_pbr_policyroute_add_to_zebra(bgp, binfo, bgp_pbr_policyroute_add_to_zebra(bgp, path, &bpf, &bpof,
&bpf, &bpof,
&nh, &rate); &nh, &rate);
continue_loop = 0; continue_loop = 0;
break; break;
@ -2236,7 +2197,7 @@ static void bgp_pbr_handle_entry(struct bgp *bgp,
} }
void bgp_pbr_update_entry(struct bgp *bgp, struct prefix *p, void bgp_pbr_update_entry(struct bgp *bgp, struct prefix *p,
struct bgp_info *info, afi_t afi, safi_t safi, struct bgp_path_info *info, afi_t afi, safi_t safi,
bool nlri_update) bool nlri_update)
{ {
struct bgp_pbr_entry_main api; struct bgp_pbr_entry_main api;

View File

@ -219,7 +219,7 @@ struct bgp_pbr_match_entry {
uint16_t dst_port_max; uint16_t dst_port_max;
uint8_t proto; uint8_t proto;
void *bgp_info; void *path;
bool installed; bool installed;
bool install_in_progress; bool install_in_progress;
@ -279,11 +279,10 @@ extern int bgp_pbr_match_hash_equal(const void *arg1,
void bgp_pbr_print_policy_route(struct bgp_pbr_entry_main *api); void bgp_pbr_print_policy_route(struct bgp_pbr_entry_main *api);
struct bgp_node; struct bgp_node;
struct bgp_info; struct bgp_path_info;
extern void bgp_pbr_update_entry(struct bgp *bgp, struct prefix *p, extern void bgp_pbr_update_entry(struct bgp *bgp, struct prefix *p,
struct bgp_info *new_select, struct bgp_path_info *new_select, afi_t afi,
afi_t afi, safi_t safi, safi_t safi, bool nlri_update);
bool nlri_update);
/* bgp pbr utilities */ /* bgp pbr utilities */
extern struct bgp_pbr_interface *pbr_interface_lookup(const char *name); extern struct bgp_pbr_interface *pbr_interface_lookup(const char *name);

File diff suppressed because it is too large Load Diff

View File

@ -72,11 +72,11 @@ enum bgp_show_adj_route_type {
*/ */
#define BGP_MAX_LABELS 2 #define BGP_MAX_LABELS 2
/* Ancillary information to struct bgp_info, /* Ancillary information to struct bgp_path_info,
* used for uncommonly used data (aggregation, MPLS, etc.) * used for uncommonly used data (aggregation, MPLS, etc.)
* and lazily allocated to save memory. * and lazily allocated to save memory.
*/ */
struct bgp_info_extra { struct bgp_path_info_extra {
/* Pointer to dampening structure. */ /* Pointer to dampening structure. */
struct bgp_damp_info *damp_info; struct bgp_damp_info *damp_info;
@ -150,13 +150,13 @@ struct bgp_info_extra {
struct list *bgp_fs_pbr; struct list *bgp_fs_pbr;
}; };
struct bgp_info { struct bgp_path_info {
/* For linked list. */ /* For linked list. */
struct bgp_info *next; struct bgp_path_info *next;
struct bgp_info *prev; struct bgp_path_info *prev;
/* For nexthop linked list */ /* For nexthop linked list */
LIST_ENTRY(bgp_info) nh_thread; LIST_ENTRY(bgp_path_info) nh_thread;
/* Back pointer to the prefix node */ /* Back pointer to the prefix node */
struct bgp_node *net; struct bgp_node *net;
@ -171,11 +171,11 @@ struct bgp_info {
struct attr *attr; struct attr *attr;
/* Extra information */ /* Extra information */
struct bgp_info_extra *extra; struct bgp_path_info_extra *extra;
/* Multipath information */ /* Multipath information */
struct bgp_info_mpath *mpath; struct bgp_path_info_mpath *mpath;
/* Uptime. */ /* Uptime. */
time_t uptime; time_t uptime;
@ -185,21 +185,21 @@ struct bgp_info {
/* BGP information status. */ /* BGP information status. */
uint16_t flags; uint16_t flags;
#define BGP_INFO_IGP_CHANGED (1 << 0) #define BGP_PATH_IGP_CHANGED (1 << 0)
#define BGP_INFO_DAMPED (1 << 1) #define BGP_PATH_DAMPED (1 << 1)
#define BGP_INFO_HISTORY (1 << 2) #define BGP_PATH_HISTORY (1 << 2)
#define BGP_INFO_SELECTED (1 << 3) #define BGP_PATH_SELECTED (1 << 3)
#define BGP_INFO_VALID (1 << 4) #define BGP_PATH_VALID (1 << 4)
#define BGP_INFO_ATTR_CHANGED (1 << 5) #define BGP_PATH_ATTR_CHANGED (1 << 5)
#define BGP_INFO_DMED_CHECK (1 << 6) #define BGP_PATH_DMED_CHECK (1 << 6)
#define BGP_INFO_DMED_SELECTED (1 << 7) #define BGP_PATH_DMED_SELECTED (1 << 7)
#define BGP_INFO_STALE (1 << 8) #define BGP_PATH_STALE (1 << 8)
#define BGP_INFO_REMOVED (1 << 9) #define BGP_PATH_REMOVED (1 << 9)
#define BGP_INFO_COUNTED (1 << 10) #define BGP_PATH_COUNTED (1 << 10)
#define BGP_INFO_MULTIPATH (1 << 11) #define BGP_PATH_MULTIPATH (1 << 11)
#define BGP_INFO_MULTIPATH_CHG (1 << 12) #define BGP_PATH_MULTIPATH_CHG (1 << 12)
#define BGP_INFO_RIB_ATTR_CHG (1 << 13) #define BGP_PATH_RIB_ATTR_CHG (1 << 13)
#define BGP_INFO_ANNC_NH_SELF (1 << 14) #define BGP_PATH_ANNC_NH_SELF (1 << 14)
/* BGP route type. This can be static, RIP, OSPF, BGP etc. */ /* BGP route type. This can be static, RIP, OSPF, BGP etc. */
uint8_t type; uint8_t type;
@ -224,9 +224,9 @@ struct bgp_info {
}; };
/* Structure used in BGP path selection */ /* Structure used in BGP path selection */
struct bgp_info_pair { struct bgp_path_info_pair {
struct bgp_info *old; struct bgp_path_info *old;
struct bgp_info *new; struct bgp_path_info *new;
}; };
/* BGP static route configuration. */ /* BGP static route configuration. */
@ -277,20 +277,20 @@ struct bgp_static {
#define BGP_ATTR_NEXTHOP_AFI_IP6(attr) \ #define BGP_ATTR_NEXTHOP_AFI_IP6(attr) \
(!CHECK_FLAG(attr->flag, ATTR_FLAG_BIT(BGP_ATTR_NEXT_HOP)) \ (!CHECK_FLAG(attr->flag, ATTR_FLAG_BIT(BGP_ATTR_NEXT_HOP)) \
&& ((attr)->mp_nexthop_len == 16 || (attr)->mp_nexthop_len == 32)) && ((attr)->mp_nexthop_len == 16 || (attr)->mp_nexthop_len == 32))
#define BGP_INFO_COUNTABLE(BI) \ #define BGP_PATH_COUNTABLE(BI) \
(!CHECK_FLAG((BI)->flags, BGP_INFO_HISTORY) \ (!CHECK_FLAG((BI)->flags, BGP_PATH_HISTORY) \
&& !CHECK_FLAG((BI)->flags, BGP_INFO_REMOVED)) && !CHECK_FLAG((BI)->flags, BGP_PATH_REMOVED))
/* Flags which indicate a route is unuseable in some form */ /* Flags which indicate a route is unuseable in some form */
#define BGP_INFO_UNUSEABLE \ #define BGP_PATH_UNUSEABLE \
(BGP_INFO_HISTORY | BGP_INFO_DAMPED | BGP_INFO_REMOVED) (BGP_PATH_HISTORY | BGP_PATH_DAMPED | BGP_PATH_REMOVED)
/* Macro to check BGP information is alive or not. Sadly, /* Macro to check BGP information is alive or not. Sadly,
* not equivalent to just checking previous, because of the * not equivalent to just checking previous, because of the
* sense of the additional VALID flag. * sense of the additional VALID flag.
*/ */
#define BGP_INFO_HOLDDOWN(BI) \ #define BGP_PATH_HOLDDOWN(BI) \
(!CHECK_FLAG((BI)->flags, BGP_INFO_VALID) \ (!CHECK_FLAG((BI)->flags, BGP_PATH_VALID) \
|| CHECK_FLAG((BI)->flags, BGP_INFO_UNUSEABLE)) || CHECK_FLAG((BI)->flags, BGP_PATH_UNUSEABLE))
#define DISTRIBUTE_IN_NAME(F) ((F)->dlist[FILTER_IN].name) #define DISTRIBUTE_IN_NAME(F) ((F)->dlist[FILTER_IN].name)
#define DISTRIBUTE_IN(F) ((F)->dlist[FILTER_IN].alist) #define DISTRIBUTE_IN(F) ((F)->dlist[FILTER_IN].alist)
@ -318,7 +318,11 @@ struct bgp_static {
/* path PREFIX (addpath rxid NUMBER) */ /* path PREFIX (addpath rxid NUMBER) */
#define PATH_ADDPATH_STR_BUFFER PREFIX2STR_BUFFER + 32 #define PATH_ADDPATH_STR_BUFFER PREFIX2STR_BUFFER + 32
enum bgp_path_type { BGP_PATH_ALL, BGP_PATH_BESTPATH, BGP_PATH_MULTIPATH }; enum bgp_path_type {
BGP_PATH_SHOW_ALL,
BGP_PATH_SHOW_BESTPATH,
BGP_PATH_SHOW_MULTIPATH
};
static inline void bgp_bump_version(struct bgp_node *node) static inline void bgp_bump_version(struct bgp_node *node)
{ {
@ -335,7 +339,7 @@ static inline int bgp_fibupd_safi(safi_t safi)
} }
/* Prototypes. */ /* Prototypes. */
extern void bgp_rib_remove(struct bgp_node *rn, struct bgp_info *ri, extern void bgp_rib_remove(struct bgp_node *rn, struct bgp_path_info *pi,
struct peer *peer, afi_t afi, safi_t safi); struct peer *peer, afi_t afi, safi_t safi);
extern void bgp_process_queue_init(void); extern void bgp_process_queue_init(void);
extern void bgp_route_init(void); extern void bgp_route_init(void);
@ -354,15 +358,19 @@ extern void bgp_clear_stale_route(struct peer *, afi_t, safi_t);
extern struct bgp_node *bgp_afi_node_get(struct bgp_table *table, afi_t afi, extern struct bgp_node *bgp_afi_node_get(struct bgp_table *table, afi_t afi,
safi_t safi, struct prefix *p, safi_t safi, struct prefix *p,
struct prefix_rd *prd); struct prefix_rd *prd);
extern struct bgp_info *bgp_info_lock(struct bgp_info *); extern struct bgp_path_info *bgp_path_info_lock(struct bgp_path_info *path);
extern struct bgp_info *bgp_info_unlock(struct bgp_info *); extern struct bgp_path_info *bgp_path_info_unlock(struct bgp_path_info *path);
extern void bgp_info_add(struct bgp_node *rn, struct bgp_info *ri); extern void bgp_path_info_add(struct bgp_node *rn, struct bgp_path_info *pi);
extern void bgp_info_reap(struct bgp_node *rn, struct bgp_info *ri); extern void bgp_path_info_reap(struct bgp_node *rn, struct bgp_path_info *pi);
extern void bgp_info_delete(struct bgp_node *rn, struct bgp_info *ri); extern void bgp_path_info_delete(struct bgp_node *rn, struct bgp_path_info *pi);
extern struct bgp_info_extra *bgp_info_extra_get(struct bgp_info *); extern struct bgp_path_info_extra *
extern void bgp_info_set_flag(struct bgp_node *, struct bgp_info *, uint32_t); bgp_path_info_extra_get(struct bgp_path_info *path);
extern void bgp_info_unset_flag(struct bgp_node *, struct bgp_info *, uint32_t); extern void bgp_path_info_set_flag(struct bgp_node *rn,
extern void bgp_info_path_with_addpath_rx_str(struct bgp_info *ri, char *buf); struct bgp_path_info *path, uint32_t flag);
extern void bgp_path_info_unset_flag(struct bgp_node *rn,
struct bgp_path_info *path, uint32_t flag);
extern void bgp_path_info_path_with_addpath_rx_str(struct bgp_path_info *pi,
char *buf);
extern int bgp_nlri_parse_ip(struct peer *, struct attr *, struct bgp_nlri *); extern int bgp_nlri_parse_ip(struct peer *, struct attr *, struct bgp_nlri *);
@ -416,38 +424,44 @@ extern void bgp_config_write_network(struct vty *, struct bgp *, afi_t, safi_t);
extern void bgp_config_write_distance(struct vty *, struct bgp *, afi_t, extern void bgp_config_write_distance(struct vty *, struct bgp *, afi_t,
safi_t); safi_t);
extern void bgp_aggregate_increment(struct bgp *, struct prefix *, extern void bgp_aggregate_increment(struct bgp *bgp, struct prefix *p,
struct bgp_info *, afi_t, safi_t); struct bgp_path_info *path, afi_t afi,
extern void bgp_aggregate_decrement(struct bgp *, struct prefix *, safi_t safi);
struct bgp_info *, afi_t, safi_t); extern void bgp_aggregate_decrement(struct bgp *bgp, struct prefix *p,
struct bgp_path_info *path, afi_t afi,
safi_t safi);
extern uint8_t bgp_distance_apply(struct prefix *, struct bgp_info *, afi_t, extern uint8_t bgp_distance_apply(struct prefix *p, struct bgp_path_info *path,
safi_t, struct bgp *); afi_t afi, safi_t safi, struct bgp *bgp);
extern afi_t bgp_node_afi(struct vty *); extern afi_t bgp_node_afi(struct vty *);
extern safi_t bgp_node_safi(struct vty *); extern safi_t bgp_node_safi(struct vty *);
extern struct bgp_info *info_make(int type, int sub_type, extern struct bgp_path_info *info_make(int type, int sub_type,
unsigned short instance, struct peer *peer, unsigned short instance,
struct attr *attr, struct bgp_node *rn); struct peer *peer, struct attr *attr,
struct bgp_node *rn);
extern void route_vty_out(struct vty *, struct prefix *, struct bgp_info *, int, extern void route_vty_out(struct vty *vty, struct prefix *p,
safi_t, json_object *); struct bgp_path_info *path, int display, safi_t safi,
extern void route_vty_out_tag(struct vty *, struct prefix *, struct bgp_info *, json_object *json_paths);
int, safi_t, json_object *); extern void route_vty_out_tag(struct vty *vty, struct prefix *p,
struct bgp_path_info *path, int display,
safi_t safi, json_object *json);
extern void route_vty_out_tmp(struct vty *vty, struct prefix *p, extern void route_vty_out_tmp(struct vty *vty, struct prefix *p,
struct attr *attr, safi_t safi, bool use_json, struct attr *attr, safi_t safi, bool use_json,
json_object *json_ar); json_object *json_ar);
extern void route_vty_out_overlay(struct vty *vty, struct prefix *p, extern void route_vty_out_overlay(struct vty *vty, struct prefix *p,
struct bgp_info *binfo, int display, struct bgp_path_info *path, int display,
json_object *json); json_object *json);
extern int subgroup_process_announce_selected(struct update_subgroup *subgrp, extern int subgroup_process_announce_selected(struct update_subgroup *subgrp,
struct bgp_info *selected, struct bgp_path_info *selected,
struct bgp_node *rn, struct bgp_node *rn,
uint32_t addpath_tx_id); uint32_t addpath_tx_id);
extern int subgroup_announce_check(struct bgp_node *rn, struct bgp_info *ri, extern int subgroup_announce_check(struct bgp_node *rn,
struct bgp_path_info *pi,
struct update_subgroup *subgrp, struct update_subgroup *subgrp,
struct prefix *p, struct attr *attr); struct prefix *p, struct attr *attr);
@ -458,28 +472,30 @@ extern void bgp_process_queues_drain_immediate(void);
extern struct bgp_node *bgp_afi_node_lookup(struct bgp_table *table, afi_t afi, extern struct bgp_node *bgp_afi_node_lookup(struct bgp_table *table, afi_t afi,
safi_t safi, struct prefix *p, safi_t safi, struct prefix *p,
struct prefix_rd *prd); struct prefix_rd *prd);
extern struct bgp_info *bgp_info_new(void); extern struct bgp_path_info *bgp_path_info_new(void);
extern void bgp_info_restore(struct bgp_node *, struct bgp_info *); extern void bgp_path_info_restore(struct bgp_node *rn,
struct bgp_path_info *path);
extern int bgp_info_cmp_compatible(struct bgp *, struct bgp_info *, extern int bgp_path_info_cmp_compatible(struct bgp *bgp,
struct bgp_info *, char *pfx_buf, afi_t afi, struct bgp_path_info *new,
safi_t safi); struct bgp_path_info *exist,
char *pfx_buf, afi_t afi, safi_t safi);
extern void bgp_attr_add_gshut_community(struct attr *attr); extern void bgp_attr_add_gshut_community(struct attr *attr);
extern void bgp_best_selection(struct bgp *bgp, struct bgp_node *rn, extern void bgp_best_selection(struct bgp *bgp, struct bgp_node *rn,
struct bgp_maxpaths_cfg *mpath_cfg, struct bgp_maxpaths_cfg *mpath_cfg,
struct bgp_info_pair *result, afi_t afi, struct bgp_path_info_pair *result, afi_t afi,
safi_t safi); safi_t safi);
extern void bgp_zebra_clear_route_change_flags(struct bgp_node *rn); extern void bgp_zebra_clear_route_change_flags(struct bgp_node *rn);
extern int bgp_zebra_has_route_changed(struct bgp_node *rn, extern int bgp_zebra_has_route_changed(struct bgp_node *rn,
struct bgp_info *selected); struct bgp_path_info *selected);
extern void route_vty_out_detail_header(struct vty *vty, struct bgp *bgp, extern void route_vty_out_detail_header(struct vty *vty, struct bgp *bgp,
struct bgp_node *rn, struct bgp_node *rn,
struct prefix_rd *prd, afi_t afi, struct prefix_rd *prd, afi_t afi,
safi_t safi, json_object *json); safi_t safi, json_object *json);
extern void route_vty_out_detail(struct vty *vty, struct bgp *bgp, extern void route_vty_out_detail(struct vty *vty, struct bgp *bgp,
struct prefix *p, struct bgp_info *binfo, struct prefix *p, struct bgp_path_info *path,
afi_t afi, safi_t safi, afi_t afi, safi_t safi,
json_object *json_paths); json_object *json_paths);
extern int bgp_show_table_rd(struct vty *vty, struct bgp *bgp, safi_t safi, extern int bgp_show_table_rd(struct vty *vty, struct bgp *bgp, safi_t safi,

File diff suppressed because it is too large Load Diff

View File

@ -217,12 +217,12 @@ static route_map_result_t route_match(void *rule, const struct prefix *prefix,
route_map_object_t type, void *object) route_map_object_t type, void *object)
{ {
int *rpki_status = rule; int *rpki_status = rule;
struct bgp_info *bgp_info; struct bgp_path_info *path;
if (type == RMAP_BGP) { if (type == RMAP_BGP) {
bgp_info = object; path = object;
if (rpki_validate_prefix(bgp_info->peer, bgp_info->attr, prefix) if (rpki_validate_prefix(path->peer, path->attr, prefix)
== *rpki_status) { == *rpki_status) {
return RMAP_MATCH; return RMAP_MATCH;
} }
@ -418,13 +418,13 @@ static void revalidate_bgp_node(struct bgp_node *bgp_node, afi_t afi,
for (ain = bgp_node->adj_in; ain; ain = ain->next) { for (ain = bgp_node->adj_in; ain; ain = ain->next) {
int ret; int ret;
struct bgp_info *bgp_info = bgp_node->info; struct bgp_path_info *path = bgp_node->info;
mpls_label_t *label = NULL; mpls_label_t *label = NULL;
uint32_t num_labels = 0; uint32_t num_labels = 0;
if (bgp_info && bgp_info->extra) { if (path && path->extra) {
label = bgp_info->extra->label; label = path->extra->label;
num_labels = bgp_info->extra->num_labels; num_labels = path->extra->num_labels;
} }
ret = bgp_update(ain->peer, &bgp_node->p, ain->addpath_rx_id, ret = bgp_update(ain->peer, &bgp_node->p, ain->addpath_rx_id,
ain->attr, afi, safi, ZEBRA_ROUTE_BGP, ain->attr, afi, safi, ZEBRA_ROUTE_BGP,

View File

@ -674,14 +674,15 @@ static uint8_t *bgpRcvdPathAttrTable(struct variable *v, oid name[],
return NULL; return NULL;
} }
static struct bgp_info *bgp4PathAttrLookup(struct variable *v, oid name[], static struct bgp_path_info *bgp4PathAttrLookup(struct variable *v, oid name[],
size_t *length, struct bgp *bgp, size_t *length, struct bgp *bgp,
struct prefix_ipv4 *addr, int exact) struct prefix_ipv4 *addr,
int exact)
{ {
oid *offset; oid *offset;
int offsetlen; int offsetlen;
struct bgp_info *binfo; struct bgp_path_info *path;
struct bgp_info *min; struct bgp_path_info *min;
struct bgp_node *rn; struct bgp_node *rn;
union sockunion su; union sockunion su;
unsigned int len; unsigned int len;
@ -714,9 +715,9 @@ static struct bgp_info *bgp4PathAttrLookup(struct variable *v, oid name[],
if (rn) { if (rn) {
bgp_unlock_node(rn); bgp_unlock_node(rn);
for (binfo = rn->info; binfo; binfo = binfo->next) for (path = rn->info; path; path = path->next)
if (sockunion_same(&binfo->peer->su, &su)) if (sockunion_same(&path->peer->su, &su))
return binfo; return path;
} }
} else { } else {
offset = name + v->namelen; offset = name + v->namelen;
@ -761,22 +762,22 @@ static struct bgp_info *bgp4PathAttrLookup(struct variable *v, oid name[],
do { do {
min = NULL; min = NULL;
for (binfo = rn->info; binfo; binfo = binfo->next) { for (path = rn->info; path; path = path->next) {
if (binfo->peer->su.sin.sin_family == AF_INET if (path->peer->su.sin.sin_family == AF_INET
&& ntohl(paddr.s_addr) && ntohl(paddr.s_addr)
< ntohl(binfo->peer->su.sin < ntohl(path->peer->su.sin
.sin_addr .sin_addr
.s_addr)) { .s_addr)) {
if (min) { if (min) {
if (ntohl(binfo->peer->su.sin if (ntohl(path->peer->su.sin
.sin_addr .sin_addr
.s_addr) .s_addr)
< ntohl(min->peer->su.sin < ntohl(min->peer->su.sin
.sin_addr .sin_addr
.s_addr)) .s_addr))
min = binfo; min = path;
} else } else
min = binfo; min = path;
} }
} }
@ -812,7 +813,7 @@ static uint8_t *bgp4PathAttrTable(struct variable *v, oid name[],
WriteMethod **write_method) WriteMethod **write_method)
{ {
struct bgp *bgp; struct bgp *bgp;
struct bgp_info *binfo; struct bgp_path_info *path;
struct prefix_ipv4 addr; struct prefix_ipv4 addr;
bgp = bgp_get_default(); bgp = bgp_get_default();
@ -824,13 +825,13 @@ static uint8_t *bgp4PathAttrTable(struct variable *v, oid name[],
return NULL; return NULL;
memset(&addr, 0, sizeof(struct prefix_ipv4)); memset(&addr, 0, sizeof(struct prefix_ipv4));
binfo = bgp4PathAttrLookup(v, name, length, bgp, &addr, exact); path = bgp4PathAttrLookup(v, name, length, bgp, &addr, exact);
if (!binfo) if (!path)
return NULL; return NULL;
switch (v->magic) { switch (v->magic) {
case BGP4PATHATTRPEER: /* 1 */ case BGP4PATHATTRPEER: /* 1 */
return SNMP_IPADDRESS(binfo->peer->su.sin.sin_addr); return SNMP_IPADDRESS(path->peer->su.sin.sin_addr);
break; break;
case BGP4PATHATTRIPADDRPREFIXLEN: /* 2 */ case BGP4PATHATTRIPADDRPREFIXLEN: /* 2 */
return SNMP_INTEGER(addr.prefixlen); return SNMP_INTEGER(addr.prefixlen);
@ -839,28 +840,28 @@ static uint8_t *bgp4PathAttrTable(struct variable *v, oid name[],
return SNMP_IPADDRESS(addr.prefix); return SNMP_IPADDRESS(addr.prefix);
break; break;
case BGP4PATHATTRORIGIN: /* 4 */ case BGP4PATHATTRORIGIN: /* 4 */
return SNMP_INTEGER(binfo->attr->origin); return SNMP_INTEGER(path->attr->origin);
break; break;
case BGP4PATHATTRASPATHSEGMENT: /* 5 */ case BGP4PATHATTRASPATHSEGMENT: /* 5 */
return aspath_snmp_pathseg(binfo->attr->aspath, var_len); return aspath_snmp_pathseg(path->attr->aspath, var_len);
break; break;
case BGP4PATHATTRNEXTHOP: /* 6 */ case BGP4PATHATTRNEXTHOP: /* 6 */
return SNMP_IPADDRESS(binfo->attr->nexthop); return SNMP_IPADDRESS(path->attr->nexthop);
break; break;
case BGP4PATHATTRMULTIEXITDISC: /* 7 */ case BGP4PATHATTRMULTIEXITDISC: /* 7 */
return SNMP_INTEGER(binfo->attr->med); return SNMP_INTEGER(path->attr->med);
break; break;
case BGP4PATHATTRLOCALPREF: /* 8 */ case BGP4PATHATTRLOCALPREF: /* 8 */
return SNMP_INTEGER(binfo->attr->local_pref); return SNMP_INTEGER(path->attr->local_pref);
break; break;
case BGP4PATHATTRATOMICAGGREGATE: /* 9 */ case BGP4PATHATTRATOMICAGGREGATE: /* 9 */
return SNMP_INTEGER(1); return SNMP_INTEGER(1);
break; break;
case BGP4PATHATTRAGGREGATORAS: /* 10 */ case BGP4PATHATTRAGGREGATORAS: /* 10 */
return SNMP_INTEGER(binfo->attr->aggregator_as); return SNMP_INTEGER(path->attr->aggregator_as);
break; break;
case BGP4PATHATTRAGGREGATORADDR: /* 11 */ case BGP4PATHATTRAGGREGATORADDR: /* 11 */
return SNMP_IPADDRESS(binfo->attr->aggregator_addr); return SNMP_IPADDRESS(path->attr->aggregator_addr);
break; break;
case BGP4PATHATTRCALCLOCALPREF: /* 12 */ case BGP4PATHATTRCALCLOCALPREF: /* 12 */
return SNMP_INTEGER(-1); return SNMP_INTEGER(-1);
@ -868,7 +869,7 @@ static uint8_t *bgp4PathAttrTable(struct variable *v, oid name[],
case BGP4PATHATTRBEST: /* 13 */ case BGP4PATHATTRBEST: /* 13 */
#define BGP4_PathAttrBest_false 1 #define BGP4_PathAttrBest_false 1
#define BGP4_PathAttrBest_true 2 #define BGP4_PathAttrBest_true 2
if (CHECK_FLAG(binfo->flags, BGP_INFO_SELECTED)) if (CHECK_FLAG(path->flags, BGP_INFO_SELECTED))
return SNMP_INTEGER(BGP4_PathAttrBest_true); return SNMP_INTEGER(BGP4_PathAttrBest_true);
else else
return SNMP_INTEGER(BGP4_PathAttrBest_false); return SNMP_INTEGER(BGP4_PathAttrBest_false);

View File

@ -104,7 +104,7 @@ struct bgp_table *bgp_table_init(struct bgp *bgp, afi_t afi, safi_t safi)
route_table_set_info(rt->route_table, rt); route_table_set_info(rt->route_table, rt);
/* /*
* pointer to bgp instance allows working back from bgp_info to bgp * pointer to bgp instance allows working back from bgp_path_info to bgp
*/ */
rt->bgp = bgp; rt->bgp = bgp;

View File

@ -1906,7 +1906,7 @@ int bgp_addpath_encode_tx(struct peer *peer, afi_t afi, safi_t safi)
* configured addpath-tx knob * configured addpath-tx knob
*/ */
int bgp_addpath_tx_path(struct peer *peer, afi_t afi, safi_t safi, int bgp_addpath_tx_path(struct peer *peer, afi_t afi, safi_t safi,
struct bgp_info *ri) struct bgp_path_info *pi)
{ {
if (CHECK_FLAG(peer->af_flags[afi][safi], if (CHECK_FLAG(peer->af_flags[afi][safi],
PEER_FLAG_ADDPATH_TX_ALL_PATHS)) PEER_FLAG_ADDPATH_TX_ALL_PATHS))
@ -1914,7 +1914,7 @@ int bgp_addpath_tx_path(struct peer *peer, afi_t afi, safi_t safi,
if (CHECK_FLAG(peer->af_flags[afi][safi], if (CHECK_FLAG(peer->af_flags[afi][safi],
PEER_FLAG_ADDPATH_TX_BESTPATH_PER_AS) PEER_FLAG_ADDPATH_TX_BESTPATH_PER_AS)
&& CHECK_FLAG(ri->flags, BGP_INFO_DMED_SELECTED)) && CHECK_FLAG(pi->flags, BGP_PATH_DMED_SELECTED))
return 1; return 1;
return 0; return 0;

View File

@ -293,7 +293,7 @@ typedef int (*updgrp_walkcb)(struct update_group *updgrp, void *ctx);
struct updwalk_context { struct updwalk_context {
struct vty *vty; struct vty *vty;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *pi;
uint64_t updgrp_id; uint64_t updgrp_id;
uint64_t subgrp_id; uint64_t subgrp_id;
bgp_policy_type_e policy_type; bgp_policy_type_e policy_type;
@ -442,7 +442,7 @@ extern void subgroup_announce_all(struct update_subgroup *subgrp);
extern void subgroup_default_originate(struct update_subgroup *subgrp, extern void subgroup_default_originate(struct update_subgroup *subgrp,
int withdraw); int withdraw);
extern void group_announce_route(struct bgp *bgp, afi_t afi, safi_t safi, extern void group_announce_route(struct bgp *bgp, afi_t afi, safi_t safi,
struct bgp_node *rn, struct bgp_info *ri); struct bgp_node *rn, struct bgp_path_info *pi);
extern void subgroup_clear_table(struct update_subgroup *subgrp); extern void subgroup_clear_table(struct update_subgroup *subgrp);
extern void update_group_announce(struct bgp *bgp); extern void update_group_announce(struct bgp *bgp);
extern void update_group_announce_rrclients(struct bgp *bgp); extern void update_group_announce_rrclients(struct bgp *bgp);
@ -455,7 +455,8 @@ extern void bgp_adj_out_remove_subgroup(struct bgp_node *rn,
struct update_subgroup *subgrp); struct update_subgroup *subgrp);
extern void bgp_adj_out_set_subgroup(struct bgp_node *rn, extern void bgp_adj_out_set_subgroup(struct bgp_node *rn,
struct update_subgroup *subgrp, struct update_subgroup *subgrp,
struct attr *attr, struct bgp_info *binfo); struct attr *attr,
struct bgp_path_info *path);
extern void bgp_adj_out_unset_subgroup(struct bgp_node *rn, extern void bgp_adj_out_unset_subgroup(struct bgp_node *rn,
struct update_subgroup *subgrp, struct update_subgroup *subgrp,
char withdraw, uint32_t addpath_tx_id); char withdraw, uint32_t addpath_tx_id);
@ -469,7 +470,7 @@ extern int update_group_clear_update_dbg(struct update_group *updgrp,
extern void update_bgp_group_free(struct bgp *bgp); extern void update_bgp_group_free(struct bgp *bgp);
extern int bgp_addpath_encode_tx(struct peer *peer, afi_t afi, safi_t safi); extern int bgp_addpath_encode_tx(struct peer *peer, afi_t afi, safi_t safi);
extern int bgp_addpath_tx_path(struct peer *peer, afi_t afi, safi_t safi, extern int bgp_addpath_tx_path(struct peer *peer, afi_t afi, safi_t safi,
struct bgp_info *ri); struct bgp_path_info *pi);
/* /*
* Inline functions * Inline functions

View File

@ -101,7 +101,7 @@ static int group_announce_route_walkcb(struct update_group *updgrp, void *arg)
{ {
struct updwalk_context *ctx = arg; struct updwalk_context *ctx = arg;
struct update_subgroup *subgrp; struct update_subgroup *subgrp;
struct bgp_info *ri; struct bgp_path_info *pi;
afi_t afi; afi_t afi;
safi_t safi; safi_t safi;
struct peer *peer; struct peer *peer;
@ -140,15 +140,15 @@ static int group_announce_route_walkcb(struct update_group *updgrp, void *arg)
adj_next = adj->next; adj_next = adj->next;
if (adj->subgroup == subgrp) { if (adj->subgroup == subgrp) {
for (ri = ctx->rn->info; ri; for (pi = ctx->rn->info; pi;
ri = ri->next) { pi = pi->next) {
if (ri->addpath_tx_id if (pi->addpath_tx_id
== adj->addpath_tx_id) { == adj->addpath_tx_id) {
break; break;
} }
} }
if (!ri) { if (!pi) {
subgroup_process_announce_selected( subgroup_process_announce_selected(
subgrp, NULL, subgrp, NULL,
ctx->rn, ctx->rn,
@ -157,32 +157,32 @@ static int group_announce_route_walkcb(struct update_group *updgrp, void *arg)
} }
} }
for (ri = ctx->rn->info; ri; ri = ri->next) { for (pi = ctx->rn->info; pi; pi = pi->next) {
/* Skip the bestpath for now */ /* Skip the bestpath for now */
if (ri == ctx->ri) if (pi == ctx->pi)
continue; continue;
subgroup_process_announce_selected( subgroup_process_announce_selected(
subgrp, ri, ctx->rn, subgrp, pi, ctx->rn,
ri->addpath_tx_id); pi->addpath_tx_id);
} }
/* Process the bestpath last so the "show [ip] /* Process the bestpath last so the "show [ip]
* bgp neighbor x.x.x.x advertised" * bgp neighbor x.x.x.x advertised"
* output shows the attributes from the bestpath * output shows the attributes from the bestpath
*/ */
if (ctx->ri) if (ctx->pi)
subgroup_process_announce_selected( subgroup_process_announce_selected(
subgrp, ctx->ri, ctx->rn, subgrp, ctx->pi, ctx->rn,
ctx->ri->addpath_tx_id); ctx->pi->addpath_tx_id);
} }
/* An update-group that does not use addpath */ /* An update-group that does not use addpath */
else { else {
if (ctx->ri) { if (ctx->pi) {
subgroup_process_announce_selected( subgroup_process_announce_selected(
subgrp, ctx->ri, ctx->rn, subgrp, ctx->pi, ctx->rn,
ctx->ri->addpath_tx_id); ctx->pi->addpath_tx_id);
} else { } else {
/* Find the addpath_tx_id of the path we /* Find the addpath_tx_id of the path we
* had advertised and * had advertised and
@ -429,7 +429,7 @@ bgp_advertise_clean_subgroup(struct update_subgroup *subgrp,
void bgp_adj_out_set_subgroup(struct bgp_node *rn, void bgp_adj_out_set_subgroup(struct bgp_node *rn,
struct update_subgroup *subgrp, struct attr *attr, struct update_subgroup *subgrp, struct attr *attr,
struct bgp_info *binfo) struct bgp_path_info *path)
{ {
struct bgp_adj_out *adj = NULL; struct bgp_adj_out *adj = NULL;
struct bgp_advertise *adv; struct bgp_advertise *adv;
@ -438,10 +438,10 @@ void bgp_adj_out_set_subgroup(struct bgp_node *rn,
return; return;
/* Look for adjacency information. */ /* Look for adjacency information. */
adj = adj_lookup(rn, subgrp, binfo->addpath_tx_id); adj = adj_lookup(rn, subgrp, path->addpath_tx_id);
if (!adj) { if (!adj) {
adj = bgp_adj_out_alloc(subgrp, rn, binfo->addpath_tx_id); adj = bgp_adj_out_alloc(subgrp, rn, path->addpath_tx_id);
if (!adj) if (!adj)
return; return;
} }
@ -452,8 +452,9 @@ void bgp_adj_out_set_subgroup(struct bgp_node *rn,
adv = adj->adv; adv = adj->adv;
adv->rn = rn; adv->rn = rn;
assert(adv->binfo == NULL); assert(adv->pathi == NULL);
adv->binfo = bgp_info_lock(binfo); /* bgp_info adj_out reference */ /* bgp_path_info adj_out reference */
adv->pathi = bgp_path_info_lock(path);
if (attr) if (attr)
adv->baa = bgp_advertise_intern(subgrp->hash, attr); adv->baa = bgp_advertise_intern(subgrp->hash, attr);
@ -568,7 +569,7 @@ void subgroup_announce_table(struct update_subgroup *subgrp,
struct bgp_table *table) struct bgp_table *table)
{ {
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *ri;
struct attr attr; struct attr attr;
struct peer *peer; struct peer *peer;
afi_t afi; afi_t afi;
@ -594,7 +595,7 @@ void subgroup_announce_table(struct update_subgroup *subgrp,
for (rn = bgp_table_top(table); rn; rn = bgp_route_next(rn)) for (rn = bgp_table_top(table); rn; rn = bgp_route_next(rn))
for (ri = rn->info; ri; ri = ri->next) for (ri = rn->info; ri; ri = ri->next)
if (CHECK_FLAG(ri->flags, BGP_INFO_SELECTED) if (CHECK_FLAG(ri->flags, BGP_PATH_SELECTED)
|| (addpath_capable || (addpath_capable
&& bgp_addpath_tx_path(peer, afi, safi, ri))) { && bgp_addpath_tx_path(peer, afi, safi, ri))) {
if (subgroup_announce_check(rn, ri, subgrp, if (subgroup_announce_check(rn, ri, subgrp,
@ -663,11 +664,11 @@ void subgroup_default_originate(struct update_subgroup *subgrp, int withdraw)
{ {
struct bgp *bgp; struct bgp *bgp;
struct attr attr; struct attr attr;
struct bgp_info *info, init_info, tmp_info; struct bgp_path_info *info, init_info, tmp_info;
struct prefix p; struct prefix p;
struct peer *from; struct peer *from;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *ri;
struct peer *peer; struct peer *peer;
int ret = RMAP_DENYMATCH; int ret = RMAP_DENYMATCH;
afi_t afi; afi_t afi;
@ -830,10 +831,10 @@ void subgroup_announce_all(struct update_subgroup *subgrp)
* input route. * input route.
*/ */
void group_announce_route(struct bgp *bgp, afi_t afi, safi_t safi, void group_announce_route(struct bgp *bgp, afi_t afi, safi_t safi,
struct bgp_node *rn, struct bgp_info *ri) struct bgp_node *rn, struct bgp_path_info *pi)
{ {
struct updwalk_context ctx; struct updwalk_context ctx;
ctx.ri = ri; ctx.pi = pi;
ctx.rn = rn; ctx.rn = rn;
update_group_af_walk(bgp, afi, safi, group_announce_route_walkcb, &ctx); update_group_af_walk(bgp, afi, safi, group_announce_route_walkcb, &ctx);
} }

View File

@ -687,7 +687,7 @@ struct bpacket *subgroup_update_packet(struct update_subgroup *subgrp)
struct bgp_adj_out *adj; struct bgp_adj_out *adj;
struct bgp_advertise *adv; struct bgp_advertise *adv;
struct bgp_node *rn = NULL; struct bgp_node *rn = NULL;
struct bgp_info *binfo = NULL; struct bgp_path_info *path = NULL;
bgp_size_t total_attr_len = 0; bgp_size_t total_attr_len = 0;
unsigned long attrlen_pos = 0; unsigned long attrlen_pos = 0;
size_t mpattrlen_pos = 0; size_t mpattrlen_pos = 0;
@ -731,7 +731,7 @@ struct bpacket *subgroup_update_packet(struct update_subgroup *subgrp)
rn = adv->rn; rn = adv->rn;
adj = adv->adj; adj = adv->adj;
addpath_tx_id = adj->addpath_tx_id; addpath_tx_id = adj->addpath_tx_id;
binfo = adv->binfo; path = adv->pathi;
space_remaining = STREAM_CONCAT_REMAIN(s, snlri, STREAM_SIZE(s)) space_remaining = STREAM_CONCAT_REMAIN(s, snlri, STREAM_SIZE(s))
- BGP_MAX_PACKET_SIZE_OVERFLOW; - BGP_MAX_PACKET_SIZE_OVERFLOW;
@ -747,8 +747,8 @@ struct bpacket *subgroup_update_packet(struct update_subgroup *subgrp)
if (stream_empty(s)) { if (stream_empty(s)) {
struct peer *from = NULL; struct peer *from = NULL;
if (binfo) if (path)
from = binfo->peer; from = path->peer;
/* 1: Write the BGP message header - 16 bytes marker, 2 /* 1: Write the BGP message header - 16 bytes marker, 2
* bytes length, * bytes length,
@ -821,13 +821,13 @@ struct bpacket *subgroup_update_packet(struct update_subgroup *subgrp)
prd = (struct prefix_rd *)&rn->prn->p; prd = (struct prefix_rd *)&rn->prn->p;
if (safi == SAFI_LABELED_UNICAST) { if (safi == SAFI_LABELED_UNICAST) {
label = bgp_adv_label(rn, binfo, peer, afi, label = bgp_adv_label(rn, path, peer, afi,
safi); safi);
label_pnt = &label; label_pnt = &label;
num_labels = 1; num_labels = 1;
} else if (binfo && binfo->extra) { } else if (path && path->extra) {
label_pnt = &binfo->extra->label[0]; label_pnt = &path->extra->label[0];
num_labels = binfo->extra->num_labels; num_labels = path->extra->num_labels;
} }
if (stream_empty(snlri)) if (stream_empty(snlri))

View File

@ -7524,12 +7524,13 @@ DEFUN (show_bgp_memory,
count = mtype_stats_alloc(MTYPE_BGP_ROUTE); count = mtype_stats_alloc(MTYPE_BGP_ROUTE);
vty_out(vty, "%ld BGP routes, using %s of memory\n", count, vty_out(vty, "%ld BGP routes, using %s of memory\n", count,
mtype_memstr(memstrbuf, sizeof(memstrbuf), mtype_memstr(memstrbuf, sizeof(memstrbuf),
count * sizeof(struct bgp_info))); count * sizeof(struct bgp_path_info)));
if ((count = mtype_stats_alloc(MTYPE_BGP_ROUTE_EXTRA))) if ((count = mtype_stats_alloc(MTYPE_BGP_ROUTE_EXTRA)))
vty_out(vty, "%ld BGP route ancillaries, using %s of memory\n", vty_out(vty, "%ld BGP route ancillaries, using %s of memory\n",
count, count,
mtype_memstr(memstrbuf, sizeof(memstrbuf), mtype_memstr(
count * sizeof(struct bgp_info_extra))); memstrbuf, sizeof(memstrbuf),
count * sizeof(struct bgp_path_info_extra)));
if ((count = mtype_stats_alloc(MTYPE_BGP_STATIC))) if ((count = mtype_stats_alloc(MTYPE_BGP_STATIC)))
vty_out(vty, "%ld Static routes, using %s of memory\n", count, vty_out(vty, "%ld Static routes, using %s of memory\n", count,

View File

@ -925,41 +925,40 @@ bool bgp_zebra_nexthop_set(union sockunion *local, union sockunion *remote,
return true; return true;
} }
static struct in6_addr *bgp_info_to_ipv6_nexthop(struct bgp_info *info, static struct in6_addr *
ifindex_t *ifindex) bgp_path_info_to_ipv6_nexthop(struct bgp_path_info *path, ifindex_t *ifindex)
{ {
struct in6_addr *nexthop = NULL; struct in6_addr *nexthop = NULL;
/* Only global address nexthop exists. */ /* Only global address nexthop exists. */
if (info->attr->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL) { if (path->attr->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL) {
nexthop = &info->attr->mp_nexthop_global; nexthop = &path->attr->mp_nexthop_global;
if (IN6_IS_ADDR_LINKLOCAL(nexthop)) if (IN6_IS_ADDR_LINKLOCAL(nexthop))
*ifindex = info->attr->nh_ifindex; *ifindex = path->attr->nh_ifindex;
} }
/* If both global and link-local address present. */ /* If both global and link-local address present. */
if (info->attr->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL) { if (path->attr->mp_nexthop_len == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL) {
/* Check if route-map is set to prefer global over link-local */ /* Check if route-map is set to prefer global over link-local */
if (info->attr->mp_nexthop_prefer_global) { if (path->attr->mp_nexthop_prefer_global) {
nexthop = &info->attr->mp_nexthop_global; nexthop = &path->attr->mp_nexthop_global;
if (IN6_IS_ADDR_LINKLOCAL(nexthop)) if (IN6_IS_ADDR_LINKLOCAL(nexthop))
*ifindex = info->attr->nh_ifindex; *ifindex = path->attr->nh_ifindex;
} else { } else {
/* Workaround for Cisco's nexthop bug. */ /* Workaround for Cisco's nexthop bug. */
if (IN6_IS_ADDR_UNSPECIFIED( if (IN6_IS_ADDR_UNSPECIFIED(
&info->attr->mp_nexthop_global) &path->attr->mp_nexthop_global)
&& info->peer->su_remote->sa.sa_family && path->peer->su_remote->sa.sa_family
== AF_INET6) { == AF_INET6) {
nexthop = nexthop =
&info->peer->su_remote->sin6.sin6_addr; &path->peer->su_remote->sin6.sin6_addr;
if (IN6_IS_ADDR_LINKLOCAL(nexthop)) if (IN6_IS_ADDR_LINKLOCAL(nexthop))
*ifindex = info->peer->nexthop.ifp *ifindex = path->peer->nexthop.ifp
->ifindex; ->ifindex;
} else { } else {
nexthop = &info->attr->mp_nexthop_local; nexthop = &path->attr->mp_nexthop_local;
if (IN6_IS_ADDR_LINKLOCAL(nexthop)) if (IN6_IS_ADDR_LINKLOCAL(nexthop))
*ifindex = info->attr->nh_lla_ifindex; *ifindex = path->attr->nh_lla_ifindex;
} }
} }
} }
@ -968,12 +967,12 @@ static struct in6_addr *bgp_info_to_ipv6_nexthop(struct bgp_info *info,
} }
static int bgp_table_map_apply(struct route_map *map, struct prefix *p, static int bgp_table_map_apply(struct route_map *map, struct prefix *p,
struct bgp_info *info) struct bgp_path_info *path)
{ {
route_map_result_t ret; route_map_result_t ret;
ret = route_map_apply(map, p, RMAP_BGP, info); ret = route_map_apply(map, p, RMAP_BGP, path);
bgp_attr_flush(info->attr); bgp_attr_flush(path->attr);
if (ret != RMAP_DENYMATCH) if (ret != RMAP_DENYMATCH)
return 1; return 1;
@ -986,7 +985,7 @@ static int bgp_table_map_apply(struct route_map *map, struct prefix *p,
inet_ntop(AF_INET, &p->u.prefix4, buf[0], inet_ntop(AF_INET, &p->u.prefix4, buf[0],
sizeof(buf[0])), sizeof(buf[0])),
p->prefixlen, p->prefixlen,
inet_ntop(AF_INET, &info->attr->nexthop, buf[1], inet_ntop(AF_INET, &path->attr->nexthop, buf[1],
sizeof(buf[1]))); sizeof(buf[1])));
} }
if (p->family == AF_INET6) { if (p->family == AF_INET6) {
@ -994,7 +993,7 @@ static int bgp_table_map_apply(struct route_map *map, struct prefix *p,
ifindex_t ifindex; ifindex_t ifindex;
struct in6_addr *nexthop; struct in6_addr *nexthop;
nexthop = bgp_info_to_ipv6_nexthop(info, &ifindex); nexthop = bgp_path_info_to_ipv6_nexthop(path, &ifindex);
zlog_debug( zlog_debug(
"Zebra rmap deny: IPv6 route %s/%d nexthop %s", "Zebra rmap deny: IPv6 route %s/%d nexthop %s",
inet_ntop(AF_INET6, &p->u.prefix6, buf[0], inet_ntop(AF_INET6, &p->u.prefix6, buf[0],
@ -1121,17 +1120,15 @@ static int update_ipv4nh_for_route_install(int nh_othervrf,
return 1; return 1;
} }
static int update_ipv6nh_for_route_install(int nh_othervrf, static int
struct in6_addr *nexthop, update_ipv6nh_for_route_install(int nh_othervrf, struct in6_addr *nexthop,
ifindex_t ifindex, ifindex_t ifindex, struct bgp_path_info *pi,
struct bgp_info *ri, struct bgp_path_info *best_pi, bool is_evpn,
struct bgp_info *best_ri,
bool is_evpn,
struct zapi_nexthop *api_nh) struct zapi_nexthop *api_nh)
{ {
struct attr *attr; struct attr *attr;
attr = ri->attr; attr = pi->attr;
if (is_evpn) if (is_evpn)
api_nh->type = NEXTHOP_TYPE_IPV6_IFINDEX; api_nh->type = NEXTHOP_TYPE_IPV6_IFINDEX;
@ -1150,22 +1147,22 @@ static int update_ipv6nh_for_route_install(int nh_othervrf,
} }
} else { } else {
if (IN6_IS_ADDR_LINKLOCAL(nexthop)) { if (IN6_IS_ADDR_LINKLOCAL(nexthop)) {
if (ri == best_ri && if (pi == best_pi
attr->mp_nexthop_len && attr->mp_nexthop_len
== BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL) == BGP_ATTR_NHLEN_IPV6_GLOBAL_AND_LL)
if (ri->peer->nexthop.ifp) if (pi->peer->nexthop.ifp)
ifindex = ri->peer->nexthop.ifp ifindex =
->ifindex; pi->peer->nexthop.ifp->ifindex;
if (!ifindex) { if (!ifindex) {
if (ri->peer->conf_if) if (pi->peer->conf_if)
ifindex = ri->peer->ifp->ifindex; ifindex = pi->peer->ifp->ifindex;
else if (ri->peer->ifname) else if (pi->peer->ifname)
ifindex = ifname2ifindex( ifindex = ifname2ifindex(
ri->peer->ifname, pi->peer->ifname,
ri->peer->bgp->vrf_id); pi->peer->bgp->vrf_id);
else if (ri->peer->nexthop.ifp) else if (pi->peer->nexthop.ifp)
ifindex = ri->peer->nexthop.ifp ifindex =
->ifindex; pi->peer->nexthop.ifp->ifindex;
} }
if (ifindex == 0) if (ifindex == 0)
@ -1183,7 +1180,7 @@ static int update_ipv6nh_for_route_install(int nh_othervrf,
} }
void bgp_zebra_announce(struct bgp_node *rn, struct prefix *p, void bgp_zebra_announce(struct bgp_node *rn, struct prefix *p,
struct bgp_info *info, struct bgp *bgp, afi_t afi, struct bgp_path_info *info, struct bgp *bgp, afi_t afi,
safi_t safi) safi_t safi)
{ {
struct zapi_route api; struct zapi_route api;
@ -1193,11 +1190,11 @@ void bgp_zebra_announce(struct bgp_node *rn, struct prefix *p,
int has_valid_label = 0; int has_valid_label = 0;
uint8_t distance; uint8_t distance;
struct peer *peer; struct peer *peer;
struct bgp_info *mpinfo; struct bgp_path_info *mpinfo;
uint32_t metric; uint32_t metric;
struct attr local_attr; struct attr local_attr;
struct bgp_info local_info; struct bgp_path_info local_info;
struct bgp_info *mpinfo_cp = &local_info; struct bgp_path_info *mpinfo_cp = &local_info;
route_tag_t tag; route_tag_t tag;
mpls_label_t label; mpls_label_t label;
int nh_othervrf = 0; int nh_othervrf = 0;
@ -1242,7 +1239,8 @@ void bgp_zebra_announce(struct bgp_node *rn, struct prefix *p,
/* Obtain peer from parent */ /* Obtain peer from parent */
if (info->extra && info->extra->parent) if (info->extra && info->extra->parent)
peer = ((struct bgp_info *)(info->extra->parent))->peer; peer = ((struct bgp_path_info *)(info->extra->parent))
->peer;
} }
tag = info->attr->tag; tag = info->attr->tag;
@ -1266,7 +1264,7 @@ void bgp_zebra_announce(struct bgp_node *rn, struct prefix *p,
/* Metric is currently based on the best-path only */ /* Metric is currently based on the best-path only */
metric = info->attr->med; metric = info->attr->med;
for (mpinfo = info; mpinfo; mpinfo = bgp_info_mpath_next(mpinfo)) { for (mpinfo = info; mpinfo; mpinfo = bgp_path_info_mpath_next(mpinfo)) {
if (valid_nh_count >= multipath_num) if (valid_nh_count >= multipath_num)
break; break;
@ -1356,7 +1354,7 @@ void bgp_zebra_announce(struct bgp_node *rn, struct prefix *p,
tag = mpinfo_cp->attr->tag; tag = mpinfo_cp->attr->tag;
} }
} }
nexthop = bgp_info_to_ipv6_nexthop(mpinfo_cp, nexthop = bgp_path_info_to_ipv6_nexthop(mpinfo_cp,
&ifindex); &ifindex);
nh_updated = update_ipv6nh_for_route_install( nh_updated = update_ipv6nh_for_route_install(
nh_othervrf, nexthop, ifindex, nh_othervrf, nexthop, ifindex,
@ -1466,7 +1464,7 @@ void bgp_zebra_announce_table(struct bgp *bgp, afi_t afi, safi_t safi)
{ {
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_table *table; struct bgp_table *table;
struct bgp_info *ri; struct bgp_path_info *pi;
/* Don't try to install if we're not connected to Zebra or Zebra doesn't /* Don't try to install if we're not connected to Zebra or Zebra doesn't
* know of this instance. * know of this instance.
@ -1479,18 +1477,18 @@ void bgp_zebra_announce_table(struct bgp *bgp, afi_t afi, safi_t safi)
return; return;
for (rn = bgp_table_top(table); rn; rn = bgp_route_next(rn)) for (rn = bgp_table_top(table); rn; rn = bgp_route_next(rn))
for (ri = rn->info; ri; ri = ri->next) for (pi = rn->info; pi; pi = pi->next)
if (CHECK_FLAG(ri->flags, BGP_INFO_SELECTED) && if (CHECK_FLAG(pi->flags, BGP_PATH_SELECTED) &&
(ri->type == ZEBRA_ROUTE_BGP (pi->type == ZEBRA_ROUTE_BGP
&& (ri->sub_type == BGP_ROUTE_NORMAL && (pi->sub_type == BGP_ROUTE_NORMAL
|| ri->sub_type == BGP_ROUTE_IMPORTED))) || pi->sub_type == BGP_ROUTE_IMPORTED)))
bgp_zebra_announce(rn, &rn->p, ri, bgp, afi, bgp_zebra_announce(rn, &rn->p, pi, bgp, afi,
safi); safi);
} }
void bgp_zebra_withdraw(struct prefix *p, struct bgp_info *info, void bgp_zebra_withdraw(struct prefix *p, struct bgp_path_info *info,
struct bgp *bgp, safi_t safi) struct bgp *bgp, safi_t safi)
{ {
struct zapi_route api; struct zapi_route api;
@ -1680,7 +1678,7 @@ int bgp_redistribute_metric_set(struct bgp *bgp, struct bgp_redist *red,
afi_t afi, int type, uint32_t metric) afi_t afi, int type, uint32_t metric)
{ {
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *pi;
if (red->redist_metric_flag && red->redist_metric == metric) if (red->redist_metric_flag && red->redist_metric == metric)
return 0; return 0;
@ -1690,21 +1688,21 @@ int bgp_redistribute_metric_set(struct bgp *bgp, struct bgp_redist *red,
for (rn = bgp_table_top(bgp->rib[afi][SAFI_UNICAST]); rn; for (rn = bgp_table_top(bgp->rib[afi][SAFI_UNICAST]); rn;
rn = bgp_route_next(rn)) { rn = bgp_route_next(rn)) {
for (ri = rn->info; ri; ri = ri->next) { for (pi = rn->info; pi; pi = pi->next) {
if (ri->sub_type == BGP_ROUTE_REDISTRIBUTE if (pi->sub_type == BGP_ROUTE_REDISTRIBUTE
&& ri->type == type && pi->type == type
&& ri->instance == red->instance) { && pi->instance == red->instance) {
struct attr *old_attr; struct attr *old_attr;
struct attr new_attr; struct attr new_attr;
bgp_attr_dup(&new_attr, ri->attr); bgp_attr_dup(&new_attr, pi->attr);
new_attr.med = red->redist_metric; new_attr.med = red->redist_metric;
old_attr = ri->attr; old_attr = pi->attr;
ri->attr = bgp_attr_intern(&new_attr); pi->attr = bgp_attr_intern(&new_attr);
bgp_attr_unintern(&old_attr); bgp_attr_unintern(&old_attr);
bgp_info_set_flag(rn, ri, bgp_path_info_set_flag(rn, pi,
BGP_INFO_ATTR_CHANGED); BGP_PATH_ATTR_CHANGED);
bgp_process(bgp, rn, afi, SAFI_UNICAST); bgp_process(bgp, rn, afi, SAFI_UNICAST);
} }
} }
@ -2081,17 +2079,17 @@ static int ipset_entry_notify_owner(int command, struct zclient *zclient,
break; break;
case ZAPI_IPSET_ENTRY_INSTALLED: case ZAPI_IPSET_ENTRY_INSTALLED:
{ {
struct bgp_info *bgp_info; struct bgp_path_info *path;
struct bgp_info_extra *extra; struct bgp_path_info_extra *extra;
bgp_pbime->installed = true; bgp_pbime->installed = true;
bgp_pbime->install_in_progress = false; bgp_pbime->install_in_progress = false;
if (BGP_DEBUG(zebra, ZEBRA)) if (BGP_DEBUG(zebra, ZEBRA))
zlog_debug("%s: Received IPSET_ENTRY_INSTALLED", zlog_debug("%s: Received IPSET_ENTRY_INSTALLED",
__PRETTY_FUNCTION__); __PRETTY_FUNCTION__);
/* link bgp_info to bpme */ /* link bgp_path_info to bpme */
bgp_info = (struct bgp_info *)bgp_pbime->bgp_info; path = (struct bgp_path_info *)bgp_pbime->path;
extra = bgp_info_extra_get(bgp_info); extra = bgp_path_info_extra_get(path);
if (extra->bgp_fs_pbr == NULL) if (extra->bgp_fs_pbr == NULL)
extra->bgp_fs_pbr = list_new(); extra->bgp_fs_pbr = list_new();
listnode_add(extra->bgp_fs_pbr, bgp_pbime); listnode_add(extra->bgp_fs_pbr, bgp_pbime);

View File

@ -36,11 +36,12 @@ extern void bgp_config_write_maxpaths(struct vty *, struct bgp *, afi_t,
safi_t); safi_t);
extern void bgp_config_write_redistribute(struct vty *, struct bgp *, afi_t, extern void bgp_config_write_redistribute(struct vty *, struct bgp *, afi_t,
safi_t); safi_t);
extern void bgp_zebra_announce(struct bgp_node *, struct prefix *, extern void bgp_zebra_announce(struct bgp_node *rn, struct prefix *p,
struct bgp_info *, struct bgp *, afi_t, safi_t); struct bgp_path_info *path, struct bgp *bgp,
afi_t afi, safi_t safi);
extern void bgp_zebra_announce_table(struct bgp *, afi_t, safi_t); extern void bgp_zebra_announce_table(struct bgp *, afi_t, safi_t);
extern void bgp_zebra_withdraw(struct prefix *, struct bgp_info *, extern void bgp_zebra_withdraw(struct prefix *p, struct bgp_path_info *path,
struct bgp *, safi_t); struct bgp *bgp, safi_t safi);
extern void bgp_zebra_initiate_radv(struct bgp *bgp, struct peer *peer); extern void bgp_zebra_initiate_radv(struct bgp *bgp, struct peer *peer);
extern void bgp_zebra_terminate_radv(struct bgp *bgp, struct peer *peer); extern void bgp_zebra_terminate_radv(struct bgp *bgp, struct peer *peer);

View File

@ -361,7 +361,7 @@ void del_vnc_route(struct rfapi_descriptor *rfd,
{ {
afi_t afi; /* of the VN address */ afi_t afi; /* of the VN address */
struct bgp_node *bn; struct bgp_node *bn;
struct bgp_info *bi; struct bgp_path_info *bpi;
char buf[PREFIX_STRLEN]; char buf[PREFIX_STRLEN];
char buf2[RD_ADDRSTRLEN]; char buf2[RD_ADDRSTRLEN];
struct prefix_rd prd0; struct prefix_rd prd0;
@ -384,21 +384,22 @@ void del_vnc_route(struct rfapi_descriptor *rfd,
__func__, peer, buf, prefix_rd2str(prd, buf2, sizeof(buf2)), __func__, peer, buf, prefix_rd2str(prd, buf2, sizeof(buf2)),
afi, safi, bn, (bn ? bn->info : NULL)); afi, safi, bn, (bn ? bn->info : NULL));
for (bi = (bn ? bn->info : NULL); bi; bi = bi->next) { for (bpi = (bn ? bn->info : NULL); bpi; bpi = bpi->next) {
vnc_zlog_debug_verbose( vnc_zlog_debug_verbose(
"%s: trying bi=%p, bi->peer=%p, bi->type=%d, bi->sub_type=%d, bi->extra->vnc.export.rfapi_handle=%p, local_pref=%u", "%s: trying bpi=%p, bpi->peer=%p, bpi->type=%d, bpi->sub_type=%d, bpi->extra->vnc.export.rfapi_handle=%p, local_pref=%u",
__func__, bi, bi->peer, bi->type, bi->sub_type, __func__, bpi, bpi->peer, bpi->type, bpi->sub_type,
(bi->extra ? bi->extra->vnc.export.rfapi_handle : NULL), (bpi->extra ? bpi->extra->vnc.export.rfapi_handle
((bi->attr : NULL),
&& CHECK_FLAG(bi->attr->flag, ((bpi->attr
&& CHECK_FLAG(bpi->attr->flag,
ATTR_FLAG_BIT(BGP_ATTR_LOCAL_PREF))) ATTR_FLAG_BIT(BGP_ATTR_LOCAL_PREF)))
? bi->attr->local_pref ? bpi->attr->local_pref
: 0)); : 0));
if (bi->peer == peer && bi->type == type if (bpi->peer == peer && bpi->type == type
&& bi->sub_type == sub_type && bi->extra && bpi->sub_type == sub_type && bpi->extra
&& bi->extra->vnc.export.rfapi_handle == (void *)rfd) { && bpi->extra->vnc.export.rfapi_handle == (void *)rfd) {
vnc_zlog_debug_verbose("%s: matched it", __func__); vnc_zlog_debug_verbose("%s: matched it", __func__);
@ -412,8 +413,8 @@ void del_vnc_route(struct rfapi_descriptor *rfd,
* route. Leave the route itself in place. * route. Leave the route itself in place.
* TBD add return code reporting of success/failure * TBD add return code reporting of success/failure
*/ */
if (!bi || !bi->extra if (!bpi || !bpi->extra
|| !bi->extra->vnc.export.local_nexthops) { || !bpi->extra->vnc.export.local_nexthops) {
/* /*
* no local nexthops * no local nexthops
*/ */
@ -429,7 +430,7 @@ void del_vnc_route(struct rfapi_descriptor *rfd,
struct listnode *node; struct listnode *node;
struct rfapi_nexthop *pLnh = NULL; struct rfapi_nexthop *pLnh = NULL;
for (ALL_LIST_ELEMENTS_RO(bi->extra->vnc.export.local_nexthops, for (ALL_LIST_ELEMENTS_RO(bpi->extra->vnc.export.local_nexthops,
node, pLnh)) { node, pLnh)) {
if (prefix_same(&pLnh->addr, &lnh->addr)) { if (prefix_same(&pLnh->addr, &lnh->addr)) {
@ -438,7 +439,7 @@ void del_vnc_route(struct rfapi_descriptor *rfd,
} }
if (pLnh) { if (pLnh) {
listnode_delete(bi->extra->vnc.export.local_nexthops, listnode_delete(bpi->extra->vnc.export.local_nexthops,
pLnh); pLnh);
/* silly rabbit, listnode_delete doesn't invoke /* silly rabbit, listnode_delete doesn't invoke
@ -458,7 +459,7 @@ void del_vnc_route(struct rfapi_descriptor *rfd,
*/ */
rfapiProcessWithdraw(peer, rfd, p, prd, NULL, afi, safi, type, kill); rfapiProcessWithdraw(peer, rfd, p, prd, NULL, afi, safi, type, kill);
if (bi) { if (bpi) {
prefix2str(p, buf, sizeof(buf)); prefix2str(p, buf, sizeof(buf));
vnc_zlog_debug_verbose( vnc_zlog_debug_verbose(
"%s: Found route (safi=%d) to delete at prefix %s", "%s: Found route (safi=%d) to delete at prefix %s",
@ -474,7 +475,7 @@ void del_vnc_route(struct rfapi_descriptor *rfd,
table = (struct bgp_table *)(prn->info); table = (struct bgp_table *)(prn->info);
vnc_import_bgp_del_vnc_host_route_mode_resolve_nve( vnc_import_bgp_del_vnc_host_route_mode_resolve_nve(
bgp, prd, table, p, bi); bgp, prd, table, p, bpi);
} }
bgp_unlock_node(prn); bgp_unlock_node(prn);
} }
@ -482,13 +483,11 @@ void del_vnc_route(struct rfapi_descriptor *rfd,
/* /*
* Delete local_nexthops list * Delete local_nexthops list
*/ */
if (bi->extra && bi->extra->vnc.export.local_nexthops) { if (bpi->extra && bpi->extra->vnc.export.local_nexthops)
list_delete( list_delete(&bpi->extra->vnc.export.local_nexthops);
&bi->extra->vnc.export.local_nexthops);
}
bgp_aggregate_decrement(bgp, p, bi, afi, safi); bgp_aggregate_decrement(bgp, p, bpi, afi, safi);
bgp_info_delete(bn, bi); bgp_path_info_delete(bn, bpi);
bgp_process(bgp, bn, afi, safi); bgp_process(bgp, bn, afi, safi);
} else { } else {
vnc_zlog_debug_verbose( vnc_zlog_debug_verbose(
@ -575,8 +574,8 @@ void add_vnc_route(struct rfapi_descriptor *rfd, /* cookie, VPN UN addr, peer */
int flags) int flags)
{ {
afi_t afi; /* of the VN address */ afi_t afi; /* of the VN address */
struct bgp_info *new; struct bgp_path_info *new;
struct bgp_info *bi; struct bgp_path_info *bpi;
struct bgp_node *bn; struct bgp_node *bn;
struct attr attr = {0}; struct attr attr = {0};
@ -946,29 +945,29 @@ void add_vnc_route(struct rfapi_descriptor *rfd, /* cookie, VPN UN addr, peer */
* ecommunity: POINTS TO interned/refcounted dynamic 2-part AS attr * ecommunity: POINTS TO interned/refcounted dynamic 2-part AS attr
* aspath: POINTS TO interned/refcounted hashed block * aspath: POINTS TO interned/refcounted hashed block
*/ */
for (bi = bn->info; bi; bi = bi->next) { for (bpi = bn->info; bpi; bpi = bpi->next) {
/* probably only need to check /* probably only need to check
* bi->extra->vnc.export.rfapi_handle */ * bpi->extra->vnc.export.rfapi_handle */
if (bi->peer == rfd->peer && bi->type == type if (bpi->peer == rfd->peer && bpi->type == type
&& bi->sub_type == sub_type && bi->extra && bpi->sub_type == sub_type && bpi->extra
&& bi->extra->vnc.export.rfapi_handle == (void *)rfd) { && bpi->extra->vnc.export.rfapi_handle == (void *)rfd) {
break; break;
} }
} }
if (bi) { if (bpi) {
/* /*
* Adding new local_nexthop, which does not by itself change * Adding new local_nexthop, which does not by itself change
* what is advertised via BGP * what is advertised via BGP
*/ */
if (lnh) { if (lnh) {
if (!bi->extra->vnc.export.local_nexthops) { if (!bpi->extra->vnc.export.local_nexthops) {
/* TBD make arrangements to free when needed */ /* TBD make arrangements to free when needed */
bi->extra->vnc.export.local_nexthops = bpi->extra->vnc.export.local_nexthops =
list_new(); list_new();
bi->extra->vnc.export.local_nexthops->del = bpi->extra->vnc.export.local_nexthops->del =
rfapi_nexthop_free; rfapi_nexthop_free;
} }
@ -979,8 +978,8 @@ void add_vnc_route(struct rfapi_descriptor *rfd, /* cookie, VPN UN addr, peer */
struct rfapi_nexthop *pLnh = NULL; struct rfapi_nexthop *pLnh = NULL;
for (ALL_LIST_ELEMENTS_RO( for (ALL_LIST_ELEMENTS_RO(
bi->extra->vnc.export.local_nexthops, node, bpi->extra->vnc.export.local_nexthops,
pLnh)) { node, pLnh)) {
if (prefix_same(&pLnh->addr, &lnh->addr)) { if (prefix_same(&pLnh->addr, &lnh->addr)) {
break; break;
@ -993,13 +992,13 @@ void add_vnc_route(struct rfapi_descriptor *rfd, /* cookie, VPN UN addr, peer */
if (!pLnh) { if (!pLnh) {
pLnh = rfapi_nexthop_new(lnh); pLnh = rfapi_nexthop_new(lnh);
listnode_add( listnode_add(
bi->extra->vnc.export.local_nexthops, bpi->extra->vnc.export.local_nexthops,
pLnh); pLnh);
} }
} }
if (attrhash_cmp(bi->attr, new_attr) if (attrhash_cmp(bpi->attr, new_attr)
&& !CHECK_FLAG(bi->flags, BGP_INFO_REMOVED)) { && !CHECK_FLAG(bpi->flags, BGP_PATH_REMOVED)) {
bgp_attr_unintern(&new_attr); bgp_attr_unintern(&new_attr);
bgp_unlock_node(bn); bgp_unlock_node(bn);
@ -1010,7 +1009,7 @@ void add_vnc_route(struct rfapi_descriptor *rfd, /* cookie, VPN UN addr, peer */
goto done; goto done;
} else { } else {
/* The attribute is changed. */ /* The attribute is changed. */
bgp_info_set_flag(bn, bi, BGP_INFO_ATTR_CHANGED); bgp_path_info_set_flag(bn, bpi, BGP_PATH_ATTR_CHANGED);
if (safi == SAFI_MPLS_VPN) { if (safi == SAFI_MPLS_VPN) {
struct bgp_node *prn = NULL; struct bgp_node *prn = NULL;
@ -1022,19 +1021,19 @@ void add_vnc_route(struct rfapi_descriptor *rfd, /* cookie, VPN UN addr, peer */
table = (struct bgp_table *)(prn->info); table = (struct bgp_table *)(prn->info);
vnc_import_bgp_del_vnc_host_route_mode_resolve_nve( vnc_import_bgp_del_vnc_host_route_mode_resolve_nve(
bgp, prd, table, p, bi); bgp, prd, table, p, bpi);
} }
bgp_unlock_node(prn); bgp_unlock_node(prn);
} }
/* Rewrite BGP route information. */ /* Rewrite BGP route information. */
if (CHECK_FLAG(bi->flags, BGP_INFO_REMOVED)) if (CHECK_FLAG(bpi->flags, BGP_PATH_REMOVED))
bgp_info_restore(bn, bi); bgp_path_info_restore(bn, bpi);
else else
bgp_aggregate_decrement(bgp, p, bi, afi, safi); bgp_aggregate_decrement(bgp, p, bpi, afi, safi);
bgp_attr_unintern(&bi->attr); bgp_attr_unintern(&bpi->attr);
bi->attr = new_attr; bpi->attr = new_attr;
bi->uptime = bgp_clock(); bpi->uptime = bgp_clock();
if (safi == SAFI_MPLS_VPN) { if (safi == SAFI_MPLS_VPN) {
@ -1047,13 +1046,13 @@ void add_vnc_route(struct rfapi_descriptor *rfd, /* cookie, VPN UN addr, peer */
table = (struct bgp_table *)(prn->info); table = (struct bgp_table *)(prn->info);
vnc_import_bgp_add_vnc_host_route_mode_resolve_nve( vnc_import_bgp_add_vnc_host_route_mode_resolve_nve(
bgp, prd, table, p, bi); bgp, prd, table, p, bpi);
} }
bgp_unlock_node(prn); bgp_unlock_node(prn);
} }
/* Process change. */ /* Process change. */
bgp_aggregate_increment(bgp, p, bi, afi, safi); bgp_aggregate_increment(bgp, p, bpi, afi, safi);
bgp_process(bgp, bn, afi, safi); bgp_process(bgp, bn, afi, safi);
bgp_unlock_node(bn); bgp_unlock_node(bn);
@ -1066,16 +1065,16 @@ void add_vnc_route(struct rfapi_descriptor *rfd, /* cookie, VPN UN addr, peer */
} }
new = bgp_info_new(); new = bgp_path_info_new();
new->type = type; new->type = type;
new->sub_type = sub_type; new->sub_type = sub_type;
new->peer = rfd->peer; new->peer = rfd->peer;
SET_FLAG(new->flags, BGP_INFO_VALID); SET_FLAG(new->flags, BGP_PATH_VALID);
new->attr = new_attr; new->attr = new_attr;
new->uptime = bgp_clock(); new->uptime = bgp_clock();
/* save backref to rfapi handle */ /* save backref to rfapi handle */
assert(bgp_info_extra_get(new)); assert(bgp_path_info_extra_get(new));
new->extra->vnc.export.rfapi_handle = (void *)rfd; new->extra->vnc.export.rfapi_handle = (void *)rfd;
encode_label(label_val, &new->extra->label[0]); encode_label(label_val, &new->extra->label[0]);
@ -1087,7 +1086,7 @@ void add_vnc_route(struct rfapi_descriptor *rfd, /* cookie, VPN UN addr, peer */
} }
bgp_aggregate_increment(bgp, p, new, afi, safi); bgp_aggregate_increment(bgp, p, new, afi, safi);
bgp_info_add(bn, new); bgp_path_info_add(bn, new);
if (safi == SAFI_MPLS_VPN) { if (safi == SAFI_MPLS_VPN) {
struct bgp_node *prn = NULL; struct bgp_node *prn = NULL;
@ -3690,7 +3689,7 @@ static void rfapi_print_exported(struct bgp *bgp)
{ {
struct bgp_node *rdn; struct bgp_node *rdn;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *bi; struct bgp_path_info *bpi;
if (!bgp) if (!bgp)
return; return;
@ -3705,8 +3704,8 @@ static void rfapi_print_exported(struct bgp *bgp)
if (!rn->info) if (!rn->info)
continue; continue;
fprintf(stderr, "%s: rn=%p\n", __func__, rn); fprintf(stderr, "%s: rn=%p\n", __func__, rn);
for (bi = rn->info; bi; bi = bi->next) { for (bpi = rn->info; bpi; bpi = bpi->next) {
rfapiPrintBi((void *)2, bi); /* 2 => stderr */ rfapiPrintBi((void *)2, bpi); /* 2 => stderr */
} }
} }
} }
@ -3720,8 +3719,8 @@ static void rfapi_print_exported(struct bgp *bgp)
if (!rn->info) if (!rn->info)
continue; continue;
fprintf(stderr, "%s: rn=%p\n", __func__, rn); fprintf(stderr, "%s: rn=%p\n", __func__, rn);
for (bi = rn->info; bi; bi = bi->next) { for (bpi = rn->info; bpi; bpi = bpi->next) {
rfapiPrintBi((void *)2, bi); /* 2 => stderr */ rfapiPrintBi((void *)2, bpi); /* 2 => stderr */
} }
} }
} }

View File

@ -48,14 +48,16 @@ extern void rfapiProcessWithdraw(struct peer *peer, void *rfd, struct prefix *p,
extern void rfapiProcessPeerDown(struct peer *peer); extern void rfapiProcessPeerDown(struct peer *peer);
extern void vnc_zebra_announce(struct prefix *p, struct bgp_info *new_select, extern void vnc_zebra_announce(struct prefix *p,
struct bgp_path_info *new_select,
struct bgp *bgp); struct bgp *bgp);
extern void vnc_zebra_withdraw(struct prefix *p, struct bgp_info *old_select); extern void vnc_zebra_withdraw(struct prefix *p,
struct bgp_path_info *old_select);
extern void rfapi_vty_out_vncinfo(struct vty *vty, struct prefix *p, extern void rfapi_vty_out_vncinfo(struct vty *vty, struct prefix *p,
struct bgp_info *bi, safi_t safi); struct bgp_path_info *bpi, safi_t safi);
extern void vnc_direct_bgp_vpn_enable(struct bgp *bgp, afi_t afi); extern void vnc_direct_bgp_vpn_enable(struct bgp *bgp, afi_t afi);

File diff suppressed because it is too large Load Diff

View File

@ -31,7 +31,7 @@
/* /*
* These are per-rt-import-list * These are per-rt-import-list
* *
* routes are not segregated by RD - the RD is stored in bgp_info_extra * routes are not segregated by RD - the RD is stored in bgp_path_info_extra
* and is needed to determine if two prefixes are the same. * and is needed to determine if two prefixes are the same.
*/ */
struct rfapi_import_table { struct rfapi_import_table {
@ -51,18 +51,18 @@ struct rfapi_import_table {
int imported_count[AFI_MAX]; int imported_count[AFI_MAX];
}; };
#define RFAPI_LOCAL_BI(bi) \ #define RFAPI_LOCAL_BI(bpi) \
(((bi)->type == ZEBRA_ROUTE_BGP) && ((bi)->sub_type == BGP_ROUTE_RFP)) (((bpi)->type == ZEBRA_ROUTE_BGP) && ((bpi)->sub_type == BGP_ROUTE_RFP))
#define RFAPI_DIRECT_IMPORT_BI(bi) \ #define RFAPI_DIRECT_IMPORT_BI(bpi) \
(((bi)->type == ZEBRA_ROUTE_BGP_DIRECT) \ (((bpi)->type == ZEBRA_ROUTE_BGP_DIRECT) \
|| ((bi)->type == ZEBRA_ROUTE_BGP_DIRECT_EXT)) || ((bpi)->type == ZEBRA_ROUTE_BGP_DIRECT_EXT))
#define RFAPI_UPDATE_ITABLE_COUNT(bi, itable, afi, cnt) \ #define RFAPI_UPDATE_ITABLE_COUNT(bpi, itable, afi, cnt) \
if (RFAPI_LOCAL_BI(bi)) { \ if (RFAPI_LOCAL_BI(bpi)) { \
(itable)->local_count[(afi)] += (cnt); \ (itable)->local_count[(afi)] += (cnt); \
} else { \ } else { \
if (RFAPI_DIRECT_IMPORT_BI(bi)) \ if (RFAPI_DIRECT_IMPORT_BI(bpi)) \
(itable)->imported_count[(afi)] += (cnt); \ (itable)->imported_count[(afi)] += (cnt); \
else \ else \
(itable)->remote_count[(afi)] += (cnt); \ (itable)->remote_count[(afi)] += (cnt); \
@ -75,9 +75,9 @@ extern void rfapiDebugBacktrace(void);
extern void rfapiCheckRouteCount(void); extern void rfapiCheckRouteCount(void);
/* /*
* Print BI in an Import Table * Print BPI in an Import Table
*/ */
extern void rfapiPrintBi(void *stream, struct bgp_info *bi); extern void rfapiPrintBi(void *stream, struct bgp_path_info *bpi);
extern void rfapiShowImportTable(void *stream, const char *label, extern void rfapiShowImportTable(void *stream, const char *label,
struct agg_table *rt, int isvpn); struct agg_table *rt, int isvpn);
@ -94,7 +94,7 @@ extern void rfapiImportTableRefDelByIt(struct bgp *bgp,
* Construct an rfapi nexthop list based on the routes attached to * Construct an rfapi nexthop list based on the routes attached to
* the specified node. * the specified node.
* *
* If there are any routes that do NOT have BGP_INFO_REMOVED set, * If there are any routes that do NOT have BGP_PATH_REMOVED set,
* return those only. If there are ONLY routes with BGP_INFO_REMOVED, * return those only. If there are ONLY routes with BGP_INFO_REMOVED,
* then return those, and also include all the non-removed routes from the * then return those, and also include all the non-removed routes from the
* next less-specific node (i.e., this node's parent) at the end. * next less-specific node (i.e., this node's parent) at the end.
@ -128,7 +128,7 @@ extern int rfapiHasNonRemovedRoutes(struct agg_node *rn);
extern int rfapiProcessDeferredClose(struct thread *t); extern int rfapiProcessDeferredClose(struct thread *t);
extern int rfapiGetUnAddrOfVpnBi(struct bgp_info *bi, struct prefix *p); extern int rfapiGetUnAddrOfVpnBi(struct bgp_path_info *bpi, struct prefix *p);
extern void rfapiNexthop2Prefix(struct attr *attr, struct prefix *p); extern void rfapiNexthop2Prefix(struct attr *attr, struct prefix *p);
@ -146,10 +146,10 @@ extern void rfapiBgpInfoFilteredImportVPN(
struct prefix *p, struct prefix *p,
struct prefix *aux_prefix, /* AFI_ETHER: optional IP */ struct prefix *aux_prefix, /* AFI_ETHER: optional IP */
afi_t afi, struct prefix_rd *prd, afi_t afi, struct prefix_rd *prd,
struct attr *attr, /* part of bgp_info */ struct attr *attr, /* part of bgp_path_info */
uint8_t type, /* part of bgp_info */ uint8_t type, /* part of bgp_path_info */
uint8_t sub_type, /* part of bgp_info */ uint8_t sub_type, /* part of bgp_path_info */
uint32_t *label); /* part of bgp_info */ uint32_t *label); /* part of bgp_path_info */
extern struct rfapi_next_hop_entry *rfapiEthRouteNode2NextHopList( extern struct rfapi_next_hop_entry *rfapiEthRouteNode2NextHopList(
struct agg_node *rn, struct rfapi_ip_prefix *rprefix, struct agg_node *rn, struct rfapi_ip_prefix *rprefix,

View File

@ -226,7 +226,7 @@ void rfapiMonitorExtraFlush(safi_t safi, struct agg_node *rn)
agg_unlock_node(rn); agg_unlock_node(rn);
} }
if (hie->u.vpn.idx_rd) { if (hie->u.vpn.idx_rd) {
/* looping through bi->extra->vnc.import.rd is tbd */ /* looping through bpi->extra->vnc.import.rd is tbd */
while (!skiplist_delete_first(hie->u.vpn.idx_rd)) { while (!skiplist_delete_first(hie->u.vpn.idx_rd)) {
agg_unlock_node(rn); agg_unlock_node(rn);
} }
@ -346,16 +346,16 @@ struct agg_node *rfapiMonitorGetAttachNode(struct rfapi_descriptor *rfd,
for (rn = agg_node_match(rfd->import_table->imported_vpn[afi], p); for (rn = agg_node_match(rfd->import_table->imported_vpn[afi], p);
rn;) { rn;) {
struct bgp_info *bi; struct bgp_path_info *bpi;
struct prefix pfx_dummy; struct prefix pfx_dummy;
/* TBD update this code to use new valid_interior_count */ /* TBD update this code to use new valid_interior_count */
for (bi = rn->info; bi; bi = bi->next) { for (bpi = rn->info; bpi; bpi = bpi->next) {
/* /*
* If there is a cached ENCAP UN address, it's a usable * If there is a cached ENCAP UN address, it's a usable
* VPN route * VPN route
*/ */
if (bi->extra && bi->extra->vnc.import.un_family) { if (bpi->extra && bpi->extra->vnc.import.un_family) {
break; break;
} }
@ -364,11 +364,11 @@ struct agg_node *rfapiMonitorGetAttachNode(struct rfapi_descriptor *rfd,
* address, * address,
* it's a usable VPN route. * it's a usable VPN route.
*/ */
if (!rfapiGetVncTunnelUnAddr(bi->attr, &pfx_dummy)) { if (!rfapiGetVncTunnelUnAddr(bpi->attr, &pfx_dummy)) {
break; break;
} }
} }
if (bi) if (bpi)
break; break;
agg_unlock_node(rn); agg_unlock_node(rn);

View File

@ -45,7 +45,7 @@ struct rfapi_monitor_encap {
struct rfapi_monitor_encap *next; struct rfapi_monitor_encap *next;
struct rfapi_monitor_encap *prev; struct rfapi_monitor_encap *prev;
struct agg_node *node; /* VPN node */ struct agg_node *node; /* VPN node */
struct bgp_info *bi; /* VPN bi */ struct bgp_path_info *bpi; /* VPN bpi */
struct agg_node *rn; /* parent node */ struct agg_node *rn; /* parent node */
}; };
@ -83,7 +83,7 @@ struct rfapi_it_extra {
* Encap TLV */ * Encap TLV */
int valid_interior_count; int valid_interior_count;
/* unicast exterior routes, key=bi, /* unicast exterior routes, key=bpi,
* val=allocated prefix */ * val=allocated prefix */
struct skiplist *source; struct skiplist *source;
} e; } e;

View File

@ -212,7 +212,7 @@ struct rfapi {
/* /*
* when importing bgp-direct routes in resolve-nve mode, * when importing bgp-direct routes in resolve-nve mode,
* this list maps unicast route nexthops to their bgp_infos * this list maps unicast route nexthops to their bgp_path_infos
* in the unicast table * in the unicast table
*/ */
struct skiplist *resolve_nve_nexthop; struct skiplist *resolve_nve_nexthop;

View File

@ -616,18 +616,18 @@ void rfapiRibFree(struct rfapi_descriptor *rfd)
} }
/* /*
* Copies struct bgp_info to struct rfapi_info, except for rk fields and un * Copies struct bgp_path_info to struct rfapi_info, except for rk fields and un
*/ */
static void rfapiRibBi2Ri(struct bgp_info *bi, struct rfapi_info *ri, static void rfapiRibBi2Ri(struct bgp_path_info *bpi, struct rfapi_info *ri,
uint32_t lifetime) uint32_t lifetime)
{ {
struct bgp_attr_encap_subtlv *pEncap; struct bgp_attr_encap_subtlv *pEncap;
ri->cost = rfapiRfpCost(bi->attr); ri->cost = rfapiRfpCost(bpi->attr);
ri->lifetime = lifetime; ri->lifetime = lifetime;
/* This loop based on rfapiRouteInfo2NextHopEntry() */ /* This loop based on rfapiRouteInfo2NextHopEntry() */
for (pEncap = bi->attr->vnc_subtlvs; pEncap; pEncap = pEncap->next) { for (pEncap = bpi->attr->vnc_subtlvs; pEncap; pEncap = pEncap->next) {
struct bgp_tea_options *hop; struct bgp_tea_options *hop;
switch (pEncap->type) { switch (pEncap->type) {
@ -665,13 +665,13 @@ static void rfapiRibBi2Ri(struct bgp_info *bi, struct rfapi_info *ri,
} }
rfapi_un_options_free(ri->un_options); /* maybe free old version */ rfapi_un_options_free(ri->un_options); /* maybe free old version */
ri->un_options = rfapi_encap_tlv_to_un_option(bi->attr); ri->un_options = rfapi_encap_tlv_to_un_option(bpi->attr);
/* /*
* VN options * VN options
*/ */
if (bi->extra if (bpi->extra
&& decode_rd_type(bi->extra->vnc.import.rd.val) && decode_rd_type(bpi->extra->vnc.import.rd.val)
== RD_TYPE_VNC_ETH) { == RD_TYPE_VNC_ETH) {
/* ethernet route */ /* ethernet route */
@ -683,21 +683,21 @@ static void rfapiRibBi2Ri(struct bgp_info *bi, struct rfapi_info *ri,
vo->type = RFAPI_VN_OPTION_TYPE_L2ADDR; vo->type = RFAPI_VN_OPTION_TYPE_L2ADDR;
/* copy from RD already stored in bi, so we don't need it_node /* copy from RD already stored in bpi, so we don't need it_node
*/ */
memcpy(&vo->v.l2addr.macaddr, bi->extra->vnc.import.rd.val + 2, memcpy(&vo->v.l2addr.macaddr, bpi->extra->vnc.import.rd.val + 2,
ETH_ALEN); ETH_ALEN);
(void)rfapiEcommunityGetLNI(bi->attr->ecommunity, (void)rfapiEcommunityGetLNI(bpi->attr->ecommunity,
&vo->v.l2addr.logical_net_id); &vo->v.l2addr.logical_net_id);
(void)rfapiEcommunityGetEthernetTag(bi->attr->ecommunity, (void)rfapiEcommunityGetEthernetTag(bpi->attr->ecommunity,
&vo->v.l2addr.tag_id); &vo->v.l2addr.tag_id);
/* local_nve_id comes from RD */ /* local_nve_id comes from RD */
vo->v.l2addr.local_nve_id = bi->extra->vnc.import.rd.val[1]; vo->v.l2addr.local_nve_id = bpi->extra->vnc.import.rd.val[1];
/* label comes from MP_REACH_NLRI label */ /* label comes from MP_REACH_NLRI label */
vo->v.l2addr.label = decode_label(&bi->extra->label[0]); vo->v.l2addr.label = decode_label(&bpi->extra->label[0]);
rfapi_vn_options_free( rfapi_vn_options_free(
ri->vn_options); /* maybe free old version */ ri->vn_options); /* maybe free old version */
@ -707,8 +707,8 @@ static void rfapiRibBi2Ri(struct bgp_info *bi, struct rfapi_info *ri,
/* /*
* If there is an auxiliary IP address (L2 can have it), copy it * If there is an auxiliary IP address (L2 can have it), copy it
*/ */
if (bi->extra && bi->extra->vnc.import.aux_prefix.family) { if (bpi->extra && bpi->extra->vnc.import.aux_prefix.family) {
ri->rk.aux_prefix = bi->extra->vnc.import.aux_prefix; ri->rk.aux_prefix = bpi->extra->vnc.import.aux_prefix;
} }
} }
@ -733,7 +733,7 @@ static void rfapiRibBi2Ri(struct bgp_info *bi, struct rfapi_info *ri,
int rfapiRibPreloadBi( int rfapiRibPreloadBi(
struct agg_node *rfd_rib_node, /* NULL = don't preload or filter */ struct agg_node *rfd_rib_node, /* NULL = don't preload or filter */
struct prefix *pfx_vn, struct prefix *pfx_un, uint32_t lifetime, struct prefix *pfx_vn, struct prefix *pfx_un, uint32_t lifetime,
struct bgp_info *bi) struct bgp_path_info *bpi)
{ {
struct rfapi_descriptor *rfd; struct rfapi_descriptor *rfd;
struct skiplist *slRibPt = NULL; struct skiplist *slRibPt = NULL;
@ -751,13 +751,13 @@ int rfapiRibPreloadBi(
memset((void *)&rk, 0, sizeof(rk)); memset((void *)&rk, 0, sizeof(rk));
rk.vn = *pfx_vn; rk.vn = *pfx_vn;
rk.rd = bi->extra->vnc.import.rd; rk.rd = bpi->extra->vnc.import.rd;
/* /*
* If there is an auxiliary IP address (L2 can have it), copy it * If there is an auxiliary IP address (L2 can have it), copy it
*/ */
if (bi->extra->vnc.import.aux_prefix.family) { if (bpi->extra->vnc.import.aux_prefix.family) {
rk.aux_prefix = bi->extra->vnc.import.aux_prefix; rk.aux_prefix = bpi->extra->vnc.import.aux_prefix;
} }
/* /*
@ -774,13 +774,13 @@ int rfapiRibPreloadBi(
/* found: update contents of existing route in RIB */ /* found: update contents of existing route in RIB */
ori->un = *pfx_un; ori->un = *pfx_un;
rfapiRibBi2Ri(bi, ori, lifetime); rfapiRibBi2Ri(bpi, ori, lifetime);
} else { } else {
/* not found: add new route to RIB */ /* not found: add new route to RIB */
ori = rfapi_info_new(); ori = rfapi_info_new();
ori->rk = rk; ori->rk = rk;
ori->un = *pfx_un; ori->un = *pfx_un;
rfapiRibBi2Ri(bi, ori, lifetime); rfapiRibBi2Ri(bpi, ori, lifetime);
if (!slRibPt) { if (!slRibPt) {
slRibPt = skiplist_new(0, rfapi_rib_key_cmp, NULL); slRibPt = skiplist_new(0, rfapi_rib_key_cmp, NULL);
@ -1590,7 +1590,7 @@ void rfapiRibUpdatePendingNode(
struct agg_node *it_node, uint32_t lifetime) struct agg_node *it_node, uint32_t lifetime)
{ {
struct prefix *prefix; struct prefix *prefix;
struct bgp_info *bi; struct bgp_path_info *bpi;
struct agg_node *pn; struct agg_node *pn;
afi_t afi; afi_t afi;
uint32_t queued_flag; uint32_t queued_flag;
@ -1640,25 +1640,25 @@ void rfapiRibUpdatePendingNode(
} }
/* /*
* The BIs in the import table are already sorted by cost * The BPIs in the import table are already sorted by cost
*/ */
for (bi = it_node->info; bi; bi = bi->next) { for (bpi = it_node->info; bpi; bpi = bpi->next) {
struct rfapi_info *ri; struct rfapi_info *ri;
struct prefix pfx_nh; struct prefix pfx_nh;
if (!bi->attr) { if (!bpi->attr) {
/* shouldn't happen */ /* shouldn't happen */
/* TBD increment error stats counter */ /* TBD increment error stats counter */
continue; continue;
} }
if (!bi->extra) { if (!bpi->extra) {
/* shouldn't happen */ /* shouldn't happen */
/* TBD increment error stats counter */ /* TBD increment error stats counter */
continue; continue;
} }
rfapiNexthop2Prefix(bi->attr, &pfx_nh); rfapiNexthop2Prefix(bpi->attr, &pfx_nh);
/* /*
* Omit route if nexthop is self * Omit route if nexthop is self
@ -1675,15 +1675,15 @@ void rfapiRibUpdatePendingNode(
ri = rfapi_info_new(); ri = rfapi_info_new();
ri->rk.vn = pfx_nh; ri->rk.vn = pfx_nh;
ri->rk.rd = bi->extra->vnc.import.rd; ri->rk.rd = bpi->extra->vnc.import.rd;
/* /*
* If there is an auxiliary IP address (L2 can have it), copy it * If there is an auxiliary IP address (L2 can have it), copy it
*/ */
if (bi->extra->vnc.import.aux_prefix.family) { if (bpi->extra->vnc.import.aux_prefix.family) {
ri->rk.aux_prefix = bi->extra->vnc.import.aux_prefix; ri->rk.aux_prefix = bpi->extra->vnc.import.aux_prefix;
} }
if (rfapiGetUnAddrOfVpnBi(bi, &ri->un)) { if (rfapiGetUnAddrOfVpnBi(bpi, &ri->un)) {
rfapi_info_free(ri); rfapi_info_free(ri);
continue; continue;
} }
@ -1711,7 +1711,7 @@ void rfapiRibUpdatePendingNode(
continue; continue;
} }
rfapiRibBi2Ri(bi, ri, lifetime); rfapiRibBi2Ri(bpi, ri, lifetime);
if (!pn->info) { if (!pn->info) {
pn->info = list_new(); pn->info = list_new();

View File

@ -105,7 +105,7 @@ extern void rfapiRibUpdatePendingNodeSubtree(struct bgp *bgp,
extern int rfapiRibPreloadBi(struct agg_node *rfd_rib_node, extern int rfapiRibPreloadBi(struct agg_node *rfd_rib_node,
struct prefix *pfx_vn, struct prefix *pfx_un, struct prefix *pfx_vn, struct prefix *pfx_un,
uint32_t lifetime, struct bgp_info *bi); uint32_t lifetime, struct bgp_path_info *bpi);
extern struct rfapi_next_hop_entry * extern struct rfapi_next_hop_entry *
rfapiRibPreload(struct bgp *bgp, struct rfapi_descriptor *rfd, rfapiRibPreload(struct bgp *bgp, struct rfapi_descriptor *rfd,

View File

@ -394,7 +394,7 @@ int rfapiStream2Vty(void *stream, /* input */
/* called from bgpd/bgp_vty.c'route_vty_out() */ /* called from bgpd/bgp_vty.c'route_vty_out() */
void rfapi_vty_out_vncinfo(struct vty *vty, struct prefix *p, void rfapi_vty_out_vncinfo(struct vty *vty, struct prefix *p,
struct bgp_info *bi, safi_t safi) struct bgp_path_info *bpi, safi_t safi)
{ {
char *s; char *s;
uint32_t lifetime; uint32_t lifetime;
@ -410,7 +410,7 @@ void rfapi_vty_out_vncinfo(struct vty *vty, struct prefix *p,
if (safi == SAFI_MPLS_VPN) { if (safi == SAFI_MPLS_VPN) {
struct prefix pfx_un; struct prefix pfx_un;
if (!rfapiGetVncTunnelUnAddr(bi->attr, &pfx_un)) { if (!rfapiGetVncTunnelUnAddr(bpi->attr, &pfx_un)) {
char buf[BUFSIZ]; char buf[BUFSIZ];
vty_out(vty, "UN=%s", vty_out(vty, "UN=%s",
inet_ntop(pfx_un.family, pfx_un.u.val, buf, inet_ntop(pfx_un.family, pfx_un.u.val, buf,
@ -418,27 +418,27 @@ void rfapi_vty_out_vncinfo(struct vty *vty, struct prefix *p,
} }
} }
if (bi->attr && bi->attr->ecommunity) { if (bpi->attr && bpi->attr->ecommunity) {
s = ecommunity_ecom2str(bi->attr->ecommunity, s = ecommunity_ecom2str(bpi->attr->ecommunity,
ECOMMUNITY_FORMAT_ROUTE_MAP, 0); ECOMMUNITY_FORMAT_ROUTE_MAP, 0);
vty_out(vty, " EC{%s}", s); vty_out(vty, " EC{%s}", s);
XFREE(MTYPE_ECOMMUNITY_STR, s); XFREE(MTYPE_ECOMMUNITY_STR, s);
} }
if (bi->extra != NULL) { if (bpi->extra != NULL) {
if (bi->extra->label[0] == BGP_PREVENT_VRF_2_VRF_LEAK) if (bpi->extra->label[0] == BGP_PREVENT_VRF_2_VRF_LEAK)
vty_out(vty, " label=VRF2VRF"); vty_out(vty, " label=VRF2VRF");
else else
vty_out(vty, " label=%u", vty_out(vty, " label=%u",
decode_label(&bi->extra->label[0])); decode_label(&bpi->extra->label[0]));
} }
if (!rfapiGetVncLifetime(bi->attr, &lifetime)) { if (!rfapiGetVncLifetime(bpi->attr, &lifetime)) {
vty_out(vty, " life=%d", lifetime); vty_out(vty, " life=%d", lifetime);
} }
vty_out(vty, " type=%s, subtype=%d", zebra_route_string(bi->type), vty_out(vty, " type=%s, subtype=%d", zebra_route_string(bpi->type),
bi->sub_type); bpi->sub_type);
vty_out(vty, "%s", HVTYNL); vty_out(vty, "%s", HVTYNL);
} }
@ -477,9 +477,9 @@ void rfapiPrintAttrPtrs(void *stream, struct attr *attr)
} }
/* /*
* Print BI in an Import Table * Print BPI in an Import Table
*/ */
void rfapiPrintBi(void *stream, struct bgp_info *bi) void rfapiPrintBi(void *stream, struct bgp_path_info *bpi)
{ {
char buf[BUFSIZ]; char buf[BUFSIZ];
char *s; char *s;
@ -503,12 +503,13 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
if (rfapiStream2Vty(stream, &fp, &vty, &out, &vty_newline) == 0) if (rfapiStream2Vty(stream, &fp, &vty, &out, &vty_newline) == 0)
return; return;
if (!bi) if (!bpi)
return; return;
if (CHECK_FLAG(bi->flags, BGP_INFO_REMOVED) && bi->extra if (CHECK_FLAG(bpi->flags, BGP_PATH_REMOVED) && bpi->extra
&& bi->extra->vnc.import.timer) { && bpi->extra->vnc.import.timer) {
struct thread *t = (struct thread *)bi->extra->vnc.import.timer; struct thread *t =
(struct thread *)bpi->extra->vnc.import.timer;
r = snprintf(p, REMAIN, " [%4lu] ", r = snprintf(p, REMAIN, " [%4lu] ",
thread_timer_remain_second(t)); thread_timer_remain_second(t));
INCP; INCP;
@ -518,14 +519,14 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
INCP; INCP;
} }
if (bi->extra) { if (bpi->extra) {
/* TBD This valid only for SAFI_MPLS_VPN, but not for encap */ /* TBD This valid only for SAFI_MPLS_VPN, but not for encap */
if (decode_rd_type(bi->extra->vnc.import.rd.val) if (decode_rd_type(bpi->extra->vnc.import.rd.val)
== RD_TYPE_VNC_ETH) { == RD_TYPE_VNC_ETH) {
has_macaddr = 1; has_macaddr = 1;
memcpy(macaddr.octet, bi->extra->vnc.import.rd.val + 2, memcpy(macaddr.octet, bpi->extra->vnc.import.rd.val + 2,
6); 6);
l2hid = bi->extra->vnc.import.rd.val[1]; l2hid = bpi->extra->vnc.import.rd.val[1];
} }
} }
@ -537,24 +538,24 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
* RFP option sizes (they are opaque values) * RFP option sizes (they are opaque values)
* extended communities (RTs) * extended communities (RTs)
*/ */
if (bi->attr) { if (bpi->attr) {
uint32_t lifetime; uint32_t lifetime;
int printed_1st_gol = 0; int printed_1st_gol = 0;
struct bgp_attr_encap_subtlv *pEncap; struct bgp_attr_encap_subtlv *pEncap;
struct prefix pfx_un; struct prefix pfx_un;
int af = BGP_MP_NEXTHOP_FAMILY(bi->attr->mp_nexthop_len); int af = BGP_MP_NEXTHOP_FAMILY(bpi->attr->mp_nexthop_len);
/* Nexthop */ /* Nexthop */
if (af == AF_INET) { if (af == AF_INET) {
r = snprintf(p, REMAIN, "%s", r = snprintf(p, REMAIN, "%s",
inet_ntop(AF_INET, inet_ntop(AF_INET,
&bi->attr->mp_nexthop_global_in, &bpi->attr->mp_nexthop_global_in,
buf, BUFSIZ)); buf, BUFSIZ));
INCP; INCP;
} else if (af == AF_INET6) { } else if (af == AF_INET6) {
r = snprintf(p, REMAIN, "%s", r = snprintf(p, REMAIN, "%s",
inet_ntop(AF_INET6, inet_ntop(AF_INET6,
&bi->attr->mp_nexthop_global, &bpi->attr->mp_nexthop_global,
buf, BUFSIZ)); buf, BUFSIZ));
INCP; INCP;
} else { } else {
@ -565,7 +566,7 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
/* /*
* VNC tunnel subtlv, if present, contains UN address * VNC tunnel subtlv, if present, contains UN address
*/ */
if (!rfapiGetVncTunnelUnAddr(bi->attr, &pfx_un)) { if (!rfapiGetVncTunnelUnAddr(bpi->attr, &pfx_un)) {
r = snprintf(p, REMAIN, " un=%s", r = snprintf(p, REMAIN, " un=%s",
inet_ntop(pfx_un.family, pfx_un.u.val, buf, inet_ntop(pfx_un.family, pfx_un.u.val, buf,
BUFSIZ)); BUFSIZ));
@ -573,7 +574,7 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
} }
/* Lifetime */ /* Lifetime */
if (rfapiGetVncLifetime(bi->attr, &lifetime)) { if (rfapiGetVncLifetime(bpi->attr, &lifetime)) {
r = snprintf(p, REMAIN, " nolife"); r = snprintf(p, REMAIN, " nolife");
INCP; INCP;
} else { } else {
@ -585,7 +586,7 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
} }
/* RFP option lengths */ /* RFP option lengths */
for (pEncap = bi->attr->vnc_subtlvs; pEncap; for (pEncap = bpi->attr->vnc_subtlvs; pEncap;
pEncap = pEncap->next) { pEncap = pEncap->next) {
if (pEncap->type == BGP_VNC_SUBTLV_TYPE_RFPOPTION) { if (pEncap->type == BGP_VNC_SUBTLV_TYPE_RFPOPTION) {
@ -604,8 +605,8 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
} }
/* RT list */ /* RT list */
if (bi->attr->ecommunity) { if (bpi->attr->ecommunity) {
s = ecommunity_ecom2str(bi->attr->ecommunity, s = ecommunity_ecom2str(bpi->attr->ecommunity,
ECOMMUNITY_FORMAT_ROUTE_MAP, 0); ECOMMUNITY_FORMAT_ROUTE_MAP, 0);
r = snprintf(p, REMAIN, " %s", s); r = snprintf(p, REMAIN, " %s", s);
INCP; INCP;
@ -613,13 +614,13 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
} }
} }
r = snprintf(p, REMAIN, " bi@%p", bi); r = snprintf(p, REMAIN, " bpi@%p", bpi);
INCP; INCP;
r = snprintf(p, REMAIN, " p@%p", bi->peer); r = snprintf(p, REMAIN, " p@%p", bpi->peer);
INCP; INCP;
if (CHECK_FLAG(bi->flags, BGP_INFO_REMOVED)) { if (CHECK_FLAG(bpi->flags, BGP_PATH_REMOVED)) {
r = snprintf(p, REMAIN, " HD=yes"); r = snprintf(p, REMAIN, " HD=yes");
INCP; INCP;
} else { } else {
@ -627,15 +628,16 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
INCP; INCP;
} }
if (bi->attr) { if (bpi->attr) {
if (bi->attr->weight) { if (bpi->attr->weight) {
r = snprintf(p, REMAIN, " W=%d", bi->attr->weight); r = snprintf(p, REMAIN, " W=%d", bpi->attr->weight);
INCP; INCP;
} }
if (bi->attr->flag & ATTR_FLAG_BIT(BGP_ATTR_LOCAL_PREF)) { if (bpi->attr->flag & ATTR_FLAG_BIT(BGP_ATTR_LOCAL_PREF)) {
r = snprintf(p, REMAIN, " LP=%d", bi->attr->local_pref); r = snprintf(p, REMAIN, " LP=%d",
bpi->attr->local_pref);
INCP; INCP;
} else { } else {
r = snprintf(p, REMAIN, " LP=unset"); r = snprintf(p, REMAIN, " LP=unset");
@ -643,8 +645,8 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
} }
} }
r = snprintf(p, REMAIN, " %c:%u", zebra_route_char(bi->type), r = snprintf(p, REMAIN, " %c:%u", zebra_route_char(bpi->type),
bi->sub_type); bpi->sub_type);
INCP; INCP;
fp(out, "%s%s", line, HVTYNL); fp(out, "%s%s", line, HVTYNL);
@ -656,7 +658,7 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
HVTYNL); HVTYNL);
} }
if (!rfapiGetL2o(bi->attr, &l2o_buf)) { if (!rfapiGetL2o(bpi->attr, &l2o_buf)) {
fp(out, fp(out,
" L2O ETH=%02x:%02x:%02x:%02x:%02x:%02x LBL=%d LNI=%d LHI=%hhu%s", " L2O ETH=%02x:%02x:%02x:%02x:%02x:%02x LBL=%d LNI=%d LHI=%hhu%s",
l2o_buf.macaddr.octet[0], l2o_buf.macaddr.octet[1], l2o_buf.macaddr.octet[0], l2o_buf.macaddr.octet[1],
@ -665,12 +667,12 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
l2o_buf.label, l2o_buf.logical_net_id, l2o_buf.local_nve_id, l2o_buf.label, l2o_buf.logical_net_id, l2o_buf.local_nve_id,
HVTYNL); HVTYNL);
} }
if (bi->extra && bi->extra->vnc.import.aux_prefix.family) { if (bpi->extra && bpi->extra->vnc.import.aux_prefix.family) {
const char *sp; const char *sp;
sp = rfapi_ntop(bi->extra->vnc.import.aux_prefix.family, sp = rfapi_ntop(bpi->extra->vnc.import.aux_prefix.family,
&bi->extra->vnc.import.aux_prefix.u.prefix, buf, &bpi->extra->vnc.import.aux_prefix.u.prefix,
BUFSIZ); buf, BUFSIZ);
buf[BUFSIZ - 1] = 0; buf[BUFSIZ - 1] = 0;
if (sp) { if (sp) {
fp(out, " IP: %s%s", sp, HVTYNL); fp(out, " IP: %s%s", sp, HVTYNL);
@ -678,7 +680,7 @@ void rfapiPrintBi(void *stream, struct bgp_info *bi)
} }
{ {
struct rfapi_un_option *uo = struct rfapi_un_option *uo =
rfapi_encap_tlv_to_un_option(bi->attr); rfapi_encap_tlv_to_un_option(bpi->attr);
if (uo) { if (uo) {
rfapi_print_tunneltype_option(stream, 8, &uo->v.tunnel); rfapi_print_tunneltype_option(stream, 8, &uo->v.tunnel);
rfapi_un_options_free(uo); rfapi_un_options_free(uo);
@ -734,13 +736,13 @@ static void rfapiDebugPrintMonitorEncap(void *stream,
if (rfapiStream2Vty(stream, &fp, &vty, &out, &vty_newline) == 0) if (rfapiStream2Vty(stream, &fp, &vty, &out, &vty_newline) == 0)
return; return;
fp(out, " Mon m=%p, next=%p, node=%p, bi=%p%s", m, m->next, m->node, fp(out, " Mon m=%p, next=%p, node=%p, bpi=%p%s", m, m->next, m->node,
m->bi, HVTYNL); m->bpi, HVTYNL);
} }
void rfapiShowItNode(void *stream, struct agg_node *rn) void rfapiShowItNode(void *stream, struct agg_node *rn)
{ {
struct bgp_info *bi; struct bgp_path_info *bpi;
char buf[BUFSIZ]; char buf[BUFSIZ];
int (*fp)(void *, const char *, ...); int (*fp)(void *, const char *, ...);
@ -755,8 +757,8 @@ void rfapiShowItNode(void *stream, struct agg_node *rn)
rfapi_ntop(rn->p.family, &rn->p.u.prefix, buf, BUFSIZ), rfapi_ntop(rn->p.family, &rn->p.u.prefix, buf, BUFSIZ),
rn->p.prefixlen, rn, rn->lock, HVTYNL); rn->p.prefixlen, rn, rn->lock, HVTYNL);
for (bi = rn->info; bi; bi = bi->next) { for (bpi = rn->info; bpi; bpi = bpi->next) {
rfapiPrintBi(stream, bi); rfapiPrintBi(stream, bpi);
} }
/* doesn't show montors */ /* doesn't show montors */
@ -779,7 +781,7 @@ void rfapiShowImportTable(void *stream, const char *label, struct agg_table *rt,
fp(out, "Import Table [%s]%s", label, HVTYNL); fp(out, "Import Table [%s]%s", label, HVTYNL);
for (rn = agg_route_top(rt); rn; rn = agg_route_next(rn)) { for (rn = agg_route_top(rt); rn; rn = agg_route_next(rn)) {
struct bgp_info *bi; struct bgp_path_info *bpi;
if (rn->p.family == AF_ETHERNET) { if (rn->p.family == AF_ETHERNET) {
rfapiEthAddr2Str(&rn->p.u.prefix_eth, buf, BUFSIZ); rfapiEthAddr2Str(&rn->p.u.prefix_eth, buf, BUFSIZ);
@ -791,8 +793,8 @@ void rfapiShowImportTable(void *stream, const char *label, struct agg_table *rt,
rn->lock - 1, /* account for loop iterator locking */ rn->lock - 1, /* account for loop iterator locking */
HVTYNL); HVTYNL);
for (bi = rn->info; bi; bi = bi->next) { for (bpi = rn->info; bpi; bpi = bpi->next) {
rfapiPrintBi(stream, bi); rfapiPrintBi(stream, bpi);
} }
if (isvpn) { if (isvpn) {
@ -1008,7 +1010,7 @@ int rfapiShowVncQueries(void *stream, struct prefix *pfx_match)
} }
static int rfapiPrintRemoteRegBi(struct bgp *bgp, void *stream, static int rfapiPrintRemoteRegBi(struct bgp *bgp, void *stream,
struct agg_node *rn, struct bgp_info *bi) struct agg_node *rn, struct bgp_path_info *bpi)
{ {
int (*fp)(void *, const char *, ...); int (*fp)(void *, const char *, ...);
struct vty *vty; struct vty *vty;
@ -1047,26 +1049,26 @@ static int rfapiPrintRemoteRegBi(struct bgp *bgp, void *stream,
* UN addr * UN addr
*/ */
buf_un[0] = 0; buf_un[0] = 0;
if (!rfapiGetUnAddrOfVpnBi(bi, &pfx_un)) { if (!rfapiGetUnAddrOfVpnBi(bpi, &pfx_un)) {
snprintf(buf_un, BUFSIZ, "%s", snprintf(buf_un, BUFSIZ, "%s",
inet_ntop(pfx_un.family, &pfx_un.u.prefix, buf_ntop, inet_ntop(pfx_un.family, &pfx_un.u.prefix, buf_ntop,
BUFSIZ)); BUFSIZ));
} }
rfapiGetTunnelType(bi->attr, &tun_type); rfapiGetTunnelType(bpi->attr, &tun_type);
/* /*
* VN addr * VN addr
*/ */
buf_vn[0] = 0; buf_vn[0] = 0;
rfapiNexthop2Prefix(bi->attr, &pfx_vn); rfapiNexthop2Prefix(bpi->attr, &pfx_vn);
if (tun_type == BGP_ENCAP_TYPE_MPLS) { if (tun_type == BGP_ENCAP_TYPE_MPLS) {
/* MPLS carries un in nrli next hop (same as vn for IP tunnels) /* MPLS carries un in nrli next hop (same as vn for IP tunnels)
*/ */
snprintf(buf_un, BUFSIZ, "%s", snprintf(buf_un, BUFSIZ, "%s",
inet_ntop(pfx_vn.family, &pfx_vn.u.prefix, buf_ntop, inet_ntop(pfx_vn.family, &pfx_vn.u.prefix, buf_ntop,
BUFSIZ)); BUFSIZ));
if (bi->extra) { if (bpi->extra) {
uint32_t l = decode_label(&bi->extra->label[0]); uint32_t l = decode_label(&bpi->extra->label[0]);
snprintf(buf_vn, BUFSIZ, "Label: %d", l); snprintf(buf_vn, BUFSIZ, "Label: %d", l);
} else /* should never happen */ } else /* should never happen */
{ {
@ -1085,10 +1087,10 @@ static int rfapiPrintRemoteRegBi(struct bgp *bgp, void *stream,
* See rfapi_import.c'rfapiRouteInfo2NextHopEntry() for conversion * See rfapi_import.c'rfapiRouteInfo2NextHopEntry() for conversion
* back to cost. * back to cost.
*/ */
if (bi->attr) { if (bpi->attr) {
uint32_t local_pref; uint32_t local_pref;
if (bi->attr->flag & ATTR_FLAG_BIT(BGP_ATTR_LOCAL_PREF)) if (bpi->attr->flag & ATTR_FLAG_BIT(BGP_ATTR_LOCAL_PREF))
local_pref = bi->attr->local_pref; local_pref = bpi->attr->local_pref;
else else
local_pref = 0; local_pref = 0;
cost = (local_pref > 255) ? 0 : 255 - local_pref; cost = (local_pref > 255) ? 0 : 255 - local_pref;
@ -1103,7 +1105,7 @@ static int rfapiPrintRemoteRegBi(struct bgp *bgp, void *stream,
/* Lifetime */ /* Lifetime */
/* NB rfapiGetVncLifetime sets infinite value when returning !0 */ /* NB rfapiGetVncLifetime sets infinite value when returning !0 */
if (rfapiGetVncLifetime(bi->attr, &lifetime) if (rfapiGetVncLifetime(bpi->attr, &lifetime)
|| (lifetime == RFAPI_INFINITE_LIFETIME)) { || (lifetime == RFAPI_INFINITE_LIFETIME)) {
fp(out, "%-10s ", "infinite"); fp(out, "%-10s ", "infinite");
@ -1113,20 +1115,21 @@ static int rfapiPrintRemoteRegBi(struct bgp *bgp, void *stream,
fp(out, "%-10s ", buf_lifetime); fp(out, "%-10s ", buf_lifetime);
} }
if (CHECK_FLAG(bi->flags, BGP_INFO_REMOVED) && bi->extra if (CHECK_FLAG(bpi->flags, BGP_PATH_REMOVED) && bpi->extra
&& bi->extra->vnc.import.timer) { && bpi->extra->vnc.import.timer) {
uint32_t remaining; uint32_t remaining;
time_t age; time_t age;
char buf_age[BUFSIZ]; char buf_age[BUFSIZ];
struct thread *t = (struct thread *)bi->extra->vnc.import.timer; struct thread *t =
(struct thread *)bpi->extra->vnc.import.timer;
remaining = thread_timer_remain_second(t); remaining = thread_timer_remain_second(t);
#if RFAPI_REGISTRATIONS_REPORT_AGE #if RFAPI_REGISTRATIONS_REPORT_AGE
/* /*
* Calculate when the timer started. Doing so here saves * Calculate when the timer started. Doing so here saves
* us a timestamp field in "struct bgp_info". * us a timestamp field in "struct bgp_path_info".
* *
* See rfapi_import.c'rfapiBiStartWithdrawTimer() for the * See rfapi_import.c'rfapiBiStartWithdrawTimer() for the
* original calculation. * original calculation.
@ -1140,12 +1143,12 @@ static int rfapiPrintRemoteRegBi(struct bgp *bgp, void *stream,
fp(out, "%-10s ", buf_age); fp(out, "%-10s ", buf_age);
} else if (RFAPI_LOCAL_BI(bi)) { } else if (RFAPI_LOCAL_BI(bpi)) {
char buf_age[BUFSIZ]; char buf_age[BUFSIZ];
if (bi->extra && bi->extra->vnc.import.create_time) { if (bpi->extra && bpi->extra->vnc.import.create_time) {
rfapiFormatAge(bi->extra->vnc.import.create_time, rfapiFormatAge(bpi->extra->vnc.import.create_time,
buf_age, BUFSIZ); buf_age, BUFSIZ);
} else { } else {
buf_age[0] = '?'; buf_age[0] = '?';
@ -1161,12 +1164,12 @@ static int rfapiPrintRemoteRegBi(struct bgp *bgp, void *stream,
* print that on the next line * print that on the next line
*/ */
if (bi->extra && bi->extra->vnc.import.aux_prefix.family) { if (bpi->extra && bpi->extra->vnc.import.aux_prefix.family) {
const char *sp; const char *sp;
sp = rfapi_ntop( sp = rfapi_ntop(
bi->extra->vnc.import.aux_prefix.family, bpi->extra->vnc.import.aux_prefix.family,
&bi->extra->vnc.import.aux_prefix.u.prefix, &bpi->extra->vnc.import.aux_prefix.u.prefix,
buf_ntop, BUFSIZ); buf_ntop, BUFSIZ);
buf_ntop[BUFSIZ - 1] = 0; buf_ntop[BUFSIZ - 1] = 0;
@ -1177,8 +1180,8 @@ static int rfapiPrintRemoteRegBi(struct bgp *bgp, void *stream,
} }
} }
} }
if (tun_type != BGP_ENCAP_TYPE_MPLS && bi->extra) { if (tun_type != BGP_ENCAP_TYPE_MPLS && bpi->extra) {
uint32_t l = decode_label(&bi->extra->label[0]); uint32_t l = decode_label(&bpi->extra->label[0]);
if (!MPLS_LABEL_IS_NULL(l)) { if (!MPLS_LABEL_IS_NULL(l)) {
fp(out, " Label: %d", l); fp(out, " Label: %d", l);
if (nlines == 1) if (nlines == 1)
@ -1222,7 +1225,7 @@ static int rfapiShowRemoteRegistrationsIt(struct bgp *bgp, void *stream,
for (rn = agg_route_top(it->imported_vpn[afi]); rn; for (rn = agg_route_top(it->imported_vpn[afi]); rn;
rn = agg_route_next(rn)) { rn = agg_route_next(rn)) {
struct bgp_info *bi; struct bgp_path_info *bpi;
int count_only; int count_only;
/* allow for wider or more narrow mask from user */ /* allow for wider or more narrow mask from user */
@ -1232,30 +1235,32 @@ static int rfapiShowRemoteRegistrationsIt(struct bgp *bgp, void *stream,
else else
count_only = 0; count_only = 0;
for (bi = rn->info; bi; bi = bi->next) { for (bpi = rn->info; bpi; bpi = bpi->next) {
if (!show_local && RFAPI_LOCAL_BI(bi)) { if (!show_local && RFAPI_LOCAL_BI(bpi)) {
/* local route from RFP */ /* local route from RFP */
continue; continue;
} }
if (!show_remote && !RFAPI_LOCAL_BI(bi)) { if (!show_remote && !RFAPI_LOCAL_BI(bpi)) {
/* remote route */ /* remote route */
continue; continue;
} }
if (show_expiring if (show_expiring
&& !CHECK_FLAG(bi->flags, BGP_INFO_REMOVED)) && !CHECK_FLAG(bpi->flags,
BGP_PATH_REMOVED))
continue; continue;
if (!show_expiring if (!show_expiring
&& CHECK_FLAG(bi->flags, BGP_INFO_REMOVED)) && CHECK_FLAG(bpi->flags, BGP_PATH_REMOVED))
continue; continue;
if (bi->type == ZEBRA_ROUTE_BGP_DIRECT if (bpi->type == ZEBRA_ROUTE_BGP_DIRECT
|| bi->type == ZEBRA_ROUTE_BGP_DIRECT_EXT) { || bpi->type
== ZEBRA_ROUTE_BGP_DIRECT_EXT) {
if (!show_imported) if (!show_imported)
continue; continue;
} else { } else {
@ -1277,7 +1282,7 @@ static int rfapiShowRemoteRegistrationsIt(struct bgp *bgp, void *stream,
type = "Holddown"; type = "Holddown";
} else { } else {
if (RFAPI_LOCAL_BI( if (RFAPI_LOCAL_BI(
bi)) { bpi)) {
type = "Local"; type = "Local";
} else { } else {
type = "Remote"; type = "Remote";
@ -1327,7 +1332,7 @@ static int rfapiShowRemoteRegistrationsIt(struct bgp *bgp, void *stream,
"Lifetime", agetype, HVTYNL); "Lifetime", agetype, HVTYNL);
} }
printed += rfapiPrintRemoteRegBi(bgp, stream, printed += rfapiPrintRemoteRegBi(bgp, stream,
rn, bi); rn, bpi);
} }
} }
} }
@ -1535,7 +1540,7 @@ void rfapiPrintAdvertisedInfo(struct vty *vty, struct rfapi_descriptor *rfd,
{ {
afi_t afi; /* of the VN address */ afi_t afi; /* of the VN address */
struct bgp_node *bn; struct bgp_node *bn;
struct bgp_info *bi; struct bgp_path_info *bpi;
uint8_t type = ZEBRA_ROUTE_BGP; uint8_t type = ZEBRA_ROUTE_BGP;
struct bgp *bgp; struct bgp *bgp;
int printed = 0; int printed = 0;
@ -1543,7 +1548,7 @@ void rfapiPrintAdvertisedInfo(struct vty *vty, struct rfapi_descriptor *rfd,
struct prefix_rd *prd; struct prefix_rd *prd;
/* /*
* Find the bgp_info in the RIB corresponding to this * Find the bgp_path in the RIB corresponding to this
* prefix and rfd * prefix and rfd
*/ */
@ -1565,12 +1570,12 @@ void rfapiPrintAdvertisedInfo(struct vty *vty, struct rfapi_descriptor *rfd,
vty_out(vty, " bn=%p%s", bn, HVTYNL); vty_out(vty, " bn=%p%s", bn, HVTYNL);
for (bi = bn->info; bi; bi = bi->next) { for (bpi = bn->info; bpi; bpi = bpi->next) {
if (bi->peer == rfd->peer && bi->type == type if (bpi->peer == rfd->peer && bpi->type == type
&& bi->sub_type == BGP_ROUTE_RFP && bi->extra && bpi->sub_type == BGP_ROUTE_RFP && bpi->extra
&& bi->extra->vnc.export.rfapi_handle == (void *)rfd) { && bpi->extra->vnc.export.rfapi_handle == (void *)rfd) {
rfapiPrintBi(vty, bi); rfapiPrintBi(vty, bpi);
printed = 1; printed = 1;
} }
} }

View File

@ -173,14 +173,14 @@ static int getce(struct bgp *bgp, struct attr *attr, struct prefix *pfx_ce)
void vnc_direct_bgp_add_route_ce(struct bgp *bgp, struct agg_node *rn, void vnc_direct_bgp_add_route_ce(struct bgp *bgp, struct agg_node *rn,
struct bgp_info *bi) struct bgp_path_info *bpi)
{ {
struct attr *attr = bi->attr; struct attr *attr = bpi->attr;
struct peer *peer = bi->peer; struct peer *peer = bpi->peer;
struct prefix *prefix = &rn->p; struct prefix *prefix = &rn->p;
afi_t afi = family2afi(prefix->family); afi_t afi = family2afi(prefix->family);
struct bgp_node *urn; struct bgp_node *urn;
struct bgp_info *ubi; struct bgp_path_info *ubpi;
struct attr hattr; struct attr hattr;
struct attr *iattr; struct attr *iattr;
struct prefix ce_nexthop; struct prefix ce_nexthop;
@ -193,10 +193,10 @@ void vnc_direct_bgp_add_route_ce(struct bgp *bgp, struct agg_node *rn,
return; return;
} }
if ((bi->type != ZEBRA_ROUTE_BGP) if ((bpi->type != ZEBRA_ROUTE_BGP)
|| (bi->sub_type != BGP_ROUTE_NORMAL || (bpi->sub_type != BGP_ROUTE_NORMAL
&& bi->sub_type != BGP_ROUTE_RFP && bpi->sub_type != BGP_ROUTE_RFP
&& bi->sub_type != BGP_ROUTE_STATIC)) { && bpi->sub_type != BGP_ROUTE_STATIC)) {
vnc_zlog_debug_verbose( vnc_zlog_debug_verbose(
"%s: wrong route type/sub_type for export, skipping", "%s: wrong route type/sub_type for export, skipping",
@ -256,17 +256,17 @@ void vnc_direct_bgp_add_route_ce(struct bgp *bgp, struct agg_node *rn,
*/ */
urn = bgp_afi_node_get(bgp->rib[afi][SAFI_UNICAST], afi, SAFI_UNICAST, urn = bgp_afi_node_get(bgp->rib[afi][SAFI_UNICAST], afi, SAFI_UNICAST,
prefix, NULL); prefix, NULL);
for (ubi = urn->info; ubi; ubi = ubi->next) { for (ubpi = urn->info; ubpi; ubpi = ubpi->next) {
struct prefix unicast_nexthop; struct prefix unicast_nexthop;
if (CHECK_FLAG(ubi->flags, BGP_INFO_REMOVED)) if (CHECK_FLAG(ubpi->flags, BGP_PATH_REMOVED))
continue; continue;
rfapiUnicastNexthop2Prefix(afi, ubi->attr, &unicast_nexthop); rfapiUnicastNexthop2Prefix(afi, ubpi->attr, &unicast_nexthop);
if (ubi->type == ZEBRA_ROUTE_VNC_DIRECT if (ubpi->type == ZEBRA_ROUTE_VNC_DIRECT
&& ubi->sub_type == BGP_ROUTE_REDISTRIBUTE && ubpi->sub_type == BGP_ROUTE_REDISTRIBUTE
&& ubi->peer == peer && ubpi->peer == peer
&& prefix_same(&unicast_nexthop, &ce_nexthop)) { && prefix_same(&unicast_nexthop, &ce_nexthop)) {
vnc_zlog_debug_verbose( vnc_zlog_debug_verbose(
@ -282,7 +282,7 @@ void vnc_direct_bgp_add_route_ce(struct bgp *bgp, struct agg_node *rn,
*/ */
encap_attr_export_ce(&hattr, attr, &ce_nexthop); encap_attr_export_ce(&hattr, attr, &ce_nexthop);
if (bgp->rfapi_cfg->routemap_export_bgp) { if (bgp->rfapi_cfg->routemap_export_bgp) {
struct bgp_info info; struct bgp_path_info info;
route_map_result_t ret; route_map_result_t ret;
memset(&info, 0, sizeof(info)); memset(&info, 0, sizeof(info));
@ -328,10 +328,10 @@ void vnc_direct_bgp_add_route_ce(struct bgp *bgp, struct agg_node *rn,
* "Withdrawing a Route" export process * "Withdrawing a Route" export process
*/ */
void vnc_direct_bgp_del_route_ce(struct bgp *bgp, struct agg_node *rn, void vnc_direct_bgp_del_route_ce(struct bgp *bgp, struct agg_node *rn,
struct bgp_info *bi) struct bgp_path_info *bpi)
{ {
afi_t afi = family2afi(rn->p.family); afi_t afi = family2afi(rn->p.family);
struct bgp_info *vbi; struct bgp_path_info *vbpi;
struct prefix ce_nexthop; struct prefix ce_nexthop;
if (!afi) { if (!afi) {
@ -364,7 +364,7 @@ void vnc_direct_bgp_del_route_ce(struct bgp *bgp, struct agg_node *rn,
* This works only for IPv4 because IPv6 addresses are too big * This works only for IPv4 because IPv6 addresses are too big
* to fit in an extended community * to fit in an extended community
*/ */
if (getce(bgp, bi->attr, &ce_nexthop)) { if (getce(bgp, bpi->attr, &ce_nexthop)) {
vnc_zlog_debug_verbose("%s: EC has no encoded CE, skipping", vnc_zlog_debug_verbose("%s: EC has no encoded CE, skipping",
__func__); __func__);
return; return;
@ -376,13 +376,13 @@ void vnc_direct_bgp_del_route_ce(struct bgp *bgp, struct agg_node *rn,
* route from the unicast RIB * route from the unicast RIB
*/ */
for (vbi = rn->info; vbi; vbi = vbi->next) { for (vbpi = rn->info; vbpi; vbpi = vbpi->next) {
struct prefix ce; struct prefix ce;
if (bi == vbi) if (bpi == vbpi)
continue; continue;
if (bi->peer != vbi->peer) if (bpi->peer != vbpi->peer)
continue; continue;
if (getce(bgp, vbi->attr, &ce)) if (getce(bgp, vbpi->attr, &ce))
continue; continue;
if (prefix_same(&ce, &ce_nexthop)) { if (prefix_same(&ce, &ce_nexthop)) {
vnc_zlog_debug_verbose( vnc_zlog_debug_verbose(
@ -395,7 +395,7 @@ void vnc_direct_bgp_del_route_ce(struct bgp *bgp, struct agg_node *rn,
/* /*
* withdraw the route * withdraw the route
*/ */
bgp_withdraw(bi->peer, &rn->p, 0, /* addpath_id */ bgp_withdraw(bpi->peer, &rn->p, 0, /* addpath_id */
NULL, /* attr, ignored */ NULL, /* attr, ignored */
afi, SAFI_UNICAST, ZEBRA_ROUTE_VNC_DIRECT, afi, SAFI_UNICAST, ZEBRA_ROUTE_VNC_DIRECT,
BGP_ROUTE_REDISTRIBUTE, NULL, /* RD not used for unicast */ BGP_ROUTE_REDISTRIBUTE, NULL, /* RD not used for unicast */
@ -405,7 +405,7 @@ void vnc_direct_bgp_del_route_ce(struct bgp *bgp, struct agg_node *rn,
static void vnc_direct_bgp_vpn_enable_ce(struct bgp *bgp, afi_t afi) static void vnc_direct_bgp_vpn_enable_ce(struct bgp *bgp, afi_t afi)
{ {
struct agg_node *rn; struct agg_node *rn;
struct bgp_info *ri; struct bgp_path_info *ri;
vnc_zlog_debug_verbose("%s: entry, afi=%d", __func__, afi); vnc_zlog_debug_verbose("%s: entry, afi=%d", __func__, afi);
@ -480,8 +480,8 @@ static void vnc_direct_bgp_vpn_disable_ce(struct bgp *bgp, afi_t afi)
for (rn = bgp_table_top(bgp->rib[afi][SAFI_UNICAST]); rn; for (rn = bgp_table_top(bgp->rib[afi][SAFI_UNICAST]); rn;
rn = bgp_route_next(rn)) { rn = bgp_route_next(rn)) {
struct bgp_info *ri; struct bgp_path_info *ri;
struct bgp_info *next; struct bgp_path_info *next;
for (ri = rn->info, next = NULL; ri; ri = next) { for (ri = rn->info, next = NULL; ri; ri = next) {
@ -516,24 +516,24 @@ static void vnc_direct_bgp_vpn_disable_ce(struct bgp *bgp, afi_t afi)
static struct ecommunity *vnc_route_origin_ecom(struct agg_node *rn) static struct ecommunity *vnc_route_origin_ecom(struct agg_node *rn)
{ {
struct ecommunity *new; struct ecommunity *new;
struct bgp_info *bi; struct bgp_path_info *bpi;
if (!rn->info) if (!rn->info)
return NULL; return NULL;
new = ecommunity_new(); new = ecommunity_new();
for (bi = rn->info; bi; bi = bi->next) { for (bpi = rn->info; bpi; bpi = bpi->next) {
struct ecommunity_val roec; struct ecommunity_val roec;
switch (BGP_MP_NEXTHOP_FAMILY(bi->attr->mp_nexthop_len)) { switch (BGP_MP_NEXTHOP_FAMILY(bpi->attr->mp_nexthop_len)) {
case AF_INET: case AF_INET:
memset(&roec, 0, sizeof(roec)); memset(&roec, 0, sizeof(roec));
roec.val[0] = 0x01; roec.val[0] = 0x01;
roec.val[1] = 0x03; roec.val[1] = 0x03;
memcpy(roec.val + 2, memcpy(roec.val + 2,
&bi->attr->mp_nexthop_global_in.s_addr, 4); &bpi->attr->mp_nexthop_global_in.s_addr, 4);
roec.val[6] = 0; roec.val[6] = 0;
roec.val[7] = 0; roec.val[7] = 0;
ecommunity_add_val(new, &roec); ecommunity_add_val(new, &roec);
@ -996,7 +996,7 @@ void vnc_direct_bgp_add_nve(struct bgp *bgp, struct rfapi_descriptor *rfd)
struct rfapi_descriptor *irfd = rfd; struct rfapi_descriptor *irfd = rfd;
struct attr hattr; struct attr hattr;
struct attr *iattr; struct attr *iattr;
struct bgp_info info; struct bgp_path_info info;
if (rfapiRaddr2Qprefix(&irfd->vn_addr, if (rfapiRaddr2Qprefix(&irfd->vn_addr,
&nhp)) &nhp))
@ -1165,7 +1165,7 @@ static void vnc_direct_add_rn_group_rd(struct bgp *bgp,
afi_t afi, struct rfapi_descriptor *irfd) afi_t afi, struct rfapi_descriptor *irfd)
{ {
struct prefix nhp; struct prefix nhp;
struct bgp_info info; struct bgp_path_info info;
struct attr hattr; struct attr hattr;
struct attr *iattr; struct attr *iattr;
@ -1629,7 +1629,7 @@ void vnc_direct_bgp_vpn_disable(struct bgp *bgp, afi_t afi)
/* /*
* "Adding a Route" export process * "Adding a Route" export process
* TBD do we need to check bi->type and bi->sub_type here, or does * TBD do we need to check bpi->type and bpi->sub_type here, or does
* caller do it? * caller do it?
*/ */
void vnc_direct_bgp_rh_add_route(struct bgp *bgp, afi_t afi, void vnc_direct_bgp_rh_add_route(struct bgp *bgp, afi_t afi,
@ -1684,7 +1684,7 @@ void vnc_direct_bgp_rh_add_route(struct bgp *bgp, afi_t afi,
if (encap_attr_export(&hattr, attr, NULL, NULL)) if (encap_attr_export(&hattr, attr, NULL, NULL))
return; return;
if (hc->routemap_export_bgp) { if (hc->routemap_export_bgp) {
struct bgp_info info; struct bgp_path_info info;
route_map_result_t ret; route_map_result_t ret;
memset(&info, 0, sizeof(info)); memset(&info, 0, sizeof(info));
@ -1753,7 +1753,7 @@ static int vncExportWithdrawTimer(struct thread *t)
/* /*
* "Withdrawing a Route" export process * "Withdrawing a Route" export process
* TBD do we need to check bi->type and bi->sub_type here, or does * TBD do we need to check bpi->type and bpi->sub_type here, or does
* caller do it? * caller do it?
*/ */
void vnc_direct_bgp_rh_del_route(struct bgp *bgp, afi_t afi, void vnc_direct_bgp_rh_del_route(struct bgp *bgp, afi_t afi,
@ -1839,7 +1839,7 @@ void vnc_direct_bgp_rh_vpn_enable(struct bgp *bgp, afi_t afi)
struct bgp_table *table; struct bgp_table *table;
struct bgp_node *rn; struct bgp_node *rn;
struct bgp_info *ri; struct bgp_path_info *ri;
memset(&prd, 0, sizeof(prd)); memset(&prd, 0, sizeof(prd));
prd.family = AF_UNSPEC; prd.family = AF_UNSPEC;
@ -1910,7 +1910,7 @@ void vnc_direct_bgp_rh_vpn_enable(struct bgp *bgp, afi_t afi)
} }
if (hc->routemap_export_bgp) { if (hc->routemap_export_bgp) {
struct bgp_info info; struct bgp_path_info info;
route_map_result_t ret; route_map_result_t ret;
memset(&info, 0, sizeof(info)); memset(&info, 0, sizeof(info));
@ -2001,8 +2001,8 @@ void vnc_direct_bgp_rh_vpn_disable(struct bgp *bgp, afi_t afi)
for (rn = bgp_table_top(bgp->rib[afi][SAFI_UNICAST]); rn; for (rn = bgp_table_top(bgp->rib[afi][SAFI_UNICAST]); rn;
rn = bgp_route_next(rn)) { rn = bgp_route_next(rn)) {
struct bgp_info *ri; struct bgp_path_info *ri;
struct bgp_info *next; struct bgp_path_info *next;
for (ri = rn->info, next = NULL; ri; ri = next) { for (ri = rn->info, next = NULL; ri; ri = next) {

View File

@ -30,10 +30,10 @@
#include "rfapi_private.h" #include "rfapi_private.h"
extern void vnc_direct_bgp_add_route_ce(struct bgp *bgp, struct agg_node *rn, extern void vnc_direct_bgp_add_route_ce(struct bgp *bgp, struct agg_node *rn,
struct bgp_info *bi); struct bgp_path_info *bpi);
extern void vnc_direct_bgp_del_route_ce(struct bgp *bgp, struct agg_node *rn, extern void vnc_direct_bgp_del_route_ce(struct bgp *bgp, struct agg_node *rn,
struct bgp_info *bi); struct bgp_path_info *bpi);
extern void vnc_direct_bgp_add_prefix(struct bgp *bgp, extern void vnc_direct_bgp_add_prefix(struct bgp *bgp,
struct rfapi_import_table *import_table, struct rfapi_import_table *import_table,

File diff suppressed because it is too large Load Diff

View File

@ -35,10 +35,10 @@ extern uint32_t calc_local_pref(struct attr *attr, struct peer *peer);
extern int vnc_prefix_cmp(void *pfx1, void *pfx2); extern int vnc_prefix_cmp(void *pfx1, void *pfx2);
extern void vnc_import_bgp_add_route(struct bgp *bgp, struct prefix *prefix, extern void vnc_import_bgp_add_route(struct bgp *bgp, struct prefix *prefix,
struct bgp_info *info); struct bgp_path_info *info);
extern void vnc_import_bgp_del_route(struct bgp *bgp, struct prefix *prefix, extern void vnc_import_bgp_del_route(struct bgp *bgp, struct prefix *prefix,
struct bgp_info *info); struct bgp_path_info *info);
extern void vnc_import_bgp_redist_enable(struct bgp *bgp, afi_t afi); extern void vnc_import_bgp_redist_enable(struct bgp *bgp, afi_t afi);
@ -52,23 +52,22 @@ extern void vnc_import_bgp_exterior_redist_disable(struct bgp *bgp, afi_t afi);
extern void vnc_import_bgp_exterior_add_route( extern void vnc_import_bgp_exterior_add_route(
struct bgp *bgp, /* exterior instance, we hope */ struct bgp *bgp, /* exterior instance, we hope */
struct prefix *prefix, /* unicast prefix */ struct prefix *prefix, /* unicast prefix */
struct bgp_info *info); /* unicast info */ struct bgp_path_info *info); /* unicast info */
extern void extern void vnc_import_bgp_exterior_del_route(
vnc_import_bgp_exterior_del_route(struct bgp *bgp, struct bgp *bgp, struct prefix *prefix, /* unicast prefix */
struct prefix *prefix, /* unicast prefix */ struct bgp_path_info *info); /* unicast info */
struct bgp_info *info); /* unicast info */
extern void vnc_import_bgp_add_vnc_host_route_mode_resolve_nve( extern void vnc_import_bgp_add_vnc_host_route_mode_resolve_nve(
struct bgp *bgp, struct prefix_rd *prd, /* RD */ struct bgp *bgp, struct prefix_rd *prd, /* RD */
struct bgp_table *table_rd, /* per-rd VPN route table */ struct bgp_table *table_rd, /* per-rd VPN route table */
struct prefix *prefix, /* VPN prefix */ struct prefix *prefix, /* VPN prefix */
struct bgp_info *bi); /* new VPN host route */ struct bgp_path_info *bpi); /* new VPN host route */
extern void vnc_import_bgp_del_vnc_host_route_mode_resolve_nve( extern void vnc_import_bgp_del_vnc_host_route_mode_resolve_nve(
struct bgp *bgp, struct prefix_rd *prd, /* RD */ struct bgp *bgp, struct prefix_rd *prd, /* RD */
struct bgp_table *table_rd, /* per-rd VPN route table */ struct bgp_table *table_rd, /* per-rd VPN route table */
struct prefix *prefix, /* VPN prefix */ struct prefix *prefix, /* VPN prefix */
struct bgp_info *bi); /* old VPN host route */ struct bgp_path_info *bpi); /* old VPN host route */
#endif /* _QUAGGA_RFAPI_VNC_IMPORT_BGP_H_ */ #endif /* _QUAGGA_RFAPI_VNC_IMPORT_BGP_H_ */

View File

@ -30,12 +30,12 @@
extern void vnc_import_bgp_exterior_add_route_interior( extern void vnc_import_bgp_exterior_add_route_interior(
struct bgp *bgp, struct rfapi_import_table *it, struct bgp *bgp, struct rfapi_import_table *it,
struct agg_node *rn_interior, /* VPN IT node */ struct agg_node *rn_interior, /* VPN IT node */
struct bgp_info *bi_interior); /* VPN IT route */ struct bgp_path_info *bpi_interior); /* VPN IT route */
extern void vnc_import_bgp_exterior_del_route_interior( extern void vnc_import_bgp_exterior_del_route_interior(
struct bgp *bgp, struct rfapi_import_table *it, struct bgp *bgp, struct rfapi_import_table *it,
struct agg_node *rn_interior, /* VPN IT node */ struct agg_node *rn_interior, /* VPN IT node */
struct bgp_info *bi_interior); /* VPN IT route */ struct bgp_path_info *bpi_interior); /* VPN IT route */
extern void extern void
vnc_import_bgp_exterior_redist_enable_it(struct bgp *bgp, afi_t afi, vnc_import_bgp_exterior_redist_enable_it(struct bgp *bgp, afi_t afi,

View File

@ -316,7 +316,7 @@ static void vnc_redistribute_withdraw(struct bgp *bgp, afi_t afi, uint8_t type)
for (rn = bgp_table_top(table); rn; rn = bgp_route_next(rn)) { for (rn = bgp_table_top(table); rn; rn = bgp_route_next(rn)) {
struct bgp_info *ri; struct bgp_path_info *ri;
for (ri = rn->info; ri; ri = ri->next) { for (ri = rn->info; ri; ri = ri->next) {
if (ri->type if (ri->type

View File

@ -241,7 +241,7 @@ Legend:
/\ struct bgp_node: a BGP destination/route/prefix /\ struct bgp_node: a BGP destination/route/prefix
\/ \/
[ ] struct bgp_info: a BGP path (e.g. route received from a peer) [ ] struct bgp_path_info: a BGP path (e.g. route received from a peer)
_ _
(_) struct bgp_nexthop_cache: a BGP nexthop (_) struct bgp_nexthop_cache: a BGP nexthop

View File

@ -16,7 +16,7 @@
# ... # ...
# (gdb) cont # (gdb) cont
# Breakpoint 3, bgp_write_packet (peer=0x7fa885199080) at bgp_packet.c:614 # Breakpoint 3, bgp_write_packet (peer=0x7fa885199080) at bgp_packet.c:614
# 614 if (CHECK_FLAG (adv->binfo->peer->cap,PEER_CAP_RESTART_RCV) # 614 if (CHECK_FLAG (adv->path->peer->cap,PEER_CAP_RESTART_RCV)
# (gdb) dump_prefix4 &adv->rn->p # (gdb) dump_prefix4 &adv->rn->p
# IPv4:10.1.1.0/24 # IPv4:10.1.1.0/24
# (gdb) dump_prefix &adv->rn->p # (gdb) dump_prefix &adv->rn->p

View File

@ -207,7 +207,7 @@ struct peer test_mp_list_peer[] = {
}; };
int test_mp_list_peer_count = sizeof(test_mp_list_peer) / sizeof(struct peer); int test_mp_list_peer_count = sizeof(test_mp_list_peer) / sizeof(struct peer);
struct attr test_mp_list_attr[4]; struct attr test_mp_list_attr[4];
struct bgp_info test_mp_list_info[] = { struct bgp_path_info test_mp_list_info[] = {
{.peer = &test_mp_list_peer[0], .attr = &test_mp_list_attr[0]}, {.peer = &test_mp_list_peer[0], .attr = &test_mp_list_attr[0]},
{.peer = &test_mp_list_peer[1], .attr = &test_mp_list_attr[1]}, {.peer = &test_mp_list_peer[1], .attr = &test_mp_list_attr[1]},
{.peer = &test_mp_list_peer[2], .attr = &test_mp_list_attr[1]}, {.peer = &test_mp_list_peer[2], .attr = &test_mp_list_attr[1]},
@ -215,7 +215,7 @@ struct bgp_info test_mp_list_info[] = {
{.peer = &test_mp_list_peer[4], .attr = &test_mp_list_attr[3]}, {.peer = &test_mp_list_peer[4], .attr = &test_mp_list_attr[3]},
}; };
int test_mp_list_info_count = int test_mp_list_info_count =
sizeof(test_mp_list_info) / sizeof(struct bgp_info); sizeof(test_mp_list_info) / sizeof(struct bgp_path_info);
static int setup_bgp_mp_list(testcase_t *t) static int setup_bgp_mp_list(testcase_t *t)
{ {
@ -247,7 +247,7 @@ static int run_bgp_mp_list(testcase_t *t)
{ {
struct list mp_list; struct list mp_list;
struct listnode *mp_node; struct listnode *mp_node;
struct bgp_info *info; struct bgp_path_info *info;
int i; int i;
int test_result = TEST_PASSED; int test_result = TEST_PASSED;
bgp_mp_list_init(&mp_list); bgp_mp_list_init(&mp_list);
@ -289,24 +289,24 @@ testcase_t test_bgp_mp_list = {
}; };
/*========================================================= /*=========================================================
* Testcase for bgp_info_mpath_update * Testcase for bgp_path_info_mpath_update
*/ */
struct bgp_node test_rn; struct bgp_node test_rn;
static int setup_bgp_info_mpath_update(testcase_t *t) static int setup_bgp_path_info_mpath_update(testcase_t *t)
{ {
int i; int i;
str2prefix("42.1.1.0/24", &test_rn.p); str2prefix("42.1.1.0/24", &test_rn.p);
setup_bgp_mp_list(t); setup_bgp_mp_list(t);
for (i = 0; i < test_mp_list_info_count; i++) for (i = 0; i < test_mp_list_info_count; i++)
bgp_info_add(&test_rn, &test_mp_list_info[i]); bgp_path_info_add(&test_rn, &test_mp_list_info[i]);
return 0; return 0;
} }
static int run_bgp_info_mpath_update(testcase_t *t) static int run_bgp_path_info_mpath_update(testcase_t *t)
{ {
struct bgp_info *new_best, *old_best, *mpath; struct bgp_path_info *new_best, *old_best, *mpath;
struct list mp_list; struct list mp_list;
struct bgp_maxpaths_cfg mp_cfg = {3, 3}; struct bgp_maxpaths_cfg mp_cfg = {3, 3};
int test_result = TEST_PASSED; int test_result = TEST_PASSED;
@ -317,33 +317,35 @@ static int run_bgp_info_mpath_update(testcase_t *t)
bgp_mp_list_add(&mp_list, &test_mp_list_info[1]); bgp_mp_list_add(&mp_list, &test_mp_list_info[1]);
new_best = &test_mp_list_info[3]; new_best = &test_mp_list_info[3];
old_best = NULL; old_best = NULL;
bgp_info_mpath_update(&test_rn, new_best, old_best, &mp_list, &mp_cfg); bgp_path_info_mpath_update(&test_rn, new_best, old_best, &mp_list,
&mp_cfg);
bgp_mp_list_clear(&mp_list); bgp_mp_list_clear(&mp_list);
EXPECT_TRUE(bgp_info_mpath_count(new_best) == 2, test_result); EXPECT_TRUE(bgp_path_info_mpath_count(new_best) == 2, test_result);
mpath = bgp_info_mpath_first(new_best); mpath = bgp_path_info_mpath_first(new_best);
EXPECT_TRUE(mpath == &test_mp_list_info[0], test_result); EXPECT_TRUE(mpath == &test_mp_list_info[0], test_result);
EXPECT_TRUE(CHECK_FLAG(mpath->flags, BGP_INFO_MULTIPATH), test_result); EXPECT_TRUE(CHECK_FLAG(mpath->flags, BGP_PATH_MULTIPATH), test_result);
mpath = bgp_info_mpath_next(mpath); mpath = bgp_path_info_mpath_next(mpath);
EXPECT_TRUE(mpath == &test_mp_list_info[1], test_result); EXPECT_TRUE(mpath == &test_mp_list_info[1], test_result);
EXPECT_TRUE(CHECK_FLAG(mpath->flags, BGP_INFO_MULTIPATH), test_result); EXPECT_TRUE(CHECK_FLAG(mpath->flags, BGP_PATH_MULTIPATH), test_result);
bgp_mp_list_add(&mp_list, &test_mp_list_info[0]); bgp_mp_list_add(&mp_list, &test_mp_list_info[0]);
bgp_mp_list_add(&mp_list, &test_mp_list_info[1]); bgp_mp_list_add(&mp_list, &test_mp_list_info[1]);
new_best = &test_mp_list_info[0]; new_best = &test_mp_list_info[0];
old_best = &test_mp_list_info[3]; old_best = &test_mp_list_info[3];
bgp_info_mpath_update(&test_rn, new_best, old_best, &mp_list, &mp_cfg); bgp_path_info_mpath_update(&test_rn, new_best, old_best, &mp_list,
&mp_cfg);
bgp_mp_list_clear(&mp_list); bgp_mp_list_clear(&mp_list);
EXPECT_TRUE(bgp_info_mpath_count(new_best) == 1, test_result); EXPECT_TRUE(bgp_path_info_mpath_count(new_best) == 1, test_result);
mpath = bgp_info_mpath_first(new_best); mpath = bgp_path_info_mpath_first(new_best);
EXPECT_TRUE(mpath == &test_mp_list_info[1], test_result); EXPECT_TRUE(mpath == &test_mp_list_info[1], test_result);
EXPECT_TRUE(CHECK_FLAG(mpath->flags, BGP_INFO_MULTIPATH), test_result); EXPECT_TRUE(CHECK_FLAG(mpath->flags, BGP_PATH_MULTIPATH), test_result);
EXPECT_TRUE(!CHECK_FLAG(test_mp_list_info[0].flags, BGP_INFO_MULTIPATH), EXPECT_TRUE(!CHECK_FLAG(test_mp_list_info[0].flags, BGP_PATH_MULTIPATH),
test_result); test_result);
return test_result; return test_result;
} }
static int cleanup_bgp_info_mpath_update(testcase_t *t) static int cleanup_bgp_path_info_mpath_update(testcase_t *t)
{ {
int i; int i;
@ -353,11 +355,11 @@ static int cleanup_bgp_info_mpath_update(testcase_t *t)
return 0; return 0;
} }
testcase_t test_bgp_info_mpath_update = { testcase_t test_bgp_path_info_mpath_update = {
.desc = "Test bgp_info_mpath_update", .desc = "Test bgp_path_info_mpath_update",
.setup = setup_bgp_info_mpath_update, .setup = setup_bgp_path_info_mpath_update,
.run = run_bgp_info_mpath_update, .run = run_bgp_path_info_mpath_update,
.cleanup = cleanup_bgp_info_mpath_update, .cleanup = cleanup_bgp_path_info_mpath_update,
}; };
/*========================================================= /*=========================================================
@ -365,7 +367,7 @@ testcase_t test_bgp_info_mpath_update = {
*/ */
testcase_t *all_tests[] = { testcase_t *all_tests[] = {
&test_bgp_cfg_maximum_paths, &test_bgp_mp_list, &test_bgp_cfg_maximum_paths, &test_bgp_mp_list,
&test_bgp_info_mpath_update, &test_bgp_path_info_mpath_update,
}; };
int all_tests_count = (sizeof(all_tests) / sizeof(testcase_t *)); int all_tests_count = (sizeof(all_tests) / sizeof(testcase_t *));

View File

@ -5,5 +5,5 @@ class TestMpath(frrtest.TestMultiOut):
TestMpath.okfail("bgp maximum-paths config") TestMpath.okfail("bgp maximum-paths config")
TestMpath.okfail("bgp_mp_list") TestMpath.okfail("bgp_mp_list")
TestMpath.okfail("bgp_info_mpath_update") TestMpath.okfail("bgp_path_info_mpath_update")