summaryrefslogtreecommitdiff
path: root/zebra/zebra_ptm.c
diff options
context:
space:
mode:
Diffstat (limited to 'zebra/zebra_ptm.c')
-rw-r--r--zebra/zebra_ptm.c41
1 files changed, 14 insertions, 27 deletions
diff --git a/zebra/zebra_ptm.c b/zebra/zebra_ptm.c
index 46f1385520..b48756302a 100644
--- a/zebra/zebra_ptm.c
+++ b/zebra/zebra_ptm.c
@@ -1295,7 +1295,6 @@ static void zebra_ptm_send_bfdd(struct stream *msg)
}
stream_free(msgc);
- stream_free(msg);
}
static void zebra_ptm_send_clients(struct stream *msg)
@@ -1327,7 +1326,6 @@ static void zebra_ptm_send_clients(struct stream *msg)
}
stream_free(msgc);
- stream_free(msg);
}
static int _zebra_ptm_bfd_client_deregister(struct zserv *zs)
@@ -1402,37 +1400,25 @@ static void _zebra_ptm_reroute(struct zserv *zs, struct zebra_vrf *zvrf,
struct stream *msg, uint32_t command)
{
struct stream *msgc;
- size_t zmsglen, zhdrlen;
+ char buf[ZEBRA_MAX_PACKET_SIZ];
pid_t ppid;
- /*
- * Don't modify message in the zebra API. In order to do that we
- * need to allocate a new message stream and copy the message
- * provided by zebra.
- */
+ /* Create BFD header */
msgc = stream_new(ZEBRA_MAX_PACKET_SIZ);
- if (msgc == NULL) {
- zlog_debug("%s: not enough memory", __func__);
- return;
- }
-
- /* Calculate our header size plus the message contents. */
- zhdrlen = ZEBRA_HEADER_SIZE + sizeof(uint32_t);
- zmsglen = msg->endp - msg->getp;
- memcpy(msgc->data + zhdrlen, msg->data + msg->getp, zmsglen);
-
- /*
- * The message type will be BFD_DEST_REPLY so we can use only
- * one callback at the `bfdd` side, however the real command
- * number will be included right after the zebra header.
- */
zclient_create_header(msgc, ZEBRA_BFD_DEST_REPLAY, zvrf->vrf->vrf_id);
stream_putl(msgc, command);
- /* Update the data pointers. */
- msgc->getp = 0;
- msgc->endp = zhdrlen + zmsglen;
- stream_putw_at(msgc, 0, stream_get_endp(msgc));
+ if (STREAM_READABLE(msg) > STREAM_WRITEABLE(msgc)) {
+ zlog_warn("Cannot fit extended BFD header plus original message contents into ZAPI packet; dropping message");
+ goto stream_failure;
+ }
+
+ /* Copy original message, excluding header, into new message */
+ stream_get_from(buf, msg, stream_get_getp(msg), STREAM_READABLE(msg));
+ stream_put(msgc, buf, STREAM_READABLE(msg));
+
+ /* Update length field */
+ stream_putw_at(msgc, 0, STREAM_READABLE(msgc));
zebra_ptm_send_bfdd(msgc);
@@ -1443,6 +1429,7 @@ static void _zebra_ptm_reroute(struct zserv *zs, struct zebra_vrf *zvrf,
return;
stream_failure:
+ stream_free(msgc);
zlog_err("%s:%d failed to registrate client pid", __FILE__, __LINE__);
}