net/i40evf: fix packet loss for X722
[dpdk.git] / drivers / net / i40e / i40e_rxtx_vec_neon.c
index deb185f..da16dfc 100644 (file)
@@ -4,8 +4,9 @@
  */
 
 #include <stdint.h>
-#include <rte_ethdev_driver.h>
+#include <ethdev_driver.h>
 #include <rte_malloc.h>
+#include <rte_vect.h>
 
 #include "base/i40e_prototype.h"
 #include "base/i40e_type.h"
@@ -13,7 +14,6 @@
 #include "i40e_rxtx.h"
 #include "i40e_rxtx_vec_common.h"
 
-#include <arm_neon.h>
 
 #pragma GCC diagnostic ignored "-Wcast-qual"
 
@@ -72,8 +72,9 @@ i40e_rxq_rearm(struct i40e_rx_queue *rxq)
        rx_id = (uint16_t)((rxq->rxrearm_start == 0) ?
                             (rxq->nb_rx_desc - 1) : (rxq->rxrearm_start - 1));
 
+       rte_io_wmb();
        /* Update the tail pointer on the NIC */
-       I40E_PCI_REG_WRITE(rxq->qrx_tail, rx_id);
+       I40E_PCI_REG_WRITE_RELAXED(rxq->qrx_tail, rx_id);
 }
 
 static inline void
