diff options
| -rw-r--r-- | bgpd/bgp_evpn.c | 3 | ||||
| -rw-r--r-- | bgpd/bgp_label.c | 3 | ||||
| -rw-r--r-- | bgpd/bgp_mplsvpn.c | 3 | ||||
| -rw-r--r-- | bgpd/bgp_route.c | 2 | ||||
| -rw-r--r-- | zebra/zapi_msg.c | 15 | ||||
| -rw-r--r-- | zebra/zebra_ptm.c | 39 | ||||
| -rw-r--r-- | zebra/zebra_vxlan.c | 99 |
7 files changed, 98 insertions, 66 deletions
diff --git a/bgpd/bgp_evpn.c b/bgpd/bgp_evpn.c index b8798a7ced..79a8fae530 100644 --- a/bgpd/bgp_evpn.c +++ b/bgpd/bgp_evpn.c @@ -5100,7 +5100,8 @@ int bgp_nlri_parse_evpn(struct peer *peer, struct attr *attr, if (pnt + BGP_ADDPATH_ID_LEN > lim) return BGP_NLRI_PARSE_ERROR_PACKET_OVERFLOW; - addpath_id = ntohl(*((uint32_t *)pnt)); + memcpy(&addpath_id, pnt, BGP_ADDPATH_ID_LEN); + addpath_id = ntohl(addpath_id); pnt += BGP_ADDPATH_ID_LEN; } diff --git a/bgpd/bgp_label.c b/bgpd/bgp_label.c index 489ac6ea9f..ff1ab1a37d 100644 --- a/bgpd/bgp_label.c +++ b/bgpd/bgp_label.c @@ -368,7 +368,8 @@ int bgp_nlri_parse_label(struct peer *peer, struct attr *attr, if (pnt + BGP_ADDPATH_ID_LEN > lim) return BGP_NLRI_PARSE_ERROR_PACKET_OVERFLOW; - addpath_id = ntohl(*((uint32_t *)pnt)); + memcpy(&addpath_id, pnt, BGP_ADDPATH_ID_LEN); + addpath_id = ntohl(addpath_id); pnt += BGP_ADDPATH_ID_LEN; } diff --git a/bgpd/bgp_mplsvpn.c b/bgpd/bgp_mplsvpn.c index 59ed433e58..86c04b71f0 100644 --- a/bgpd/bgp_mplsvpn.c +++ b/bgpd/bgp_mplsvpn.c @@ -142,7 +142,8 @@ int bgp_nlri_parse_vpn(struct peer *peer, struct attr *attr, if (pnt + BGP_ADDPATH_ID_LEN > lim) return BGP_NLRI_PARSE_ERROR_PACKET_OVERFLOW; - addpath_id = ntohl(*((uint32_t *)pnt)); + memcpy(&addpath_id, pnt, BGP_ADDPATH_ID_LEN); + addpath_id = ntohl(addpath_id); pnt += BGP_ADDPATH_ID_LEN; } diff --git a/bgpd/bgp_route.c b/bgpd/bgp_route.c index b216f85c40..5f4486b800 100644 --- a/bgpd/bgp_route.c +++ b/bgpd/bgp_route.c @@ -4515,7 +4515,7 @@ int bgp_nlri_parse_ip(struct peer *peer, struct attr *attr, if (pnt + BGP_ADDPATH_ID_LEN >= lim) return BGP_NLRI_PARSE_ERROR_PACKET_OVERFLOW; - memcpy(&addpath_id, pnt, 4); + memcpy(&addpath_id, pnt, BGP_ADDPATH_ID_LEN); addpath_id = ntohl(addpath_id); pnt += BGP_ADDPATH_ID_LEN; } diff --git a/zebra/zapi_msg.c b/zebra/zapi_msg.c index df41220c5d..5a63c1e4f6 100644 --- a/zebra/zapi_msg.c +++ b/zebra/zapi_msg.c @@ -2463,6 +2463,13 @@ static inline void zread_ipset_entry(ZAPI_HANDLER_ARGS) /* calculate backpointer */ zpi.backpointer = zebra_pbr_lookup_ipset_pername(ipset.ipset_name); + + if (!zpi.backpointer) { + zlog_warn("ipset name specified: %s does not exist", + ipset.ipset_name); + goto stream_failure; + } + if (hdr->command == ZEBRA_IPSET_ENTRY_ADD) zebra_pbr_add_ipset_entry(&zpi); else @@ -2615,6 +2622,14 @@ void zserv_handle_commands(struct zserv *client, struct stream *msg) struct zmsghdr hdr; struct zebra_vrf *zvrf; + if (STREAM_READABLE(msg) > ZEBRA_MAX_PACKET_SIZ) { + if (IS_ZEBRA_DEBUG_PACKET && IS_ZEBRA_DEBUG_RECV) + zlog_debug( + "ZAPI message is %zu bytes long but the maximum packet size is %u; dropping", + STREAM_READABLE(msg), ZEBRA_MAX_PACKET_SIZ); + return; + } + zapi_parse_header(msg, &hdr); if (IS_ZEBRA_DEBUG_PACKET && IS_ZEBRA_DEBUG_RECV) diff --git a/zebra/zebra_ptm.c b/zebra/zebra_ptm.c index 8640a4a720..b48756302a 100644 --- a/zebra/zebra_ptm.c +++ b/zebra/zebra_ptm.c @@ -1400,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); @@ -1441,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__); } diff --git a/zebra/zebra_vxlan.c b/zebra/zebra_vxlan.c index 086b13d670..564573dcb3 100644 --- a/zebra/zebra_vxlan.c +++ b/zebra/zebra_vxlan.c @@ -7682,6 +7682,55 @@ int zebra_vxlan_handle_kernel_neigh_update(struct interface *ifp, return zvni_remote_neigh_update(zvni, ifp, ip, macaddr, state); } +static int32_t +zebra_vxlan_remote_macip_helper(bool add, struct stream *s, vni_t *vni, + struct ethaddr *macaddr, uint16_t *ipa_len, + struct ipaddr *ip, struct in_addr *vtep_ip, + uint8_t *flags, uint32_t *seq) +{ + uint16_t l = 0; + + /* + * Obtain each remote MACIP and process. + * Message contains VNI, followed by MAC followed by IP (if any) + * followed by remote VTEP IP. + */ + memset(ip, 0, sizeof(*ip)); + STREAM_GETL(s, *vni); + STREAM_GET(macaddr->octet, s, ETH_ALEN); + STREAM_GETL(s, *ipa_len); + + if (*ipa_len) { + if (*ipa_len == IPV4_MAX_BYTELEN) + ip->ipa_type = IPADDR_V4; + else if (*ipa_len == IPV6_MAX_BYTELEN) + ip->ipa_type = IPADDR_V6; + else { + if (IS_ZEBRA_DEBUG_VXLAN) + zlog_debug( + "ipa_len *must* be %d or %d bytes in length not %d", + IPV4_MAX_BYTELEN, IPV6_MAX_BYTELEN, + *ipa_len); + goto stream_failure; + } + + STREAM_GET(&ip->ip.addr, s, *ipa_len); + } + l += 4 + ETH_ALEN + 4 + *ipa_len; + STREAM_GET(&vtep_ip->s_addr, s, IPV4_MAX_BYTELEN); + l += IPV4_MAX_BYTELEN; + + if (add) { + STREAM_GETC(s, *flags); + STREAM_GETL(s, *seq); + l += 5; + } + + return l; + +stream_failure: + return -1; +} /* * Handle message from client to delete a remote MACIP for a VNI. @@ -7704,23 +7753,14 @@ void zebra_vxlan_remote_macip_del(ZAPI_HANDLER_ARGS) s = msg; while (l < hdr->length) { - /* Obtain each remote MACIP and process. */ - /* Message contains VNI, followed by MAC followed by IP (if any) - * followed by remote VTEP IP. - */ - memset(&ip, 0, sizeof(ip)); - STREAM_GETL(s, vni); - STREAM_GET(&macaddr.octet, s, ETH_ALEN); - STREAM_GETL(s, ipa_len); - if (ipa_len) { - ip.ipa_type = (ipa_len == IPV4_MAX_BYTELEN) ? IPADDR_V4 - : IPADDR_V6; - STREAM_GET(&ip.ip.addr, s, ipa_len); - } - l += 4 + ETH_ALEN + 4 + ipa_len; - STREAM_GET(&vtep_ip.s_addr, s, IPV4_MAX_BYTELEN); - l += IPV4_MAX_BYTELEN; + int res_length = zebra_vxlan_remote_macip_helper( + false, s, &vni, &macaddr, &ipa_len, &ip, &vtep_ip, NULL, + NULL); + if (res_length == -1) + goto stream_failure; + + l += res_length; if (IS_ZEBRA_DEBUG_VXLAN) zlog_debug( "Recv MACIP DEL VNI %u MAC %s%s%s Remote VTEP %s from %s", @@ -7769,29 +7809,14 @@ void zebra_vxlan_remote_macip_add(ZAPI_HANDLER_ARGS) s = msg; while (l < hdr->length) { - /* Obtain each remote MACIP and process. */ - /* Message contains VNI, followed by MAC followed by IP (if any) - * followed by remote VTEP IP. - */ - memset(&ip, 0, sizeof(ip)); - STREAM_GETL(s, vni); - STREAM_GET(&macaddr.octet, s, ETH_ALEN); - STREAM_GETL(s, ipa_len); - if (ipa_len) { - ip.ipa_type = (ipa_len == IPV4_MAX_BYTELEN) ? IPADDR_V4 - : IPADDR_V6; - STREAM_GET(&ip.ip.addr, s, ipa_len); - } - l += 4 + ETH_ALEN + 4 + ipa_len; - STREAM_GET(&vtep_ip.s_addr, s, IPV4_MAX_BYTELEN); - l += IPV4_MAX_BYTELEN; + int res_length = zebra_vxlan_remote_macip_helper( + true, s, &vni, &macaddr, &ipa_len, &ip, &vtep_ip, + &flags, &seq); - /* Get flags - sticky mac and/or gateway mac */ - STREAM_GETC(s, flags); - l++; - STREAM_GETL(s, seq); - l += 4; + if (res_length == -1) + goto stream_failure; + l += res_length; if (IS_ZEBRA_DEBUG_VXLAN) zlog_debug( "Recv MACIP ADD VNI %u MAC %s%s%s flags 0x%x seq %u VTEP %s from %s", |
