1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2010-2017 Intel Corporation 3 */ 4 5 #include <stdarg.h> 6 #include <stdio.h> 7 #include <stdlib.h> 8 #include <signal.h> 9 #include <string.h> 10 #include <time.h> 11 #include <fcntl.h> 12 #ifndef RTE_EXEC_ENV_WINDOWS 13 #include <sys/mman.h> 14 #include <sys/select.h> 15 #endif 16 #include <sys/types.h> 17 #include <errno.h> 18 #include <stdbool.h> 19 20 #include <sys/queue.h> 21 #include <sys/stat.h> 22 23 #include <stdint.h> 24 #include <unistd.h> 25 #include <inttypes.h> 26 27 #include <rte_common.h> 28 #include <rte_errno.h> 29 #include <rte_byteorder.h> 30 #include <rte_log.h> 31 #include <rte_debug.h> 32 #include <rte_cycles.h> 33 #include <rte_memory.h> 34 #include <rte_memcpy.h> 35 #include <rte_launch.h> 36 #include <rte_bus.h> 37 #include <rte_eal.h> 38 #include <rte_alarm.h> 39 #include <rte_per_lcore.h> 40 #include <rte_lcore.h> 41 #include <rte_branch_prediction.h> 42 #include <rte_mempool.h> 43 #include <rte_malloc.h> 44 #include <rte_mbuf.h> 45 #include <rte_mbuf_pool_ops.h> 46 #include <rte_interrupts.h> 47 #include <rte_ether.h> 48 #include <rte_ethdev.h> 49 #include <rte_dev.h> 50 #include <rte_string_fns.h> 51 #ifdef RTE_NET_IXGBE 52 #include <rte_pmd_ixgbe.h> 53 #endif 54 #ifdef RTE_LIB_PDUMP 55 #include <rte_pdump.h> 56 #endif 57 #include <rte_flow.h> 58 #ifdef RTE_LIB_METRICS 59 #include <rte_metrics.h> 60 #endif 61 #ifdef RTE_LIB_BITRATESTATS 62 #include <rte_bitrate.h> 63 #endif 64 #ifdef RTE_LIB_LATENCYSTATS 65 #include <rte_latencystats.h> 66 #endif 67 #ifdef RTE_EXEC_ENV_WINDOWS 68 #include <process.h> 69 #endif 70 #ifdef RTE_NET_BOND 71 #include <rte_eth_bond.h> 72 #endif 73 #ifdef RTE_NET_MLX5 74 #include "mlx5_testpmd.h" 75 #endif 76 77 #include "testpmd.h" 78 79 #ifndef MAP_HUGETLB 80 /* FreeBSD may not have MAP_HUGETLB (in fact, it probably doesn't) */ 81 #define HUGE_FLAG (0x40000) 82 #else 83 #define HUGE_FLAG MAP_HUGETLB 84 #endif 85 86 #ifndef MAP_HUGE_SHIFT 87 /* older kernels (or FreeBSD) will not have this define */ 88 #define HUGE_SHIFT (26) 89 #else 90 #define HUGE_SHIFT MAP_HUGE_SHIFT 91 #endif 92 93 #define EXTMEM_HEAP_NAME "extmem" 94 /* 95 * Zone size with the malloc overhead (max of debug and release variants) 96 * must fit into the smallest supported hugepage size (2M), 97 * so that an IOVA-contiguous zone of this size can always be allocated 98 * if there are free 2M hugepages. 99 */ 100 #define EXTBUF_ZONE_SIZE (RTE_PGSIZE_2M - 4 * RTE_CACHE_LINE_SIZE) 101 102 uint16_t verbose_level = 0; /**< Silent by default. */ 103 int testpmd_logtype; /**< Log type for testpmd logs */ 104 105 /* use main core for command line ? */ 106 uint8_t interactive = 0; 107 uint8_t auto_start = 0; 108 uint8_t tx_first; 109 char cmdline_filename[PATH_MAX] = {0}; 110 111 /* 112 * NUMA support configuration. 113 * When set, the NUMA support attempts to dispatch the allocation of the 114 * RX and TX memory rings, and of the DMA memory buffers (mbufs) for the 115 * probed ports among the CPU sockets 0 and 1. 116 * Otherwise, all memory is allocated from CPU socket 0. 117 */ 118 uint8_t numa_support = 1; /**< numa enabled by default */ 119 120 /* 121 * In UMA mode,all memory is allocated from socket 0 if --socket-num is 122 * not configured. 123 */ 124 uint8_t socket_num = UMA_NO_CONFIG; 125 126 /* 127 * Select mempool allocation type: 128 * - native: use regular DPDK memory 129 * - anon: use regular DPDK memory to create mempool, but populate using 130 * anonymous memory (may not be IOVA-contiguous) 131 * - xmem: use externally allocated hugepage memory 132 */ 133 uint8_t mp_alloc_type = MP_ALLOC_NATIVE; 134 135 /* 136 * Store specified sockets on which memory pool to be used by ports 137 * is allocated. 138 */ 139 uint8_t port_numa[RTE_MAX_ETHPORTS]; 140 141 /* 142 * Store specified sockets on which RX ring to be used by ports 143 * is allocated. 144 */ 145 uint8_t rxring_numa[RTE_MAX_ETHPORTS]; 146 147 /* 148 * Store specified sockets on which TX ring to be used by ports 149 * is allocated. 150 */ 151 uint8_t txring_numa[RTE_MAX_ETHPORTS]; 152 153 /* 154 * Record the Ethernet address of peer target ports to which packets are 155 * forwarded. 156 * Must be instantiated with the ethernet addresses of peer traffic generator 157 * ports. 158 */ 159 struct rte_ether_addr peer_eth_addrs[RTE_MAX_ETHPORTS]; 160 portid_t nb_peer_eth_addrs = 0; 161 162 /* 163 * Probed Target Environment. 164 */ 165 struct rte_port *ports; /**< For all probed ethernet ports. */ 166 portid_t nb_ports; /**< Number of probed ethernet ports. */ 167 struct fwd_lcore **fwd_lcores; /**< For all probed logical cores. */ 168 lcoreid_t nb_lcores; /**< Number of probed logical cores. */ 169 170 portid_t ports_ids[RTE_MAX_ETHPORTS]; /**< Store all port ids. */ 171 172 /* 173 * Test Forwarding Configuration. 174 * nb_fwd_lcores <= nb_cfg_lcores <= nb_lcores 175 * nb_fwd_ports <= nb_cfg_ports <= nb_ports 176 */ 177 lcoreid_t nb_cfg_lcores; /**< Number of configured logical cores. */ 178 lcoreid_t nb_fwd_lcores; /**< Number of forwarding logical cores. */ 179 portid_t nb_cfg_ports; /**< Number of configured ports. */ 180 portid_t nb_fwd_ports; /**< Number of forwarding ports. */ 181 182 unsigned int fwd_lcores_cpuids[RTE_MAX_LCORE]; /**< CPU ids configuration. */ 183 portid_t fwd_ports_ids[RTE_MAX_ETHPORTS]; /**< Port ids configuration. */ 184 185 struct fwd_stream **fwd_streams; /**< For each RX queue of each port. */ 186 streamid_t nb_fwd_streams; /**< Is equal to (nb_ports * nb_rxq). */ 187 188 /* 189 * Forwarding engines. 190 */ 191 struct fwd_engine * fwd_engines[] = { 192 &io_fwd_engine, 193 &mac_fwd_engine, 194 &mac_swap_engine, 195 &flow_gen_engine, 196 &rx_only_engine, 197 &tx_only_engine, 198 &csum_fwd_engine, 199 &icmp_echo_engine, 200 &noisy_vnf_engine, 201 &five_tuple_swap_fwd_engine, 202 #ifdef RTE_LIBRTE_IEEE1588 203 &ieee1588_fwd_engine, 204 #endif 205 &shared_rxq_engine, 206 NULL, 207 }; 208 209 struct rte_mempool *mempools[RTE_MAX_NUMA_NODES * MAX_SEGS_BUFFER_SPLIT]; 210 uint16_t mempool_flags; 211 212 struct fwd_config cur_fwd_config; 213 struct fwd_engine *cur_fwd_eng = &io_fwd_engine; /**< IO mode by default. */ 214 uint32_t retry_enabled; 215 uint32_t burst_tx_delay_time = BURST_TX_WAIT_US; 216 uint32_t burst_tx_retry_num = BURST_TX_RETRIES; 217 218 uint32_t mbuf_data_size_n = 1; /* Number of specified mbuf sizes. */ 219 uint16_t mbuf_data_size[MAX_SEGS_BUFFER_SPLIT] = { 220 DEFAULT_MBUF_DATA_SIZE 221 }; /**< Mbuf data space size. */ 222 uint32_t param_total_num_mbufs = 0; /**< number of mbufs in all pools - if 223 * specified on command-line. */ 224 uint16_t stats_period; /**< Period to show statistics (disabled by default) */ 225 226 /** Extended statistics to show. */ 227 struct rte_eth_xstat_name *xstats_display; 228 229 unsigned int xstats_display_num; /**< Size of extended statistics to show */ 230 231 /* 232 * In container, it cannot terminate the process which running with 'stats-period' 233 * option. Set flag to exit stats period loop after received SIGINT/SIGTERM. 234 */ 235 volatile uint8_t f_quit; 236 uint8_t cl_quit; /* Quit testpmd from cmdline. */ 237 238 /* 239 * Max Rx frame size, set by '--max-pkt-len' parameter. 240 */ 241 uint32_t max_rx_pkt_len; 242 243 /* 244 * Configuration of packet segments used to scatter received packets 245 * if some of split features is configured. 246 */ 247 uint16_t rx_pkt_seg_lengths[MAX_SEGS_BUFFER_SPLIT]; 248 uint8_t rx_pkt_nb_segs; /**< Number of segments to split */ 249 uint16_t rx_pkt_seg_offsets[MAX_SEGS_BUFFER_SPLIT]; 250 uint8_t rx_pkt_nb_offs; /**< Number of specified offsets */ 251 uint32_t rx_pkt_hdr_protos[MAX_SEGS_BUFFER_SPLIT]; 252 253 uint8_t multi_rx_mempool; /**< Enables multi-rx-mempool feature */ 254 255 /* 256 * Configuration of packet segments used by the "txonly" processing engine. 257 */ 258 uint16_t tx_pkt_length = TXONLY_DEF_PACKET_LEN; /**< TXONLY packet length. */ 259 uint16_t tx_pkt_seg_lengths[RTE_MAX_SEGS_PER_PKT] = { 260 TXONLY_DEF_PACKET_LEN, 261 }; 262 uint8_t tx_pkt_nb_segs = 1; /**< Number of segments in TXONLY packets */ 263 264 enum tx_pkt_split tx_pkt_split = TX_PKT_SPLIT_OFF; 265 /**< Split policy for packets to TX. */ 266 267 uint8_t txonly_multi_flow; 268 /**< Whether multiple flows are generated in TXONLY mode. */ 269 270 uint32_t tx_pkt_times_inter; 271 /**< Timings for send scheduling in TXONLY mode, time between bursts. */ 272 273 uint32_t tx_pkt_times_intra; 274 /**< Timings for send scheduling in TXONLY mode, time between packets. */ 275 276 uint16_t nb_pkt_per_burst = DEF_PKT_BURST; /**< Number of packets per burst. */ 277 uint16_t nb_pkt_flowgen_clones; /**< Number of Tx packet clones to send in flowgen mode. */ 278 int nb_flows_flowgen = 1024; /**< Number of flows in flowgen mode. */ 279 uint16_t mb_mempool_cache = DEF_MBUF_CACHE; /**< Size of mbuf mempool cache. */ 280 281 /* current configuration is in DCB or not,0 means it is not in DCB mode */ 282 uint8_t dcb_config = 0; 283 284 /* 285 * Configurable number of RX/TX queues. 286 */ 287 queueid_t nb_hairpinq; /**< Number of hairpin queues per port. */ 288 queueid_t nb_rxq = 1; /**< Number of RX queues per port. */ 289 queueid_t nb_txq = 1; /**< Number of TX queues per port. */ 290 291 /* 292 * Configurable number of RX/TX ring descriptors. 293 * Defaults are supplied by drivers via ethdev. 294 */ 295 #define RX_DESC_DEFAULT 0 296 #define TX_DESC_DEFAULT 0 297 uint16_t nb_rxd = RX_DESC_DEFAULT; /**< Number of RX descriptors. */ 298 uint16_t nb_txd = TX_DESC_DEFAULT; /**< Number of TX descriptors. */ 299 300 #define RTE_PMD_PARAM_UNSET -1 301 /* 302 * Configurable values of RX and TX ring threshold registers. 303 */ 304 305 int8_t rx_pthresh = RTE_PMD_PARAM_UNSET; 306 int8_t rx_hthresh = RTE_PMD_PARAM_UNSET; 307 int8_t rx_wthresh = RTE_PMD_PARAM_UNSET; 308 309 int8_t tx_pthresh = RTE_PMD_PARAM_UNSET; 310 int8_t tx_hthresh = RTE_PMD_PARAM_UNSET; 311 int8_t tx_wthresh = RTE_PMD_PARAM_UNSET; 312 313 /* 314 * Configurable value of RX free threshold. 315 */ 316 int16_t rx_free_thresh = RTE_PMD_PARAM_UNSET; 317 318 /* 319 * Configurable value of RX drop enable. 320 */ 321 int8_t rx_drop_en = RTE_PMD_PARAM_UNSET; 322 323 /* 324 * Configurable value of TX free threshold. 325 */ 326 int16_t tx_free_thresh = RTE_PMD_PARAM_UNSET; 327 328 /* 329 * Configurable value of TX RS bit threshold. 330 */ 331 int16_t tx_rs_thresh = RTE_PMD_PARAM_UNSET; 332 333 /* 334 * Configurable sub-forwarding mode for the noisy_vnf forwarding mode. 335 */ 336 enum noisy_fwd_mode noisy_fwd_mode; 337 338 /* String version of enum noisy_fwd_mode */ 339 const char * const noisy_fwd_mode_desc[] = { 340 [NOISY_FWD_MODE_IO] = "io", 341 [NOISY_FWD_MODE_MAC] = "mac", 342 [NOISY_FWD_MODE_MACSWAP] = "macswap", 343 [NOISY_FWD_MODE_5TSWAP] = "5tswap", 344 [NOISY_FWD_MODE_MAX] = NULL, 345 }; 346 347 /* 348 * Configurable value of buffered packets before sending. 349 */ 350 uint16_t noisy_tx_sw_bufsz; 351 352 /* 353 * Configurable value of packet buffer timeout. 354 */ 355 uint16_t noisy_tx_sw_buf_flush_time; 356 357 /* 358 * Configurable value for size of VNF internal memory area 359 * used for simulating noisy neighbour behaviour 360 */ 361 uint64_t noisy_lkup_mem_sz; 362 363 /* 364 * Configurable value of number of random writes done in 365 * VNF simulation memory area. 366 */ 367 uint64_t noisy_lkup_num_writes; 368 369 /* 370 * Configurable value of number of random reads done in 371 * VNF simulation memory area. 372 */ 373 uint64_t noisy_lkup_num_reads; 374 375 /* 376 * Configurable value of number of random reads/writes done in 377 * VNF simulation memory area. 378 */ 379 uint64_t noisy_lkup_num_reads_writes; 380 381 /* 382 * Receive Side Scaling (RSS) configuration. 383 */ 384 uint64_t rss_hf = RTE_ETH_RSS_IP; /* RSS IP by default. */ 385 386 /* 387 * Port topology configuration 388 */ 389 uint16_t port_topology = PORT_TOPOLOGY_PAIRED; /* Ports are paired by default */ 390 391 /* 392 * Avoids to flush all the RX streams before starts forwarding. 393 */ 394 uint8_t no_flush_rx = 0; /* flush by default */ 395 396 /* 397 * Flow API isolated mode. 398 */ 399 uint8_t flow_isolate_all; 400 401 /* 402 * Disable port flow flush when stop port. 403 */ 404 uint8_t no_flow_flush = 0; /* do flow flush by default */ 405 406 /* 407 * Avoids to check link status when starting/stopping a port. 408 */ 409 uint8_t no_link_check = 0; /* check by default */ 410 411 /* 412 * Don't automatically start all ports in interactive mode. 413 */ 414 uint8_t no_device_start = 0; 415 416 /* 417 * Enable link status change notification 418 */ 419 uint8_t lsc_interrupt = 1; /* enabled by default */ 420 421 /* 422 * Enable device removal notification. 423 */ 424 uint8_t rmv_interrupt = 1; /* enabled by default */ 425 426 uint8_t hot_plug = 0; /**< hotplug disabled by default. */ 427 428 /* After attach, port setup is called on event or by iterator */ 429 bool setup_on_probe_event = true; 430 431 /* Clear ptypes on port initialization. */ 432 uint8_t clear_ptypes = true; 433 434 /* Hairpin ports configuration mode. */ 435 uint32_t hairpin_mode; 436 437 /* Pretty printing of ethdev events */ 438 static const char * const eth_event_desc[] = { 439 [RTE_ETH_EVENT_UNKNOWN] = "unknown", 440 [RTE_ETH_EVENT_INTR_LSC] = "link state change", 441 [RTE_ETH_EVENT_QUEUE_STATE] = "queue state", 442 [RTE_ETH_EVENT_INTR_RESET] = "reset", 443 [RTE_ETH_EVENT_VF_MBOX] = "VF mbox", 444 [RTE_ETH_EVENT_IPSEC] = "IPsec", 445 [RTE_ETH_EVENT_MACSEC] = "MACsec", 446 [RTE_ETH_EVENT_INTR_RMV] = "device removal", 447 [RTE_ETH_EVENT_NEW] = "device probed", 448 [RTE_ETH_EVENT_DESTROY] = "device released", 449 [RTE_ETH_EVENT_FLOW_AGED] = "flow aged", 450 [RTE_ETH_EVENT_RX_AVAIL_THRESH] = "RxQ available descriptors threshold reached", 451 [RTE_ETH_EVENT_ERR_RECOVERING] = "error recovering", 452 [RTE_ETH_EVENT_RECOVERY_SUCCESS] = "error recovery successful", 453 [RTE_ETH_EVENT_RECOVERY_FAILED] = "error recovery failed", 454 [RTE_ETH_EVENT_MAX] = NULL, 455 }; 456 457 /* 458 * Display or mask ether events 459 * Default to all events except VF_MBOX 460 */ 461 uint32_t event_print_mask = (UINT32_C(1) << RTE_ETH_EVENT_UNKNOWN) | 462 (UINT32_C(1) << RTE_ETH_EVENT_INTR_LSC) | 463 (UINT32_C(1) << RTE_ETH_EVENT_QUEUE_STATE) | 464 (UINT32_C(1) << RTE_ETH_EVENT_INTR_RESET) | 465 (UINT32_C(1) << RTE_ETH_EVENT_IPSEC) | 466 (UINT32_C(1) << RTE_ETH_EVENT_MACSEC) | 467 (UINT32_C(1) << RTE_ETH_EVENT_INTR_RMV) | 468 (UINT32_C(1) << RTE_ETH_EVENT_FLOW_AGED) | 469 (UINT32_C(1) << RTE_ETH_EVENT_ERR_RECOVERING) | 470 (UINT32_C(1) << RTE_ETH_EVENT_RECOVERY_SUCCESS) | 471 (UINT32_C(1) << RTE_ETH_EVENT_RECOVERY_FAILED); 472 /* 473 * Decide if all memory are locked for performance. 474 */ 475 int do_mlockall = 0; 476 477 #ifdef RTE_LIB_LATENCYSTATS 478 479 /* 480 * Set when latency stats is enabled in the commandline 481 */ 482 uint8_t latencystats_enabled; 483 484 /* 485 * Lcore ID to service latency statistics. 486 */ 487 lcoreid_t latencystats_lcore_id = -1; 488 489 #endif 490 491 /* 492 * Ethernet device configuration. 493 */ 494 struct rte_eth_rxmode rx_mode; 495 496 struct rte_eth_txmode tx_mode = { 497 .offloads = RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE, 498 }; 499 500 volatile int test_done = 1; /* stop packet forwarding when set to 1. */ 501 502 /* 503 * Display zero values by default for xstats 504 */ 505 uint8_t xstats_hide_zero; 506 507 /* 508 * Measure of CPU cycles disabled by default 509 */ 510 uint8_t record_core_cycles; 511 512 /* 513 * Display of RX and TX bursts disabled by default 514 */ 515 uint8_t record_burst_stats; 516 517 /* 518 * Number of ports per shared Rx queue group, 0 disable. 519 */ 520 uint32_t rxq_share; 521 522 unsigned int num_sockets = 0; 523 unsigned int socket_ids[RTE_MAX_NUMA_NODES]; 524 525 #ifdef RTE_LIB_BITRATESTATS 526 /* Bitrate statistics */ 527 struct rte_stats_bitrates *bitrate_data; 528 lcoreid_t bitrate_lcore_id; 529 uint8_t bitrate_enabled; 530 #endif 531 532 #ifdef RTE_LIB_GRO 533 struct gro_status gro_ports[RTE_MAX_ETHPORTS]; 534 uint8_t gro_flush_cycles = GRO_DEFAULT_FLUSH_CYCLES; 535 #endif 536 537 /* 538 * hexadecimal bitmask of RX mq mode can be enabled. 539 */ 540 enum rte_eth_rx_mq_mode rx_mq_mode = RTE_ETH_MQ_RX_VMDQ_DCB_RSS; 541 542 /* 543 * Used to set forced link speed 544 */ 545 uint32_t eth_link_speed; 546 547 /* 548 * ID of the current process in multi-process, used to 549 * configure the queues to be polled. 550 */ 551 int proc_id; 552 553 /* 554 * Number of processes in multi-process, used to 555 * configure the queues to be polled. 556 */ 557 unsigned int num_procs = 1; 558 559 static void 560 eth_rx_metadata_negotiate_mp(uint16_t port_id) 561 { 562 uint64_t rx_meta_features = 0; 563 int ret; 564 565 if (!is_proc_primary()) 566 return; 567 568 rx_meta_features |= RTE_ETH_RX_METADATA_USER_FLAG; 569 rx_meta_features |= RTE_ETH_RX_METADATA_USER_MARK; 570 rx_meta_features |= RTE_ETH_RX_METADATA_TUNNEL_ID; 571 572 ret = rte_eth_rx_metadata_negotiate(port_id, &rx_meta_features); 573 if (ret == 0) { 574 if (!(rx_meta_features & RTE_ETH_RX_METADATA_USER_FLAG)) { 575 TESTPMD_LOG(DEBUG, "Flow action FLAG will not affect Rx mbufs on port %u\n", 576 port_id); 577 } 578 579 if (!(rx_meta_features & RTE_ETH_RX_METADATA_USER_MARK)) { 580 TESTPMD_LOG(DEBUG, "Flow action MARK will not affect Rx mbufs on port %u\n", 581 port_id); 582 } 583 584 if (!(rx_meta_features & RTE_ETH_RX_METADATA_TUNNEL_ID)) { 585 TESTPMD_LOG(DEBUG, "Flow tunnel offload support might be limited or unavailable on port %u\n", 586 port_id); 587 } 588 } else if (ret != -ENOTSUP) { 589 rte_exit(EXIT_FAILURE, "Error when negotiating Rx meta features on port %u: %s\n", 590 port_id, rte_strerror(-ret)); 591 } 592 } 593 594 static int 595 eth_dev_configure_mp(uint16_t port_id, uint16_t nb_rx_q, uint16_t nb_tx_q, 596 const struct rte_eth_conf *dev_conf) 597 { 598 if (is_proc_primary()) 599 return rte_eth_dev_configure(port_id, nb_rx_q, nb_tx_q, 600 dev_conf); 601 return 0; 602 } 603 604 static int 605 change_bonding_slave_port_status(portid_t bond_pid, bool is_stop) 606 { 607 #ifdef RTE_NET_BOND 608 609 portid_t slave_pids[RTE_MAX_ETHPORTS]; 610 struct rte_port *port; 611 int num_slaves; 612 portid_t slave_pid; 613 int i; 614 615 num_slaves = rte_eth_bond_slaves_get(bond_pid, slave_pids, 616 RTE_MAX_ETHPORTS); 617 if (num_slaves < 0) { 618 fprintf(stderr, "Failed to get slave list for port = %u\n", 619 bond_pid); 620 return num_slaves; 621 } 622 623 for (i = 0; i < num_slaves; i++) { 624 slave_pid = slave_pids[i]; 625 port = &ports[slave_pid]; 626 port->port_status = 627 is_stop ? RTE_PORT_STOPPED : RTE_PORT_STARTED; 628 } 629 #else 630 RTE_SET_USED(bond_pid); 631 RTE_SET_USED(is_stop); 632 #endif 633 return 0; 634 } 635 636 static int 637 eth_dev_start_mp(uint16_t port_id) 638 { 639 int ret; 640 641 if (is_proc_primary()) { 642 ret = rte_eth_dev_start(port_id); 643 if (ret != 0) 644 return ret; 645 646 struct rte_port *port = &ports[port_id]; 647 648 /* 649 * Starting a bonded port also starts all slaves under the bonded 650 * device. So if this port is bond device, we need to modify the 651 * port status of these slaves. 652 */ 653 if (port->bond_flag == 1) 654 return change_bonding_slave_port_status(port_id, false); 655 } 656 657 return 0; 658 } 659 660 static int 661 eth_dev_stop_mp(uint16_t port_id) 662 { 663 int ret; 664 665 if (is_proc_primary()) { 666 ret = rte_eth_dev_stop(port_id); 667 if (ret != 0) 668 return ret; 669 670 struct rte_port *port = &ports[port_id]; 671 672 /* 673 * Stopping a bonded port also stops all slaves under the bonded 674 * device. So if this port is bond device, we need to modify the 675 * port status of these slaves. 676 */ 677 if (port->bond_flag == 1) 678 return change_bonding_slave_port_status(port_id, true); 679 } 680 681 return 0; 682 } 683 684 static void 685 mempool_free_mp(struct rte_mempool *mp) 686 { 687 if (is_proc_primary()) 688 rte_mempool_free(mp); 689 } 690 691 static int 692 eth_dev_set_mtu_mp(uint16_t port_id, uint16_t mtu) 693 { 694 if (is_proc_primary()) 695 return rte_eth_dev_set_mtu(port_id, mtu); 696 697 return 0; 698 } 699 700 /* Forward function declarations */ 701 static void setup_attached_port(portid_t pi); 702 static void check_all_ports_link_status(uint32_t port_mask); 703 static int eth_event_callback(portid_t port_id, 704 enum rte_eth_event_type type, 705 void *param, void *ret_param); 706 static void dev_event_callback(const char *device_name, 707 enum rte_dev_event_type type, 708 void *param); 709 static void fill_xstats_display_info(void); 710 711 /* 712 * Check if all the ports are started. 713 * If yes, return positive value. If not, return zero. 714 */ 715 static int all_ports_started(void); 716 717 #ifdef RTE_LIB_GSO 718 struct gso_status gso_ports[RTE_MAX_ETHPORTS]; 719 uint16_t gso_max_segment_size = RTE_ETHER_MAX_LEN - RTE_ETHER_CRC_LEN; 720 #endif 721 722 /* Holds the registered mbuf dynamic flags names. */ 723 char dynf_names[64][RTE_MBUF_DYN_NAMESIZE]; 724 725 726 /* 727 * Helper function to check if socket is already discovered. 728 * If yes, return positive value. If not, return zero. 729 */ 730 int 731 new_socket_id(unsigned int socket_id) 732 { 733 unsigned int i; 734 735 for (i = 0; i < num_sockets; i++) { 736 if (socket_ids[i] == socket_id) 737 return 0; 738 } 739 return 1; 740 } 741 742 /* 743 * Setup default configuration. 744 */ 745 static void 746 set_default_fwd_lcores_config(void) 747 { 748 unsigned int i; 749 unsigned int nb_lc; 750 unsigned int sock_num; 751 752 nb_lc = 0; 753 for (i = 0; i < RTE_MAX_LCORE; i++) { 754 if (!rte_lcore_is_enabled(i)) 755 continue; 756 sock_num = rte_lcore_to_socket_id(i); 757 if (new_socket_id(sock_num)) { 758 if (num_sockets >= RTE_MAX_NUMA_NODES) { 759 rte_exit(EXIT_FAILURE, 760 "Total sockets greater than %u\n", 761 RTE_MAX_NUMA_NODES); 762 } 763 socket_ids[num_sockets++] = sock_num; 764 } 765 if (i == rte_get_main_lcore()) 766 continue; 767 fwd_lcores_cpuids[nb_lc++] = i; 768 } 769 nb_lcores = (lcoreid_t) nb_lc; 770 nb_cfg_lcores = nb_lcores; 771 nb_fwd_lcores = 1; 772 } 773 774 static void 775 set_def_peer_eth_addrs(void) 776 { 777 portid_t i; 778 779 for (i = 0; i < RTE_MAX_ETHPORTS; i++) { 780 peer_eth_addrs[i].addr_bytes[0] = RTE_ETHER_LOCAL_ADMIN_ADDR; 781 peer_eth_addrs[i].addr_bytes[5] = i; 782 } 783 } 784 785 static void 786 set_default_fwd_ports_config(void) 787 { 788 portid_t pt_id; 789 int i = 0; 790 791 RTE_ETH_FOREACH_DEV(pt_id) { 792 fwd_ports_ids[i++] = pt_id; 793 794 /* Update sockets info according to the attached device */ 795 int socket_id = rte_eth_dev_socket_id(pt_id); 796 if (socket_id >= 0 && new_socket_id(socket_id)) { 797 if (num_sockets >= RTE_MAX_NUMA_NODES) { 798 rte_exit(EXIT_FAILURE, 799 "Total sockets greater than %u\n", 800 RTE_MAX_NUMA_NODES); 801 } 802 socket_ids[num_sockets++] = socket_id; 803 } 804 } 805 806 nb_cfg_ports = nb_ports; 807 nb_fwd_ports = nb_ports; 808 } 809 810 void 811 set_def_fwd_config(void) 812 { 813 set_default_fwd_lcores_config(); 814 set_def_peer_eth_addrs(); 815 set_default_fwd_ports_config(); 816 } 817 818 #ifndef RTE_EXEC_ENV_WINDOWS 819 /* extremely pessimistic estimation of memory required to create a mempool */ 820 static int 821 calc_mem_size(uint32_t nb_mbufs, uint32_t mbuf_sz, size_t pgsz, size_t *out) 822 { 823 unsigned int n_pages, mbuf_per_pg, leftover; 824 uint64_t total_mem, mbuf_mem, obj_sz; 825 826 /* there is no good way to predict how much space the mempool will 827 * occupy because it will allocate chunks on the fly, and some of those 828 * will come from default DPDK memory while some will come from our 829 * external memory, so just assume 128MB will be enough for everyone. 830 */ 831 uint64_t hdr_mem = 128 << 20; 832 833 /* account for possible non-contiguousness */ 834 obj_sz = rte_mempool_calc_obj_size(mbuf_sz, 0, NULL); 835 if (obj_sz > pgsz) { 836 TESTPMD_LOG(ERR, "Object size is bigger than page size\n"); 837 return -1; 838 } 839 840 mbuf_per_pg = pgsz / obj_sz; 841 leftover = (nb_mbufs % mbuf_per_pg) > 0; 842 n_pages = (nb_mbufs / mbuf_per_pg) + leftover; 843 844 mbuf_mem = n_pages * pgsz; 845 846 total_mem = RTE_ALIGN(hdr_mem + mbuf_mem, pgsz); 847 848 if (total_mem > SIZE_MAX) { 849 TESTPMD_LOG(ERR, "Memory size too big\n"); 850 return -1; 851 } 852 *out = (size_t)total_mem; 853 854 return 0; 855 } 856 857 static int 858 pagesz_flags(uint64_t page_sz) 859 { 860 /* as per mmap() manpage, all page sizes are log2 of page size 861 * shifted by MAP_HUGE_SHIFT 862 */ 863 int log2 = rte_log2_u64(page_sz); 864 865 return (log2 << HUGE_SHIFT); 866 } 867 868 static void * 869 alloc_mem(size_t memsz, size_t pgsz, bool huge) 870 { 871 void *addr; 872 int flags; 873 874 /* allocate anonymous hugepages */ 875 flags = MAP_ANONYMOUS | MAP_PRIVATE; 876 if (huge) 877 flags |= HUGE_FLAG | pagesz_flags(pgsz); 878 879 addr = mmap(NULL, memsz, PROT_READ | PROT_WRITE, flags, -1, 0); 880 if (addr == MAP_FAILED) 881 return NULL; 882 883 return addr; 884 } 885 886 struct extmem_param { 887 void *addr; 888 size_t len; 889 size_t pgsz; 890 rte_iova_t *iova_table; 891 unsigned int iova_table_len; 892 }; 893 894 static int 895 create_extmem(uint32_t nb_mbufs, uint32_t mbuf_sz, struct extmem_param *param, 896 bool huge) 897 { 898 uint64_t pgsizes[] = {RTE_PGSIZE_2M, RTE_PGSIZE_1G, /* x86_64, ARM */ 899 RTE_PGSIZE_16M, RTE_PGSIZE_16G}; /* POWER */ 900 unsigned int cur_page, n_pages, pgsz_idx; 901 size_t mem_sz, cur_pgsz; 902 rte_iova_t *iovas = NULL; 903 void *addr; 904 int ret; 905 906 for (pgsz_idx = 0; pgsz_idx < RTE_DIM(pgsizes); pgsz_idx++) { 907 /* skip anything that is too big */ 908 if (pgsizes[pgsz_idx] > SIZE_MAX) 909 continue; 910 911 cur_pgsz = pgsizes[pgsz_idx]; 912 913 /* if we were told not to allocate hugepages, override */ 914 if (!huge) 915 cur_pgsz = sysconf(_SC_PAGESIZE); 916 917 ret = calc_mem_size(nb_mbufs, mbuf_sz, cur_pgsz, &mem_sz); 918 if (ret < 0) { 919 TESTPMD_LOG(ERR, "Cannot calculate memory size\n"); 920 return -1; 921 } 922 923 /* allocate our memory */ 924 addr = alloc_mem(mem_sz, cur_pgsz, huge); 925 926 /* if we couldn't allocate memory with a specified page size, 927 * that doesn't mean we can't do it with other page sizes, so 928 * try another one. 929 */ 930 if (addr == NULL) 931 continue; 932 933 /* store IOVA addresses for every page in this memory area */ 934 n_pages = mem_sz / cur_pgsz; 935 936 iovas = malloc(sizeof(*iovas) * n_pages); 937 938 if (iovas == NULL) { 939 TESTPMD_LOG(ERR, "Cannot allocate memory for iova addresses\n"); 940 goto fail; 941 } 942 /* lock memory if it's not huge pages */ 943 if (!huge) 944 mlock(addr, mem_sz); 945 946 /* populate IOVA addresses */ 947 for (cur_page = 0; cur_page < n_pages; cur_page++) { 948 rte_iova_t iova; 949 size_t offset; 950 void *cur; 951 952 offset = cur_pgsz * cur_page; 953 cur = RTE_PTR_ADD(addr, offset); 954 955 /* touch the page before getting its IOVA */ 956 *(volatile char *)cur = 0; 957 958 iova = rte_mem_virt2iova(cur); 959 960 iovas[cur_page] = iova; 961 } 962 963 break; 964 } 965 /* if we couldn't allocate anything */ 966 if (iovas == NULL) 967 return -1; 968 969 param->addr = addr; 970 param->len = mem_sz; 971 param->pgsz = cur_pgsz; 972 param->iova_table = iovas; 973 param->iova_table_len = n_pages; 974 975 return 0; 976 fail: 977 free(iovas); 978 if (addr) 979 munmap(addr, mem_sz); 980 981 return -1; 982 } 983 984 static int 985 setup_extmem(uint32_t nb_mbufs, uint32_t mbuf_sz, bool huge) 986 { 987 struct extmem_param param; 988 int socket_id, ret; 989 990 memset(¶m, 0, sizeof(param)); 991 992 /* check if our heap exists */ 993 socket_id = rte_malloc_heap_get_socket(EXTMEM_HEAP_NAME); 994 if (socket_id < 0) { 995 /* create our heap */ 996 ret = rte_malloc_heap_create(EXTMEM_HEAP_NAME); 997 if (ret < 0) { 998 TESTPMD_LOG(ERR, "Cannot create heap\n"); 999 return -1; 1000 } 1001 } 1002 1003 ret = create_extmem(nb_mbufs, mbuf_sz, ¶m, huge); 1004 if (ret < 0) { 1005 TESTPMD_LOG(ERR, "Cannot create memory area\n"); 1006 return -1; 1007 } 1008 1009 /* we now have a valid memory area, so add it to heap */ 1010 ret = rte_malloc_heap_memory_add(EXTMEM_HEAP_NAME, 1011 param.addr, param.len, param.iova_table, 1012 param.iova_table_len, param.pgsz); 1013 1014 /* when using VFIO, memory is automatically mapped for DMA by EAL */ 1015 1016 /* not needed any more */ 1017 free(param.iova_table); 1018 1019 if (ret < 0) { 1020 TESTPMD_LOG(ERR, "Cannot add memory to heap\n"); 1021 munmap(param.addr, param.len); 1022 return -1; 1023 } 1024 1025 /* success */ 1026 1027 TESTPMD_LOG(DEBUG, "Allocated %zuMB of external memory\n", 1028 param.len >> 20); 1029 1030 return 0; 1031 } 1032 static void 1033 dma_unmap_cb(struct rte_mempool *mp __rte_unused, void *opaque __rte_unused, 1034 struct rte_mempool_memhdr *memhdr, unsigned mem_idx __rte_unused) 1035 { 1036 uint16_t pid = 0; 1037 int ret; 1038 1039 RTE_ETH_FOREACH_DEV(pid) { 1040 struct rte_eth_dev_info dev_info; 1041 1042 ret = eth_dev_info_get_print_err(pid, &dev_info); 1043 if (ret != 0) { 1044 TESTPMD_LOG(DEBUG, 1045 "unable to get device info for port %d on addr 0x%p," 1046 "mempool unmapping will not be performed\n", 1047 pid, memhdr->addr); 1048 continue; 1049 } 1050 1051 ret = rte_dev_dma_unmap(dev_info.device, memhdr->addr, 0, memhdr->len); 1052 if (ret) { 1053 TESTPMD_LOG(DEBUG, 1054 "unable to DMA unmap addr 0x%p " 1055 "for device %s\n", 1056 memhdr->addr, rte_dev_name(dev_info.device)); 1057 } 1058 } 1059 ret = rte_extmem_unregister(memhdr->addr, memhdr->len); 1060 if (ret) { 1061 TESTPMD_LOG(DEBUG, 1062 "unable to un-register addr 0x%p\n", memhdr->addr); 1063 } 1064 } 1065 1066 static void 1067 dma_map_cb(struct rte_mempool *mp __rte_unused, void *opaque __rte_unused, 1068 struct rte_mempool_memhdr *memhdr, unsigned mem_idx __rte_unused) 1069 { 1070 uint16_t pid = 0; 1071 size_t page_size = sysconf(_SC_PAGESIZE); 1072 int ret; 1073 1074 ret = rte_extmem_register(memhdr->addr, memhdr->len, NULL, 0, 1075 page_size); 1076 if (ret) { 1077 TESTPMD_LOG(DEBUG, 1078 "unable to register addr 0x%p\n", memhdr->addr); 1079 return; 1080 } 1081 RTE_ETH_FOREACH_DEV(pid) { 1082 struct rte_eth_dev_info dev_info; 1083 1084 ret = eth_dev_info_get_print_err(pid, &dev_info); 1085 if (ret != 0) { 1086 TESTPMD_LOG(DEBUG, 1087 "unable to get device info for port %d on addr 0x%p," 1088 "mempool mapping will not be performed\n", 1089 pid, memhdr->addr); 1090 continue; 1091 } 1092 ret = rte_dev_dma_map(dev_info.device, memhdr->addr, 0, memhdr->len); 1093 if (ret) { 1094 TESTPMD_LOG(DEBUG, 1095 "unable to DMA map addr 0x%p " 1096 "for device %s\n", 1097 memhdr->addr, rte_dev_name(dev_info.device)); 1098 } 1099 } 1100 } 1101 #endif 1102 1103 static unsigned int 1104 setup_extbuf(uint32_t nb_mbufs, uint16_t mbuf_sz, unsigned int socket_id, 1105 char *pool_name, struct rte_pktmbuf_extmem **ext_mem) 1106 { 1107 struct rte_pktmbuf_extmem *xmem; 1108 unsigned int ext_num, zone_num, elt_num; 1109 uint16_t elt_size; 1110 1111 elt_size = RTE_ALIGN_CEIL(mbuf_sz, RTE_CACHE_LINE_SIZE); 1112 elt_num = EXTBUF_ZONE_SIZE / elt_size; 1113 zone_num = (nb_mbufs + elt_num - 1) / elt_num; 1114 1115 xmem = malloc(sizeof(struct rte_pktmbuf_extmem) * zone_num); 1116 if (xmem == NULL) { 1117 TESTPMD_LOG(ERR, "Cannot allocate memory for " 1118 "external buffer descriptors\n"); 1119 *ext_mem = NULL; 1120 return 0; 1121 } 1122 for (ext_num = 0; ext_num < zone_num; ext_num++) { 1123 struct rte_pktmbuf_extmem *xseg = xmem + ext_num; 1124 const struct rte_memzone *mz; 1125 char mz_name[RTE_MEMZONE_NAMESIZE]; 1126 int ret; 1127 1128 ret = snprintf(mz_name, sizeof(mz_name), 1129 RTE_MEMPOOL_MZ_FORMAT "_xb_%u", pool_name, ext_num); 1130 if (ret < 0 || ret >= (int)sizeof(mz_name)) { 1131 errno = ENAMETOOLONG; 1132 ext_num = 0; 1133 break; 1134 } 1135 mz = rte_memzone_reserve(mz_name, EXTBUF_ZONE_SIZE, 1136 socket_id, 1137 RTE_MEMZONE_IOVA_CONTIG | 1138 RTE_MEMZONE_1GB | 1139 RTE_MEMZONE_SIZE_HINT_ONLY); 1140 if (mz == NULL) { 1141 /* 1142 * The caller exits on external buffer creation 1143 * error, so there is no need to free memzones. 1144 */ 1145 errno = ENOMEM; 1146 ext_num = 0; 1147 break; 1148 } 1149 xseg->buf_ptr = mz->addr; 1150 xseg->buf_iova = mz->iova; 1151 xseg->buf_len = EXTBUF_ZONE_SIZE; 1152 xseg->elt_size = elt_size; 1153 } 1154 if (ext_num == 0 && xmem != NULL) { 1155 free(xmem); 1156 xmem = NULL; 1157 } 1158 *ext_mem = xmem; 1159 return ext_num; 1160 } 1161 1162 /* 1163 * Configuration initialisation done once at init time. 1164 */ 1165 static struct rte_mempool * 1166 mbuf_pool_create(uint16_t mbuf_seg_size, unsigned nb_mbuf, 1167 unsigned int socket_id, uint16_t size_idx) 1168 { 1169 char pool_name[RTE_MEMPOOL_NAMESIZE]; 1170 struct rte_mempool *rte_mp = NULL; 1171 #ifndef RTE_EXEC_ENV_WINDOWS 1172 uint32_t mb_size; 1173 1174 mb_size = sizeof(struct rte_mbuf) + mbuf_seg_size; 1175 #endif 1176 mbuf_poolname_build(socket_id, pool_name, sizeof(pool_name), size_idx); 1177 if (!is_proc_primary()) { 1178 rte_mp = rte_mempool_lookup(pool_name); 1179 if (rte_mp == NULL) 1180 rte_exit(EXIT_FAILURE, 1181 "Get mbuf pool for socket %u failed: %s\n", 1182 socket_id, rte_strerror(rte_errno)); 1183 return rte_mp; 1184 } 1185 1186 TESTPMD_LOG(INFO, 1187 "create a new mbuf pool <%s>: n=%u, size=%u, socket=%u\n", 1188 pool_name, nb_mbuf, mbuf_seg_size, socket_id); 1189 1190 switch (mp_alloc_type) { 1191 case MP_ALLOC_NATIVE: 1192 { 1193 /* wrapper to rte_mempool_create() */ 1194 TESTPMD_LOG(INFO, "preferred mempool ops selected: %s\n", 1195 rte_mbuf_best_mempool_ops()); 1196 rte_mp = rte_pktmbuf_pool_create(pool_name, nb_mbuf, 1197 mb_mempool_cache, 0, mbuf_seg_size, socket_id); 1198 break; 1199 } 1200 #ifndef RTE_EXEC_ENV_WINDOWS 1201 case MP_ALLOC_ANON: 1202 { 1203 rte_mp = rte_mempool_create_empty(pool_name, nb_mbuf, 1204 mb_size, (unsigned int) mb_mempool_cache, 1205 sizeof(struct rte_pktmbuf_pool_private), 1206 socket_id, mempool_flags); 1207 if (rte_mp == NULL) 1208 goto err; 1209 1210 if (rte_mempool_populate_anon(rte_mp) == 0) { 1211 rte_mempool_free(rte_mp); 1212 rte_mp = NULL; 1213 goto err; 1214 } 1215 rte_pktmbuf_pool_init(rte_mp, NULL); 1216 rte_mempool_obj_iter(rte_mp, rte_pktmbuf_init, NULL); 1217 rte_mempool_mem_iter(rte_mp, dma_map_cb, NULL); 1218 break; 1219 } 1220 case MP_ALLOC_XMEM: 1221 case MP_ALLOC_XMEM_HUGE: 1222 { 1223 int heap_socket; 1224 bool huge = mp_alloc_type == MP_ALLOC_XMEM_HUGE; 1225 1226 if (setup_extmem(nb_mbuf, mbuf_seg_size, huge) < 0) 1227 rte_exit(EXIT_FAILURE, "Could not create external memory\n"); 1228 1229 heap_socket = 1230 rte_malloc_heap_get_socket(EXTMEM_HEAP_NAME); 1231 if (heap_socket < 0) 1232 rte_exit(EXIT_FAILURE, "Could not get external memory socket ID\n"); 1233 1234 TESTPMD_LOG(INFO, "preferred mempool ops selected: %s\n", 1235 rte_mbuf_best_mempool_ops()); 1236 rte_mp = rte_pktmbuf_pool_create(pool_name, nb_mbuf, 1237 mb_mempool_cache, 0, mbuf_seg_size, 1238 heap_socket); 1239 break; 1240 } 1241 #endif 1242 case MP_ALLOC_XBUF: 1243 { 1244 struct rte_pktmbuf_extmem *ext_mem; 1245 unsigned int ext_num; 1246 1247 ext_num = setup_extbuf(nb_mbuf, mbuf_seg_size, 1248 socket_id, pool_name, &ext_mem); 1249 if (ext_num == 0) 1250 rte_exit(EXIT_FAILURE, 1251 "Can't create pinned data buffers\n"); 1252 1253 TESTPMD_LOG(INFO, "preferred mempool ops selected: %s\n", 1254 rte_mbuf_best_mempool_ops()); 1255 rte_mp = rte_pktmbuf_pool_create_extbuf 1256 (pool_name, nb_mbuf, mb_mempool_cache, 1257 0, mbuf_seg_size, socket_id, 1258 ext_mem, ext_num); 1259 free(ext_mem); 1260 break; 1261 } 1262 default: 1263 { 1264 rte_exit(EXIT_FAILURE, "Invalid mempool creation mode\n"); 1265 } 1266 } 1267 1268 #ifndef RTE_EXEC_ENV_WINDOWS 1269 err: 1270 #endif 1271 if (rte_mp == NULL) { 1272 rte_exit(EXIT_FAILURE, 1273 "Creation of mbuf pool for socket %u failed: %s\n", 1274 socket_id, rte_strerror(rte_errno)); 1275 } else if (verbose_level > 0) { 1276 rte_mempool_dump(stdout, rte_mp); 1277 } 1278 return rte_mp; 1279 } 1280 1281 /* 1282 * Check given socket id is valid or not with NUMA mode, 1283 * if valid, return 0, else return -1 1284 */ 1285 static int 1286 check_socket_id(const unsigned int socket_id) 1287 { 1288 static int warning_once = 0; 1289 1290 if (new_socket_id(socket_id)) { 1291 if (!warning_once && numa_support) 1292 fprintf(stderr, 1293 "Warning: NUMA should be configured manually by using --port-numa-config and --ring-numa-config parameters along with --numa.\n"); 1294 warning_once = 1; 1295 return -1; 1296 } 1297 return 0; 1298 } 1299 1300 /* 1301 * Get the allowed maximum number of RX queues. 1302 * *pid return the port id which has minimal value of 1303 * max_rx_queues in all ports. 1304 */ 1305 queueid_t 1306 get_allowed_max_nb_rxq(portid_t *pid) 1307 { 1308 queueid_t allowed_max_rxq = RTE_MAX_QUEUES_PER_PORT; 1309 bool max_rxq_valid = false; 1310 portid_t pi; 1311 struct rte_eth_dev_info dev_info; 1312 1313 RTE_ETH_FOREACH_DEV(pi) { 1314 if (eth_dev_info_get_print_err(pi, &dev_info) != 0) 1315 continue; 1316 1317 max_rxq_valid = true; 1318 if (dev_info.max_rx_queues < allowed_max_rxq) { 1319 allowed_max_rxq = dev_info.max_rx_queues; 1320 *pid = pi; 1321 } 1322 } 1323 return max_rxq_valid ? allowed_max_rxq : 0; 1324 } 1325 1326 /* 1327 * Check input rxq is valid or not. 1328 * If input rxq is not greater than any of maximum number 1329 * of RX queues of all ports, it is valid. 1330 * if valid, return 0, else return -1 1331 */ 1332 int 1333 check_nb_rxq(queueid_t rxq) 1334 { 1335 queueid_t allowed_max_rxq; 1336 portid_t pid = 0; 1337 1338 allowed_max_rxq = get_allowed_max_nb_rxq(&pid); 1339 if (rxq > allowed_max_rxq) { 1340 fprintf(stderr, 1341 "Fail: input rxq (%u) can't be greater than max_rx_queues (%u) of port %u\n", 1342 rxq, allowed_max_rxq, pid); 1343 return -1; 1344 } 1345 return 0; 1346 } 1347 1348 /* 1349 * Get the allowed maximum number of TX queues. 1350 * *pid return the port id which has minimal value of 1351 * max_tx_queues in all ports. 1352 */ 1353 queueid_t 1354 get_allowed_max_nb_txq(portid_t *pid) 1355 { 1356 queueid_t allowed_max_txq = RTE_MAX_QUEUES_PER_PORT; 1357 bool max_txq_valid = false; 1358 portid_t pi; 1359 struct rte_eth_dev_info dev_info; 1360 1361 RTE_ETH_FOREACH_DEV(pi) { 1362 if (eth_dev_info_get_print_err(pi, &dev_info) != 0) 1363 continue; 1364 1365 max_txq_valid = true; 1366 if (dev_info.max_tx_queues < allowed_max_txq) { 1367 allowed_max_txq = dev_info.max_tx_queues; 1368 *pid = pi; 1369 } 1370 } 1371 return max_txq_valid ? allowed_max_txq : 0; 1372 } 1373 1374 /* 1375 * Check input txq is valid or not. 1376 * If input txq is not greater than any of maximum number 1377 * of TX queues of all ports, it is valid. 1378 * if valid, return 0, else return -1 1379 */ 1380 int 1381 check_nb_txq(queueid_t txq) 1382 { 1383 queueid_t allowed_max_txq; 1384 portid_t pid = 0; 1385 1386 allowed_max_txq = get_allowed_max_nb_txq(&pid); 1387 if (txq > allowed_max_txq) { 1388 fprintf(stderr, 1389 "Fail: input txq (%u) can't be greater than max_tx_queues (%u) of port %u\n", 1390 txq, allowed_max_txq, pid); 1391 return -1; 1392 } 1393 return 0; 1394 } 1395 1396 /* 1397 * Get the allowed maximum number of RXDs of every rx queue. 1398 * *pid return the port id which has minimal value of 1399 * max_rxd in all queues of all ports. 1400 */ 1401 static uint16_t 1402 get_allowed_max_nb_rxd(portid_t *pid) 1403 { 1404 uint16_t allowed_max_rxd = UINT16_MAX; 1405 portid_t pi; 1406 struct rte_eth_dev_info dev_info; 1407 1408 RTE_ETH_FOREACH_DEV(pi) { 1409 if (eth_dev_info_get_print_err(pi, &dev_info) != 0) 1410 continue; 1411 1412 if (dev_info.rx_desc_lim.nb_max < allowed_max_rxd) { 1413 allowed_max_rxd = dev_info.rx_desc_lim.nb_max; 1414 *pid = pi; 1415 } 1416 } 1417 return allowed_max_rxd; 1418 } 1419 1420 /* 1421 * Get the allowed minimal number of RXDs of every rx queue. 1422 * *pid return the port id which has minimal value of 1423 * min_rxd in all queues of all ports. 1424 */ 1425 static uint16_t 1426 get_allowed_min_nb_rxd(portid_t *pid) 1427 { 1428 uint16_t allowed_min_rxd = 0; 1429 portid_t pi; 1430 struct rte_eth_dev_info dev_info; 1431 1432 RTE_ETH_FOREACH_DEV(pi) { 1433 if (eth_dev_info_get_print_err(pi, &dev_info) != 0) 1434 continue; 1435 1436 if (dev_info.rx_desc_lim.nb_min > allowed_min_rxd) { 1437 allowed_min_rxd = dev_info.rx_desc_lim.nb_min; 1438 *pid = pi; 1439 } 1440 } 1441 1442 return allowed_min_rxd; 1443 } 1444 1445 /* 1446 * Check input rxd is valid or not. 1447 * If input rxd is not greater than any of maximum number 1448 * of RXDs of every Rx queues and is not less than any of 1449 * minimal number of RXDs of every Rx queues, it is valid. 1450 * if valid, return 0, else return -1 1451 */ 1452 int 1453 check_nb_rxd(queueid_t rxd) 1454 { 1455 uint16_t allowed_max_rxd; 1456 uint16_t allowed_min_rxd; 1457 portid_t pid = 0; 1458 1459 allowed_max_rxd = get_allowed_max_nb_rxd(&pid); 1460 if (rxd > allowed_max_rxd) { 1461 fprintf(stderr, 1462 "Fail: input rxd (%u) can't be greater than max_rxds (%u) of port %u\n", 1463 rxd, allowed_max_rxd, pid); 1464 return -1; 1465 } 1466 1467 allowed_min_rxd = get_allowed_min_nb_rxd(&pid); 1468 if (rxd < allowed_min_rxd) { 1469 fprintf(stderr, 1470 "Fail: input rxd (%u) can't be less than min_rxds (%u) of port %u\n", 1471 rxd, allowed_min_rxd, pid); 1472 return -1; 1473 } 1474 1475 return 0; 1476 } 1477 1478 /* 1479 * Get the allowed maximum number of TXDs of every rx queues. 1480 * *pid return the port id which has minimal value of 1481 * max_txd in every tx queue. 1482 */ 1483 static uint16_t 1484 get_allowed_max_nb_txd(portid_t *pid) 1485 { 1486 uint16_t allowed_max_txd = UINT16_MAX; 1487 portid_t pi; 1488 struct rte_eth_dev_info dev_info; 1489 1490 RTE_ETH_FOREACH_DEV(pi) { 1491 if (eth_dev_info_get_print_err(pi, &dev_info) != 0) 1492 continue; 1493 1494 if (dev_info.tx_desc_lim.nb_max < allowed_max_txd) { 1495 allowed_max_txd = dev_info.tx_desc_lim.nb_max; 1496 *pid = pi; 1497 } 1498 } 1499 return allowed_max_txd; 1500 } 1501 1502 /* 1503 * Get the allowed maximum number of TXDs of every tx queues. 1504 * *pid return the port id which has minimal value of 1505 * min_txd in every tx queue. 1506 */ 1507 static uint16_t 1508 get_allowed_min_nb_txd(portid_t *pid) 1509 { 1510 uint16_t allowed_min_txd = 0; 1511 portid_t pi; 1512 struct rte_eth_dev_info dev_info; 1513 1514 RTE_ETH_FOREACH_DEV(pi) { 1515 if (eth_dev_info_get_print_err(pi, &dev_info) != 0) 1516 continue; 1517 1518 if (dev_info.tx_desc_lim.nb_min > allowed_min_txd) { 1519 allowed_min_txd = dev_info.tx_desc_lim.nb_min; 1520 *pid = pi; 1521 } 1522 } 1523 1524 return allowed_min_txd; 1525 } 1526 1527 /* 1528 * Check input txd is valid or not. 1529 * If input txd is not greater than any of maximum number 1530 * of TXDs of every Rx queues, it is valid. 1531 * if valid, return 0, else return -1 1532 */ 1533 int 1534 check_nb_txd(queueid_t txd) 1535 { 1536 uint16_t allowed_max_txd; 1537 uint16_t allowed_min_txd; 1538 portid_t pid = 0; 1539 1540 allowed_max_txd = get_allowed_max_nb_txd(&pid); 1541 if (txd > allowed_max_txd) { 1542 fprintf(stderr, 1543 "Fail: input txd (%u) can't be greater than max_txds (%u) of port %u\n", 1544 txd, allowed_max_txd, pid); 1545 return -1; 1546 } 1547 1548 allowed_min_txd = get_allowed_min_nb_txd(&pid); 1549 if (txd < allowed_min_txd) { 1550 fprintf(stderr, 1551 "Fail: input txd (%u) can't be less than min_txds (%u) of port %u\n", 1552 txd, allowed_min_txd, pid); 1553 return -1; 1554 } 1555 return 0; 1556 } 1557 1558 1559 /* 1560 * Get the allowed maximum number of hairpin queues. 1561 * *pid return the port id which has minimal value of 1562 * max_hairpin_queues in all ports. 1563 */ 1564 queueid_t 1565 get_allowed_max_nb_hairpinq(portid_t *pid) 1566 { 1567 queueid_t allowed_max_hairpinq = RTE_MAX_QUEUES_PER_PORT; 1568 portid_t pi; 1569 struct rte_eth_hairpin_cap cap; 1570 1571 RTE_ETH_FOREACH_DEV(pi) { 1572 if (rte_eth_dev_hairpin_capability_get(pi, &cap) != 0) { 1573 *pid = pi; 1574 return 0; 1575 } 1576 if (cap.max_nb_queues < allowed_max_hairpinq) { 1577 allowed_max_hairpinq = cap.max_nb_queues; 1578 *pid = pi; 1579 } 1580 } 1581 return allowed_max_hairpinq; 1582 } 1583 1584 /* 1585 * Check input hairpin is valid or not. 1586 * If input hairpin is not greater than any of maximum number 1587 * of hairpin queues of all ports, it is valid. 1588 * if valid, return 0, else return -1 1589 */ 1590 int 1591 check_nb_hairpinq(queueid_t hairpinq) 1592 { 1593 queueid_t allowed_max_hairpinq; 1594 portid_t pid = 0; 1595 1596 allowed_max_hairpinq = get_allowed_max_nb_hairpinq(&pid); 1597 if (hairpinq > allowed_max_hairpinq) { 1598 fprintf(stderr, 1599 "Fail: input hairpin (%u) can't be greater than max_hairpin_queues (%u) of port %u\n", 1600 hairpinq, allowed_max_hairpinq, pid); 1601 return -1; 1602 } 1603 return 0; 1604 } 1605 1606 static int 1607 get_eth_overhead(struct rte_eth_dev_info *dev_info) 1608 { 1609 uint32_t eth_overhead; 1610 1611 if (dev_info->max_mtu != UINT16_MAX && 1612 dev_info->max_rx_pktlen > dev_info->max_mtu) 1613 eth_overhead = dev_info->max_rx_pktlen - dev_info->max_mtu; 1614 else 1615 eth_overhead = RTE_ETHER_HDR_LEN + RTE_ETHER_CRC_LEN; 1616 1617 return eth_overhead; 1618 } 1619 1620 static void 1621 init_config_port_offloads(portid_t pid, uint32_t socket_id) 1622 { 1623 struct rte_port *port = &ports[pid]; 1624 int ret; 1625 int i; 1626 1627 eth_rx_metadata_negotiate_mp(pid); 1628 1629 port->dev_conf.txmode = tx_mode; 1630 port->dev_conf.rxmode = rx_mode; 1631 1632 ret = eth_dev_info_get_print_err(pid, &port->dev_info); 1633 if (ret != 0) 1634 rte_exit(EXIT_FAILURE, "rte_eth_dev_info_get() failed\n"); 1635 1636 if (!(port->dev_info.tx_offload_capa & RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE)) 1637 port->dev_conf.txmode.offloads &= 1638 ~RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE; 1639 1640 /* Apply Rx offloads configuration */ 1641 for (i = 0; i < port->dev_info.max_rx_queues; i++) 1642 port->rxq[i].conf.offloads = port->dev_conf.rxmode.offloads; 1643 /* Apply Tx offloads configuration */ 1644 for (i = 0; i < port->dev_info.max_tx_queues; i++) 1645 port->txq[i].conf.offloads = port->dev_conf.txmode.offloads; 1646 1647 if (eth_link_speed) 1648 port->dev_conf.link_speeds = eth_link_speed; 1649 1650 if (max_rx_pkt_len) 1651 port->dev_conf.rxmode.mtu = max_rx_pkt_len - 1652 get_eth_overhead(&port->dev_info); 1653 1654 /* set flag to initialize port/queue */ 1655 port->need_reconfig = 1; 1656 port->need_reconfig_queues = 1; 1657 port->socket_id = socket_id; 1658 port->tx_metadata = 0; 1659 1660 /* 1661 * Check for maximum number of segments per MTU. 1662 * Accordingly update the mbuf data size. 1663 */ 1664 if (port->dev_info.rx_desc_lim.nb_mtu_seg_max != UINT16_MAX && 1665 port->dev_info.rx_desc_lim.nb_mtu_seg_max != 0) { 1666 uint32_t eth_overhead = get_eth_overhead(&port->dev_info); 1667 uint16_t mtu; 1668 1669 if (rte_eth_dev_get_mtu(pid, &mtu) == 0) { 1670 uint16_t data_size = (mtu + eth_overhead) / 1671 port->dev_info.rx_desc_lim.nb_mtu_seg_max; 1672 uint16_t buffer_size = data_size + RTE_PKTMBUF_HEADROOM; 1673 1674 if (buffer_size > mbuf_data_size[0]) { 1675 mbuf_data_size[0] = buffer_size; 1676 TESTPMD_LOG(WARNING, 1677 "Configured mbuf size of the first segment %hu\n", 1678 mbuf_data_size[0]); 1679 } 1680 } 1681 } 1682 } 1683 1684 static void 1685 init_config(void) 1686 { 1687 portid_t pid; 1688 struct rte_mempool *mbp; 1689 unsigned int nb_mbuf_per_pool; 1690 lcoreid_t lc_id; 1691 #ifdef RTE_LIB_GRO 1692 struct rte_gro_param gro_param; 1693 #endif 1694 #ifdef RTE_LIB_GSO 1695 uint32_t gso_types; 1696 #endif 1697 1698 /* Configuration of logical cores. */ 1699 fwd_lcores = rte_zmalloc("testpmd: fwd_lcores", 1700 sizeof(struct fwd_lcore *) * nb_lcores, 1701 RTE_CACHE_LINE_SIZE); 1702 if (fwd_lcores == NULL) { 1703 rte_exit(EXIT_FAILURE, "rte_zmalloc(%d (struct fwd_lcore *)) " 1704 "failed\n", nb_lcores); 1705 } 1706 for (lc_id = 0; lc_id < nb_lcores; lc_id++) { 1707 fwd_lcores[lc_id] = rte_zmalloc("testpmd: struct fwd_lcore", 1708 sizeof(struct fwd_lcore), 1709 RTE_CACHE_LINE_SIZE); 1710 if (fwd_lcores[lc_id] == NULL) { 1711 rte_exit(EXIT_FAILURE, "rte_zmalloc(struct fwd_lcore) " 1712 "failed\n"); 1713 } 1714 fwd_lcores[lc_id]->cpuid_idx = lc_id; 1715 } 1716 1717 RTE_ETH_FOREACH_DEV(pid) { 1718 uint32_t socket_id; 1719 1720 if (numa_support) { 1721 socket_id = port_numa[pid]; 1722 if (port_numa[pid] == NUMA_NO_CONFIG) { 1723 socket_id = rte_eth_dev_socket_id(pid); 1724 1725 /* 1726 * if socket_id is invalid, 1727 * set to the first available socket. 1728 */ 1729 if (check_socket_id(socket_id) < 0) 1730 socket_id = socket_ids[0]; 1731 } 1732 } else { 1733 socket_id = (socket_num == UMA_NO_CONFIG) ? 1734 0 : socket_num; 1735 } 1736 /* Apply default TxRx configuration for all ports */ 1737 init_config_port_offloads(pid, socket_id); 1738 } 1739 /* 1740 * Create pools of mbuf. 1741 * If NUMA support is disabled, create a single pool of mbuf in 1742 * socket 0 memory by default. 1743 * Otherwise, create a pool of mbuf in the memory of sockets 0 and 1. 1744 * 1745 * Use the maximum value of nb_rxd and nb_txd here, then nb_rxd and 1746 * nb_txd can be configured at run time. 1747 */ 1748 if (param_total_num_mbufs) 1749 nb_mbuf_per_pool = param_total_num_mbufs; 1750 else { 1751 nb_mbuf_per_pool = RX_DESC_MAX + 1752 (nb_lcores * mb_mempool_cache) + 1753 TX_DESC_MAX + MAX_PKT_BURST; 1754 nb_mbuf_per_pool *= RTE_MAX_ETHPORTS; 1755 } 1756 1757 if (numa_support) { 1758 uint8_t i, j; 1759 1760 for (i = 0; i < num_sockets; i++) 1761 for (j = 0; j < mbuf_data_size_n; j++) 1762 mempools[i * MAX_SEGS_BUFFER_SPLIT + j] = 1763 mbuf_pool_create(mbuf_data_size[j], 1764 nb_mbuf_per_pool, 1765 socket_ids[i], j); 1766 } else { 1767 uint8_t i; 1768 1769 for (i = 0; i < mbuf_data_size_n; i++) 1770 mempools[i] = mbuf_pool_create 1771 (mbuf_data_size[i], 1772 nb_mbuf_per_pool, 1773 socket_num == UMA_NO_CONFIG ? 1774 0 : socket_num, i); 1775 } 1776 1777 init_port_config(); 1778 1779 #ifdef RTE_LIB_GSO 1780 gso_types = RTE_ETH_TX_OFFLOAD_TCP_TSO | RTE_ETH_TX_OFFLOAD_VXLAN_TNL_TSO | 1781 RTE_ETH_TX_OFFLOAD_GRE_TNL_TSO | RTE_ETH_TX_OFFLOAD_UDP_TSO; 1782 #endif 1783 /* 1784 * Records which Mbuf pool to use by each logical core, if needed. 1785 */ 1786 for (lc_id = 0; lc_id < nb_lcores; lc_id++) { 1787 mbp = mbuf_pool_find( 1788 rte_lcore_to_socket_id(fwd_lcores_cpuids[lc_id]), 0); 1789 1790 if (mbp == NULL) 1791 mbp = mbuf_pool_find(0, 0); 1792 fwd_lcores[lc_id]->mbp = mbp; 1793 #ifdef RTE_LIB_GSO 1794 /* initialize GSO context */ 1795 fwd_lcores[lc_id]->gso_ctx.direct_pool = mbp; 1796 fwd_lcores[lc_id]->gso_ctx.indirect_pool = mbp; 1797 fwd_lcores[lc_id]->gso_ctx.gso_types = gso_types; 1798 fwd_lcores[lc_id]->gso_ctx.gso_size = RTE_ETHER_MAX_LEN - 1799 RTE_ETHER_CRC_LEN; 1800 fwd_lcores[lc_id]->gso_ctx.flag = 0; 1801 #endif 1802 } 1803 1804 fwd_config_setup(); 1805 1806 #ifdef RTE_LIB_GRO 1807 /* create a gro context for each lcore */ 1808 gro_param.gro_types = RTE_GRO_TCP_IPV4; 1809 gro_param.max_flow_num = GRO_MAX_FLUSH_CYCLES; 1810 gro_param.max_item_per_flow = MAX_PKT_BURST; 1811 for (lc_id = 0; lc_id < nb_lcores; lc_id++) { 1812 gro_param.socket_id = rte_lcore_to_socket_id( 1813 fwd_lcores_cpuids[lc_id]); 1814 fwd_lcores[lc_id]->gro_ctx = rte_gro_ctx_create(&gro_param); 1815 if (fwd_lcores[lc_id]->gro_ctx == NULL) { 1816 rte_exit(EXIT_FAILURE, 1817 "rte_gro_ctx_create() failed\n"); 1818 } 1819 } 1820 #endif 1821 } 1822 1823 1824 void 1825 reconfig(portid_t new_port_id, unsigned socket_id) 1826 { 1827 /* Reconfiguration of Ethernet ports. */ 1828 init_config_port_offloads(new_port_id, socket_id); 1829 init_port_config(); 1830 } 1831 1832 int 1833 init_fwd_streams(void) 1834 { 1835 portid_t pid; 1836 struct rte_port *port; 1837 streamid_t sm_id, nb_fwd_streams_new; 1838 queueid_t q; 1839 1840 /* set socket id according to numa or not */ 1841 RTE_ETH_FOREACH_DEV(pid) { 1842 port = &ports[pid]; 1843 if (nb_rxq > port->dev_info.max_rx_queues) { 1844 fprintf(stderr, 1845 "Fail: nb_rxq(%d) is greater than max_rx_queues(%d)\n", 1846 nb_rxq, port->dev_info.max_rx_queues); 1847 return -1; 1848 } 1849 if (nb_txq > port->dev_info.max_tx_queues) { 1850 fprintf(stderr, 1851 "Fail: nb_txq(%d) is greater than max_tx_queues(%d)\n", 1852 nb_txq, port->dev_info.max_tx_queues); 1853 return -1; 1854 } 1855 if (numa_support) { 1856 if (port_numa[pid] != NUMA_NO_CONFIG) 1857 port->socket_id = port_numa[pid]; 1858 else { 1859 port->socket_id = rte_eth_dev_socket_id(pid); 1860 1861 /* 1862 * if socket_id is invalid, 1863 * set to the first available socket. 1864 */ 1865 if (check_socket_id(port->socket_id) < 0) 1866 port->socket_id = socket_ids[0]; 1867 } 1868 } 1869 else { 1870 if (socket_num == UMA_NO_CONFIG) 1871 port->socket_id = 0; 1872 else 1873 port->socket_id = socket_num; 1874 } 1875 } 1876 1877 q = RTE_MAX(nb_rxq, nb_txq); 1878 if (q == 0) { 1879 fprintf(stderr, 1880 "Fail: Cannot allocate fwd streams as number of queues is 0\n"); 1881 return -1; 1882 } 1883 nb_fwd_streams_new = (streamid_t)(nb_ports * q); 1884 if (nb_fwd_streams_new == nb_fwd_streams) 1885 return 0; 1886 /* clear the old */ 1887 if (fwd_streams != NULL) { 1888 for (sm_id = 0; sm_id < nb_fwd_streams; sm_id++) { 1889 if (fwd_streams[sm_id] == NULL) 1890 continue; 1891 rte_free(fwd_streams[sm_id]); 1892 fwd_streams[sm_id] = NULL; 1893 } 1894 rte_free(fwd_streams); 1895 fwd_streams = NULL; 1896 } 1897 1898 /* init new */ 1899 nb_fwd_streams = nb_fwd_streams_new; 1900 if (nb_fwd_streams) { 1901 fwd_streams = rte_zmalloc("testpmd: fwd_streams", 1902 sizeof(struct fwd_stream *) * nb_fwd_streams, 1903 RTE_CACHE_LINE_SIZE); 1904 if (fwd_streams == NULL) 1905 rte_exit(EXIT_FAILURE, "rte_zmalloc(%d" 1906 " (struct fwd_stream *)) failed\n", 1907 nb_fwd_streams); 1908 1909 for (sm_id = 0; sm_id < nb_fwd_streams; sm_id++) { 1910 fwd_streams[sm_id] = rte_zmalloc("testpmd:" 1911 " struct fwd_stream", sizeof(struct fwd_stream), 1912 RTE_CACHE_LINE_SIZE); 1913 if (fwd_streams[sm_id] == NULL) 1914 rte_exit(EXIT_FAILURE, "rte_zmalloc" 1915 "(struct fwd_stream) failed\n"); 1916 } 1917 } 1918 1919 return 0; 1920 } 1921 1922 static void 1923 pkt_burst_stats_display(const char *rx_tx, struct pkt_burst_stats *pbs) 1924 { 1925 uint64_t total_burst, sburst; 1926 uint64_t nb_burst; 1927 uint64_t burst_stats[4]; 1928 uint16_t pktnb_stats[4]; 1929 uint16_t nb_pkt; 1930 int burst_percent[4], sburstp; 1931 int i; 1932 1933 /* 1934 * First compute the total number of packet bursts and the 1935 * two highest numbers of bursts of the same number of packets. 1936 */ 1937 memset(&burst_stats, 0x0, sizeof(burst_stats)); 1938 memset(&pktnb_stats, 0x0, sizeof(pktnb_stats)); 1939 1940 /* Show stats for 0 burst size always */ 1941 total_burst = pbs->pkt_burst_spread[0]; 1942 burst_stats[0] = pbs->pkt_burst_spread[0]; 1943 pktnb_stats[0] = 0; 1944 1945 /* Find the next 2 burst sizes with highest occurrences. */ 1946 for (nb_pkt = 1; nb_pkt < MAX_PKT_BURST + 1; nb_pkt++) { 1947 nb_burst = pbs->pkt_burst_spread[nb_pkt]; 1948 1949 if (nb_burst == 0) 1950 continue; 1951 1952 total_burst += nb_burst; 1953 1954 if (nb_burst > burst_stats[1]) { 1955 burst_stats[2] = burst_stats[1]; 1956 pktnb_stats[2] = pktnb_stats[1]; 1957 burst_stats[1] = nb_burst; 1958 pktnb_stats[1] = nb_pkt; 1959 } else if (nb_burst > burst_stats[2]) { 1960 burst_stats[2] = nb_burst; 1961 pktnb_stats[2] = nb_pkt; 1962 } 1963 } 1964 if (total_burst == 0) 1965 return; 1966 1967 printf(" %s-bursts : %"PRIu64" [", rx_tx, total_burst); 1968 for (i = 0, sburst = 0, sburstp = 0; i < 4; i++) { 1969 if (i == 3) { 1970 printf("%d%% of other]\n", 100 - sburstp); 1971 return; 1972 } 1973 1974 sburst += burst_stats[i]; 1975 if (sburst == total_burst) { 1976 printf("%d%% of %d pkts]\n", 1977 100 - sburstp, (int) pktnb_stats[i]); 1978 return; 1979 } 1980 1981 burst_percent[i] = 1982 (double)burst_stats[i] / total_burst * 100; 1983 printf("%d%% of %d pkts + ", 1984 burst_percent[i], (int) pktnb_stats[i]); 1985 sburstp += burst_percent[i]; 1986 } 1987 } 1988 1989 static void 1990 fwd_stream_stats_display(streamid_t stream_id) 1991 { 1992 struct fwd_stream *fs; 1993 static const char *fwd_top_stats_border = "-------"; 1994 1995 fs = fwd_streams[stream_id]; 1996 if ((fs->rx_packets == 0) && (fs->tx_packets == 0) && 1997 (fs->fwd_dropped == 0)) 1998 return; 1999 printf("\n %s Forward Stats for RX Port=%2d/Queue=%2d -> " 2000 "TX Port=%2d/Queue=%2d %s\n", 2001 fwd_top_stats_border, fs->rx_port, fs->rx_queue, 2002 fs->tx_port, fs->tx_queue, fwd_top_stats_border); 2003 printf(" RX-packets: %-14"PRIu64" TX-packets: %-14"PRIu64 2004 " TX-dropped: %-14"PRIu64, 2005 fs->rx_packets, fs->tx_packets, fs->fwd_dropped); 2006 2007 /* if checksum mode */ 2008 if (cur_fwd_eng == &csum_fwd_engine) { 2009 printf(" RX- bad IP checksum: %-14"PRIu64 2010 " Rx- bad L4 checksum: %-14"PRIu64 2011 " Rx- bad outer L4 checksum: %-14"PRIu64"\n", 2012 fs->rx_bad_ip_csum, fs->rx_bad_l4_csum, 2013 fs->rx_bad_outer_l4_csum); 2014 printf(" RX- bad outer IP checksum: %-14"PRIu64"\n", 2015 fs->rx_bad_outer_ip_csum); 2016 } else { 2017 printf("\n"); 2018 } 2019 2020 if (record_burst_stats) { 2021 pkt_burst_stats_display("RX", &fs->rx_burst_stats); 2022 pkt_burst_stats_display("TX", &fs->tx_burst_stats); 2023 } 2024 } 2025 2026 void 2027 fwd_stats_display(void) 2028 { 2029 static const char *fwd_stats_border = "----------------------"; 2030 static const char *acc_stats_border = "+++++++++++++++"; 2031 struct { 2032 struct fwd_stream *rx_stream; 2033 struct fwd_stream *tx_stream; 2034 uint64_t tx_dropped; 2035 uint64_t rx_bad_ip_csum; 2036 uint64_t rx_bad_l4_csum; 2037 uint64_t rx_bad_outer_l4_csum; 2038 uint64_t rx_bad_outer_ip_csum; 2039 } ports_stats[RTE_MAX_ETHPORTS]; 2040 uint64_t total_rx_dropped = 0; 2041 uint64_t total_tx_dropped = 0; 2042 uint64_t total_rx_nombuf = 0; 2043 struct rte_eth_stats stats; 2044 uint64_t fwd_cycles = 0; 2045 uint64_t total_recv = 0; 2046 uint64_t total_xmit = 0; 2047 struct rte_port *port; 2048 streamid_t sm_id; 2049 portid_t pt_id; 2050 int ret; 2051 int i; 2052 2053 memset(ports_stats, 0, sizeof(ports_stats)); 2054 2055 for (sm_id = 0; sm_id < cur_fwd_config.nb_fwd_streams; sm_id++) { 2056 struct fwd_stream *fs = fwd_streams[sm_id]; 2057 2058 if (cur_fwd_config.nb_fwd_streams > 2059 cur_fwd_config.nb_fwd_ports) { 2060 fwd_stream_stats_display(sm_id); 2061 } else { 2062 ports_stats[fs->tx_port].tx_stream = fs; 2063 ports_stats[fs->rx_port].rx_stream = fs; 2064 } 2065 2066 ports_stats[fs->tx_port].tx_dropped += fs->fwd_dropped; 2067 2068 ports_stats[fs->rx_port].rx_bad_ip_csum += fs->rx_bad_ip_csum; 2069 ports_stats[fs->rx_port].rx_bad_l4_csum += fs->rx_bad_l4_csum; 2070 ports_stats[fs->rx_port].rx_bad_outer_l4_csum += 2071 fs->rx_bad_outer_l4_csum; 2072 ports_stats[fs->rx_port].rx_bad_outer_ip_csum += 2073 fs->rx_bad_outer_ip_csum; 2074 2075 if (record_core_cycles) 2076 fwd_cycles += fs->busy_cycles; 2077 } 2078 for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++) { 2079 uint64_t tx_dropped = 0; 2080 2081 pt_id = fwd_ports_ids[i]; 2082 port = &ports[pt_id]; 2083 2084 ret = rte_eth_stats_get(pt_id, &stats); 2085 if (ret != 0) { 2086 fprintf(stderr, 2087 "%s: Error: failed to get stats (port %u): %d", 2088 __func__, pt_id, ret); 2089 continue; 2090 } 2091 stats.ipackets -= port->stats.ipackets; 2092 stats.opackets -= port->stats.opackets; 2093 stats.ibytes -= port->stats.ibytes; 2094 stats.obytes -= port->stats.obytes; 2095 stats.imissed -= port->stats.imissed; 2096 stats.oerrors -= port->stats.oerrors; 2097 stats.rx_nombuf -= port->stats.rx_nombuf; 2098 2099 total_recv += stats.ipackets; 2100 total_xmit += stats.opackets; 2101 total_rx_dropped += stats.imissed; 2102 tx_dropped += ports_stats[pt_id].tx_dropped; 2103 tx_dropped += stats.oerrors; 2104 total_tx_dropped += tx_dropped; 2105 total_rx_nombuf += stats.rx_nombuf; 2106 2107 printf("\n %s Forward statistics for port %-2d %s\n", 2108 fwd_stats_border, pt_id, fwd_stats_border); 2109 2110 printf(" RX-packets: %-14"PRIu64" RX-dropped: %-14"PRIu64 2111 "RX-total: %-"PRIu64"\n", stats.ipackets, stats.imissed, 2112 stats.ipackets + stats.imissed); 2113 2114 if (cur_fwd_eng == &csum_fwd_engine) { 2115 printf(" Bad-ipcsum: %-14"PRIu64 2116 " Bad-l4csum: %-14"PRIu64 2117 "Bad-outer-l4csum: %-14"PRIu64"\n", 2118 ports_stats[pt_id].rx_bad_ip_csum, 2119 ports_stats[pt_id].rx_bad_l4_csum, 2120 ports_stats[pt_id].rx_bad_outer_l4_csum); 2121 printf(" Bad-outer-ipcsum: %-14"PRIu64"\n", 2122 ports_stats[pt_id].rx_bad_outer_ip_csum); 2123 } 2124 if (stats.ierrors + stats.rx_nombuf > 0) { 2125 printf(" RX-error: %-"PRIu64"\n", stats.ierrors); 2126 printf(" RX-nombufs: %-14"PRIu64"\n", stats.rx_nombuf); 2127 } 2128 2129 printf(" TX-packets: %-14"PRIu64" TX-dropped: %-14"PRIu64 2130 "TX-total: %-"PRIu64"\n", 2131 stats.opackets, tx_dropped, 2132 stats.opackets + tx_dropped); 2133 2134 if (record_burst_stats) { 2135 if (ports_stats[pt_id].rx_stream) 2136 pkt_burst_stats_display("RX", 2137 &ports_stats[pt_id].rx_stream->rx_burst_stats); 2138 if (ports_stats[pt_id].tx_stream) 2139 pkt_burst_stats_display("TX", 2140 &ports_stats[pt_id].tx_stream->tx_burst_stats); 2141 } 2142 2143 printf(" %s--------------------------------%s\n", 2144 fwd_stats_border, fwd_stats_border); 2145 } 2146 2147 printf("\n %s Accumulated forward statistics for all ports" 2148 "%s\n", 2149 acc_stats_border, acc_stats_border); 2150 printf(" RX-packets: %-14"PRIu64" RX-dropped: %-14"PRIu64"RX-total: " 2151 "%-"PRIu64"\n" 2152 " TX-packets: %-14"PRIu64" TX-dropped: %-14"PRIu64"TX-total: " 2153 "%-"PRIu64"\n", 2154 total_recv, total_rx_dropped, total_recv + total_rx_dropped, 2155 total_xmit, total_tx_dropped, total_xmit + total_tx_dropped); 2156 if (total_rx_nombuf > 0) 2157 printf(" RX-nombufs: %-14"PRIu64"\n", total_rx_nombuf); 2158 printf(" %s++++++++++++++++++++++++++++++++++++++++++++++" 2159 "%s\n", 2160 acc_stats_border, acc_stats_border); 2161 if (record_core_cycles) { 2162 #define CYC_PER_MHZ 1E6 2163 if (total_recv > 0 || total_xmit > 0) { 2164 uint64_t total_pkts = 0; 2165 if (strcmp(cur_fwd_eng->fwd_mode_name, "txonly") == 0 || 2166 strcmp(cur_fwd_eng->fwd_mode_name, "flowgen") == 0) 2167 total_pkts = total_xmit; 2168 else 2169 total_pkts = total_recv; 2170 2171 printf("\n CPU cycles/packet=%.2F (busy cycles=" 2172 "%"PRIu64" / total %s packets=%"PRIu64") at %"PRIu64 2173 " MHz Clock\n", 2174 (double) fwd_cycles / total_pkts, 2175 fwd_cycles, cur_fwd_eng->fwd_mode_name, total_pkts, 2176 (uint64_t)(rte_get_tsc_hz() / CYC_PER_MHZ)); 2177 } 2178 } 2179 } 2180 2181 void 2182 fwd_stats_reset(void) 2183 { 2184 streamid_t sm_id; 2185 portid_t pt_id; 2186 int ret; 2187 int i; 2188 2189 for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++) { 2190 pt_id = fwd_ports_ids[i]; 2191 ret = rte_eth_stats_get(pt_id, &ports[pt_id].stats); 2192 if (ret != 0) 2193 fprintf(stderr, 2194 "%s: Error: failed to clear stats (port %u):%d", 2195 __func__, pt_id, ret); 2196 } 2197 for (sm_id = 0; sm_id < cur_fwd_config.nb_fwd_streams; sm_id++) { 2198 struct fwd_stream *fs = fwd_streams[sm_id]; 2199 2200 fs->rx_packets = 0; 2201 fs->tx_packets = 0; 2202 fs->fwd_dropped = 0; 2203 fs->rx_bad_ip_csum = 0; 2204 fs->rx_bad_l4_csum = 0; 2205 fs->rx_bad_outer_l4_csum = 0; 2206 fs->rx_bad_outer_ip_csum = 0; 2207 2208 memset(&fs->rx_burst_stats, 0, sizeof(fs->rx_burst_stats)); 2209 memset(&fs->tx_burst_stats, 0, sizeof(fs->tx_burst_stats)); 2210 fs->busy_cycles = 0; 2211 } 2212 } 2213 2214 static void 2215 flush_fwd_rx_queues(void) 2216 { 2217 struct rte_mbuf *pkts_burst[MAX_PKT_BURST]; 2218 portid_t rxp; 2219 portid_t port_id; 2220 queueid_t rxq; 2221 uint16_t nb_rx; 2222 uint8_t j; 2223 uint64_t prev_tsc = 0, diff_tsc, cur_tsc, timer_tsc = 0; 2224 uint64_t timer_period; 2225 2226 if (num_procs > 1) { 2227 printf("multi-process not support for flushing fwd Rx queues, skip the below lines and return.\n"); 2228 return; 2229 } 2230 2231 /* convert to number of cycles */ 2232 timer_period = rte_get_timer_hz(); /* 1 second timeout */ 2233 2234 for (j = 0; j < 2; j++) { 2235 for (rxp = 0; rxp < cur_fwd_config.nb_fwd_ports; rxp++) { 2236 for (rxq = 0; rxq < nb_rxq; rxq++) { 2237 port_id = fwd_ports_ids[rxp]; 2238 2239 /* Polling stopped queues is prohibited. */ 2240 if (ports[port_id].rxq[rxq].state == 2241 RTE_ETH_QUEUE_STATE_STOPPED) 2242 continue; 2243 2244 /** 2245 * testpmd can stuck in the below do while loop 2246 * if rte_eth_rx_burst() always returns nonzero 2247 * packets. So timer is added to exit this loop 2248 * after 1sec timer expiry. 2249 */ 2250 prev_tsc = rte_rdtsc(); 2251 do { 2252 nb_rx = rte_eth_rx_burst(port_id, rxq, 2253 pkts_burst, MAX_PKT_BURST); 2254 rte_pktmbuf_free_bulk(pkts_burst, nb_rx); 2255 2256 cur_tsc = rte_rdtsc(); 2257 diff_tsc = cur_tsc - prev_tsc; 2258 timer_tsc += diff_tsc; 2259 } while ((nb_rx > 0) && 2260 (timer_tsc < timer_period)); 2261 timer_tsc = 0; 2262 } 2263 } 2264 rte_delay_ms(10); /* wait 10 milli-seconds before retrying */ 2265 } 2266 } 2267 2268 static void 2269 run_pkt_fwd_on_lcore(struct fwd_lcore *fc, packet_fwd_t pkt_fwd) 2270 { 2271 struct fwd_stream **fsm; 2272 uint64_t prev_tsc; 2273 streamid_t nb_fs; 2274 streamid_t sm_id; 2275 #ifdef RTE_LIB_BITRATESTATS 2276 uint64_t tics_per_1sec; 2277 uint64_t tics_datum; 2278 uint64_t tics_current; 2279 uint16_t i, cnt_ports; 2280 2281 cnt_ports = nb_ports; 2282 tics_datum = rte_rdtsc(); 2283 tics_per_1sec = rte_get_timer_hz(); 2284 #endif 2285 fsm = &fwd_streams[fc->stream_idx]; 2286 nb_fs = fc->stream_nb; 2287 prev_tsc = rte_rdtsc(); 2288 do { 2289 for (sm_id = 0; sm_id < nb_fs; sm_id++) { 2290 struct fwd_stream *fs = fsm[sm_id]; 2291 uint64_t start_fs_tsc = 0; 2292 bool busy; 2293 2294 if (fs->disabled) 2295 continue; 2296 if (record_core_cycles) 2297 start_fs_tsc = rte_rdtsc(); 2298 busy = (*pkt_fwd)(fs); 2299 if (record_core_cycles && busy) 2300 fs->busy_cycles += rte_rdtsc() - start_fs_tsc; 2301 } 2302 #ifdef RTE_LIB_BITRATESTATS 2303 if (bitrate_enabled != 0 && 2304 bitrate_lcore_id == rte_lcore_id()) { 2305 tics_current = rte_rdtsc(); 2306 if (tics_current - tics_datum >= tics_per_1sec) { 2307 /* Periodic bitrate calculation */ 2308 for (i = 0; i < cnt_ports; i++) 2309 rte_stats_bitrate_calc(bitrate_data, 2310 ports_ids[i]); 2311 tics_datum = tics_current; 2312 } 2313 } 2314 #endif 2315 #ifdef RTE_LIB_LATENCYSTATS 2316 if (latencystats_enabled != 0 && 2317 latencystats_lcore_id == rte_lcore_id()) 2318 rte_latencystats_update(); 2319 #endif 2320 if (record_core_cycles) { 2321 uint64_t tsc = rte_rdtsc(); 2322 2323 fc->total_cycles += tsc - prev_tsc; 2324 prev_tsc = tsc; 2325 } 2326 } while (! fc->stopped); 2327 } 2328 2329 static int 2330 lcore_usage_callback(unsigned int lcore_id, struct rte_lcore_usage *usage) 2331 { 2332 struct fwd_stream **fsm; 2333 struct fwd_lcore *fc; 2334 streamid_t nb_fs; 2335 streamid_t sm_id; 2336 2337 fc = lcore_to_fwd_lcore(lcore_id); 2338 if (fc == NULL) 2339 return -1; 2340 2341 fsm = &fwd_streams[fc->stream_idx]; 2342 nb_fs = fc->stream_nb; 2343 usage->busy_cycles = 0; 2344 usage->total_cycles = fc->total_cycles; 2345 2346 for (sm_id = 0; sm_id < nb_fs; sm_id++) { 2347 if (!fsm[sm_id]->disabled) 2348 usage->busy_cycles += fsm[sm_id]->busy_cycles; 2349 } 2350 2351 return 0; 2352 } 2353 2354 static int 2355 start_pkt_forward_on_core(void *fwd_arg) 2356 { 2357 run_pkt_fwd_on_lcore((struct fwd_lcore *) fwd_arg, 2358 cur_fwd_config.fwd_eng->packet_fwd); 2359 return 0; 2360 } 2361 2362 /* 2363 * Run the TXONLY packet forwarding engine to send a single burst of packets. 2364 * Used to start communication flows in network loopback test configurations. 2365 */ 2366 static int 2367 run_one_txonly_burst_on_core(void *fwd_arg) 2368 { 2369 struct fwd_lcore *fwd_lc; 2370 struct fwd_lcore tmp_lcore; 2371 2372 fwd_lc = (struct fwd_lcore *) fwd_arg; 2373 tmp_lcore = *fwd_lc; 2374 tmp_lcore.stopped = 1; 2375 run_pkt_fwd_on_lcore(&tmp_lcore, tx_only_engine.packet_fwd); 2376 return 0; 2377 } 2378 2379 /* 2380 * Launch packet forwarding: 2381 * - Setup per-port forwarding context. 2382 * - launch logical cores with their forwarding configuration. 2383 */ 2384 static void 2385 launch_packet_forwarding(lcore_function_t *pkt_fwd_on_lcore) 2386 { 2387 unsigned int i; 2388 unsigned int lc_id; 2389 int diag; 2390 2391 for (i = 0; i < cur_fwd_config.nb_fwd_lcores; i++) { 2392 lc_id = fwd_lcores_cpuids[i]; 2393 if ((interactive == 0) || (lc_id != rte_lcore_id())) { 2394 fwd_lcores[i]->stopped = 0; 2395 diag = rte_eal_remote_launch(pkt_fwd_on_lcore, 2396 fwd_lcores[i], lc_id); 2397 if (diag != 0) 2398 fprintf(stderr, 2399 "launch lcore %u failed - diag=%d\n", 2400 lc_id, diag); 2401 } 2402 } 2403 } 2404 2405 void 2406 common_fwd_stream_init(struct fwd_stream *fs) 2407 { 2408 bool rx_stopped, tx_stopped; 2409 2410 rx_stopped = (ports[fs->rx_port].rxq[fs->rx_queue].state == RTE_ETH_QUEUE_STATE_STOPPED); 2411 tx_stopped = (ports[fs->tx_port].txq[fs->tx_queue].state == RTE_ETH_QUEUE_STATE_STOPPED); 2412 fs->disabled = rx_stopped || tx_stopped; 2413 } 2414 2415 static void 2416 update_rx_queue_state(uint16_t port_id, uint16_t queue_id) 2417 { 2418 struct rte_eth_rxq_info rx_qinfo; 2419 int32_t rc; 2420 2421 rc = rte_eth_rx_queue_info_get(port_id, 2422 queue_id, &rx_qinfo); 2423 if (rc == 0) { 2424 ports[port_id].rxq[queue_id].state = 2425 rx_qinfo.queue_state; 2426 } else if (rc == -ENOTSUP) { 2427 /* 2428 * Set the rxq state to RTE_ETH_QUEUE_STATE_STARTED 2429 * to ensure that the PMDs do not implement 2430 * rte_eth_rx_queue_info_get can forward. 2431 */ 2432 ports[port_id].rxq[queue_id].state = 2433 RTE_ETH_QUEUE_STATE_STARTED; 2434 } else { 2435 TESTPMD_LOG(WARNING, 2436 "Failed to get rx queue info\n"); 2437 } 2438 } 2439 2440 static void 2441 update_tx_queue_state(uint16_t port_id, uint16_t queue_id) 2442 { 2443 struct rte_eth_txq_info tx_qinfo; 2444 int32_t rc; 2445 2446 rc = rte_eth_tx_queue_info_get(port_id, 2447 queue_id, &tx_qinfo); 2448 if (rc == 0) { 2449 ports[port_id].txq[queue_id].state = 2450 tx_qinfo.queue_state; 2451 } else if (rc == -ENOTSUP) { 2452 /* 2453 * Set the txq state to RTE_ETH_QUEUE_STATE_STARTED 2454 * to ensure that the PMDs do not implement 2455 * rte_eth_tx_queue_info_get can forward. 2456 */ 2457 ports[port_id].txq[queue_id].state = 2458 RTE_ETH_QUEUE_STATE_STARTED; 2459 } else { 2460 TESTPMD_LOG(WARNING, 2461 "Failed to get tx queue info\n"); 2462 } 2463 } 2464 2465 static void 2466 update_queue_state(void) 2467 { 2468 portid_t pi; 2469 queueid_t qi; 2470 2471 RTE_ETH_FOREACH_DEV(pi) { 2472 for (qi = 0; qi < nb_rxq; qi++) 2473 update_rx_queue_state(pi, qi); 2474 for (qi = 0; qi < nb_txq; qi++) 2475 update_tx_queue_state(pi, qi); 2476 } 2477 } 2478 2479 /* 2480 * Launch packet forwarding configuration. 2481 */ 2482 void 2483 start_packet_forwarding(int with_tx_first) 2484 { 2485 port_fwd_begin_t port_fwd_begin; 2486 port_fwd_end_t port_fwd_end; 2487 stream_init_t stream_init = cur_fwd_eng->stream_init; 2488 unsigned int i; 2489 2490 if (strcmp(cur_fwd_eng->fwd_mode_name, "rxonly") == 0 && !nb_rxq) 2491 rte_exit(EXIT_FAILURE, "rxq are 0, cannot use rxonly fwd mode\n"); 2492 2493 if (strcmp(cur_fwd_eng->fwd_mode_name, "txonly") == 0 && !nb_txq) 2494 rte_exit(EXIT_FAILURE, "txq are 0, cannot use txonly fwd mode\n"); 2495 2496 if ((strcmp(cur_fwd_eng->fwd_mode_name, "rxonly") != 0 && 2497 strcmp(cur_fwd_eng->fwd_mode_name, "txonly") != 0) && 2498 (!nb_rxq || !nb_txq)) 2499 rte_exit(EXIT_FAILURE, 2500 "Either rxq or txq are 0, cannot use %s fwd mode\n", 2501 cur_fwd_eng->fwd_mode_name); 2502 2503 if (all_ports_started() == 0) { 2504 fprintf(stderr, "Not all ports were started\n"); 2505 return; 2506 } 2507 if (test_done == 0) { 2508 fprintf(stderr, "Packet forwarding already started\n"); 2509 return; 2510 } 2511 2512 fwd_config_setup(); 2513 2514 pkt_fwd_config_display(&cur_fwd_config); 2515 if (!pkt_fwd_shared_rxq_check()) 2516 return; 2517 2518 if (stream_init != NULL) { 2519 if (rte_eal_process_type() == RTE_PROC_SECONDARY) 2520 update_queue_state(); 2521 for (i = 0; i < cur_fwd_config.nb_fwd_streams; i++) 2522 stream_init(fwd_streams[i]); 2523 } 2524 2525 port_fwd_begin = cur_fwd_config.fwd_eng->port_fwd_begin; 2526 if (port_fwd_begin != NULL) { 2527 for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++) { 2528 if (port_fwd_begin(fwd_ports_ids[i])) { 2529 fprintf(stderr, 2530 "Packet forwarding is not ready\n"); 2531 return; 2532 } 2533 } 2534 } 2535 2536 if (with_tx_first) { 2537 port_fwd_begin = tx_only_engine.port_fwd_begin; 2538 if (port_fwd_begin != NULL) { 2539 for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++) { 2540 if (port_fwd_begin(fwd_ports_ids[i])) { 2541 fprintf(stderr, 2542 "Packet forwarding is not ready\n"); 2543 return; 2544 } 2545 } 2546 } 2547 } 2548 2549 test_done = 0; 2550 2551 if(!no_flush_rx) 2552 flush_fwd_rx_queues(); 2553 2554 rxtx_config_display(); 2555 2556 fwd_stats_reset(); 2557 if (with_tx_first) { 2558 while (with_tx_first--) { 2559 launch_packet_forwarding( 2560 run_one_txonly_burst_on_core); 2561 rte_eal_mp_wait_lcore(); 2562 } 2563 port_fwd_end = tx_only_engine.port_fwd_end; 2564 if (port_fwd_end != NULL) { 2565 for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++) 2566 (*port_fwd_end)(fwd_ports_ids[i]); 2567 } 2568 } 2569 launch_packet_forwarding(start_pkt_forward_on_core); 2570 } 2571 2572 void 2573 stop_packet_forwarding(void) 2574 { 2575 port_fwd_end_t port_fwd_end; 2576 lcoreid_t lc_id; 2577 portid_t pt_id; 2578 int i; 2579 2580 if (test_done) { 2581 fprintf(stderr, "Packet forwarding not started\n"); 2582 return; 2583 } 2584 printf("Telling cores to stop..."); 2585 for (lc_id = 0; lc_id < cur_fwd_config.nb_fwd_lcores; lc_id++) 2586 fwd_lcores[lc_id]->stopped = 1; 2587 printf("\nWaiting for lcores to finish...\n"); 2588 rte_eal_mp_wait_lcore(); 2589 port_fwd_end = cur_fwd_config.fwd_eng->port_fwd_end; 2590 if (port_fwd_end != NULL) { 2591 for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++) { 2592 pt_id = fwd_ports_ids[i]; 2593 (*port_fwd_end)(pt_id); 2594 } 2595 } 2596 2597 fwd_stats_display(); 2598 2599 printf("\nDone.\n"); 2600 test_done = 1; 2601 } 2602 2603 void 2604 dev_set_link_up(portid_t pid) 2605 { 2606 if (rte_eth_dev_set_link_up(pid) < 0) 2607 fprintf(stderr, "\nSet link up fail.\n"); 2608 } 2609 2610 void 2611 dev_set_link_down(portid_t pid) 2612 { 2613 if (rte_eth_dev_set_link_down(pid) < 0) 2614 fprintf(stderr, "\nSet link down fail.\n"); 2615 } 2616 2617 static int 2618 all_ports_started(void) 2619 { 2620 portid_t pi; 2621 struct rte_port *port; 2622 2623 RTE_ETH_FOREACH_DEV(pi) { 2624 port = &ports[pi]; 2625 /* Check if there is a port which is not started */ 2626 if ((port->port_status != RTE_PORT_STARTED) && 2627 (port->slave_flag == 0)) 2628 return 0; 2629 } 2630 2631 /* No port is not started */ 2632 return 1; 2633 } 2634 2635 int 2636 port_is_stopped(portid_t port_id) 2637 { 2638 struct rte_port *port = &ports[port_id]; 2639 2640 if ((port->port_status != RTE_PORT_STOPPED) && 2641 (port->slave_flag == 0)) 2642 return 0; 2643 return 1; 2644 } 2645 2646 int 2647 all_ports_stopped(void) 2648 { 2649 portid_t pi; 2650 2651 RTE_ETH_FOREACH_DEV(pi) { 2652 if (!port_is_stopped(pi)) 2653 return 0; 2654 } 2655 2656 return 1; 2657 } 2658 2659 int 2660 port_is_started(portid_t port_id) 2661 { 2662 if (port_id_is_invalid(port_id, ENABLED_WARN)) 2663 return 0; 2664 2665 if (ports[port_id].port_status != RTE_PORT_STARTED) 2666 return 0; 2667 2668 return 1; 2669 } 2670 2671 #define HAIRPIN_MODE_RX_FORCE_MEMORY RTE_BIT32(8) 2672 #define HAIRPIN_MODE_TX_FORCE_MEMORY RTE_BIT32(9) 2673 2674 #define HAIRPIN_MODE_RX_LOCKED_MEMORY RTE_BIT32(12) 2675 #define HAIRPIN_MODE_RX_RTE_MEMORY RTE_BIT32(13) 2676 2677 #define HAIRPIN_MODE_TX_LOCKED_MEMORY RTE_BIT32(16) 2678 #define HAIRPIN_MODE_TX_RTE_MEMORY RTE_BIT32(17) 2679 2680 2681 /* Configure the Rx and Tx hairpin queues for the selected port. */ 2682 static int 2683 setup_hairpin_queues(portid_t pi, portid_t p_pi, uint16_t cnt_pi) 2684 { 2685 queueid_t qi; 2686 struct rte_eth_hairpin_conf hairpin_conf = { 2687 .peer_count = 1, 2688 }; 2689 int i; 2690 int diag; 2691 struct rte_port *port = &ports[pi]; 2692 uint16_t peer_rx_port = pi; 2693 uint16_t peer_tx_port = pi; 2694 uint32_t manual = 1; 2695 uint32_t tx_exp = hairpin_mode & 0x10; 2696 uint32_t rx_force_memory = hairpin_mode & HAIRPIN_MODE_RX_FORCE_MEMORY; 2697 uint32_t rx_locked_memory = hairpin_mode & HAIRPIN_MODE_RX_LOCKED_MEMORY; 2698 uint32_t rx_rte_memory = hairpin_mode & HAIRPIN_MODE_RX_RTE_MEMORY; 2699 uint32_t tx_force_memory = hairpin_mode & HAIRPIN_MODE_TX_FORCE_MEMORY; 2700 uint32_t tx_locked_memory = hairpin_mode & HAIRPIN_MODE_TX_LOCKED_MEMORY; 2701 uint32_t tx_rte_memory = hairpin_mode & HAIRPIN_MODE_TX_RTE_MEMORY; 2702 2703 if (!(hairpin_mode & 0xf)) { 2704 peer_rx_port = pi; 2705 peer_tx_port = pi; 2706 manual = 0; 2707 } else if (hairpin_mode & 0x1) { 2708 peer_tx_port = rte_eth_find_next_owned_by(pi + 1, 2709 RTE_ETH_DEV_NO_OWNER); 2710 if (peer_tx_port >= RTE_MAX_ETHPORTS) 2711 peer_tx_port = rte_eth_find_next_owned_by(0, 2712 RTE_ETH_DEV_NO_OWNER); 2713 if (p_pi != RTE_MAX_ETHPORTS) { 2714 peer_rx_port = p_pi; 2715 } else { 2716 uint16_t next_pi; 2717 2718 /* Last port will be the peer RX port of the first. */ 2719 RTE_ETH_FOREACH_DEV(next_pi) 2720 peer_rx_port = next_pi; 2721 } 2722 manual = 1; 2723 } else if (hairpin_mode & 0x2) { 2724 if (cnt_pi & 0x1) { 2725 peer_rx_port = p_pi; 2726 } else { 2727 peer_rx_port = rte_eth_find_next_owned_by(pi + 1, 2728 RTE_ETH_DEV_NO_OWNER); 2729 if (peer_rx_port >= RTE_MAX_ETHPORTS) 2730 peer_rx_port = pi; 2731 } 2732 peer_tx_port = peer_rx_port; 2733 manual = 1; 2734 } 2735 2736 for (qi = nb_txq, i = 0; qi < nb_hairpinq + nb_txq; qi++) { 2737 hairpin_conf.peers[0].port = peer_rx_port; 2738 hairpin_conf.peers[0].queue = i + nb_rxq; 2739 hairpin_conf.manual_bind = !!manual; 2740 hairpin_conf.tx_explicit = !!tx_exp; 2741 hairpin_conf.force_memory = !!tx_force_memory; 2742 hairpin_conf.use_locked_device_memory = !!tx_locked_memory; 2743 hairpin_conf.use_rte_memory = !!tx_rte_memory; 2744 diag = rte_eth_tx_hairpin_queue_setup 2745 (pi, qi, nb_txd, &hairpin_conf); 2746 i++; 2747 if (diag == 0) 2748 continue; 2749 2750 /* Fail to setup rx queue, return */ 2751 if (port->port_status == RTE_PORT_HANDLING) 2752 port->port_status = RTE_PORT_STOPPED; 2753 else 2754 fprintf(stderr, 2755 "Port %d can not be set back to stopped\n", pi); 2756 fprintf(stderr, "Fail to configure port %d hairpin queues\n", 2757 pi); 2758 /* try to reconfigure queues next time */ 2759 port->need_reconfig_queues = 1; 2760 return -1; 2761 } 2762 for (qi = nb_rxq, i = 0; qi < nb_hairpinq + nb_rxq; qi++) { 2763 hairpin_conf.peers[0].port = peer_tx_port; 2764 hairpin_conf.peers[0].queue = i + nb_txq; 2765 hairpin_conf.manual_bind = !!manual; 2766 hairpin_conf.tx_explicit = !!tx_exp; 2767 hairpin_conf.force_memory = !!rx_force_memory; 2768 hairpin_conf.use_locked_device_memory = !!rx_locked_memory; 2769 hairpin_conf.use_rte_memory = !!rx_rte_memory; 2770 diag = rte_eth_rx_hairpin_queue_setup 2771 (pi, qi, nb_rxd, &hairpin_conf); 2772 i++; 2773 if (diag == 0) 2774 continue; 2775 2776 /* Fail to setup rx queue, return */ 2777 if (port->port_status == RTE_PORT_HANDLING) 2778 port->port_status = RTE_PORT_STOPPED; 2779 else 2780 fprintf(stderr, 2781 "Port %d can not be set back to stopped\n", pi); 2782 fprintf(stderr, "Fail to configure port %d hairpin queues\n", 2783 pi); 2784 /* try to reconfigure queues next time */ 2785 port->need_reconfig_queues = 1; 2786 return -1; 2787 } 2788 return 0; 2789 } 2790 2791 /* Configure the Rx with optional split. */ 2792 int 2793 rx_queue_setup(uint16_t port_id, uint16_t rx_queue_id, 2794 uint16_t nb_rx_desc, unsigned int socket_id, 2795 struct rte_eth_rxconf *rx_conf, struct rte_mempool *mp) 2796 { 2797 union rte_eth_rxseg rx_useg[MAX_SEGS_BUFFER_SPLIT] = {}; 2798 struct rte_mempool *rx_mempool[MAX_MEMPOOL] = {}; 2799 struct rte_mempool *mpx; 2800 unsigned int i, mp_n; 2801 uint32_t prev_hdrs = 0; 2802 int ret; 2803 2804 2805 if ((rx_pkt_nb_segs > 1) && 2806 (rx_conf->offloads & RTE_ETH_RX_OFFLOAD_BUFFER_SPLIT)) { 2807 /* multi-segment configuration */ 2808 for (i = 0; i < rx_pkt_nb_segs; i++) { 2809 struct rte_eth_rxseg_split *rx_seg = &rx_useg[i].split; 2810 /* 2811 * Use last valid pool for the segments with number 2812 * exceeding the pool index. 2813 */ 2814 mp_n = (i >= mbuf_data_size_n) ? mbuf_data_size_n - 1 : i; 2815 mpx = mbuf_pool_find(socket_id, mp_n); 2816 /* Handle zero as mbuf data buffer size. */ 2817 rx_seg->offset = i < rx_pkt_nb_offs ? 2818 rx_pkt_seg_offsets[i] : 0; 2819 rx_seg->mp = mpx ? mpx : mp; 2820 if (rx_pkt_hdr_protos[i] != 0 && rx_pkt_seg_lengths[i] == 0) { 2821 rx_seg->proto_hdr = rx_pkt_hdr_protos[i] & ~prev_hdrs; 2822 prev_hdrs |= rx_seg->proto_hdr; 2823 } else { 2824 rx_seg->length = rx_pkt_seg_lengths[i] ? 2825 rx_pkt_seg_lengths[i] : 2826 mbuf_data_size[mp_n]; 2827 } 2828 } 2829 rx_conf->rx_nseg = rx_pkt_nb_segs; 2830 rx_conf->rx_seg = rx_useg; 2831 rx_conf->rx_mempools = NULL; 2832 rx_conf->rx_nmempool = 0; 2833 ret = rte_eth_rx_queue_setup(port_id, rx_queue_id, nb_rx_desc, 2834 socket_id, rx_conf, NULL); 2835 rx_conf->rx_seg = NULL; 2836 rx_conf->rx_nseg = 0; 2837 } else if (multi_rx_mempool == 1) { 2838 /* multi-pool configuration */ 2839 struct rte_eth_dev_info dev_info; 2840 2841 if (mbuf_data_size_n <= 1) { 2842 fprintf(stderr, "Invalid number of mempools %u\n", 2843 mbuf_data_size_n); 2844 return -EINVAL; 2845 } 2846 ret = rte_eth_dev_info_get(port_id, &dev_info); 2847 if (ret != 0) 2848 return ret; 2849 if (dev_info.max_rx_mempools == 0) { 2850 fprintf(stderr, 2851 "Port %u doesn't support requested multi-rx-mempool configuration.\n", 2852 port_id); 2853 return -ENOTSUP; 2854 } 2855 for (i = 0; i < mbuf_data_size_n; i++) { 2856 mpx = mbuf_pool_find(socket_id, i); 2857 rx_mempool[i] = mpx ? mpx : mp; 2858 } 2859 rx_conf->rx_mempools = rx_mempool; 2860 rx_conf->rx_nmempool = mbuf_data_size_n; 2861 rx_conf->rx_seg = NULL; 2862 rx_conf->rx_nseg = 0; 2863 ret = rte_eth_rx_queue_setup(port_id, rx_queue_id, nb_rx_desc, 2864 socket_id, rx_conf, NULL); 2865 rx_conf->rx_mempools = NULL; 2866 rx_conf->rx_nmempool = 0; 2867 } else { 2868 /* Single pool/segment configuration */ 2869 rx_conf->rx_seg = NULL; 2870 rx_conf->rx_nseg = 0; 2871 rx_conf->rx_mempools = NULL; 2872 rx_conf->rx_nmempool = 0; 2873 ret = rte_eth_rx_queue_setup(port_id, rx_queue_id, nb_rx_desc, 2874 socket_id, rx_conf, mp); 2875 } 2876 2877 ports[port_id].rxq[rx_queue_id].state = rx_conf->rx_deferred_start ? 2878 RTE_ETH_QUEUE_STATE_STOPPED : 2879 RTE_ETH_QUEUE_STATE_STARTED; 2880 return ret; 2881 } 2882 2883 static int 2884 alloc_xstats_display_info(portid_t pi) 2885 { 2886 uint64_t **ids_supp = &ports[pi].xstats_info.ids_supp; 2887 uint64_t **prev_values = &ports[pi].xstats_info.prev_values; 2888 uint64_t **curr_values = &ports[pi].xstats_info.curr_values; 2889 2890 if (xstats_display_num == 0) 2891 return 0; 2892 2893 *ids_supp = calloc(xstats_display_num, sizeof(**ids_supp)); 2894 if (*ids_supp == NULL) 2895 goto fail_ids_supp; 2896 2897 *prev_values = calloc(xstats_display_num, 2898 sizeof(**prev_values)); 2899 if (*prev_values == NULL) 2900 goto fail_prev_values; 2901 2902 *curr_values = calloc(xstats_display_num, 2903 sizeof(**curr_values)); 2904 if (*curr_values == NULL) 2905 goto fail_curr_values; 2906 2907 ports[pi].xstats_info.allocated = true; 2908 2909 return 0; 2910 2911 fail_curr_values: 2912 free(*prev_values); 2913 fail_prev_values: 2914 free(*ids_supp); 2915 fail_ids_supp: 2916 return -ENOMEM; 2917 } 2918 2919 static void 2920 free_xstats_display_info(portid_t pi) 2921 { 2922 if (!ports[pi].xstats_info.allocated) 2923 return; 2924 free(ports[pi].xstats_info.ids_supp); 2925 free(ports[pi].xstats_info.prev_values); 2926 free(ports[pi].xstats_info.curr_values); 2927 ports[pi].xstats_info.allocated = false; 2928 } 2929 2930 /** Fill helper structures for specified port to show extended statistics. */ 2931 static void 2932 fill_xstats_display_info_for_port(portid_t pi) 2933 { 2934 unsigned int stat, stat_supp; 2935 const char *xstat_name; 2936 struct rte_port *port; 2937 uint64_t *ids_supp; 2938 int rc; 2939 2940 if (xstats_display_num == 0) 2941 return; 2942 2943 if (pi == (portid_t)RTE_PORT_ALL) { 2944 fill_xstats_display_info(); 2945 return; 2946 } 2947 2948 port = &ports[pi]; 2949 if (port->port_status != RTE_PORT_STARTED) 2950 return; 2951 2952 if (!port->xstats_info.allocated && alloc_xstats_display_info(pi) != 0) 2953 rte_exit(EXIT_FAILURE, 2954 "Failed to allocate xstats display memory\n"); 2955 2956 ids_supp = port->xstats_info.ids_supp; 2957 for (stat = stat_supp = 0; stat < xstats_display_num; stat++) { 2958 xstat_name = xstats_display[stat].name; 2959 rc = rte_eth_xstats_get_id_by_name(pi, xstat_name, 2960 ids_supp + stat_supp); 2961 if (rc != 0) { 2962 fprintf(stderr, "No xstat '%s' on port %u - skip it %u\n", 2963 xstat_name, pi, stat); 2964 continue; 2965 } 2966 stat_supp++; 2967 } 2968 2969 port->xstats_info.ids_supp_sz = stat_supp; 2970 } 2971 2972 /** Fill helper structures for all ports to show extended statistics. */ 2973 static void 2974 fill_xstats_display_info(void) 2975 { 2976 portid_t pi; 2977 2978 if (xstats_display_num == 0) 2979 return; 2980 2981 RTE_ETH_FOREACH_DEV(pi) 2982 fill_xstats_display_info_for_port(pi); 2983 } 2984 2985 /* 2986 * Some capabilities (like, rx_offload_capa and tx_offload_capa) of bonding 2987 * device in dev_info is zero when no slave is added. And its capability 2988 * will be updated when add a new slave device. So adding a slave device need 2989 * to update the port configurations of bonding device. 2990 */ 2991 static void 2992 update_bonding_port_dev_conf(portid_t bond_pid) 2993 { 2994 #ifdef RTE_NET_BOND 2995 struct rte_port *port = &ports[bond_pid]; 2996 uint16_t i; 2997 int ret; 2998 2999 ret = eth_dev_info_get_print_err(bond_pid, &port->dev_info); 3000 if (ret != 0) { 3001 fprintf(stderr, "Failed to get dev info for port = %u\n", 3002 bond_pid); 3003 return; 3004 } 3005 3006 if (port->dev_info.tx_offload_capa & RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE) 3007 port->dev_conf.txmode.offloads |= 3008 RTE_ETH_TX_OFFLOAD_MBUF_FAST_FREE; 3009 /* Apply Tx offloads configuration */ 3010 for (i = 0; i < port->dev_info.max_tx_queues; i++) 3011 port->txq[i].conf.offloads = port->dev_conf.txmode.offloads; 3012 3013 port->dev_conf.rx_adv_conf.rss_conf.rss_hf &= 3014 port->dev_info.flow_type_rss_offloads; 3015 #else 3016 RTE_SET_USED(bond_pid); 3017 #endif 3018 } 3019 3020 int 3021 start_port(portid_t pid) 3022 { 3023 int diag; 3024 portid_t pi; 3025 portid_t p_pi = RTE_MAX_ETHPORTS; 3026 portid_t pl[RTE_MAX_ETHPORTS]; 3027 portid_t peer_pl[RTE_MAX_ETHPORTS]; 3028 uint16_t cnt_pi = 0; 3029 uint16_t cfg_pi = 0; 3030 int peer_pi; 3031 queueid_t qi; 3032 struct rte_port *port; 3033 struct rte_eth_hairpin_cap cap; 3034 bool at_least_one_port_exist = false; 3035 bool all_ports_already_started = true; 3036 bool at_least_one_port_successfully_started = false; 3037 3038 if (port_id_is_invalid(pid, ENABLED_WARN)) 3039 return 0; 3040 3041 RTE_ETH_FOREACH_DEV(pi) { 3042 if (pid != pi && pid != (portid_t)RTE_PORT_ALL) 3043 continue; 3044 3045 if (port_is_bonding_slave(pi)) { 3046 fprintf(stderr, 3047 "Please remove port %d from bonded device.\n", 3048 pi); 3049 continue; 3050 } 3051 3052 at_least_one_port_exist = true; 3053 3054 port = &ports[pi]; 3055 if (port->port_status == RTE_PORT_STOPPED) { 3056 port->port_status = RTE_PORT_HANDLING; 3057 all_ports_already_started = false; 3058 } else { 3059 fprintf(stderr, "Port %d is now not stopped\n", pi); 3060 continue; 3061 } 3062 3063 if (port->need_reconfig > 0) { 3064 struct rte_eth_conf dev_conf; 3065 int k; 3066 3067 port->need_reconfig = 0; 3068 3069 if (flow_isolate_all) { 3070 int ret = port_flow_isolate(pi, 1); 3071 if (ret) { 3072 fprintf(stderr, 3073 "Failed to apply isolated mode on port %d\n", 3074 pi); 3075 return -1; 3076 } 3077 } 3078 configure_rxtx_dump_callbacks(0); 3079 printf("Configuring Port %d (socket %u)\n", pi, 3080 port->socket_id); 3081 if (nb_hairpinq > 0 && 3082 rte_eth_dev_hairpin_capability_get(pi, &cap)) { 3083 fprintf(stderr, 3084 "Port %d doesn't support hairpin queues\n", 3085 pi); 3086 return -1; 3087 } 3088 3089 if (port->bond_flag == 1 && port->update_conf == 1) { 3090 update_bonding_port_dev_conf(pi); 3091 port->update_conf = 0; 3092 } 3093 3094 /* configure port */ 3095 diag = eth_dev_configure_mp(pi, nb_rxq + nb_hairpinq, 3096 nb_txq + nb_hairpinq, 3097 &(port->dev_conf)); 3098 if (diag != 0) { 3099 if (port->port_status == RTE_PORT_HANDLING) 3100 port->port_status = RTE_PORT_STOPPED; 3101 else 3102 fprintf(stderr, 3103 "Port %d can not be set back to stopped\n", 3104 pi); 3105 fprintf(stderr, "Fail to configure port %d\n", 3106 pi); 3107 /* try to reconfigure port next time */ 3108 port->need_reconfig = 1; 3109 return -1; 3110 } 3111 /* get device configuration*/ 3112 if (0 != 3113 eth_dev_conf_get_print_err(pi, &dev_conf)) { 3114 fprintf(stderr, 3115 "port %d can not get device configuration\n", 3116 pi); 3117 return -1; 3118 } 3119 /* Apply Rx offloads configuration */ 3120 if (dev_conf.rxmode.offloads != 3121 port->dev_conf.rxmode.offloads) { 3122 port->dev_conf.rxmode.offloads |= 3123 dev_conf.rxmode.offloads; 3124 for (k = 0; 3125 k < port->dev_info.max_rx_queues; 3126 k++) 3127 port->rxq[k].conf.offloads |= 3128 dev_conf.rxmode.offloads; 3129 } 3130 /* Apply Tx offloads configuration */ 3131 if (dev_conf.txmode.offloads != 3132 port->dev_conf.txmode.offloads) { 3133 port->dev_conf.txmode.offloads |= 3134 dev_conf.txmode.offloads; 3135 for (k = 0; 3136 k < port->dev_info.max_tx_queues; 3137 k++) 3138 port->txq[k].conf.offloads |= 3139 dev_conf.txmode.offloads; 3140 } 3141 } 3142 if (port->need_reconfig_queues > 0 && is_proc_primary()) { 3143 port->need_reconfig_queues = 0; 3144 /* setup tx queues */ 3145 for (qi = 0; qi < nb_txq; qi++) { 3146 struct rte_eth_txconf *conf = 3147 &port->txq[qi].conf; 3148 3149 if ((numa_support) && 3150 (txring_numa[pi] != NUMA_NO_CONFIG)) 3151 diag = rte_eth_tx_queue_setup(pi, qi, 3152 port->nb_tx_desc[qi], 3153 txring_numa[pi], 3154 &(port->txq[qi].conf)); 3155 else 3156 diag = rte_eth_tx_queue_setup(pi, qi, 3157 port->nb_tx_desc[qi], 3158 port->socket_id, 3159 &(port->txq[qi].conf)); 3160 3161 if (diag == 0) { 3162 port->txq[qi].state = 3163 conf->tx_deferred_start ? 3164 RTE_ETH_QUEUE_STATE_STOPPED : 3165 RTE_ETH_QUEUE_STATE_STARTED; 3166 continue; 3167 } 3168 3169 /* Fail to setup tx queue, return */ 3170 if (port->port_status == RTE_PORT_HANDLING) 3171 port->port_status = RTE_PORT_STOPPED; 3172 else 3173 fprintf(stderr, 3174 "Port %d can not be set back to stopped\n", 3175 pi); 3176 fprintf(stderr, 3177 "Fail to configure port %d tx queues\n", 3178 pi); 3179 /* try to reconfigure queues next time */ 3180 port->need_reconfig_queues = 1; 3181 return -1; 3182 } 3183 for (qi = 0; qi < nb_rxq; qi++) { 3184 /* setup rx queues */ 3185 if ((numa_support) && 3186 (rxring_numa[pi] != NUMA_NO_CONFIG)) { 3187 struct rte_mempool * mp = 3188 mbuf_pool_find 3189 (rxring_numa[pi], 0); 3190 if (mp == NULL) { 3191 fprintf(stderr, 3192 "Failed to setup RX queue: No mempool allocation on the socket %d\n", 3193 rxring_numa[pi]); 3194 return -1; 3195 } 3196 3197 diag = rx_queue_setup(pi, qi, 3198 port->nb_rx_desc[qi], 3199 rxring_numa[pi], 3200 &(port->rxq[qi].conf), 3201 mp); 3202 } else { 3203 struct rte_mempool *mp = 3204 mbuf_pool_find 3205 (port->socket_id, 0); 3206 if (mp == NULL) { 3207 fprintf(stderr, 3208 "Failed to setup RX queue: No mempool allocation on the socket %d\n", 3209 port->socket_id); 3210 return -1; 3211 } 3212 diag = rx_queue_setup(pi, qi, 3213 port->nb_rx_desc[qi], 3214 port->socket_id, 3215 &(port->rxq[qi].conf), 3216 mp); 3217 } 3218 if (diag == 0) 3219 continue; 3220 3221 /* Fail to setup rx queue, return */ 3222 if (port->port_status == RTE_PORT_HANDLING) 3223 port->port_status = RTE_PORT_STOPPED; 3224 else 3225 fprintf(stderr, 3226 "Port %d can not be set back to stopped\n", 3227 pi); 3228 fprintf(stderr, 3229 "Fail to configure port %d rx queues\n", 3230 pi); 3231 /* try to reconfigure queues next time */ 3232 port->need_reconfig_queues = 1; 3233 return -1; 3234 } 3235 /* setup hairpin queues */ 3236 if (setup_hairpin_queues(pi, p_pi, cnt_pi) != 0) 3237 return -1; 3238 } 3239 configure_rxtx_dump_callbacks(verbose_level); 3240 if (clear_ptypes) { 3241 diag = rte_eth_dev_set_ptypes(pi, RTE_PTYPE_UNKNOWN, 3242 NULL, 0); 3243 if (diag < 0) 3244 fprintf(stderr, 3245 "Port %d: Failed to disable Ptype parsing\n", 3246 pi); 3247 } 3248 3249 p_pi = pi; 3250 cnt_pi++; 3251 3252 /* start port */ 3253 diag = eth_dev_start_mp(pi); 3254 if (diag < 0) { 3255 fprintf(stderr, "Fail to start port %d: %s\n", 3256 pi, rte_strerror(-diag)); 3257 3258 /* Fail to setup rx queue, return */ 3259 if (port->port_status == RTE_PORT_HANDLING) 3260 port->port_status = RTE_PORT_STOPPED; 3261 else 3262 fprintf(stderr, 3263 "Port %d can not be set back to stopped\n", 3264 pi); 3265 continue; 3266 } 3267 3268 if (port->port_status == RTE_PORT_HANDLING) 3269 port->port_status = RTE_PORT_STARTED; 3270 else 3271 fprintf(stderr, "Port %d can not be set into started\n", 3272 pi); 3273 3274 if (eth_macaddr_get_print_err(pi, &port->eth_addr) == 0) 3275 printf("Port %d: " RTE_ETHER_ADDR_PRT_FMT "\n", pi, 3276 RTE_ETHER_ADDR_BYTES(&port->eth_addr)); 3277 3278 at_least_one_port_successfully_started = true; 3279 3280 pl[cfg_pi++] = pi; 3281 } 3282 3283 if (rte_eal_process_type() == RTE_PROC_SECONDARY) 3284 update_queue_state(); 3285 3286 if (at_least_one_port_successfully_started && !no_link_check) 3287 check_all_ports_link_status(RTE_PORT_ALL); 3288 else if (at_least_one_port_exist & all_ports_already_started) 3289 fprintf(stderr, "Please stop the ports first\n"); 3290 3291 if (hairpin_mode & 0xf) { 3292 uint16_t i; 3293 int j; 3294 3295 /* bind all started hairpin ports */ 3296 for (i = 0; i < cfg_pi; i++) { 3297 pi = pl[i]; 3298 /* bind current Tx to all peer Rx */ 3299 peer_pi = rte_eth_hairpin_get_peer_ports(pi, peer_pl, 3300 RTE_MAX_ETHPORTS, 1); 3301 if (peer_pi < 0) 3302 return peer_pi; 3303 for (j = 0; j < peer_pi; j++) { 3304 if (!port_is_started(peer_pl[j])) 3305 continue; 3306 diag = rte_eth_hairpin_bind(pi, peer_pl[j]); 3307 if (diag < 0) { 3308 fprintf(stderr, 3309 "Error during binding hairpin Tx port %u to %u: %s\n", 3310 pi, peer_pl[j], 3311 rte_strerror(-diag)); 3312 return -1; 3313 } 3314 } 3315 /* bind all peer Tx to current Rx */ 3316 peer_pi = rte_eth_hairpin_get_peer_ports(pi, peer_pl, 3317 RTE_MAX_ETHPORTS, 0); 3318 if (peer_pi < 0) 3319 return peer_pi; 3320 for (j = 0; j < peer_pi; j++) { 3321 if (!port_is_started(peer_pl[j])) 3322 continue; 3323 diag = rte_eth_hairpin_bind(peer_pl[j], pi); 3324 if (diag < 0) { 3325 fprintf(stderr, 3326 "Error during binding hairpin Tx port %u to %u: %s\n", 3327 peer_pl[j], pi, 3328 rte_strerror(-diag)); 3329 return -1; 3330 } 3331 } 3332 } 3333 } 3334 3335 fill_xstats_display_info_for_port(pid); 3336 3337 printf("Done\n"); 3338 return 0; 3339 } 3340 3341 void 3342 stop_port(portid_t pid) 3343 { 3344 portid_t pi; 3345 struct rte_port *port; 3346 int need_check_link_status = 0; 3347 portid_t peer_pl[RTE_MAX_ETHPORTS]; 3348 int peer_pi; 3349 int ret; 3350 3351 if (port_id_is_invalid(pid, ENABLED_WARN)) 3352 return; 3353 3354 printf("Stopping ports...\n"); 3355 3356 RTE_ETH_FOREACH_DEV(pi) { 3357 if (pid != pi && pid != (portid_t)RTE_PORT_ALL) 3358 continue; 3359 3360 if (port_is_forwarding(pi) != 0 && test_done == 0) { 3361 fprintf(stderr, 3362 "Please remove port %d from forwarding configuration.\n", 3363 pi); 3364 continue; 3365 } 3366 3367 if (port_is_bonding_slave(pi)) { 3368 fprintf(stderr, 3369 "Please remove port %d from bonded device.\n", 3370 pi); 3371 continue; 3372 } 3373 3374 port = &ports[pi]; 3375 if (port->port_status == RTE_PORT_STARTED) 3376 port->port_status = RTE_PORT_HANDLING; 3377 else 3378 continue; 3379 3380 if (hairpin_mode & 0xf) { 3381 int j; 3382 3383 rte_eth_hairpin_unbind(pi, RTE_MAX_ETHPORTS); 3384 /* unbind all peer Tx from current Rx */ 3385 peer_pi = rte_eth_hairpin_get_peer_ports(pi, peer_pl, 3386 RTE_MAX_ETHPORTS, 0); 3387 if (peer_pi < 0) 3388 continue; 3389 for (j = 0; j < peer_pi; j++) { 3390 if (!port_is_started(peer_pl[j])) 3391 continue; 3392 rte_eth_hairpin_unbind(peer_pl[j], pi); 3393 } 3394 } 3395 3396 if (port->flow_list && !no_flow_flush) 3397 port_flow_flush(pi); 3398 3399 ret = eth_dev_stop_mp(pi); 3400 if (ret != 0) { 3401 RTE_LOG(ERR, EAL, "rte_eth_dev_stop failed for port %u\n", 3402 pi); 3403 /* Allow to retry stopping the port. */ 3404 port->port_status = RTE_PORT_STARTED; 3405 continue; 3406 } 3407 3408 if (port->port_status == RTE_PORT_HANDLING) 3409 port->port_status = RTE_PORT_STOPPED; 3410 else 3411 fprintf(stderr, "Port %d can not be set into stopped\n", 3412 pi); 3413 need_check_link_status = 1; 3414 } 3415 if (need_check_link_status && !no_link_check) 3416 check_all_ports_link_status(RTE_PORT_ALL); 3417 3418 printf("Done\n"); 3419 } 3420 3421 static void 3422 remove_invalid_ports_in(portid_t *array, portid_t *total) 3423 { 3424 portid_t i; 3425 portid_t new_total = 0; 3426 3427 for (i = 0; i < *total; i++) 3428 if (!port_id_is_invalid(array[i], DISABLED_WARN)) { 3429 array[new_total] = array[i]; 3430 new_total++; 3431 } 3432 *total = new_total; 3433 } 3434 3435 static void 3436 remove_invalid_ports(void) 3437 { 3438 remove_invalid_ports_in(ports_ids, &nb_ports); 3439 remove_invalid_ports_in(fwd_ports_ids, &nb_fwd_ports); 3440 nb_cfg_ports = nb_fwd_ports; 3441 } 3442 3443 static void 3444 flush_port_owned_resources(portid_t pi) 3445 { 3446 mcast_addr_pool_destroy(pi); 3447 port_flow_flush(pi); 3448 port_flow_template_table_flush(pi); 3449 port_flow_pattern_template_flush(pi); 3450 port_flow_actions_template_flush(pi); 3451 port_flex_item_flush(pi); 3452 port_action_handle_flush(pi); 3453 } 3454 3455 static void 3456 clear_bonding_slave_device(portid_t *slave_pids, uint16_t num_slaves) 3457 { 3458 struct rte_port *port; 3459 portid_t slave_pid; 3460 uint16_t i; 3461 3462 for (i = 0; i < num_slaves; i++) { 3463 slave_pid = slave_pids[i]; 3464 if (port_is_started(slave_pid) == 1) { 3465 if (rte_eth_dev_stop(slave_pid) != 0) 3466 fprintf(stderr, "rte_eth_dev_stop failed for port %u\n", 3467 slave_pid); 3468 3469 port = &ports[slave_pid]; 3470 port->port_status = RTE_PORT_STOPPED; 3471 } 3472 3473 clear_port_slave_flag(slave_pid); 3474 3475 /* Close slave device when testpmd quit or is killed. */ 3476 if (cl_quit == 1 || f_quit == 1) 3477 rte_eth_dev_close(slave_pid); 3478 } 3479 } 3480 3481 void 3482 close_port(portid_t pid) 3483 { 3484 portid_t pi; 3485 struct rte_port *port; 3486 portid_t slave_pids[RTE_MAX_ETHPORTS]; 3487 int num_slaves = 0; 3488 3489 if (port_id_is_invalid(pid, ENABLED_WARN)) 3490 return; 3491 3492 printf("Closing ports...\n"); 3493 3494 RTE_ETH_FOREACH_DEV(pi) { 3495 if (pid != pi && pid != (portid_t)RTE_PORT_ALL) 3496 continue; 3497 3498 if (port_is_forwarding(pi) != 0 && test_done == 0) { 3499 fprintf(stderr, 3500 "Please remove port %d from forwarding configuration.\n", 3501 pi); 3502 continue; 3503 } 3504 3505 if (port_is_bonding_slave(pi)) { 3506 fprintf(stderr, 3507 "Please remove port %d from bonded device.\n", 3508 pi); 3509 continue; 3510 } 3511 3512 port = &ports[pi]; 3513 if (port->port_status == RTE_PORT_CLOSED) { 3514 fprintf(stderr, "Port %d is already closed\n", pi); 3515 continue; 3516 } 3517 3518 if (is_proc_primary()) { 3519 flush_port_owned_resources(pi); 3520 #ifdef RTE_NET_BOND 3521 if (port->bond_flag == 1) 3522 num_slaves = rte_eth_bond_slaves_get(pi, 3523 slave_pids, RTE_MAX_ETHPORTS); 3524 #endif 3525 rte_eth_dev_close(pi); 3526 /* 3527 * If this port is bonded device, all slaves under the 3528 * device need to be removed or closed. 3529 */ 3530 if (port->bond_flag == 1 && num_slaves > 0) 3531 clear_bonding_slave_device(slave_pids, 3532 num_slaves); 3533 } 3534 3535 free_xstats_display_info(pi); 3536 } 3537 3538 remove_invalid_ports(); 3539 printf("Done\n"); 3540 } 3541 3542 void 3543 reset_port(portid_t pid) 3544 { 3545 int diag; 3546 portid_t pi; 3547 struct rte_port *port; 3548 3549 if (port_id_is_invalid(pid, ENABLED_WARN)) 3550 return; 3551 3552 if ((pid == (portid_t)RTE_PORT_ALL && !all_ports_stopped()) || 3553 (pid != (portid_t)RTE_PORT_ALL && !port_is_stopped(pid))) { 3554 fprintf(stderr, 3555 "Can not reset port(s), please stop port(s) first.\n"); 3556 return; 3557 } 3558 3559 printf("Resetting ports...\n"); 3560 3561 RTE_ETH_FOREACH_DEV(pi) { 3562 if (pid != pi && pid != (portid_t)RTE_PORT_ALL) 3563 continue; 3564 3565 if (port_is_forwarding(pi) != 0 && test_done == 0) { 3566 fprintf(stderr, 3567 "Please remove port %d from forwarding configuration.\n", 3568 pi); 3569 continue; 3570 } 3571 3572 if (port_is_bonding_slave(pi)) { 3573 fprintf(stderr, 3574 "Please remove port %d from bonded device.\n", 3575 pi); 3576 continue; 3577 } 3578 3579 if (is_proc_primary()) { 3580 diag = rte_eth_dev_reset(pi); 3581 if (diag == 0) { 3582 port = &ports[pi]; 3583 port->need_reconfig = 1; 3584 port->need_reconfig_queues = 1; 3585 } else { 3586 fprintf(stderr, "Failed to reset port %d. diag=%d\n", 3587 pi, diag); 3588 } 3589 } 3590 } 3591 3592 printf("Done\n"); 3593 } 3594 3595 void 3596 attach_port(char *identifier) 3597 { 3598 portid_t pi; 3599 struct rte_dev_iterator iterator; 3600 3601 printf("Attaching a new port...\n"); 3602 3603 if (identifier == NULL) { 3604 fprintf(stderr, "Invalid parameters are specified\n"); 3605 return; 3606 } 3607 3608 if (rte_dev_probe(identifier) < 0) { 3609 TESTPMD_LOG(ERR, "Failed to attach port %s\n", identifier); 3610 return; 3611 } 3612 3613 /* first attach mode: event */ 3614 if (setup_on_probe_event) { 3615 /* new ports are detected on RTE_ETH_EVENT_NEW event */ 3616 for (pi = 0; pi < RTE_MAX_ETHPORTS; pi++) 3617 if (ports[pi].port_status == RTE_PORT_HANDLING && 3618 ports[pi].need_setup != 0) 3619 setup_attached_port(pi); 3620 return; 3621 } 3622 3623 /* second attach mode: iterator */ 3624 RTE_ETH_FOREACH_MATCHING_DEV(pi, identifier, &iterator) { 3625 /* setup ports matching the devargs used for probing */ 3626 if (port_is_forwarding(pi)) 3627 continue; /* port was already attached before */ 3628 setup_attached_port(pi); 3629 } 3630 } 3631 3632 static void 3633 setup_attached_port(portid_t pi) 3634 { 3635 unsigned int socket_id; 3636 int ret; 3637 3638 socket_id = (unsigned)rte_eth_dev_socket_id(pi); 3639 /* if socket_id is invalid, set to the first available socket. */ 3640 if (check_socket_id(socket_id) < 0) 3641 socket_id = socket_ids[0]; 3642 reconfig(pi, socket_id); 3643 ret = rte_eth_promiscuous_enable(pi); 3644 if (ret != 0) 3645 fprintf(stderr, 3646 "Error during enabling promiscuous mode for port %u: %s - ignore\n", 3647 pi, rte_strerror(-ret)); 3648 3649 ports_ids[nb_ports++] = pi; 3650 fwd_ports_ids[nb_fwd_ports++] = pi; 3651 nb_cfg_ports = nb_fwd_ports; 3652 ports[pi].need_setup = 0; 3653 ports[pi].port_status = RTE_PORT_STOPPED; 3654 3655 printf("Port %d is attached. Now total ports is %d\n", pi, nb_ports); 3656 printf("Done\n"); 3657 } 3658 3659 static void 3660 detach_device(struct rte_device *dev) 3661 { 3662 portid_t sibling; 3663 3664 if (dev == NULL) { 3665 fprintf(stderr, "Device already removed\n"); 3666 return; 3667 } 3668 3669 printf("Removing a device...\n"); 3670 3671 RTE_ETH_FOREACH_DEV_OF(sibling, dev) { 3672 if (ports[sibling].port_status != RTE_PORT_CLOSED) { 3673 if (ports[sibling].port_status != RTE_PORT_STOPPED) { 3674 fprintf(stderr, "Port %u not stopped\n", 3675 sibling); 3676 return; 3677 } 3678 flush_port_owned_resources(sibling); 3679 } 3680 } 3681 3682 if (rte_dev_remove(dev) < 0) { 3683 TESTPMD_LOG(ERR, "Failed to detach device %s\n", rte_dev_name(dev)); 3684 return; 3685 } 3686 remove_invalid_ports(); 3687 3688 printf("Device is detached\n"); 3689 printf("Now total ports is %d\n", nb_ports); 3690 printf("Done\n"); 3691 return; 3692 } 3693 3694 void 3695 detach_port_device(portid_t port_id) 3696 { 3697 int ret; 3698 struct rte_eth_dev_info dev_info; 3699 3700 if (port_id_is_invalid(port_id, ENABLED_WARN)) 3701 return; 3702 3703 if (ports[port_id].port_status != RTE_PORT_CLOSED) { 3704 if (ports[port_id].port_status != RTE_PORT_STOPPED) { 3705 fprintf(stderr, "Port not stopped\n"); 3706 return; 3707 } 3708 fprintf(stderr, "Port was not closed\n"); 3709 } 3710 3711 ret = eth_dev_info_get_print_err(port_id, &dev_info); 3712 if (ret != 0) { 3713 TESTPMD_LOG(ERR, 3714 "Failed to get device info for port %d, not detaching\n", 3715 port_id); 3716 return; 3717 } 3718 detach_device(dev_info.device); 3719 } 3720 3721 void 3722 detach_devargs(char *identifier) 3723 { 3724 struct rte_dev_iterator iterator; 3725 struct rte_devargs da; 3726 portid_t port_id; 3727 3728 printf("Removing a device...\n"); 3729 3730 memset(&da, 0, sizeof(da)); 3731 if (rte_devargs_parsef(&da, "%s", identifier)) { 3732 fprintf(stderr, "cannot parse identifier\n"); 3733 return; 3734 } 3735 3736 RTE_ETH_FOREACH_MATCHING_DEV(port_id, identifier, &iterator) { 3737 if (ports[port_id].port_status != RTE_PORT_CLOSED) { 3738 if (ports[port_id].port_status != RTE_PORT_STOPPED) { 3739 fprintf(stderr, "Port %u not stopped\n", 3740 port_id); 3741 rte_eth_iterator_cleanup(&iterator); 3742 rte_devargs_reset(&da); 3743 return; 3744 } 3745 flush_port_owned_resources(port_id); 3746 } 3747 } 3748 3749 if (rte_eal_hotplug_remove(rte_bus_name(da.bus), da.name) != 0) { 3750 TESTPMD_LOG(ERR, "Failed to detach device %s(%s)\n", 3751 da.name, rte_bus_name(da.bus)); 3752 rte_devargs_reset(&da); 3753 return; 3754 } 3755 3756 remove_invalid_ports(); 3757 3758 printf("Device %s is detached\n", identifier); 3759 printf("Now total ports is %d\n", nb_ports); 3760 printf("Done\n"); 3761 rte_devargs_reset(&da); 3762 } 3763 3764 void 3765 pmd_test_exit(void) 3766 { 3767 portid_t pt_id; 3768 unsigned int i; 3769 int ret; 3770 3771 if (test_done == 0) 3772 stop_packet_forwarding(); 3773 3774 #ifndef RTE_EXEC_ENV_WINDOWS 3775 for (i = 0 ; i < RTE_DIM(mempools) ; i++) { 3776 if (mempools[i]) { 3777 if (mp_alloc_type == MP_ALLOC_ANON) 3778 rte_mempool_mem_iter(mempools[i], dma_unmap_cb, 3779 NULL); 3780 } 3781 } 3782 #endif 3783 if (ports != NULL) { 3784 no_link_check = 1; 3785 RTE_ETH_FOREACH_DEV(pt_id) { 3786 printf("\nStopping port %d...\n", pt_id); 3787 fflush(stdout); 3788 stop_port(pt_id); 3789 } 3790 RTE_ETH_FOREACH_DEV(pt_id) { 3791 printf("\nShutting down port %d...\n", pt_id); 3792 fflush(stdout); 3793 close_port(pt_id); 3794 } 3795 } 3796 3797 if (hot_plug) { 3798 ret = rte_dev_event_monitor_stop(); 3799 if (ret) { 3800 RTE_LOG(ERR, EAL, 3801 "fail to stop device event monitor."); 3802 return; 3803 } 3804 3805 ret = rte_dev_event_callback_unregister(NULL, 3806 dev_event_callback, NULL); 3807 if (ret < 0) { 3808 RTE_LOG(ERR, EAL, 3809 "fail to unregister device event callback.\n"); 3810 return; 3811 } 3812 3813 ret = rte_dev_hotplug_handle_disable(); 3814 if (ret) { 3815 RTE_LOG(ERR, EAL, 3816 "fail to disable hotplug handling.\n"); 3817 return; 3818 } 3819 } 3820 for (i = 0 ; i < RTE_DIM(mempools) ; i++) { 3821 if (mempools[i]) 3822 mempool_free_mp(mempools[i]); 3823 } 3824 free(xstats_display); 3825 3826 printf("\nBye...\n"); 3827 } 3828 3829 typedef void (*cmd_func_t)(void); 3830 struct pmd_test_command { 3831 const char *cmd_name; 3832 cmd_func_t cmd_func; 3833 }; 3834 3835 /* Check the link status of all ports in up to 9s, and print them finally */ 3836 static void 3837 check_all_ports_link_status(uint32_t port_mask) 3838 { 3839 #define CHECK_INTERVAL 100 /* 100ms */ 3840 #define MAX_CHECK_TIME 90 /* 9s (90 * 100ms) in total */ 3841 portid_t portid; 3842 uint8_t count, all_ports_up, print_flag = 0; 3843 struct rte_eth_link link; 3844 int ret; 3845 char link_status[RTE_ETH_LINK_MAX_STR_LEN]; 3846 3847 printf("Checking link statuses...\n"); 3848 fflush(stdout); 3849 for (count = 0; count <= MAX_CHECK_TIME; count++) { 3850 all_ports_up = 1; 3851 RTE_ETH_FOREACH_DEV(portid) { 3852 if ((port_mask & (1 << portid)) == 0) 3853 continue; 3854 memset(&link, 0, sizeof(link)); 3855 ret = rte_eth_link_get_nowait(portid, &link); 3856 if (ret < 0) { 3857 all_ports_up = 0; 3858 if (print_flag == 1) 3859 fprintf(stderr, 3860 "Port %u link get failed: %s\n", 3861 portid, rte_strerror(-ret)); 3862 continue; 3863 } 3864 /* print link status if flag set */ 3865 if (print_flag == 1) { 3866 rte_eth_link_to_str(link_status, 3867 sizeof(link_status), &link); 3868 printf("Port %d %s\n", portid, link_status); 3869 continue; 3870 } 3871 /* clear all_ports_up flag if any link down */ 3872 if (link.link_status == RTE_ETH_LINK_DOWN) { 3873 all_ports_up = 0; 3874 break; 3875 } 3876 } 3877 /* after finally printing all link status, get out */ 3878 if (print_flag == 1) 3879 break; 3880 3881 if (all_ports_up == 0) { 3882 fflush(stdout); 3883 rte_delay_ms(CHECK_INTERVAL); 3884 } 3885 3886 /* set the print_flag if all ports up or timeout */ 3887 if (all_ports_up == 1 || count == (MAX_CHECK_TIME - 1)) { 3888 print_flag = 1; 3889 } 3890 3891 if (lsc_interrupt) 3892 break; 3893 } 3894 } 3895 3896 static void 3897 rmv_port_callback(void *arg) 3898 { 3899 int need_to_start = 0; 3900 int org_no_link_check = no_link_check; 3901 portid_t port_id = (intptr_t)arg; 3902 struct rte_eth_dev_info dev_info; 3903 int ret; 3904 3905 RTE_ETH_VALID_PORTID_OR_RET(port_id); 3906 3907 if (!test_done && port_is_forwarding(port_id)) { 3908 need_to_start = 1; 3909 stop_packet_forwarding(); 3910 } 3911 no_link_check = 1; 3912 stop_port(port_id); 3913 no_link_check = org_no_link_check; 3914 3915 ret = eth_dev_info_get_print_err(port_id, &dev_info); 3916 if (ret != 0) 3917 TESTPMD_LOG(ERR, 3918 "Failed to get device info for port %d, not detaching\n", 3919 port_id); 3920 else { 3921 struct rte_device *device = dev_info.device; 3922 close_port(port_id); 3923 detach_device(device); /* might be already removed or have more ports */ 3924 } 3925 if (need_to_start) 3926 start_packet_forwarding(0); 3927 } 3928 3929 /* This function is used by the interrupt thread */ 3930 static int 3931 eth_event_callback(portid_t port_id, enum rte_eth_event_type type, void *param, 3932 void *ret_param) 3933 { 3934 RTE_SET_USED(param); 3935 RTE_SET_USED(ret_param); 3936 3937 if (type >= RTE_ETH_EVENT_MAX) { 3938 fprintf(stderr, 3939 "\nPort %" PRIu16 ": %s called upon invalid event %d\n", 3940 port_id, __func__, type); 3941 fflush(stderr); 3942 } else if (event_print_mask & (UINT32_C(1) << type)) { 3943 printf("\nPort %" PRIu16 ": %s event\n", port_id, 3944 eth_event_desc[type]); 3945 fflush(stdout); 3946 } 3947 3948 switch (type) { 3949 case RTE_ETH_EVENT_NEW: 3950 ports[port_id].need_setup = 1; 3951 ports[port_id].port_status = RTE_PORT_HANDLING; 3952 break; 3953 case RTE_ETH_EVENT_INTR_RMV: 3954 if (port_id_is_invalid(port_id, DISABLED_WARN)) 3955 break; 3956 if (rte_eal_alarm_set(100000, 3957 rmv_port_callback, (void *)(intptr_t)port_id)) 3958 fprintf(stderr, 3959 "Could not set up deferred device removal\n"); 3960 break; 3961 case RTE_ETH_EVENT_DESTROY: 3962 ports[port_id].port_status = RTE_PORT_CLOSED; 3963 printf("Port %u is closed\n", port_id); 3964 break; 3965 case RTE_ETH_EVENT_RX_AVAIL_THRESH: { 3966 uint16_t rxq_id; 3967 int ret; 3968 3969 /* avail_thresh query API rewinds rxq_id, no need to check max RxQ num */ 3970 for (rxq_id = 0; ; rxq_id++) { 3971 ret = rte_eth_rx_avail_thresh_query(port_id, &rxq_id, 3972 NULL); 3973 if (ret <= 0) 3974 break; 3975 printf("Received avail_thresh event, port: %u, rxq_id: %u\n", 3976 port_id, rxq_id); 3977 3978 #ifdef RTE_NET_MLX5 3979 mlx5_test_avail_thresh_event_handler(port_id, rxq_id); 3980 #endif 3981 } 3982 break; 3983 } 3984 default: 3985 break; 3986 } 3987 return 0; 3988 } 3989 3990 static int 3991 register_eth_event_callback(void) 3992 { 3993 int ret; 3994 enum rte_eth_event_type event; 3995 3996 for (event = RTE_ETH_EVENT_UNKNOWN; 3997 event < RTE_ETH_EVENT_MAX; event++) { 3998 ret = rte_eth_dev_callback_register(RTE_ETH_ALL, 3999 event, 4000 eth_event_callback, 4001 NULL); 4002 if (ret != 0) { 4003 TESTPMD_LOG(ERR, "Failed to register callback for " 4004 "%s event\n", eth_event_desc[event]); 4005 return -1; 4006 } 4007 } 4008 4009 return 0; 4010 } 4011 4012 /* This function is used by the interrupt thread */ 4013 static void 4014 dev_event_callback(const char *device_name, enum rte_dev_event_type type, 4015 __rte_unused void *arg) 4016 { 4017 uint16_t port_id; 4018 int ret; 4019 4020 if (type >= RTE_DEV_EVENT_MAX) { 4021 fprintf(stderr, "%s called upon invalid event %d\n", 4022 __func__, type); 4023 fflush(stderr); 4024 } 4025 4026 switch (type) { 4027 case RTE_DEV_EVENT_REMOVE: 4028 RTE_LOG(DEBUG, EAL, "The device: %s has been removed!\n", 4029 device_name); 4030 ret = rte_eth_dev_get_port_by_name(device_name, &port_id); 4031 if (ret) { 4032 RTE_LOG(ERR, EAL, "can not get port by device %s!\n", 4033 device_name); 4034 return; 4035 } 4036 /* 4037 * Because the user's callback is invoked in eal interrupt 4038 * callback, the interrupt callback need to be finished before 4039 * it can be unregistered when detaching device. So finish 4040 * callback soon and use a deferred removal to detach device 4041 * is need. It is a workaround, once the device detaching be 4042 * moved into the eal in the future, the deferred removal could 4043 * be deleted. 4044 */ 4045 if (rte_eal_alarm_set(100000, 4046 rmv_port_callback, (void *)(intptr_t)port_id)) 4047 RTE_LOG(ERR, EAL, 4048 "Could not set up deferred device removal\n"); 4049 break; 4050 case RTE_DEV_EVENT_ADD: 4051 RTE_LOG(ERR, EAL, "The device: %s has been added!\n", 4052 device_name); 4053 /* TODO: After finish kernel driver binding, 4054 * begin to attach port. 4055 */ 4056 break; 4057 default: 4058 break; 4059 } 4060 } 4061 4062 static void 4063 rxtx_port_config(portid_t pid) 4064 { 4065 uint16_t qid; 4066 uint64_t offloads; 4067 struct rte_port *port = &ports[pid]; 4068 4069 for (qid = 0; qid < nb_rxq; qid++) { 4070 offloads = port->rxq[qid].conf.offloads; 4071 port->rxq[qid].conf = port->dev_info.default_rxconf; 4072 4073 if (rxq_share > 0 && 4074 (port->dev_info.dev_capa & RTE_ETH_DEV_CAPA_RXQ_SHARE)) { 4075 /* Non-zero share group to enable RxQ share. */ 4076 port->rxq[qid].conf.share_group = pid / rxq_share + 1; 4077 port->rxq[qid].conf.share_qid = qid; /* Equal mapping. */ 4078 } 4079 4080 if (offloads != 0) 4081 port->rxq[qid].conf.offloads = offloads; 4082 4083 /* Check if any Rx parameters have been passed */ 4084 if (rx_pthresh != RTE_PMD_PARAM_UNSET) 4085 port->rxq[qid].conf.rx_thresh.pthresh = rx_pthresh; 4086 4087 if (rx_hthresh != RTE_PMD_PARAM_UNSET) 4088 port->rxq[qid].conf.rx_thresh.hthresh = rx_hthresh; 4089 4090 if (rx_wthresh != RTE_PMD_PARAM_UNSET) 4091 port->rxq[qid].conf.rx_thresh.wthresh = rx_wthresh; 4092 4093 if (rx_free_thresh != RTE_PMD_PARAM_UNSET) 4094 port->rxq[qid].conf.rx_free_thresh = rx_free_thresh; 4095 4096 if (rx_drop_en != RTE_PMD_PARAM_UNSET) 4097 port->rxq[qid].conf.rx_drop_en = rx_drop_en; 4098 4099 port->nb_rx_desc[qid] = nb_rxd; 4100 } 4101 4102 for (qid = 0; qid < nb_txq; qid++) { 4103 offloads = port->txq[qid].conf.offloads; 4104 port->txq[qid].conf = port->dev_info.default_txconf; 4105 if (offloads != 0) 4106 port->txq[qid].conf.offloads = offloads; 4107 4108 /* Check if any Tx parameters have been passed */ 4109 if (tx_pthresh != RTE_PMD_PARAM_UNSET) 4110 port->txq[qid].conf.tx_thresh.pthresh = tx_pthresh; 4111 4112 if (tx_hthresh != RTE_PMD_PARAM_UNSET) 4113 port->txq[qid].conf.tx_thresh.hthresh = tx_hthresh; 4114 4115 if (tx_wthresh != RTE_PMD_PARAM_UNSET) 4116 port->txq[qid].conf.tx_thresh.wthresh = tx_wthresh; 4117 4118 if (tx_rs_thresh != RTE_PMD_PARAM_UNSET) 4119 port->txq[qid].conf.tx_rs_thresh = tx_rs_thresh; 4120 4121 if (tx_free_thresh != RTE_PMD_PARAM_UNSET) 4122 port->txq[qid].conf.tx_free_thresh = tx_free_thresh; 4123 4124 port->nb_tx_desc[qid] = nb_txd; 4125 } 4126 } 4127 4128 /* 4129 * Helper function to set MTU from frame size 4130 * 4131 * port->dev_info should be set before calling this function. 4132 * 4133 * return 0 on success, negative on error 4134 */ 4135 int 4136 update_mtu_from_frame_size(portid_t portid, uint32_t max_rx_pktlen) 4137 { 4138 struct rte_port *port = &ports[portid]; 4139 uint32_t eth_overhead; 4140 uint16_t mtu, new_mtu; 4141 4142 eth_overhead = get_eth_overhead(&port->dev_info); 4143 4144 if (rte_eth_dev_get_mtu(portid, &mtu) != 0) { 4145 printf("Failed to get MTU for port %u\n", portid); 4146 return -1; 4147 } 4148 4149 new_mtu = max_rx_pktlen - eth_overhead; 4150 4151 if (mtu == new_mtu) 4152 return 0; 4153 4154 if (eth_dev_set_mtu_mp(portid, new_mtu) != 0) { 4155 fprintf(stderr, 4156 "Failed to set MTU to %u for port %u\n", 4157 new_mtu, portid); 4158 return -1; 4159 } 4160 4161 port->dev_conf.rxmode.mtu = new_mtu; 4162 4163 return 0; 4164 } 4165 4166 void 4167 init_port_config(void) 4168 { 4169 portid_t pid; 4170 struct rte_port *port; 4171 int ret, i; 4172 4173 RTE_ETH_FOREACH_DEV(pid) { 4174 port = &ports[pid]; 4175 4176 ret = eth_dev_info_get_print_err(pid, &port->dev_info); 4177 if (ret != 0) 4178 return; 4179 4180 if (nb_rxq > 1) { 4181 port->dev_conf.rx_adv_conf.rss_conf.rss_key = NULL; 4182 port->dev_conf.rx_adv_conf.rss_conf.rss_hf = 4183 rss_hf & port->dev_info.flow_type_rss_offloads; 4184 } else { 4185 port->dev_conf.rx_adv_conf.rss_conf.rss_key = NULL; 4186 port->dev_conf.rx_adv_conf.rss_conf.rss_hf = 0; 4187 } 4188 4189 if (port->dcb_flag == 0) { 4190 if (port->dev_conf.rx_adv_conf.rss_conf.rss_hf != 0) { 4191 port->dev_conf.rxmode.mq_mode = 4192 (enum rte_eth_rx_mq_mode) 4193 (rx_mq_mode & RTE_ETH_MQ_RX_RSS); 4194 } else { 4195 port->dev_conf.rxmode.mq_mode = RTE_ETH_MQ_RX_NONE; 4196 port->dev_conf.rxmode.offloads &= 4197 ~RTE_ETH_RX_OFFLOAD_RSS_HASH; 4198 4199 for (i = 0; 4200 i < port->dev_info.nb_rx_queues; 4201 i++) 4202 port->rxq[i].conf.offloads &= 4203 ~RTE_ETH_RX_OFFLOAD_RSS_HASH; 4204 } 4205 } 4206 4207 rxtx_port_config(pid); 4208 4209 ret = eth_macaddr_get_print_err(pid, &port->eth_addr); 4210 if (ret != 0) 4211 return; 4212 4213 if (lsc_interrupt && (*port->dev_info.dev_flags & RTE_ETH_DEV_INTR_LSC)) 4214 port->dev_conf.intr_conf.lsc = 1; 4215 if (rmv_interrupt && (*port->dev_info.dev_flags & RTE_ETH_DEV_INTR_RMV)) 4216 port->dev_conf.intr_conf.rmv = 1; 4217 } 4218 } 4219 4220 void set_port_slave_flag(portid_t slave_pid) 4221 { 4222 struct rte_port *port; 4223 4224 port = &ports[slave_pid]; 4225 port->slave_flag = 1; 4226 } 4227 4228 void clear_port_slave_flag(portid_t slave_pid) 4229 { 4230 struct rte_port *port; 4231 4232 port = &ports[slave_pid]; 4233 port->slave_flag = 0; 4234 } 4235 4236 uint8_t port_is_bonding_slave(portid_t slave_pid) 4237 { 4238 struct rte_port *port; 4239 struct rte_eth_dev_info dev_info; 4240 int ret; 4241 4242 port = &ports[slave_pid]; 4243 ret = eth_dev_info_get_print_err(slave_pid, &dev_info); 4244 if (ret != 0) { 4245 TESTPMD_LOG(ERR, 4246 "Failed to get device info for port id %d," 4247 "cannot determine if the port is a bonded slave", 4248 slave_pid); 4249 return 0; 4250 } 4251 if ((*dev_info.dev_flags & RTE_ETH_DEV_BONDED_SLAVE) || (port->slave_flag == 1)) 4252 return 1; 4253 return 0; 4254 } 4255 4256 const uint16_t vlan_tags[] = { 4257 0, 1, 2, 3, 4, 5, 6, 7, 4258 8, 9, 10, 11, 12, 13, 14, 15, 4259 16, 17, 18, 19, 20, 21, 22, 23, 4260 24, 25, 26, 27, 28, 29, 30, 31 4261 }; 4262 4263 static int 4264 get_eth_dcb_conf(portid_t pid, struct rte_eth_conf *eth_conf, 4265 enum dcb_mode_enable dcb_mode, 4266 enum rte_eth_nb_tcs num_tcs, 4267 uint8_t pfc_en) 4268 { 4269 uint8_t i; 4270 int32_t rc; 4271 struct rte_eth_rss_conf rss_conf; 4272 4273 /* 4274 * Builds up the correct configuration for dcb+vt based on the vlan tags array 4275 * given above, and the number of traffic classes available for use. 4276 */ 4277 if (dcb_mode == DCB_VT_ENABLED) { 4278 struct rte_eth_vmdq_dcb_conf *vmdq_rx_conf = 4279 ð_conf->rx_adv_conf.vmdq_dcb_conf; 4280 struct rte_eth_vmdq_dcb_tx_conf *vmdq_tx_conf = 4281 ð_conf->tx_adv_conf.vmdq_dcb_tx_conf; 4282 4283 /* VMDQ+DCB RX and TX configurations */ 4284 vmdq_rx_conf->enable_default_pool = 0; 4285 vmdq_rx_conf->default_pool = 0; 4286 vmdq_rx_conf->nb_queue_pools = 4287 (num_tcs == RTE_ETH_4_TCS ? RTE_ETH_32_POOLS : RTE_ETH_16_POOLS); 4288 vmdq_tx_conf->nb_queue_pools = 4289 (num_tcs == RTE_ETH_4_TCS ? RTE_ETH_32_POOLS : RTE_ETH_16_POOLS); 4290 4291 vmdq_rx_conf->nb_pool_maps = vmdq_rx_conf->nb_queue_pools; 4292 for (i = 0; i < vmdq_rx_conf->nb_pool_maps; i++) { 4293 vmdq_rx_conf->pool_map[i].vlan_id = vlan_tags[i]; 4294 vmdq_rx_conf->pool_map[i].pools = 4295 1 << (i % vmdq_rx_conf->nb_queue_pools); 4296 } 4297 for (i = 0; i < RTE_ETH_DCB_NUM_USER_PRIORITIES; i++) { 4298 vmdq_rx_conf->dcb_tc[i] = i % num_tcs; 4299 vmdq_tx_conf->dcb_tc[i] = i % num_tcs; 4300 } 4301 4302 /* set DCB mode of RX and TX of multiple queues */ 4303 eth_conf->rxmode.mq_mode = 4304 (enum rte_eth_rx_mq_mode) 4305 (rx_mq_mode & RTE_ETH_MQ_RX_VMDQ_DCB); 4306 eth_conf->txmode.mq_mode = RTE_ETH_MQ_TX_VMDQ_DCB; 4307 } else { 4308 struct rte_eth_dcb_rx_conf *rx_conf = 4309 ð_conf->rx_adv_conf.dcb_rx_conf; 4310 struct rte_eth_dcb_tx_conf *tx_conf = 4311 ð_conf->tx_adv_conf.dcb_tx_conf; 4312 4313 memset(&rss_conf, 0, sizeof(struct rte_eth_rss_conf)); 4314 4315 rc = rte_eth_dev_rss_hash_conf_get(pid, &rss_conf); 4316 if (rc != 0) 4317 return rc; 4318 4319 rx_conf->nb_tcs = num_tcs; 4320 tx_conf->nb_tcs = num_tcs; 4321 4322 for (i = 0; i < RTE_ETH_DCB_NUM_USER_PRIORITIES; i++) { 4323 rx_conf->dcb_tc[i] = i % num_tcs; 4324 tx_conf->dcb_tc[i] = i % num_tcs; 4325 } 4326 4327 eth_conf->rxmode.mq_mode = 4328 (enum rte_eth_rx_mq_mode) 4329 (rx_mq_mode & RTE_ETH_MQ_RX_DCB_RSS); 4330 eth_conf->rx_adv_conf.rss_conf = rss_conf; 4331 eth_conf->txmode.mq_mode = RTE_ETH_MQ_TX_DCB; 4332 } 4333 4334 if (pfc_en) 4335 eth_conf->dcb_capability_en = 4336 RTE_ETH_DCB_PG_SUPPORT | RTE_ETH_DCB_PFC_SUPPORT; 4337 else 4338 eth_conf->dcb_capability_en = RTE_ETH_DCB_PG_SUPPORT; 4339 4340 return 0; 4341 } 4342 4343 int 4344 init_port_dcb_config(portid_t pid, 4345 enum dcb_mode_enable dcb_mode, 4346 enum rte_eth_nb_tcs num_tcs, 4347 uint8_t pfc_en) 4348 { 4349 struct rte_eth_conf port_conf; 4350 struct rte_port *rte_port; 4351 int retval; 4352 uint16_t i; 4353 4354 if (num_procs > 1) { 4355 printf("The multi-process feature doesn't support dcb.\n"); 4356 return -ENOTSUP; 4357 } 4358 rte_port = &ports[pid]; 4359 4360 /* retain the original device configuration. */ 4361 memcpy(&port_conf, &rte_port->dev_conf, sizeof(struct rte_eth_conf)); 4362 4363 /*set configuration of DCB in vt mode and DCB in non-vt mode*/ 4364 retval = get_eth_dcb_conf(pid, &port_conf, dcb_mode, num_tcs, pfc_en); 4365 if (retval < 0) 4366 return retval; 4367 port_conf.rxmode.offloads |= RTE_ETH_RX_OFFLOAD_VLAN_FILTER; 4368 /* remove RSS HASH offload for DCB in vt mode */ 4369 if (port_conf.rxmode.mq_mode == RTE_ETH_MQ_RX_VMDQ_DCB) { 4370 port_conf.rxmode.offloads &= ~RTE_ETH_RX_OFFLOAD_RSS_HASH; 4371 for (i = 0; i < nb_rxq; i++) 4372 rte_port->rxq[i].conf.offloads &= 4373 ~RTE_ETH_RX_OFFLOAD_RSS_HASH; 4374 } 4375 4376 /* re-configure the device . */ 4377 retval = rte_eth_dev_configure(pid, nb_rxq, nb_rxq, &port_conf); 4378 if (retval < 0) 4379 return retval; 4380 4381 retval = eth_dev_info_get_print_err(pid, &rte_port->dev_info); 4382 if (retval != 0) 4383 return retval; 4384 4385 /* If dev_info.vmdq_pool_base is greater than 0, 4386 * the queue id of vmdq pools is started after pf queues. 4387 */ 4388 if (dcb_mode == DCB_VT_ENABLED && 4389 rte_port->dev_info.vmdq_pool_base > 0) { 4390 fprintf(stderr, 4391 "VMDQ_DCB multi-queue mode is nonsensical for port %d.\n", 4392 pid); 4393 return -1; 4394 } 4395 4396 /* Assume the ports in testpmd have the same dcb capability 4397 * and has the same number of rxq and txq in dcb mode 4398 */ 4399 if (dcb_mode == DCB_VT_ENABLED) { 4400 if (rte_port->dev_info.max_vfs > 0) { 4401 nb_rxq = rte_port->dev_info.nb_rx_queues; 4402 nb_txq = rte_port->dev_info.nb_tx_queues; 4403 } else { 4404 nb_rxq = rte_port->dev_info.max_rx_queues; 4405 nb_txq = rte_port->dev_info.max_tx_queues; 4406 } 4407 } else { 4408 /*if vt is disabled, use all pf queues */ 4409 if (rte_port->dev_info.vmdq_pool_base == 0) { 4410 nb_rxq = rte_port->dev_info.max_rx_queues; 4411 nb_txq = rte_port->dev_info.max_tx_queues; 4412 } else { 4413 nb_rxq = (queueid_t)num_tcs; 4414 nb_txq = (queueid_t)num_tcs; 4415 4416 } 4417 } 4418 rx_free_thresh = 64; 4419 4420 memcpy(&rte_port->dev_conf, &port_conf, sizeof(struct rte_eth_conf)); 4421 4422 rxtx_port_config(pid); 4423 /* VLAN filter */ 4424 rte_port->dev_conf.rxmode.offloads |= RTE_ETH_RX_OFFLOAD_VLAN_FILTER; 4425 for (i = 0; i < RTE_DIM(vlan_tags); i++) 4426 rx_vft_set(pid, vlan_tags[i], 1); 4427 4428 retval = eth_macaddr_get_print_err(pid, &rte_port->eth_addr); 4429 if (retval != 0) 4430 return retval; 4431 4432 rte_port->dcb_flag = 1; 4433 4434 /* Enter DCB configuration status */ 4435 dcb_config = 1; 4436 4437 return 0; 4438 } 4439 4440 static void 4441 init_port(void) 4442 { 4443 int i; 4444 4445 /* Configuration of Ethernet ports. */ 4446 ports = rte_zmalloc("testpmd: ports", 4447 sizeof(struct rte_port) * RTE_MAX_ETHPORTS, 4448 RTE_CACHE_LINE_SIZE); 4449 if (ports == NULL) { 4450 rte_exit(EXIT_FAILURE, 4451 "rte_zmalloc(%d struct rte_port) failed\n", 4452 RTE_MAX_ETHPORTS); 4453 } 4454 for (i = 0; i < RTE_MAX_ETHPORTS; i++) { 4455 ports[i].fwd_mac_swap = 1; 4456 ports[i].xstats_info.allocated = false; 4457 LIST_INIT(&ports[i].flow_tunnel_list); 4458 } 4459 /* Initialize ports NUMA structures */ 4460 memset(port_numa, NUMA_NO_CONFIG, RTE_MAX_ETHPORTS); 4461 memset(rxring_numa, NUMA_NO_CONFIG, RTE_MAX_ETHPORTS); 4462 memset(txring_numa, NUMA_NO_CONFIG, RTE_MAX_ETHPORTS); 4463 } 4464 4465 static void 4466 print_stats(void) 4467 { 4468 uint8_t i; 4469 const char clr[] = { 27, '[', '2', 'J', '\0' }; 4470 const char top_left[] = { 27, '[', '1', ';', '1', 'H', '\0' }; 4471 4472 /* Clear screen and move to top left */ 4473 printf("%s%s", clr, top_left); 4474 4475 printf("\nPort statistics ===================================="); 4476 for (i = 0; i < cur_fwd_config.nb_fwd_ports; i++) 4477 nic_stats_display(fwd_ports_ids[i]); 4478 4479 fflush(stdout); 4480 } 4481 4482 static void 4483 signal_handler(int signum __rte_unused) 4484 { 4485 f_quit = 1; 4486 prompt_exit(); 4487 } 4488 4489 int 4490 main(int argc, char** argv) 4491 { 4492 int diag; 4493 portid_t port_id; 4494 uint16_t count; 4495 int ret; 4496 4497 #ifdef RTE_EXEC_ENV_WINDOWS 4498 signal(SIGINT, signal_handler); 4499 signal(SIGTERM, signal_handler); 4500 #else 4501 /* Want read() not to be restarted on signal */ 4502 struct sigaction action = { 4503 .sa_handler = signal_handler, 4504 }; 4505 4506 sigaction(SIGINT, &action, NULL); 4507 sigaction(SIGTERM, &action, NULL); 4508 #endif 4509 4510 testpmd_logtype = rte_log_register("testpmd"); 4511 if (testpmd_logtype < 0) 4512 rte_exit(EXIT_FAILURE, "Cannot register log type"); 4513 rte_log_set_level(testpmd_logtype, RTE_LOG_DEBUG); 4514 4515 diag = rte_eal_init(argc, argv); 4516 if (diag < 0) 4517 rte_exit(EXIT_FAILURE, "Cannot init EAL: %s\n", 4518 rte_strerror(rte_errno)); 4519 4520 /* allocate port structures, and init them */ 4521 init_port(); 4522 4523 ret = register_eth_event_callback(); 4524 if (ret != 0) 4525 rte_exit(EXIT_FAILURE, "Cannot register for ethdev events"); 4526 4527 #ifdef RTE_LIB_PDUMP 4528 /* initialize packet capture framework */ 4529 rte_pdump_init(); 4530 #endif 4531 4532 count = 0; 4533 RTE_ETH_FOREACH_DEV(port_id) { 4534 ports_ids[count] = port_id; 4535 count++; 4536 } 4537 nb_ports = (portid_t) count; 4538 if (nb_ports == 0) 4539 TESTPMD_LOG(WARNING, "No probed ethernet devices\n"); 4540 4541 set_def_fwd_config(); 4542 if (nb_lcores == 0) 4543 rte_exit(EXIT_FAILURE, "No cores defined for forwarding\n" 4544 "Check the core mask argument\n"); 4545 4546 /* Bitrate/latency stats disabled by default */ 4547 #ifdef RTE_LIB_BITRATESTATS 4548 bitrate_enabled = 0; 4549 #endif 4550 #ifdef RTE_LIB_LATENCYSTATS 4551 latencystats_enabled = 0; 4552 #endif 4553 4554 /* on FreeBSD, mlockall() is disabled by default */ 4555 #ifdef RTE_EXEC_ENV_FREEBSD 4556 do_mlockall = 0; 4557 #else 4558 do_mlockall = 1; 4559 #endif 4560 4561 argc -= diag; 4562 argv += diag; 4563 if (argc > 1) 4564 launch_args_parse(argc, argv); 4565 4566 #ifndef RTE_EXEC_ENV_WINDOWS 4567 if (do_mlockall && mlockall(MCL_CURRENT | MCL_FUTURE)) { 4568 TESTPMD_LOG(NOTICE, "mlockall() failed with error \"%s\"\n", 4569 strerror(errno)); 4570 } 4571 #endif 4572 4573 if (tx_first && interactive) 4574 rte_exit(EXIT_FAILURE, "--tx-first cannot be used on " 4575 "interactive mode.\n"); 4576 4577 if (tx_first && lsc_interrupt) { 4578 fprintf(stderr, 4579 "Warning: lsc_interrupt needs to be off when using tx_first. Disabling.\n"); 4580 lsc_interrupt = 0; 4581 } 4582 4583 if (!nb_rxq && !nb_txq) 4584 fprintf(stderr, 4585 "Warning: Either rx or tx queues should be non-zero\n"); 4586 4587 if (nb_rxq > 1 && nb_rxq > nb_txq) 4588 fprintf(stderr, 4589 "Warning: nb_rxq=%d enables RSS configuration, but nb_txq=%d will prevent to fully test it.\n", 4590 nb_rxq, nb_txq); 4591 4592 init_config(); 4593 4594 if (hot_plug) { 4595 ret = rte_dev_hotplug_handle_enable(); 4596 if (ret) { 4597 RTE_LOG(ERR, EAL, 4598 "fail to enable hotplug handling."); 4599 return -1; 4600 } 4601 4602 ret = rte_dev_event_monitor_start(); 4603 if (ret) { 4604 RTE_LOG(ERR, EAL, 4605 "fail to start device event monitoring."); 4606 return -1; 4607 } 4608 4609 ret = rte_dev_event_callback_register(NULL, 4610 dev_event_callback, NULL); 4611 if (ret) { 4612 RTE_LOG(ERR, EAL, 4613 "fail to register device event callback\n"); 4614 return -1; 4615 } 4616 } 4617 4618 if (!no_device_start && start_port(RTE_PORT_ALL) != 0) { 4619 if (!interactive) { 4620 rte_eal_cleanup(); 4621 rte_exit(EXIT_FAILURE, "Start ports failed\n"); 4622 } 4623 fprintf(stderr, "Start ports failed\n"); 4624 } 4625 4626 /* set all ports to promiscuous mode by default */ 4627 RTE_ETH_FOREACH_DEV(port_id) { 4628 ret = rte_eth_promiscuous_enable(port_id); 4629 if (ret != 0) 4630 fprintf(stderr, 4631 "Error during enabling promiscuous mode for port %u: %s - ignore\n", 4632 port_id, rte_strerror(-ret)); 4633 } 4634 4635 #ifdef RTE_LIB_METRICS 4636 /* Init metrics library */ 4637 rte_metrics_init(rte_socket_id()); 4638 #endif 4639 4640 #ifdef RTE_LIB_LATENCYSTATS 4641 if (latencystats_enabled != 0) { 4642 int ret = rte_latencystats_init(1, NULL); 4643 if (ret) 4644 fprintf(stderr, 4645 "Warning: latencystats init() returned error %d\n", 4646 ret); 4647 fprintf(stderr, "Latencystats running on lcore %d\n", 4648 latencystats_lcore_id); 4649 } 4650 #endif 4651 4652 /* Setup bitrate stats */ 4653 #ifdef RTE_LIB_BITRATESTATS 4654 if (bitrate_enabled != 0) { 4655 bitrate_data = rte_stats_bitrate_create(); 4656 if (bitrate_data == NULL) 4657 rte_exit(EXIT_FAILURE, 4658 "Could not allocate bitrate data.\n"); 4659 rte_stats_bitrate_reg(bitrate_data); 4660 } 4661 #endif 4662 4663 if (record_core_cycles) 4664 rte_lcore_register_usage_cb(lcore_usage_callback); 4665 4666 #ifdef RTE_LIB_CMDLINE 4667 if (init_cmdline() != 0) 4668 rte_exit(EXIT_FAILURE, 4669 "Could not initialise cmdline context.\n"); 4670 4671 if (strlen(cmdline_filename) != 0) 4672 cmdline_read_from_file(cmdline_filename); 4673 4674 if (interactive == 1) { 4675 if (auto_start) { 4676 printf("Start automatic packet forwarding\n"); 4677 start_packet_forwarding(0); 4678 } 4679 prompt(); 4680 } else 4681 #endif 4682 { 4683 printf("No commandline core given, start packet forwarding\n"); 4684 start_packet_forwarding(tx_first); 4685 if (stats_period != 0) { 4686 uint64_t prev_time = 0, cur_time, diff_time = 0; 4687 uint64_t timer_period; 4688 4689 /* Convert to number of cycles */ 4690 timer_period = stats_period * rte_get_timer_hz(); 4691 4692 while (f_quit == 0) { 4693 cur_time = rte_get_timer_cycles(); 4694 diff_time += cur_time - prev_time; 4695 4696 if (diff_time >= timer_period) { 4697 print_stats(); 4698 /* Reset the timer */ 4699 diff_time = 0; 4700 } 4701 /* Sleep to avoid unnecessary checks */ 4702 prev_time = cur_time; 4703 rte_delay_us_sleep(US_PER_S); 4704 } 4705 } else { 4706 char c; 4707 fd_set fds; 4708 4709 printf("Press enter to exit\n"); 4710 4711 FD_ZERO(&fds); 4712 FD_SET(0, &fds); 4713 4714 /* wait for signal or enter */ 4715 ret = select(1, &fds, NULL, NULL, NULL); 4716 if (ret < 0 && errno != EINTR) 4717 rte_exit(EXIT_FAILURE, 4718 "Select failed: %s\n", 4719 strerror(errno)); 4720 4721 /* if got enter then consume it */ 4722 if (ret == 1 && read(0, &c, 1) < 0) 4723 rte_exit(EXIT_FAILURE, 4724 "Read failed: %s\n", 4725 strerror(errno)); 4726 } 4727 } 4728 4729 pmd_test_exit(); 4730 4731 #ifdef RTE_LIB_PDUMP 4732 /* uninitialize packet capture framework */ 4733 rte_pdump_uninit(); 4734 #endif 4735 #ifdef RTE_LIB_LATENCYSTATS 4736 if (latencystats_enabled != 0) 4737 rte_latencystats_uninit(); 4738 #endif 4739 4740 ret = rte_eal_cleanup(); 4741 if (ret != 0) 4742 rte_exit(EXIT_FAILURE, 4743 "EAL cleanup failed: %s\n", strerror(-ret)); 4744 4745 return EXIT_SUCCESS; 4746 } 4747