diff mbox series

[net-next,03/12] mlxsw: Add struct mlxsw_pci_rx_pkt_info

Message ID 67e4b6dbb35d1e977b56e1a40e8227704ba353a3.1738665783.git.petrm@nvidia.com (mailing list archive)
State New
Delegated to: Netdev Maintainers
Headers show
Series mlxsw: Preparations for XDP support | expand

Checks

Context Check Description
netdev/series_format success Posting correctly formatted
netdev/tree_selection success Clearly marked for net-next
netdev/ynl success Generated files up to date; no warnings/errors; no diff in generated;
netdev/fixes_present success Fixes tag not required for -next series
netdev/header_inline success No static functions without inline keyword in header files
netdev/build_32bit success Errors and warnings before: 0 this patch: 0
netdev/build_tools success No tools touched, skip
netdev/cc_maintainers success CCed 8 of 8 maintainers
netdev/build_clang success Errors and warnings before: 4 this patch: 4
netdev/verify_signedoff success Signed-off-by tag matches author and committer
netdev/deprecated_api success None detected
netdev/check_selftest success No net selftest shell script
netdev/verify_fixes success No Fixes tag
netdev/build_allmodconfig_warn success Errors and warnings before: 0 this patch: 0
netdev/checkpatch success total: 0 errors, 0 warnings, 0 checks, 113 lines checked
netdev/build_clang_rust success No Rust files in patch. Skipping build
netdev/kdoc success Errors and warnings before: 0 this patch: 0
netdev/source_inline success Was 0 now: 0
netdev/contest success net-next-2025-02-04--15-00 (tests: 886)

Commit Message

Petr Machata Feb. 4, 2025, 11:04 a.m. UTC
From: Amit Cohen <amcohen@nvidia.com>

When Rx packet is received, given byte_count value from the CQE, we
calculate how many scatter/gather entries are used and the size of each
entry.

Such calculation is used for syncing the buffers for CPU and for building
SKB. When XDP will be supported, these values will be used also to create
XDP buffer.

To avoid recalculating number of scatter/gather entries and size of each
entry, add a dedicated structure to hold such info. Store also pointers
to pages. Initialize the new structure once Rx packet is received. This
patch only initializes the structure, next patches will use it.

Add struct mlxsw_pci_rx_pkt_info in pci.h as next patch in this set will
use it from another file.

Signed-off-by: Amit Cohen <amcohen@nvidia.com>
Reviewed-by: Ido Schimmel <idosch@nvidia.com>
Signed-off-by: Petr Machata <petrm@nvidia.com>
---
 drivers/net/ethernet/mellanox/mlxsw/pci.c    | 57 +++++++++++++++++---
 drivers/net/ethernet/mellanox/mlxsw/pci.h    |  8 +++
 drivers/net/ethernet/mellanox/mlxsw/pci_hw.h |  1 -
 3 files changed, 57 insertions(+), 9 deletions(-)
diff mbox series

Patch

diff --git a/drivers/net/ethernet/mellanox/mlxsw/pci.c b/drivers/net/ethernet/mellanox/mlxsw/pci.c
index 55ef185c9f5a..aca1857a4e70 100644
--- a/drivers/net/ethernet/mellanox/mlxsw/pci.c
+++ b/drivers/net/ethernet/mellanox/mlxsw/pci.c
@@ -390,6 +390,49 @@  static void mlxsw_pci_wqe_frag_unmap(struct mlxsw_pci *mlxsw_pci, char *wqe,
 	dma_unmap_single(&pdev->dev, mapaddr, frag_len, direction);
 }
 
+static u8 mlxsw_pci_num_sg_entries_get(u16 byte_count)
+{
+	return DIV_ROUND_UP(byte_count + MLXSW_PCI_RX_BUF_SW_OVERHEAD,
+			    PAGE_SIZE);
+}
+
+static int
+mlxsw_pci_rx_pkt_info_init(const struct mlxsw_pci *pci,
+			   const struct mlxsw_pci_queue_elem_info *elem_info,
+			   u16 byte_count,
+			   struct mlxsw_pci_rx_pkt_info *rx_pkt_info)
+{
+	unsigned int linear_data_size;
+	u8 num_sg_entries;
+	bool linear_only;
+	int i;
+
+	num_sg_entries = mlxsw_pci_num_sg_entries_get(byte_count);
+	if (WARN_ON_ONCE(num_sg_entries > pci->num_sg_entries))
+		return -EINVAL;
+
+	rx_pkt_info->num_sg_entries = num_sg_entries;
+
+	linear_only = byte_count + MLXSW_PCI_RX_BUF_SW_OVERHEAD <= PAGE_SIZE;
+	linear_data_size = linear_only ? byte_count :
+					 PAGE_SIZE -
+					 MLXSW_PCI_RX_BUF_SW_OVERHEAD;
+
+	for (i = 0; i < num_sg_entries; i++) {
+		unsigned int sg_entry_size;
+
+		sg_entry_size = i ? min(byte_count, PAGE_SIZE) :
+				    linear_data_size;
+
+		rx_pkt_info->sg_entries_size[i] = sg_entry_size;
+		rx_pkt_info->pages[i] = elem_info->pages[i];
+
+		byte_count -= sg_entry_size;
+	}
+
+	return 0;
+}
+
 static struct sk_buff *mlxsw_pci_rdq_build_skb(struct mlxsw_pci_queue *q,
 					       struct page *pages[],
 					       u16 byte_count)