@@ -94,16 +95,16 @@ desc_to_olflags_v(struct i40e_rx_queue *rxq, uint64x2_t descs[4],
        const uint32x4_t cksum_mask = {
                        PKT_RX_IP_CKSUM_GOOD | PKT_RX_IP_CKSUM_BAD |
                        PKT_RX_L4_CKSUM_GOOD | PKT_RX_L4_CKSUM_BAD |
-                       PKT_RX_EIP_CKSUM_BAD,
+                       PKT_RX_OUTER_IP_CKSUM_BAD,
                        PKT_RX_IP_CKSUM_GOOD | PKT_RX_IP_CKSUM_BAD |
                        PKT_RX_L4_CKSUM_GOOD | PKT_RX_L4_CKSUM_BAD |
-                       PKT_RX_EIP_CKSUM_BAD,
+                       PKT_RX_OUTER_IP_CKSUM_BAD,
                        PKT_RX_IP_CKSUM_GOOD | PKT_RX_IP_CKSUM_BAD |
                        PKT_RX_L4_CKSUM_GOOD | PKT_RX_L4_CKSUM_BAD |
-                       PKT_RX_EIP_CKSUM_BAD,
+                       PKT_RX_OUTER_IP_CKSUM_BAD,
                        PKT_RX_IP_CKSUM_GOOD | PKT_RX_IP_CKSUM_BAD |
                        PKT_RX_L4_CKSUM_GOOD | PKT_RX_L4_CKSUM_BAD |
-                       PKT_RX_EIP_CKSUM_BAD};
+                       PKT_RX_OUTER_IP_CKSUM_BAD};
 
        /* map rss and vlan type to rss hash and vlan flag */
        const uint8x16_t vlan_flags = {
@@ -123,11 +124,11 @@ desc_to_olflags_v(struct i40e_rx_queue *rxq, uint64x2_t descs[4],
                        PKT_RX_IP_CKSUM_BAD >> 1,
                        (PKT_RX_IP_CKSUM_GOOD | PKT_RX_L4_CKSUM_BAD) >> 1,
                        (PKT_RX_L4_CKSUM_BAD | PKT_RX_IP_CKSUM_BAD) >> 1,
-                       (PKT_RX_IP_CKSUM_GOOD | PKT_RX_EIP_CKSUM_BAD) >> 1,
-                       (PKT_RX_EIP_CKSUM_BAD | PKT_RX_IP_CKSUM_BAD) >> 1,
-                       (PKT_RX_IP_CKSUM_GOOD | PKT_RX_EIP_CKSUM_BAD |
+                       (PKT_RX_IP_CKSUM_GOOD | PKT_RX_OUTER_IP_CKSUM_BAD) >> 1,
+                       (PKT_RX_OUTER_IP_CKSUM_BAD | PKT_RX_IP_CKSUM_BAD) >> 1,
+                       (PKT_RX_IP_CKSUM_GOOD | PKT_RX_OUTER_IP_CKSUM_BAD |
                         PKT_RX_L4_CKSUM_BAD) >> 1,
-                       (PKT_RX_EIP_CKSUM_BAD | PKT_RX_L4_CKSUM_BAD |
+                       (PKT_RX_OUTER_IP_CKSUM_BAD | PKT_RX_L4_CKSUM_BAD |
                         PKT_RX_IP_CKSUM_BAD) >> 1,
                        0, 0, 0, 0, 0, 0, 0, 0};
 
@@ -171,8 +172,8 @@ desc_to_olflags_v(struct i40e_rx_queue *rxq, uint64x2_t descs[4],
 #define I40E_UINT16_BIT (CHAR_BIT * sizeof(uint16_t))
 
 static inline void
-desc_to_ptype_v(uint64x2_t descs[4], struct rte_mbuf **rx_pkts,
-               uint32_t *ptype_tbl)
+desc_to_ptype_v(uint64x2_t descs[4], struct rte_mbuf **__rte_restrict rx_pkts,
+               uint32_t *__rte_restrict ptype_tbl)
 {
        int i;
        uint8_t ptype;
@@ -186,14 +187,16 @@ desc_to_ptype_v(uint64x2_t descs[4], struct rte_mbuf **rx_pkts,
 
 }
 
- /*
+/**
+ * vPMD raw receive routine, only accept(nb_pkts >= RTE_I40E_DESCS_PER_LOOP)
+ *
  * Notice:
  * - nb_pkts < RTE_I40E_DESCS_PER_LOOP, just return no packet
- * - nb_pkts > RTE_I40E_VPMD_RX_BURST, only scan RTE_I40E_VPMD_RX_BURST
- *   numbers of DD bits
+ * - floor align nb_pkts to a RTE_I40E_DESCS_PER_LOOP power-of-two
  */
 static inline uint16_t
-_recv_raw_pkts_vec(struct i40e_rx_queue *rxq, struct rte_mbuf **rx_pkts,
+_recv_raw_pkts_vec(struct i40e_rx_queue *__rte_restrict rxq,
+                  struct rte_mbuf **__rte_restrict rx_pkts,
                   uint16_t nb_pkts, uint8_t *split_packet)
 {
        volatile union i40e_rx_desc *rxdp;
@@ -228,9 +231,6 @@ _recv_raw_pkts_vec(struct i40e_rx_queue *rxq, struct rte_mbuf **rx_pkts,
                0, 0, 0       /* ignore non-length fields */
                };
 
-       /* nb_pkts shall be less equal than RTE_I40E_MAX_RX_BURST */
-       nb_pkts = RTE_MIN(nb_pkts, RTE_I40E_MAX_RX_BURST);
-
        /* nb_pkts has to be floor-aligned to RTE_I40E_DESCS_PER_LOOP */
        nb_pkts = RTE_ALIGN_FLOOR(nb_pkts, RTE_I40E_DESCS_PER_LOOP);
 
@@ -431,21 +431,21 @@ _recv_raw_pkts_vec(struct i40e_rx_queue *rxq, struct rte_mbuf **rx_pkts,
  *   numbers of DD bits
  */
 uint16_t
-i40e_recv_pkts_vec(void *rx_queue, struct rte_mbuf **rx_pkts,
-                  uint16_t nb_pkts)
+i40e_recv_pkts_vec(void *__rte_restrict rx_queue,
+               struct rte_mbuf **__rte_restrict rx_pkts, uint16_t nb_pkts)
 {
        return _recv_raw_pkts_vec(rx_queue, rx_pkts, nb_pkts, NULL);
 }
 
- /* vPMD receive routine that reassembles scattered packets
+/**
+ * vPMD receive routine that reassembles single burst of 32 scattered packets
+ *
  * Notice:
  * - nb_pkts < RTE_I40E_DESCS_PER_LOOP, just return no packet
- * - nb_pkts > RTE_I40E_VPMD_RX_BURST, only scan RTE_I40E_VPMD_RX_BURST
- *   numbers of DD bits
  */
-uint16_t
-i40e_recv_scattered_pkts_vec(void *rx_queue, struct rte_mbuf **rx_pkts,
-                            uint16_t nb_pkts)
+static uint16_t
+i40e_recv_scattered_burst_vec(void *rx_queue, struct rte_mbuf **rx_pkts,
+                             uint16_t nb_pkts)
 {
 
        struct i40e_rx_queue *rxq = rx_queue;
@@ -480,6 +480,32 @@ i40e_recv_scattered_pkts_vec(void *rx_queue, struct rte_mbuf **rx_pkts,
                &split_flags[i]);
 }
 
+/**
+ * vPMD receive routine that reassembles scattered packets.
+ */
+uint16_t
+i40e_recv_scattered_pkts_vec(void *rx_queue, struct rte_mbuf **rx_pkts,
+                            uint16_t nb_pkts)
+{
+       uint16_t retval = 0;
+
+       while (nb_pkts > RTE_I40E_VPMD_RX_BURST) {
+               uint16_t burst;
+
+               burst = i40e_recv_scattered_burst_vec(rx_queue,
+                                                     rx_pkts + retval,
+                                                     RTE_I40E_VPMD_RX_BURST);
+               retval += burst;
+               nb_pkts -= burst;
+               if (burst < RTE_I40E_VPMD_RX_BURST)
+                       return retval;
+       }
+
+       return retval + i40e_recv_scattered_burst_vec(rx_queue,
+                                                     rx_pkts + retval,
+                                                     nb_pkts);
+}
+
 static inline void
 vtx1(volatile struct i40e_tx_desc *txdp,
                struct rte_mbuf *pkt, uint64_t flags)
@@ -493,8 +519,8 @@ vtx1(volatile struct i40e_tx_desc *txdp,
 }
 
 static inline void
-vtx(volatile struct i40e_tx_desc *txdp,
-               struct rte_mbuf **pkt, uint16_t nb_pkts,  uint64_t flags)
+vtx(volatile struct i40e_tx_desc *txdp, struct rte_mbuf **pkt,
+               uint16_t nb_pkts,  uint64_t flags)
 {
        int i;
 
@@ -503,8 +529,8 @@ vtx(volatile struct i40e_tx_desc *txdp,
 }
 
 uint16_t
-i40e_xmit_fixed_burst_vec(void *tx_queue, struct rte_mbuf **tx_pkts,
-                         uint16_t nb_pkts)
+i40e_xmit_fixed_burst_vec(void *__rte_restrict tx_queue,
+       struct rte_mbuf **__rte_restrict tx_pkts, uint16_t nb_pkts)
 {
        struct i40e_tx_queue *txq = (struct i40e_tx_queue *)tx_queue;
        volatile struct i40e_tx_desc *txdp;
@@ -564,30 +590,31 @@ i40e_xmit_fixed_burst_vec(void *tx_queue, struct rte_mbuf **tx_pkts,
 
        txq->tx_tail = tx_id;
 
-       I40E_PCI_REG_WRITE(txq->qtx_tail, txq->tx_tail);
+       rte_io_wmb();
+       I40E_PCI_REG_WRITE_RELAXED(txq->qtx_tail, tx_id);
 
        return nb_pkts;
 }
 
-void __attribute__((cold))
+void __rte_cold
 i40e_rx_queue_release_mbufs_vec(struct i40e_rx_queue *rxq)
 {
        _i40e_rx_queue_release_mbufs_vec(rxq);
 }
 
-int __attribute__((cold))
+int __rte_cold
 i40e_rxq_vec_setup(struct i40e_rx_queue *rxq)
 {
        return i40e_rxq_vec_setup_default(rxq);
 }
 
-int __attribute__((cold))
+int __rte_cold
 i40e_txq_vec_setup(struct i40e_tx_queue __rte_unused *txq)
 {
        return 0;
 }
 
-int __attribute__((cold))
+int __rte_cold
 i40e_rx_vec_dev_conf_condition_check(struct rte_eth_dev *dev)
 {
        return i40e_rx_vec_dev_conf_condition_check_default(dev);