1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2014-2021 Broadcom 3 * All rights reserved. 4 */ 5 6 #include <inttypes.h> 7 #include <stdbool.h> 8 9 #include <rte_dev.h> 10 #include <ethdev_driver.h> 11 #include <ethdev_pci.h> 12 #include <rte_malloc.h> 13 #include <rte_cycles.h> 14 #include <rte_alarm.h> 15 #include <rte_kvargs.h> 16 #include <rte_vect.h> 17 18 #include "bnxt.h" 19 #include "bnxt_filter.h" 20 #include "bnxt_hwrm.h" 21 #include "bnxt_irq.h" 22 #include "bnxt_reps.h" 23 #include "bnxt_ring.h" 24 #include "bnxt_rxq.h" 25 #include "bnxt_rxr.h" 26 #include "bnxt_stats.h" 27 #include "bnxt_txq.h" 28 #include "bnxt_txr.h" 29 #include "bnxt_vnic.h" 30 #include "hsi_struct_def_dpdk.h" 31 #include "bnxt_nvm_defs.h" 32 #include "bnxt_tf_common.h" 33 #include "ulp_flow_db.h" 34 #include "rte_pmd_bnxt.h" 35 36 #define DRV_MODULE_NAME "bnxt" 37 static const char bnxt_version[] = 38 "Broadcom NetXtreme driver " DRV_MODULE_NAME; 39 40 /* 41 * The set of PCI devices this driver supports 42 */ 43 static const struct rte_pci_id bnxt_pci_id_map[] = { 44 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 45 BROADCOM_DEV_ID_STRATUS_NIC_VF1) }, 46 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 47 BROADCOM_DEV_ID_STRATUS_NIC_VF2) }, 48 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_STRATUS_NIC) }, 49 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57414_VF) }, 50 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57304_VF) }, 51 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_NS2) }, 52 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57406_VF) }, 53 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57407_MF) }, 54 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_5741X_VF) }, 55 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_5731X_VF) }, 56 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57417_MF) }, 57 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57412) }, 58 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57414) }, 59 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57416_RJ45) }, 60 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57417_RJ45) }, 61 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57412_MF) }, 62 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57317_RJ45) }, 63 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57417_SFP) }, 64 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57416_SFP) }, 65 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57317_SFP) }, 66 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57414_MF) }, 67 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57416_MF) }, 68 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58802) }, 69 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58804) }, 70 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58808) }, 71 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58802_VF) }, 72 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57508) }, 73 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57504) }, 74 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57502) }, 75 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57500_VF1) }, 76 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57500_VF2) }, 77 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57508_MF1) }, 78 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57504_MF1) }, 79 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57502_MF1) }, 80 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57508_MF2) }, 81 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57504_MF2) }, 82 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57502_MF2) }, 83 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58812) }, 84 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58814) }, 85 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58818) }, 86 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58818_VF) }, 87 { .vendor_id = 0, /* sentinel */ }, 88 }; 89 90 #define BNXT_DEVARG_ACCUM_STATS "accum-stats" 91 #define BNXT_DEVARG_FLOW_XSTAT "flow-xstat" 92 #define BNXT_DEVARG_MAX_NUM_KFLOWS "max-num-kflows" 93 #define BNXT_DEVARG_REPRESENTOR "representor" 94 #define BNXT_DEVARG_REP_BASED_PF "rep-based-pf" 95 #define BNXT_DEVARG_REP_IS_PF "rep-is-pf" 96 #define BNXT_DEVARG_REP_Q_R2F "rep-q-r2f" 97 #define BNXT_DEVARG_REP_Q_F2R "rep-q-f2r" 98 #define BNXT_DEVARG_REP_FC_R2F "rep-fc-r2f" 99 #define BNXT_DEVARG_REP_FC_F2R "rep-fc-f2r" 100 #define BNXT_DEVARG_APP_ID "app-id" 101 102 static const char *const bnxt_dev_args[] = { 103 BNXT_DEVARG_REPRESENTOR, 104 BNXT_DEVARG_ACCUM_STATS, 105 BNXT_DEVARG_FLOW_XSTAT, 106 BNXT_DEVARG_MAX_NUM_KFLOWS, 107 BNXT_DEVARG_REP_BASED_PF, 108 BNXT_DEVARG_REP_IS_PF, 109 BNXT_DEVARG_REP_Q_R2F, 110 BNXT_DEVARG_REP_Q_F2R, 111 BNXT_DEVARG_REP_FC_R2F, 112 BNXT_DEVARG_REP_FC_F2R, 113 BNXT_DEVARG_APP_ID, 114 NULL 115 }; 116 117 /* 118 * accum-stats == false to disable flow counter accumulation 119 * accum-stats == true to enable flow counter accumulation 120 */ 121 #define BNXT_DEVARG_ACCUM_STATS_INVALID(accum_stats) ((accum_stats) > 1) 122 123 /* 124 * app-id = an non-negative 8-bit number 125 */ 126 #define BNXT_DEVARG_APP_ID_INVALID(val) ((val) > 255) 127 128 /* 129 * flow_xstat == false to disable the feature 130 * flow_xstat == true to enable the feature 131 */ 132 #define BNXT_DEVARG_FLOW_XSTAT_INVALID(flow_xstat) ((flow_xstat) > 1) 133 134 /* 135 * rep_is_pf == false to indicate VF representor 136 * rep_is_pf == true to indicate PF representor 137 */ 138 #define BNXT_DEVARG_REP_IS_PF_INVALID(rep_is_pf) ((rep_is_pf) > 1) 139 140 /* 141 * rep_based_pf == Physical index of the PF 142 */ 143 #define BNXT_DEVARG_REP_BASED_PF_INVALID(rep_based_pf) ((rep_based_pf) > 15) 144 /* 145 * rep_q_r2f == Logical COS Queue index for the rep to endpoint direction 146 */ 147 #define BNXT_DEVARG_REP_Q_R2F_INVALID(rep_q_r2f) ((rep_q_r2f) > 3) 148 149 /* 150 * rep_q_f2r == Logical COS Queue index for the endpoint to rep direction 151 */ 152 #define BNXT_DEVARG_REP_Q_F2R_INVALID(rep_q_f2r) ((rep_q_f2r) > 3) 153 154 /* 155 * rep_fc_r2f == Flow control for the representor to endpoint direction 156 */ 157 #define BNXT_DEVARG_REP_FC_R2F_INVALID(rep_fc_r2f) ((rep_fc_r2f) > 1) 158 159 /* 160 * rep_fc_f2r == Flow control for the endpoint to representor direction 161 */ 162 #define BNXT_DEVARG_REP_FC_F2R_INVALID(rep_fc_f2r) ((rep_fc_f2r) > 1) 163 164 int bnxt_cfa_code_dynfield_offset = -1; 165 166 /* 167 * max_num_kflows must be >= 32 168 * and must be a power-of-2 supported value 169 * return: 1 -> invalid 170 * 0 -> valid 171 */ 172 static int bnxt_devarg_max_num_kflow_invalid(uint16_t max_num_kflows) 173 { 174 if (max_num_kflows < 32 || !rte_is_power_of_2(max_num_kflows)) 175 return 1; 176 return 0; 177 } 178 179 static int bnxt_vlan_offload_set_op(struct rte_eth_dev *dev, int mask); 180 static int bnxt_dev_uninit(struct rte_eth_dev *eth_dev); 181 static int bnxt_init_resources(struct bnxt *bp, bool reconfig_dev); 182 static int bnxt_uninit_resources(struct bnxt *bp, bool reconfig_dev); 183 static void bnxt_cancel_fw_health_check(struct bnxt *bp); 184 static int bnxt_restore_vlan_filters(struct bnxt *bp); 185 static void bnxt_dev_recover(void *arg); 186 static void bnxt_free_error_recovery_info(struct bnxt *bp); 187 static void bnxt_free_rep_info(struct bnxt *bp); 188 189 int is_bnxt_in_error(struct bnxt *bp) 190 { 191 if (bp->flags & BNXT_FLAG_FATAL_ERROR) 192 return -EIO; 193 if (bp->flags & BNXT_FLAG_FW_RESET) 194 return -EBUSY; 195 196 return 0; 197 } 198 199 /***********************/ 200 201 /* 202 * High level utility functions 203 */ 204 205 static uint16_t bnxt_rss_ctxts(const struct bnxt *bp) 206 { 207 unsigned int num_rss_rings = RTE_MIN(bp->rx_nr_rings, 208 BNXT_RSS_TBL_SIZE_P5); 209 210 if (!BNXT_CHIP_P5(bp)) 211 return 1; 212 213 return RTE_ALIGN_MUL_CEIL(num_rss_rings, 214 BNXT_RSS_ENTRIES_PER_CTX_P5) / 215 BNXT_RSS_ENTRIES_PER_CTX_P5; 216 } 217 218 uint16_t bnxt_rss_hash_tbl_size(const struct bnxt *bp) 219 { 220 if (!BNXT_CHIP_P5(bp)) 221 return HW_HASH_INDEX_SIZE; 222 223 return bnxt_rss_ctxts(bp) * BNXT_RSS_ENTRIES_PER_CTX_P5; 224 } 225 226 static void bnxt_free_parent_info(struct bnxt *bp) 227 { 228 rte_free(bp->parent); 229 bp->parent = NULL; 230 } 231 232 static void bnxt_free_pf_info(struct bnxt *bp) 233 { 234 rte_free(bp->pf); 235 bp->pf = NULL; 236 } 237 238 static void bnxt_free_link_info(struct bnxt *bp) 239 { 240 rte_free(bp->link_info); 241 bp->link_info = NULL; 242 } 243 244 static void bnxt_free_leds_info(struct bnxt *bp) 245 { 246 if (BNXT_VF(bp)) 247 return; 248 249 rte_free(bp->leds); 250 bp->leds = NULL; 251 } 252 253 static void bnxt_free_flow_stats_info(struct bnxt *bp) 254 { 255 rte_free(bp->flow_stat); 256 bp->flow_stat = NULL; 257 } 258 259 static void bnxt_free_cos_queues(struct bnxt *bp) 260 { 261 rte_free(bp->rx_cos_queue); 262 bp->rx_cos_queue = NULL; 263 rte_free(bp->tx_cos_queue); 264 bp->tx_cos_queue = NULL; 265 } 266 267 static void bnxt_free_mem(struct bnxt *bp, bool reconfig) 268 { 269 bnxt_free_filter_mem(bp); 270 bnxt_free_vnic_attributes(bp); 271 bnxt_free_vnic_mem(bp); 272 273 /* tx/rx rings are configured as part of *_queue_setup callbacks. 274 * If the number of rings change across fw update, 275 * we don't have much choice except to warn the user. 276 */ 277 if (!reconfig) { 278 bnxt_free_stats(bp); 279 bnxt_free_tx_rings(bp); 280 bnxt_free_rx_rings(bp); 281 } 282 bnxt_free_async_cp_ring(bp); 283 bnxt_free_rxtx_nq_ring(bp); 284 285 rte_free(bp->grp_info); 286 bp->grp_info = NULL; 287 } 288 289 static int bnxt_alloc_parent_info(struct bnxt *bp) 290 { 291 bp->parent = rte_zmalloc("bnxt_parent_info", 292 sizeof(struct bnxt_parent_info), 0); 293 if (bp->parent == NULL) 294 return -ENOMEM; 295 296 return 0; 297 } 298 299 static int bnxt_alloc_pf_info(struct bnxt *bp) 300 { 301 bp->pf = rte_zmalloc("bnxt_pf_info", sizeof(struct bnxt_pf_info), 0); 302 if (bp->pf == NULL) 303 return -ENOMEM; 304 305 return 0; 306 } 307 308 static int bnxt_alloc_link_info(struct bnxt *bp) 309 { 310 bp->link_info = 311 rte_zmalloc("bnxt_link_info", sizeof(struct bnxt_link_info), 0); 312 if (bp->link_info == NULL) 313 return -ENOMEM; 314 315 return 0; 316 } 317 318 static int bnxt_alloc_leds_info(struct bnxt *bp) 319 { 320 if (BNXT_VF(bp)) 321 return 0; 322 323 bp->leds = rte_zmalloc("bnxt_leds", 324 BNXT_MAX_LED * sizeof(struct bnxt_led_info), 325 0); 326 if (bp->leds == NULL) 327 return -ENOMEM; 328 329 return 0; 330 } 331 332 static int bnxt_alloc_cos_queues(struct bnxt *bp) 333 { 334 bp->rx_cos_queue = 335 rte_zmalloc("bnxt_rx_cosq", 336 BNXT_COS_QUEUE_COUNT * 337 sizeof(struct bnxt_cos_queue_info), 338 0); 339 if (bp->rx_cos_queue == NULL) 340 return -ENOMEM; 341 342 bp->tx_cos_queue = 343 rte_zmalloc("bnxt_tx_cosq", 344 BNXT_COS_QUEUE_COUNT * 345 sizeof(struct bnxt_cos_queue_info), 346 0); 347 if (bp->tx_cos_queue == NULL) 348 return -ENOMEM; 349 350 return 0; 351 } 352 353 static int bnxt_alloc_flow_stats_info(struct bnxt *bp) 354 { 355 bp->flow_stat = rte_zmalloc("bnxt_flow_xstat", 356 sizeof(struct bnxt_flow_stat_info), 0); 357 if (bp->flow_stat == NULL) 358 return -ENOMEM; 359 360 return 0; 361 } 362 363 static int bnxt_alloc_mem(struct bnxt *bp, bool reconfig) 364 { 365 int rc; 366 367 rc = bnxt_alloc_ring_grps(bp); 368 if (rc) 369 goto alloc_mem_err; 370 371 rc = bnxt_alloc_async_ring_struct(bp); 372 if (rc) 373 goto alloc_mem_err; 374 375 rc = bnxt_alloc_vnic_mem(bp); 376 if (rc) 377 goto alloc_mem_err; 378 379 rc = bnxt_alloc_vnic_attributes(bp); 380 if (rc) 381 goto alloc_mem_err; 382 383 rc = bnxt_alloc_filter_mem(bp); 384 if (rc) 385 goto alloc_mem_err; 386 387 rc = bnxt_alloc_async_cp_ring(bp); 388 if (rc) 389 goto alloc_mem_err; 390 391 rc = bnxt_alloc_rxtx_nq_ring(bp); 392 if (rc) 393 goto alloc_mem_err; 394 395 if (BNXT_FLOW_XSTATS_EN(bp)) { 396 rc = bnxt_alloc_flow_stats_info(bp); 397 if (rc) 398 goto alloc_mem_err; 399 } 400 401 return 0; 402 403 alloc_mem_err: 404 bnxt_free_mem(bp, reconfig); 405 return rc; 406 } 407 408 static int bnxt_setup_one_vnic(struct bnxt *bp, uint16_t vnic_id) 409 { 410 struct rte_eth_conf *dev_conf = &bp->eth_dev->data->dev_conf; 411 struct bnxt_vnic_info *vnic = &bp->vnic_info[vnic_id]; 412 uint64_t rx_offloads = dev_conf->rxmode.offloads; 413 struct bnxt_rx_queue *rxq; 414 unsigned int j; 415 int rc; 416 417 rc = bnxt_vnic_grp_alloc(bp, vnic); 418 if (rc) 419 goto err_out; 420 421 PMD_DRV_LOG(DEBUG, "vnic[%d] = %p vnic->fw_grp_ids = %p\n", 422 vnic_id, vnic, vnic->fw_grp_ids); 423 424 rc = bnxt_hwrm_vnic_alloc(bp, vnic); 425 if (rc) 426 goto err_out; 427 428 /* Alloc RSS context only if RSS mode is enabled */ 429 if (dev_conf->rxmode.mq_mode & ETH_MQ_RX_RSS) { 430 int j, nr_ctxs = bnxt_rss_ctxts(bp); 431 432 /* RSS table size in Thor is 512. 433 * Cap max Rx rings to same value 434 */ 435 if (bp->rx_nr_rings > BNXT_RSS_TBL_SIZE_P5) { 436 PMD_DRV_LOG(ERR, "RxQ cnt %d > reta_size %d\n", 437 bp->rx_nr_rings, BNXT_RSS_TBL_SIZE_P5); 438 goto err_out; 439 } 440 441 rc = 0; 442 for (j = 0; j < nr_ctxs; j++) { 443 rc = bnxt_hwrm_vnic_ctx_alloc(bp, vnic, j); 444 if (rc) 445 break; 446 } 447 if (rc) { 448 PMD_DRV_LOG(ERR, 449 "HWRM vnic %d ctx %d alloc failure rc: %x\n", 450 vnic_id, j, rc); 451 goto err_out; 452 } 453 vnic->num_lb_ctxts = nr_ctxs; 454 } 455 456 /* 457 * Firmware sets pf pair in default vnic cfg. If the VLAN strip 458 * setting is not available at this time, it will not be 459 * configured correctly in the CFA. 460 */ 461 if (rx_offloads & DEV_RX_OFFLOAD_VLAN_STRIP) 462 vnic->vlan_strip = true; 463 else 464 vnic->vlan_strip = false; 465 466 rc = bnxt_hwrm_vnic_cfg(bp, vnic); 467 if (rc) 468 goto err_out; 469 470 rc = bnxt_set_hwrm_vnic_filters(bp, vnic); 471 if (rc) 472 goto err_out; 473 474 for (j = 0; j < bp->rx_num_qs_per_vnic; j++) { 475 rxq = bp->eth_dev->data->rx_queues[j]; 476 477 PMD_DRV_LOG(DEBUG, 478 "rxq[%d]->vnic=%p vnic->fw_grp_ids=%p\n", 479 j, rxq->vnic, rxq->vnic->fw_grp_ids); 480 481 if (BNXT_HAS_RING_GRPS(bp) && rxq->rx_deferred_start) 482 rxq->vnic->fw_grp_ids[j] = INVALID_HW_RING_ID; 483 else 484 vnic->rx_queue_cnt++; 485 } 486 487 PMD_DRV_LOG(DEBUG, "vnic->rx_queue_cnt = %d\n", vnic->rx_queue_cnt); 488 489 rc = bnxt_vnic_rss_configure(bp, vnic); 490 if (rc) 491 goto err_out; 492 493 bnxt_hwrm_vnic_plcmode_cfg(bp, vnic); 494 495 rc = bnxt_hwrm_vnic_tpa_cfg(bp, vnic, 496 (rx_offloads & DEV_RX_OFFLOAD_TCP_LRO) ? 497 true : false); 498 if (rc) 499 goto err_out; 500 501 return 0; 502 err_out: 503 PMD_DRV_LOG(ERR, "HWRM vnic %d cfg failure rc: %x\n", 504 vnic_id, rc); 505 return rc; 506 } 507 508 static int bnxt_register_fc_ctx_mem(struct bnxt *bp) 509 { 510 int rc = 0; 511 512 rc = bnxt_hwrm_ctx_rgtr(bp, bp->flow_stat->rx_fc_in_tbl.dma, 513 &bp->flow_stat->rx_fc_in_tbl.ctx_id); 514 if (rc) 515 return rc; 516 517 PMD_DRV_LOG(DEBUG, 518 "rx_fc_in_tbl.va = %p rx_fc_in_tbl.dma = %p" 519 " rx_fc_in_tbl.ctx_id = %d\n", 520 bp->flow_stat->rx_fc_in_tbl.va, 521 (void *)((uintptr_t)bp->flow_stat->rx_fc_in_tbl.dma), 522 bp->flow_stat->rx_fc_in_tbl.ctx_id); 523 524 rc = bnxt_hwrm_ctx_rgtr(bp, bp->flow_stat->rx_fc_out_tbl.dma, 525 &bp->flow_stat->rx_fc_out_tbl.ctx_id); 526 if (rc) 527 return rc; 528 529 PMD_DRV_LOG(DEBUG, 530 "rx_fc_out_tbl.va = %p rx_fc_out_tbl.dma = %p" 531 " rx_fc_out_tbl.ctx_id = %d\n", 532 bp->flow_stat->rx_fc_out_tbl.va, 533 (void *)((uintptr_t)bp->flow_stat->rx_fc_out_tbl.dma), 534 bp->flow_stat->rx_fc_out_tbl.ctx_id); 535 536 rc = bnxt_hwrm_ctx_rgtr(bp, bp->flow_stat->tx_fc_in_tbl.dma, 537 &bp->flow_stat->tx_fc_in_tbl.ctx_id); 538 if (rc) 539 return rc; 540 541 PMD_DRV_LOG(DEBUG, 542 "tx_fc_in_tbl.va = %p tx_fc_in_tbl.dma = %p" 543 " tx_fc_in_tbl.ctx_id = %d\n", 544 bp->flow_stat->tx_fc_in_tbl.va, 545 (void *)((uintptr_t)bp->flow_stat->tx_fc_in_tbl.dma), 546 bp->flow_stat->tx_fc_in_tbl.ctx_id); 547 548 rc = bnxt_hwrm_ctx_rgtr(bp, bp->flow_stat->tx_fc_out_tbl.dma, 549 &bp->flow_stat->tx_fc_out_tbl.ctx_id); 550 if (rc) 551 return rc; 552 553 PMD_DRV_LOG(DEBUG, 554 "tx_fc_out_tbl.va = %p tx_fc_out_tbl.dma = %p" 555 " tx_fc_out_tbl.ctx_id = %d\n", 556 bp->flow_stat->tx_fc_out_tbl.va, 557 (void *)((uintptr_t)bp->flow_stat->tx_fc_out_tbl.dma), 558 bp->flow_stat->tx_fc_out_tbl.ctx_id); 559 560 memset(bp->flow_stat->rx_fc_out_tbl.va, 561 0, 562 bp->flow_stat->rx_fc_out_tbl.size); 563 rc = bnxt_hwrm_cfa_counter_cfg(bp, BNXT_DIR_RX, 564 CFA_COUNTER_CFG_IN_COUNTER_TYPE_FC, 565 bp->flow_stat->rx_fc_out_tbl.ctx_id, 566 bp->flow_stat->max_fc, 567 true); 568 if (rc) 569 return rc; 570 571 memset(bp->flow_stat->tx_fc_out_tbl.va, 572 0, 573 bp->flow_stat->tx_fc_out_tbl.size); 574 rc = bnxt_hwrm_cfa_counter_cfg(bp, BNXT_DIR_TX, 575 CFA_COUNTER_CFG_IN_COUNTER_TYPE_FC, 576 bp->flow_stat->tx_fc_out_tbl.ctx_id, 577 bp->flow_stat->max_fc, 578 true); 579 580 return rc; 581 } 582 583 static int bnxt_alloc_ctx_mem_buf(char *type, size_t size, 584 struct bnxt_ctx_mem_buf_info *ctx) 585 { 586 if (!ctx) 587 return -EINVAL; 588 589 ctx->va = rte_zmalloc(type, size, 0); 590 if (ctx->va == NULL) 591 return -ENOMEM; 592 rte_mem_lock_page(ctx->va); 593 ctx->size = size; 594 ctx->dma = rte_mem_virt2iova(ctx->va); 595 if (ctx->dma == RTE_BAD_IOVA) 596 return -ENOMEM; 597 598 return 0; 599 } 600 601 static int bnxt_init_fc_ctx_mem(struct bnxt *bp) 602 { 603 struct rte_pci_device *pdev = bp->pdev; 604 char type[RTE_MEMZONE_NAMESIZE]; 605 uint16_t max_fc; 606 int rc = 0; 607 608 max_fc = bp->flow_stat->max_fc; 609 610 sprintf(type, "bnxt_rx_fc_in_" PCI_PRI_FMT, pdev->addr.domain, 611 pdev->addr.bus, pdev->addr.devid, pdev->addr.function); 612 /* 4 bytes for each counter-id */ 613 rc = bnxt_alloc_ctx_mem_buf(type, 614 max_fc * 4, 615 &bp->flow_stat->rx_fc_in_tbl); 616 if (rc) 617 return rc; 618 619 sprintf(type, "bnxt_rx_fc_out_" PCI_PRI_FMT, pdev->addr.domain, 620 pdev->addr.bus, pdev->addr.devid, pdev->addr.function); 621 /* 16 bytes for each counter - 8 bytes pkt_count, 8 bytes byte_count */ 622 rc = bnxt_alloc_ctx_mem_buf(type, 623 max_fc * 16, 624 &bp->flow_stat->rx_fc_out_tbl); 625 if (rc) 626 return rc; 627 628 sprintf(type, "bnxt_tx_fc_in_" PCI_PRI_FMT, pdev->addr.domain, 629 pdev->addr.bus, pdev->addr.devid, pdev->addr.function); 630 /* 4 bytes for each counter-id */ 631 rc = bnxt_alloc_ctx_mem_buf(type, 632 max_fc * 4, 633 &bp->flow_stat->tx_fc_in_tbl); 634 if (rc) 635 return rc; 636 637 sprintf(type, "bnxt_tx_fc_out_" PCI_PRI_FMT, pdev->addr.domain, 638 pdev->addr.bus, pdev->addr.devid, pdev->addr.function); 639 /* 16 bytes for each counter - 8 bytes pkt_count, 8 bytes byte_count */ 640 rc = bnxt_alloc_ctx_mem_buf(type, 641 max_fc * 16, 642 &bp->flow_stat->tx_fc_out_tbl); 643 if (rc) 644 return rc; 645 646 rc = bnxt_register_fc_ctx_mem(bp); 647 648 return rc; 649 } 650 651 static int bnxt_init_ctx_mem(struct bnxt *bp) 652 { 653 int rc = 0; 654 655 if (!(bp->fw_cap & BNXT_FW_CAP_ADV_FLOW_COUNTERS) || 656 !(BNXT_PF(bp) || BNXT_VF_IS_TRUSTED(bp)) || 657 !BNXT_FLOW_XSTATS_EN(bp)) 658 return 0; 659 660 rc = bnxt_hwrm_cfa_counter_qcaps(bp, &bp->flow_stat->max_fc); 661 if (rc) 662 return rc; 663 664 rc = bnxt_init_fc_ctx_mem(bp); 665 666 return rc; 667 } 668 669 static int bnxt_update_phy_setting(struct bnxt *bp) 670 { 671 struct rte_eth_link new; 672 int rc; 673 674 rc = bnxt_get_hwrm_link_config(bp, &new); 675 if (rc) { 676 PMD_DRV_LOG(ERR, "Failed to get link settings\n"); 677 return rc; 678 } 679 680 /* 681 * On BCM957508-N2100 adapters, FW will not allow any user other 682 * than BMC to shutdown the port. bnxt_get_hwrm_link_config() call 683 * always returns link up. Force phy update always in that case. 684 */ 685 if (!new.link_status || IS_BNXT_DEV_957508_N2100(bp)) { 686 rc = bnxt_set_hwrm_link_config(bp, true); 687 if (rc) { 688 PMD_DRV_LOG(ERR, "Failed to update PHY settings\n"); 689 return rc; 690 } 691 } 692 693 return rc; 694 } 695 696 static void bnxt_free_prev_ring_stats(struct bnxt *bp) 697 { 698 rte_free(bp->prev_rx_ring_stats); 699 rte_free(bp->prev_tx_ring_stats); 700 701 bp->prev_rx_ring_stats = NULL; 702 bp->prev_tx_ring_stats = NULL; 703 } 704 705 static int bnxt_alloc_prev_ring_stats(struct bnxt *bp) 706 { 707 bp->prev_rx_ring_stats = rte_zmalloc("bnxt_prev_rx_ring_stats", 708 sizeof(struct bnxt_ring_stats) * 709 bp->rx_cp_nr_rings, 710 0); 711 if (bp->prev_rx_ring_stats == NULL) 712 return -ENOMEM; 713 714 bp->prev_tx_ring_stats = rte_zmalloc("bnxt_prev_tx_ring_stats", 715 sizeof(struct bnxt_ring_stats) * 716 bp->tx_cp_nr_rings, 717 0); 718 if (bp->prev_tx_ring_stats == NULL) 719 goto error; 720 721 return 0; 722 723 error: 724 bnxt_free_prev_ring_stats(bp); 725 return -ENOMEM; 726 } 727 728 static int bnxt_start_nic(struct bnxt *bp) 729 { 730 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(bp->eth_dev); 731 struct rte_intr_handle *intr_handle = &pci_dev->intr_handle; 732 uint32_t intr_vector = 0; 733 uint32_t queue_id, base = BNXT_MISC_VEC_ID; 734 uint32_t vec = BNXT_MISC_VEC_ID; 735 unsigned int i, j; 736 int rc; 737 738 if (bp->eth_dev->data->mtu > RTE_ETHER_MTU) { 739 bp->eth_dev->data->dev_conf.rxmode.offloads |= 740 DEV_RX_OFFLOAD_JUMBO_FRAME; 741 bp->flags |= BNXT_FLAG_JUMBO; 742 } else { 743 bp->eth_dev->data->dev_conf.rxmode.offloads &= 744 ~DEV_RX_OFFLOAD_JUMBO_FRAME; 745 bp->flags &= ~BNXT_FLAG_JUMBO; 746 } 747 748 /* THOR does not support ring groups. 749 * But we will use the array to save RSS context IDs. 750 */ 751 if (BNXT_CHIP_P5(bp)) 752 bp->max_ring_grps = BNXT_MAX_RSS_CTXTS_P5; 753 754 rc = bnxt_alloc_all_hwrm_stat_ctxs(bp); 755 if (rc) { 756 PMD_DRV_LOG(ERR, "HWRM stat ctx alloc failure rc: %x\n", rc); 757 goto err_out; 758 } 759 760 rc = bnxt_alloc_hwrm_rings(bp); 761 if (rc) { 762 PMD_DRV_LOG(ERR, "HWRM ring alloc failure rc: %x\n", rc); 763 goto err_out; 764 } 765 766 rc = bnxt_alloc_all_hwrm_ring_grps(bp); 767 if (rc) { 768 PMD_DRV_LOG(ERR, "HWRM ring grp alloc failure: %x\n", rc); 769 goto err_out; 770 } 771 772 if (!(bp->vnic_cap_flags & BNXT_VNIC_CAP_COS_CLASSIFY)) 773 goto skip_cosq_cfg; 774 775 for (j = 0, i = 0; i < BNXT_COS_QUEUE_COUNT; i++) { 776 if (bp->rx_cos_queue[i].id != 0xff) { 777 struct bnxt_vnic_info *vnic = &bp->vnic_info[j++]; 778 779 if (!vnic) { 780 PMD_DRV_LOG(ERR, 781 "Num pools more than FW profile\n"); 782 rc = -EINVAL; 783 goto err_out; 784 } 785 vnic->cos_queue_id = bp->rx_cos_queue[i].id; 786 bp->rx_cosq_cnt++; 787 } 788 } 789 790 skip_cosq_cfg: 791 rc = bnxt_mq_rx_configure(bp); 792 if (rc) { 793 PMD_DRV_LOG(ERR, "MQ mode configure failure rc: %x\n", rc); 794 goto err_out; 795 } 796 797 /* default vnic 0 */ 798 rc = bnxt_setup_one_vnic(bp, 0); 799 if (rc) 800 goto err_out; 801 /* VNIC configuration */ 802 if (BNXT_RFS_NEEDS_VNIC(bp)) { 803 for (i = 1; i < bp->nr_vnics; i++) { 804 rc = bnxt_setup_one_vnic(bp, i); 805 if (rc) 806 goto err_out; 807 } 808 } 809 810 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, &bp->vnic_info[0], 0, NULL); 811 if (rc) { 812 PMD_DRV_LOG(ERR, 813 "HWRM cfa l2 rx mask failure rc: %x\n", rc); 814 goto err_out; 815 } 816 817 /* check and configure queue intr-vector mapping */ 818 if ((rte_intr_cap_multiple(intr_handle) || 819 !RTE_ETH_DEV_SRIOV(bp->eth_dev).active) && 820 bp->eth_dev->data->dev_conf.intr_conf.rxq != 0) { 821 intr_vector = bp->eth_dev->data->nb_rx_queues; 822 PMD_DRV_LOG(DEBUG, "intr_vector = %d\n", intr_vector); 823 if (intr_vector > bp->rx_cp_nr_rings) { 824 PMD_DRV_LOG(ERR, "At most %d intr queues supported", 825 bp->rx_cp_nr_rings); 826 return -ENOTSUP; 827 } 828 rc = rte_intr_efd_enable(intr_handle, intr_vector); 829 if (rc) 830 return rc; 831 } 832 833 if (rte_intr_dp_is_en(intr_handle) && !intr_handle->intr_vec) { 834 intr_handle->intr_vec = 835 rte_zmalloc("intr_vec", 836 bp->eth_dev->data->nb_rx_queues * 837 sizeof(int), 0); 838 if (intr_handle->intr_vec == NULL) { 839 PMD_DRV_LOG(ERR, "Failed to allocate %d rx_queues" 840 " intr_vec", bp->eth_dev->data->nb_rx_queues); 841 rc = -ENOMEM; 842 goto err_out; 843 } 844 PMD_DRV_LOG(DEBUG, "intr_handle->intr_vec = %p " 845 "intr_handle->nb_efd = %d intr_handle->max_intr = %d\n", 846 intr_handle->intr_vec, intr_handle->nb_efd, 847 intr_handle->max_intr); 848 for (queue_id = 0; queue_id < bp->eth_dev->data->nb_rx_queues; 849 queue_id++) { 850 intr_handle->intr_vec[queue_id] = 851 vec + BNXT_RX_VEC_START; 852 if (vec < base + intr_handle->nb_efd - 1) 853 vec++; 854 } 855 } 856 857 /* enable uio/vfio intr/eventfd mapping */ 858 rc = rte_intr_enable(intr_handle); 859 #ifndef RTE_EXEC_ENV_FREEBSD 860 /* In FreeBSD OS, nic_uio driver does not support interrupts */ 861 if (rc) 862 goto err_out; 863 #endif 864 865 rc = bnxt_update_phy_setting(bp); 866 if (rc) 867 goto err_out; 868 869 bp->mark_table = rte_zmalloc("bnxt_mark_table", BNXT_MARK_TABLE_SZ, 0); 870 if (!bp->mark_table) 871 PMD_DRV_LOG(ERR, "Allocation of mark table failed\n"); 872 873 return 0; 874 875 err_out: 876 /* Some of the error status returned by FW may not be from errno.h */ 877 if (rc > 0) 878 rc = -EIO; 879 880 return rc; 881 } 882 883 static int bnxt_shutdown_nic(struct bnxt *bp) 884 { 885 bnxt_free_all_hwrm_resources(bp); 886 bnxt_free_all_filters(bp); 887 bnxt_free_all_vnics(bp); 888 return 0; 889 } 890 891 /* 892 * Device configuration and status function 893 */ 894 895 uint32_t bnxt_get_speed_capabilities(struct bnxt *bp) 896 { 897 uint32_t link_speed = 0; 898 uint32_t speed_capa = 0; 899 900 if (bp->link_info == NULL) 901 return 0; 902 903 link_speed = bp->link_info->support_speeds; 904 905 /* If PAM4 is configured, use PAM4 supported speed */ 906 if (link_speed == 0 && bp->link_info->support_pam4_speeds > 0) 907 link_speed = bp->link_info->support_pam4_speeds; 908 909 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_LINK_SPEED_100MB) 910 speed_capa |= ETH_LINK_SPEED_100M; 911 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_SPEEDS_100MBHD) 912 speed_capa |= ETH_LINK_SPEED_100M_HD; 913 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_SPEEDS_1GB) 914 speed_capa |= ETH_LINK_SPEED_1G; 915 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_SPEEDS_2_5GB) 916 speed_capa |= ETH_LINK_SPEED_2_5G; 917 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_SPEEDS_10GB) 918 speed_capa |= ETH_LINK_SPEED_10G; 919 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_SPEEDS_20GB) 920 speed_capa |= ETH_LINK_SPEED_20G; 921 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_SPEEDS_25GB) 922 speed_capa |= ETH_LINK_SPEED_25G; 923 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_SPEEDS_40GB) 924 speed_capa |= ETH_LINK_SPEED_40G; 925 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_SPEEDS_50GB) 926 speed_capa |= ETH_LINK_SPEED_50G; 927 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_SPEEDS_100GB) 928 speed_capa |= ETH_LINK_SPEED_100G; 929 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_PAM4_SPEEDS_50G) 930 speed_capa |= ETH_LINK_SPEED_50G; 931 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_PAM4_SPEEDS_100G) 932 speed_capa |= ETH_LINK_SPEED_100G; 933 if (link_speed & HWRM_PORT_PHY_QCFG_OUTPUT_SUPPORT_PAM4_SPEEDS_200G) 934 speed_capa |= ETH_LINK_SPEED_200G; 935 936 if (bp->link_info->auto_mode == 937 HWRM_PORT_PHY_QCFG_OUTPUT_AUTO_MODE_NONE) 938 speed_capa |= ETH_LINK_SPEED_FIXED; 939 940 return speed_capa; 941 } 942 943 static int bnxt_dev_info_get_op(struct rte_eth_dev *eth_dev, 944 struct rte_eth_dev_info *dev_info) 945 { 946 struct rte_pci_device *pdev = RTE_DEV_TO_PCI(eth_dev->device); 947 struct bnxt *bp = eth_dev->data->dev_private; 948 uint16_t max_vnics, i, j, vpool, vrxq; 949 unsigned int max_rx_rings; 950 int rc; 951 952 rc = is_bnxt_in_error(bp); 953 if (rc) 954 return rc; 955 956 /* MAC Specifics */ 957 dev_info->max_mac_addrs = bp->max_l2_ctx; 958 dev_info->max_hash_mac_addrs = 0; 959 960 /* PF/VF specifics */ 961 if (BNXT_PF(bp)) 962 dev_info->max_vfs = pdev->max_vfs; 963 964 max_rx_rings = bnxt_max_rings(bp); 965 /* For the sake of symmetry, max_rx_queues = max_tx_queues */ 966 dev_info->max_rx_queues = max_rx_rings; 967 dev_info->max_tx_queues = max_rx_rings; 968 dev_info->reta_size = bnxt_rss_hash_tbl_size(bp); 969 dev_info->hash_key_size = 40; 970 max_vnics = bp->max_vnics; 971 972 /* MTU specifics */ 973 dev_info->min_mtu = RTE_ETHER_MIN_MTU; 974 dev_info->max_mtu = BNXT_MAX_MTU; 975 976 /* Fast path specifics */ 977 dev_info->min_rx_bufsize = 1; 978 dev_info->max_rx_pktlen = BNXT_MAX_PKT_LEN; 979 980 dev_info->rx_offload_capa = BNXT_DEV_RX_OFFLOAD_SUPPORT; 981 if (bp->flags & BNXT_FLAG_PTP_SUPPORTED) 982 dev_info->rx_offload_capa |= DEV_RX_OFFLOAD_TIMESTAMP; 983 dev_info->tx_queue_offload_capa = DEV_TX_OFFLOAD_MBUF_FAST_FREE; 984 dev_info->tx_offload_capa = BNXT_DEV_TX_OFFLOAD_SUPPORT | 985 dev_info->tx_queue_offload_capa; 986 dev_info->flow_type_rss_offloads = BNXT_ETH_RSS_SUPPORT; 987 988 dev_info->speed_capa = bnxt_get_speed_capabilities(bp); 989 990 dev_info->default_rxconf = (struct rte_eth_rxconf) { 991 .rx_thresh = { 992 .pthresh = 8, 993 .hthresh = 8, 994 .wthresh = 0, 995 }, 996 .rx_free_thresh = 32, 997 .rx_drop_en = BNXT_DEFAULT_RX_DROP_EN, 998 }; 999 1000 dev_info->default_txconf = (struct rte_eth_txconf) { 1001 .tx_thresh = { 1002 .pthresh = 32, 1003 .hthresh = 0, 1004 .wthresh = 0, 1005 }, 1006 .tx_free_thresh = 32, 1007 .tx_rs_thresh = 32, 1008 }; 1009 eth_dev->data->dev_conf.intr_conf.lsc = 1; 1010 1011 eth_dev->data->dev_conf.intr_conf.rxq = 1; 1012 dev_info->rx_desc_lim.nb_min = BNXT_MIN_RING_DESC; 1013 dev_info->rx_desc_lim.nb_max = BNXT_MAX_RX_RING_DESC; 1014 dev_info->tx_desc_lim.nb_min = BNXT_MIN_RING_DESC; 1015 dev_info->tx_desc_lim.nb_max = BNXT_MAX_TX_RING_DESC; 1016 1017 if (BNXT_PF(bp) || BNXT_VF_IS_TRUSTED(bp)) { 1018 dev_info->switch_info.name = eth_dev->device->name; 1019 dev_info->switch_info.domain_id = bp->switch_domain_id; 1020 dev_info->switch_info.port_id = 1021 BNXT_PF(bp) ? BNXT_SWITCH_PORT_ID_PF : 1022 BNXT_SWITCH_PORT_ID_TRUSTED_VF; 1023 } 1024 1025 /* 1026 * TODO: default_rxconf, default_txconf, rx_desc_lim, and tx_desc_lim 1027 * need further investigation. 1028 */ 1029 1030 /* VMDq resources */ 1031 vpool = 64; /* ETH_64_POOLS */ 1032 vrxq = 128; /* ETH_VMDQ_DCB_NUM_QUEUES */ 1033 for (i = 0; i < 4; vpool >>= 1, i++) { 1034 if (max_vnics > vpool) { 1035 for (j = 0; j < 5; vrxq >>= 1, j++) { 1036 if (dev_info->max_rx_queues > vrxq) { 1037 if (vpool > vrxq) 1038 vpool = vrxq; 1039 goto found; 1040 } 1041 } 1042 /* Not enough resources to support VMDq */ 1043 break; 1044 } 1045 } 1046 /* Not enough resources to support VMDq */ 1047 vpool = 0; 1048 vrxq = 0; 1049 found: 1050 dev_info->max_vmdq_pools = vpool; 1051 dev_info->vmdq_queue_num = vrxq; 1052 1053 dev_info->vmdq_pool_base = 0; 1054 dev_info->vmdq_queue_base = 0; 1055 1056 return 0; 1057 } 1058 1059 /* Configure the device based on the configuration provided */ 1060 static int bnxt_dev_configure_op(struct rte_eth_dev *eth_dev) 1061 { 1062 struct bnxt *bp = eth_dev->data->dev_private; 1063 uint64_t rx_offloads = eth_dev->data->dev_conf.rxmode.offloads; 1064 int rc; 1065 1066 bp->rx_queues = (void *)eth_dev->data->rx_queues; 1067 bp->tx_queues = (void *)eth_dev->data->tx_queues; 1068 bp->tx_nr_rings = eth_dev->data->nb_tx_queues; 1069 bp->rx_nr_rings = eth_dev->data->nb_rx_queues; 1070 1071 rc = is_bnxt_in_error(bp); 1072 if (rc) 1073 return rc; 1074 1075 if (BNXT_VF(bp) && (bp->flags & BNXT_FLAG_NEW_RM)) { 1076 rc = bnxt_hwrm_check_vf_rings(bp); 1077 if (rc) { 1078 PMD_DRV_LOG(ERR, "HWRM insufficient resources\n"); 1079 return -ENOSPC; 1080 } 1081 1082 /* If a resource has already been allocated - in this case 1083 * it is the async completion ring, free it. Reallocate it after 1084 * resource reservation. This will ensure the resource counts 1085 * are calculated correctly. 1086 */ 1087 1088 pthread_mutex_lock(&bp->def_cp_lock); 1089 1090 if (!BNXT_HAS_NQ(bp) && bp->async_cp_ring) { 1091 bnxt_disable_int(bp); 1092 bnxt_free_cp_ring(bp, bp->async_cp_ring); 1093 } 1094 1095 rc = bnxt_hwrm_func_reserve_vf_resc(bp, false); 1096 if (rc) { 1097 PMD_DRV_LOG(ERR, "HWRM resource alloc fail:%x\n", rc); 1098 pthread_mutex_unlock(&bp->def_cp_lock); 1099 return -ENOSPC; 1100 } 1101 1102 if (!BNXT_HAS_NQ(bp) && bp->async_cp_ring) { 1103 rc = bnxt_alloc_async_cp_ring(bp); 1104 if (rc) { 1105 pthread_mutex_unlock(&bp->def_cp_lock); 1106 return rc; 1107 } 1108 bnxt_enable_int(bp); 1109 } 1110 1111 pthread_mutex_unlock(&bp->def_cp_lock); 1112 } 1113 1114 /* Inherit new configurations */ 1115 if (eth_dev->data->nb_rx_queues > bp->max_rx_rings || 1116 eth_dev->data->nb_tx_queues > bp->max_tx_rings || 1117 eth_dev->data->nb_rx_queues + eth_dev->data->nb_tx_queues 1118 + BNXT_NUM_ASYNC_CPR(bp) > bp->max_cp_rings || 1119 eth_dev->data->nb_rx_queues + eth_dev->data->nb_tx_queues > 1120 bp->max_stat_ctx) 1121 goto resource_error; 1122 1123 if (BNXT_HAS_RING_GRPS(bp) && 1124 (uint32_t)(eth_dev->data->nb_rx_queues) > bp->max_ring_grps) 1125 goto resource_error; 1126 1127 if (!(eth_dev->data->dev_conf.rxmode.mq_mode & ETH_MQ_RX_RSS) && 1128 bp->max_vnics < eth_dev->data->nb_rx_queues) 1129 goto resource_error; 1130 1131 bp->rx_cp_nr_rings = bp->rx_nr_rings; 1132 bp->tx_cp_nr_rings = bp->tx_nr_rings; 1133 1134 if (eth_dev->data->dev_conf.rxmode.mq_mode & ETH_MQ_RX_RSS_FLAG) 1135 rx_offloads |= DEV_RX_OFFLOAD_RSS_HASH; 1136 eth_dev->data->dev_conf.rxmode.offloads = rx_offloads; 1137 1138 if (rx_offloads & DEV_RX_OFFLOAD_JUMBO_FRAME) { 1139 eth_dev->data->mtu = 1140 eth_dev->data->dev_conf.rxmode.max_rx_pkt_len - 1141 RTE_ETHER_HDR_LEN - RTE_ETHER_CRC_LEN - VLAN_TAG_SIZE * 1142 BNXT_NUM_VLANS; 1143 bnxt_mtu_set_op(eth_dev, eth_dev->data->mtu); 1144 } 1145 return 0; 1146 1147 resource_error: 1148 PMD_DRV_LOG(ERR, 1149 "Insufficient resources to support requested config\n"); 1150 PMD_DRV_LOG(ERR, 1151 "Num Queues Requested: Tx %d, Rx %d\n", 1152 eth_dev->data->nb_tx_queues, 1153 eth_dev->data->nb_rx_queues); 1154 PMD_DRV_LOG(ERR, 1155 "MAX: TxQ %d, RxQ %d, CQ %d Stat %d, Grp %d, Vnic %d\n", 1156 bp->max_tx_rings, bp->max_rx_rings, bp->max_cp_rings, 1157 bp->max_stat_ctx, bp->max_ring_grps, bp->max_vnics); 1158 return -ENOSPC; 1159 } 1160 1161 void bnxt_print_link_info(struct rte_eth_dev *eth_dev) 1162 { 1163 struct rte_eth_link *link = ð_dev->data->dev_link; 1164 1165 if (link->link_status) 1166 PMD_DRV_LOG(INFO, "Port %d Link Up - speed %u Mbps - %s\n", 1167 eth_dev->data->port_id, 1168 (uint32_t)link->link_speed, 1169 (link->link_duplex == ETH_LINK_FULL_DUPLEX) ? 1170 ("full-duplex") : ("half-duplex\n")); 1171 else 1172 PMD_DRV_LOG(INFO, "Port %d Link Down\n", 1173 eth_dev->data->port_id); 1174 } 1175 1176 /* 1177 * Determine whether the current configuration requires support for scattered 1178 * receive; return 1 if scattered receive is required and 0 if not. 1179 */ 1180 static int bnxt_scattered_rx(struct rte_eth_dev *eth_dev) 1181 { 1182 uint16_t buf_size; 1183 int i; 1184 1185 if (eth_dev->data->dev_conf.rxmode.offloads & DEV_RX_OFFLOAD_SCATTER) 1186 return 1; 1187 1188 if (eth_dev->data->dev_conf.rxmode.offloads & DEV_RX_OFFLOAD_TCP_LRO) 1189 return 1; 1190 1191 for (i = 0; i < eth_dev->data->nb_rx_queues; i++) { 1192 struct bnxt_rx_queue *rxq = eth_dev->data->rx_queues[i]; 1193 1194 buf_size = (uint16_t)(rte_pktmbuf_data_room_size(rxq->mb_pool) - 1195 RTE_PKTMBUF_HEADROOM); 1196 if (eth_dev->data->dev_conf.rxmode.max_rx_pkt_len > buf_size) 1197 return 1; 1198 } 1199 return 0; 1200 } 1201 1202 static eth_rx_burst_t 1203 bnxt_receive_function(struct rte_eth_dev *eth_dev) 1204 { 1205 struct bnxt *bp = eth_dev->data->dev_private; 1206 1207 /* Disable vector mode RX for Stingray2 for now */ 1208 if (BNXT_CHIP_SR2(bp)) { 1209 bp->flags &= ~BNXT_FLAG_RX_VECTOR_PKT_MODE; 1210 return bnxt_recv_pkts; 1211 } 1212 1213 #if (defined(RTE_ARCH_X86) || defined(RTE_ARCH_ARM64)) && \ 1214 !defined(RTE_LIBRTE_IEEE1588) 1215 1216 /* Vector mode receive cannot be enabled if scattered rx is in use. */ 1217 if (eth_dev->data->scattered_rx) 1218 goto use_scalar_rx; 1219 1220 /* 1221 * Vector mode receive cannot be enabled if Truflow is enabled or if 1222 * asynchronous completions and receive completions can be placed in 1223 * the same completion ring. 1224 */ 1225 if (BNXT_TRUFLOW_EN(bp) || !BNXT_NUM_ASYNC_CPR(bp)) 1226 goto use_scalar_rx; 1227 1228 /* 1229 * Vector mode receive cannot be enabled if any receive offloads outside 1230 * a limited subset have been enabled. 1231 */ 1232 if (eth_dev->data->dev_conf.rxmode.offloads & 1233 ~(DEV_RX_OFFLOAD_VLAN_STRIP | 1234 DEV_RX_OFFLOAD_KEEP_CRC | 1235 DEV_RX_OFFLOAD_JUMBO_FRAME | 1236 DEV_RX_OFFLOAD_IPV4_CKSUM | 1237 DEV_RX_OFFLOAD_UDP_CKSUM | 1238 DEV_RX_OFFLOAD_TCP_CKSUM | 1239 DEV_RX_OFFLOAD_OUTER_IPV4_CKSUM | 1240 DEV_RX_OFFLOAD_OUTER_UDP_CKSUM | 1241 DEV_RX_OFFLOAD_RSS_HASH | 1242 DEV_RX_OFFLOAD_VLAN_FILTER)) 1243 goto use_scalar_rx; 1244 1245 #if defined(RTE_ARCH_X86) && defined(CC_AVX2_SUPPORT) 1246 if (rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_256 && 1247 rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX2) == 1) { 1248 PMD_DRV_LOG(INFO, 1249 "Using AVX2 vector mode receive for port %d\n", 1250 eth_dev->data->port_id); 1251 bp->flags |= BNXT_FLAG_RX_VECTOR_PKT_MODE; 1252 return bnxt_recv_pkts_vec_avx2; 1253 } 1254 #endif 1255 if (rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_128) { 1256 PMD_DRV_LOG(INFO, 1257 "Using SSE vector mode receive for port %d\n", 1258 eth_dev->data->port_id); 1259 bp->flags |= BNXT_FLAG_RX_VECTOR_PKT_MODE; 1260 return bnxt_recv_pkts_vec; 1261 } 1262 1263 use_scalar_rx: 1264 PMD_DRV_LOG(INFO, "Vector mode receive disabled for port %d\n", 1265 eth_dev->data->port_id); 1266 PMD_DRV_LOG(INFO, 1267 "Port %d scatter: %d rx offload: %" PRIX64 "\n", 1268 eth_dev->data->port_id, 1269 eth_dev->data->scattered_rx, 1270 eth_dev->data->dev_conf.rxmode.offloads); 1271 #endif 1272 bp->flags &= ~BNXT_FLAG_RX_VECTOR_PKT_MODE; 1273 return bnxt_recv_pkts; 1274 } 1275 1276 static eth_tx_burst_t 1277 bnxt_transmit_function(struct rte_eth_dev *eth_dev) 1278 { 1279 struct bnxt *bp = eth_dev->data->dev_private; 1280 1281 /* Disable vector mode TX for Stingray2 for now */ 1282 if (BNXT_CHIP_SR2(bp)) 1283 return bnxt_xmit_pkts; 1284 1285 #if defined(RTE_ARCH_X86) || defined(RTE_ARCH_ARM64) && \ 1286 !defined(RTE_LIBRTE_IEEE1588) 1287 uint64_t offloads = eth_dev->data->dev_conf.txmode.offloads; 1288 1289 /* 1290 * Vector mode transmit can be enabled only if not using scatter rx 1291 * or tx offloads. 1292 */ 1293 if (eth_dev->data->scattered_rx || 1294 (offloads & ~DEV_TX_OFFLOAD_MBUF_FAST_FREE) || 1295 BNXT_TRUFLOW_EN(bp)) 1296 goto use_scalar_tx; 1297 1298 #if defined(RTE_ARCH_X86) && defined(CC_AVX2_SUPPORT) 1299 if (rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_256 && 1300 rte_cpu_get_flag_enabled(RTE_CPUFLAG_AVX2) == 1) { 1301 PMD_DRV_LOG(INFO, 1302 "Using AVX2 vector mode transmit for port %d\n", 1303 eth_dev->data->port_id); 1304 return bnxt_xmit_pkts_vec_avx2; 1305 } 1306 #endif 1307 if (rte_vect_get_max_simd_bitwidth() >= RTE_VECT_SIMD_128) { 1308 PMD_DRV_LOG(INFO, 1309 "Using SSE vector mode transmit for port %d\n", 1310 eth_dev->data->port_id); 1311 return bnxt_xmit_pkts_vec; 1312 } 1313 1314 use_scalar_tx: 1315 PMD_DRV_LOG(INFO, "Vector mode transmit disabled for port %d\n", 1316 eth_dev->data->port_id); 1317 PMD_DRV_LOG(INFO, 1318 "Port %d scatter: %d tx offload: %" PRIX64 "\n", 1319 eth_dev->data->port_id, 1320 eth_dev->data->scattered_rx, 1321 offloads); 1322 #endif 1323 return bnxt_xmit_pkts; 1324 } 1325 1326 static int bnxt_handle_if_change_status(struct bnxt *bp) 1327 { 1328 int rc; 1329 1330 /* Since fw has undergone a reset and lost all contexts, 1331 * set fatal flag to not issue hwrm during cleanup 1332 */ 1333 bp->flags |= BNXT_FLAG_FATAL_ERROR; 1334 bnxt_uninit_resources(bp, true); 1335 1336 /* clear fatal flag so that re-init happens */ 1337 bp->flags &= ~BNXT_FLAG_FATAL_ERROR; 1338 rc = bnxt_init_resources(bp, true); 1339 1340 bp->flags &= ~BNXT_FLAG_IF_CHANGE_HOT_FW_RESET_DONE; 1341 1342 return rc; 1343 } 1344 1345 static int bnxt_dev_set_link_up_op(struct rte_eth_dev *eth_dev) 1346 { 1347 struct bnxt *bp = eth_dev->data->dev_private; 1348 int rc = 0; 1349 1350 if (!BNXT_SINGLE_PF(bp)) 1351 return -ENOTSUP; 1352 1353 if (!bp->link_info->link_up) 1354 rc = bnxt_set_hwrm_link_config(bp, true); 1355 if (!rc) 1356 eth_dev->data->dev_link.link_status = 1; 1357 1358 bnxt_print_link_info(eth_dev); 1359 return rc; 1360 } 1361 1362 static int bnxt_dev_set_link_down_op(struct rte_eth_dev *eth_dev) 1363 { 1364 struct bnxt *bp = eth_dev->data->dev_private; 1365 1366 if (!BNXT_SINGLE_PF(bp)) 1367 return -ENOTSUP; 1368 1369 eth_dev->data->dev_link.link_status = 0; 1370 bnxt_set_hwrm_link_config(bp, false); 1371 bp->link_info->link_up = 0; 1372 1373 return 0; 1374 } 1375 1376 static void bnxt_free_switch_domain(struct bnxt *bp) 1377 { 1378 int rc = 0; 1379 1380 if (!(BNXT_PF(bp) || BNXT_VF_IS_TRUSTED(bp))) 1381 return; 1382 1383 rc = rte_eth_switch_domain_free(bp->switch_domain_id); 1384 if (rc) 1385 PMD_DRV_LOG(ERR, "free switch domain:%d fail: %d\n", 1386 bp->switch_domain_id, rc); 1387 } 1388 1389 static void bnxt_ptp_get_current_time(void *arg) 1390 { 1391 struct bnxt *bp = arg; 1392 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 1393 int rc; 1394 1395 rc = is_bnxt_in_error(bp); 1396 if (rc) 1397 return; 1398 1399 if (!ptp) 1400 return; 1401 1402 bnxt_hwrm_port_ts_query(bp, BNXT_PTP_FLAGS_CURRENT_TIME, 1403 &ptp->current_time); 1404 1405 rc = rte_eal_alarm_set(US_PER_S, bnxt_ptp_get_current_time, (void *)bp); 1406 if (rc != 0) { 1407 PMD_DRV_LOG(ERR, "Failed to re-schedule PTP alarm\n"); 1408 bp->flags2 &= ~BNXT_FLAGS2_PTP_ALARM_SCHEDULED; 1409 } 1410 } 1411 1412 static int bnxt_schedule_ptp_alarm(struct bnxt *bp) 1413 { 1414 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 1415 int rc; 1416 1417 if (bp->flags2 & BNXT_FLAGS2_PTP_ALARM_SCHEDULED) 1418 return 0; 1419 1420 bnxt_hwrm_port_ts_query(bp, BNXT_PTP_FLAGS_CURRENT_TIME, 1421 &ptp->current_time); 1422 1423 rc = rte_eal_alarm_set(US_PER_S, bnxt_ptp_get_current_time, (void *)bp); 1424 return rc; 1425 } 1426 1427 static void bnxt_cancel_ptp_alarm(struct bnxt *bp) 1428 { 1429 if (bp->flags2 & BNXT_FLAGS2_PTP_ALARM_SCHEDULED) { 1430 rte_eal_alarm_cancel(bnxt_ptp_get_current_time, (void *)bp); 1431 bp->flags2 &= ~BNXT_FLAGS2_PTP_ALARM_SCHEDULED; 1432 } 1433 } 1434 1435 static void bnxt_ptp_stop(struct bnxt *bp) 1436 { 1437 bnxt_cancel_ptp_alarm(bp); 1438 bp->flags2 &= ~BNXT_FLAGS2_PTP_TIMESYNC_ENABLED; 1439 } 1440 1441 static int bnxt_ptp_start(struct bnxt *bp) 1442 { 1443 int rc; 1444 1445 rc = bnxt_schedule_ptp_alarm(bp); 1446 if (rc != 0) { 1447 PMD_DRV_LOG(ERR, "Failed to schedule PTP alarm\n"); 1448 } else { 1449 bp->flags2 |= BNXT_FLAGS2_PTP_TIMESYNC_ENABLED; 1450 bp->flags2 |= BNXT_FLAGS2_PTP_ALARM_SCHEDULED; 1451 } 1452 1453 return rc; 1454 } 1455 1456 static int bnxt_dev_stop(struct rte_eth_dev *eth_dev) 1457 { 1458 struct bnxt *bp = eth_dev->data->dev_private; 1459 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(eth_dev); 1460 struct rte_intr_handle *intr_handle = &pci_dev->intr_handle; 1461 struct rte_eth_link link; 1462 int ret; 1463 1464 eth_dev->data->dev_started = 0; 1465 eth_dev->data->scattered_rx = 0; 1466 1467 /* Prevent crashes when queues are still in use */ 1468 eth_dev->rx_pkt_burst = &bnxt_dummy_recv_pkts; 1469 eth_dev->tx_pkt_burst = &bnxt_dummy_xmit_pkts; 1470 1471 bnxt_disable_int(bp); 1472 1473 /* disable uio/vfio intr/eventfd mapping */ 1474 rte_intr_disable(intr_handle); 1475 1476 /* Stop the child representors for this device */ 1477 ret = bnxt_rep_stop_all(bp); 1478 if (ret != 0) 1479 return ret; 1480 1481 /* delete the bnxt ULP port details */ 1482 bnxt_ulp_port_deinit(bp); 1483 1484 bnxt_cancel_fw_health_check(bp); 1485 1486 if (BNXT_P5_PTP_TIMESYNC_ENABLED(bp)) 1487 bnxt_cancel_ptp_alarm(bp); 1488 1489 /* Do not bring link down during reset recovery */ 1490 if (!is_bnxt_in_error(bp)) { 1491 bnxt_dev_set_link_down_op(eth_dev); 1492 /* Wait for link to be reset */ 1493 if (BNXT_SINGLE_PF(bp)) 1494 rte_delay_ms(500); 1495 /* clear the recorded link status */ 1496 memset(&link, 0, sizeof(link)); 1497 rte_eth_linkstatus_set(eth_dev, &link); 1498 } 1499 1500 /* Clean queue intr-vector mapping */ 1501 rte_intr_efd_disable(intr_handle); 1502 if (intr_handle->intr_vec != NULL) { 1503 rte_free(intr_handle->intr_vec); 1504 intr_handle->intr_vec = NULL; 1505 } 1506 1507 bnxt_hwrm_port_clr_stats(bp); 1508 bnxt_free_tx_mbufs(bp); 1509 bnxt_free_rx_mbufs(bp); 1510 /* Process any remaining notifications in default completion queue */ 1511 bnxt_int_handler(eth_dev); 1512 bnxt_shutdown_nic(bp); 1513 bnxt_hwrm_if_change(bp, false); 1514 1515 bnxt_free_prev_ring_stats(bp); 1516 rte_free(bp->mark_table); 1517 bp->mark_table = NULL; 1518 1519 bp->flags &= ~BNXT_FLAG_RX_VECTOR_PKT_MODE; 1520 bp->rx_cosq_cnt = 0; 1521 /* All filters are deleted on a port stop. */ 1522 if (BNXT_FLOW_XSTATS_EN(bp)) 1523 bp->flow_stat->flow_count = 0; 1524 1525 return 0; 1526 } 1527 1528 /* Unload the driver, release resources */ 1529 static int bnxt_dev_stop_op(struct rte_eth_dev *eth_dev) 1530 { 1531 struct bnxt *bp = eth_dev->data->dev_private; 1532 1533 pthread_mutex_lock(&bp->err_recovery_lock); 1534 if (bp->flags & BNXT_FLAG_FW_RESET) { 1535 PMD_DRV_LOG(ERR, 1536 "Adapter recovering from error..Please retry\n"); 1537 pthread_mutex_unlock(&bp->err_recovery_lock); 1538 return -EAGAIN; 1539 } 1540 pthread_mutex_unlock(&bp->err_recovery_lock); 1541 1542 return bnxt_dev_stop(eth_dev); 1543 } 1544 1545 static int bnxt_dev_start_op(struct rte_eth_dev *eth_dev) 1546 { 1547 struct bnxt *bp = eth_dev->data->dev_private; 1548 uint64_t rx_offloads = eth_dev->data->dev_conf.rxmode.offloads; 1549 int vlan_mask = 0; 1550 int rc, retry_cnt = BNXT_IF_CHANGE_RETRY_COUNT; 1551 1552 if (!eth_dev->data->nb_tx_queues || !eth_dev->data->nb_rx_queues) { 1553 PMD_DRV_LOG(ERR, "Queues are not configured yet!\n"); 1554 return -EINVAL; 1555 } 1556 1557 if (bp->rx_cp_nr_rings > RTE_ETHDEV_QUEUE_STAT_CNTRS) 1558 PMD_DRV_LOG(ERR, 1559 "RxQ cnt %d > RTE_ETHDEV_QUEUE_STAT_CNTRS %d\n", 1560 bp->rx_cp_nr_rings, RTE_ETHDEV_QUEUE_STAT_CNTRS); 1561 1562 do { 1563 rc = bnxt_hwrm_if_change(bp, true); 1564 if (rc == 0 || rc != -EAGAIN) 1565 break; 1566 1567 rte_delay_ms(BNXT_IF_CHANGE_RETRY_INTERVAL); 1568 } while (retry_cnt--); 1569 1570 if (rc) 1571 return rc; 1572 1573 if (bp->flags & BNXT_FLAG_IF_CHANGE_HOT_FW_RESET_DONE) { 1574 rc = bnxt_handle_if_change_status(bp); 1575 if (rc) 1576 return rc; 1577 } 1578 1579 bnxt_enable_int(bp); 1580 1581 eth_dev->data->scattered_rx = bnxt_scattered_rx(eth_dev); 1582 1583 rc = bnxt_start_nic(bp); 1584 if (rc) 1585 goto error; 1586 1587 rc = bnxt_alloc_prev_ring_stats(bp); 1588 if (rc) 1589 goto error; 1590 1591 eth_dev->data->dev_started = 1; 1592 1593 bnxt_link_update_op(eth_dev, 1); 1594 1595 if (rx_offloads & DEV_RX_OFFLOAD_VLAN_FILTER) 1596 vlan_mask |= ETH_VLAN_FILTER_MASK; 1597 if (rx_offloads & DEV_RX_OFFLOAD_VLAN_STRIP) 1598 vlan_mask |= ETH_VLAN_STRIP_MASK; 1599 rc = bnxt_vlan_offload_set_op(eth_dev, vlan_mask); 1600 if (rc) 1601 goto error; 1602 1603 /* Initialize bnxt ULP port details */ 1604 rc = bnxt_ulp_port_init(bp); 1605 if (rc) 1606 goto error; 1607 1608 eth_dev->rx_pkt_burst = bnxt_receive_function(eth_dev); 1609 eth_dev->tx_pkt_burst = bnxt_transmit_function(eth_dev); 1610 1611 bnxt_schedule_fw_health_check(bp); 1612 1613 if (BNXT_P5_PTP_TIMESYNC_ENABLED(bp)) 1614 bnxt_schedule_ptp_alarm(bp); 1615 1616 return 0; 1617 1618 error: 1619 bnxt_dev_stop(eth_dev); 1620 return rc; 1621 } 1622 1623 static void 1624 bnxt_uninit_locks(struct bnxt *bp) 1625 { 1626 pthread_mutex_destroy(&bp->flow_lock); 1627 pthread_mutex_destroy(&bp->def_cp_lock); 1628 pthread_mutex_destroy(&bp->health_check_lock); 1629 pthread_mutex_destroy(&bp->err_recovery_lock); 1630 if (bp->rep_info) { 1631 pthread_mutex_destroy(&bp->rep_info->vfr_lock); 1632 pthread_mutex_destroy(&bp->rep_info->vfr_start_lock); 1633 } 1634 } 1635 1636 static void bnxt_drv_uninit(struct bnxt *bp) 1637 { 1638 bnxt_free_leds_info(bp); 1639 bnxt_free_cos_queues(bp); 1640 bnxt_free_link_info(bp); 1641 bnxt_free_parent_info(bp); 1642 bnxt_uninit_locks(bp); 1643 1644 rte_memzone_free((const struct rte_memzone *)bp->tx_mem_zone); 1645 bp->tx_mem_zone = NULL; 1646 rte_memzone_free((const struct rte_memzone *)bp->rx_mem_zone); 1647 bp->rx_mem_zone = NULL; 1648 1649 bnxt_free_vf_info(bp); 1650 bnxt_free_pf_info(bp); 1651 1652 rte_free(bp->grp_info); 1653 bp->grp_info = NULL; 1654 } 1655 1656 static int bnxt_dev_close_op(struct rte_eth_dev *eth_dev) 1657 { 1658 struct bnxt *bp = eth_dev->data->dev_private; 1659 int ret = 0; 1660 1661 if (rte_eal_process_type() != RTE_PROC_PRIMARY) 1662 return 0; 1663 1664 pthread_mutex_lock(&bp->err_recovery_lock); 1665 if (bp->flags & BNXT_FLAG_FW_RESET) { 1666 PMD_DRV_LOG(ERR, 1667 "Adapter recovering from error...Please retry\n"); 1668 pthread_mutex_unlock(&bp->err_recovery_lock); 1669 return -EAGAIN; 1670 } 1671 pthread_mutex_unlock(&bp->err_recovery_lock); 1672 1673 /* cancel the recovery handler before remove dev */ 1674 rte_eal_alarm_cancel(bnxt_dev_reset_and_resume, (void *)bp); 1675 rte_eal_alarm_cancel(bnxt_dev_recover, (void *)bp); 1676 bnxt_cancel_fc_thread(bp); 1677 1678 if (eth_dev->data->dev_started) 1679 ret = bnxt_dev_stop(eth_dev); 1680 1681 bnxt_uninit_resources(bp, false); 1682 1683 bnxt_drv_uninit(bp); 1684 1685 return ret; 1686 } 1687 1688 static void bnxt_mac_addr_remove_op(struct rte_eth_dev *eth_dev, 1689 uint32_t index) 1690 { 1691 struct bnxt *bp = eth_dev->data->dev_private; 1692 uint64_t pool_mask = eth_dev->data->mac_pool_sel[index]; 1693 struct bnxt_vnic_info *vnic; 1694 struct bnxt_filter_info *filter, *temp_filter; 1695 uint32_t i; 1696 1697 if (is_bnxt_in_error(bp)) 1698 return; 1699 1700 /* 1701 * Loop through all VNICs from the specified filter flow pools to 1702 * remove the corresponding MAC addr filter 1703 */ 1704 for (i = 0; i < bp->nr_vnics; i++) { 1705 if (!(pool_mask & (1ULL << i))) 1706 continue; 1707 1708 vnic = &bp->vnic_info[i]; 1709 filter = STAILQ_FIRST(&vnic->filter); 1710 while (filter) { 1711 temp_filter = STAILQ_NEXT(filter, next); 1712 if (filter->mac_index == index) { 1713 STAILQ_REMOVE(&vnic->filter, filter, 1714 bnxt_filter_info, next); 1715 bnxt_hwrm_clear_l2_filter(bp, filter); 1716 bnxt_free_filter(bp, filter); 1717 } 1718 filter = temp_filter; 1719 } 1720 } 1721 } 1722 1723 static int bnxt_add_mac_filter(struct bnxt *bp, struct bnxt_vnic_info *vnic, 1724 struct rte_ether_addr *mac_addr, uint32_t index, 1725 uint32_t pool) 1726 { 1727 struct bnxt_filter_info *filter; 1728 int rc = 0; 1729 1730 /* Attach requested MAC address to the new l2_filter */ 1731 STAILQ_FOREACH(filter, &vnic->filter, next) { 1732 if (filter->mac_index == index) { 1733 PMD_DRV_LOG(DEBUG, 1734 "MAC addr already existed for pool %d\n", 1735 pool); 1736 return 0; 1737 } 1738 } 1739 1740 filter = bnxt_alloc_filter(bp); 1741 if (!filter) { 1742 PMD_DRV_LOG(ERR, "L2 filter alloc failed\n"); 1743 return -ENODEV; 1744 } 1745 1746 /* bnxt_alloc_filter copies default MAC to filter->l2_addr. So, 1747 * if the MAC that's been programmed now is a different one, then, 1748 * copy that addr to filter->l2_addr 1749 */ 1750 if (mac_addr) 1751 memcpy(filter->l2_addr, mac_addr, RTE_ETHER_ADDR_LEN); 1752 filter->flags |= HWRM_CFA_L2_FILTER_ALLOC_INPUT_FLAGS_OUTERMOST; 1753 1754 rc = bnxt_hwrm_set_l2_filter(bp, vnic->fw_vnic_id, filter); 1755 if (!rc) { 1756 filter->mac_index = index; 1757 if (filter->mac_index == 0) 1758 STAILQ_INSERT_HEAD(&vnic->filter, filter, next); 1759 else 1760 STAILQ_INSERT_TAIL(&vnic->filter, filter, next); 1761 } else { 1762 bnxt_free_filter(bp, filter); 1763 } 1764 1765 return rc; 1766 } 1767 1768 static int bnxt_mac_addr_add_op(struct rte_eth_dev *eth_dev, 1769 struct rte_ether_addr *mac_addr, 1770 uint32_t index, uint32_t pool) 1771 { 1772 struct bnxt *bp = eth_dev->data->dev_private; 1773 struct bnxt_vnic_info *vnic = &bp->vnic_info[pool]; 1774 int rc = 0; 1775 1776 rc = is_bnxt_in_error(bp); 1777 if (rc) 1778 return rc; 1779 1780 if (BNXT_VF(bp) && !BNXT_VF_IS_TRUSTED(bp)) { 1781 PMD_DRV_LOG(ERR, "Cannot add MAC address to a VF interface\n"); 1782 return -ENOTSUP; 1783 } 1784 1785 if (!vnic) { 1786 PMD_DRV_LOG(ERR, "VNIC not found for pool %d!\n", pool); 1787 return -EINVAL; 1788 } 1789 1790 /* Filter settings will get applied when port is started */ 1791 if (!eth_dev->data->dev_started) 1792 return 0; 1793 1794 rc = bnxt_add_mac_filter(bp, vnic, mac_addr, index, pool); 1795 1796 return rc; 1797 } 1798 1799 int bnxt_link_update_op(struct rte_eth_dev *eth_dev, int wait_to_complete) 1800 { 1801 int rc = 0; 1802 struct bnxt *bp = eth_dev->data->dev_private; 1803 struct rte_eth_link new; 1804 int cnt = wait_to_complete ? BNXT_MAX_LINK_WAIT_CNT : 1805 BNXT_MIN_LINK_WAIT_CNT; 1806 1807 rc = is_bnxt_in_error(bp); 1808 if (rc) 1809 return rc; 1810 1811 memset(&new, 0, sizeof(new)); 1812 1813 if (bp->link_info == NULL) 1814 goto out; 1815 1816 do { 1817 /* Retrieve link info from hardware */ 1818 rc = bnxt_get_hwrm_link_config(bp, &new); 1819 if (rc) { 1820 new.link_speed = ETH_LINK_SPEED_100M; 1821 new.link_duplex = ETH_LINK_FULL_DUPLEX; 1822 PMD_DRV_LOG(ERR, 1823 "Failed to retrieve link rc = 0x%x!\n", rc); 1824 goto out; 1825 } 1826 1827 if (!wait_to_complete || new.link_status) 1828 break; 1829 1830 rte_delay_ms(BNXT_LINK_WAIT_INTERVAL); 1831 } while (cnt--); 1832 1833 /* Only single function PF can bring phy down. 1834 * When port is stopped, report link down for VF/MH/NPAR functions. 1835 */ 1836 if (!BNXT_SINGLE_PF(bp) && !eth_dev->data->dev_started) 1837 memset(&new, 0, sizeof(new)); 1838 1839 out: 1840 /* Timed out or success */ 1841 if (new.link_status != eth_dev->data->dev_link.link_status || 1842 new.link_speed != eth_dev->data->dev_link.link_speed) { 1843 rte_eth_linkstatus_set(eth_dev, &new); 1844 1845 rte_eth_dev_callback_process(eth_dev, 1846 RTE_ETH_EVENT_INTR_LSC, 1847 NULL); 1848 1849 bnxt_print_link_info(eth_dev); 1850 } 1851 1852 return rc; 1853 } 1854 1855 static int bnxt_promiscuous_enable_op(struct rte_eth_dev *eth_dev) 1856 { 1857 struct bnxt *bp = eth_dev->data->dev_private; 1858 struct bnxt_vnic_info *vnic; 1859 uint32_t old_flags; 1860 int rc; 1861 1862 rc = is_bnxt_in_error(bp); 1863 if (rc) 1864 return rc; 1865 1866 /* Filter settings will get applied when port is started */ 1867 if (!eth_dev->data->dev_started) 1868 return 0; 1869 1870 if (bp->vnic_info == NULL) 1871 return 0; 1872 1873 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1874 1875 old_flags = vnic->flags; 1876 vnic->flags |= BNXT_VNIC_INFO_PROMISC; 1877 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 1878 if (rc != 0) 1879 vnic->flags = old_flags; 1880 1881 return rc; 1882 } 1883 1884 static int bnxt_promiscuous_disable_op(struct rte_eth_dev *eth_dev) 1885 { 1886 struct bnxt *bp = eth_dev->data->dev_private; 1887 struct bnxt_vnic_info *vnic; 1888 uint32_t old_flags; 1889 int rc; 1890 1891 rc = is_bnxt_in_error(bp); 1892 if (rc) 1893 return rc; 1894 1895 /* Filter settings will get applied when port is started */ 1896 if (!eth_dev->data->dev_started) 1897 return 0; 1898 1899 if (bp->vnic_info == NULL) 1900 return 0; 1901 1902 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1903 1904 old_flags = vnic->flags; 1905 vnic->flags &= ~BNXT_VNIC_INFO_PROMISC; 1906 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 1907 if (rc != 0) 1908 vnic->flags = old_flags; 1909 1910 return rc; 1911 } 1912 1913 static int bnxt_allmulticast_enable_op(struct rte_eth_dev *eth_dev) 1914 { 1915 struct bnxt *bp = eth_dev->data->dev_private; 1916 struct bnxt_vnic_info *vnic; 1917 uint32_t old_flags; 1918 int rc; 1919 1920 rc = is_bnxt_in_error(bp); 1921 if (rc) 1922 return rc; 1923 1924 /* Filter settings will get applied when port is started */ 1925 if (!eth_dev->data->dev_started) 1926 return 0; 1927 1928 if (bp->vnic_info == NULL) 1929 return 0; 1930 1931 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1932 1933 old_flags = vnic->flags; 1934 vnic->flags |= BNXT_VNIC_INFO_ALLMULTI; 1935 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 1936 if (rc != 0) 1937 vnic->flags = old_flags; 1938 1939 return rc; 1940 } 1941 1942 static int bnxt_allmulticast_disable_op(struct rte_eth_dev *eth_dev) 1943 { 1944 struct bnxt *bp = eth_dev->data->dev_private; 1945 struct bnxt_vnic_info *vnic; 1946 uint32_t old_flags; 1947 int rc; 1948 1949 rc = is_bnxt_in_error(bp); 1950 if (rc) 1951 return rc; 1952 1953 /* Filter settings will get applied when port is started */ 1954 if (!eth_dev->data->dev_started) 1955 return 0; 1956 1957 if (bp->vnic_info == NULL) 1958 return 0; 1959 1960 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1961 1962 old_flags = vnic->flags; 1963 vnic->flags &= ~BNXT_VNIC_INFO_ALLMULTI; 1964 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 1965 if (rc != 0) 1966 vnic->flags = old_flags; 1967 1968 return rc; 1969 } 1970 1971 /* Return bnxt_rx_queue pointer corresponding to a given rxq. */ 1972 static struct bnxt_rx_queue *bnxt_qid_to_rxq(struct bnxt *bp, uint16_t qid) 1973 { 1974 if (qid >= bp->rx_nr_rings) 1975 return NULL; 1976 1977 return bp->eth_dev->data->rx_queues[qid]; 1978 } 1979 1980 /* Return rxq corresponding to a given rss table ring/group ID. */ 1981 static uint16_t bnxt_rss_to_qid(struct bnxt *bp, uint16_t fwr) 1982 { 1983 struct bnxt_rx_queue *rxq; 1984 unsigned int i; 1985 1986 if (!BNXT_HAS_RING_GRPS(bp)) { 1987 for (i = 0; i < bp->rx_nr_rings; i++) { 1988 rxq = bp->eth_dev->data->rx_queues[i]; 1989 if (rxq->rx_ring->rx_ring_struct->fw_ring_id == fwr) 1990 return rxq->index; 1991 } 1992 } else { 1993 for (i = 0; i < bp->rx_nr_rings; i++) { 1994 if (bp->grp_info[i].fw_grp_id == fwr) 1995 return i; 1996 } 1997 } 1998 1999 return INVALID_HW_RING_ID; 2000 } 2001 2002 static int bnxt_reta_update_op(struct rte_eth_dev *eth_dev, 2003 struct rte_eth_rss_reta_entry64 *reta_conf, 2004 uint16_t reta_size) 2005 { 2006 struct bnxt *bp = eth_dev->data->dev_private; 2007 struct rte_eth_conf *dev_conf = &bp->eth_dev->data->dev_conf; 2008 struct bnxt_vnic_info *vnic = BNXT_GET_DEFAULT_VNIC(bp); 2009 uint16_t tbl_size = bnxt_rss_hash_tbl_size(bp); 2010 uint16_t idx, sft; 2011 int i, rc; 2012 2013 rc = is_bnxt_in_error(bp); 2014 if (rc) 2015 return rc; 2016 2017 if (!vnic->rss_table) 2018 return -EINVAL; 2019 2020 if (!(dev_conf->rxmode.mq_mode & ETH_MQ_RX_RSS_FLAG)) 2021 return -EINVAL; 2022 2023 if (reta_size != tbl_size) { 2024 PMD_DRV_LOG(ERR, "The configured hash table lookup size " 2025 "(%d) must equal the size supported by the hardware " 2026 "(%d)\n", reta_size, tbl_size); 2027 return -EINVAL; 2028 } 2029 2030 for (i = 0; i < reta_size; i++) { 2031 struct bnxt_rx_queue *rxq; 2032 2033 idx = i / RTE_RETA_GROUP_SIZE; 2034 sft = i % RTE_RETA_GROUP_SIZE; 2035 2036 if (!(reta_conf[idx].mask & (1ULL << sft))) 2037 continue; 2038 2039 rxq = bnxt_qid_to_rxq(bp, reta_conf[idx].reta[sft]); 2040 if (!rxq) { 2041 PMD_DRV_LOG(ERR, "Invalid ring in reta_conf.\n"); 2042 return -EINVAL; 2043 } 2044 2045 if (BNXT_CHIP_P5(bp)) { 2046 vnic->rss_table[i * 2] = 2047 rxq->rx_ring->rx_ring_struct->fw_ring_id; 2048 vnic->rss_table[i * 2 + 1] = 2049 rxq->cp_ring->cp_ring_struct->fw_ring_id; 2050 } else { 2051 vnic->rss_table[i] = 2052 vnic->fw_grp_ids[reta_conf[idx].reta[sft]]; 2053 } 2054 } 2055 2056 rc = bnxt_hwrm_vnic_rss_cfg(bp, vnic); 2057 return rc; 2058 } 2059 2060 static int bnxt_reta_query_op(struct rte_eth_dev *eth_dev, 2061 struct rte_eth_rss_reta_entry64 *reta_conf, 2062 uint16_t reta_size) 2063 { 2064 struct bnxt *bp = eth_dev->data->dev_private; 2065 struct bnxt_vnic_info *vnic = BNXT_GET_DEFAULT_VNIC(bp); 2066 uint16_t tbl_size = bnxt_rss_hash_tbl_size(bp); 2067 uint16_t idx, sft, i; 2068 int rc; 2069 2070 rc = is_bnxt_in_error(bp); 2071 if (rc) 2072 return rc; 2073 2074 /* Retrieve from the default VNIC */ 2075 if (!vnic) 2076 return -EINVAL; 2077 if (!vnic->rss_table) 2078 return -EINVAL; 2079 2080 if (reta_size != tbl_size) { 2081 PMD_DRV_LOG(ERR, "The configured hash table lookup size " 2082 "(%d) must equal the size supported by the hardware " 2083 "(%d)\n", reta_size, tbl_size); 2084 return -EINVAL; 2085 } 2086 2087 for (idx = 0, i = 0; i < reta_size; i++) { 2088 idx = i / RTE_RETA_GROUP_SIZE; 2089 sft = i % RTE_RETA_GROUP_SIZE; 2090 2091 if (reta_conf[idx].mask & (1ULL << sft)) { 2092 uint16_t qid; 2093 2094 if (BNXT_CHIP_P5(bp)) 2095 qid = bnxt_rss_to_qid(bp, 2096 vnic->rss_table[i * 2]); 2097 else 2098 qid = bnxt_rss_to_qid(bp, vnic->rss_table[i]); 2099 2100 if (qid == INVALID_HW_RING_ID) { 2101 PMD_DRV_LOG(ERR, "Inv. entry in rss table.\n"); 2102 return -EINVAL; 2103 } 2104 reta_conf[idx].reta[sft] = qid; 2105 } 2106 } 2107 2108 return 0; 2109 } 2110 2111 static int bnxt_rss_hash_update_op(struct rte_eth_dev *eth_dev, 2112 struct rte_eth_rss_conf *rss_conf) 2113 { 2114 struct bnxt *bp = eth_dev->data->dev_private; 2115 struct rte_eth_conf *dev_conf = &bp->eth_dev->data->dev_conf; 2116 struct bnxt_vnic_info *vnic; 2117 int rc; 2118 2119 rc = is_bnxt_in_error(bp); 2120 if (rc) 2121 return rc; 2122 2123 /* 2124 * If RSS enablement were different than dev_configure, 2125 * then return -EINVAL 2126 */ 2127 if (dev_conf->rxmode.mq_mode & ETH_MQ_RX_RSS_FLAG) { 2128 if (!rss_conf->rss_hf) 2129 PMD_DRV_LOG(ERR, "Hash type NONE\n"); 2130 } else { 2131 if (rss_conf->rss_hf & BNXT_ETH_RSS_SUPPORT) 2132 return -EINVAL; 2133 } 2134 2135 bp->flags |= BNXT_FLAG_UPDATE_HASH; 2136 memcpy(ð_dev->data->dev_conf.rx_adv_conf.rss_conf, 2137 rss_conf, 2138 sizeof(*rss_conf)); 2139 2140 /* Update the default RSS VNIC(s) */ 2141 vnic = BNXT_GET_DEFAULT_VNIC(bp); 2142 vnic->hash_type = bnxt_rte_to_hwrm_hash_types(rss_conf->rss_hf); 2143 vnic->hash_mode = 2144 bnxt_rte_to_hwrm_hash_level(bp, rss_conf->rss_hf, 2145 ETH_RSS_LEVEL(rss_conf->rss_hf)); 2146 2147 /* 2148 * If hashkey is not specified, use the previously configured 2149 * hashkey 2150 */ 2151 if (!rss_conf->rss_key) 2152 goto rss_config; 2153 2154 if (rss_conf->rss_key_len != HW_HASH_KEY_SIZE) { 2155 PMD_DRV_LOG(ERR, 2156 "Invalid hashkey length, should be 16 bytes\n"); 2157 return -EINVAL; 2158 } 2159 memcpy(vnic->rss_hash_key, rss_conf->rss_key, rss_conf->rss_key_len); 2160 2161 rss_config: 2162 rc = bnxt_hwrm_vnic_rss_cfg(bp, vnic); 2163 return rc; 2164 } 2165 2166 static int bnxt_rss_hash_conf_get_op(struct rte_eth_dev *eth_dev, 2167 struct rte_eth_rss_conf *rss_conf) 2168 { 2169 struct bnxt *bp = eth_dev->data->dev_private; 2170 struct bnxt_vnic_info *vnic = BNXT_GET_DEFAULT_VNIC(bp); 2171 int len, rc; 2172 uint32_t hash_types; 2173 2174 rc = is_bnxt_in_error(bp); 2175 if (rc) 2176 return rc; 2177 2178 /* RSS configuration is the same for all VNICs */ 2179 if (vnic && vnic->rss_hash_key) { 2180 if (rss_conf->rss_key) { 2181 len = rss_conf->rss_key_len <= HW_HASH_KEY_SIZE ? 2182 rss_conf->rss_key_len : HW_HASH_KEY_SIZE; 2183 memcpy(rss_conf->rss_key, vnic->rss_hash_key, len); 2184 } 2185 2186 hash_types = vnic->hash_type; 2187 rss_conf->rss_hf = 0; 2188 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_IPV4) { 2189 rss_conf->rss_hf |= ETH_RSS_IPV4; 2190 hash_types &= ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_IPV4; 2191 } 2192 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_TCP_IPV4) { 2193 rss_conf->rss_hf |= ETH_RSS_NONFRAG_IPV4_TCP; 2194 hash_types &= 2195 ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_TCP_IPV4; 2196 } 2197 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_UDP_IPV4) { 2198 rss_conf->rss_hf |= ETH_RSS_NONFRAG_IPV4_UDP; 2199 hash_types &= 2200 ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_UDP_IPV4; 2201 } 2202 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_IPV6) { 2203 rss_conf->rss_hf |= ETH_RSS_IPV6; 2204 hash_types &= ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_IPV6; 2205 } 2206 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_TCP_IPV6) { 2207 rss_conf->rss_hf |= ETH_RSS_NONFRAG_IPV6_TCP; 2208 hash_types &= 2209 ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_TCP_IPV6; 2210 } 2211 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_UDP_IPV6) { 2212 rss_conf->rss_hf |= ETH_RSS_NONFRAG_IPV6_UDP; 2213 hash_types &= 2214 ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_UDP_IPV6; 2215 } 2216 2217 rss_conf->rss_hf |= 2218 bnxt_hwrm_to_rte_rss_level(bp, vnic->hash_mode); 2219 2220 if (hash_types) { 2221 PMD_DRV_LOG(ERR, 2222 "Unknown RSS config from firmware (%08x), RSS disabled", 2223 vnic->hash_type); 2224 return -ENOTSUP; 2225 } 2226 } else { 2227 rss_conf->rss_hf = 0; 2228 } 2229 return 0; 2230 } 2231 2232 static int bnxt_flow_ctrl_get_op(struct rte_eth_dev *dev, 2233 struct rte_eth_fc_conf *fc_conf) 2234 { 2235 struct bnxt *bp = dev->data->dev_private; 2236 struct rte_eth_link link_info; 2237 int rc; 2238 2239 rc = is_bnxt_in_error(bp); 2240 if (rc) 2241 return rc; 2242 2243 rc = bnxt_get_hwrm_link_config(bp, &link_info); 2244 if (rc) 2245 return rc; 2246 2247 memset(fc_conf, 0, sizeof(*fc_conf)); 2248 if (bp->link_info->auto_pause) 2249 fc_conf->autoneg = 1; 2250 switch (bp->link_info->pause) { 2251 case 0: 2252 fc_conf->mode = RTE_FC_NONE; 2253 break; 2254 case HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX: 2255 fc_conf->mode = RTE_FC_TX_PAUSE; 2256 break; 2257 case HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX: 2258 fc_conf->mode = RTE_FC_RX_PAUSE; 2259 break; 2260 case (HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX | 2261 HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX): 2262 fc_conf->mode = RTE_FC_FULL; 2263 break; 2264 } 2265 return 0; 2266 } 2267 2268 static int bnxt_flow_ctrl_set_op(struct rte_eth_dev *dev, 2269 struct rte_eth_fc_conf *fc_conf) 2270 { 2271 struct bnxt *bp = dev->data->dev_private; 2272 int rc; 2273 2274 rc = is_bnxt_in_error(bp); 2275 if (rc) 2276 return rc; 2277 2278 if (!BNXT_SINGLE_PF(bp)) { 2279 PMD_DRV_LOG(ERR, 2280 "Flow Control Settings cannot be modified on VF or on shared PF\n"); 2281 return -ENOTSUP; 2282 } 2283 2284 switch (fc_conf->mode) { 2285 case RTE_FC_NONE: 2286 bp->link_info->auto_pause = 0; 2287 bp->link_info->force_pause = 0; 2288 break; 2289 case RTE_FC_RX_PAUSE: 2290 if (fc_conf->autoneg) { 2291 bp->link_info->auto_pause = 2292 HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_RX; 2293 bp->link_info->force_pause = 0; 2294 } else { 2295 bp->link_info->auto_pause = 0; 2296 bp->link_info->force_pause = 2297 HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_RX; 2298 } 2299 break; 2300 case RTE_FC_TX_PAUSE: 2301 if (fc_conf->autoneg) { 2302 bp->link_info->auto_pause = 2303 HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_TX; 2304 bp->link_info->force_pause = 0; 2305 } else { 2306 bp->link_info->auto_pause = 0; 2307 bp->link_info->force_pause = 2308 HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_TX; 2309 } 2310 break; 2311 case RTE_FC_FULL: 2312 if (fc_conf->autoneg) { 2313 bp->link_info->auto_pause = 2314 HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_TX | 2315 HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_RX; 2316 bp->link_info->force_pause = 0; 2317 } else { 2318 bp->link_info->auto_pause = 0; 2319 bp->link_info->force_pause = 2320 HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_TX | 2321 HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_RX; 2322 } 2323 break; 2324 } 2325 return bnxt_set_hwrm_link_config(bp, true); 2326 } 2327 2328 /* Add UDP tunneling port */ 2329 static int 2330 bnxt_udp_tunnel_port_add_op(struct rte_eth_dev *eth_dev, 2331 struct rte_eth_udp_tunnel *udp_tunnel) 2332 { 2333 struct bnxt *bp = eth_dev->data->dev_private; 2334 uint16_t tunnel_type = 0; 2335 int rc = 0; 2336 2337 rc = is_bnxt_in_error(bp); 2338 if (rc) 2339 return rc; 2340 2341 switch (udp_tunnel->prot_type) { 2342 case RTE_TUNNEL_TYPE_VXLAN: 2343 if (bp->vxlan_port_cnt) { 2344 PMD_DRV_LOG(ERR, "Tunnel Port %d already programmed\n", 2345 udp_tunnel->udp_port); 2346 if (bp->vxlan_port != udp_tunnel->udp_port) { 2347 PMD_DRV_LOG(ERR, "Only one port allowed\n"); 2348 return -ENOSPC; 2349 } 2350 bp->vxlan_port_cnt++; 2351 return 0; 2352 } 2353 tunnel_type = 2354 HWRM_TUNNEL_DST_PORT_ALLOC_INPUT_TUNNEL_TYPE_VXLAN; 2355 bp->vxlan_port_cnt++; 2356 break; 2357 case RTE_TUNNEL_TYPE_GENEVE: 2358 if (bp->geneve_port_cnt) { 2359 PMD_DRV_LOG(ERR, "Tunnel Port %d already programmed\n", 2360 udp_tunnel->udp_port); 2361 if (bp->geneve_port != udp_tunnel->udp_port) { 2362 PMD_DRV_LOG(ERR, "Only one port allowed\n"); 2363 return -ENOSPC; 2364 } 2365 bp->geneve_port_cnt++; 2366 return 0; 2367 } 2368 tunnel_type = 2369 HWRM_TUNNEL_DST_PORT_ALLOC_INPUT_TUNNEL_TYPE_GENEVE; 2370 bp->geneve_port_cnt++; 2371 break; 2372 default: 2373 PMD_DRV_LOG(ERR, "Tunnel type is not supported\n"); 2374 return -ENOTSUP; 2375 } 2376 rc = bnxt_hwrm_tunnel_dst_port_alloc(bp, udp_tunnel->udp_port, 2377 tunnel_type); 2378 return rc; 2379 } 2380 2381 static int 2382 bnxt_udp_tunnel_port_del_op(struct rte_eth_dev *eth_dev, 2383 struct rte_eth_udp_tunnel *udp_tunnel) 2384 { 2385 struct bnxt *bp = eth_dev->data->dev_private; 2386 uint16_t tunnel_type = 0; 2387 uint16_t port = 0; 2388 int rc = 0; 2389 2390 rc = is_bnxt_in_error(bp); 2391 if (rc) 2392 return rc; 2393 2394 switch (udp_tunnel->prot_type) { 2395 case RTE_TUNNEL_TYPE_VXLAN: 2396 if (!bp->vxlan_port_cnt) { 2397 PMD_DRV_LOG(ERR, "No Tunnel port configured yet\n"); 2398 return -EINVAL; 2399 } 2400 if (bp->vxlan_port != udp_tunnel->udp_port) { 2401 PMD_DRV_LOG(ERR, "Req Port: %d. Configured port: %d\n", 2402 udp_tunnel->udp_port, bp->vxlan_port); 2403 return -EINVAL; 2404 } 2405 if (--bp->vxlan_port_cnt) 2406 return 0; 2407 2408 tunnel_type = 2409 HWRM_TUNNEL_DST_PORT_FREE_INPUT_TUNNEL_TYPE_VXLAN; 2410 port = bp->vxlan_fw_dst_port_id; 2411 break; 2412 case RTE_TUNNEL_TYPE_GENEVE: 2413 if (!bp->geneve_port_cnt) { 2414 PMD_DRV_LOG(ERR, "No Tunnel port configured yet\n"); 2415 return -EINVAL; 2416 } 2417 if (bp->geneve_port != udp_tunnel->udp_port) { 2418 PMD_DRV_LOG(ERR, "Req Port: %d. Configured port: %d\n", 2419 udp_tunnel->udp_port, bp->geneve_port); 2420 return -EINVAL; 2421 } 2422 if (--bp->geneve_port_cnt) 2423 return 0; 2424 2425 tunnel_type = 2426 HWRM_TUNNEL_DST_PORT_FREE_INPUT_TUNNEL_TYPE_GENEVE; 2427 port = bp->geneve_fw_dst_port_id; 2428 break; 2429 default: 2430 PMD_DRV_LOG(ERR, "Tunnel type is not supported\n"); 2431 return -ENOTSUP; 2432 } 2433 2434 rc = bnxt_hwrm_tunnel_dst_port_free(bp, port, tunnel_type); 2435 return rc; 2436 } 2437 2438 static int bnxt_del_vlan_filter(struct bnxt *bp, uint16_t vlan_id) 2439 { 2440 struct bnxt_filter_info *filter; 2441 struct bnxt_vnic_info *vnic; 2442 int rc = 0; 2443 uint32_t chk = HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_IVLAN; 2444 2445 vnic = BNXT_GET_DEFAULT_VNIC(bp); 2446 filter = STAILQ_FIRST(&vnic->filter); 2447 while (filter) { 2448 /* Search for this matching MAC+VLAN filter */ 2449 if (bnxt_vlan_filter_exists(bp, filter, chk, vlan_id)) { 2450 /* Delete the filter */ 2451 rc = bnxt_hwrm_clear_l2_filter(bp, filter); 2452 if (rc) 2453 return rc; 2454 STAILQ_REMOVE(&vnic->filter, filter, 2455 bnxt_filter_info, next); 2456 bnxt_free_filter(bp, filter); 2457 PMD_DRV_LOG(INFO, 2458 "Deleted vlan filter for %d\n", 2459 vlan_id); 2460 return 0; 2461 } 2462 filter = STAILQ_NEXT(filter, next); 2463 } 2464 return -ENOENT; 2465 } 2466 2467 static int bnxt_add_vlan_filter(struct bnxt *bp, uint16_t vlan_id) 2468 { 2469 struct bnxt_filter_info *filter; 2470 struct bnxt_vnic_info *vnic; 2471 int rc = 0; 2472 uint32_t en = HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_IVLAN | 2473 HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_IVLAN_MASK; 2474 uint32_t chk = HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_IVLAN; 2475 2476 /* Implementation notes on the use of VNIC in this command: 2477 * 2478 * By default, these filters belong to default vnic for the function. 2479 * Once these filters are set up, only destination VNIC can be modified. 2480 * If the destination VNIC is not specified in this command, 2481 * then the HWRM shall only create an l2 context id. 2482 */ 2483 2484 vnic = BNXT_GET_DEFAULT_VNIC(bp); 2485 filter = STAILQ_FIRST(&vnic->filter); 2486 /* Check if the VLAN has already been added */ 2487 while (filter) { 2488 if (bnxt_vlan_filter_exists(bp, filter, chk, vlan_id)) 2489 return -EEXIST; 2490 2491 filter = STAILQ_NEXT(filter, next); 2492 } 2493 2494 /* No match found. Alloc a fresh filter and issue the L2_FILTER_ALLOC 2495 * command to create MAC+VLAN filter with the right flags, enables set. 2496 */ 2497 filter = bnxt_alloc_filter(bp); 2498 if (!filter) { 2499 PMD_DRV_LOG(ERR, 2500 "MAC/VLAN filter alloc failed\n"); 2501 return -ENOMEM; 2502 } 2503 /* MAC + VLAN ID filter */ 2504 /* If l2_ivlan == 0 and l2_ivlan_mask != 0, only 2505 * untagged packets are received 2506 * 2507 * If l2_ivlan != 0 and l2_ivlan_mask != 0, untagged 2508 * packets and only the programmed vlan's packets are received 2509 */ 2510 filter->l2_ivlan = vlan_id; 2511 filter->l2_ivlan_mask = 0x0FFF; 2512 filter->enables |= en; 2513 filter->flags |= HWRM_CFA_L2_FILTER_ALLOC_INPUT_FLAGS_OUTERMOST; 2514 2515 rc = bnxt_hwrm_set_l2_filter(bp, vnic->fw_vnic_id, filter); 2516 if (rc) { 2517 /* Free the newly allocated filter as we were 2518 * not able to create the filter in hardware. 2519 */ 2520 bnxt_free_filter(bp, filter); 2521 return rc; 2522 } 2523 2524 filter->mac_index = 0; 2525 /* Add this new filter to the list */ 2526 if (vlan_id == 0) 2527 STAILQ_INSERT_HEAD(&vnic->filter, filter, next); 2528 else 2529 STAILQ_INSERT_TAIL(&vnic->filter, filter, next); 2530 2531 PMD_DRV_LOG(INFO, 2532 "Added Vlan filter for %d\n", vlan_id); 2533 return rc; 2534 } 2535 2536 static int bnxt_vlan_filter_set_op(struct rte_eth_dev *eth_dev, 2537 uint16_t vlan_id, int on) 2538 { 2539 struct bnxt *bp = eth_dev->data->dev_private; 2540 int rc; 2541 2542 rc = is_bnxt_in_error(bp); 2543 if (rc) 2544 return rc; 2545 2546 if (!eth_dev->data->dev_started) { 2547 PMD_DRV_LOG(ERR, "port must be started before setting vlan\n"); 2548 return -EINVAL; 2549 } 2550 2551 /* These operations apply to ALL existing MAC/VLAN filters */ 2552 if (on) 2553 return bnxt_add_vlan_filter(bp, vlan_id); 2554 else 2555 return bnxt_del_vlan_filter(bp, vlan_id); 2556 } 2557 2558 static int bnxt_del_dflt_mac_filter(struct bnxt *bp, 2559 struct bnxt_vnic_info *vnic) 2560 { 2561 struct bnxt_filter_info *filter; 2562 int rc; 2563 2564 filter = STAILQ_FIRST(&vnic->filter); 2565 while (filter) { 2566 if (filter->mac_index == 0 && 2567 !memcmp(filter->l2_addr, bp->mac_addr, 2568 RTE_ETHER_ADDR_LEN)) { 2569 rc = bnxt_hwrm_clear_l2_filter(bp, filter); 2570 if (!rc) { 2571 STAILQ_REMOVE(&vnic->filter, filter, 2572 bnxt_filter_info, next); 2573 bnxt_free_filter(bp, filter); 2574 } 2575 return rc; 2576 } 2577 filter = STAILQ_NEXT(filter, next); 2578 } 2579 return 0; 2580 } 2581 2582 static int 2583 bnxt_config_vlan_hw_filter(struct bnxt *bp, uint64_t rx_offloads) 2584 { 2585 struct bnxt_vnic_info *vnic; 2586 unsigned int i; 2587 int rc; 2588 2589 vnic = BNXT_GET_DEFAULT_VNIC(bp); 2590 if (!(rx_offloads & DEV_RX_OFFLOAD_VLAN_FILTER)) { 2591 /* Remove any VLAN filters programmed */ 2592 for (i = 0; i < RTE_ETHER_MAX_VLAN_ID; i++) 2593 bnxt_del_vlan_filter(bp, i); 2594 2595 rc = bnxt_add_mac_filter(bp, vnic, NULL, 0, 0); 2596 if (rc) 2597 return rc; 2598 } else { 2599 /* Default filter will allow packets that match the 2600 * dest mac. So, it has to be deleted, otherwise, we 2601 * will endup receiving vlan packets for which the 2602 * filter is not programmed, when hw-vlan-filter 2603 * configuration is ON 2604 */ 2605 bnxt_del_dflt_mac_filter(bp, vnic); 2606 /* This filter will allow only untagged packets */ 2607 bnxt_add_vlan_filter(bp, 0); 2608 } 2609 PMD_DRV_LOG(DEBUG, "VLAN Filtering: %d\n", 2610 !!(rx_offloads & DEV_RX_OFFLOAD_VLAN_FILTER)); 2611 2612 return 0; 2613 } 2614 2615 static int bnxt_free_one_vnic(struct bnxt *bp, uint16_t vnic_id) 2616 { 2617 struct bnxt_vnic_info *vnic = &bp->vnic_info[vnic_id]; 2618 unsigned int i; 2619 int rc; 2620 2621 /* Destroy vnic filters and vnic */ 2622 if (bp->eth_dev->data->dev_conf.rxmode.offloads & 2623 DEV_RX_OFFLOAD_VLAN_FILTER) { 2624 for (i = 0; i < RTE_ETHER_MAX_VLAN_ID; i++) 2625 bnxt_del_vlan_filter(bp, i); 2626 } 2627 bnxt_del_dflt_mac_filter(bp, vnic); 2628 2629 rc = bnxt_hwrm_vnic_ctx_free(bp, vnic); 2630 if (rc) 2631 return rc; 2632 2633 rc = bnxt_hwrm_vnic_free(bp, vnic); 2634 if (rc) 2635 return rc; 2636 2637 rte_free(vnic->fw_grp_ids); 2638 vnic->fw_grp_ids = NULL; 2639 2640 vnic->rx_queue_cnt = 0; 2641 2642 return 0; 2643 } 2644 2645 static int 2646 bnxt_config_vlan_hw_stripping(struct bnxt *bp, uint64_t rx_offloads) 2647 { 2648 struct bnxt_vnic_info *vnic = BNXT_GET_DEFAULT_VNIC(bp); 2649 int rc; 2650 2651 /* Destroy, recreate and reconfigure the default vnic */ 2652 rc = bnxt_free_one_vnic(bp, 0); 2653 if (rc) 2654 return rc; 2655 2656 /* default vnic 0 */ 2657 rc = bnxt_setup_one_vnic(bp, 0); 2658 if (rc) 2659 return rc; 2660 2661 if (bp->eth_dev->data->dev_conf.rxmode.offloads & 2662 DEV_RX_OFFLOAD_VLAN_FILTER) { 2663 rc = bnxt_add_vlan_filter(bp, 0); 2664 if (rc) 2665 return rc; 2666 rc = bnxt_restore_vlan_filters(bp); 2667 if (rc) 2668 return rc; 2669 } else { 2670 rc = bnxt_add_mac_filter(bp, vnic, NULL, 0, 0); 2671 if (rc) 2672 return rc; 2673 } 2674 2675 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 2676 if (rc) 2677 return rc; 2678 2679 PMD_DRV_LOG(DEBUG, "VLAN Strip Offload: %d\n", 2680 !!(rx_offloads & DEV_RX_OFFLOAD_VLAN_STRIP)); 2681 2682 return rc; 2683 } 2684 2685 static int 2686 bnxt_vlan_offload_set_op(struct rte_eth_dev *dev, int mask) 2687 { 2688 uint64_t rx_offloads = dev->data->dev_conf.rxmode.offloads; 2689 struct bnxt *bp = dev->data->dev_private; 2690 int rc; 2691 2692 rc = is_bnxt_in_error(bp); 2693 if (rc) 2694 return rc; 2695 2696 /* Filter settings will get applied when port is started */ 2697 if (!dev->data->dev_started) 2698 return 0; 2699 2700 if (mask & ETH_VLAN_FILTER_MASK) { 2701 /* Enable or disable VLAN filtering */ 2702 rc = bnxt_config_vlan_hw_filter(bp, rx_offloads); 2703 if (rc) 2704 return rc; 2705 } 2706 2707 if (mask & ETH_VLAN_STRIP_MASK) { 2708 /* Enable or disable VLAN stripping */ 2709 rc = bnxt_config_vlan_hw_stripping(bp, rx_offloads); 2710 if (rc) 2711 return rc; 2712 } 2713 2714 if (mask & ETH_VLAN_EXTEND_MASK) { 2715 if (rx_offloads & DEV_RX_OFFLOAD_VLAN_EXTEND) 2716 PMD_DRV_LOG(DEBUG, "Extend VLAN supported\n"); 2717 else 2718 PMD_DRV_LOG(INFO, "Extend VLAN unsupported\n"); 2719 } 2720 2721 return 0; 2722 } 2723 2724 static int 2725 bnxt_vlan_tpid_set_op(struct rte_eth_dev *dev, enum rte_vlan_type vlan_type, 2726 uint16_t tpid) 2727 { 2728 struct bnxt *bp = dev->data->dev_private; 2729 int qinq = dev->data->dev_conf.rxmode.offloads & 2730 DEV_RX_OFFLOAD_VLAN_EXTEND; 2731 2732 if (vlan_type != ETH_VLAN_TYPE_INNER && 2733 vlan_type != ETH_VLAN_TYPE_OUTER) { 2734 PMD_DRV_LOG(ERR, 2735 "Unsupported vlan type."); 2736 return -EINVAL; 2737 } 2738 if (!qinq) { 2739 PMD_DRV_LOG(ERR, 2740 "QinQ not enabled. Needs to be ON as we can " 2741 "accelerate only outer vlan\n"); 2742 return -EINVAL; 2743 } 2744 2745 if (vlan_type == ETH_VLAN_TYPE_OUTER) { 2746 switch (tpid) { 2747 case RTE_ETHER_TYPE_QINQ: 2748 bp->outer_tpid_bd = 2749 TX_BD_LONG_CFA_META_VLAN_TPID_TPID88A8; 2750 break; 2751 case RTE_ETHER_TYPE_VLAN: 2752 bp->outer_tpid_bd = 2753 TX_BD_LONG_CFA_META_VLAN_TPID_TPID8100; 2754 break; 2755 case RTE_ETHER_TYPE_QINQ1: 2756 bp->outer_tpid_bd = 2757 TX_BD_LONG_CFA_META_VLAN_TPID_TPID9100; 2758 break; 2759 case RTE_ETHER_TYPE_QINQ2: 2760 bp->outer_tpid_bd = 2761 TX_BD_LONG_CFA_META_VLAN_TPID_TPID9200; 2762 break; 2763 case RTE_ETHER_TYPE_QINQ3: 2764 bp->outer_tpid_bd = 2765 TX_BD_LONG_CFA_META_VLAN_TPID_TPID9300; 2766 break; 2767 default: 2768 PMD_DRV_LOG(ERR, "Invalid TPID: %x\n", tpid); 2769 return -EINVAL; 2770 } 2771 bp->outer_tpid_bd |= tpid; 2772 PMD_DRV_LOG(INFO, "outer_tpid_bd = %x\n", bp->outer_tpid_bd); 2773 } else if (vlan_type == ETH_VLAN_TYPE_INNER) { 2774 PMD_DRV_LOG(ERR, 2775 "Can accelerate only outer vlan in QinQ\n"); 2776 return -EINVAL; 2777 } 2778 2779 return 0; 2780 } 2781 2782 static int 2783 bnxt_set_default_mac_addr_op(struct rte_eth_dev *dev, 2784 struct rte_ether_addr *addr) 2785 { 2786 struct bnxt *bp = dev->data->dev_private; 2787 /* Default Filter is tied to VNIC 0 */ 2788 struct bnxt_vnic_info *vnic = BNXT_GET_DEFAULT_VNIC(bp); 2789 int rc; 2790 2791 rc = is_bnxt_in_error(bp); 2792 if (rc) 2793 return rc; 2794 2795 if (BNXT_VF(bp) && !BNXT_VF_IS_TRUSTED(bp)) 2796 return -EPERM; 2797 2798 if (rte_is_zero_ether_addr(addr)) 2799 return -EINVAL; 2800 2801 /* Filter settings will get applied when port is started */ 2802 if (!dev->data->dev_started) 2803 return 0; 2804 2805 /* Check if the requested MAC is already added */ 2806 if (memcmp(addr, bp->mac_addr, RTE_ETHER_ADDR_LEN) == 0) 2807 return 0; 2808 2809 /* Destroy filter and re-create it */ 2810 bnxt_del_dflt_mac_filter(bp, vnic); 2811 2812 memcpy(bp->mac_addr, addr, RTE_ETHER_ADDR_LEN); 2813 if (dev->data->dev_conf.rxmode.offloads & DEV_RX_OFFLOAD_VLAN_FILTER) { 2814 /* This filter will allow only untagged packets */ 2815 rc = bnxt_add_vlan_filter(bp, 0); 2816 } else { 2817 rc = bnxt_add_mac_filter(bp, vnic, addr, 0, 0); 2818 } 2819 2820 PMD_DRV_LOG(DEBUG, "Set MAC addr\n"); 2821 return rc; 2822 } 2823 2824 static int 2825 bnxt_dev_set_mc_addr_list_op(struct rte_eth_dev *eth_dev, 2826 struct rte_ether_addr *mc_addr_set, 2827 uint32_t nb_mc_addr) 2828 { 2829 struct bnxt *bp = eth_dev->data->dev_private; 2830 char *mc_addr_list = (char *)mc_addr_set; 2831 struct bnxt_vnic_info *vnic; 2832 uint32_t off = 0, i = 0; 2833 int rc; 2834 2835 rc = is_bnxt_in_error(bp); 2836 if (rc) 2837 return rc; 2838 2839 vnic = BNXT_GET_DEFAULT_VNIC(bp); 2840 2841 if (nb_mc_addr > BNXT_MAX_MC_ADDRS) { 2842 vnic->flags |= BNXT_VNIC_INFO_ALLMULTI; 2843 goto allmulti; 2844 } 2845 2846 /* TODO Check for Duplicate mcast addresses */ 2847 vnic->flags &= ~BNXT_VNIC_INFO_ALLMULTI; 2848 for (i = 0; i < nb_mc_addr; i++) { 2849 memcpy(vnic->mc_list + off, &mc_addr_list[i], 2850 RTE_ETHER_ADDR_LEN); 2851 off += RTE_ETHER_ADDR_LEN; 2852 } 2853 2854 vnic->mc_addr_cnt = i; 2855 if (vnic->mc_addr_cnt) 2856 vnic->flags |= BNXT_VNIC_INFO_MCAST; 2857 else 2858 vnic->flags &= ~BNXT_VNIC_INFO_MCAST; 2859 2860 allmulti: 2861 return bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 2862 } 2863 2864 static int 2865 bnxt_fw_version_get(struct rte_eth_dev *dev, char *fw_version, size_t fw_size) 2866 { 2867 struct bnxt *bp = dev->data->dev_private; 2868 uint8_t fw_major = (bp->fw_ver >> 24) & 0xff; 2869 uint8_t fw_minor = (bp->fw_ver >> 16) & 0xff; 2870 uint8_t fw_updt = (bp->fw_ver >> 8) & 0xff; 2871 uint8_t fw_rsvd = bp->fw_ver & 0xff; 2872 int ret; 2873 2874 ret = snprintf(fw_version, fw_size, "%d.%d.%d.%d", 2875 fw_major, fw_minor, fw_updt, fw_rsvd); 2876 if (ret < 0) 2877 return -EINVAL; 2878 2879 ret += 1; /* add the size of '\0' */ 2880 if (fw_size < (size_t)ret) 2881 return ret; 2882 else 2883 return 0; 2884 } 2885 2886 static void 2887 bnxt_rxq_info_get_op(struct rte_eth_dev *dev, uint16_t queue_id, 2888 struct rte_eth_rxq_info *qinfo) 2889 { 2890 struct bnxt *bp = dev->data->dev_private; 2891 struct bnxt_rx_queue *rxq; 2892 2893 if (is_bnxt_in_error(bp)) 2894 return; 2895 2896 rxq = dev->data->rx_queues[queue_id]; 2897 2898 qinfo->mp = rxq->mb_pool; 2899 qinfo->scattered_rx = dev->data->scattered_rx; 2900 qinfo->nb_desc = rxq->nb_rx_desc; 2901 2902 qinfo->conf.rx_free_thresh = rxq->rx_free_thresh; 2903 qinfo->conf.rx_drop_en = rxq->drop_en; 2904 qinfo->conf.rx_deferred_start = rxq->rx_deferred_start; 2905 qinfo->conf.offloads = dev->data->dev_conf.rxmode.offloads; 2906 } 2907 2908 static void 2909 bnxt_txq_info_get_op(struct rte_eth_dev *dev, uint16_t queue_id, 2910 struct rte_eth_txq_info *qinfo) 2911 { 2912 struct bnxt *bp = dev->data->dev_private; 2913 struct bnxt_tx_queue *txq; 2914 2915 if (is_bnxt_in_error(bp)) 2916 return; 2917 2918 txq = dev->data->tx_queues[queue_id]; 2919 2920 qinfo->nb_desc = txq->nb_tx_desc; 2921 2922 qinfo->conf.tx_thresh.pthresh = txq->pthresh; 2923 qinfo->conf.tx_thresh.hthresh = txq->hthresh; 2924 qinfo->conf.tx_thresh.wthresh = txq->wthresh; 2925 2926 qinfo->conf.tx_free_thresh = txq->tx_free_thresh; 2927 qinfo->conf.tx_rs_thresh = 0; 2928 qinfo->conf.tx_deferred_start = txq->tx_deferred_start; 2929 qinfo->conf.offloads = txq->offloads; 2930 } 2931 2932 static const struct { 2933 eth_rx_burst_t pkt_burst; 2934 const char *info; 2935 } bnxt_rx_burst_info[] = { 2936 {bnxt_recv_pkts, "Scalar"}, 2937 #if defined(RTE_ARCH_X86) 2938 {bnxt_recv_pkts_vec, "Vector SSE"}, 2939 #endif 2940 #if defined(RTE_ARCH_X86) && defined(CC_AVX2_SUPPORT) 2941 {bnxt_recv_pkts_vec_avx2, "Vector AVX2"}, 2942 #endif 2943 #if defined(RTE_ARCH_ARM64) 2944 {bnxt_recv_pkts_vec, "Vector Neon"}, 2945 #endif 2946 }; 2947 2948 static int 2949 bnxt_rx_burst_mode_get(struct rte_eth_dev *dev, __rte_unused uint16_t queue_id, 2950 struct rte_eth_burst_mode *mode) 2951 { 2952 eth_rx_burst_t pkt_burst = dev->rx_pkt_burst; 2953 size_t i; 2954 2955 for (i = 0; i < RTE_DIM(bnxt_rx_burst_info); i++) { 2956 if (pkt_burst == bnxt_rx_burst_info[i].pkt_burst) { 2957 snprintf(mode->info, sizeof(mode->info), "%s", 2958 bnxt_rx_burst_info[i].info); 2959 return 0; 2960 } 2961 } 2962 2963 return -EINVAL; 2964 } 2965 2966 static const struct { 2967 eth_tx_burst_t pkt_burst; 2968 const char *info; 2969 } bnxt_tx_burst_info[] = { 2970 {bnxt_xmit_pkts, "Scalar"}, 2971 #if defined(RTE_ARCH_X86) 2972 {bnxt_xmit_pkts_vec, "Vector SSE"}, 2973 #endif 2974 #if defined(RTE_ARCH_X86) && defined(CC_AVX2_SUPPORT) 2975 {bnxt_xmit_pkts_vec_avx2, "Vector AVX2"}, 2976 #endif 2977 #if defined(RTE_ARCH_ARM64) 2978 {bnxt_xmit_pkts_vec, "Vector Neon"}, 2979 #endif 2980 }; 2981 2982 static int 2983 bnxt_tx_burst_mode_get(struct rte_eth_dev *dev, __rte_unused uint16_t queue_id, 2984 struct rte_eth_burst_mode *mode) 2985 { 2986 eth_tx_burst_t pkt_burst = dev->tx_pkt_burst; 2987 size_t i; 2988 2989 for (i = 0; i < RTE_DIM(bnxt_tx_burst_info); i++) { 2990 if (pkt_burst == bnxt_tx_burst_info[i].pkt_burst) { 2991 snprintf(mode->info, sizeof(mode->info), "%s", 2992 bnxt_tx_burst_info[i].info); 2993 return 0; 2994 } 2995 } 2996 2997 return -EINVAL; 2998 } 2999 3000 int bnxt_mtu_set_op(struct rte_eth_dev *eth_dev, uint16_t new_mtu) 3001 { 3002 struct bnxt *bp = eth_dev->data->dev_private; 3003 uint32_t new_pkt_size; 3004 uint32_t rc = 0; 3005 uint32_t i; 3006 3007 rc = is_bnxt_in_error(bp); 3008 if (rc) 3009 return rc; 3010 3011 /* Exit if receive queues are not configured yet */ 3012 if (!eth_dev->data->nb_rx_queues) 3013 return rc; 3014 3015 new_pkt_size = new_mtu + RTE_ETHER_HDR_LEN + RTE_ETHER_CRC_LEN + 3016 VLAN_TAG_SIZE * BNXT_NUM_VLANS; 3017 3018 /* 3019 * Disallow any MTU change that would require scattered receive support 3020 * if it is not already enabled. 3021 */ 3022 if (eth_dev->data->dev_started && 3023 !eth_dev->data->scattered_rx && 3024 (new_pkt_size > 3025 eth_dev->data->min_rx_buf_size - RTE_PKTMBUF_HEADROOM)) { 3026 PMD_DRV_LOG(ERR, 3027 "MTU change would require scattered rx support. "); 3028 PMD_DRV_LOG(ERR, "Stop port before changing MTU.\n"); 3029 return -EINVAL; 3030 } 3031 3032 if (new_mtu > RTE_ETHER_MTU) { 3033 bp->flags |= BNXT_FLAG_JUMBO; 3034 bp->eth_dev->data->dev_conf.rxmode.offloads |= 3035 DEV_RX_OFFLOAD_JUMBO_FRAME; 3036 } else { 3037 bp->eth_dev->data->dev_conf.rxmode.offloads &= 3038 ~DEV_RX_OFFLOAD_JUMBO_FRAME; 3039 bp->flags &= ~BNXT_FLAG_JUMBO; 3040 } 3041 3042 /* Is there a change in mtu setting? */ 3043 if (eth_dev->data->dev_conf.rxmode.max_rx_pkt_len == new_pkt_size) 3044 return rc; 3045 3046 for (i = 0; i < bp->nr_vnics; i++) { 3047 struct bnxt_vnic_info *vnic = &bp->vnic_info[i]; 3048 uint16_t size = 0; 3049 3050 vnic->mru = BNXT_VNIC_MRU(new_mtu); 3051 rc = bnxt_hwrm_vnic_cfg(bp, vnic); 3052 if (rc) 3053 break; 3054 3055 size = rte_pktmbuf_data_room_size(bp->rx_queues[0]->mb_pool); 3056 size -= RTE_PKTMBUF_HEADROOM; 3057 3058 if (size < new_mtu) { 3059 rc = bnxt_hwrm_vnic_plcmode_cfg(bp, vnic); 3060 if (rc) 3061 return rc; 3062 } 3063 } 3064 3065 if (!rc) 3066 eth_dev->data->dev_conf.rxmode.max_rx_pkt_len = new_pkt_size; 3067 3068 PMD_DRV_LOG(INFO, "New MTU is %d\n", new_mtu); 3069 3070 return rc; 3071 } 3072 3073 static int 3074 bnxt_vlan_pvid_set_op(struct rte_eth_dev *dev, uint16_t pvid, int on) 3075 { 3076 struct bnxt *bp = dev->data->dev_private; 3077 uint16_t vlan = bp->vlan; 3078 int rc; 3079 3080 rc = is_bnxt_in_error(bp); 3081 if (rc) 3082 return rc; 3083 3084 if (!BNXT_SINGLE_PF(bp)) { 3085 PMD_DRV_LOG(ERR, "PVID cannot be modified on VF or on shared PF\n"); 3086 return -ENOTSUP; 3087 } 3088 bp->vlan = on ? pvid : 0; 3089 3090 rc = bnxt_hwrm_set_default_vlan(bp, 0, 0); 3091 if (rc) 3092 bp->vlan = vlan; 3093 return rc; 3094 } 3095 3096 static int 3097 bnxt_dev_led_on_op(struct rte_eth_dev *dev) 3098 { 3099 struct bnxt *bp = dev->data->dev_private; 3100 int rc; 3101 3102 rc = is_bnxt_in_error(bp); 3103 if (rc) 3104 return rc; 3105 3106 return bnxt_hwrm_port_led_cfg(bp, true); 3107 } 3108 3109 static int 3110 bnxt_dev_led_off_op(struct rte_eth_dev *dev) 3111 { 3112 struct bnxt *bp = dev->data->dev_private; 3113 int rc; 3114 3115 rc = is_bnxt_in_error(bp); 3116 if (rc) 3117 return rc; 3118 3119 return bnxt_hwrm_port_led_cfg(bp, false); 3120 } 3121 3122 static uint32_t 3123 bnxt_rx_queue_count_op(struct rte_eth_dev *dev, uint16_t rx_queue_id) 3124 { 3125 struct bnxt *bp = (struct bnxt *)dev->data->dev_private; 3126 struct bnxt_cp_ring_info *cpr; 3127 uint32_t desc = 0, raw_cons; 3128 struct bnxt_rx_queue *rxq; 3129 struct rx_pkt_cmpl *rxcmp; 3130 int rc; 3131 3132 rc = is_bnxt_in_error(bp); 3133 if (rc) 3134 return rc; 3135 3136 rxq = dev->data->rx_queues[rx_queue_id]; 3137 cpr = rxq->cp_ring; 3138 raw_cons = cpr->cp_raw_cons; 3139 3140 while (1) { 3141 uint32_t agg_cnt, cons, cmpl_type; 3142 3143 cons = RING_CMP(cpr->cp_ring_struct, raw_cons); 3144 rxcmp = (struct rx_pkt_cmpl *)&cpr->cp_desc_ring[cons]; 3145 3146 if (!CMP_VALID(rxcmp, raw_cons, cpr->cp_ring_struct)) 3147 break; 3148 3149 cmpl_type = CMP_TYPE(rxcmp); 3150 3151 switch (cmpl_type) { 3152 case CMPL_BASE_TYPE_RX_L2: 3153 case CMPL_BASE_TYPE_RX_L2_V2: 3154 agg_cnt = BNXT_RX_L2_AGG_BUFS(rxcmp); 3155 raw_cons = raw_cons + CMP_LEN(cmpl_type) + agg_cnt; 3156 desc++; 3157 break; 3158 3159 case CMPL_BASE_TYPE_RX_TPA_END: 3160 if (BNXT_CHIP_P5(rxq->bp)) { 3161 struct rx_tpa_v2_end_cmpl_hi *p5_tpa_end; 3162 3163 p5_tpa_end = (void *)rxcmp; 3164 agg_cnt = BNXT_TPA_END_AGG_BUFS_TH(p5_tpa_end); 3165 } else { 3166 struct rx_tpa_end_cmpl *tpa_end; 3167 3168 tpa_end = (void *)rxcmp; 3169 agg_cnt = BNXT_TPA_END_AGG_BUFS(tpa_end); 3170 } 3171 3172 raw_cons = raw_cons + CMP_LEN(cmpl_type) + agg_cnt; 3173 desc++; 3174 break; 3175 3176 default: 3177 raw_cons += CMP_LEN(cmpl_type); 3178 } 3179 } 3180 3181 return desc; 3182 } 3183 3184 static int 3185 bnxt_rx_descriptor_status_op(void *rx_queue, uint16_t offset) 3186 { 3187 struct bnxt_rx_queue *rxq = rx_queue; 3188 struct bnxt_cp_ring_info *cpr; 3189 struct bnxt_rx_ring_info *rxr; 3190 uint32_t desc, raw_cons; 3191 struct bnxt *bp = rxq->bp; 3192 struct rx_pkt_cmpl *rxcmp; 3193 int rc; 3194 3195 rc = is_bnxt_in_error(bp); 3196 if (rc) 3197 return rc; 3198 3199 if (offset >= rxq->nb_rx_desc) 3200 return -EINVAL; 3201 3202 rxr = rxq->rx_ring; 3203 cpr = rxq->cp_ring; 3204 3205 /* 3206 * For the vector receive case, the completion at the requested 3207 * offset can be indexed directly. 3208 */ 3209 #if defined(RTE_ARCH_X86) || defined(RTE_ARCH_ARM64) 3210 if (bp->flags & BNXT_FLAG_RX_VECTOR_PKT_MODE) { 3211 struct rx_pkt_cmpl *rxcmp; 3212 uint32_t cons; 3213 3214 /* Check status of completion descriptor. */ 3215 raw_cons = cpr->cp_raw_cons + 3216 offset * CMP_LEN(CMPL_BASE_TYPE_RX_L2); 3217 cons = RING_CMP(cpr->cp_ring_struct, raw_cons); 3218 rxcmp = (struct rx_pkt_cmpl *)&cpr->cp_desc_ring[cons]; 3219 3220 if (CMP_VALID(rxcmp, raw_cons, cpr->cp_ring_struct)) 3221 return RTE_ETH_RX_DESC_DONE; 3222 3223 /* Check whether rx desc has an mbuf attached. */ 3224 cons = RING_CMP(rxr->rx_ring_struct, raw_cons / 2); 3225 if (cons >= rxq->rxrearm_start && 3226 cons < rxq->rxrearm_start + rxq->rxrearm_nb) { 3227 return RTE_ETH_RX_DESC_UNAVAIL; 3228 } 3229 3230 return RTE_ETH_RX_DESC_AVAIL; 3231 } 3232 #endif 3233 3234 /* 3235 * For the non-vector receive case, scan the completion ring to 3236 * locate the completion descriptor for the requested offset. 3237 */ 3238 raw_cons = cpr->cp_raw_cons; 3239 desc = 0; 3240 while (1) { 3241 uint32_t agg_cnt, cons, cmpl_type; 3242 3243 cons = RING_CMP(cpr->cp_ring_struct, raw_cons); 3244 rxcmp = (struct rx_pkt_cmpl *)&cpr->cp_desc_ring[cons]; 3245 3246 if (!CMP_VALID(rxcmp, raw_cons, cpr->cp_ring_struct)) 3247 break; 3248 3249 cmpl_type = CMP_TYPE(rxcmp); 3250 3251 switch (cmpl_type) { 3252 case CMPL_BASE_TYPE_RX_L2: 3253 case CMPL_BASE_TYPE_RX_L2_V2: 3254 if (desc == offset) { 3255 cons = rxcmp->opaque; 3256 if (rxr->rx_buf_ring[cons]) 3257 return RTE_ETH_RX_DESC_DONE; 3258 else 3259 return RTE_ETH_RX_DESC_UNAVAIL; 3260 } 3261 agg_cnt = BNXT_RX_L2_AGG_BUFS(rxcmp); 3262 raw_cons = raw_cons + CMP_LEN(cmpl_type) + agg_cnt; 3263 desc++; 3264 break; 3265 3266 case CMPL_BASE_TYPE_RX_TPA_END: 3267 if (desc == offset) 3268 return RTE_ETH_RX_DESC_DONE; 3269 3270 if (BNXT_CHIP_P5(rxq->bp)) { 3271 struct rx_tpa_v2_end_cmpl_hi *p5_tpa_end; 3272 3273 p5_tpa_end = (void *)rxcmp; 3274 agg_cnt = BNXT_TPA_END_AGG_BUFS_TH(p5_tpa_end); 3275 } else { 3276 struct rx_tpa_end_cmpl *tpa_end; 3277 3278 tpa_end = (void *)rxcmp; 3279 agg_cnt = BNXT_TPA_END_AGG_BUFS(tpa_end); 3280 } 3281 3282 raw_cons = raw_cons + CMP_LEN(cmpl_type) + agg_cnt; 3283 desc++; 3284 break; 3285 3286 default: 3287 raw_cons += CMP_LEN(cmpl_type); 3288 } 3289 } 3290 3291 return RTE_ETH_RX_DESC_AVAIL; 3292 } 3293 3294 static int 3295 bnxt_tx_descriptor_status_op(void *tx_queue, uint16_t offset) 3296 { 3297 struct bnxt_tx_queue *txq = (struct bnxt_tx_queue *)tx_queue; 3298 struct bnxt_tx_ring_info *txr; 3299 struct bnxt_cp_ring_info *cpr; 3300 struct rte_mbuf **tx_buf; 3301 struct tx_pkt_cmpl *txcmp; 3302 uint32_t cons, cp_cons; 3303 int rc; 3304 3305 if (!txq) 3306 return -EINVAL; 3307 3308 rc = is_bnxt_in_error(txq->bp); 3309 if (rc) 3310 return rc; 3311 3312 cpr = txq->cp_ring; 3313 txr = txq->tx_ring; 3314 3315 if (offset >= txq->nb_tx_desc) 3316 return -EINVAL; 3317 3318 cons = RING_CMP(cpr->cp_ring_struct, offset); 3319 txcmp = (struct tx_pkt_cmpl *)&cpr->cp_desc_ring[cons]; 3320 cp_cons = cpr->cp_raw_cons; 3321 3322 if (cons > cp_cons) { 3323 if (CMPL_VALID(txcmp, cpr->valid)) 3324 return RTE_ETH_TX_DESC_UNAVAIL; 3325 } else { 3326 if (CMPL_VALID(txcmp, !cpr->valid)) 3327 return RTE_ETH_TX_DESC_UNAVAIL; 3328 } 3329 tx_buf = &txr->tx_buf_ring[cons]; 3330 if (*tx_buf == NULL) 3331 return RTE_ETH_TX_DESC_DONE; 3332 3333 return RTE_ETH_TX_DESC_FULL; 3334 } 3335 3336 int 3337 bnxt_flow_ops_get_op(struct rte_eth_dev *dev, 3338 const struct rte_flow_ops **ops) 3339 { 3340 struct bnxt *bp = dev->data->dev_private; 3341 int ret = 0; 3342 3343 if (!bp) 3344 return -EIO; 3345 3346 if (BNXT_ETH_DEV_IS_REPRESENTOR(dev)) { 3347 struct bnxt_representor *vfr = dev->data->dev_private; 3348 bp = vfr->parent_dev->data->dev_private; 3349 /* parent is deleted while children are still valid */ 3350 if (!bp) { 3351 PMD_DRV_LOG(DEBUG, "BNXT Port:%d VFR Error\n", 3352 dev->data->port_id); 3353 return -EIO; 3354 } 3355 } 3356 3357 ret = is_bnxt_in_error(bp); 3358 if (ret) 3359 return ret; 3360 3361 /* PMD supports thread-safe flow operations. rte_flow API 3362 * functions can avoid mutex for multi-thread safety. 3363 */ 3364 dev->data->dev_flags |= RTE_ETH_DEV_FLOW_OPS_THREAD_SAFE; 3365 3366 if (BNXT_TRUFLOW_EN(bp)) 3367 *ops = &bnxt_ulp_rte_flow_ops; 3368 else 3369 *ops = &bnxt_flow_ops; 3370 3371 return ret; 3372 } 3373 3374 static const uint32_t * 3375 bnxt_dev_supported_ptypes_get_op(struct rte_eth_dev *dev) 3376 { 3377 static const uint32_t ptypes[] = { 3378 RTE_PTYPE_L2_ETHER_VLAN, 3379 RTE_PTYPE_L3_IPV4_EXT_UNKNOWN, 3380 RTE_PTYPE_L3_IPV6_EXT_UNKNOWN, 3381 RTE_PTYPE_L4_ICMP, 3382 RTE_PTYPE_L4_TCP, 3383 RTE_PTYPE_L4_UDP, 3384 RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN, 3385 RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN, 3386 RTE_PTYPE_INNER_L4_ICMP, 3387 RTE_PTYPE_INNER_L4_TCP, 3388 RTE_PTYPE_INNER_L4_UDP, 3389 RTE_PTYPE_UNKNOWN 3390 }; 3391 3392 if (!dev->rx_pkt_burst) 3393 return NULL; 3394 3395 return ptypes; 3396 } 3397 3398 static int bnxt_map_regs(struct bnxt *bp, uint32_t *reg_arr, int count, 3399 int reg_win) 3400 { 3401 uint32_t reg_base = *reg_arr & 0xfffff000; 3402 uint32_t win_off; 3403 int i; 3404 3405 for (i = 0; i < count; i++) { 3406 if ((reg_arr[i] & 0xfffff000) != reg_base) 3407 return -ERANGE; 3408 } 3409 win_off = BNXT_GRCPF_REG_WINDOW_BASE_OUT + (reg_win - 1) * 4; 3410 rte_write32(reg_base, (uint8_t *)bp->bar0 + win_off); 3411 return 0; 3412 } 3413 3414 static int bnxt_map_ptp_regs(struct bnxt *bp) 3415 { 3416 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3417 uint32_t *reg_arr; 3418 int rc, i; 3419 3420 reg_arr = ptp->rx_regs; 3421 rc = bnxt_map_regs(bp, reg_arr, BNXT_PTP_RX_REGS, 5); 3422 if (rc) 3423 return rc; 3424 3425 reg_arr = ptp->tx_regs; 3426 rc = bnxt_map_regs(bp, reg_arr, BNXT_PTP_TX_REGS, 6); 3427 if (rc) 3428 return rc; 3429 3430 for (i = 0; i < BNXT_PTP_RX_REGS; i++) 3431 ptp->rx_mapped_regs[i] = 0x5000 + (ptp->rx_regs[i] & 0xfff); 3432 3433 for (i = 0; i < BNXT_PTP_TX_REGS; i++) 3434 ptp->tx_mapped_regs[i] = 0x6000 + (ptp->tx_regs[i] & 0xfff); 3435 3436 return 0; 3437 } 3438 3439 static void bnxt_unmap_ptp_regs(struct bnxt *bp) 3440 { 3441 rte_write32(0, (uint8_t *)bp->bar0 + 3442 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 16); 3443 rte_write32(0, (uint8_t *)bp->bar0 + 3444 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 20); 3445 } 3446 3447 static uint64_t bnxt_cc_read(struct bnxt *bp) 3448 { 3449 uint64_t ns; 3450 3451 ns = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3452 BNXT_GRCPF_REG_SYNC_TIME)); 3453 ns |= (uint64_t)(rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3454 BNXT_GRCPF_REG_SYNC_TIME + 4))) << 32; 3455 return ns; 3456 } 3457 3458 static int bnxt_get_tx_ts(struct bnxt *bp, uint64_t *ts) 3459 { 3460 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3461 uint32_t fifo; 3462 3463 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3464 ptp->tx_mapped_regs[BNXT_PTP_TX_FIFO])); 3465 if (fifo & BNXT_PTP_TX_FIFO_EMPTY) 3466 return -EAGAIN; 3467 3468 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3469 ptp->tx_mapped_regs[BNXT_PTP_TX_FIFO])); 3470 *ts = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3471 ptp->tx_mapped_regs[BNXT_PTP_TX_TS_L])); 3472 *ts |= (uint64_t)rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3473 ptp->tx_mapped_regs[BNXT_PTP_TX_TS_H])) << 32; 3474 rte_read32((uint8_t *)bp->bar0 + ptp->tx_mapped_regs[BNXT_PTP_TX_SEQ]); 3475 3476 return 0; 3477 } 3478 3479 static int bnxt_clr_rx_ts(struct bnxt *bp, uint64_t *last_ts) 3480 { 3481 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3482 struct bnxt_pf_info *pf = bp->pf; 3483 uint16_t port_id; 3484 int i = 0; 3485 uint32_t fifo; 3486 3487 if (!ptp || (bp->flags & BNXT_FLAG_CHIP_P5)) 3488 return -EINVAL; 3489 3490 port_id = pf->port_id; 3491 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3492 ptp->rx_mapped_regs[BNXT_PTP_RX_FIFO])); 3493 while ((fifo & BNXT_PTP_RX_FIFO_PENDING) && (i < BNXT_PTP_RX_PND_CNT)) { 3494 rte_write32(1 << port_id, (uint8_t *)bp->bar0 + 3495 ptp->rx_mapped_regs[BNXT_PTP_RX_FIFO_ADV]); 3496 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3497 ptp->rx_mapped_regs[BNXT_PTP_RX_FIFO])); 3498 *last_ts = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3499 ptp->rx_mapped_regs[BNXT_PTP_RX_TS_L])); 3500 *last_ts |= (uint64_t)rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3501 ptp->rx_mapped_regs[BNXT_PTP_RX_TS_H])) << 32; 3502 i++; 3503 } 3504 3505 if (i >= BNXT_PTP_RX_PND_CNT) 3506 return -EBUSY; 3507 3508 return 0; 3509 } 3510 3511 static int bnxt_get_rx_ts(struct bnxt *bp, uint64_t *ts) 3512 { 3513 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3514 struct bnxt_pf_info *pf = bp->pf; 3515 uint16_t port_id; 3516 uint32_t fifo; 3517 3518 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3519 ptp->rx_mapped_regs[BNXT_PTP_RX_FIFO])); 3520 if (!(fifo & BNXT_PTP_RX_FIFO_PENDING)) 3521 return -EAGAIN; 3522 3523 port_id = pf->port_id; 3524 rte_write32(1 << port_id, (uint8_t *)bp->bar0 + 3525 ptp->rx_mapped_regs[BNXT_PTP_RX_FIFO_ADV]); 3526 3527 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3528 ptp->rx_mapped_regs[BNXT_PTP_RX_FIFO])); 3529 if (fifo & BNXT_PTP_RX_FIFO_PENDING) 3530 return bnxt_clr_rx_ts(bp, ts); 3531 3532 *ts = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3533 ptp->rx_mapped_regs[BNXT_PTP_RX_TS_L])); 3534 *ts |= (uint64_t)rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3535 ptp->rx_mapped_regs[BNXT_PTP_RX_TS_H])) << 32; 3536 3537 return 0; 3538 } 3539 3540 static int 3541 bnxt_timesync_write_time(struct rte_eth_dev *dev, const struct timespec *ts) 3542 { 3543 uint64_t ns; 3544 struct bnxt *bp = dev->data->dev_private; 3545 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3546 3547 if (!ptp) 3548 return -ENOTSUP; 3549 3550 ns = rte_timespec_to_ns(ts); 3551 /* Set the timecounters to a new value. */ 3552 ptp->tc.nsec = ns; 3553 ptp->tx_tstamp_tc.nsec = ns; 3554 ptp->rx_tstamp_tc.nsec = ns; 3555 3556 return 0; 3557 } 3558 3559 static int 3560 bnxt_timesync_read_time(struct rte_eth_dev *dev, struct timespec *ts) 3561 { 3562 struct bnxt *bp = dev->data->dev_private; 3563 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3564 uint64_t ns, systime_cycles = 0; 3565 int rc = 0; 3566 3567 if (!ptp) 3568 return -ENOTSUP; 3569 3570 if (BNXT_CHIP_P5(bp)) 3571 rc = bnxt_hwrm_port_ts_query(bp, BNXT_PTP_FLAGS_CURRENT_TIME, 3572 &systime_cycles); 3573 else 3574 systime_cycles = bnxt_cc_read(bp); 3575 3576 ns = rte_timecounter_update(&ptp->tc, systime_cycles); 3577 *ts = rte_ns_to_timespec(ns); 3578 3579 return rc; 3580 } 3581 static int 3582 bnxt_timesync_enable(struct rte_eth_dev *dev) 3583 { 3584 struct bnxt *bp = dev->data->dev_private; 3585 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3586 uint32_t shift = 0; 3587 int rc; 3588 3589 if (!ptp) 3590 return -ENOTSUP; 3591 3592 ptp->rx_filter = 1; 3593 ptp->tx_tstamp_en = 1; 3594 ptp->rxctl = BNXT_PTP_MSG_EVENTS; 3595 3596 rc = bnxt_hwrm_ptp_cfg(bp); 3597 if (rc) 3598 return rc; 3599 3600 memset(&ptp->tc, 0, sizeof(struct rte_timecounter)); 3601 memset(&ptp->rx_tstamp_tc, 0, sizeof(struct rte_timecounter)); 3602 memset(&ptp->tx_tstamp_tc, 0, sizeof(struct rte_timecounter)); 3603 3604 ptp->tc.cc_mask = BNXT_CYCLECOUNTER_MASK; 3605 ptp->tc.cc_shift = shift; 3606 ptp->tc.nsec_mask = (1ULL << shift) - 1; 3607 3608 ptp->rx_tstamp_tc.cc_mask = BNXT_CYCLECOUNTER_MASK; 3609 ptp->rx_tstamp_tc.cc_shift = shift; 3610 ptp->rx_tstamp_tc.nsec_mask = (1ULL << shift) - 1; 3611 3612 ptp->tx_tstamp_tc.cc_mask = BNXT_CYCLECOUNTER_MASK; 3613 ptp->tx_tstamp_tc.cc_shift = shift; 3614 ptp->tx_tstamp_tc.nsec_mask = (1ULL << shift) - 1; 3615 3616 if (!BNXT_CHIP_P5(bp)) 3617 bnxt_map_ptp_regs(bp); 3618 else 3619 rc = bnxt_ptp_start(bp); 3620 3621 return rc; 3622 } 3623 3624 static int 3625 bnxt_timesync_disable(struct rte_eth_dev *dev) 3626 { 3627 struct bnxt *bp = dev->data->dev_private; 3628 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3629 3630 if (!ptp) 3631 return -ENOTSUP; 3632 3633 ptp->rx_filter = 0; 3634 ptp->tx_tstamp_en = 0; 3635 ptp->rxctl = 0; 3636 3637 bnxt_hwrm_ptp_cfg(bp); 3638 3639 if (!BNXT_CHIP_P5(bp)) 3640 bnxt_unmap_ptp_regs(bp); 3641 else 3642 bnxt_ptp_stop(bp); 3643 3644 return 0; 3645 } 3646 3647 static int 3648 bnxt_timesync_read_rx_timestamp(struct rte_eth_dev *dev, 3649 struct timespec *timestamp, 3650 uint32_t flags __rte_unused) 3651 { 3652 struct bnxt *bp = dev->data->dev_private; 3653 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3654 uint64_t rx_tstamp_cycles = 0; 3655 uint64_t ns; 3656 3657 if (!ptp) 3658 return -ENOTSUP; 3659 3660 if (BNXT_CHIP_P5(bp)) 3661 rx_tstamp_cycles = ptp->rx_timestamp; 3662 else 3663 bnxt_get_rx_ts(bp, &rx_tstamp_cycles); 3664 3665 ns = rte_timecounter_update(&ptp->rx_tstamp_tc, rx_tstamp_cycles); 3666 *timestamp = rte_ns_to_timespec(ns); 3667 return 0; 3668 } 3669 3670 static int 3671 bnxt_timesync_read_tx_timestamp(struct rte_eth_dev *dev, 3672 struct timespec *timestamp) 3673 { 3674 struct bnxt *bp = dev->data->dev_private; 3675 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3676 uint64_t tx_tstamp_cycles = 0; 3677 uint64_t ns; 3678 int rc = 0; 3679 3680 if (!ptp) 3681 return -ENOTSUP; 3682 3683 if (BNXT_CHIP_P5(bp)) 3684 rc = bnxt_hwrm_port_ts_query(bp, BNXT_PTP_FLAGS_PATH_TX, 3685 &tx_tstamp_cycles); 3686 else 3687 rc = bnxt_get_tx_ts(bp, &tx_tstamp_cycles); 3688 3689 ns = rte_timecounter_update(&ptp->tx_tstamp_tc, tx_tstamp_cycles); 3690 *timestamp = rte_ns_to_timespec(ns); 3691 3692 return rc; 3693 } 3694 3695 static int 3696 bnxt_timesync_adjust_time(struct rte_eth_dev *dev, int64_t delta) 3697 { 3698 struct bnxt *bp = dev->data->dev_private; 3699 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3700 3701 if (!ptp) 3702 return -ENOTSUP; 3703 3704 ptp->tc.nsec += delta; 3705 ptp->tx_tstamp_tc.nsec += delta; 3706 ptp->rx_tstamp_tc.nsec += delta; 3707 3708 return 0; 3709 } 3710 3711 static int 3712 bnxt_get_eeprom_length_op(struct rte_eth_dev *dev) 3713 { 3714 struct bnxt *bp = dev->data->dev_private; 3715 int rc; 3716 uint32_t dir_entries; 3717 uint32_t entry_length; 3718 3719 rc = is_bnxt_in_error(bp); 3720 if (rc) 3721 return rc; 3722 3723 PMD_DRV_LOG(INFO, PCI_PRI_FMT "\n", 3724 bp->pdev->addr.domain, bp->pdev->addr.bus, 3725 bp->pdev->addr.devid, bp->pdev->addr.function); 3726 3727 rc = bnxt_hwrm_nvm_get_dir_info(bp, &dir_entries, &entry_length); 3728 if (rc != 0) 3729 return rc; 3730 3731 return dir_entries * entry_length; 3732 } 3733 3734 static int 3735 bnxt_get_eeprom_op(struct rte_eth_dev *dev, 3736 struct rte_dev_eeprom_info *in_eeprom) 3737 { 3738 struct bnxt *bp = dev->data->dev_private; 3739 uint32_t index; 3740 uint32_t offset; 3741 int rc; 3742 3743 rc = is_bnxt_in_error(bp); 3744 if (rc) 3745 return rc; 3746 3747 PMD_DRV_LOG(INFO, PCI_PRI_FMT " in_eeprom->offset = %d len = %d\n", 3748 bp->pdev->addr.domain, bp->pdev->addr.bus, 3749 bp->pdev->addr.devid, bp->pdev->addr.function, 3750 in_eeprom->offset, in_eeprom->length); 3751 3752 if (in_eeprom->offset == 0) /* special offset value to get directory */ 3753 return bnxt_get_nvram_directory(bp, in_eeprom->length, 3754 in_eeprom->data); 3755 3756 index = in_eeprom->offset >> 24; 3757 offset = in_eeprom->offset & 0xffffff; 3758 3759 if (index != 0) 3760 return bnxt_hwrm_get_nvram_item(bp, index - 1, offset, 3761 in_eeprom->length, in_eeprom->data); 3762 3763 return 0; 3764 } 3765 3766 static bool bnxt_dir_type_is_ape_bin_format(uint16_t dir_type) 3767 { 3768 switch (dir_type) { 3769 case BNX_DIR_TYPE_CHIMP_PATCH: 3770 case BNX_DIR_TYPE_BOOTCODE: 3771 case BNX_DIR_TYPE_BOOTCODE_2: 3772 case BNX_DIR_TYPE_APE_FW: 3773 case BNX_DIR_TYPE_APE_PATCH: 3774 case BNX_DIR_TYPE_KONG_FW: 3775 case BNX_DIR_TYPE_KONG_PATCH: 3776 case BNX_DIR_TYPE_BONO_FW: 3777 case BNX_DIR_TYPE_BONO_PATCH: 3778 /* FALLTHROUGH */ 3779 return true; 3780 } 3781 3782 return false; 3783 } 3784 3785 static bool bnxt_dir_type_is_other_exec_format(uint16_t dir_type) 3786 { 3787 switch (dir_type) { 3788 case BNX_DIR_TYPE_AVS: 3789 case BNX_DIR_TYPE_EXP_ROM_MBA: 3790 case BNX_DIR_TYPE_PCIE: 3791 case BNX_DIR_TYPE_TSCF_UCODE: 3792 case BNX_DIR_TYPE_EXT_PHY: 3793 case BNX_DIR_TYPE_CCM: 3794 case BNX_DIR_TYPE_ISCSI_BOOT: 3795 case BNX_DIR_TYPE_ISCSI_BOOT_IPV6: 3796 case BNX_DIR_TYPE_ISCSI_BOOT_IPV4N6: 3797 /* FALLTHROUGH */ 3798 return true; 3799 } 3800 3801 return false; 3802 } 3803 3804 static bool bnxt_dir_type_is_executable(uint16_t dir_type) 3805 { 3806 return bnxt_dir_type_is_ape_bin_format(dir_type) || 3807 bnxt_dir_type_is_other_exec_format(dir_type); 3808 } 3809 3810 static int 3811 bnxt_set_eeprom_op(struct rte_eth_dev *dev, 3812 struct rte_dev_eeprom_info *in_eeprom) 3813 { 3814 struct bnxt *bp = dev->data->dev_private; 3815 uint8_t index, dir_op; 3816 uint16_t type, ext, ordinal, attr; 3817 int rc; 3818 3819 rc = is_bnxt_in_error(bp); 3820 if (rc) 3821 return rc; 3822 3823 PMD_DRV_LOG(INFO, PCI_PRI_FMT " in_eeprom->offset = %d len = %d\n", 3824 bp->pdev->addr.domain, bp->pdev->addr.bus, 3825 bp->pdev->addr.devid, bp->pdev->addr.function, 3826 in_eeprom->offset, in_eeprom->length); 3827 3828 if (!BNXT_PF(bp)) { 3829 PMD_DRV_LOG(ERR, "NVM write not supported from a VF\n"); 3830 return -EINVAL; 3831 } 3832 3833 type = in_eeprom->magic >> 16; 3834 3835 if (type == 0xffff) { /* special value for directory operations */ 3836 index = in_eeprom->magic & 0xff; 3837 dir_op = in_eeprom->magic >> 8; 3838 if (index == 0) 3839 return -EINVAL; 3840 switch (dir_op) { 3841 case 0x0e: /* erase */ 3842 if (in_eeprom->offset != ~in_eeprom->magic) 3843 return -EINVAL; 3844 return bnxt_hwrm_erase_nvram_directory(bp, index - 1); 3845 default: 3846 return -EINVAL; 3847 } 3848 } 3849 3850 /* Create or re-write an NVM item: */ 3851 if (bnxt_dir_type_is_executable(type) == true) 3852 return -EOPNOTSUPP; 3853 ext = in_eeprom->magic & 0xffff; 3854 ordinal = in_eeprom->offset >> 16; 3855 attr = in_eeprom->offset & 0xffff; 3856 3857 return bnxt_hwrm_flash_nvram(bp, type, ordinal, ext, attr, 3858 in_eeprom->data, in_eeprom->length); 3859 } 3860 3861 /* 3862 * Initialization 3863 */ 3864 3865 static const struct eth_dev_ops bnxt_dev_ops = { 3866 .dev_infos_get = bnxt_dev_info_get_op, 3867 .dev_close = bnxt_dev_close_op, 3868 .dev_configure = bnxt_dev_configure_op, 3869 .dev_start = bnxt_dev_start_op, 3870 .dev_stop = bnxt_dev_stop_op, 3871 .dev_set_link_up = bnxt_dev_set_link_up_op, 3872 .dev_set_link_down = bnxt_dev_set_link_down_op, 3873 .stats_get = bnxt_stats_get_op, 3874 .stats_reset = bnxt_stats_reset_op, 3875 .rx_queue_setup = bnxt_rx_queue_setup_op, 3876 .rx_queue_release = bnxt_rx_queue_release_op, 3877 .tx_queue_setup = bnxt_tx_queue_setup_op, 3878 .tx_queue_release = bnxt_tx_queue_release_op, 3879 .rx_queue_intr_enable = bnxt_rx_queue_intr_enable_op, 3880 .rx_queue_intr_disable = bnxt_rx_queue_intr_disable_op, 3881 .reta_update = bnxt_reta_update_op, 3882 .reta_query = bnxt_reta_query_op, 3883 .rss_hash_update = bnxt_rss_hash_update_op, 3884 .rss_hash_conf_get = bnxt_rss_hash_conf_get_op, 3885 .link_update = bnxt_link_update_op, 3886 .promiscuous_enable = bnxt_promiscuous_enable_op, 3887 .promiscuous_disable = bnxt_promiscuous_disable_op, 3888 .allmulticast_enable = bnxt_allmulticast_enable_op, 3889 .allmulticast_disable = bnxt_allmulticast_disable_op, 3890 .mac_addr_add = bnxt_mac_addr_add_op, 3891 .mac_addr_remove = bnxt_mac_addr_remove_op, 3892 .flow_ctrl_get = bnxt_flow_ctrl_get_op, 3893 .flow_ctrl_set = bnxt_flow_ctrl_set_op, 3894 .udp_tunnel_port_add = bnxt_udp_tunnel_port_add_op, 3895 .udp_tunnel_port_del = bnxt_udp_tunnel_port_del_op, 3896 .vlan_filter_set = bnxt_vlan_filter_set_op, 3897 .vlan_offload_set = bnxt_vlan_offload_set_op, 3898 .vlan_tpid_set = bnxt_vlan_tpid_set_op, 3899 .vlan_pvid_set = bnxt_vlan_pvid_set_op, 3900 .mtu_set = bnxt_mtu_set_op, 3901 .mac_addr_set = bnxt_set_default_mac_addr_op, 3902 .xstats_get = bnxt_dev_xstats_get_op, 3903 .xstats_get_names = bnxt_dev_xstats_get_names_op, 3904 .xstats_reset = bnxt_dev_xstats_reset_op, 3905 .fw_version_get = bnxt_fw_version_get, 3906 .set_mc_addr_list = bnxt_dev_set_mc_addr_list_op, 3907 .rxq_info_get = bnxt_rxq_info_get_op, 3908 .txq_info_get = bnxt_txq_info_get_op, 3909 .rx_burst_mode_get = bnxt_rx_burst_mode_get, 3910 .tx_burst_mode_get = bnxt_tx_burst_mode_get, 3911 .dev_led_on = bnxt_dev_led_on_op, 3912 .dev_led_off = bnxt_dev_led_off_op, 3913 .rx_queue_start = bnxt_rx_queue_start, 3914 .rx_queue_stop = bnxt_rx_queue_stop, 3915 .tx_queue_start = bnxt_tx_queue_start, 3916 .tx_queue_stop = bnxt_tx_queue_stop, 3917 .flow_ops_get = bnxt_flow_ops_get_op, 3918 .dev_supported_ptypes_get = bnxt_dev_supported_ptypes_get_op, 3919 .get_eeprom_length = bnxt_get_eeprom_length_op, 3920 .get_eeprom = bnxt_get_eeprom_op, 3921 .set_eeprom = bnxt_set_eeprom_op, 3922 .timesync_enable = bnxt_timesync_enable, 3923 .timesync_disable = bnxt_timesync_disable, 3924 .timesync_read_time = bnxt_timesync_read_time, 3925 .timesync_write_time = bnxt_timesync_write_time, 3926 .timesync_adjust_time = bnxt_timesync_adjust_time, 3927 .timesync_read_rx_timestamp = bnxt_timesync_read_rx_timestamp, 3928 .timesync_read_tx_timestamp = bnxt_timesync_read_tx_timestamp, 3929 }; 3930 3931 static uint32_t bnxt_map_reset_regs(struct bnxt *bp, uint32_t reg) 3932 { 3933 uint32_t offset; 3934 3935 /* Only pre-map the reset GRC registers using window 3 */ 3936 rte_write32(reg & 0xfffff000, (uint8_t *)bp->bar0 + 3937 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 8); 3938 3939 offset = BNXT_GRCP_WINDOW_3_BASE + (reg & 0xffc); 3940 3941 return offset; 3942 } 3943 3944 int bnxt_map_fw_health_status_regs(struct bnxt *bp) 3945 { 3946 struct bnxt_error_recovery_info *info = bp->recovery_info; 3947 uint32_t reg_base = 0xffffffff; 3948 int i; 3949 3950 /* Only pre-map the monitoring GRC registers using window 2 */ 3951 for (i = 0; i < BNXT_FW_STATUS_REG_CNT; i++) { 3952 uint32_t reg = info->status_regs[i]; 3953 3954 if (BNXT_FW_STATUS_REG_TYPE(reg) != BNXT_FW_STATUS_REG_TYPE_GRC) 3955 continue; 3956 3957 if (reg_base == 0xffffffff) 3958 reg_base = reg & 0xfffff000; 3959 if ((reg & 0xfffff000) != reg_base) 3960 return -ERANGE; 3961 3962 /* Use mask 0xffc as the Lower 2 bits indicates 3963 * address space location 3964 */ 3965 info->mapped_status_regs[i] = BNXT_GRCP_WINDOW_2_BASE + 3966 (reg & 0xffc); 3967 } 3968 3969 if (reg_base == 0xffffffff) 3970 return 0; 3971 3972 rte_write32(reg_base, (uint8_t *)bp->bar0 + 3973 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 4); 3974 3975 return 0; 3976 } 3977 3978 static void bnxt_write_fw_reset_reg(struct bnxt *bp, uint32_t index) 3979 { 3980 struct bnxt_error_recovery_info *info = bp->recovery_info; 3981 uint32_t delay = info->delay_after_reset[index]; 3982 uint32_t val = info->reset_reg_val[index]; 3983 uint32_t reg = info->reset_reg[index]; 3984 uint32_t type, offset; 3985 int ret; 3986 3987 type = BNXT_FW_STATUS_REG_TYPE(reg); 3988 offset = BNXT_FW_STATUS_REG_OFF(reg); 3989 3990 switch (type) { 3991 case BNXT_FW_STATUS_REG_TYPE_CFG: 3992 ret = rte_pci_write_config(bp->pdev, &val, sizeof(val), offset); 3993 if (ret < 0) { 3994 PMD_DRV_LOG(ERR, "Failed to write %#x at PCI offset %#x", 3995 val, offset); 3996 return; 3997 } 3998 break; 3999 case BNXT_FW_STATUS_REG_TYPE_GRC: 4000 offset = bnxt_map_reset_regs(bp, offset); 4001 rte_write32(val, (uint8_t *)bp->bar0 + offset); 4002 break; 4003 case BNXT_FW_STATUS_REG_TYPE_BAR0: 4004 rte_write32(val, (uint8_t *)bp->bar0 + offset); 4005 break; 4006 } 4007 /* wait on a specific interval of time until core reset is complete */ 4008 if (delay) 4009 rte_delay_ms(delay); 4010 } 4011 4012 static void bnxt_dev_cleanup(struct bnxt *bp) 4013 { 4014 bp->eth_dev->data->dev_link.link_status = 0; 4015 bp->link_info->link_up = 0; 4016 if (bp->eth_dev->data->dev_started) 4017 bnxt_dev_stop(bp->eth_dev); 4018 4019 bnxt_uninit_resources(bp, true); 4020 } 4021 4022 static int 4023 bnxt_check_fw_reset_done(struct bnxt *bp) 4024 { 4025 int timeout = bp->fw_reset_max_msecs; 4026 uint16_t val = 0; 4027 int rc; 4028 4029 do { 4030 rc = rte_pci_read_config(bp->pdev, &val, sizeof(val), PCI_SUBSYSTEM_ID_OFFSET); 4031 if (rc < 0) { 4032 PMD_DRV_LOG(ERR, "Failed to read PCI offset 0x%x", PCI_SUBSYSTEM_ID_OFFSET); 4033 return rc; 4034 } 4035 if (val != 0xffff) 4036 break; 4037 rte_delay_ms(1); 4038 } while (timeout--); 4039 4040 if (val == 0xffff) { 4041 PMD_DRV_LOG(ERR, "Firmware reset aborted, PCI config space invalid\n"); 4042 return -1; 4043 } 4044 4045 return 0; 4046 } 4047 4048 static int bnxt_restore_vlan_filters(struct bnxt *bp) 4049 { 4050 struct rte_eth_dev *dev = bp->eth_dev; 4051 struct rte_vlan_filter_conf *vfc; 4052 int vidx, vbit, rc; 4053 uint16_t vlan_id; 4054 4055 for (vlan_id = 1; vlan_id <= RTE_ETHER_MAX_VLAN_ID; vlan_id++) { 4056 vfc = &dev->data->vlan_filter_conf; 4057 vidx = vlan_id / 64; 4058 vbit = vlan_id % 64; 4059 4060 /* Each bit corresponds to a VLAN id */ 4061 if (vfc->ids[vidx] & (UINT64_C(1) << vbit)) { 4062 rc = bnxt_add_vlan_filter(bp, vlan_id); 4063 if (rc) 4064 return rc; 4065 } 4066 } 4067 4068 return 0; 4069 } 4070 4071 static int bnxt_restore_mac_filters(struct bnxt *bp) 4072 { 4073 struct rte_eth_dev *dev = bp->eth_dev; 4074 struct rte_eth_dev_info dev_info; 4075 struct rte_ether_addr *addr; 4076 uint64_t pool_mask; 4077 uint32_t pool = 0; 4078 uint32_t i; 4079 int rc; 4080 4081 if (BNXT_VF(bp) && !BNXT_VF_IS_TRUSTED(bp)) 4082 return 0; 4083 4084 rc = bnxt_dev_info_get_op(dev, &dev_info); 4085 if (rc) 4086 return rc; 4087 4088 /* replay MAC address configuration */ 4089 for (i = 1; i < dev_info.max_mac_addrs; i++) { 4090 addr = &dev->data->mac_addrs[i]; 4091 4092 /* skip zero address */ 4093 if (rte_is_zero_ether_addr(addr)) 4094 continue; 4095 4096 pool = 0; 4097 pool_mask = dev->data->mac_pool_sel[i]; 4098 4099 do { 4100 if (pool_mask & 1ULL) { 4101 rc = bnxt_mac_addr_add_op(dev, addr, i, pool); 4102 if (rc) 4103 return rc; 4104 } 4105 pool_mask >>= 1; 4106 pool++; 4107 } while (pool_mask); 4108 } 4109 4110 return 0; 4111 } 4112 4113 static int bnxt_restore_filters(struct bnxt *bp) 4114 { 4115 struct rte_eth_dev *dev = bp->eth_dev; 4116 int ret = 0; 4117 4118 if (dev->data->all_multicast) { 4119 ret = bnxt_allmulticast_enable_op(dev); 4120 if (ret) 4121 return ret; 4122 } 4123 if (dev->data->promiscuous) { 4124 ret = bnxt_promiscuous_enable_op(dev); 4125 if (ret) 4126 return ret; 4127 } 4128 4129 ret = bnxt_restore_mac_filters(bp); 4130 if (ret) 4131 return ret; 4132 4133 ret = bnxt_restore_vlan_filters(bp); 4134 /* TODO restore other filters as well */ 4135 return ret; 4136 } 4137 4138 static int bnxt_check_fw_ready(struct bnxt *bp) 4139 { 4140 int timeout = bp->fw_reset_max_msecs; 4141 int rc = 0; 4142 4143 do { 4144 rc = bnxt_hwrm_poll_ver_get(bp); 4145 if (rc == 0) 4146 break; 4147 rte_delay_ms(BNXT_FW_READY_WAIT_INTERVAL); 4148 timeout -= BNXT_FW_READY_WAIT_INTERVAL; 4149 } while (rc && timeout > 0); 4150 4151 if (rc) 4152 PMD_DRV_LOG(ERR, "FW is not Ready after reset\n"); 4153 4154 return rc; 4155 } 4156 4157 static void bnxt_dev_recover(void *arg) 4158 { 4159 struct bnxt *bp = arg; 4160 int rc = 0; 4161 4162 pthread_mutex_lock(&bp->err_recovery_lock); 4163 4164 if (!bp->fw_reset_min_msecs) { 4165 rc = bnxt_check_fw_reset_done(bp); 4166 if (rc) 4167 goto err; 4168 } 4169 4170 /* Clear Error flag so that device re-init should happen */ 4171 bp->flags &= ~BNXT_FLAG_FATAL_ERROR; 4172 4173 rc = bnxt_check_fw_ready(bp); 4174 if (rc) 4175 goto err; 4176 4177 rc = bnxt_init_resources(bp, true); 4178 if (rc) { 4179 PMD_DRV_LOG(ERR, 4180 "Failed to initialize resources after reset\n"); 4181 goto err; 4182 } 4183 /* clear reset flag as the device is initialized now */ 4184 bp->flags &= ~BNXT_FLAG_FW_RESET; 4185 4186 rc = bnxt_dev_start_op(bp->eth_dev); 4187 if (rc) { 4188 PMD_DRV_LOG(ERR, "Failed to start port after reset\n"); 4189 goto err_start; 4190 } 4191 4192 rc = bnxt_restore_filters(bp); 4193 if (rc) 4194 goto err_start; 4195 4196 PMD_DRV_LOG(INFO, "Recovered from FW reset\n"); 4197 pthread_mutex_unlock(&bp->err_recovery_lock); 4198 4199 return; 4200 err_start: 4201 bnxt_dev_stop(bp->eth_dev); 4202 err: 4203 bp->flags |= BNXT_FLAG_FATAL_ERROR; 4204 bnxt_uninit_resources(bp, false); 4205 pthread_mutex_unlock(&bp->err_recovery_lock); 4206 PMD_DRV_LOG(ERR, "Failed to recover from FW reset\n"); 4207 } 4208 4209 void bnxt_dev_reset_and_resume(void *arg) 4210 { 4211 struct bnxt *bp = arg; 4212 uint32_t us = US_PER_MS * bp->fw_reset_min_msecs; 4213 uint16_t val = 0; 4214 int rc; 4215 4216 bnxt_dev_cleanup(bp); 4217 4218 bnxt_wait_for_device_shutdown(bp); 4219 4220 /* During some fatal firmware error conditions, the PCI config space 4221 * register 0x2e which normally contains the subsystem ID will become 4222 * 0xffff. This register will revert back to the normal value after 4223 * the chip has completed core reset. If we detect this condition, 4224 * we can poll this config register immediately for the value to revert. 4225 */ 4226 if (bp->flags & BNXT_FLAG_FATAL_ERROR) { 4227 rc = rte_pci_read_config(bp->pdev, &val, sizeof(val), PCI_SUBSYSTEM_ID_OFFSET); 4228 if (rc < 0) { 4229 PMD_DRV_LOG(ERR, "Failed to read PCI offset 0x%x", PCI_SUBSYSTEM_ID_OFFSET); 4230 return; 4231 } 4232 if (val == 0xffff) { 4233 bp->fw_reset_min_msecs = 0; 4234 us = 1; 4235 } 4236 } 4237 4238 rc = rte_eal_alarm_set(us, bnxt_dev_recover, (void *)bp); 4239 if (rc) 4240 PMD_DRV_LOG(ERR, "Error setting recovery alarm"); 4241 } 4242 4243 uint32_t bnxt_read_fw_status_reg(struct bnxt *bp, uint32_t index) 4244 { 4245 struct bnxt_error_recovery_info *info = bp->recovery_info; 4246 uint32_t reg = info->status_regs[index]; 4247 uint32_t type, offset, val = 0; 4248 int ret = 0; 4249 4250 type = BNXT_FW_STATUS_REG_TYPE(reg); 4251 offset = BNXT_FW_STATUS_REG_OFF(reg); 4252 4253 switch (type) { 4254 case BNXT_FW_STATUS_REG_TYPE_CFG: 4255 ret = rte_pci_read_config(bp->pdev, &val, sizeof(val), offset); 4256 if (ret < 0) 4257 PMD_DRV_LOG(ERR, "Failed to read PCI offset %#x", 4258 offset); 4259 break; 4260 case BNXT_FW_STATUS_REG_TYPE_GRC: 4261 offset = info->mapped_status_regs[index]; 4262 /* FALLTHROUGH */ 4263 case BNXT_FW_STATUS_REG_TYPE_BAR0: 4264 val = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 4265 offset)); 4266 break; 4267 } 4268 4269 return val; 4270 } 4271 4272 static int bnxt_fw_reset_all(struct bnxt *bp) 4273 { 4274 struct bnxt_error_recovery_info *info = bp->recovery_info; 4275 uint32_t i; 4276 int rc = 0; 4277 4278 if (info->flags & BNXT_FLAG_ERROR_RECOVERY_HOST) { 4279 /* Reset through master function driver */ 4280 for (i = 0; i < info->reg_array_cnt; i++) 4281 bnxt_write_fw_reset_reg(bp, i); 4282 /* Wait for time specified by FW after triggering reset */ 4283 rte_delay_ms(info->master_func_wait_period_after_reset); 4284 } else if (info->flags & BNXT_FLAG_ERROR_RECOVERY_CO_CPU) { 4285 /* Reset with the help of Kong processor */ 4286 rc = bnxt_hwrm_fw_reset(bp); 4287 if (rc) 4288 PMD_DRV_LOG(ERR, "Failed to reset FW\n"); 4289 } 4290 4291 return rc; 4292 } 4293 4294 static void bnxt_fw_reset_cb(void *arg) 4295 { 4296 struct bnxt *bp = arg; 4297 struct bnxt_error_recovery_info *info = bp->recovery_info; 4298 int rc = 0; 4299 4300 /* Only Master function can do FW reset */ 4301 if (bnxt_is_master_func(bp) && 4302 bnxt_is_recovery_enabled(bp)) { 4303 rc = bnxt_fw_reset_all(bp); 4304 if (rc) { 4305 PMD_DRV_LOG(ERR, "Adapter recovery failed\n"); 4306 return; 4307 } 4308 } 4309 4310 /* if recovery method is ERROR_RECOVERY_CO_CPU, KONG will send 4311 * EXCEPTION_FATAL_ASYNC event to all the functions 4312 * (including MASTER FUNC). After receiving this Async, all the active 4313 * drivers should treat this case as FW initiated recovery 4314 */ 4315 if (info->flags & BNXT_FLAG_ERROR_RECOVERY_HOST) { 4316 bp->fw_reset_min_msecs = BNXT_MIN_FW_READY_TIMEOUT; 4317 bp->fw_reset_max_msecs = BNXT_MAX_FW_RESET_TIMEOUT; 4318 4319 /* To recover from error */ 4320 rte_eal_alarm_set(US_PER_MS, bnxt_dev_reset_and_resume, 4321 (void *)bp); 4322 } 4323 } 4324 4325 /* Driver should poll FW heartbeat, reset_counter with the frequency 4326 * advertised by FW in HWRM_ERROR_RECOVERY_QCFG. 4327 * When the driver detects heartbeat stop or change in reset_counter, 4328 * it has to trigger a reset to recover from the error condition. 4329 * A “master PF” is the function who will have the privilege to 4330 * initiate the chimp reset. The master PF will be elected by the 4331 * firmware and will be notified through async message. 4332 */ 4333 static void bnxt_check_fw_health(void *arg) 4334 { 4335 struct bnxt *bp = arg; 4336 struct bnxt_error_recovery_info *info = bp->recovery_info; 4337 uint32_t val = 0, wait_msec; 4338 4339 if (!info || !bnxt_is_recovery_enabled(bp) || 4340 is_bnxt_in_error(bp)) 4341 return; 4342 4343 val = bnxt_read_fw_status_reg(bp, BNXT_FW_HEARTBEAT_CNT_REG); 4344 if (val == info->last_heart_beat) 4345 goto reset; 4346 4347 info->last_heart_beat = val; 4348 4349 val = bnxt_read_fw_status_reg(bp, BNXT_FW_RECOVERY_CNT_REG); 4350 if (val != info->last_reset_counter) 4351 goto reset; 4352 4353 info->last_reset_counter = val; 4354 4355 rte_eal_alarm_set(US_PER_MS * info->driver_polling_freq, 4356 bnxt_check_fw_health, (void *)bp); 4357 4358 return; 4359 reset: 4360 /* Stop DMA to/from device */ 4361 bp->flags |= BNXT_FLAG_FATAL_ERROR; 4362 bp->flags |= BNXT_FLAG_FW_RESET; 4363 4364 bnxt_stop_rxtx(bp); 4365 4366 PMD_DRV_LOG(ERR, "Detected FW dead condition\n"); 4367 4368 if (bnxt_is_master_func(bp)) 4369 wait_msec = info->master_func_wait_period; 4370 else 4371 wait_msec = info->normal_func_wait_period; 4372 4373 rte_eal_alarm_set(US_PER_MS * wait_msec, 4374 bnxt_fw_reset_cb, (void *)bp); 4375 } 4376 4377 void bnxt_schedule_fw_health_check(struct bnxt *bp) 4378 { 4379 uint32_t polling_freq; 4380 4381 pthread_mutex_lock(&bp->health_check_lock); 4382 4383 if (!bnxt_is_recovery_enabled(bp)) 4384 goto done; 4385 4386 if (bp->flags & BNXT_FLAG_FW_HEALTH_CHECK_SCHEDULED) 4387 goto done; 4388 4389 polling_freq = bp->recovery_info->driver_polling_freq; 4390 4391 rte_eal_alarm_set(US_PER_MS * polling_freq, 4392 bnxt_check_fw_health, (void *)bp); 4393 bp->flags |= BNXT_FLAG_FW_HEALTH_CHECK_SCHEDULED; 4394 4395 done: 4396 pthread_mutex_unlock(&bp->health_check_lock); 4397 } 4398 4399 static void bnxt_cancel_fw_health_check(struct bnxt *bp) 4400 { 4401 rte_eal_alarm_cancel(bnxt_check_fw_health, (void *)bp); 4402 bp->flags &= ~BNXT_FLAG_FW_HEALTH_CHECK_SCHEDULED; 4403 } 4404 4405 static bool bnxt_vf_pciid(uint16_t device_id) 4406 { 4407 switch (device_id) { 4408 case BROADCOM_DEV_ID_57304_VF: 4409 case BROADCOM_DEV_ID_57406_VF: 4410 case BROADCOM_DEV_ID_5731X_VF: 4411 case BROADCOM_DEV_ID_5741X_VF: 4412 case BROADCOM_DEV_ID_57414_VF: 4413 case BROADCOM_DEV_ID_STRATUS_NIC_VF1: 4414 case BROADCOM_DEV_ID_STRATUS_NIC_VF2: 4415 case BROADCOM_DEV_ID_58802_VF: 4416 case BROADCOM_DEV_ID_57500_VF1: 4417 case BROADCOM_DEV_ID_57500_VF2: 4418 case BROADCOM_DEV_ID_58818_VF: 4419 /* FALLTHROUGH */ 4420 return true; 4421 default: 4422 return false; 4423 } 4424 } 4425 4426 /* Phase 5 device */ 4427 static bool bnxt_p5_device(uint16_t device_id) 4428 { 4429 switch (device_id) { 4430 case BROADCOM_DEV_ID_57508: 4431 case BROADCOM_DEV_ID_57504: 4432 case BROADCOM_DEV_ID_57502: 4433 case BROADCOM_DEV_ID_57508_MF1: 4434 case BROADCOM_DEV_ID_57504_MF1: 4435 case BROADCOM_DEV_ID_57502_MF1: 4436 case BROADCOM_DEV_ID_57508_MF2: 4437 case BROADCOM_DEV_ID_57504_MF2: 4438 case BROADCOM_DEV_ID_57502_MF2: 4439 case BROADCOM_DEV_ID_57500_VF1: 4440 case BROADCOM_DEV_ID_57500_VF2: 4441 case BROADCOM_DEV_ID_58812: 4442 case BROADCOM_DEV_ID_58814: 4443 case BROADCOM_DEV_ID_58818: 4444 case BROADCOM_DEV_ID_58818_VF: 4445 /* FALLTHROUGH */ 4446 return true; 4447 default: 4448 return false; 4449 } 4450 } 4451 4452 bool bnxt_stratus_device(struct bnxt *bp) 4453 { 4454 uint16_t device_id = bp->pdev->id.device_id; 4455 4456 switch (device_id) { 4457 case BROADCOM_DEV_ID_STRATUS_NIC: 4458 case BROADCOM_DEV_ID_STRATUS_NIC_VF1: 4459 case BROADCOM_DEV_ID_STRATUS_NIC_VF2: 4460 /* FALLTHROUGH */ 4461 return true; 4462 default: 4463 return false; 4464 } 4465 } 4466 4467 static int bnxt_map_pci_bars(struct rte_eth_dev *eth_dev) 4468 { 4469 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(eth_dev); 4470 struct bnxt *bp = eth_dev->data->dev_private; 4471 4472 /* enable device (incl. PCI PM wakeup), and bus-mastering */ 4473 bp->bar0 = (void *)pci_dev->mem_resource[0].addr; 4474 bp->doorbell_base = (void *)pci_dev->mem_resource[2].addr; 4475 if (!bp->bar0 || !bp->doorbell_base) { 4476 PMD_DRV_LOG(ERR, "Unable to access Hardware\n"); 4477 return -ENODEV; 4478 } 4479 4480 bp->eth_dev = eth_dev; 4481 bp->pdev = pci_dev; 4482 4483 return 0; 4484 } 4485 4486 static int bnxt_alloc_ctx_mem_blk(struct bnxt *bp, 4487 struct bnxt_ctx_pg_info *ctx_pg, 4488 uint32_t mem_size, 4489 const char *suffix, 4490 uint16_t idx) 4491 { 4492 struct bnxt_ring_mem_info *rmem = &ctx_pg->ring_mem; 4493 const struct rte_memzone *mz = NULL; 4494 char mz_name[RTE_MEMZONE_NAMESIZE]; 4495 rte_iova_t mz_phys_addr; 4496 uint64_t valid_bits = 0; 4497 uint32_t sz; 4498 int i; 4499 4500 if (!mem_size) 4501 return 0; 4502 4503 rmem->nr_pages = RTE_ALIGN_MUL_CEIL(mem_size, BNXT_PAGE_SIZE) / 4504 BNXT_PAGE_SIZE; 4505 rmem->page_size = BNXT_PAGE_SIZE; 4506 rmem->pg_arr = ctx_pg->ctx_pg_arr; 4507 rmem->dma_arr = ctx_pg->ctx_dma_arr; 4508 rmem->flags = BNXT_RMEM_VALID_PTE_FLAG; 4509 4510 valid_bits = PTU_PTE_VALID; 4511 4512 if (rmem->nr_pages > 1) { 4513 snprintf(mz_name, RTE_MEMZONE_NAMESIZE, 4514 "bnxt_ctx_pg_tbl%s_%x_%d", 4515 suffix, idx, bp->eth_dev->data->port_id); 4516 mz_name[RTE_MEMZONE_NAMESIZE - 1] = 0; 4517 mz = rte_memzone_lookup(mz_name); 4518 if (!mz) { 4519 mz = rte_memzone_reserve_aligned(mz_name, 4520 rmem->nr_pages * 8, 4521 SOCKET_ID_ANY, 4522 RTE_MEMZONE_2MB | 4523 RTE_MEMZONE_SIZE_HINT_ONLY | 4524 RTE_MEMZONE_IOVA_CONTIG, 4525 BNXT_PAGE_SIZE); 4526 if (mz == NULL) 4527 return -ENOMEM; 4528 } 4529 4530 memset(mz->addr, 0, mz->len); 4531 mz_phys_addr = mz->iova; 4532 4533 rmem->pg_tbl = mz->addr; 4534 rmem->pg_tbl_map = mz_phys_addr; 4535 rmem->pg_tbl_mz = mz; 4536 } 4537 4538 snprintf(mz_name, RTE_MEMZONE_NAMESIZE, "bnxt_ctx_%s_%x_%d", 4539 suffix, idx, bp->eth_dev->data->port_id); 4540 mz = rte_memzone_lookup(mz_name); 4541 if (!mz) { 4542 mz = rte_memzone_reserve_aligned(mz_name, 4543 mem_size, 4544 SOCKET_ID_ANY, 4545 RTE_MEMZONE_1GB | 4546 RTE_MEMZONE_SIZE_HINT_ONLY | 4547 RTE_MEMZONE_IOVA_CONTIG, 4548 BNXT_PAGE_SIZE); 4549 if (mz == NULL) 4550 return -ENOMEM; 4551 } 4552 4553 memset(mz->addr, 0, mz->len); 4554 mz_phys_addr = mz->iova; 4555 4556 for (sz = 0, i = 0; sz < mem_size; sz += BNXT_PAGE_SIZE, i++) { 4557 rmem->pg_arr[i] = ((char *)mz->addr) + sz; 4558 rmem->dma_arr[i] = mz_phys_addr + sz; 4559 4560 if (rmem->nr_pages > 1) { 4561 if (i == rmem->nr_pages - 2 && 4562 (rmem->flags & BNXT_RMEM_RING_PTE_FLAG)) 4563 valid_bits |= PTU_PTE_NEXT_TO_LAST; 4564 else if (i == rmem->nr_pages - 1 && 4565 (rmem->flags & BNXT_RMEM_RING_PTE_FLAG)) 4566 valid_bits |= PTU_PTE_LAST; 4567 4568 rmem->pg_tbl[i] = rte_cpu_to_le_64(rmem->dma_arr[i] | 4569 valid_bits); 4570 } 4571 } 4572 4573 rmem->mz = mz; 4574 if (rmem->vmem_size) 4575 rmem->vmem = (void **)mz->addr; 4576 rmem->dma_arr[0] = mz_phys_addr; 4577 return 0; 4578 } 4579 4580 static void bnxt_free_ctx_mem(struct bnxt *bp) 4581 { 4582 int i; 4583 4584 if (!bp->ctx || !(bp->ctx->flags & BNXT_CTX_FLAG_INITED)) 4585 return; 4586 4587 bp->ctx->flags &= ~BNXT_CTX_FLAG_INITED; 4588 rte_memzone_free(bp->ctx->qp_mem.ring_mem.mz); 4589 rte_memzone_free(bp->ctx->srq_mem.ring_mem.mz); 4590 rte_memzone_free(bp->ctx->cq_mem.ring_mem.mz); 4591 rte_memzone_free(bp->ctx->vnic_mem.ring_mem.mz); 4592 rte_memzone_free(bp->ctx->stat_mem.ring_mem.mz); 4593 rte_memzone_free(bp->ctx->qp_mem.ring_mem.pg_tbl_mz); 4594 rte_memzone_free(bp->ctx->srq_mem.ring_mem.pg_tbl_mz); 4595 rte_memzone_free(bp->ctx->cq_mem.ring_mem.pg_tbl_mz); 4596 rte_memzone_free(bp->ctx->vnic_mem.ring_mem.pg_tbl_mz); 4597 rte_memzone_free(bp->ctx->stat_mem.ring_mem.pg_tbl_mz); 4598 4599 for (i = 0; i < bp->ctx->tqm_fp_rings_count + 1; i++) { 4600 if (bp->ctx->tqm_mem[i]) 4601 rte_memzone_free(bp->ctx->tqm_mem[i]->ring_mem.mz); 4602 } 4603 4604 rte_free(bp->ctx); 4605 bp->ctx = NULL; 4606 } 4607 4608 #define bnxt_roundup(x, y) ((((x) + ((y) - 1)) / (y)) * (y)) 4609 4610 #define min_t(type, x, y) ({ \ 4611 type __min1 = (x); \ 4612 type __min2 = (y); \ 4613 __min1 < __min2 ? __min1 : __min2; }) 4614 4615 #define max_t(type, x, y) ({ \ 4616 type __max1 = (x); \ 4617 type __max2 = (y); \ 4618 __max1 > __max2 ? __max1 : __max2; }) 4619 4620 #define clamp_t(type, _x, min, max) min_t(type, max_t(type, _x, min), max) 4621 4622 int bnxt_alloc_ctx_mem(struct bnxt *bp) 4623 { 4624 struct bnxt_ctx_pg_info *ctx_pg; 4625 struct bnxt_ctx_mem_info *ctx; 4626 uint32_t mem_size, ena, entries; 4627 uint32_t entries_sp, min; 4628 int i, rc; 4629 4630 rc = bnxt_hwrm_func_backing_store_qcaps(bp); 4631 if (rc) { 4632 PMD_DRV_LOG(ERR, "Query context mem capability failed\n"); 4633 return rc; 4634 } 4635 ctx = bp->ctx; 4636 if (!ctx || (ctx->flags & BNXT_CTX_FLAG_INITED)) 4637 return 0; 4638 4639 ctx_pg = &ctx->qp_mem; 4640 ctx_pg->entries = ctx->qp_min_qp1_entries + ctx->qp_max_l2_entries; 4641 if (ctx->qp_entry_size) { 4642 mem_size = ctx->qp_entry_size * ctx_pg->entries; 4643 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "qp_mem", 0); 4644 if (rc) 4645 return rc; 4646 } 4647 4648 ctx_pg = &ctx->srq_mem; 4649 ctx_pg->entries = ctx->srq_max_l2_entries; 4650 if (ctx->srq_entry_size) { 4651 mem_size = ctx->srq_entry_size * ctx_pg->entries; 4652 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "srq_mem", 0); 4653 if (rc) 4654 return rc; 4655 } 4656 4657 ctx_pg = &ctx->cq_mem; 4658 ctx_pg->entries = ctx->cq_max_l2_entries; 4659 if (ctx->cq_entry_size) { 4660 mem_size = ctx->cq_entry_size * ctx_pg->entries; 4661 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "cq_mem", 0); 4662 if (rc) 4663 return rc; 4664 } 4665 4666 ctx_pg = &ctx->vnic_mem; 4667 ctx_pg->entries = ctx->vnic_max_vnic_entries + 4668 ctx->vnic_max_ring_table_entries; 4669 if (ctx->vnic_entry_size) { 4670 mem_size = ctx->vnic_entry_size * ctx_pg->entries; 4671 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "vnic_mem", 0); 4672 if (rc) 4673 return rc; 4674 } 4675 4676 ctx_pg = &ctx->stat_mem; 4677 ctx_pg->entries = ctx->stat_max_entries; 4678 if (ctx->stat_entry_size) { 4679 mem_size = ctx->stat_entry_size * ctx_pg->entries; 4680 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "stat_mem", 0); 4681 if (rc) 4682 return rc; 4683 } 4684 4685 min = ctx->tqm_min_entries_per_ring; 4686 4687 entries_sp = ctx->qp_max_l2_entries + 4688 ctx->vnic_max_vnic_entries + 4689 2 * ctx->qp_min_qp1_entries + min; 4690 entries_sp = bnxt_roundup(entries_sp, ctx->tqm_entries_multiple); 4691 4692 entries = ctx->qp_max_l2_entries + ctx->qp_min_qp1_entries; 4693 entries = bnxt_roundup(entries, ctx->tqm_entries_multiple); 4694 entries = clamp_t(uint32_t, entries, min, 4695 ctx->tqm_max_entries_per_ring); 4696 for (i = 0, ena = 0; i < ctx->tqm_fp_rings_count + 1; i++) { 4697 /* i=0 is for TQM_SP. i=1 to i=8 applies to RING0 to RING7. 4698 * i > 8 is other ext rings. 4699 */ 4700 ctx_pg = ctx->tqm_mem[i]; 4701 ctx_pg->entries = i ? entries : entries_sp; 4702 if (ctx->tqm_entry_size) { 4703 mem_size = ctx->tqm_entry_size * ctx_pg->entries; 4704 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, 4705 "tqm_mem", i); 4706 if (rc) 4707 return rc; 4708 } 4709 if (i < BNXT_MAX_TQM_LEGACY_RINGS) 4710 ena |= HWRM_FUNC_BACKING_STORE_CFG_INPUT_ENABLES_TQM_SP << i; 4711 else 4712 ena |= HWRM_FUNC_BACKING_STORE_CFG_INPUT_ENABLES_TQM_RING8; 4713 } 4714 4715 ena |= FUNC_BACKING_STORE_CFG_INPUT_DFLT_ENABLES; 4716 rc = bnxt_hwrm_func_backing_store_cfg(bp, ena); 4717 if (rc) 4718 PMD_DRV_LOG(ERR, 4719 "Failed to configure context mem: rc = %d\n", rc); 4720 else 4721 ctx->flags |= BNXT_CTX_FLAG_INITED; 4722 4723 return rc; 4724 } 4725 4726 static int bnxt_alloc_stats_mem(struct bnxt *bp) 4727 { 4728 struct rte_pci_device *pci_dev = bp->pdev; 4729 char mz_name[RTE_MEMZONE_NAMESIZE]; 4730 const struct rte_memzone *mz = NULL; 4731 uint32_t total_alloc_len; 4732 rte_iova_t mz_phys_addr; 4733 4734 if (pci_dev->id.device_id == BROADCOM_DEV_ID_NS2) 4735 return 0; 4736 4737 snprintf(mz_name, RTE_MEMZONE_NAMESIZE, 4738 "bnxt_" PCI_PRI_FMT "-%s", pci_dev->addr.domain, 4739 pci_dev->addr.bus, pci_dev->addr.devid, 4740 pci_dev->addr.function, "rx_port_stats"); 4741 mz_name[RTE_MEMZONE_NAMESIZE - 1] = 0; 4742 mz = rte_memzone_lookup(mz_name); 4743 total_alloc_len = 4744 RTE_CACHE_LINE_ROUNDUP(sizeof(struct rx_port_stats) + 4745 sizeof(struct rx_port_stats_ext) + 512); 4746 if (!mz) { 4747 mz = rte_memzone_reserve(mz_name, total_alloc_len, 4748 SOCKET_ID_ANY, 4749 RTE_MEMZONE_2MB | 4750 RTE_MEMZONE_SIZE_HINT_ONLY | 4751 RTE_MEMZONE_IOVA_CONTIG); 4752 if (mz == NULL) 4753 return -ENOMEM; 4754 } 4755 memset(mz->addr, 0, mz->len); 4756 mz_phys_addr = mz->iova; 4757 4758 bp->rx_mem_zone = (const void *)mz; 4759 bp->hw_rx_port_stats = mz->addr; 4760 bp->hw_rx_port_stats_map = mz_phys_addr; 4761 4762 snprintf(mz_name, RTE_MEMZONE_NAMESIZE, 4763 "bnxt_" PCI_PRI_FMT "-%s", pci_dev->addr.domain, 4764 pci_dev->addr.bus, pci_dev->addr.devid, 4765 pci_dev->addr.function, "tx_port_stats"); 4766 mz_name[RTE_MEMZONE_NAMESIZE - 1] = 0; 4767 mz = rte_memzone_lookup(mz_name); 4768 total_alloc_len = 4769 RTE_CACHE_LINE_ROUNDUP(sizeof(struct tx_port_stats) + 4770 sizeof(struct tx_port_stats_ext) + 512); 4771 if (!mz) { 4772 mz = rte_memzone_reserve(mz_name, 4773 total_alloc_len, 4774 SOCKET_ID_ANY, 4775 RTE_MEMZONE_2MB | 4776 RTE_MEMZONE_SIZE_HINT_ONLY | 4777 RTE_MEMZONE_IOVA_CONTIG); 4778 if (mz == NULL) 4779 return -ENOMEM; 4780 } 4781 memset(mz->addr, 0, mz->len); 4782 mz_phys_addr = mz->iova; 4783 4784 bp->tx_mem_zone = (const void *)mz; 4785 bp->hw_tx_port_stats = mz->addr; 4786 bp->hw_tx_port_stats_map = mz_phys_addr; 4787 bp->flags |= BNXT_FLAG_PORT_STATS; 4788 4789 /* Display extended statistics if FW supports it */ 4790 if (bp->hwrm_spec_code < HWRM_SPEC_CODE_1_8_4 || 4791 bp->hwrm_spec_code == HWRM_SPEC_CODE_1_9_0 || 4792 !(bp->flags & BNXT_FLAG_EXT_STATS_SUPPORTED)) 4793 return 0; 4794 4795 bp->hw_rx_port_stats_ext = (void *) 4796 ((uint8_t *)bp->hw_rx_port_stats + 4797 sizeof(struct rx_port_stats)); 4798 bp->hw_rx_port_stats_ext_map = bp->hw_rx_port_stats_map + 4799 sizeof(struct rx_port_stats); 4800 bp->flags |= BNXT_FLAG_EXT_RX_PORT_STATS; 4801 4802 if (bp->hwrm_spec_code < HWRM_SPEC_CODE_1_9_2 || 4803 bp->flags & BNXT_FLAG_EXT_STATS_SUPPORTED) { 4804 bp->hw_tx_port_stats_ext = (void *) 4805 ((uint8_t *)bp->hw_tx_port_stats + 4806 sizeof(struct tx_port_stats)); 4807 bp->hw_tx_port_stats_ext_map = 4808 bp->hw_tx_port_stats_map + 4809 sizeof(struct tx_port_stats); 4810 bp->flags |= BNXT_FLAG_EXT_TX_PORT_STATS; 4811 } 4812 4813 return 0; 4814 } 4815 4816 static int bnxt_setup_mac_addr(struct rte_eth_dev *eth_dev) 4817 { 4818 struct bnxt *bp = eth_dev->data->dev_private; 4819 int rc = 0; 4820 4821 eth_dev->data->mac_addrs = rte_zmalloc("bnxt_mac_addr_tbl", 4822 RTE_ETHER_ADDR_LEN * 4823 bp->max_l2_ctx, 4824 0); 4825 if (eth_dev->data->mac_addrs == NULL) { 4826 PMD_DRV_LOG(ERR, "Failed to alloc MAC addr tbl\n"); 4827 return -ENOMEM; 4828 } 4829 4830 if (!BNXT_HAS_DFLT_MAC_SET(bp)) { 4831 if (BNXT_PF(bp)) 4832 return -EINVAL; 4833 4834 /* Generate a random MAC address, if none was assigned by PF */ 4835 PMD_DRV_LOG(INFO, "VF MAC address not assigned by Host PF\n"); 4836 bnxt_eth_hw_addr_random(bp->mac_addr); 4837 PMD_DRV_LOG(INFO, 4838 "Assign random MAC:%02X:%02X:%02X:%02X:%02X:%02X\n", 4839 bp->mac_addr[0], bp->mac_addr[1], bp->mac_addr[2], 4840 bp->mac_addr[3], bp->mac_addr[4], bp->mac_addr[5]); 4841 4842 rc = bnxt_hwrm_set_mac(bp); 4843 if (rc) 4844 return rc; 4845 } 4846 4847 /* Copy the permanent MAC from the FUNC_QCAPS response */ 4848 memcpy(ð_dev->data->mac_addrs[0], bp->mac_addr, RTE_ETHER_ADDR_LEN); 4849 4850 return rc; 4851 } 4852 4853 static int bnxt_restore_dflt_mac(struct bnxt *bp) 4854 { 4855 int rc = 0; 4856 4857 /* MAC is already configured in FW */ 4858 if (BNXT_HAS_DFLT_MAC_SET(bp)) 4859 return 0; 4860 4861 /* Restore the old MAC configured */ 4862 rc = bnxt_hwrm_set_mac(bp); 4863 if (rc) 4864 PMD_DRV_LOG(ERR, "Failed to restore MAC address\n"); 4865 4866 return rc; 4867 } 4868 4869 static void bnxt_config_vf_req_fwd(struct bnxt *bp) 4870 { 4871 if (!BNXT_PF(bp)) 4872 return; 4873 4874 memset(bp->pf->vf_req_fwd, 0, sizeof(bp->pf->vf_req_fwd)); 4875 4876 if (!(bp->fw_cap & BNXT_FW_CAP_LINK_ADMIN)) 4877 BNXT_HWRM_CMD_TO_FORWARD(HWRM_PORT_PHY_QCFG); 4878 BNXT_HWRM_CMD_TO_FORWARD(HWRM_FUNC_CFG); 4879 BNXT_HWRM_CMD_TO_FORWARD(HWRM_FUNC_VF_CFG); 4880 BNXT_HWRM_CMD_TO_FORWARD(HWRM_CFA_L2_FILTER_ALLOC); 4881 BNXT_HWRM_CMD_TO_FORWARD(HWRM_OEM_CMD); 4882 } 4883 4884 struct bnxt * 4885 bnxt_get_bp(uint16_t port) 4886 { 4887 struct bnxt *bp; 4888 struct rte_eth_dev *dev; 4889 4890 if (!rte_eth_dev_is_valid_port(port)) { 4891 PMD_DRV_LOG(ERR, "Invalid port %d\n", port); 4892 return NULL; 4893 } 4894 4895 dev = &rte_eth_devices[port]; 4896 if (!is_bnxt_supported(dev)) { 4897 PMD_DRV_LOG(ERR, "Device %d not supported\n", port); 4898 return NULL; 4899 } 4900 4901 bp = (struct bnxt *)dev->data->dev_private; 4902 if (!BNXT_TRUFLOW_EN(bp)) { 4903 PMD_DRV_LOG(ERR, "TRUFLOW not enabled\n"); 4904 return NULL; 4905 } 4906 4907 return bp; 4908 } 4909 4910 uint16_t 4911 bnxt_get_svif(uint16_t port_id, bool func_svif, 4912 enum bnxt_ulp_intf_type type) 4913 { 4914 struct rte_eth_dev *eth_dev; 4915 struct bnxt *bp; 4916 4917 eth_dev = &rte_eth_devices[port_id]; 4918 if (BNXT_ETH_DEV_IS_REPRESENTOR(eth_dev)) { 4919 struct bnxt_representor *vfr = eth_dev->data->dev_private; 4920 if (!vfr) 4921 return 0; 4922 4923 if (type == BNXT_ULP_INTF_TYPE_VF_REP) 4924 return vfr->svif; 4925 4926 eth_dev = vfr->parent_dev; 4927 } 4928 4929 bp = eth_dev->data->dev_private; 4930 4931 return func_svif ? bp->func_svif : bp->port_svif; 4932 } 4933 4934 void 4935 bnxt_get_iface_mac(uint16_t port, enum bnxt_ulp_intf_type type, 4936 uint8_t *mac, uint8_t *parent_mac) 4937 { 4938 struct rte_eth_dev *eth_dev; 4939 struct bnxt *bp; 4940 4941 if (type != BNXT_ULP_INTF_TYPE_TRUSTED_VF && 4942 type != BNXT_ULP_INTF_TYPE_PF) 4943 return; 4944 4945 eth_dev = &rte_eth_devices[port]; 4946 bp = eth_dev->data->dev_private; 4947 memcpy(mac, bp->mac_addr, RTE_ETHER_ADDR_LEN); 4948 4949 if (type == BNXT_ULP_INTF_TYPE_TRUSTED_VF) 4950 memcpy(parent_mac, bp->parent->mac_addr, RTE_ETHER_ADDR_LEN); 4951 } 4952 4953 uint16_t 4954 bnxt_get_parent_vnic_id(uint16_t port, enum bnxt_ulp_intf_type type) 4955 { 4956 struct rte_eth_dev *eth_dev; 4957 struct bnxt *bp; 4958 4959 if (type != BNXT_ULP_INTF_TYPE_TRUSTED_VF) 4960 return 0; 4961 4962 eth_dev = &rte_eth_devices[port]; 4963 bp = eth_dev->data->dev_private; 4964 4965 return bp->parent->vnic; 4966 } 4967 uint16_t 4968 bnxt_get_vnic_id(uint16_t port, enum bnxt_ulp_intf_type type) 4969 { 4970 struct rte_eth_dev *eth_dev; 4971 struct bnxt_vnic_info *vnic; 4972 struct bnxt *bp; 4973 4974 eth_dev = &rte_eth_devices[port]; 4975 if (BNXT_ETH_DEV_IS_REPRESENTOR(eth_dev)) { 4976 struct bnxt_representor *vfr = eth_dev->data->dev_private; 4977 if (!vfr) 4978 return 0; 4979 4980 if (type == BNXT_ULP_INTF_TYPE_VF_REP) 4981 return vfr->dflt_vnic_id; 4982 4983 eth_dev = vfr->parent_dev; 4984 } 4985 4986 bp = eth_dev->data->dev_private; 4987 4988 vnic = BNXT_GET_DEFAULT_VNIC(bp); 4989 4990 return vnic->fw_vnic_id; 4991 } 4992 4993 uint16_t 4994 bnxt_get_fw_func_id(uint16_t port, enum bnxt_ulp_intf_type type) 4995 { 4996 struct rte_eth_dev *eth_dev; 4997 struct bnxt *bp; 4998 4999 eth_dev = &rte_eth_devices[port]; 5000 if (BNXT_ETH_DEV_IS_REPRESENTOR(eth_dev)) { 5001 struct bnxt_representor *vfr = eth_dev->data->dev_private; 5002 if (!vfr) 5003 return 0; 5004 5005 if (type == BNXT_ULP_INTF_TYPE_VF_REP) 5006 return vfr->fw_fid; 5007 5008 eth_dev = vfr->parent_dev; 5009 } 5010 5011 bp = eth_dev->data->dev_private; 5012 5013 return bp->fw_fid; 5014 } 5015 5016 enum bnxt_ulp_intf_type 5017 bnxt_get_interface_type(uint16_t port) 5018 { 5019 struct rte_eth_dev *eth_dev; 5020 struct bnxt *bp; 5021 5022 eth_dev = &rte_eth_devices[port]; 5023 if (BNXT_ETH_DEV_IS_REPRESENTOR(eth_dev)) 5024 return BNXT_ULP_INTF_TYPE_VF_REP; 5025 5026 bp = eth_dev->data->dev_private; 5027 if (BNXT_PF(bp)) 5028 return BNXT_ULP_INTF_TYPE_PF; 5029 else if (BNXT_VF_IS_TRUSTED(bp)) 5030 return BNXT_ULP_INTF_TYPE_TRUSTED_VF; 5031 else if (BNXT_VF(bp)) 5032 return BNXT_ULP_INTF_TYPE_VF; 5033 5034 return BNXT_ULP_INTF_TYPE_INVALID; 5035 } 5036 5037 uint16_t 5038 bnxt_get_phy_port_id(uint16_t port_id) 5039 { 5040 struct bnxt_representor *vfr; 5041 struct rte_eth_dev *eth_dev; 5042 struct bnxt *bp; 5043 5044 eth_dev = &rte_eth_devices[port_id]; 5045 if (BNXT_ETH_DEV_IS_REPRESENTOR(eth_dev)) { 5046 vfr = eth_dev->data->dev_private; 5047 if (!vfr) 5048 return 0; 5049 5050 eth_dev = vfr->parent_dev; 5051 } 5052 5053 bp = eth_dev->data->dev_private; 5054 5055 return BNXT_PF(bp) ? bp->pf->port_id : bp->parent->port_id; 5056 } 5057 5058 uint16_t 5059 bnxt_get_parif(uint16_t port_id, enum bnxt_ulp_intf_type type) 5060 { 5061 struct rte_eth_dev *eth_dev; 5062 struct bnxt *bp; 5063 5064 eth_dev = &rte_eth_devices[port_id]; 5065 if (BNXT_ETH_DEV_IS_REPRESENTOR(eth_dev)) { 5066 struct bnxt_representor *vfr = eth_dev->data->dev_private; 5067 if (!vfr) 5068 return 0; 5069 5070 if (type == BNXT_ULP_INTF_TYPE_VF_REP) 5071 return vfr->fw_fid - 1; 5072 5073 eth_dev = vfr->parent_dev; 5074 } 5075 5076 bp = eth_dev->data->dev_private; 5077 5078 return BNXT_PF(bp) ? bp->fw_fid - 1 : bp->parent->fid - 1; 5079 } 5080 5081 uint16_t 5082 bnxt_get_vport(uint16_t port_id) 5083 { 5084 return (1 << bnxt_get_phy_port_id(port_id)); 5085 } 5086 5087 static void bnxt_alloc_error_recovery_info(struct bnxt *bp) 5088 { 5089 struct bnxt_error_recovery_info *info = bp->recovery_info; 5090 5091 if (info) { 5092 if (!(bp->fw_cap & BNXT_FW_CAP_HCOMM_FW_STATUS)) 5093 memset(info, 0, sizeof(*info)); 5094 return; 5095 } 5096 5097 if (!(bp->fw_cap & BNXT_FW_CAP_ERROR_RECOVERY)) 5098 return; 5099 5100 info = rte_zmalloc("bnxt_hwrm_error_recovery_qcfg", 5101 sizeof(*info), 0); 5102 if (!info) 5103 bp->fw_cap &= ~BNXT_FW_CAP_ERROR_RECOVERY; 5104 5105 bp->recovery_info = info; 5106 } 5107 5108 static void bnxt_check_fw_status(struct bnxt *bp) 5109 { 5110 uint32_t fw_status; 5111 5112 if (!(bp->recovery_info && 5113 (bp->fw_cap & BNXT_FW_CAP_HCOMM_FW_STATUS))) 5114 return; 5115 5116 fw_status = bnxt_read_fw_status_reg(bp, BNXT_FW_STATUS_REG); 5117 if (fw_status != BNXT_FW_STATUS_HEALTHY) 5118 PMD_DRV_LOG(ERR, "Firmware not responding, status: %#x\n", 5119 fw_status); 5120 } 5121 5122 static int bnxt_map_hcomm_fw_status_reg(struct bnxt *bp) 5123 { 5124 struct bnxt_error_recovery_info *info = bp->recovery_info; 5125 uint32_t status_loc; 5126 uint32_t sig_ver; 5127 5128 rte_write32(HCOMM_STATUS_STRUCT_LOC, (uint8_t *)bp->bar0 + 5129 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 4); 5130 sig_ver = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 5131 BNXT_GRCP_WINDOW_2_BASE + 5132 offsetof(struct hcomm_status, 5133 sig_ver))); 5134 /* If the signature is absent, then FW does not support this feature */ 5135 if ((sig_ver & HCOMM_STATUS_SIGNATURE_MASK) != 5136 HCOMM_STATUS_SIGNATURE_VAL) 5137 return 0; 5138 5139 if (!info) { 5140 info = rte_zmalloc("bnxt_hwrm_error_recovery_qcfg", 5141 sizeof(*info), 0); 5142 if (!info) 5143 return -ENOMEM; 5144 bp->recovery_info = info; 5145 } else { 5146 memset(info, 0, sizeof(*info)); 5147 } 5148 5149 status_loc = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 5150 BNXT_GRCP_WINDOW_2_BASE + 5151 offsetof(struct hcomm_status, 5152 fw_status_loc))); 5153 5154 /* Only pre-map the FW health status GRC register */ 5155 if (BNXT_FW_STATUS_REG_TYPE(status_loc) != BNXT_FW_STATUS_REG_TYPE_GRC) 5156 return 0; 5157 5158 info->status_regs[BNXT_FW_STATUS_REG] = status_loc; 5159 info->mapped_status_regs[BNXT_FW_STATUS_REG] = 5160 BNXT_GRCP_WINDOW_2_BASE + (status_loc & BNXT_GRCP_OFFSET_MASK); 5161 5162 rte_write32((status_loc & BNXT_GRCP_BASE_MASK), (uint8_t *)bp->bar0 + 5163 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 4); 5164 5165 bp->fw_cap |= BNXT_FW_CAP_HCOMM_FW_STATUS; 5166 5167 return 0; 5168 } 5169 5170 /* This function gets the FW version along with the 5171 * capabilities(MAX and current) of the function, vnic, 5172 * error recovery, phy and other chip related info 5173 */ 5174 static int bnxt_get_config(struct bnxt *bp) 5175 { 5176 uint16_t mtu; 5177 int rc = 0; 5178 5179 bp->fw_cap = 0; 5180 5181 rc = bnxt_map_hcomm_fw_status_reg(bp); 5182 if (rc) 5183 return rc; 5184 5185 rc = bnxt_hwrm_ver_get(bp, DFLT_HWRM_CMD_TIMEOUT); 5186 if (rc) { 5187 bnxt_check_fw_status(bp); 5188 return rc; 5189 } 5190 5191 rc = bnxt_hwrm_func_reset(bp); 5192 if (rc) 5193 return -EIO; 5194 5195 rc = bnxt_hwrm_vnic_qcaps(bp); 5196 if (rc) 5197 return rc; 5198 5199 rc = bnxt_hwrm_queue_qportcfg(bp); 5200 if (rc) 5201 return rc; 5202 5203 /* Get the MAX capabilities for this function. 5204 * This function also allocates context memory for TQM rings and 5205 * informs the firmware about this allocated backing store memory. 5206 */ 5207 rc = bnxt_hwrm_func_qcaps(bp); 5208 if (rc) 5209 return rc; 5210 5211 rc = bnxt_hwrm_func_qcfg(bp, &mtu); 5212 if (rc) 5213 return rc; 5214 5215 rc = bnxt_hwrm_cfa_adv_flow_mgmt_qcaps(bp); 5216 if (rc) 5217 return rc; 5218 5219 bnxt_hwrm_port_mac_qcfg(bp); 5220 5221 bnxt_hwrm_parent_pf_qcfg(bp); 5222 5223 bnxt_hwrm_port_phy_qcaps(bp); 5224 5225 bnxt_alloc_error_recovery_info(bp); 5226 /* Get the adapter error recovery support info */ 5227 rc = bnxt_hwrm_error_recovery_qcfg(bp); 5228 if (rc) 5229 bp->fw_cap &= ~BNXT_FW_CAP_ERROR_RECOVERY; 5230 5231 bnxt_hwrm_port_led_qcaps(bp); 5232 5233 return 0; 5234 } 5235 5236 static int 5237 bnxt_init_locks(struct bnxt *bp) 5238 { 5239 int err; 5240 5241 err = pthread_mutex_init(&bp->flow_lock, NULL); 5242 if (err) { 5243 PMD_DRV_LOG(ERR, "Unable to initialize flow_lock\n"); 5244 return err; 5245 } 5246 5247 err = pthread_mutex_init(&bp->def_cp_lock, NULL); 5248 if (err) { 5249 PMD_DRV_LOG(ERR, "Unable to initialize def_cp_lock\n"); 5250 return err; 5251 } 5252 5253 err = pthread_mutex_init(&bp->health_check_lock, NULL); 5254 if (err) { 5255 PMD_DRV_LOG(ERR, "Unable to initialize health_check_lock\n"); 5256 return err; 5257 } 5258 5259 err = pthread_mutex_init(&bp->err_recovery_lock, NULL); 5260 if (err) 5261 PMD_DRV_LOG(ERR, "Unable to initialize err_recovery_lock\n"); 5262 5263 return err; 5264 } 5265 5266 static int bnxt_init_resources(struct bnxt *bp, bool reconfig_dev) 5267 { 5268 int rc = 0; 5269 5270 rc = bnxt_get_config(bp); 5271 if (rc) 5272 return rc; 5273 5274 if (!reconfig_dev) { 5275 rc = bnxt_setup_mac_addr(bp->eth_dev); 5276 if (rc) 5277 return rc; 5278 } else { 5279 rc = bnxt_restore_dflt_mac(bp); 5280 if (rc) 5281 return rc; 5282 } 5283 5284 bnxt_config_vf_req_fwd(bp); 5285 5286 rc = bnxt_hwrm_func_driver_register(bp); 5287 if (rc) { 5288 PMD_DRV_LOG(ERR, "Failed to register driver"); 5289 return -EBUSY; 5290 } 5291 5292 if (BNXT_PF(bp)) { 5293 if (bp->pdev->max_vfs) { 5294 rc = bnxt_hwrm_allocate_vfs(bp, bp->pdev->max_vfs); 5295 if (rc) { 5296 PMD_DRV_LOG(ERR, "Failed to allocate VFs\n"); 5297 return rc; 5298 } 5299 } else { 5300 rc = bnxt_hwrm_allocate_pf_only(bp); 5301 if (rc) { 5302 PMD_DRV_LOG(ERR, 5303 "Failed to allocate PF resources"); 5304 return rc; 5305 } 5306 } 5307 } 5308 5309 rc = bnxt_alloc_mem(bp, reconfig_dev); 5310 if (rc) 5311 return rc; 5312 5313 rc = bnxt_setup_int(bp); 5314 if (rc) 5315 return rc; 5316 5317 rc = bnxt_request_int(bp); 5318 if (rc) 5319 return rc; 5320 5321 rc = bnxt_init_ctx_mem(bp); 5322 if (rc) { 5323 PMD_DRV_LOG(ERR, "Failed to init adv_flow_counters\n"); 5324 return rc; 5325 } 5326 5327 return 0; 5328 } 5329 5330 static int 5331 bnxt_parse_devarg_accum_stats(__rte_unused const char *key, 5332 const char *value, void *opaque_arg) 5333 { 5334 struct bnxt *bp = opaque_arg; 5335 unsigned long accum_stats; 5336 char *end = NULL; 5337 5338 if (!value || !opaque_arg) { 5339 PMD_DRV_LOG(ERR, 5340 "Invalid parameter passed to accum-stats devargs.\n"); 5341 return -EINVAL; 5342 } 5343 5344 accum_stats = strtoul(value, &end, 10); 5345 if (end == NULL || *end != '\0' || 5346 (accum_stats == ULONG_MAX && errno == ERANGE)) { 5347 PMD_DRV_LOG(ERR, 5348 "Invalid parameter passed to accum-stats devargs.\n"); 5349 return -EINVAL; 5350 } 5351 5352 if (BNXT_DEVARG_ACCUM_STATS_INVALID(accum_stats)) { 5353 PMD_DRV_LOG(ERR, 5354 "Invalid value passed to accum-stats devargs.\n"); 5355 return -EINVAL; 5356 } 5357 5358 if (accum_stats) { 5359 bp->flags2 |= BNXT_FLAGS2_ACCUM_STATS_EN; 5360 PMD_DRV_LOG(INFO, "Host-based accum-stats feature enabled.\n"); 5361 } else { 5362 bp->flags2 &= ~BNXT_FLAGS2_ACCUM_STATS_EN; 5363 PMD_DRV_LOG(INFO, "Host-based accum-stats feature disabled.\n"); 5364 } 5365 5366 return 0; 5367 } 5368 5369 static int 5370 bnxt_parse_devarg_flow_xstat(__rte_unused const char *key, 5371 const char *value, void *opaque_arg) 5372 { 5373 struct bnxt *bp = opaque_arg; 5374 unsigned long flow_xstat; 5375 char *end = NULL; 5376 5377 if (!value || !opaque_arg) { 5378 PMD_DRV_LOG(ERR, 5379 "Invalid parameter passed to flow_xstat devarg.\n"); 5380 return -EINVAL; 5381 } 5382 5383 flow_xstat = strtoul(value, &end, 10); 5384 if (end == NULL || *end != '\0' || 5385 (flow_xstat == ULONG_MAX && errno == ERANGE)) { 5386 PMD_DRV_LOG(ERR, 5387 "Invalid parameter passed to flow_xstat devarg.\n"); 5388 return -EINVAL; 5389 } 5390 5391 if (BNXT_DEVARG_FLOW_XSTAT_INVALID(flow_xstat)) { 5392 PMD_DRV_LOG(ERR, 5393 "Invalid value passed to flow_xstat devarg.\n"); 5394 return -EINVAL; 5395 } 5396 5397 bp->flags |= BNXT_FLAG_FLOW_XSTATS_EN; 5398 if (BNXT_FLOW_XSTATS_EN(bp)) 5399 PMD_DRV_LOG(INFO, "flow_xstat feature enabled.\n"); 5400 5401 return 0; 5402 } 5403 5404 static int 5405 bnxt_parse_devarg_max_num_kflows(__rte_unused const char *key, 5406 const char *value, void *opaque_arg) 5407 { 5408 struct bnxt *bp = opaque_arg; 5409 unsigned long max_num_kflows; 5410 char *end = NULL; 5411 5412 if (!value || !opaque_arg) { 5413 PMD_DRV_LOG(ERR, 5414 "Invalid parameter passed to max_num_kflows devarg.\n"); 5415 return -EINVAL; 5416 } 5417 5418 max_num_kflows = strtoul(value, &end, 10); 5419 if (end == NULL || *end != '\0' || 5420 (max_num_kflows == ULONG_MAX && errno == ERANGE)) { 5421 PMD_DRV_LOG(ERR, 5422 "Invalid parameter passed to max_num_kflows devarg.\n"); 5423 return -EINVAL; 5424 } 5425 5426 if (bnxt_devarg_max_num_kflow_invalid(max_num_kflows)) { 5427 PMD_DRV_LOG(ERR, 5428 "Invalid value passed to max_num_kflows devarg.\n"); 5429 return -EINVAL; 5430 } 5431 5432 bp->max_num_kflows = max_num_kflows; 5433 if (bp->max_num_kflows) 5434 PMD_DRV_LOG(INFO, "max_num_kflows set as %ldK.\n", 5435 max_num_kflows); 5436 5437 return 0; 5438 } 5439 5440 static int 5441 bnxt_parse_devarg_app_id(__rte_unused const char *key, 5442 const char *value, void *opaque_arg) 5443 { 5444 struct bnxt *bp = opaque_arg; 5445 unsigned long app_id; 5446 char *end = NULL; 5447 5448 if (!value || !opaque_arg) { 5449 PMD_DRV_LOG(ERR, 5450 "Invalid parameter passed to app-id " 5451 "devargs.\n"); 5452 return -EINVAL; 5453 } 5454 5455 app_id = strtoul(value, &end, 10); 5456 if (end == NULL || *end != '\0' || 5457 (app_id == ULONG_MAX && errno == ERANGE)) { 5458 PMD_DRV_LOG(ERR, 5459 "Invalid parameter passed to app_id " 5460 "devargs.\n"); 5461 return -EINVAL; 5462 } 5463 5464 if (BNXT_DEVARG_APP_ID_INVALID(app_id)) { 5465 PMD_DRV_LOG(ERR, "Invalid app-id(%d) devargs.\n", 5466 (uint16_t)app_id); 5467 return -EINVAL; 5468 } 5469 5470 bp->app_id = app_id; 5471 PMD_DRV_LOG(INFO, "app-id=%d feature enabled.\n", (uint16_t)app_id); 5472 5473 return 0; 5474 } 5475 5476 static int 5477 bnxt_parse_devarg_rep_is_pf(__rte_unused const char *key, 5478 const char *value, void *opaque_arg) 5479 { 5480 struct bnxt_representor *vfr_bp = opaque_arg; 5481 unsigned long rep_is_pf; 5482 char *end = NULL; 5483 5484 if (!value || !opaque_arg) { 5485 PMD_DRV_LOG(ERR, 5486 "Invalid parameter passed to rep_is_pf devargs.\n"); 5487 return -EINVAL; 5488 } 5489 5490 rep_is_pf = strtoul(value, &end, 10); 5491 if (end == NULL || *end != '\0' || 5492 (rep_is_pf == ULONG_MAX && errno == ERANGE)) { 5493 PMD_DRV_LOG(ERR, 5494 "Invalid parameter passed to rep_is_pf devargs.\n"); 5495 return -EINVAL; 5496 } 5497 5498 if (BNXT_DEVARG_REP_IS_PF_INVALID(rep_is_pf)) { 5499 PMD_DRV_LOG(ERR, 5500 "Invalid value passed to rep_is_pf devargs.\n"); 5501 return -EINVAL; 5502 } 5503 5504 vfr_bp->flags |= rep_is_pf; 5505 if (BNXT_REP_PF(vfr_bp)) 5506 PMD_DRV_LOG(INFO, "PF representor\n"); 5507 else 5508 PMD_DRV_LOG(INFO, "VF representor\n"); 5509 5510 return 0; 5511 } 5512 5513 static int 5514 bnxt_parse_devarg_rep_based_pf(__rte_unused const char *key, 5515 const char *value, void *opaque_arg) 5516 { 5517 struct bnxt_representor *vfr_bp = opaque_arg; 5518 unsigned long rep_based_pf; 5519 char *end = NULL; 5520 5521 if (!value || !opaque_arg) { 5522 PMD_DRV_LOG(ERR, 5523 "Invalid parameter passed to rep_based_pf " 5524 "devargs.\n"); 5525 return -EINVAL; 5526 } 5527 5528 rep_based_pf = strtoul(value, &end, 10); 5529 if (end == NULL || *end != '\0' || 5530 (rep_based_pf == ULONG_MAX && errno == ERANGE)) { 5531 PMD_DRV_LOG(ERR, 5532 "Invalid parameter passed to rep_based_pf " 5533 "devargs.\n"); 5534 return -EINVAL; 5535 } 5536 5537 if (BNXT_DEVARG_REP_BASED_PF_INVALID(rep_based_pf)) { 5538 PMD_DRV_LOG(ERR, 5539 "Invalid value passed to rep_based_pf devargs.\n"); 5540 return -EINVAL; 5541 } 5542 5543 vfr_bp->rep_based_pf = rep_based_pf; 5544 vfr_bp->flags |= BNXT_REP_BASED_PF_VALID; 5545 5546 PMD_DRV_LOG(INFO, "rep-based-pf = %d\n", vfr_bp->rep_based_pf); 5547 5548 return 0; 5549 } 5550 5551 static int 5552 bnxt_parse_devarg_rep_q_r2f(__rte_unused const char *key, 5553 const char *value, void *opaque_arg) 5554 { 5555 struct bnxt_representor *vfr_bp = opaque_arg; 5556 unsigned long rep_q_r2f; 5557 char *end = NULL; 5558 5559 if (!value || !opaque_arg) { 5560 PMD_DRV_LOG(ERR, 5561 "Invalid parameter passed to rep_q_r2f " 5562 "devargs.\n"); 5563 return -EINVAL; 5564 } 5565 5566 rep_q_r2f = strtoul(value, &end, 10); 5567 if (end == NULL || *end != '\0' || 5568 (rep_q_r2f == ULONG_MAX && errno == ERANGE)) { 5569 PMD_DRV_LOG(ERR, 5570 "Invalid parameter passed to rep_q_r2f " 5571 "devargs.\n"); 5572 return -EINVAL; 5573 } 5574 5575 if (BNXT_DEVARG_REP_Q_R2F_INVALID(rep_q_r2f)) { 5576 PMD_DRV_LOG(ERR, 5577 "Invalid value passed to rep_q_r2f devargs.\n"); 5578 return -EINVAL; 5579 } 5580 5581 vfr_bp->rep_q_r2f = rep_q_r2f; 5582 vfr_bp->flags |= BNXT_REP_Q_R2F_VALID; 5583 PMD_DRV_LOG(INFO, "rep-q-r2f = %d\n", vfr_bp->rep_q_r2f); 5584 5585 return 0; 5586 } 5587 5588 static int 5589 bnxt_parse_devarg_rep_q_f2r(__rte_unused const char *key, 5590 const char *value, void *opaque_arg) 5591 { 5592 struct bnxt_representor *vfr_bp = opaque_arg; 5593 unsigned long rep_q_f2r; 5594 char *end = NULL; 5595 5596 if (!value || !opaque_arg) { 5597 PMD_DRV_LOG(ERR, 5598 "Invalid parameter passed to rep_q_f2r " 5599 "devargs.\n"); 5600 return -EINVAL; 5601 } 5602 5603 rep_q_f2r = strtoul(value, &end, 10); 5604 if (end == NULL || *end != '\0' || 5605 (rep_q_f2r == ULONG_MAX && errno == ERANGE)) { 5606 PMD_DRV_LOG(ERR, 5607 "Invalid parameter passed to rep_q_f2r " 5608 "devargs.\n"); 5609 return -EINVAL; 5610 } 5611 5612 if (BNXT_DEVARG_REP_Q_F2R_INVALID(rep_q_f2r)) { 5613 PMD_DRV_LOG(ERR, 5614 "Invalid value passed to rep_q_f2r devargs.\n"); 5615 return -EINVAL; 5616 } 5617 5618 vfr_bp->rep_q_f2r = rep_q_f2r; 5619 vfr_bp->flags |= BNXT_REP_Q_F2R_VALID; 5620 PMD_DRV_LOG(INFO, "rep-q-f2r = %d\n", vfr_bp->rep_q_f2r); 5621 5622 return 0; 5623 } 5624 5625 static int 5626 bnxt_parse_devarg_rep_fc_r2f(__rte_unused const char *key, 5627 const char *value, void *opaque_arg) 5628 { 5629 struct bnxt_representor *vfr_bp = opaque_arg; 5630 unsigned long rep_fc_r2f; 5631 char *end = NULL; 5632 5633 if (!value || !opaque_arg) { 5634 PMD_DRV_LOG(ERR, 5635 "Invalid parameter passed to rep_fc_r2f " 5636 "devargs.\n"); 5637 return -EINVAL; 5638 } 5639 5640 rep_fc_r2f = strtoul(value, &end, 10); 5641 if (end == NULL || *end != '\0' || 5642 (rep_fc_r2f == ULONG_MAX && errno == ERANGE)) { 5643 PMD_DRV_LOG(ERR, 5644 "Invalid parameter passed to rep_fc_r2f " 5645 "devargs.\n"); 5646 return -EINVAL; 5647 } 5648 5649 if (BNXT_DEVARG_REP_FC_R2F_INVALID(rep_fc_r2f)) { 5650 PMD_DRV_LOG(ERR, 5651 "Invalid value passed to rep_fc_r2f devargs.\n"); 5652 return -EINVAL; 5653 } 5654 5655 vfr_bp->flags |= BNXT_REP_FC_R2F_VALID; 5656 vfr_bp->rep_fc_r2f = rep_fc_r2f; 5657 PMD_DRV_LOG(INFO, "rep-fc-r2f = %lu\n", rep_fc_r2f); 5658 5659 return 0; 5660 } 5661 5662 static int 5663 bnxt_parse_devarg_rep_fc_f2r(__rte_unused const char *key, 5664 const char *value, void *opaque_arg) 5665 { 5666 struct bnxt_representor *vfr_bp = opaque_arg; 5667 unsigned long rep_fc_f2r; 5668 char *end = NULL; 5669 5670 if (!value || !opaque_arg) { 5671 PMD_DRV_LOG(ERR, 5672 "Invalid parameter passed to rep_fc_f2r " 5673 "devargs.\n"); 5674 return -EINVAL; 5675 } 5676 5677 rep_fc_f2r = strtoul(value, &end, 10); 5678 if (end == NULL || *end != '\0' || 5679 (rep_fc_f2r == ULONG_MAX && errno == ERANGE)) { 5680 PMD_DRV_LOG(ERR, 5681 "Invalid parameter passed to rep_fc_f2r " 5682 "devargs.\n"); 5683 return -EINVAL; 5684 } 5685 5686 if (BNXT_DEVARG_REP_FC_F2R_INVALID(rep_fc_f2r)) { 5687 PMD_DRV_LOG(ERR, 5688 "Invalid value passed to rep_fc_f2r devargs.\n"); 5689 return -EINVAL; 5690 } 5691 5692 vfr_bp->flags |= BNXT_REP_FC_F2R_VALID; 5693 vfr_bp->rep_fc_f2r = rep_fc_f2r; 5694 PMD_DRV_LOG(INFO, "rep-fc-f2r = %lu\n", rep_fc_f2r); 5695 5696 return 0; 5697 } 5698 5699 static int 5700 bnxt_parse_dev_args(struct bnxt *bp, struct rte_devargs *devargs) 5701 { 5702 struct rte_kvargs *kvlist; 5703 int ret; 5704 5705 if (devargs == NULL) 5706 return 0; 5707 5708 kvlist = rte_kvargs_parse(devargs->args, bnxt_dev_args); 5709 if (kvlist == NULL) 5710 return -EINVAL; 5711 5712 /* 5713 * Handler for "flow_xstat" devarg. 5714 * Invoked as for ex: "-a 0000:00:0d.0,flow_xstat=1" 5715 */ 5716 ret = rte_kvargs_process(kvlist, BNXT_DEVARG_FLOW_XSTAT, 5717 bnxt_parse_devarg_flow_xstat, bp); 5718 if (ret) 5719 goto err; 5720 5721 /* 5722 * Handler for "accum-stats" devarg. 5723 * Invoked as for ex: "-a 0000:00:0d.0,accum-stats=1" 5724 */ 5725 rte_kvargs_process(kvlist, BNXT_DEVARG_ACCUM_STATS, 5726 bnxt_parse_devarg_accum_stats, bp); 5727 /* 5728 * Handler for "max_num_kflows" devarg. 5729 * Invoked as for ex: "-a 000:00:0d.0,max_num_kflows=32" 5730 */ 5731 ret = rte_kvargs_process(kvlist, BNXT_DEVARG_MAX_NUM_KFLOWS, 5732 bnxt_parse_devarg_max_num_kflows, bp); 5733 if (ret) 5734 goto err; 5735 5736 err: 5737 /* 5738 * Handler for "app-id" devarg. 5739 * Invoked as for ex: "-a 000:00:0d.0,app-id=1" 5740 */ 5741 rte_kvargs_process(kvlist, BNXT_DEVARG_APP_ID, 5742 bnxt_parse_devarg_app_id, bp); 5743 5744 rte_kvargs_free(kvlist); 5745 return ret; 5746 } 5747 5748 static int bnxt_alloc_switch_domain(struct bnxt *bp) 5749 { 5750 int rc = 0; 5751 5752 if (BNXT_PF(bp) || BNXT_VF_IS_TRUSTED(bp)) { 5753 rc = rte_eth_switch_domain_alloc(&bp->switch_domain_id); 5754 if (rc) 5755 PMD_DRV_LOG(ERR, 5756 "Failed to alloc switch domain: %d\n", rc); 5757 else 5758 PMD_DRV_LOG(INFO, 5759 "Switch domain allocated %d\n", 5760 bp->switch_domain_id); 5761 } 5762 5763 return rc; 5764 } 5765 5766 /* Allocate and initialize various fields in bnxt struct that 5767 * need to be allocated/destroyed only once in the lifetime of the driver 5768 */ 5769 static int bnxt_drv_init(struct rte_eth_dev *eth_dev) 5770 { 5771 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(eth_dev); 5772 struct bnxt *bp = eth_dev->data->dev_private; 5773 int rc = 0; 5774 5775 bp->flags &= ~BNXT_FLAG_RX_VECTOR_PKT_MODE; 5776 5777 if (bnxt_vf_pciid(pci_dev->id.device_id)) 5778 bp->flags |= BNXT_FLAG_VF; 5779 5780 if (bnxt_p5_device(pci_dev->id.device_id)) 5781 bp->flags |= BNXT_FLAG_CHIP_P5; 5782 5783 if (pci_dev->id.device_id == BROADCOM_DEV_ID_58802 || 5784 pci_dev->id.device_id == BROADCOM_DEV_ID_58804 || 5785 pci_dev->id.device_id == BROADCOM_DEV_ID_58808 || 5786 pci_dev->id.device_id == BROADCOM_DEV_ID_58802_VF) 5787 bp->flags |= BNXT_FLAG_STINGRAY; 5788 5789 if (BNXT_TRUFLOW_EN(bp)) { 5790 /* extra mbuf field is required to store CFA code from mark */ 5791 static const struct rte_mbuf_dynfield bnxt_cfa_code_dynfield_desc = { 5792 .name = RTE_PMD_BNXT_CFA_CODE_DYNFIELD_NAME, 5793 .size = sizeof(bnxt_cfa_code_dynfield_t), 5794 .align = __alignof__(bnxt_cfa_code_dynfield_t), 5795 }; 5796 bnxt_cfa_code_dynfield_offset = 5797 rte_mbuf_dynfield_register(&bnxt_cfa_code_dynfield_desc); 5798 if (bnxt_cfa_code_dynfield_offset < 0) { 5799 PMD_DRV_LOG(ERR, 5800 "Failed to register mbuf field for TruFlow mark\n"); 5801 return -rte_errno; 5802 } 5803 } 5804 5805 rc = bnxt_map_pci_bars(eth_dev); 5806 if (rc) { 5807 PMD_DRV_LOG(ERR, 5808 "Failed to initialize board rc: %x\n", rc); 5809 return rc; 5810 } 5811 5812 rc = bnxt_alloc_pf_info(bp); 5813 if (rc) 5814 return rc; 5815 5816 rc = bnxt_alloc_link_info(bp); 5817 if (rc) 5818 return rc; 5819 5820 rc = bnxt_alloc_parent_info(bp); 5821 if (rc) 5822 return rc; 5823 5824 rc = bnxt_alloc_hwrm_resources(bp); 5825 if (rc) { 5826 PMD_DRV_LOG(ERR, 5827 "Failed to allocate response buffer rc: %x\n", rc); 5828 return rc; 5829 } 5830 rc = bnxt_alloc_leds_info(bp); 5831 if (rc) 5832 return rc; 5833 5834 rc = bnxt_alloc_cos_queues(bp); 5835 if (rc) 5836 return rc; 5837 5838 rc = bnxt_init_locks(bp); 5839 if (rc) 5840 return rc; 5841 5842 rc = bnxt_alloc_switch_domain(bp); 5843 if (rc) 5844 return rc; 5845 5846 return rc; 5847 } 5848 5849 static int 5850 bnxt_dev_init(struct rte_eth_dev *eth_dev, void *params __rte_unused) 5851 { 5852 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(eth_dev); 5853 static int version_printed; 5854 struct bnxt *bp; 5855 int rc; 5856 5857 if (version_printed++ == 0) 5858 PMD_DRV_LOG(INFO, "%s\n", bnxt_version); 5859 5860 eth_dev->dev_ops = &bnxt_dev_ops; 5861 eth_dev->rx_queue_count = bnxt_rx_queue_count_op; 5862 eth_dev->rx_descriptor_status = bnxt_rx_descriptor_status_op; 5863 eth_dev->tx_descriptor_status = bnxt_tx_descriptor_status_op; 5864 eth_dev->rx_pkt_burst = &bnxt_recv_pkts; 5865 eth_dev->tx_pkt_burst = &bnxt_xmit_pkts; 5866 5867 /* 5868 * For secondary processes, we don't initialise any further 5869 * as primary has already done this work. 5870 */ 5871 if (rte_eal_process_type() != RTE_PROC_PRIMARY) 5872 return 0; 5873 5874 rte_eth_copy_pci_info(eth_dev, pci_dev); 5875 eth_dev->data->dev_flags |= RTE_ETH_DEV_AUTOFILL_QUEUE_XSTATS; 5876 5877 bp = eth_dev->data->dev_private; 5878 5879 /* Parse dev arguments passed on when starting the DPDK application. */ 5880 rc = bnxt_parse_dev_args(bp, pci_dev->device.devargs); 5881 if (rc) 5882 goto error_free; 5883 5884 rc = bnxt_drv_init(eth_dev); 5885 if (rc) 5886 goto error_free; 5887 5888 rc = bnxt_init_resources(bp, false); 5889 if (rc) 5890 goto error_free; 5891 5892 rc = bnxt_alloc_stats_mem(bp); 5893 if (rc) 5894 goto error_free; 5895 5896 PMD_DRV_LOG(INFO, 5897 "Found %s device at mem %" PRIX64 ", node addr %pM\n", 5898 DRV_MODULE_NAME, 5899 pci_dev->mem_resource[0].phys_addr, 5900 pci_dev->mem_resource[0].addr); 5901 5902 return 0; 5903 5904 error_free: 5905 bnxt_dev_uninit(eth_dev); 5906 return rc; 5907 } 5908 5909 5910 static void bnxt_free_ctx_mem_buf(struct bnxt_ctx_mem_buf_info *ctx) 5911 { 5912 if (!ctx) 5913 return; 5914 5915 if (ctx->va) 5916 rte_free(ctx->va); 5917 5918 ctx->va = NULL; 5919 ctx->dma = RTE_BAD_IOVA; 5920 ctx->ctx_id = BNXT_CTX_VAL_INVAL; 5921 } 5922 5923 static void bnxt_unregister_fc_ctx_mem(struct bnxt *bp) 5924 { 5925 bnxt_hwrm_cfa_counter_cfg(bp, BNXT_DIR_RX, 5926 CFA_COUNTER_CFG_IN_COUNTER_TYPE_FC, 5927 bp->flow_stat->rx_fc_out_tbl.ctx_id, 5928 bp->flow_stat->max_fc, 5929 false); 5930 5931 bnxt_hwrm_cfa_counter_cfg(bp, BNXT_DIR_TX, 5932 CFA_COUNTER_CFG_IN_COUNTER_TYPE_FC, 5933 bp->flow_stat->tx_fc_out_tbl.ctx_id, 5934 bp->flow_stat->max_fc, 5935 false); 5936 5937 if (bp->flow_stat->rx_fc_in_tbl.ctx_id != BNXT_CTX_VAL_INVAL) 5938 bnxt_hwrm_ctx_unrgtr(bp, bp->flow_stat->rx_fc_in_tbl.ctx_id); 5939 bp->flow_stat->rx_fc_in_tbl.ctx_id = BNXT_CTX_VAL_INVAL; 5940 5941 if (bp->flow_stat->rx_fc_out_tbl.ctx_id != BNXT_CTX_VAL_INVAL) 5942 bnxt_hwrm_ctx_unrgtr(bp, bp->flow_stat->rx_fc_out_tbl.ctx_id); 5943 bp->flow_stat->rx_fc_out_tbl.ctx_id = BNXT_CTX_VAL_INVAL; 5944 5945 if (bp->flow_stat->tx_fc_in_tbl.ctx_id != BNXT_CTX_VAL_INVAL) 5946 bnxt_hwrm_ctx_unrgtr(bp, bp->flow_stat->tx_fc_in_tbl.ctx_id); 5947 bp->flow_stat->tx_fc_in_tbl.ctx_id = BNXT_CTX_VAL_INVAL; 5948 5949 if (bp->flow_stat->tx_fc_out_tbl.ctx_id != BNXT_CTX_VAL_INVAL) 5950 bnxt_hwrm_ctx_unrgtr(bp, bp->flow_stat->tx_fc_out_tbl.ctx_id); 5951 bp->flow_stat->tx_fc_out_tbl.ctx_id = BNXT_CTX_VAL_INVAL; 5952 } 5953 5954 static void bnxt_uninit_fc_ctx_mem(struct bnxt *bp) 5955 { 5956 bnxt_unregister_fc_ctx_mem(bp); 5957 5958 bnxt_free_ctx_mem_buf(&bp->flow_stat->rx_fc_in_tbl); 5959 bnxt_free_ctx_mem_buf(&bp->flow_stat->rx_fc_out_tbl); 5960 bnxt_free_ctx_mem_buf(&bp->flow_stat->tx_fc_in_tbl); 5961 bnxt_free_ctx_mem_buf(&bp->flow_stat->tx_fc_out_tbl); 5962 } 5963 5964 static void bnxt_uninit_ctx_mem(struct bnxt *bp) 5965 { 5966 if (BNXT_FLOW_XSTATS_EN(bp)) 5967 bnxt_uninit_fc_ctx_mem(bp); 5968 } 5969 5970 static void 5971 bnxt_free_error_recovery_info(struct bnxt *bp) 5972 { 5973 rte_free(bp->recovery_info); 5974 bp->recovery_info = NULL; 5975 bp->fw_cap &= ~BNXT_FW_CAP_ERROR_RECOVERY; 5976 } 5977 5978 static int 5979 bnxt_uninit_resources(struct bnxt *bp, bool reconfig_dev) 5980 { 5981 int rc; 5982 5983 bnxt_free_int(bp); 5984 bnxt_free_mem(bp, reconfig_dev); 5985 5986 bnxt_hwrm_func_buf_unrgtr(bp); 5987 if (bp->pf != NULL) { 5988 rte_free(bp->pf->vf_req_buf); 5989 bp->pf->vf_req_buf = NULL; 5990 } 5991 5992 rc = bnxt_hwrm_func_driver_unregister(bp, 0); 5993 bp->flags &= ~BNXT_FLAG_REGISTERED; 5994 bnxt_free_ctx_mem(bp); 5995 if (!reconfig_dev) { 5996 bnxt_free_hwrm_resources(bp); 5997 bnxt_free_error_recovery_info(bp); 5998 } 5999 6000 bnxt_uninit_ctx_mem(bp); 6001 6002 bnxt_free_flow_stats_info(bp); 6003 if (bp->rep_info != NULL) 6004 bnxt_free_switch_domain(bp); 6005 bnxt_free_rep_info(bp); 6006 rte_free(bp->ptp_cfg); 6007 bp->ptp_cfg = NULL; 6008 return rc; 6009 } 6010 6011 static int 6012 bnxt_dev_uninit(struct rte_eth_dev *eth_dev) 6013 { 6014 if (rte_eal_process_type() != RTE_PROC_PRIMARY) 6015 return -EPERM; 6016 6017 PMD_DRV_LOG(DEBUG, "Calling Device uninit\n"); 6018 6019 if (eth_dev->state != RTE_ETH_DEV_UNUSED) 6020 bnxt_dev_close_op(eth_dev); 6021 6022 return 0; 6023 } 6024 6025 static int bnxt_pci_remove_dev_with_reps(struct rte_eth_dev *eth_dev) 6026 { 6027 struct bnxt *bp = eth_dev->data->dev_private; 6028 struct rte_eth_dev *vf_rep_eth_dev; 6029 int ret = 0, i; 6030 6031 if (!bp) 6032 return -EINVAL; 6033 6034 for (i = 0; i < bp->num_reps; i++) { 6035 vf_rep_eth_dev = bp->rep_info[i].vfr_eth_dev; 6036 if (!vf_rep_eth_dev) 6037 continue; 6038 PMD_DRV_LOG(DEBUG, "BNXT Port:%d VFR pci remove\n", 6039 vf_rep_eth_dev->data->port_id); 6040 rte_eth_dev_destroy(vf_rep_eth_dev, bnxt_representor_uninit); 6041 } 6042 PMD_DRV_LOG(DEBUG, "BNXT Port:%d pci remove\n", 6043 eth_dev->data->port_id); 6044 ret = rte_eth_dev_destroy(eth_dev, bnxt_dev_uninit); 6045 6046 return ret; 6047 } 6048 6049 static void bnxt_free_rep_info(struct bnxt *bp) 6050 { 6051 rte_free(bp->rep_info); 6052 bp->rep_info = NULL; 6053 rte_free(bp->cfa_code_map); 6054 bp->cfa_code_map = NULL; 6055 } 6056 6057 static int bnxt_init_rep_info(struct bnxt *bp) 6058 { 6059 int i = 0, rc; 6060 6061 if (bp->rep_info) 6062 return 0; 6063 6064 bp->rep_info = rte_zmalloc("bnxt_rep_info", 6065 sizeof(bp->rep_info[0]) * BNXT_MAX_VF_REPS, 6066 0); 6067 if (!bp->rep_info) { 6068 PMD_DRV_LOG(ERR, "Failed to alloc memory for rep info\n"); 6069 return -ENOMEM; 6070 } 6071 bp->cfa_code_map = rte_zmalloc("bnxt_cfa_code_map", 6072 sizeof(*bp->cfa_code_map) * 6073 BNXT_MAX_CFA_CODE, 0); 6074 if (!bp->cfa_code_map) { 6075 PMD_DRV_LOG(ERR, "Failed to alloc memory for cfa_code_map\n"); 6076 bnxt_free_rep_info(bp); 6077 return -ENOMEM; 6078 } 6079 6080 for (i = 0; i < BNXT_MAX_CFA_CODE; i++) 6081 bp->cfa_code_map[i] = BNXT_VF_IDX_INVALID; 6082 6083 rc = pthread_mutex_init(&bp->rep_info->vfr_lock, NULL); 6084 if (rc) { 6085 PMD_DRV_LOG(ERR, "Unable to initialize vfr_lock\n"); 6086 bnxt_free_rep_info(bp); 6087 return rc; 6088 } 6089 6090 rc = pthread_mutex_init(&bp->rep_info->vfr_start_lock, NULL); 6091 if (rc) { 6092 PMD_DRV_LOG(ERR, "Unable to initialize vfr_start_lock\n"); 6093 bnxt_free_rep_info(bp); 6094 return rc; 6095 } 6096 6097 return rc; 6098 } 6099 6100 static int bnxt_rep_port_probe(struct rte_pci_device *pci_dev, 6101 struct rte_eth_devargs *eth_da, 6102 struct rte_eth_dev *backing_eth_dev, 6103 const char *dev_args) 6104 { 6105 struct rte_eth_dev *vf_rep_eth_dev; 6106 char name[RTE_ETH_NAME_MAX_LEN]; 6107 struct bnxt *backing_bp; 6108 uint16_t num_rep; 6109 int i, ret = 0; 6110 struct rte_kvargs *kvlist = NULL; 6111 6112 if (eth_da->type == RTE_ETH_REPRESENTOR_NONE) 6113 return 0; 6114 if (eth_da->type != RTE_ETH_REPRESENTOR_VF) { 6115 PMD_DRV_LOG(ERR, "unsupported representor type %d\n", 6116 eth_da->type); 6117 return -ENOTSUP; 6118 } 6119 num_rep = eth_da->nb_representor_ports; 6120 if (num_rep > BNXT_MAX_VF_REPS) { 6121 PMD_DRV_LOG(ERR, "nb_representor_ports = %d > %d MAX VF REPS\n", 6122 num_rep, BNXT_MAX_VF_REPS); 6123 return -EINVAL; 6124 } 6125 6126 if (num_rep >= RTE_MAX_ETHPORTS) { 6127 PMD_DRV_LOG(ERR, 6128 "nb_representor_ports = %d > %d MAX ETHPORTS\n", 6129 num_rep, RTE_MAX_ETHPORTS); 6130 return -EINVAL; 6131 } 6132 6133 backing_bp = backing_eth_dev->data->dev_private; 6134 6135 if (!(BNXT_PF(backing_bp) || BNXT_VF_IS_TRUSTED(backing_bp))) { 6136 PMD_DRV_LOG(ERR, 6137 "Not a PF or trusted VF. No Representor support\n"); 6138 /* Returning an error is not an option. 6139 * Applications are not handling this correctly 6140 */ 6141 return 0; 6142 } 6143 6144 if (bnxt_init_rep_info(backing_bp)) 6145 return 0; 6146 6147 for (i = 0; i < num_rep; i++) { 6148 struct bnxt_representor representor = { 6149 .vf_id = eth_da->representor_ports[i], 6150 .switch_domain_id = backing_bp->switch_domain_id, 6151 .parent_dev = backing_eth_dev 6152 }; 6153 6154 if (representor.vf_id >= BNXT_MAX_VF_REPS) { 6155 PMD_DRV_LOG(ERR, "VF-Rep id %d >= %d MAX VF ID\n", 6156 representor.vf_id, BNXT_MAX_VF_REPS); 6157 continue; 6158 } 6159 6160 /* representor port net_bdf_port */ 6161 snprintf(name, sizeof(name), "net_%s_representor_%d", 6162 pci_dev->device.name, eth_da->representor_ports[i]); 6163 6164 kvlist = rte_kvargs_parse(dev_args, bnxt_dev_args); 6165 if (kvlist) { 6166 /* 6167 * Handler for "rep_is_pf" devarg. 6168 * Invoked as for ex: "-a 000:00:0d.0, 6169 * rep-based-pf=<pf index> rep-is-pf=<VF=0 or PF=1>" 6170 */ 6171 ret = rte_kvargs_process(kvlist, BNXT_DEVARG_REP_IS_PF, 6172 bnxt_parse_devarg_rep_is_pf, 6173 (void *)&representor); 6174 if (ret) { 6175 ret = -EINVAL; 6176 goto err; 6177 } 6178 /* 6179 * Handler for "rep_based_pf" devarg. 6180 * Invoked as for ex: "-a 000:00:0d.0, 6181 * rep-based-pf=<pf index> rep-is-pf=<VF=0 or PF=1>" 6182 */ 6183 ret = rte_kvargs_process(kvlist, 6184 BNXT_DEVARG_REP_BASED_PF, 6185 bnxt_parse_devarg_rep_based_pf, 6186 (void *)&representor); 6187 if (ret) { 6188 ret = -EINVAL; 6189 goto err; 6190 } 6191 /* 6192 * Handler for "rep_based_pf" devarg. 6193 * Invoked as for ex: "-a 000:00:0d.0, 6194 * rep-based-pf=<pf index> rep-is-pf=<VF=0 or PF=1>" 6195 */ 6196 ret = rte_kvargs_process(kvlist, BNXT_DEVARG_REP_Q_R2F, 6197 bnxt_parse_devarg_rep_q_r2f, 6198 (void *)&representor); 6199 if (ret) { 6200 ret = -EINVAL; 6201 goto err; 6202 } 6203 /* 6204 * Handler for "rep_based_pf" devarg. 6205 * Invoked as for ex: "-a 000:00:0d.0, 6206 * rep-based-pf=<pf index> rep-is-pf=<VF=0 or PF=1>" 6207 */ 6208 ret = rte_kvargs_process(kvlist, BNXT_DEVARG_REP_Q_F2R, 6209 bnxt_parse_devarg_rep_q_f2r, 6210 (void *)&representor); 6211 if (ret) { 6212 ret = -EINVAL; 6213 goto err; 6214 } 6215 /* 6216 * Handler for "rep_based_pf" devarg. 6217 * Invoked as for ex: "-a 000:00:0d.0, 6218 * rep-based-pf=<pf index> rep-is-pf=<VF=0 or PF=1>" 6219 */ 6220 ret = rte_kvargs_process(kvlist, BNXT_DEVARG_REP_FC_R2F, 6221 bnxt_parse_devarg_rep_fc_r2f, 6222 (void *)&representor); 6223 if (ret) { 6224 ret = -EINVAL; 6225 goto err; 6226 } 6227 /* 6228 * Handler for "rep_based_pf" devarg. 6229 * Invoked as for ex: "-a 000:00:0d.0, 6230 * rep-based-pf=<pf index> rep-is-pf=<VF=0 or PF=1>" 6231 */ 6232 ret = rte_kvargs_process(kvlist, BNXT_DEVARG_REP_FC_F2R, 6233 bnxt_parse_devarg_rep_fc_f2r, 6234 (void *)&representor); 6235 if (ret) { 6236 ret = -EINVAL; 6237 goto err; 6238 } 6239 } 6240 6241 ret = rte_eth_dev_create(&pci_dev->device, name, 6242 sizeof(struct bnxt_representor), 6243 NULL, NULL, 6244 bnxt_representor_init, 6245 &representor); 6246 if (ret) { 6247 PMD_DRV_LOG(ERR, "failed to create bnxt vf " 6248 "representor %s.", name); 6249 goto err; 6250 } 6251 6252 vf_rep_eth_dev = rte_eth_dev_allocated(name); 6253 if (!vf_rep_eth_dev) { 6254 PMD_DRV_LOG(ERR, "Failed to find the eth_dev" 6255 " for VF-Rep: %s.", name); 6256 ret = -ENODEV; 6257 goto err; 6258 } 6259 6260 PMD_DRV_LOG(DEBUG, "BNXT Port:%d VFR pci probe\n", 6261 backing_eth_dev->data->port_id); 6262 backing_bp->rep_info[representor.vf_id].vfr_eth_dev = 6263 vf_rep_eth_dev; 6264 backing_bp->num_reps++; 6265 6266 } 6267 6268 rte_kvargs_free(kvlist); 6269 return 0; 6270 6271 err: 6272 /* If num_rep > 1, then rollback already created 6273 * ports, since we'll be failing the probe anyway 6274 */ 6275 if (num_rep > 1) 6276 bnxt_pci_remove_dev_with_reps(backing_eth_dev); 6277 rte_errno = -ret; 6278 rte_kvargs_free(kvlist); 6279 6280 return ret; 6281 } 6282 6283 static int bnxt_pci_probe(struct rte_pci_driver *pci_drv __rte_unused, 6284 struct rte_pci_device *pci_dev) 6285 { 6286 struct rte_eth_devargs eth_da = { .nb_representor_ports = 0 }; 6287 struct rte_eth_dev *backing_eth_dev; 6288 uint16_t num_rep; 6289 int ret = 0; 6290 6291 if (pci_dev->device.devargs) { 6292 ret = rte_eth_devargs_parse(pci_dev->device.devargs->args, 6293 ð_da); 6294 if (ret) 6295 return ret; 6296 } 6297 6298 num_rep = eth_da.nb_representor_ports; 6299 PMD_DRV_LOG(DEBUG, "nb_representor_ports = %d\n", 6300 num_rep); 6301 6302 /* We could come here after first level of probe is already invoked 6303 * as part of an application bringup(OVS-DPDK vswitchd), so first check 6304 * for already allocated eth_dev for the backing device (PF/Trusted VF) 6305 */ 6306 backing_eth_dev = rte_eth_dev_allocated(pci_dev->device.name); 6307 if (backing_eth_dev == NULL) { 6308 ret = rte_eth_dev_create(&pci_dev->device, pci_dev->device.name, 6309 sizeof(struct bnxt), 6310 eth_dev_pci_specific_init, pci_dev, 6311 bnxt_dev_init, NULL); 6312 6313 if (ret || !num_rep) 6314 return ret; 6315 6316 backing_eth_dev = rte_eth_dev_allocated(pci_dev->device.name); 6317 } 6318 PMD_DRV_LOG(DEBUG, "BNXT Port:%d pci probe\n", 6319 backing_eth_dev->data->port_id); 6320 6321 if (!num_rep) 6322 return ret; 6323 6324 /* probe representor ports now */ 6325 ret = bnxt_rep_port_probe(pci_dev, ð_da, backing_eth_dev, 6326 pci_dev->device.devargs->args); 6327 6328 return ret; 6329 } 6330 6331 static int bnxt_pci_remove(struct rte_pci_device *pci_dev) 6332 { 6333 struct rte_eth_dev *eth_dev; 6334 6335 eth_dev = rte_eth_dev_allocated(pci_dev->device.name); 6336 if (!eth_dev) 6337 return 0; /* Invoked typically only by OVS-DPDK, by the 6338 * time it comes here the eth_dev is already 6339 * deleted by rte_eth_dev_close(), so returning 6340 * +ve value will at least help in proper cleanup 6341 */ 6342 6343 PMD_DRV_LOG(DEBUG, "BNXT Port:%d pci remove\n", eth_dev->data->port_id); 6344 if (rte_eal_process_type() == RTE_PROC_PRIMARY) { 6345 if (eth_dev->data->dev_flags & RTE_ETH_DEV_REPRESENTOR) 6346 return rte_eth_dev_destroy(eth_dev, 6347 bnxt_representor_uninit); 6348 else 6349 return rte_eth_dev_destroy(eth_dev, 6350 bnxt_dev_uninit); 6351 } else { 6352 return rte_eth_dev_pci_generic_remove(pci_dev, NULL); 6353 } 6354 } 6355 6356 static struct rte_pci_driver bnxt_rte_pmd = { 6357 .id_table = bnxt_pci_id_map, 6358 .drv_flags = RTE_PCI_DRV_NEED_MAPPING | RTE_PCI_DRV_INTR_LSC | 6359 RTE_PCI_DRV_PROBE_AGAIN, /* Needed in case of VF-REPs 6360 * and OVS-DPDK 6361 */ 6362 .probe = bnxt_pci_probe, 6363 .remove = bnxt_pci_remove, 6364 }; 6365 6366 static bool 6367 is_device_supported(struct rte_eth_dev *dev, struct rte_pci_driver *drv) 6368 { 6369 if (strcmp(dev->device->driver->name, drv->driver.name)) 6370 return false; 6371 6372 return true; 6373 } 6374 6375 bool is_bnxt_supported(struct rte_eth_dev *dev) 6376 { 6377 return is_device_supported(dev, &bnxt_rte_pmd); 6378 } 6379 6380 RTE_LOG_REGISTER_SUFFIX(bnxt_logtype_driver, driver, NOTICE); 6381 RTE_PMD_REGISTER_PCI(net_bnxt, bnxt_rte_pmd); 6382 RTE_PMD_REGISTER_PCI_TABLE(net_bnxt, bnxt_pci_id_map); 6383 RTE_PMD_REGISTER_KMOD_DEP(net_bnxt, "* igb_uio | uio_pci_generic | vfio-pci"); 6384