@@ -470,12 +513,6 @@  static void mlxsw_pci_rdq_page_free(struct mlxsw_pci_queue *q,
 			   false);
 }
 
-static u8 mlxsw_pci_num_sg_entries_get(u16 byte_count)
-{
-	return DIV_ROUND_UP(byte_count + MLXSW_PCI_RX_BUF_SW_OVERHEAD,
-			    PAGE_SIZE);
-}
-
 static int
 mlxsw_pci_elem_info_pages_ref_store(const struct mlxsw_pci_queue *q,
 				    const struct mlxsw_pci_queue_elem_info *el,
@@ -486,8 +523,6 @@  mlxsw_pci_elem_info_pages_ref_store(const struct mlxsw_pci_queue *q,
 	int i;
 
 	num_sg_entries = mlxsw_pci_num_sg_entries_get(byte_count);
-	if (WARN_ON_ONCE(num_sg_entries > q->pci->num_sg_entries))
-		return -EINVAL;
 
 	for (i = 0; i < num_sg_entries; i++)
 		pages[i] = el->pages[i];
@@ -743,6 +778,7 @@  static void mlxsw_pci_cqe_rdq_handle(struct mlxsw_pci *mlxsw_pci,
 				     u16 consumer_counter_limit,
 				     enum mlxsw_pci_cqe_v cqe_v, char *cqe)
 {
+	struct mlxsw_pci_rx_pkt_info rx_pkt_info = {};
 	struct pci_dev *pdev = mlxsw_pci->pdev;
 	struct page *pages[MLXSW_PCI_WQE_SG_ENTRIES];
 	struct mlxsw_pci_queue_elem_info *elem_info;
@@ -773,6 +809,11 @@  static void mlxsw_pci_cqe_rdq_handle(struct mlxsw_pci *mlxsw_pci,
 		rx_info.local_port = mlxsw_pci_cqe_system_port_get(cqe);
 	}
 
+	err = mlxsw_pci_rx_pkt_info_init(q->pci, elem_info, byte_count,
+					 &rx_pkt_info);
+	if (err)
+		goto out;
+
 	err = mlxsw_pci_elem_info_pages_ref_store(q, elem_info, byte_count,
 						  pages, &num_sg_entries);
 	if (err)
diff --git a/drivers/net/ethernet/mellanox/mlxsw/pci.h b/drivers/net/ethernet/mellanox/mlxsw/pci.h
index cacc2f9fa1d4..74677feacbb5 100644
--- a/drivers/net/ethernet/mellanox/mlxsw/pci.h
+++ b/drivers/net/ethernet/mellanox/mlxsw/pci.h
@@ -11,11 +11,19 @@ 
 #define PCI_DEVICE_ID_MELLANOX_SPECTRUM3	0xcf70
 #define PCI_DEVICE_ID_MELLANOX_SPECTRUM4	0xcf80
 
+#define MLXSW_PCI_WQE_SG_ENTRIES	3
+
 #if IS_ENABLED(CONFIG_MLXSW_PCI)
 
 int mlxsw_pci_driver_register(struct pci_driver *pci_driver);
 void mlxsw_pci_driver_unregister(struct pci_driver *pci_driver);
 
+struct mlxsw_pci_rx_pkt_info {
+	struct page *pages[MLXSW_PCI_WQE_SG_ENTRIES];
+	unsigned int sg_entries_size[MLXSW_PCI_WQE_SG_ENTRIES];
+	u8 num_sg_entries;
+};
+
 #else
 
 static inline int
diff --git a/drivers/net/ethernet/mellanox/mlxsw/pci_hw.h b/drivers/net/ethernet/mellanox/mlxsw/pci_hw.h
index 6bed495dcf0f..83d25f926287 100644
--- a/drivers/net/ethernet/mellanox/mlxsw/pci_hw.h
+++ b/drivers/net/ethernet/mellanox/mlxsw/pci_hw.h
@@ -64,7 +64,6 @@ 
 #define MLXSW_PCI_EQE_COUNT	(MLXSW_PCI_AQ_SIZE / MLXSW_PCI_EQE_SIZE)
 #define MLXSW_PCI_EQE_UPDATE_COUNT	0x80
 
-#define MLXSW_PCI_WQE_SG_ENTRIES	3
 #define MLXSW_PCI_WQE_TYPE_ETHERNET	0xA
 
 /* pci_wqe_c