Skip to content

Commit d4c13ab

Browse files
Vivek Beheraanguy11
authored andcommitted
igb: Fix trigger of incorrect irq in igb_xsk_wakeup
The current implementation in the igb_xsk_wakeup expects the Rx and Tx queues to share the same irq. This would lead to triggering of incorrect irq in split irq configuration. This patch addresses this issue which could impact environments with 2 active cpu cores or when the number of queues is reduced to 2 or less cat /proc/interrupts | grep eno2 167: 0 0 0 0 IR-PCI-MSIX-0000:08:00.0 0-edge eno2 168: 0 0 0 0 IR-PCI-MSIX-0000:08:00.0 1-edge eno2-rx-0 169: 0 0 0 0 IR-PCI-MSIX-0000:08:00.0 2-edge eno2-rx-1 170: 0 0 0 0 IR-PCI-MSIX-0000:08:00.0 3-edge eno2-tx-0 171: 0 0 0 0 IR-PCI-MSIX-0000:08:00.0 4-edge eno2-tx-1 Furthermore it uses the flags input argument to trigger either rx, tx or both rx and tx irqs as specified in the ndo_xsk_wakeup api documentation Fixes: 80f6ccf ("igb: Introduce XSK data structures and helpers") Signed-off-by: Vivek Behera <vivek.behera@siemens.com> Reviewed-by: Aleksandr Loktionov <aleksandr.loktionov@intel.com> Suggested-by: Maciej Fijalkowski <maciej.fijalkowski@intel.com> Acked-by: Maciej Fijalkowski <maciej.fijalkowski@intel.com> Tested-by: Saritha Sanigani <sarithax.sanigani@intel.com> (A Contingent Worker at Intel) Signed-off-by: Tony Nguyen <anthony.l.nguyen@intel.com>
1 parent b848521 commit d4c13ab

1 file changed

Lines changed: 30 additions & 8 deletions

File tree

drivers/net/ethernet/intel/igb/igb_xsk.c

Lines changed: 30 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -524,6 +524,16 @@ bool igb_xmit_zc(struct igb_ring *tx_ring, struct xsk_buff_pool *xsk_pool)
524524
return nb_pkts < budget;
525525
}
526526

527+
static u32 igb_sw_irq_prep(struct igb_q_vector *q_vector)
528+
{
529+
u32 eics = 0;
530+
531+
if (!napi_if_scheduled_mark_missed(&q_vector->napi))
532+
eics = q_vector->eims_value;
533+
534+
return eics;
535+
}
536+
527537
int igb_xsk_wakeup(struct net_device *dev, u32 qid, u32 flags)
528538
{
529539
struct igb_adapter *adapter = netdev_priv(dev);
@@ -542,20 +552,32 @@ int igb_xsk_wakeup(struct net_device *dev, u32 qid, u32 flags)
542552

543553
ring = adapter->tx_ring[qid];
544554

545-
if (test_bit(IGB_RING_FLAG_TX_DISABLED, &ring->flags))
546-
return -ENETDOWN;
547-
548555
if (!READ_ONCE(ring->xsk_pool))
549556
return -EINVAL;
550557

551-
if (!napi_if_scheduled_mark_missed(&ring->q_vector->napi)) {
558+
if (flags & XDP_WAKEUP_TX) {
559+
if (test_bit(IGB_RING_FLAG_TX_DISABLED, &ring->flags))
560+
return -ENETDOWN;
561+
562+
eics |= igb_sw_irq_prep(ring->q_vector);
563+
}
564+
565+
if (flags & XDP_WAKEUP_RX) {
566+
/* If IGB_FLAG_QUEUE_PAIRS is active, the q_vector
567+
* and NAPI is shared between RX and TX.
568+
* If NAPI is already running it would be marked as missed
569+
* from the TX path, making this RX call a NOP
570+
*/
571+
ring = adapter->rx_ring[qid];
572+
eics |= igb_sw_irq_prep(ring->q_vector);
573+
}
574+
575+
if (eics) {
552576
/* Cause software interrupt */
553-
if (adapter->flags & IGB_FLAG_HAS_MSIX) {
554-
eics |= ring->q_vector->eims_value;
577+
if (adapter->flags & IGB_FLAG_HAS_MSIX)
555578
wr32(E1000_EICS, eics);
556-
} else {
579+
else
557580
wr32(E1000_ICS, E1000_ICS_RXDMT0);
558-
}
559581
}
560582

561583
return 0;

0 commit comments

Comments
 (0)