From: Jiawen Wu Date: Mon, 19 Oct 2020 08:53:46 +0000 (+0800) Subject: net/txgbe: add Rx and Tx data path start and stop X-Git-Url: http://git.droids-corp.org/?a=commitdiff_plain;h=127a1abe6cbe7dc9b6f21a3e7d25da72a000868a;p=dpdk.git net/txgbe: add Rx and Tx data path start and stop Add receive and transmit data path start and stop. Signed-off-by: Jiawen Wu Reviewed-by: Ferruh Yigit --- diff --git a/drivers/net/txgbe/base/txgbe_hw.c b/drivers/net/txgbe/base/txgbe_hw.c index 1b40bfa2f8..9023ff1980 100644 --- a/drivers/net/txgbe/base/txgbe_hw.c +++ b/drivers/net/txgbe/base/txgbe_hw.c @@ -549,6 +549,113 @@ s32 txgbe_update_mc_addr_list(struct txgbe_hw *hw, u8 *mc_addr_list, return 0; } +/** + * txgbe_disable_sec_rx_path - Stops the receive data path + * @hw: pointer to hardware structure + * + * Stops the receive data path and waits for the HW to internally empty + * the Rx security block + **/ +s32 txgbe_disable_sec_rx_path(struct txgbe_hw *hw) +{ +#define TXGBE_MAX_SECRX_POLL 4000 + + int i; + u32 secrxreg; + + DEBUGFUNC("txgbe_disable_sec_rx_path"); + + secrxreg = rd32(hw, TXGBE_SECRXCTL); + secrxreg |= TXGBE_SECRXCTL_XDSA; + wr32(hw, TXGBE_SECRXCTL, secrxreg); + for (i = 0; i < TXGBE_MAX_SECRX_POLL; i++) { + secrxreg = rd32(hw, TXGBE_SECRXSTAT); + if (!(secrxreg & TXGBE_SECRXSTAT_RDY)) + /* Use interrupt-safe sleep just in case */ + usec_delay(10); + else + break; + } + + /* For informational purposes only */ + if (i >= TXGBE_MAX_SECRX_POLL) + DEBUGOUT("Rx unit being enabled before security " + "path fully disabled. Continuing with init.\n"); + + return 0; +} + +/** + * txgbe_enable_sec_rx_path - Enables the receive data path + * @hw: pointer to hardware structure + * + * Enables the receive data path. + **/ +s32 txgbe_enable_sec_rx_path(struct txgbe_hw *hw) +{ + u32 secrxreg; + + DEBUGFUNC("txgbe_enable_sec_rx_path"); + + secrxreg = rd32(hw, TXGBE_SECRXCTL); + secrxreg &= ~TXGBE_SECRXCTL_XDSA; + wr32(hw, TXGBE_SECRXCTL, secrxreg); + txgbe_flush(hw); + + return 0; +} + +/** + * txgbe_disable_sec_tx_path - Stops the transmit data path + * @hw: pointer to hardware structure + * + * Stops the transmit data path and waits for the HW to internally empty + * the Tx security block + **/ +int txgbe_disable_sec_tx_path(struct txgbe_hw *hw) +{ +#define TXGBE_MAX_SECTX_POLL 40 + + int i; + u32 sectxreg; + + sectxreg = rd32(hw, TXGBE_SECTXCTL); + sectxreg |= TXGBE_SECTXCTL_XDSA; + wr32(hw, TXGBE_SECTXCTL, sectxreg); + for (i = 0; i < TXGBE_MAX_SECTX_POLL; i++) { + sectxreg = rd32(hw, TXGBE_SECTXSTAT); + if (sectxreg & TXGBE_SECTXSTAT_RDY) + break; + /* Use interrupt-safe sleep just in case */ + usec_delay(1000); + } + + /* For informational purposes only */ + if (i >= TXGBE_MAX_SECTX_POLL) + PMD_DRV_LOG(DEBUG, "Tx unit being enabled before security " + "path fully disabled. Continuing with init."); + + return 0; +} + +/** + * txgbe_enable_sec_tx_path - Enables the transmit data path + * @hw: pointer to hardware structure + * + * Enables the transmit data path. + **/ +int txgbe_enable_sec_tx_path(struct txgbe_hw *hw) +{ + uint32_t sectxreg; + + sectxreg = rd32(hw, TXGBE_SECTXCTL); + sectxreg &= ~TXGBE_SECTXCTL_XDSA; + wr32(hw, TXGBE_SECTXCTL, sectxreg); + txgbe_flush(hw); + + return 0; +} + /** * txgbe_get_san_mac_addr_offset - Get SAN MAC address offset from the EEPROM * @hw: pointer to hardware structure @@ -1283,9 +1390,15 @@ s32 txgbe_init_ops_pf(struct txgbe_hw *hw) /* MAC */ mac->init_hw = txgbe_init_hw; mac->start_hw = txgbe_start_hw_raptor; + mac->enable_rx_dma = txgbe_enable_rx_dma_raptor; mac->get_mac_addr = txgbe_get_mac_addr; mac->stop_hw = txgbe_stop_hw; mac->reset_hw = txgbe_reset_hw; + + mac->disable_sec_rx_path = txgbe_disable_sec_rx_path; + mac->enable_sec_rx_path = txgbe_enable_sec_rx_path; + mac->disable_sec_tx_path = txgbe_disable_sec_tx_path; + mac->enable_sec_tx_path = txgbe_enable_sec_tx_path; mac->get_san_mac_addr = txgbe_get_san_mac_addr; mac->set_san_mac_addr = txgbe_set_san_mac_addr; mac->get_device_caps = txgbe_get_device_caps; @@ -2123,6 +2236,35 @@ out: return err; } +/** + * txgbe_enable_rx_dma_raptor - Enable the Rx DMA unit + * @hw: pointer to hardware structure + * @regval: register value to write to RXCTRL + * + * Enables the Rx DMA unit + **/ +s32 txgbe_enable_rx_dma_raptor(struct txgbe_hw *hw, u32 regval) +{ + DEBUGFUNC("txgbe_enable_rx_dma_raptor"); + + /* + * Workaround silicon errata when enabling the Rx datapath. + * If traffic is incoming before we enable the Rx unit, it could hang + * the Rx DMA unit. Therefore, make sure the security engine is + * completely disabled prior to enabling the Rx unit. + */ + + hw->mac.disable_sec_rx_path(hw); + + if (regval & TXGBE_PBRXCTL_ENA) + txgbe_enable_rx(hw); + else + txgbe_disable_rx(hw); + + hw->mac.enable_sec_rx_path(hw); + + return 0; +} /** * txgbe_verify_lesm_fw_enabled_raptor - Checks LESM FW module state. diff --git a/drivers/net/txgbe/base/txgbe_hw.h b/drivers/net/txgbe/base/txgbe_hw.h index f0d3d5b972..78b4dd2b5c 100644 --- a/drivers/net/txgbe/base/txgbe_hw.h +++ b/drivers/net/txgbe/base/txgbe_hw.h @@ -22,6 +22,10 @@ s32 txgbe_init_rx_addrs(struct txgbe_hw *hw); s32 txgbe_update_mc_addr_list(struct txgbe_hw *hw, u8 *mc_addr_list, u32 mc_addr_count, txgbe_mc_addr_itr func, bool clear); +s32 txgbe_disable_sec_rx_path(struct txgbe_hw *hw); +s32 txgbe_enable_sec_rx_path(struct txgbe_hw *hw); +s32 txgbe_disable_sec_tx_path(struct txgbe_hw *hw); +s32 txgbe_enable_sec_tx_path(struct txgbe_hw *hw); s32 txgbe_validate_mac_addr(u8 *mac_addr); @@ -67,5 +71,6 @@ void txgbe_init_mac_link_ops(struct txgbe_hw *hw); s32 txgbe_reset_hw(struct txgbe_hw *hw); s32 txgbe_start_hw_raptor(struct txgbe_hw *hw); s32 txgbe_init_phy_raptor(struct txgbe_hw *hw); +s32 txgbe_enable_rx_dma_raptor(struct txgbe_hw *hw, u32 regval); bool txgbe_verify_lesm_fw_enabled_raptor(struct txgbe_hw *hw); #endif /* _TXGBE_HW_H_ */