Commit 180012dc authored by Jakub Kicinski's avatar Jakub Kicinski Committed by David S. Miller

nfp: remove buggy RX buffer length validation

Meaning of data_len and meta_len RX WB descriptor fields is
slightly confusing.  Add a comment with a diagram clarifying
the layout.  Also remove the buffer length validation:
(a) it's imprecise for static rx-offsets; (b) if firmware
is buggy enough to DMA past the end of the buffer
WARN_ON_ONCE() doesn't seem like a strong enough response.
skb_put() will do the checking for us anyway.
Signed-off-by: default avatarJakub Kicinski <jakub.kicinski@netronome.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 2db221cd
...@@ -1298,23 +1298,25 @@ static int nfp_net_rx(struct nfp_net_rx_ring *rx_ring, int budget) ...@@ -1298,23 +1298,25 @@ static int nfp_net_rx(struct nfp_net_rx_ring *rx_ring, int budget)
nfp_net_rx_give_one(rx_ring, new_skb, new_dma_addr); nfp_net_rx_give_one(rx_ring, new_skb, new_dma_addr);
/* < meta_len >
* <-- [rx_offset] -->
* ---------------------------------------------------------
* | [XX] | metadata | packet | XXXX |
* ---------------------------------------------------------
* <---------------- data_len --------------->
*
* The rx_offset is fixed for all packets, the meta_len can vary
* on a packet by packet basis. If rx_offset is set to zero
* (_RX_OFFSET_DYNAMIC) metadata starts at the beginning of the
* buffer and is immediately followed by the packet (no [XX]).
*/
meta_len = rxd->rxd.meta_len_dd & PCIE_DESC_RX_META_LEN_MASK; meta_len = rxd->rxd.meta_len_dd & PCIE_DESC_RX_META_LEN_MASK;
data_len = le16_to_cpu(rxd->rxd.data_len); data_len = le16_to_cpu(rxd->rxd.data_len);
if (WARN_ON_ONCE(data_len > nn->fl_bufsz)) { if (nn->rx_offset == NFP_NET_CFG_RX_OFFSET_DYNAMIC)
dev_kfree_skb_any(skb);
continue;
}
if (nn->rx_offset == NFP_NET_CFG_RX_OFFSET_DYNAMIC) {
/* The packet data starts after the metadata */
skb_reserve(skb, meta_len); skb_reserve(skb, meta_len);
} else { else
/* The packet data starts at a fixed offset */
skb_reserve(skb, nn->rx_offset); skb_reserve(skb, nn->rx_offset);
}
/* Adjust the SKB for the dynamic meta data pre-pended */
skb_put(skb, data_len - meta_len); skb_put(skb, data_len - meta_len);
nfp_net_set_hash(nn->netdev, skb, rxd); nfp_net_set_hash(nn->netdev, skb, rxd);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment