Commit 434c975a authored by Michael Chan's avatar Michael Chan Committed by David S. Miller

bnxt_en: Optimize doorbell write operations for newer chips.

Older chips require the doorbells to be written twice, but newer chips
do not.  Add a new common function bnxt_db_write() to write all
doorbells appropriately depending on the chip.  Eliminating the extra
doorbell on newer chips has a significant performance improvement
on pktgen.
Signed-off-by: default avatarMichael Chan <michael.chan@broadcom.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 3284f9e1
...@@ -463,8 +463,7 @@ static netdev_tx_t bnxt_start_xmit(struct sk_buff *skb, struct net_device *dev) ...@@ -463,8 +463,7 @@ static netdev_tx_t bnxt_start_xmit(struct sk_buff *skb, struct net_device *dev)
prod = NEXT_TX(prod); prod = NEXT_TX(prod);
txr->tx_prod = prod; txr->tx_prod = prod;
writel(DB_KEY_TX | prod, txr->tx_doorbell); bnxt_db_write(bp, txr->tx_doorbell, DB_KEY_TX | prod);
writel(DB_KEY_TX | prod, txr->tx_doorbell);
tx_done: tx_done:
...@@ -1779,8 +1778,7 @@ static int bnxt_poll_work(struct bnxt *bp, struct bnxt_napi *bnapi, int budget) ...@@ -1779,8 +1778,7 @@ static int bnxt_poll_work(struct bnxt *bp, struct bnxt_napi *bnapi, int budget)
/* Sync BD data before updating doorbell */ /* Sync BD data before updating doorbell */
wmb(); wmb();
writel(DB_KEY_TX | prod, db); bnxt_db_write(bp, db, DB_KEY_TX | prod);
writel(DB_KEY_TX | prod, db);
} }
cpr->cp_raw_cons = raw_cons; cpr->cp_raw_cons = raw_cons;
...@@ -1796,14 +1794,10 @@ static int bnxt_poll_work(struct bnxt *bp, struct bnxt_napi *bnapi, int budget) ...@@ -1796,14 +1794,10 @@ static int bnxt_poll_work(struct bnxt *bp, struct bnxt_napi *bnapi, int budget)
if (event & BNXT_RX_EVENT) { if (event & BNXT_RX_EVENT) {
struct bnxt_rx_ring_info *rxr = bnapi->rx_ring; struct bnxt_rx_ring_info *rxr = bnapi->rx_ring;
writel(DB_KEY_RX | rxr->rx_prod, rxr->rx_doorbell); bnxt_db_write(bp, rxr->rx_doorbell, DB_KEY_RX | rxr->rx_prod);
writel(DB_KEY_RX | rxr->rx_prod, rxr->rx_doorbell); if (event & BNXT_AGG_EVENT)
if (event & BNXT_AGG_EVENT) { bnxt_db_write(bp, rxr->rx_agg_doorbell,
writel(DB_KEY_RX | rxr->rx_agg_prod, DB_KEY_RX | rxr->rx_agg_prod);
rxr->rx_agg_doorbell);
writel(DB_KEY_RX | rxr->rx_agg_prod,
rxr->rx_agg_doorbell);
}
} }
return rx_pkts; return rx_pkts;
} }
...@@ -1863,13 +1857,11 @@ static int bnxt_poll_nitroa0(struct napi_struct *napi, int budget) ...@@ -1863,13 +1857,11 @@ static int bnxt_poll_nitroa0(struct napi_struct *napi, int budget)
cpr->cp_raw_cons = raw_cons; cpr->cp_raw_cons = raw_cons;
BNXT_CP_DB(cpr->cp_doorbell, cpr->cp_raw_cons); BNXT_CP_DB(cpr->cp_doorbell, cpr->cp_raw_cons);
writel(DB_KEY_RX | rxr->rx_prod, rxr->rx_doorbell); bnxt_db_write(bp, rxr->rx_doorbell, DB_KEY_RX | rxr->rx_prod);
writel(DB_KEY_RX | rxr->rx_prod, rxr->rx_doorbell);
if (event & BNXT_AGG_EVENT) { if (event & BNXT_AGG_EVENT)
writel(DB_KEY_RX | rxr->rx_agg_prod, rxr->rx_agg_doorbell); bnxt_db_write(bp, rxr->rx_agg_doorbell,
writel(DB_KEY_RX | rxr->rx_agg_prod, rxr->rx_agg_doorbell); DB_KEY_RX | rxr->rx_agg_prod);
}
if (!bnxt_has_work(bp, cpr) && rx_pkts < budget) { if (!bnxt_has_work(bp, cpr) && rx_pkts < budget) {
napi_complete_done(napi, rx_pkts); napi_complete_done(napi, rx_pkts);
...@@ -7714,6 +7706,8 @@ static int bnxt_init_one(struct pci_dev *pdev, const struct pci_device_id *ent) ...@@ -7714,6 +7706,8 @@ static int bnxt_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
bp->gro_func = bnxt_gro_func_5730x; bp->gro_func = bnxt_gro_func_5730x;
if (BNXT_CHIP_P4_PLUS(bp)) if (BNXT_CHIP_P4_PLUS(bp))
bp->gro_func = bnxt_gro_func_5731x; bp->gro_func = bnxt_gro_func_5731x;
else
bp->flags |= BNXT_FLAG_DOUBLE_DB;
rc = bnxt_hwrm_func_drv_rgtr(bp); rc = bnxt_hwrm_func_drv_rgtr(bp);
if (rc) if (rc)
......
...@@ -1022,6 +1022,7 @@ struct bnxt { ...@@ -1022,6 +1022,7 @@ struct bnxt {
#define BNXT_FLAG_FW_LLDP_AGENT 0x80000 #define BNXT_FLAG_FW_LLDP_AGENT 0x80000
#define BNXT_FLAG_MULTI_HOST 0x100000 #define BNXT_FLAG_MULTI_HOST 0x100000
#define BNXT_FLAG_SHORT_CMD 0x200000 #define BNXT_FLAG_SHORT_CMD 0x200000
#define BNXT_FLAG_DOUBLE_DB 0x400000
#define BNXT_FLAG_CHIP_NITRO_A0 0x1000000 #define BNXT_FLAG_CHIP_NITRO_A0 0x1000000
#define BNXT_FLAG_ALL_CONFIG_FEATS (BNXT_FLAG_TPA | \ #define BNXT_FLAG_ALL_CONFIG_FEATS (BNXT_FLAG_TPA | \
...@@ -1254,6 +1255,14 @@ static inline u32 bnxt_tx_avail(struct bnxt *bp, struct bnxt_tx_ring_info *txr) ...@@ -1254,6 +1255,14 @@ static inline u32 bnxt_tx_avail(struct bnxt *bp, struct bnxt_tx_ring_info *txr)
((txr->tx_prod - txr->tx_cons) & bp->tx_ring_mask); ((txr->tx_prod - txr->tx_cons) & bp->tx_ring_mask);
} }
/* For TX and RX ring doorbells */
static inline void bnxt_db_write(struct bnxt *bp, void __iomem *db, u32 val)
{
writel(val, db);
if (bp->flags & BNXT_FLAG_DOUBLE_DB)
writel(val, db);
}
extern const u16 bnxt_lhint_arr[]; extern const u16 bnxt_lhint_arr[];
int bnxt_alloc_rx_data(struct bnxt *bp, struct bnxt_rx_ring_info *rxr, int bnxt_alloc_rx_data(struct bnxt *bp, struct bnxt_rx_ring_info *rxr,
......
...@@ -2376,8 +2376,7 @@ static int bnxt_run_loopback(struct bnxt *bp) ...@@ -2376,8 +2376,7 @@ static int bnxt_run_loopback(struct bnxt *bp)
/* Sync BD data before updating doorbell */ /* Sync BD data before updating doorbell */
wmb(); wmb();
writel(DB_KEY_TX | txr->tx_prod, txr->tx_doorbell); bnxt_db_write(bp, txr->tx_doorbell, DB_KEY_TX | txr->tx_prod);
writel(DB_KEY_TX | txr->tx_prod, txr->tx_doorbell);
rc = bnxt_poll_loopback(bp, pkt_size); rc = bnxt_poll_loopback(bp, pkt_size);
dma_unmap_single(&bp->pdev->dev, map, pkt_size, PCI_DMA_TODEVICE); dma_unmap_single(&bp->pdev->dev, map, pkt_size, PCI_DMA_TODEVICE);
......
...@@ -63,7 +63,7 @@ void bnxt_tx_int_xdp(struct bnxt *bp, struct bnxt_napi *bnapi, int nr_pkts) ...@@ -63,7 +63,7 @@ void bnxt_tx_int_xdp(struct bnxt *bp, struct bnxt_napi *bnapi, int nr_pkts)
tx_buf = &txr->tx_buf_ring[last_tx_cons]; tx_buf = &txr->tx_buf_ring[last_tx_cons];
rx_prod = tx_buf->rx_prod; rx_prod = tx_buf->rx_prod;
} }
writel(DB_KEY_RX | rx_prod, rxr->rx_doorbell); bnxt_db_write(bp, rxr->rx_doorbell, DB_KEY_RX | rx_prod);
} }
/* returns the following: /* returns the following:
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment