app/testpmd: add timeout in Rx queue flushing
[dpdk.git] / app / test-pmd / testpmd.c
index 38cddca..b7f28e9 100644 (file)
@@ -76,6 +76,9 @@
 #ifdef RTE_LIBRTE_PMD_XENVIRT
 #include <rte_eth_xenvirt.h>
 #endif
+#ifdef RTE_LIBRTE_PDUMP
+#include <rte_pdump.h>
+#endif
 
 #include "testpmd.h"
 
@@ -144,7 +147,6 @@ streamid_t nb_fwd_streams;       /**< Is equal to (nb_ports * nb_rxq). */
 struct fwd_engine * fwd_engines[] = {
        &io_fwd_engine,
        &mac_fwd_engine,
-       &mac_retry_fwd_engine,
        &mac_swap_engine,
        &flow_gen_engine,
        &rx_only_engine,
@@ -159,6 +161,9 @@ struct fwd_engine * fwd_engines[] = {
 
 struct fwd_config cur_fwd_config;
 struct fwd_engine *cur_fwd_eng = &io_fwd_engine; /**< IO mode by default. */
+uint32_t retry_enabled;
+uint32_t burst_tx_delay_time = BURST_TX_WAIT_US;
+uint32_t burst_tx_retry_num = BURST_TX_RETRIES;
 
 uint16_t mbuf_data_size = DEFAULT_MBUF_DATA_SIZE; /**< Mbuf data space size. */
 uint32_t param_total_num_mbufs = 0;  /**< number of mbufs in all pools - if
@@ -267,6 +272,9 @@ uint32_t bypass_timeout = RTE_BYPASS_TMT_OFF;
 
 #endif
 
+/* default period is 1 second */
+static uint64_t timer_period = 1;
+
 /*
  * Ethernet device configuration.
  */
@@ -872,17 +880,35 @@ flush_fwd_rx_queues(void)
        uint16_t  nb_rx;
        uint16_t  i;
        uint8_t   j;
+       uint64_t prev_tsc = 0, diff_tsc, cur_tsc, timer_tsc = 0;
+
+       /* convert to number of cycles */
+       timer_period *= rte_get_timer_hz();
 
        for (j = 0; j < 2; j++) {
                for (rxp = 0; rxp < cur_fwd_config.nb_fwd_ports; rxp++) {
                        for (rxq = 0; rxq < nb_rxq; rxq++) {
                                port_id = fwd_ports_ids[rxp];
+                               /**
+                               * testpmd can stuck in the below do while loop
+                               * if rte_eth_rx_burst() always returns nonzero
+                               * packets. So timer is added to exit this loop
+                               * after 1sec timer expiry.
+                               */
+                               prev_tsc = rte_rdtsc();
                                do {
                                        nb_rx = rte_eth_rx_burst(port_id, rxq,
                                                pkts_burst, MAX_PKT_BURST);
                                        for (i = 0; i < nb_rx; i++)
                                                rte_pktmbuf_free(pkts_burst[i]);
-                               } while (nb_rx > 0);
+
+                                       cur_tsc = rte_rdtsc();
+                                       diff_tsc = cur_tsc - prev_tsc;
+                                       timer_tsc += diff_tsc;
+                               } while ((nb_rx > 0) &&
+                                       (timer_tsc < timer_period));
+                               prev_tsc = cur_tsc;
+                               timer_tsc = 0;
                        }
                }
                rte_delay_ms(10); /* wait 10 milli-seconds before retrying */
@@ -1022,6 +1048,7 @@ start_packet_forwarding(int with_tx_first)
                flush_fwd_rx_queues();
 
        fwd_config_setup();
+       pkt_fwd_config_display(&cur_fwd_config);
        rxtx_config_display();
 
        for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++) {
@@ -1055,8 +1082,11 @@ start_packet_forwarding(int with_tx_first)
                        for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++)
                                (*port_fwd_begin)(fwd_ports_ids[i]);
                }
