mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-07-26 03:07:51 +00:00
staticd: Fix mixup in vrf translations
When we store the nexthop for ref-counting, keep track of the nexthop vrf_id as well. This will allow us to track the nexthop per vrf! Additionally when we get the callback from zebra about a nexthop update, iterate over all static routes to see if the nexthop we are getting a callback is one we are concerned about. Signed-off-by: Donald Sharp <sharpd@cumulusnetworks.com>
This commit is contained in:
parent
533ab00846
commit
31e2232baa
@ -29,8 +29,8 @@
|
|||||||
#include "static_zebra.h"
|
#include "static_zebra.h"
|
||||||
#include "static_nht.h"
|
#include "static_nht.h"
|
||||||
|
|
||||||
void static_nht_update(struct prefix *p, uint32_t nh_num,
|
void static_nht_update(struct prefix *p, uint32_t nh_num, afi_t afi,
|
||||||
afi_t afi, vrf_id_t vrf_id)
|
vrf_id_t nh_vrf_id)
|
||||||
{
|
{
|
||||||
struct route_table *stable;
|
struct route_table *stable;
|
||||||
struct static_route *si;
|
struct static_route *si;
|
||||||
@ -40,41 +40,47 @@ void static_nht_update(struct prefix *p, uint32_t nh_num,
|
|||||||
bool orig;
|
bool orig;
|
||||||
bool reinstall;
|
bool reinstall;
|
||||||
|
|
||||||
vrf = vrf_lookup_by_id(vrf_id);
|
RB_FOREACH (vrf, vrf_name_head, &vrfs_by_name) {
|
||||||
|
svrf = vrf->info;
|
||||||
|
if (!svrf)
|
||||||
|
continue;
|
||||||
|
|
||||||
if (!vrf || !vrf->info)
|
stable = static_vrf_static_table(afi, SAFI_UNICAST, svrf);
|
||||||
return;
|
if (!stable)
|
||||||
|
continue;
|
||||||
|
|
||||||
svrf = vrf->info;
|
for (rn = route_top(stable); rn; rn = route_next(rn)) {
|
||||||
stable = static_vrf_static_table(afi, SAFI_UNICAST, svrf);
|
reinstall = false;
|
||||||
if (!stable)
|
for (si = rn->info; si; si = si->next) {
|
||||||
return;
|
if (si->nh_vrf_id != nh_vrf_id)
|
||||||
|
continue;
|
||||||
|
|
||||||
for (rn = route_top(stable); rn; rn = route_next(rn)) {
|
if (si->type != STATIC_IPV4_GATEWAY
|
||||||
reinstall = false;
|
&& si->type != STATIC_IPV4_GATEWAY_IFNAME
|
||||||
for (si = rn->info; si; si = si->next) {
|
&& si->type != STATIC_IPV6_GATEWAY
|
||||||
if (si->type != STATIC_IPV4_GATEWAY &&
|
&& si->type != STATIC_IPV6_GATEWAY_IFNAME)
|
||||||
si->type != STATIC_IPV4_GATEWAY_IFNAME &&
|
continue;
|
||||||
si->type != STATIC_IPV6_GATEWAY &&
|
|
||||||
si->type != STATIC_IPV6_GATEWAY_IFNAME)
|
|
||||||
continue;
|
|
||||||
|
|
||||||
orig = si->nh_valid;
|
orig = si->nh_valid;
|
||||||
if (p->family == AF_INET &&
|
if (p->family == AF_INET
|
||||||
p->u.prefix4.s_addr == si->addr.ipv4.s_addr)
|
&& p->u.prefix4.s_addr
|
||||||
si->nh_valid = !!nh_num;
|
== si->addr.ipv4.s_addr)
|
||||||
|
si->nh_valid = !!nh_num;
|
||||||
|
|
||||||
if (p->family == AF_INET6 &&
|
if (p->family == AF_INET6
|
||||||
memcmp(&p->u.prefix6, &si->addr.ipv6, 16) == 0)
|
&& memcmp(&p->u.prefix6, &si->addr.ipv6, 16)
|
||||||
si->nh_valid = !!nh_num;
|
== 0)
|
||||||
|
si->nh_valid = !!nh_num;
|
||||||
|
|
||||||
if (orig != si->nh_valid)
|
if (orig != si->nh_valid)
|
||||||
reinstall = true;
|
reinstall = true;
|
||||||
|
|
||||||
if (reinstall) {
|
if (reinstall) {
|
||||||
static_zebra_route_add(rn, si, vrf_id,
|
static_zebra_route_add(
|
||||||
SAFI_UNICAST, true);
|
rn, si, vrf->vrf_id,
|
||||||
reinstall = false;
|
SAFI_UNICAST, true);
|
||||||
|
reinstall = false;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -35,6 +35,7 @@
|
|||||||
#include "nexthop.h"
|
#include "nexthop.h"
|
||||||
#include "nexthop_group.h"
|
#include "nexthop_group.h"
|
||||||
#include "hash.h"
|
#include "hash.h"
|
||||||
|
#include "jhash.h"
|
||||||
|
|
||||||
#include "static_vrf.h"
|
#include "static_vrf.h"
|
||||||
#include "static_routes.h"
|
#include "static_routes.h"
|
||||||
@ -180,6 +181,9 @@ static void zebra_connected(struct zclient *zclient)
|
|||||||
|
|
||||||
struct static_nht_data {
|
struct static_nht_data {
|
||||||
struct prefix *nh;
|
struct prefix *nh;
|
||||||
|
|
||||||
|
vrf_id_t nh_vrf_id;
|
||||||
|
|
||||||
uint32_t refcount;
|
uint32_t refcount;
|
||||||
uint8_t nh_num;
|
uint8_t nh_num;
|
||||||
};
|
};
|
||||||
@ -201,13 +205,18 @@ static int static_zebra_nexthop_update(int command, struct zclient *zclient,
|
|||||||
|
|
||||||
memset(&lookup, 0, sizeof(lookup));
|
memset(&lookup, 0, sizeof(lookup));
|
||||||
lookup.nh = &nhr.prefix;
|
lookup.nh = &nhr.prefix;
|
||||||
|
lookup.nh_vrf_id = vrf_id;
|
||||||
|
|
||||||
nhtd = hash_lookup(static_nht_hash, &lookup);
|
nhtd = hash_lookup(static_nht_hash, &lookup);
|
||||||
if (nhtd)
|
|
||||||
|
if (nhtd) {
|
||||||
nhtd->nh_num = nhr.nexthop_num;
|
nhtd->nh_num = nhr.nexthop_num;
|
||||||
|
|
||||||
|
static_nht_update(&nhr.prefix, nhr.nexthop_num, afi,
|
||||||
|
nhtd->nh_vrf_id);
|
||||||
|
} else
|
||||||
|
zlog_err("No nhtd?");
|
||||||
|
|
||||||
static_nht_update(&nhr.prefix, nhr.nexthop_num, afi, vrf_id);
|
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -219,8 +228,10 @@ static void static_zebra_capabilities(struct zclient_capabilities *cap)
|
|||||||
static unsigned int static_nht_hash_key(void *data)
|
static unsigned int static_nht_hash_key(void *data)
|
||||||
{
|
{
|
||||||
struct static_nht_data *nhtd = data;
|
struct static_nht_data *nhtd = data;
|
||||||
|
unsigned int key = 0;
|
||||||
|
|
||||||
return prefix_hash_key(nhtd->nh);
|
key = prefix_hash_key(nhtd->nh);
|
||||||
|
return jhash_1word(nhtd->nh_vrf_id, key);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int static_nht_hash_cmp(const void *d1, const void *d2)
|
static int static_nht_hash_cmp(const void *d1, const void *d2)
|
||||||
@ -228,6 +239,9 @@ static int static_nht_hash_cmp(const void *d1, const void *d2)
|
|||||||
const struct static_nht_data *nhtd1 = d1;
|
const struct static_nht_data *nhtd1 = d1;
|
||||||
const struct static_nht_data *nhtd2 = d2;
|
const struct static_nht_data *nhtd2 = d2;
|
||||||
|
|
||||||
|
if (nhtd1->nh_vrf_id != nhtd2->nh_vrf_id)
|
||||||
|
return 0;
|
||||||
|
|
||||||
return prefix_same(nhtd1->nh, nhtd2->nh);
|
return prefix_same(nhtd1->nh, nhtd2->nh);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -242,6 +256,7 @@ static void *static_nht_hash_alloc(void *data)
|
|||||||
prefix_copy(new->nh, copy->nh);
|
prefix_copy(new->nh, copy->nh);
|
||||||
new->refcount = 0;
|
new->refcount = 0;
|
||||||
new->nh_num = 0;
|
new->nh_num = 0;
|
||||||
|
new->nh_vrf_id = copy->nh_vrf_id;
|
||||||
|
|
||||||
return new;
|
return new;
|
||||||
}
|
}
|
||||||
@ -293,6 +308,7 @@ void static_zebra_nht_register(struct static_route *si, bool reg)
|
|||||||
|
|
||||||
memset(&lookup, 0, sizeof(lookup));
|
memset(&lookup, 0, sizeof(lookup));
|
||||||
lookup.nh = &p;
|
lookup.nh = &p;
|
||||||
|
lookup.nh_vrf_id = si->nh_vrf_id;
|
||||||
|
|
||||||
si->nh_registered = reg;
|
si->nh_registered = reg;
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user