net/bnx2x: fix DMAE timeout

In some cases, DPDK application may send packets
while PMD is going through load or unload flow.
This causes firmware to access invalid/unallocated
memory to process transmit buffer. Which results in
error on PCI bus and chip further blocks access to host,
causing a DMAE timeout.

Fix this issue by installing dummy empty transmit and receive
handlers at the beginning of unload path (rte_eth_dev_stop())
and install actual transmit and receive handlers after successful
load of the PMD port (rte_eth_dev_start()). This way, application
won't be able to send packets while device is going through
load/unload flow.

Fixes: 540a211084a7 ("bnx2x: driver core")
Cc: stable@dpdk.org

Signed-off-by: Shahed Shaikh <shshaikh@marvell.com>
This commit is contained in:
Shahed Shaikh 2019-04-11 18:47:40 -07:00 committed by Ferruh Yigit
parent 8bd31421c5
commit e166e0db8c
3 changed files with 22 additions and 11 deletions

View File

@ -213,6 +213,7 @@ bnx2x_dev_configure(struct rte_eth_dev *dev)
return -ENXIO;
}
bnx2x_dev_rxtx_init_dummy(dev);
return 0;
}
@ -242,11 +243,7 @@ bnx2x_dev_start(struct rte_eth_dev *dev)
PMD_DRV_LOG(ERR, sc, "rte_intr_enable failed");
}
ret = bnx2x_dev_rx_init(dev);
if (ret != 0) {
PMD_DRV_LOG(DEBUG, sc, "bnx2x_dev_rx_init returned error code");
return -3;
}
bnx2x_dev_rxtx_init(dev);
bnx2x_print_device_info(sc);
@ -261,6 +258,8 @@ bnx2x_dev_stop(struct rte_eth_dev *dev)
PMD_INIT_FUNC_TRACE(sc);
bnx2x_dev_rxtx_init_dummy(dev);
if (IS_PF(sc)) {
rte_intr_disable(&sc->pci_dev->intr_handle);
rte_intr_callback_unregister(&sc->pci_dev->intr_handle,

View File

@ -311,7 +311,6 @@ bnx2x_dev_tx_queue_setup(struct rte_eth_dev *dev,
txq->tx_bd_tail = 0;
txq->tx_bd_head = 0;
txq->nb_tx_avail = txq->nb_tx_desc;
dev->tx_pkt_burst = bnx2x_xmit_pkts;
dev->data->tx_queues[queue_idx] = txq;
if (!sc->tx_queues) sc->tx_queues = dev->data->tx_queues;
@ -441,12 +440,24 @@ next_rx:
return nb_rx;
}
int
bnx2x_dev_rx_init(struct rte_eth_dev *dev)
static uint16_t
bnx2x_rxtx_pkts_dummy(__rte_unused void *p_rxq,
__rte_unused struct rte_mbuf **rx_pkts,
__rte_unused uint16_t nb_pkts)
{
return 0;
}
void bnx2x_dev_rxtx_init_dummy(struct rte_eth_dev *dev)
{
dev->rx_pkt_burst = bnx2x_rxtx_pkts_dummy;
dev->tx_pkt_burst = bnx2x_rxtx_pkts_dummy;
}
void bnx2x_dev_rxtx_init(struct rte_eth_dev *dev)
{
dev->rx_pkt_burst = bnx2x_recv_pkts;
return 0;
dev->tx_pkt_burst = bnx2x_xmit_pkts;
}
void

View File

@ -74,7 +74,8 @@ int bnx2x_dev_tx_queue_setup(struct rte_eth_dev *dev, uint16_t tx_queue_id,
void bnx2x_dev_rx_queue_release(void *rxq);
void bnx2x_dev_tx_queue_release(void *txq);
int bnx2x_dev_rx_init(struct rte_eth_dev *dev);
void bnx2x_dev_rxtx_init(struct rte_eth_dev *dev);
void bnx2x_dev_rxtx_init_dummy(struct rte_eth_dev *dev);
void bnx2x_dev_clear_queues(struct rte_eth_dev *dev);
#endif /* _BNX2X_RXTX_H_ */