diff options
author | Mark Stapp <mjs@voltanet.io> | 2021-04-01 17:56:30 +0200 |
---|---|---|
committer | Mark Stapp <mjs@voltanet.io> | 2021-04-21 20:30:15 +0200 |
commit | a082cd9a5107cef5e51783228c7259b472d35424 (patch) | |
tree | aed4663457cea3c15f365446d45727811adb6b14 /zebra | |
parent | zebra: fix some issues in recursive backup nexthop code (diff) | |
download | frr-a082cd9a5107cef5e51783228c7259b472d35424.tar.xz frr-a082cd9a5107cef5e51783228c7259b472d35424.zip |
zebra: include inner labels with recursive backups
When capturing backup nexthops with recursive resolution,
ensure that inner labels from the recursive nexthop are
included in each backup (as they are with the resolving
primary nexthops).
Signed-off-by: Mark Stapp <mjs@voltanet.io>
Diffstat (limited to 'zebra')
-rw-r--r-- | zebra/zebra_nhg.c | 36 |
1 files changed, 36 insertions, 0 deletions
diff --git a/zebra/zebra_nhg.c b/zebra/zebra_nhg.c index 4763d7741..1354f6813 100644 --- a/zebra/zebra_nhg.c +++ b/zebra/zebra_nhg.c @@ -1811,6 +1811,8 @@ static int resolve_backup_nexthops(const struct nexthop *nexthop, int i, j, idx; const struct nexthop *bnh; struct nexthop *nh, *newnh; + mpls_label_t labels[MPLS_MAX_LABELS]; + uint8_t num_labels; assert(nexthop->backup_num <= NEXTHOP_MAX_BACKUPS); @@ -1861,6 +1863,40 @@ static int resolve_backup_nexthops(const struct nexthop *nexthop, /* Update backup info in the resolving nexthop and its nhe */ newnh = nexthop_dup_no_recurse(bnh, NULL); + /* We may need some special handling for mpls labels: the new + * backup needs to carry the recursive nexthop's labels, + * if any: they may be vrf labels e.g. + * The original/inner labels are in the stack of 'resolve_nhe', + * if that is longer than the stack in 'nexthop'. + */ + if (newnh->nh_label && resolved->nh_label && + nexthop->nh_label) { + if (resolved->nh_label->num_labels > + nexthop->nh_label->num_labels) { + /* Prepare new label stack */ + num_labels = 0; + for (j = 0; j < newnh->nh_label->num_labels; + j++) { + labels[j] = newnh->nh_label->label[j]; + num_labels++; + } + + /* Include inner labels */ + for (j = nexthop->nh_label->num_labels; + j < resolved->nh_label->num_labels; + j++) { + labels[num_labels] = + resolved->nh_label->label[j]; + num_labels++; + } + + /* Replace existing label stack in the backup */ + nexthop_del_labels(newnh); + nexthop_add_labels(newnh, bnh->nh_label_type, + num_labels, labels); + } + } + /* Need to compute the new backup index in the new * backup list, and add to map struct. */ |