mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: Vlad Banea <montrealtango@gmail.com>
To: netdev@vger.kernel.org
Cc: hkallweit1@gmail.com, javen_xu@realsil.com.cn,
	nic_swsd@realtek.com, andrew+netdev@lunn.ch, davem@davemloft.net,
	edumazet@google.com, kuba@kernel.org, pabeni@redhat.com,
	linux-kernel@vger.kernel.org
Subject: [RFC net-next 2/5] r8169: describe the vector-map interrupt layout per chip
Date: Wed, 11 Nov 2026 17:01:11 -0500	[thread overview]
Message-ID: <20261111220114.3863505-3-montrealtango@gmail.com> (raw)
In-Reply-To: <20261111220114.3863505-1-montrealtango@gmail.com>

The vector-map interrupt model hard-codes the RTL8127A's MSI-X layout.
Other chips put the TX and link change vectors elsewhere, so move the
layout into a per-chip struct rtl_vec_map.

No functional change.

Signed-off-by: Vlad Banea <montrealtango@gmail.com>
---
 drivers/net/ethernet/realtek/r8169_main.c | 79 ++++++++++++++---------
 1 file changed, 48 insertions(+), 31 deletions(-)

diff --git a/drivers/net/ethernet/realtek/r8169_main.c b/drivers/net/ethernet/realtek/r8169_main.c
index 6bd137358d1f..a77bbedc8c02 100644
--- a/drivers/net/ethernet/realtek/r8169_main.c
+++ b/drivers/net/ethernet/realtek/r8169_main.c
@@ -81,8 +81,6 @@
 #define R8169_MAX_RX_QUEUES	8
 #define R8169_DEFAULT_RX_QUEUES	1
 #define R8169_MAX_TX_QUEUES	1
-#define R8127_MAX_NUM_IRQVEC	32
-#define R8127_MIN_NUM_IRQVEC	30
 #define R8169_IRQ_DEFAULT	1
 #define RTL_RSS_KEY_SIZE	40
 #define RSS_CPU_NUM_MASK	GENMASK(18, 16)
@@ -489,7 +487,6 @@ enum rtl8125_registers {
 	IMR_SET_VEC_MAP_REG	= 0x0d0c,
 };
 
-#define MSIX_ID_VEC_MAP_LINKCHG	29
 #define LEDSEL_MASK_8125	0x23f
 
 #define RX_VLAN_INNER_8125	BIT(22)