-               launch_packet_forwarding(run_one_txonly_burst_on_core);
-               rte_eal_mp_wait_lcore();
+               while (with_tx_first--) {
+                       launch_packet_forwarding(
+                                       run_one_txonly_burst_on_core);
+                       rte_eal_mp_wait_lcore();
+               }
                port_fwd_end = tx_only_engine.port_fwd_end;
                if (port_fwd_end != NULL) {
                        for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++)
@@ -1089,10 +1119,6 @@ stop_packet_forwarding(void)
 #endif
        static const char *acc_stats_border = "+++++++++++++++";
 
-       if (all_ports_started() == 0) {
-               printf("Not all ports were started\n");
-               return;
-       }
        if (test_done) {
                printf("Packet forwarding not started\n");
                return;
@@ -1360,7 +1386,7 @@ start_port(portid_t pid)
                                        if (mp == NULL) {
                                                printf("Failed to setup RX queue:"
                                                        "No mempool allocation"
-                                                       "on the socket %d\n",
+                                                       " on the socket %d\n",
                                                        rxring_numa[pi]);
                                                return -1;
                                        }
@@ -1368,17 +1394,23 @@ start_port(portid_t pid)
                                        diag = rte_eth_rx_queue_setup(pi, qi,
                                             nb_rxd,rxring_numa[pi],
                                             &(port->rx_conf),mp);
-                               }
-                               else
+                               } else {
+                                       struct rte_mempool *mp =
+                                               mbuf_pool_find(port->socket_id);
+                                       if (mp == NULL) {
+                                               printf("Failed to setup RX queue:"
+                                                       "No mempool allocation"
+                                                       " on the socket %d\n",
+                                                       port->socket_id);
+                                               return -1;
+                                       }
                                        diag = rte_eth_rx_queue_setup(pi, qi,
                                             nb_rxd,port->socket_id,
-                                            &(port->rx_conf),
-                                            mbuf_pool_find(port->socket_id));
-
+                                            &(port->rx_conf), mp);
+                               }
                                if (diag == 0)
                                        continue;
 
-
                                /* Fail to setup rx queue, return */
                                if (rte_atomic16_cmpset(&(port->port_status),
                                                        RTE_PORT_HANDLING,
@@ -1527,6 +1559,7 @@ void
 attach_port(char *identifier)
 {
        portid_t pi = 0;
+       unsigned int socket_id;
 
        printf("Attaching a new port...\n");
 
@@ -1539,7 +1572,11 @@ attach_port(char *identifier)
                return;
 
        ports[pi].enabled = 1;
-       reconfig(pi, rte_eth_dev_socket_id(pi));
+       socket_id = (unsigned)rte_eth_dev_socket_id(pi);
+       /* if socket_id is invalid, set to 0 */
+       if (check_socket_id(socket_id) < 0)
+               socket_id = 0;
+       reconfig(pi, socket_id);
        rte_eth_promiscuous_enable(pi);
 
        nb_ports = rte_eth_dev_count();
@@ -2020,6 +2057,10 @@ signal_handler(int signum)
        if (signum == SIGINT || signum == SIGTERM) {
                printf("\nSignal %d received, preparing to exit...\n",
                                signum);
+#ifdef RTE_LIBRTE_PDUMP
+               /* uninitialize packet capture framework */
+               rte_pdump_uninit();
+#endif
                force_quit();
                /* exit with the expected status */
                signal(signum, SIG_DFL);
@@ -2040,6 +2081,11 @@ main(int argc, char** argv)
        if (diag < 0)
                rte_panic("Cannot init EAL\n");
 
+#ifdef RTE_LIBRTE_PDUMP
+       /* initialize packet capture framework */
+       rte_pdump_init(NULL);
+#endif
+
        nb_ports = (portid_t) rte_eth_dev_count();
        if (nb_ports == 0)
                RTE_LOG(WARNING, EAL, "No probed ethernet devices\n");