mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-05-02 18:56:53 +00:00
zebra: check for buffer boundary
* Move code encoding Netlink messages to separate functions * Add buffer bounds checking while creating Nelink messages Signed-off-by: Jakub Urbańczyk <xthaid@gmail.com>
This commit is contained in:
parent
312a6beed6
commit
0be6e7d75d
@ -709,11 +709,12 @@ static int fpm_nl_enqueue(struct fpm_nl_ctx *fnc, struct zebra_dplane_ctx *ctx)
|
||||
switch (op) {
|
||||
case DPLANE_OP_ROUTE_UPDATE:
|
||||
case DPLANE_OP_ROUTE_DELETE:
|
||||
rv = netlink_route_multipath(RTM_DELROUTE, ctx, nl_buf,
|
||||
sizeof(nl_buf), true,
|
||||
fnc->use_nhg);
|
||||
rv = netlink_route_multipath_msg_encode(RTM_DELROUTE, ctx,
|
||||
nl_buf, sizeof(nl_buf),
|
||||
true, fnc->use_nhg);
|
||||
if (rv <= 0) {
|
||||
zlog_err("%s: netlink_route_multipath failed",
|
||||
zlog_err(
|
||||
"%s: netlink_route_multipath_msg_encode failed",
|
||||
__func__);
|
||||
return 0;
|
||||
}
|
||||
@ -726,11 +727,12 @@ static int fpm_nl_enqueue(struct fpm_nl_ctx *fnc, struct zebra_dplane_ctx *ctx)
|
||||
|
||||
/* FALL THROUGH */
|
||||
case DPLANE_OP_ROUTE_INSTALL:
|
||||
rv = netlink_route_multipath(
|
||||
rv = netlink_route_multipath_msg_encode(
|
||||
RTM_NEWROUTE, ctx, &nl_buf[nl_buf_len],
|
||||
sizeof(nl_buf) - nl_buf_len, true, fnc->use_nhg);
|
||||
if (rv <= 0) {
|
||||
zlog_err("%s: netlink_route_multipath failed",
|
||||
zlog_err(
|
||||
"%s: netlink_route_multipath_msg_encode failed",
|
||||
__func__);
|
||||
return 0;
|
||||
}
|
||||
@ -751,10 +753,11 @@ static int fpm_nl_enqueue(struct fpm_nl_ctx *fnc, struct zebra_dplane_ctx *ctx)
|
||||
break;
|
||||
|
||||
case DPLANE_OP_NH_DELETE:
|
||||
rv = netlink_nexthop_encode(RTM_DELNEXTHOP, ctx, nl_buf,
|
||||
rv = netlink_nexthop_msg_encode(RTM_DELNEXTHOP, ctx, nl_buf,
|
||||
sizeof(nl_buf));
|
||||
if (rv <= 0) {
|
||||
zlog_err("%s: netlink_nexthop_encode failed", __func__);
|
||||
zlog_err("%s: netlink_nexthop_msg_encode failed",
|
||||
__func__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
@ -762,10 +765,11 @@ static int fpm_nl_enqueue(struct fpm_nl_ctx *fnc, struct zebra_dplane_ctx *ctx)
|
||||
break;
|
||||
case DPLANE_OP_NH_INSTALL:
|
||||
case DPLANE_OP_NH_UPDATE:
|
||||
rv = netlink_nexthop_encode(RTM_NEWNEXTHOP, ctx, nl_buf,
|
||||
rv = netlink_nexthop_msg_encode(RTM_NEWNEXTHOP, ctx, nl_buf,
|
||||
sizeof(nl_buf));
|
||||
if (rv <= 0) {
|
||||
zlog_err("%s: netlink_nexthop_encode failed", __func__);
|
||||
zlog_err("%s: netlink_nexthop_msg_encode failed",
|
||||
__func__);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -64,11 +64,14 @@ extern "C" {
|
||||
void rt_netlink_init(void);
|
||||
|
||||
/* MPLS label forwarding table change, using dataplane context information. */
|
||||
extern int netlink_mpls_multipath(int cmd, struct zebra_dplane_ctx *ctx);
|
||||
extern ssize_t netlink_mpls_multipath_msg_encode(int cmd,
|
||||
struct zebra_dplane_ctx *ctx,
|
||||
void *buf, size_t buflen);
|
||||
|
||||
extern ssize_t netlink_route_multipath(int cmd, struct zebra_dplane_ctx *ctx,
|
||||
uint8_t *data, size_t datalen, bool fpm,
|
||||
bool force_nhg);
|
||||
extern ssize_t netlink_route_multipath_msg_encode(int cmd,
|
||||
struct zebra_dplane_ctx *ctx,
|
||||
uint8_t *data, size_t datalen,
|
||||
bool fpm, bool force_nhg);
|
||||
extern ssize_t netlink_macfdb_update_ctx(struct zebra_dplane_ctx *ctx,
|
||||
uint8_t *data, size_t datalen);
|
||||
|
||||
@ -78,7 +81,7 @@ extern int netlink_route_read(struct zebra_ns *zns);
|
||||
extern int netlink_nexthop_change(struct nlmsghdr *h, ns_id_t ns_id,
|
||||
int startup);
|
||||
extern int netlink_nexthop_read(struct zebra_ns *zns);
|
||||
extern ssize_t netlink_nexthop_encode(uint16_t cmd,
|
||||
extern ssize_t netlink_nexthop_msg_encode(uint16_t cmd,
|
||||
const struct zebra_dplane_ctx *ctx,
|
||||
void *buf, size_t buflen);
|
||||
|
||||
|
@ -87,38 +87,48 @@ static ssize_t netlink_rule_msg_encode(
|
||||
req->frh.family = family;
|
||||
req->frh.action = FR_ACT_TO_TBL;
|
||||
|
||||
nl_attr_put(&req->n, buflen, FRA_PROTOCOL, &protocol, sizeof(protocol));
|
||||
if (!nl_attr_put(&req->n, buflen, FRA_PROTOCOL, &protocol,
|
||||
sizeof(protocol)))
|
||||
return 0;
|
||||
|
||||
/* rule's pref # */
|
||||
nl_attr_put32(&req->n, buflen, FRA_PRIORITY, priority);
|
||||
if (!nl_attr_put32(&req->n, buflen, FRA_PRIORITY, priority))
|
||||
return 0;
|
||||
|
||||
/* interface on which applied */
|
||||
nl_attr_put(&req->n, buflen, FRA_IFNAME, ifname, strlen(ifname) + 1);
|
||||
if (!nl_attr_put(&req->n, buflen, FRA_IFNAME, ifname,
|
||||
strlen(ifname) + 1))
|
||||
return 0;
|
||||
|
||||
/* source IP, if specified */
|
||||
if (filter_bm & PBR_FILTER_SRC_IP) {
|
||||
req->frh.src_len = src_ip->prefixlen;
|
||||
nl_attr_put(&req->n, buflen, FRA_SRC, &src_ip->u.prefix,
|
||||
bytelen);
|
||||
if (!nl_attr_put(&req->n, buflen, FRA_SRC, &src_ip->u.prefix,
|
||||
bytelen))
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* destination IP, if specified */
|
||||
if (filter_bm & PBR_FILTER_DST_IP) {
|
||||
req->frh.dst_len = dst_ip->prefixlen;
|
||||
nl_attr_put(&req->n, buflen, FRA_DST, &dst_ip->u.prefix,
|
||||
bytelen);
|
||||
if (!nl_attr_put(&req->n, buflen, FRA_DST, &dst_ip->u.prefix,
|
||||
bytelen))
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* fwmark, if specified */
|
||||
if (filter_bm & PBR_FILTER_FWMARK)
|
||||
nl_attr_put32(&req->n, buflen, FRA_FWMARK, fwmark);
|
||||
if (filter_bm & PBR_FILTER_FWMARK) {
|
||||
if (!nl_attr_put32(&req->n, buflen, FRA_FWMARK, fwmark))
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Route table to use to forward, if filter criteria matches. */
|
||||
if (table < 256)
|
||||
req->frh.table = table;
|
||||
else {
|
||||
req->frh.table = RT_TABLE_UNSPEC;
|
||||
nl_attr_put32(&req->n, buflen, FRA_TABLE, table);
|
||||
if (!nl_attr_put32(&req->n, buflen, FRA_TABLE, table))
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (IS_ZEBRA_DEBUG_KERNEL)
|
||||
|
@ -26,13 +26,16 @@
|
||||
#include "zebra/rt.h"
|
||||
#include "zebra/rt_netlink.h"
|
||||
#include "zebra/zebra_mpls.h"
|
||||
#include "zebra/kernel_netlink.h"
|
||||
|
||||
/*
|
||||
* LSP forwarding update using dataplane context information.
|
||||
*/
|
||||
enum zebra_dplane_result kernel_lsp_update(struct zebra_dplane_ctx *ctx)
|
||||
{
|
||||
int cmd, ret = -1;
|
||||
uint8_t nl_pkt[NL_PKT_BUF_SIZE];
|
||||
ssize_t ret = -1;
|
||||
int cmd;
|
||||
|
||||
/* Call to netlink layer based on type of update */
|
||||
if (dplane_ctx_get_op(ctx) == DPLANE_OP_LSP_DELETE) {
|
||||
@ -53,7 +56,13 @@ enum zebra_dplane_result kernel_lsp_update(struct zebra_dplane_ctx *ctx)
|
||||
/* Invalid op? */
|
||||
goto done;
|
||||
|
||||
ret = netlink_mpls_multipath(cmd, ctx);
|
||||
ret = netlink_mpls_multipath_msg_encode(cmd, ctx, nl_pkt,
|
||||
sizeof(nl_pkt));
|
||||
if (ret <= 0)
|
||||
return ZEBRA_DPLANE_REQUEST_FAILURE;
|
||||
|
||||
ret = netlink_talk_info(netlink_talk_filter, (struct nlmsghdr *)nl_pkt,
|
||||
dplane_ctx_get_ns(ctx), 0);
|
||||
|
||||
done:
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user