bnxt_en: 2 XDP bug fixes
Subsystems (5)
Michael Chan
maintainercover bnxt_en: 2 XDP bug fixes
The first patch fixes XDP page pool logic on systems with page size >= 64K. The second patch fixes the max_mtu setting when an XDP program supporting multi buffers is attached.
Michael Chan (1):
bnxt_en: Fix max_mtu setting for multi-buf XDP
Somnath Kotur (1):
bnxt_en: Fix page pool logic for page size >= 64K
drivers/net/ethernet/broadcom/bnxt/bnxt.c | 59 +++++++++++-------- drivers/net/ethernet/broadcom/bnxt/bnxt_xdp.c | 6 +- 2 files changed, 39 insertions(+), 26 deletions(-)
Signature · 1 line
2.30.1
Michael Chan
maintainerPATCH 1/2 bnxt_en: Fix page pool logic for page size >= 64K
From: Somnath Kotur <[email protected]>
The RXBD length field on all bnxt chips is 16-bit and so we cannot support a full page when the native page size is 64K or greater. The non-XDP (non page pool) code path has logic to handle this but the XDP page pool code path does not handle this. Add the missing logic to use page_pool_dev_alloc_frag() to allocate 32K chunks if the page size is 64K or greater.
---
v2:
- Resubmit to net since it is a bug fix
- Fix some lines > 80 characters
- Fix reverse xmas tree style
--- drivers/net/ethernet/broadcom/bnxt/bnxt.c | 42 ++++++++++++------- drivers/net/ethernet/broadcom/bnxt/bnxt_xdp.c | 6 +-- 2 files changed, 29 insertions(+), 19 deletions(-)
drivers/net/ethernet/broadcom/bnxt/bnxt.c +26 -16
@@ -697,17 +697,24 @@ static void bnxt_tx_int(struct bnxt *bp, struct bnxt_napi *bnapi, int nr_pkts)static struct page *__bnxt_alloc_rx_page (struct bnxt *bp,dma_addr_t *mapping,struct bnxt_rx_ring_info *rxr, +unsigned int *offset,gfp_t gfp) {struct device *dev = &bp->pdev->dev;struct page *page; - page =page_pool_dev_alloc_pages (rxr->page_pool); +if (PAGE_SIZE >BNXT_RX_PAGE_SIZE ) { + page =page_pool_dev_alloc_frag (rxr->page_pool, offset, +BNXT_RX_PAGE_SIZE ); + }else { + page =page_pool_dev_alloc_pages (rxr->page_pool); + *offset =0 ; + }if (!page)return NULL ; - *mapping =dma_map_page_attrs (dev, page,0 ,PAGE_SIZE , bp->rx_dir, -DMA_ATTR_WEAK_ORDERING ); + *mapping =dma_map_page_attrs (dev, page, *offset,BNXT_RX_PAGE_SIZE , + bp->rx_dir,DMA_ATTR_WEAK_ORDERING );if (dma_mapping_error (dev, *mapping)) {page_pool_recycle_direct (rxr->page_pool, page);return NULL ;
@@ -747,15 +754,16 @@ int bnxt_alloc_rx_data(struct bnxt *bp, struct bnxt_rx_ring_info *rxr,dma_addr_t mapping;if (BNXT_RX_PAGE_MODE (bp)) { +unsigned int offset;struct page *page = -__bnxt_alloc_rx_page (bp, &mapping, rxr, gfp); +__bnxt_alloc_rx_page (bp, &mapping, rxr, &offset, gfp);if (!page)return -ENOMEM ; mapping += bp->rx_dma_offset; rx_buf->data = page; - rx_buf->data_ptr =page_address (page) + bp->rx_offset; + rx_buf->data_ptr =page_address (page) + offset + bp->rx_offset; }else {u8 *data =__bnxt_alloc_rx_frag (bp, &mapping, gfp);
@@ -815,7 +823,7 @@ static inline int bnxt_alloc_rx_page(struct bnxt *bp,unsigned int offset =0 ;if (BNXT_RX_PAGE_MODE (bp)) { - page =__bnxt_alloc_rx_page (bp, &mapping, rxr, gfp); + page =__bnxt_alloc_rx_page (bp, &mapping, rxr, &offset, gfp);if (!page)return -ENOMEM ;
@@ -962,15 +970,15 @@ static struct sk_buff *bnxt_rx_multi_page_skb(struct bnxt *bp,return NULL ; } dma_addr -= bp->rx_dma_offset; -dma_unmap_page_attrs (&bp->pdev->dev, dma_addr,PAGE_SIZE , bp->rx_dir, -DMA_ATTR_WEAK_ORDERING ); - skb =build_skb (page_address (page),PAGE_SIZE ); +dma_unmap_page_attrs (&bp->pdev->dev, dma_addr,BNXT_RX_PAGE_SIZE , + bp->rx_dir,DMA_ATTR_WEAK_ORDERING ); + skb =build_skb (data_ptr - bp->rx_offset,BNXT_RX_PAGE_SIZE );if (!skb) {page_pool_recycle_direct (rxr->page_pool, page);return NULL ; }skb_mark_for_recycle (skb); -skb_reserve (skb, bp->rx_dma_offset); +skb_reserve (skb, bp->rx_offset);__skb_put (skb, len);return skb;
@@ -996,8 +1004,8 @@ static struct sk_buff *bnxt_rx_page_skb(struct bnxt *bp,return NULL ; } dma_addr -= bp->rx_dma_offset; -dma_unmap_page_attrs (&bp->pdev->dev, dma_addr,PAGE_SIZE , bp->rx_dir, -DMA_ATTR_WEAK_ORDERING ); +dma_unmap_page_attrs (&bp->pdev->dev, dma_addr,BNXT_RX_PAGE_SIZE , + bp->rx_dir,DMA_ATTR_WEAK_ORDERING );if (unlikely (!payload)) payload =eth_get_headlen (bp->dev, data_ptr, len);
@@ -1010,7 +1018,7 @@ static struct sk_buff *bnxt_rx_page_skb(struct bnxt *bp,skb_mark_for_recycle (skb); off = (void *)data_ptr -page_address (page); -skb_add_rx_frag (skb,0 , page, off, len,PAGE_SIZE ); +skb_add_rx_frag (skb,0 , page, off, len,BNXT_RX_PAGE_SIZE );memcpy (skb->data -NET_IP_ALIGN , data_ptr -NET_IP_ALIGN , payload +NET_IP_ALIGN );
@@ -1141,7 +1149,7 @@ static struct sk_buff *bnxt_rx_agg_pages_skb(struct bnxt *bp, skb->data_len += total_frag_len; skb->len += total_frag_len; - skb->truesize +=PAGE_SIZE * agg_bufs; + skb->truesize +=BNXT_RX_PAGE_SIZE * agg_bufs;return skb; }
@@ -2943,8 +2951,8 @@ static void bnxt_free_one_rx_ring_skbs(struct bnxt *bp, int ring_nr) rx_buf->data =NULL ;if (BNXT_RX_PAGE_MODE (bp)) { mapping -= bp->rx_dma_offset; -dma_unmap_page_attrs (&pdev->dev, mapping,PAGE_SIZE , - bp->rx_dir, +dma_unmap_page_attrs (&pdev->dev, mapping, +BNXT_RX_PAGE_SIZE , bp->rx_dir,DMA_ATTR_WEAK_ORDERING );page_pool_recycle_direct (rxr->page_pool, data); }else {
@@ -3213,6 +3221,8 @@ static int bnxt_alloc_rx_page_pool(struct bnxt *bp, pp.napi = &rxr->bnapi->napi; pp.dev = &bp->pdev->dev; pp.dma_dir =DMA_BIDIRECTIONAL ; +if (PAGE_SIZE >BNXT_RX_PAGE_SIZE ) + pp.flags |=PP_FLAG_PAGE_FRAG ; rxr->page_pool =page_pool_create (&pp);if (IS_ERR (rxr->page_pool)) {
drivers/net/ethernet/broadcom/bnxt/bnxt_xdp.c +3 -3
@@ -180,8 +180,8 @@ void bnxt_xdp_buff_init(struct bnxt *bp, struct bnxt_rx_ring_info *rxr, u16 cons, u8 *data_ptr, unsigned int len, struct xdp_buff *xdp) { + u32 buflen = BNXT_RX_PAGE_SIZE;struct bnxt_sw_rx_bd *rx_buf; -u32 buflen =PAGE_SIZE ;struct pci_dev *pdev;dma_addr_t mapping;u32 offset;
@@ -297,7 +297,7 @@ bool bnxt_rx_xdp(struct bnxt *bp, struct bnxt_rx_ring_info *rxr, u16 cons, rx_buf = &rxr->rx_buf_ring[cons]; mapping = rx_buf->mapping - bp->rx_dma_offset;dma_unmap_page_attrs (&pdev->dev, mapping, -PAGE_SIZE , bp->rx_dir, +BNXT_RX_PAGE_SIZE , bp->rx_dir,DMA_ATTR_WEAK_ORDERING );/* if we are unable to allocate a new buffer, abort and reuse */
@@ -480,7 +480,7 @@ bnxt_xdp_build_skb(struct bnxt *bp, struct sk_buff *skb, u8 num_frags, }xdp_update_skb_shared_info (skb, num_frags, sinfo->xdp_frags_size, -PAGE_SIZE * sinfo->nr_frags, +BNXT_RX_PAGE_SIZE * sinfo->nr_frags,xdp_buff_is_frag_pfmemalloc (xdp));return skb; }
Signature · 1 line
2.30.1
Michael Chan
maintainerPATCH 2/2 bnxt_en: Fix max_mtu setting for multi-buf XDP
In reply to Michael ChanThe existing code does not allow the MTU to be set to the maximum even after an XDP program supporting multiple buffers is attached. Fix it to set the netdev->max_mtu to the maximum value if the attached XDP program supports mutiple buffers, regardless of the current MTU value.
Also use a local variable dev instead of repeatedly using bp->dev.
--- drivers/net/ethernet/broadcom/bnxt/bnxt.c | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-)
drivers/net/ethernet/broadcom/bnxt/bnxt.c +10 -7
@@ -3999,26 +3999,29 @@ void bnxt_set_ring_params(struct bnxt *bp)*/ int bnxt_set_rx_skb_mode (struct bnxt *bp,bool page_mode) { +struct net_device *dev = bp->dev; +if (page_mode) { bp->flags &= ~BNXT_FLAG_AGG_RINGS ; bp->flags |=BNXT_FLAG_RX_PAGE_MODE ; -if (bp->dev->mtu >BNXT_MAX_PAGE_MODE_MTU ) { +if (bp->xdp_prog->aux->xdp_has_frags) + dev->max_mtu =min_t (u16, bp->max_mtu,BNXT_MAX_MTU ); +else + dev->max_mtu = +min_t (u16, bp->max_mtu,BNXT_MAX_PAGE_MODE_MTU ); +if (dev->mtu >BNXT_MAX_PAGE_MODE_MTU ) { bp->flags |=BNXT_FLAG_JUMBO ; bp->rx_skb_func = bnxt_rx_multi_page_skb; - bp->dev->max_mtu = -min_t (u16, bp->max_mtu,BNXT_MAX_MTU ); }else { bp->flags |=BNXT_FLAG_NO_AGG_RINGS ; bp->rx_skb_func = bnxt_rx_page_skb; - bp->dev->max_mtu = -min_t (u16, bp->max_mtu,BNXT_MAX_PAGE_MODE_MTU ); } bp->rx_dir =DMA_BIDIRECTIONAL ;/* Disable LRO or GRO_HW */ -netdev_update_features (bp->dev); +netdev_update_features (dev); }else { - bp->dev->max_mtu = bp->max_mtu; + dev->max_mtu = bp->max_mtu; bp->flags &= ~BNXT_FLAG_RX_PAGE_MODE ; bp->rx_dir =DMA_FROM_DEVICE ; bp->rx_skb_func = bnxt_rx_skb;
Signature · 1 line
2.30.1
This series was applied to netdev/net.git (main) by Jakub Kicinski <[email protected]>:
Hello:
This series was applied to netdev/net.git (main)
by Jakub Kicinski <[email protected]>:
Quoted 8 lines · On Mon, 31 Jul 2023 07:20:41 -0700 you wrote:
The first patch fixes XDP page pool logic on systems with page size >= 64K. The second patch fixes the
max_mtusetting when an XDP program supporting multi buffers is attached.Michael Chan (1):
bnxt_en: Fixmax_mtusetting for multi-buf XDP[...]
Here is the summary with links:
- [net,1/2] bnxt_en: Fix page pool logic for page size >= 64K
https://git.kernel.org/netdev/net/c/f6974b4c2d8e - [net,2/2] bnxt_en: Fix max_mtu setting for multi-buf XDP https://git.kernel.org/netdev/net/c/08450ea98ae9
You are awesome, thank you!
Signature · 2 lines
Deet-doot-dot, I am a bot. https://korg.docs.kernel.org/patchwork/pwbot.html