diff options
| -rw-r--r-- | lib/nexthop.c | 9 | ||||
| -rw-r--r-- | lib/nexthop.h | 2 | ||||
| -rw-r--r-- | zebra/zebra_mpls.c | 27 | 
3 files changed, 32 insertions, 6 deletions
diff --git a/lib/nexthop.c b/lib/nexthop.c index 26c338256f..d6c654a692 100644 --- a/lib/nexthop.c +++ b/lib/nexthop.c @@ -699,6 +699,15 @@ struct nexthop *nexthop_next(const struct nexthop *nexthop)  	return NULL;  } +struct nexthop *nexthop_next_resolution(const struct nexthop *nexthop, +					bool nexthop_resolution) +{ +	if (nexthop_resolution) +		return nexthop_next(nexthop); +	/* no resolution attempt */ +	return nexthop->next; +} +  /* Return the next nexthop in the tree that is resolved and active */  struct nexthop *nexthop_next_active_resolved(const struct nexthop *nexthop)  { diff --git a/lib/nexthop.h b/lib/nexthop.h index 27073b948d..457c81972e 100644 --- a/lib/nexthop.h +++ b/lib/nexthop.h @@ -223,6 +223,8 @@ extern bool nexthop_labels_match(const struct nexthop *nh1,  extern const char *nexthop2str(const struct nexthop *nexthop,  			       char *str, int size);  extern struct nexthop *nexthop_next(const struct nexthop *nexthop); +extern struct nexthop *nexthop_next_resolution(const struct nexthop *nexthop, +					       bool nexthop_resolution);  extern struct nexthop *  nexthop_next_active_resolved(const struct nexthop *nexthop);  extern unsigned int nexthop_level(const struct nexthop *nexthop); diff --git a/zebra/zebra_mpls.c b/zebra/zebra_mpls.c index ca93ce8fbd..17fe455741 100644 --- a/zebra/zebra_mpls.c +++ b/zebra/zebra_mpls.c @@ -161,12 +161,14 @@ static int lsp_install(struct zebra_vrf *zvrf, mpls_label_t label,  	enum lsp_types_t lsp_type;  	char buf[BUFSIZ];  	int added, changed; +	bool zvrf_nexthop_resolution;  	/* Lookup table. */  	lsp_table = zvrf->lsp_table;  	if (!lsp_table)  		return -1; +	zvrf_nexthop_resolution = zvrf->zebra_mpls_fec_nexthop_resolution;  	lsp_type = lsp_type_from_re_type(re->type);  	added = changed = 0; @@ -180,13 +182,20 @@ static int lsp_install(struct zebra_vrf *zvrf, mpls_label_t label,  	 * the label advertised by the recursive nexthop (plus we don't have the  	 * logic yet to push multiple labels).  	 */ -	for (nexthop = re->nhe->nhg.nexthop; -	     nexthop; nexthop = nexthop->next) { -		/* Skip inactive and recursive entries. */ -		if (!CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_ACTIVE)) +	nexthop = re->nhe->nhg.nexthop; +	while (nexthop) { +		if (!CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_ACTIVE)) { +			nexthop = +				nexthop_next_resolution(nexthop, +							zvrf_nexthop_resolution);  			continue; -		if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_RECURSIVE)) +		} +		if (CHECK_FLAG(nexthop->flags, NEXTHOP_FLAG_RECURSIVE)) { +			nexthop = +				nexthop_next_resolution(nexthop, +							zvrf_nexthop_resolution);  			continue; +		}  		nhlfe = nhlfe_find(&lsp->nhlfe_list, lsp_type,  				   nexthop->type, &nexthop->gate, @@ -194,9 +203,13 @@ static int lsp_install(struct zebra_vrf *zvrf, mpls_label_t label,  		if (nhlfe) {  			/* Clear deleted flag (in case it was set) */  			UNSET_FLAG(nhlfe->flags, NHLFE_FLAG_DELETED); -			if (nexthop_labels_match(nhlfe->nexthop, nexthop)) +			if (nexthop_labels_match(nhlfe->nexthop, nexthop)) {  				/* No change */ +				nexthop = +					nexthop_next_resolution(nexthop, +								zvrf_nexthop_resolution);  				continue; +			}  			if (IS_ZEBRA_DEBUG_MPLS) { @@ -234,6 +247,8 @@ static int lsp_install(struct zebra_vrf *zvrf, mpls_label_t label,  			SET_FLAG(nhlfe->flags, NHLFE_FLAG_CHANGED);  			added++;  		} +		nexthop = nexthop_next_resolution(nexthop, +						  zvrf_nexthop_resolution);  	}  	/* Queue LSP for processing if necessary. If no NHLFE got added (special  | 