@@ -623,9 +620,6 @@ enum rtl_register_content {
 
 	/* magic enable v2 */
 	MagicPacket_v2	= (1 << 16),	/* Wake up when receives a Magic Packet */
-#define	ISRIMR_LINKCHG	BIT(29)
-#define	ISRIMR_TOK_Q0	BIT(8)
-#define	ISRIMR_ROK_Q0	BIT(0)
 #define RTL_DESC_TYPE_CTRL		0xd8
 #define RSS_KEY_REG			0x4600
 #define RSS_INDIRECTION_TBL_REG		0x4700
@@ -843,6 +837,23 @@ enum rtl_sfp_mode {
 	RTL_SFP_8127_ATF,
 };
 
+/* Vector-map MSI-X layout. RX queue N uses vector N; a source's bit in
+ * the vector-map IMR/ISR registers is its vector number.
+ */
+struct rtl_vec_map {
+	u8 tx;		/* TX completion */
+	u8 linkchg;	/* link change */
+	u8 min_nvecs;	/* vectors that must be allocated */
+	u8 max_nvecs;
+};
+
+static const struct rtl_vec_map rtl_vec_map_8127 = {
+	.tx		= 8,
+	.linkchg	= 29,
+	.min_nvecs	= 30,
+	.max_nvecs	= 32,
+};
+
 struct rtl8169_rss_data {
 	u8 rss_key[RTL_RSS_KEY_SIZE];
 	u8 rss_indir_tbl[RTL_MAX_INDIRECTION_TABLE_ENTRIES];
@@ -871,6 +882,7 @@ struct rtl8169_private {
 	unsigned int hw_supp_num_rx_queues;
 	struct rtl8169_rss_data *rss_data;
 	unsigned int irq_nvecs;
+	const struct rtl_vec_map *vec_map;	/* NULL: single vector only */
 	enum rx_desc_type init_rx_desc_type;
 	struct clk *clk;
 	int speed;
@@ -4755,7 +4767,7 @@ static void rtl8169_napi_disable(struct rtl8169_private *tp)
 	if (tp->irq_nvecs > 1) {
 		for (int i = 0; i < tp->num_rx_rings; i++)
 			napi_disable(&tp->rtl8169_napi[i]);
-		napi_disable(&tp->rtl8169_napi[R8169_MAX_RX_QUEUES]);
+		napi_disable(&tp->rtl8169_napi[tp->vec_map->tx]);
 	} else {
 		napi_disable(&tp->rtl8169_napi[0]);
 	}
@@ -4766,7 +4778,7 @@ static void rtl8169_napi_enable(struct rtl8169_private *tp)
 	if (tp->irq_nvecs > 1) {
 		for (int i = 0; i < tp->num_rx_rings; i++)
 			napi_enable(&tp->rtl8169_napi[i]);
-		napi_enable(&tp->rtl8169_napi[R8169_MAX_RX_QUEUES]);
+		napi_enable(&tp->rtl8169_napi[tp->vec_map->tx]);
 	} else {
 		napi_enable(&tp->rtl8169_napi[0]);
 	}
@@ -5535,9 +5547,9 @@ static void rtl8169_free_one_irq(struct rtl8169_private *tp, int i)
 	napi = &tp->rtl8169_napi[i];
 
 	if (tp->irq_nvecs > 1) {
-		if (i < tp->num_rx_rings || i == R8169_MAX_RX_QUEUES)
+		if (i < tp->num_rx_rings || i == tp->vec_map->tx)
 			free_irq(irq, napi);
-		else if (i == MSIX_ID_VEC_MAP_LINKCHG)
+		else if (i == tp->vec_map->linkchg)
 			free_irq(irq, tp);
 	} else {
 		free_irq(irq, napi);
@@ -5591,7 +5603,7 @@ static irqreturn_t rtl8169_interrupt_other(int irq, void *dev_instance)
 {
 	struct rtl8169_private *tp = dev_instance;
 
-	rtl8169_clear_hw_isr(tp, MSIX_ID_VEC_MAP_LINKCHG);
+	rtl8169_clear_hw_isr(tp, tp->vec_map->linkchg);
 	if (tp->phydev)
 		phy_mac_interrupt(tp->phydev);
 	else if (tp->sfp_mode)
@@ -5615,11 +5627,11 @@ static int rtl8169_request_irq(struct rtl8169_private *tp)
 		irq = pci_irq_vector(pdev, i);
 
 		if (tp->irq_nvecs > 1) {
-			/* RX: 0~7, TX: 8*/
-			if (i < tp->num_rx_rings || i == R8169_MAX_RX_QUEUES)
+			/* RX queue N on vector N, TX and link at vec_map */
+			if (i < tp->num_rx_rings || i == tp->vec_map->tx)
 				rc = request_irq(irq, rtl8169_interrupt_msix,
 						 irqflags, dev->name, napi);
-			else if (i == MSIX_ID_VEC_MAP_LINKCHG)
+			else if (i == tp->vec_map->linkchg)
 				rc = request_irq(irq, rtl8169_interrupt_other,
 						 irqflags, dev->name, tp);
 			else
@@ -5805,7 +5817,7 @@ static void rtl8169_netpoll(struct net_device *dev)
 	if (tp->irq_nvecs > 1) {
 		for (int i = 0; i < tp->num_rx_rings; i++)
 			rtl8169_interrupt_msix(0, &tp->rtl8169_napi[i]);
-		rtl8169_interrupt_msix(0, &tp->rtl8169_napi[R8169_MAX_RX_QUEUES]);
+		rtl8169_interrupt_msix(0, &tp->rtl8169_napi[tp->vec_map->tx]);
 	} else {
 		rtl8169_interrupt(0, &tp->rtl8169_napi[0]);
 	}
@@ -6034,7 +6046,7 @@ static void r8169_free_napi(struct rtl8169_private *tp)
 	if (tp->irq_nvecs > 1) {
 		for (int i = 0; i < tp->num_rx_rings; i++)
 			netif_napi_del(&tp->rtl8169_napi[i]);
-		netif_napi_del(&tp->rtl8169_napi[R8169_MAX_RX_QUEUES]);
+		netif_napi_del(&tp->rtl8169_napi[tp->vec_map->tx]);
 	} else {
 		netif_napi_del(&tp->rtl8169_napi[0]);
 	}
@@ -6091,9 +6103,9 @@ static const struct net_device_ops rtl_netdev_ops = {
 static void rtl_set_irq_mask(struct rtl8169_private *tp)
 {
 	if (tp->irq_nvecs > 1) {
-		tp->irq_mask = ISRIMR_LINKCHG | ISRIMR_TOK_Q0;
+		tp->irq_mask = BIT(tp->vec_map->linkchg) | BIT(tp->vec_map->tx);
 		for (int i = 0; i < tp->num_rx_rings; i++)
-			tp->irq_mask |= ISRIMR_ROK_Q0 << i;
+			tp->irq_mask |= BIT(i);
 	} else {
 		tp->irq_mask = RxOK | RxErr | TxOK | TxErr | LinkChg;
 
@@ -6102,18 +6114,24 @@ static void rtl_set_irq_mask(struct rtl8169_private *tp)
 	}
 }
 
+static const struct rtl_vec_map *rtl_get_vec_map(struct rtl8169_private *tp)
+{
+	switch (tp->mac_version) {
+	case RTL_GIGA_MAC_VER_80:
+		return &rtl_vec_map_8127;
+	default:
+		return NULL;
+	}
+}
+
 static int get_max_irq_nvecs(struct rtl8169_private *tp)
 {
-	if (tp->mac_version == RTL_GIGA_MAC_VER_80)
-		return R8127_MAX_NUM_IRQVEC;
-	return R8169_IRQ_DEFAULT;
+	return tp->vec_map ? tp->vec_map->max_nvecs : R8169_IRQ_DEFAULT;
 }
 
 static int get_min_irq_nvecs(struct rtl8169_private *tp)
 {
-	if (tp->mac_version == RTL_GIGA_MAC_VER_80)
-		return R8127_MIN_NUM_IRQVEC;
-	return R8169_IRQ_DEFAULT;
+	return tp->vec_map ? tp->vec_map->min_nvecs : R8169_IRQ_DEFAULT;
 }
 
 static void rtl8169_set_rx_ring_num(struct rtl8169_private *tp)
@@ -6727,10 +6745,8 @@ static int rtl8169_poll_msix_tx(struct napi_struct *napi, int budget)
 	return 0;
 }
 
-/* RTL8127 MSI-X vector layout:
- * Vectors 0 .. (MAX_RXQ - 1)			: Rx Queues
- * Vectors MAX_RXQ .. (MAX_RXQ + MAX_TXQ - 1)	: Tx Queues
- * NAPI is only allocated for data path
+/* Vector-map MSI-X: RX queue N on vector N, TX and link change on the
+ * chip's vec_map vectors. NAPI is only allocated for the data path.
  */
 static void r8169_init_napi(struct rtl8169_private *tp)
 {
@@ -6744,10 +6760,10 @@ static void r8169_init_napi(struct rtl8169_private *tp)
 					   pci_irq_vector(tp->pci_dev, i));
 		}
 		netif_napi_add_tx(tp->dev,
-				  &tp->rtl8169_napi[R8169_MAX_RX_QUEUES],
+				  &tp->rtl8169_napi[tp->vec_map->tx],
 				  rtl8169_poll_msix_tx);
-		netif_napi_set_irq(&tp->rtl8169_napi[R8169_MAX_RX_QUEUES],
-				   pci_irq_vector(tp->pci_dev, R8169_MAX_RX_QUEUES));
+		netif_napi_set_irq(&tp->rtl8169_napi[tp->vec_map->tx],
+				   pci_irq_vector(tp->pci_dev, tp->vec_map->tx));
 	} else {
 		netif_napi_add(tp->dev, &tp->rtl8169_napi[0], rtl8169_poll);
 		netif_napi_set_irq(&tp->rtl8169_napi[0],
@@ -6913,6 +6929,7 @@ static int rtl_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
 	rtl_hw_reset(tp);
 
 	rtl_setup_rx_params(tp);
+	tp->vec_map = rtl_get_vec_map(tp);
 
 	rc = rtl_alloc_irq(tp);
 	if (rc < 0)
-- 
2.53.0


  parent reply	other threads:[~2026-11-11 22:01 UTC|newest]

Thread overview: 6+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-11-11 22:01 [RFC net-next 0/5] r8169: RSS for the RTL8125B Vlad Banea
2026-11-11 22:01 ` [RFC net-next 1/5] r8169: recheck the TX descriptor after a vector-map interrupt Vlad Banea
2026-11-11 22:01 ` Vlad Banea [this message]
2026-11-11 22:01 ` [RFC net-next 3/5] r8169: make the RSS hash types and descriptor type per chip Vlad Banea
2026-11-11 22:01 ` [RFC net-next 4/5] r8169: add the type 3 RX descriptor Vlad Banea
2026-11-11 22:01 ` [RFC net-next 5/5] r8169: enable RSS on the RTL8125B Vlad Banea

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20261111220114.3863505-3-montrealtango@gmail.com \
    --to=montrealtango@gmail.com \
    --cc=andrew+netdev@lunn.ch \
    --cc=davem@davemloft.net \
    --cc=edumazet@google.com \
    --cc=hkallweit1@gmail.com \
    --cc=javen_xu@realsil.com.cn \
    --cc=kuba@kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=netdev@vger.kernel.org \
    --cc=nic_swsd@realtek.com \
    --cc=pabeni@redhat.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®