mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-07-23 22:46:30 +00:00
Merge pull request #3893 from mjstapp/dplane_pw_nexthops
zebra: include nexthop info when installing pseudowires
This commit is contained in:
commit
6ac9718a2a
@ -927,7 +927,7 @@ static void _netlink_route_nl_add_gateway_info(uint8_t route_family,
|
||||
uint8_t gw_family,
|
||||
struct nlmsghdr *nlmsg,
|
||||
size_t req_size, int bytelen,
|
||||
struct nexthop *nexthop)
|
||||
const struct nexthop *nexthop)
|
||||
{
|
||||
if (route_family == AF_MPLS) {
|
||||
struct gw_family_t gw_fam;
|
||||
@ -954,7 +954,7 @@ static void _netlink_route_rta_add_gateway_info(uint8_t route_family,
|
||||
struct rtattr *rta,
|
||||
struct rtnexthop *rtnh,
|
||||
size_t req_size, int bytelen,
|
||||
struct nexthop *nexthop)
|
||||
const struct nexthop *nexthop)
|
||||
{
|
||||
if (route_family == AF_MPLS) {
|
||||
struct gw_family_t gw_fam;
|
||||
@ -990,7 +990,7 @@ static void _netlink_route_rta_add_gateway_info(uint8_t route_family,
|
||||
* @param req_size: The size allocated for the message.
|
||||
*/
|
||||
static void _netlink_route_build_singlepath(const char *routedesc, int bytelen,
|
||||
struct nexthop *nexthop,
|
||||
const struct nexthop *nexthop,
|
||||
struct nlmsghdr *nlmsg,
|
||||
struct rtmsg *rtmsg,
|
||||
size_t req_size, int cmd)
|
||||
@ -1009,7 +1009,7 @@ static void _netlink_route_build_singlepath(const char *routedesc, int bytelen,
|
||||
label_buf[0] = '\0';
|
||||
|
||||
assert(nexthop);
|
||||
for (struct nexthop *nh = nexthop; nh; nh = nh->rparent) {
|
||||
for (const struct nexthop *nh = nexthop; nh; nh = nh->rparent) {
|
||||
char label_buf1[20];
|
||||
|
||||
nh_label = nh->nh_label;
|
||||
@ -1175,11 +1175,11 @@ static void _netlink_route_build_singlepath(const char *routedesc, int bytelen,
|
||||
* the prefsrc should be stored.
|
||||
*/
|
||||
static void _netlink_route_build_multipath(const char *routedesc, int bytelen,
|
||||
struct nexthop *nexthop,
|
||||
const struct nexthop *nexthop,
|
||||
struct rtattr *rta,
|
||||
struct rtnexthop *rtnh,
|
||||
struct rtmsg *rtmsg,
|
||||
union g_addr **src)
|
||||
const union g_addr **src)
|
||||
{
|
||||
struct mpls_label_stack *nh_label;
|
||||
mpls_lse_t out_lse[MPLS_MAX_LABELS];
|
||||
@ -1200,7 +1200,7 @@ static void _netlink_route_build_multipath(const char *routedesc, int bytelen,
|
||||
label_buf[0] = '\0';
|
||||
|
||||
assert(nexthop);
|
||||
for (struct nexthop *nh = nexthop; nh; nh = nh->rparent) {
|
||||
for (const struct nexthop *nh = nexthop; nh; nh = nh->rparent) {
|
||||
char label_buf1[20];
|
||||
|
||||
nh_label = nh->nh_label;
|
||||
@ -1342,7 +1342,7 @@ static void _netlink_route_build_multipath(const char *routedesc, int bytelen,
|
||||
}
|
||||
|
||||
static inline void _netlink_mpls_build_singlepath(const char *routedesc,
|
||||
zebra_nhlfe_t *nhlfe,
|
||||
const zebra_nhlfe_t *nhlfe,
|
||||
struct nlmsghdr *nlmsg,
|
||||
struct rtmsg *rtmsg,
|
||||
size_t req_size, int cmd)
|
||||
@ -1358,9 +1358,9 @@ static inline void _netlink_mpls_build_singlepath(const char *routedesc,
|
||||
|
||||
|
||||
static inline void
|
||||
_netlink_mpls_build_multipath(const char *routedesc, zebra_nhlfe_t *nhlfe,
|
||||
_netlink_mpls_build_multipath(const char *routedesc, const zebra_nhlfe_t *nhlfe,
|
||||
struct rtattr *rta, struct rtnexthop *rtnh,
|
||||
struct rtmsg *rtmsg, union g_addr **src)
|
||||
struct rtmsg *rtmsg, const union g_addr **src)
|
||||
{
|
||||
int bytelen;
|
||||
uint8_t family;
|
||||
@ -1655,7 +1655,7 @@ static int netlink_route_multipath(int cmd, struct zebra_dplane_ctx *ctx)
|
||||
char buf[NL_PKT_BUF_SIZE];
|
||||
struct rtattr *rta = (void *)buf;
|
||||
struct rtnexthop *rtnh;
|
||||
union g_addr *src1 = NULL;
|
||||
const union g_addr *src1 = NULL;
|
||||
|
||||
rta->rta_type = RTA_MULTIPATH;
|
||||
rta->rta_len = RTA_LENGTH(0);
|
||||
@ -2776,7 +2776,7 @@ int kernel_upd_neigh(struct interface *ifp, struct ipaddr *ip,
|
||||
int netlink_mpls_multipath(int cmd, struct zebra_dplane_ctx *ctx)
|
||||
{
|
||||
mpls_lse_t lse;
|
||||
zebra_nhlfe_t *nhlfe;
|
||||
const zebra_nhlfe_t *nhlfe;
|
||||
struct nexthop *nexthop = NULL;
|
||||
unsigned int nexthop_num;
|
||||
const char *routedesc;
|
||||
@ -2879,7 +2879,7 @@ int netlink_mpls_multipath(int cmd, struct zebra_dplane_ctx *ctx)
|
||||
char buf[NL_PKT_BUF_SIZE];
|
||||
struct rtattr *rta = (void *)buf;
|
||||
struct rtnexthop *rtnh;
|
||||
union g_addr *src1 = NULL;
|
||||
const union g_addr *src1 = NULL;
|
||||
|
||||
rta->rta_type = RTA_MULTIPATH;
|
||||
rta->rta_len = RTA_LENGTH(0);
|
||||
|
@ -111,10 +111,13 @@ struct dplane_pw_info {
|
||||
int af;
|
||||
int status;
|
||||
uint32_t flags;
|
||||
union g_addr nexthop;
|
||||
union g_addr dest;
|
||||
mpls_label_t local_label;
|
||||
mpls_label_t remote_label;
|
||||
|
||||
/* Nexthops */
|
||||
struct nexthop_group nhg;
|
||||
|
||||
union pw_protocol_fields fields;
|
||||
};
|
||||
|
||||
@ -386,6 +389,15 @@ static void dplane_ctx_free(struct zebra_dplane_ctx **pctx)
|
||||
|
||||
case DPLANE_OP_PW_INSTALL:
|
||||
case DPLANE_OP_PW_UNINSTALL:
|
||||
/* Free allocated nexthops */
|
||||
if ((*pctx)->u.pw.nhg.nexthop) {
|
||||
/* This deals with recursive nexthops too */
|
||||
nexthops_free((*pctx)->u.pw.nhg.nexthop);
|
||||
|
||||
(*pctx)->u.pw.nhg.nexthop = NULL;
|
||||
}
|
||||
break;
|
||||
|
||||
case DPLANE_OP_NONE:
|
||||
break;
|
||||
}
|
||||
@ -744,14 +756,15 @@ uint32_t dplane_ctx_get_lsp_flags(const struct zebra_dplane_ctx *ctx)
|
||||
return ctx->u.lsp.flags;
|
||||
}
|
||||
|
||||
zebra_nhlfe_t *dplane_ctx_get_nhlfe(struct zebra_dplane_ctx *ctx)
|
||||
const zebra_nhlfe_t *dplane_ctx_get_nhlfe(const struct zebra_dplane_ctx *ctx)
|
||||
{
|
||||
DPLANE_CTX_VALID(ctx);
|
||||
|
||||
return ctx->u.lsp.nhlfe_list;
|
||||
}
|
||||
|
||||
zebra_nhlfe_t *dplane_ctx_get_best_nhlfe(struct zebra_dplane_ctx *ctx)
|
||||
const zebra_nhlfe_t *
|
||||
dplane_ctx_get_best_nhlfe(const struct zebra_dplane_ctx *ctx)
|
||||
{
|
||||
DPLANE_CTX_VALID(ctx);
|
||||
|
||||
@ -814,12 +827,12 @@ int dplane_ctx_get_pw_status(const struct zebra_dplane_ctx *ctx)
|
||||
return ctx->u.pw.status;
|
||||
}
|
||||
|
||||
const union g_addr *dplane_ctx_get_pw_nexthop(
|
||||
const union g_addr *dplane_ctx_get_pw_dest(
|
||||
const struct zebra_dplane_ctx *ctx)
|
||||
{
|
||||
DPLANE_CTX_VALID(ctx);
|
||||
|
||||
return &(ctx->u.pw.nexthop);
|
||||
return &(ctx->u.pw.dest);
|
||||
}
|
||||
|
||||
const union pw_protocol_fields *dplane_ctx_get_pw_proto(
|
||||
@ -830,6 +843,14 @@ const union pw_protocol_fields *dplane_ctx_get_pw_proto(
|
||||
return &(ctx->u.pw.fields);
|
||||
}
|
||||
|
||||
const struct nexthop_group *
|
||||
dplane_ctx_get_pw_nhg(const struct zebra_dplane_ctx *ctx)
|
||||
{
|
||||
DPLANE_CTX_VALID(ctx);
|
||||
|
||||
return &(ctx->u.pw.nhg);
|
||||
}
|
||||
|
||||
/*
|
||||
* End of dplane context accessors
|
||||
*/
|
||||
@ -1039,6 +1060,12 @@ static int dplane_ctx_pw_init(struct zebra_dplane_ctx *ctx,
|
||||
enum dplane_op_e op,
|
||||
struct zebra_pw *pw)
|
||||
{
|
||||
struct prefix p;
|
||||
afi_t afi;
|
||||
struct route_table *table;
|
||||
struct route_node *rn;
|
||||
struct route_entry *re;
|
||||
|
||||
if (IS_ZEBRA_DEBUG_DPLANE_DETAIL)
|
||||
zlog_debug("init dplane ctx %s: pw '%s', loc %u, rem %u",
|
||||
dplane_op2str(op), pw->ifname, pw->local_label,
|
||||
@ -1056,6 +1083,7 @@ static int dplane_ctx_pw_init(struct zebra_dplane_ctx *ctx,
|
||||
|
||||
/* This name appears to be c-string, so we use string copy. */
|
||||
strlcpy(ctx->u.pw.ifname, pw->ifname, sizeof(ctx->u.pw.ifname));
|
||||
|
||||
ctx->zd_vrf_id = pw->vrf_id;
|
||||
ctx->u.pw.ifindex = pw->ifindex;
|
||||
ctx->u.pw.type = pw->type;
|
||||
@ -1064,10 +1092,37 @@ static int dplane_ctx_pw_init(struct zebra_dplane_ctx *ctx,
|
||||
ctx->u.pw.remote_label = pw->remote_label;
|
||||
ctx->u.pw.flags = pw->flags;
|
||||
|
||||
ctx->u.pw.nexthop = pw->nexthop;
|
||||
ctx->u.pw.dest = pw->nexthop;
|
||||
|
||||
ctx->u.pw.fields = pw->data;
|
||||
|
||||
/* Capture nexthop info for the pw destination. We need to look
|
||||
* up and use zebra datastructs, but we're running in the zebra
|
||||
* pthread here so that should be ok.
|
||||
*/
|
||||
memcpy(&p.u, &pw->nexthop, sizeof(pw->nexthop));
|
||||
p.family = pw->af;
|
||||
p.prefixlen = ((pw->af == AF_INET) ?
|
||||
IPV4_MAX_PREFIXLEN : IPV6_MAX_PREFIXLEN);
|
||||
|
||||
afi = (pw->af == AF_INET) ? AFI_IP : AFI_IP6;
|
||||
table = zebra_vrf_table(afi, SAFI_UNICAST, pw->vrf_id);
|
||||
if (table) {
|
||||
rn = route_node_match(table, &p);
|
||||
if (rn) {
|
||||
RNODE_FOREACH_RE(rn, re) {
|
||||
if (CHECK_FLAG(re->flags, ZEBRA_FLAG_SELECTED))
|
||||
break;
|
||||
}
|
||||
|
||||
if (re)
|
||||
copy_nexthops(&(ctx->u.pw.nhg.nexthop),
|
||||
re->ng.nexthop, NULL);
|
||||
|
||||
route_unlock_node(rn);
|
||||
}
|
||||
}
|
||||
|
||||
return AOK;
|
||||
}
|
||||
|
||||
|
@ -203,8 +203,9 @@ const struct nexthop_group *dplane_ctx_get_old_ng(
|
||||
mpls_label_t dplane_ctx_get_in_label(const struct zebra_dplane_ctx *ctx);
|
||||
uint8_t dplane_ctx_get_addr_family(const struct zebra_dplane_ctx *ctx);
|
||||
uint32_t dplane_ctx_get_lsp_flags(const struct zebra_dplane_ctx *ctx);
|
||||
zebra_nhlfe_t *dplane_ctx_get_nhlfe(struct zebra_dplane_ctx *ctx);
|
||||
zebra_nhlfe_t *dplane_ctx_get_best_nhlfe(struct zebra_dplane_ctx *ctx);
|
||||
const zebra_nhlfe_t *dplane_ctx_get_nhlfe(const struct zebra_dplane_ctx *ctx);
|
||||
const zebra_nhlfe_t *dplane_ctx_get_best_nhlfe(
|
||||
const struct zebra_dplane_ctx *ctx);
|
||||
uint32_t dplane_ctx_get_lsp_num_ecmp(const struct zebra_dplane_ctx *ctx);
|
||||
|
||||
/* Accessors for pseudowire information */
|
||||
@ -215,10 +216,12 @@ int dplane_ctx_get_pw_type(const struct zebra_dplane_ctx *ctx);
|
||||
int dplane_ctx_get_pw_af(const struct zebra_dplane_ctx *ctx);
|
||||
uint32_t dplane_ctx_get_pw_flags(const struct zebra_dplane_ctx *ctx);
|
||||
int dplane_ctx_get_pw_status(const struct zebra_dplane_ctx *ctx);
|
||||
const union g_addr *dplane_ctx_get_pw_nexthop(
|
||||
const union g_addr *dplane_ctx_get_pw_dest(
|
||||
const struct zebra_dplane_ctx *ctx);
|
||||
const union pw_protocol_fields *dplane_ctx_get_pw_proto(
|
||||
const struct zebra_dplane_ctx *ctx);
|
||||
const struct nexthop_group *dplane_ctx_get_pw_nhg(
|
||||
const struct zebra_dplane_ctx *ctx);
|
||||
|
||||
/* Namespace info - esp. for netlink communication */
|
||||
const struct zebra_dplane_info *dplane_ctx_get_ns(
|
||||
|
@ -43,7 +43,7 @@ struct {
|
||||
} kr_state;
|
||||
|
||||
static int kernel_send_rtmsg_v4(int action, mpls_label_t in_label,
|
||||
zebra_nhlfe_t *nhlfe)
|
||||
const zebra_nhlfe_t *nhlfe)
|
||||
{
|
||||
struct iovec iov[5];
|
||||
struct rt_msghdr hdr;
|
||||
@ -135,7 +135,7 @@ static int kernel_send_rtmsg_v4(int action, mpls_label_t in_label,
|
||||
#endif
|
||||
|
||||
static int kernel_send_rtmsg_v6(int action, mpls_label_t in_label,
|
||||
zebra_nhlfe_t *nhlfe)
|
||||
const zebra_nhlfe_t *nhlfe)
|
||||
{
|
||||
struct iovec iov[5];
|
||||
struct rt_msghdr hdr;
|
||||
@ -238,7 +238,7 @@ static int kernel_send_rtmsg_v6(int action, mpls_label_t in_label,
|
||||
|
||||
static int kernel_lsp_cmd(struct zebra_dplane_ctx *ctx)
|
||||
{
|
||||
zebra_nhlfe_t *nhlfe;
|
||||
const zebra_nhlfe_t *nhlfe;
|
||||
struct nexthop *nexthop = NULL;
|
||||
unsigned int nexthop_num = 0;
|
||||
int action;
|
||||
@ -342,7 +342,7 @@ static enum zebra_dplane_result kmpw_install(struct zebra_dplane_ctx *ctx)
|
||||
|
||||
/* pseudowire nexthop */
|
||||
memset(&ss, 0, sizeof(ss));
|
||||
gaddr = dplane_ctx_get_pw_nexthop(ctx);
|
||||
gaddr = dplane_ctx_get_pw_dest(ctx);
|
||||
switch (dplane_ctx_get_pw_af(ctx)) {
|
||||
case AF_INET:
|
||||
sa_in->sin_family = AF_INET;
|
||||
|
Loading…
Reference in New Issue
Block a user