1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright(c) 2014-2018 Broadcom 3 * All rights reserved. 4 */ 5 6 #include <inttypes.h> 7 #include <stdbool.h> 8 9 #include <rte_dev.h> 10 #include <rte_ethdev_driver.h> 11 #include <rte_ethdev_pci.h> 12 #include <rte_malloc.h> 13 #include <rte_cycles.h> 14 #include <rte_alarm.h> 15 16 #include "bnxt.h" 17 #include "bnxt_filter.h" 18 #include "bnxt_hwrm.h" 19 #include "bnxt_irq.h" 20 #include "bnxt_ring.h" 21 #include "bnxt_rxq.h" 22 #include "bnxt_rxr.h" 23 #include "bnxt_stats.h" 24 #include "bnxt_txq.h" 25 #include "bnxt_txr.h" 26 #include "bnxt_vnic.h" 27 #include "hsi_struct_def_dpdk.h" 28 #include "bnxt_nvm_defs.h" 29 30 #define DRV_MODULE_NAME "bnxt" 31 static const char bnxt_version[] = 32 "Broadcom NetXtreme driver " DRV_MODULE_NAME; 33 int bnxt_logtype_driver; 34 35 /* 36 * The set of PCI devices this driver supports 37 */ 38 static const struct rte_pci_id bnxt_pci_id_map[] = { 39 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 40 BROADCOM_DEV_ID_STRATUS_NIC_VF1) }, 41 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, 42 BROADCOM_DEV_ID_STRATUS_NIC_VF2) }, 43 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_STRATUS_NIC) }, 44 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57414_VF) }, 45 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57301) }, 46 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57302) }, 47 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57304_PF) }, 48 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57304_VF) }, 49 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_NS2) }, 50 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57402) }, 51 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57404) }, 52 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57406_PF) }, 53 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57406_VF) }, 54 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57402_MF) }, 55 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57407_RJ45) }, 56 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57404_MF) }, 57 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57406_MF) }, 58 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57407_SFP) }, 59 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57407_MF) }, 60 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_5741X_VF) }, 61 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_5731X_VF) }, 62 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57314) }, 63 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57417_MF) }, 64 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57311) }, 65 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57312) }, 66 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57412) }, 67 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57414) }, 68 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57416_RJ45) }, 69 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57417_RJ45) }, 70 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57412_MF) }, 71 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57317_RJ45) }, 72 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57417_SFP) }, 73 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57416_SFP) }, 74 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57317_SFP) }, 75 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57414_MF) }, 76 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57416_MF) }, 77 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58802) }, 78 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58804) }, 79 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58808) }, 80 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_58802_VF) }, 81 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57508) }, 82 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57504) }, 83 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57502) }, 84 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57500_VF1) }, 85 { RTE_PCI_DEVICE(PCI_VENDOR_ID_BROADCOM, BROADCOM_DEV_ID_57500_VF2) }, 86 { .vendor_id = 0, /* sentinel */ }, 87 }; 88 89 #define BNXT_ETH_RSS_SUPPORT ( \ 90 ETH_RSS_IPV4 | \ 91 ETH_RSS_NONFRAG_IPV4_TCP | \ 92 ETH_RSS_NONFRAG_IPV4_UDP | \ 93 ETH_RSS_IPV6 | \ 94 ETH_RSS_NONFRAG_IPV6_TCP | \ 95 ETH_RSS_NONFRAG_IPV6_UDP) 96 97 #define BNXT_DEV_TX_OFFLOAD_SUPPORT (DEV_TX_OFFLOAD_VLAN_INSERT | \ 98 DEV_TX_OFFLOAD_IPV4_CKSUM | \ 99 DEV_TX_OFFLOAD_TCP_CKSUM | \ 100 DEV_TX_OFFLOAD_UDP_CKSUM | \ 101 DEV_TX_OFFLOAD_TCP_TSO | \ 102 DEV_TX_OFFLOAD_OUTER_IPV4_CKSUM | \ 103 DEV_TX_OFFLOAD_VXLAN_TNL_TSO | \ 104 DEV_TX_OFFLOAD_GRE_TNL_TSO | \ 105 DEV_TX_OFFLOAD_IPIP_TNL_TSO | \ 106 DEV_TX_OFFLOAD_GENEVE_TNL_TSO | \ 107 DEV_TX_OFFLOAD_QINQ_INSERT | \ 108 DEV_TX_OFFLOAD_MULTI_SEGS) 109 110 #define BNXT_DEV_RX_OFFLOAD_SUPPORT (DEV_RX_OFFLOAD_VLAN_FILTER | \ 111 DEV_RX_OFFLOAD_VLAN_STRIP | \ 112 DEV_RX_OFFLOAD_IPV4_CKSUM | \ 113 DEV_RX_OFFLOAD_UDP_CKSUM | \ 114 DEV_RX_OFFLOAD_TCP_CKSUM | \ 115 DEV_RX_OFFLOAD_OUTER_IPV4_CKSUM | \ 116 DEV_RX_OFFLOAD_JUMBO_FRAME | \ 117 DEV_RX_OFFLOAD_KEEP_CRC | \ 118 DEV_RX_OFFLOAD_VLAN_EXTEND | \ 119 DEV_RX_OFFLOAD_TCP_LRO | \ 120 DEV_RX_OFFLOAD_SCATTER) 121 122 static int bnxt_vlan_offload_set_op(struct rte_eth_dev *dev, int mask); 123 static void bnxt_print_link_info(struct rte_eth_dev *eth_dev); 124 static int bnxt_mtu_set_op(struct rte_eth_dev *eth_dev, uint16_t new_mtu); 125 static int bnxt_dev_uninit(struct rte_eth_dev *eth_dev); 126 static int bnxt_init_resources(struct bnxt *bp, bool reconfig_dev); 127 static int bnxt_uninit_resources(struct bnxt *bp, bool reconfig_dev); 128 static void bnxt_cancel_fw_health_check(struct bnxt *bp); 129 130 int is_bnxt_in_error(struct bnxt *bp) 131 { 132 if (bp->flags & BNXT_FLAG_FATAL_ERROR) 133 return -EIO; 134 if (bp->flags & BNXT_FLAG_FW_RESET) 135 return -EBUSY; 136 137 return 0; 138 } 139 140 /***********************/ 141 142 /* 143 * High level utility functions 144 */ 145 146 uint16_t bnxt_rss_ctxts(const struct bnxt *bp) 147 { 148 if (!BNXT_CHIP_THOR(bp)) 149 return 1; 150 151 return RTE_ALIGN_MUL_CEIL(bp->rx_nr_rings, 152 BNXT_RSS_ENTRIES_PER_CTX_THOR) / 153 BNXT_RSS_ENTRIES_PER_CTX_THOR; 154 } 155 156 static uint16_t bnxt_rss_hash_tbl_size(const struct bnxt *bp) 157 { 158 if (!BNXT_CHIP_THOR(bp)) 159 return HW_HASH_INDEX_SIZE; 160 161 return bnxt_rss_ctxts(bp) * BNXT_RSS_ENTRIES_PER_CTX_THOR; 162 } 163 164 static void bnxt_free_mem(struct bnxt *bp, bool reconfig) 165 { 166 bnxt_free_filter_mem(bp); 167 bnxt_free_vnic_attributes(bp); 168 bnxt_free_vnic_mem(bp); 169 170 /* tx/rx rings are configured as part of *_queue_setup callbacks. 171 * If the number of rings change across fw update, 172 * we don't have much choice except to warn the user. 173 */ 174 if (!reconfig) { 175 bnxt_free_stats(bp); 176 bnxt_free_tx_rings(bp); 177 bnxt_free_rx_rings(bp); 178 } 179 bnxt_free_async_cp_ring(bp); 180 bnxt_free_rxtx_nq_ring(bp); 181 } 182 183 static int bnxt_alloc_mem(struct bnxt *bp, bool reconfig) 184 { 185 int rc; 186 187 rc = bnxt_alloc_ring_grps(bp); 188 if (rc) 189 goto alloc_mem_err; 190 191 rc = bnxt_alloc_async_ring_struct(bp); 192 if (rc) 193 goto alloc_mem_err; 194 195 rc = bnxt_alloc_vnic_mem(bp); 196 if (rc) 197 goto alloc_mem_err; 198 199 rc = bnxt_alloc_vnic_attributes(bp); 200 if (rc) 201 goto alloc_mem_err; 202 203 rc = bnxt_alloc_filter_mem(bp); 204 if (rc) 205 goto alloc_mem_err; 206 207 rc = bnxt_alloc_async_cp_ring(bp); 208 if (rc) 209 goto alloc_mem_err; 210 211 rc = bnxt_alloc_rxtx_nq_ring(bp); 212 if (rc) 213 goto alloc_mem_err; 214 215 return 0; 216 217 alloc_mem_err: 218 bnxt_free_mem(bp, reconfig); 219 return rc; 220 } 221 222 static int bnxt_init_chip(struct bnxt *bp) 223 { 224 struct bnxt_rx_queue *rxq; 225 struct rte_eth_link new; 226 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(bp->eth_dev); 227 struct rte_eth_conf *dev_conf = &bp->eth_dev->data->dev_conf; 228 struct rte_intr_handle *intr_handle = &pci_dev->intr_handle; 229 uint64_t rx_offloads = dev_conf->rxmode.offloads; 230 uint32_t intr_vector = 0; 231 uint32_t queue_id, base = BNXT_MISC_VEC_ID; 232 uint32_t vec = BNXT_MISC_VEC_ID; 233 unsigned int i, j; 234 int rc; 235 236 if (bp->eth_dev->data->mtu > RTE_ETHER_MTU) { 237 bp->eth_dev->data->dev_conf.rxmode.offloads |= 238 DEV_RX_OFFLOAD_JUMBO_FRAME; 239 bp->flags |= BNXT_FLAG_JUMBO; 240 } else { 241 bp->eth_dev->data->dev_conf.rxmode.offloads &= 242 ~DEV_RX_OFFLOAD_JUMBO_FRAME; 243 bp->flags &= ~BNXT_FLAG_JUMBO; 244 } 245 246 /* THOR does not support ring groups. 247 * But we will use the array to save RSS context IDs. 248 */ 249 if (BNXT_CHIP_THOR(bp)) 250 bp->max_ring_grps = BNXT_MAX_RSS_CTXTS_THOR; 251 252 rc = bnxt_alloc_all_hwrm_stat_ctxs(bp); 253 if (rc) { 254 PMD_DRV_LOG(ERR, "HWRM stat ctx alloc failure rc: %x\n", rc); 255 goto err_out; 256 } 257 258 rc = bnxt_alloc_hwrm_rings(bp); 259 if (rc) { 260 PMD_DRV_LOG(ERR, "HWRM ring alloc failure rc: %x\n", rc); 261 goto err_out; 262 } 263 264 rc = bnxt_alloc_all_hwrm_ring_grps(bp); 265 if (rc) { 266 PMD_DRV_LOG(ERR, "HWRM ring grp alloc failure: %x\n", rc); 267 goto err_out; 268 } 269 270 if (!(bp->vnic_cap_flags & BNXT_VNIC_CAP_COS_CLASSIFY)) 271 goto skip_cosq_cfg; 272 273 for (j = 0, i = 0; i < BNXT_COS_QUEUE_COUNT; i++) { 274 if (bp->rx_cos_queue[i].id != 0xff) { 275 struct bnxt_vnic_info *vnic = &bp->vnic_info[j++]; 276 277 if (!vnic) { 278 PMD_DRV_LOG(ERR, 279 "Num pools more than FW profile\n"); 280 rc = -EINVAL; 281 goto err_out; 282 } 283 vnic->cos_queue_id = bp->rx_cos_queue[i].id; 284 bp->rx_cosq_cnt++; 285 } 286 } 287 288 skip_cosq_cfg: 289 rc = bnxt_mq_rx_configure(bp); 290 if (rc) { 291 PMD_DRV_LOG(ERR, "MQ mode configure failure rc: %x\n", rc); 292 goto err_out; 293 } 294 295 /* VNIC configuration */ 296 for (i = 0; i < bp->nr_vnics; i++) { 297 struct rte_eth_conf *dev_conf = &bp->eth_dev->data->dev_conf; 298 struct bnxt_vnic_info *vnic = &bp->vnic_info[i]; 299 300 rc = bnxt_vnic_grp_alloc(bp, vnic); 301 if (rc) 302 goto err_out; 303 304 PMD_DRV_LOG(DEBUG, "vnic[%d] = %p vnic->fw_grp_ids = %p\n", 305 i, vnic, vnic->fw_grp_ids); 306 307 rc = bnxt_hwrm_vnic_alloc(bp, vnic); 308 if (rc) { 309 PMD_DRV_LOG(ERR, "HWRM vnic %d alloc failure rc: %x\n", 310 i, rc); 311 goto err_out; 312 } 313 314 /* Alloc RSS context only if RSS mode is enabled */ 315 if (dev_conf->rxmode.mq_mode & ETH_MQ_RX_RSS) { 316 int j, nr_ctxs = bnxt_rss_ctxts(bp); 317 318 rc = 0; 319 for (j = 0; j < nr_ctxs; j++) { 320 rc = bnxt_hwrm_vnic_ctx_alloc(bp, vnic, j); 321 if (rc) 322 break; 323 } 324 if (rc) { 325 PMD_DRV_LOG(ERR, 326 "HWRM vnic %d ctx %d alloc failure rc: %x\n", 327 i, j, rc); 328 goto err_out; 329 } 330 vnic->num_lb_ctxts = nr_ctxs; 331 } 332 333 /* 334 * Firmware sets pf pair in default vnic cfg. If the VLAN strip 335 * setting is not available at this time, it will not be 336 * configured correctly in the CFA. 337 */ 338 if (rx_offloads & DEV_RX_OFFLOAD_VLAN_STRIP) 339 vnic->vlan_strip = true; 340 else 341 vnic->vlan_strip = false; 342 343 rc = bnxt_hwrm_vnic_cfg(bp, vnic); 344 if (rc) { 345 PMD_DRV_LOG(ERR, "HWRM vnic %d cfg failure rc: %x\n", 346 i, rc); 347 goto err_out; 348 } 349 350 rc = bnxt_set_hwrm_vnic_filters(bp, vnic); 351 if (rc) { 352 PMD_DRV_LOG(ERR, 353 "HWRM vnic %d filter failure rc: %x\n", 354 i, rc); 355 goto err_out; 356 } 357 358 for (j = 0; j < bp->rx_num_qs_per_vnic; j++) { 359 rxq = bp->eth_dev->data->rx_queues[j]; 360 361 PMD_DRV_LOG(DEBUG, 362 "rxq[%d]->vnic=%p vnic->fw_grp_ids=%p\n", 363 j, rxq->vnic, rxq->vnic->fw_grp_ids); 364 365 if (BNXT_HAS_RING_GRPS(bp) && rxq->rx_deferred_start) 366 rxq->vnic->fw_grp_ids[j] = INVALID_HW_RING_ID; 367 } 368 369 rc = bnxt_vnic_rss_configure(bp, vnic); 370 if (rc) { 371 PMD_DRV_LOG(ERR, 372 "HWRM vnic set RSS failure rc: %x\n", rc); 373 goto err_out; 374 } 375 376 bnxt_hwrm_vnic_plcmode_cfg(bp, vnic); 377 378 if (bp->eth_dev->data->dev_conf.rxmode.offloads & 379 DEV_RX_OFFLOAD_TCP_LRO) 380 bnxt_hwrm_vnic_tpa_cfg(bp, vnic, 1); 381 else 382 bnxt_hwrm_vnic_tpa_cfg(bp, vnic, 0); 383 } 384 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, &bp->vnic_info[0], 0, NULL); 385 if (rc) { 386 PMD_DRV_LOG(ERR, 387 "HWRM cfa l2 rx mask failure rc: %x\n", rc); 388 goto err_out; 389 } 390 391 /* check and configure queue intr-vector mapping */ 392 if ((rte_intr_cap_multiple(intr_handle) || 393 !RTE_ETH_DEV_SRIOV(bp->eth_dev).active) && 394 bp->eth_dev->data->dev_conf.intr_conf.rxq != 0) { 395 intr_vector = bp->eth_dev->data->nb_rx_queues; 396 PMD_DRV_LOG(DEBUG, "intr_vector = %d\n", intr_vector); 397 if (intr_vector > bp->rx_cp_nr_rings) { 398 PMD_DRV_LOG(ERR, "At most %d intr queues supported", 399 bp->rx_cp_nr_rings); 400 return -ENOTSUP; 401 } 402 rc = rte_intr_efd_enable(intr_handle, intr_vector); 403 if (rc) 404 return rc; 405 } 406 407 if (rte_intr_dp_is_en(intr_handle) && !intr_handle->intr_vec) { 408 intr_handle->intr_vec = 409 rte_zmalloc("intr_vec", 410 bp->eth_dev->data->nb_rx_queues * 411 sizeof(int), 0); 412 if (intr_handle->intr_vec == NULL) { 413 PMD_DRV_LOG(ERR, "Failed to allocate %d rx_queues" 414 " intr_vec", bp->eth_dev->data->nb_rx_queues); 415 rc = -ENOMEM; 416 goto err_disable; 417 } 418 PMD_DRV_LOG(DEBUG, "intr_handle->intr_vec = %p " 419 "intr_handle->nb_efd = %d intr_handle->max_intr = %d\n", 420 intr_handle->intr_vec, intr_handle->nb_efd, 421 intr_handle->max_intr); 422 for (queue_id = 0; queue_id < bp->eth_dev->data->nb_rx_queues; 423 queue_id++) { 424 intr_handle->intr_vec[queue_id] = 425 vec + BNXT_RX_VEC_START; 426 if (vec < base + intr_handle->nb_efd - 1) 427 vec++; 428 } 429 } 430 431 /* enable uio/vfio intr/eventfd mapping */ 432 rc = rte_intr_enable(intr_handle); 433 if (rc) 434 goto err_free; 435 436 rc = bnxt_get_hwrm_link_config(bp, &new); 437 if (rc) { 438 PMD_DRV_LOG(ERR, "HWRM Get link config failure rc: %x\n", rc); 439 goto err_free; 440 } 441 442 if (!bp->link_info.link_up) { 443 rc = bnxt_set_hwrm_link_config(bp, true); 444 if (rc) { 445 PMD_DRV_LOG(ERR, 446 "HWRM link config failure rc: %x\n", rc); 447 goto err_free; 448 } 449 } 450 bnxt_print_link_info(bp->eth_dev); 451 452 return 0; 453 454 err_free: 455 rte_free(intr_handle->intr_vec); 456 err_disable: 457 rte_intr_efd_disable(intr_handle); 458 err_out: 459 /* Some of the error status returned by FW may not be from errno.h */ 460 if (rc > 0) 461 rc = -EIO; 462 463 return rc; 464 } 465 466 static int bnxt_shutdown_nic(struct bnxt *bp) 467 { 468 bnxt_free_all_hwrm_resources(bp); 469 bnxt_free_all_filters(bp); 470 bnxt_free_all_vnics(bp); 471 return 0; 472 } 473 474 static int bnxt_init_nic(struct bnxt *bp) 475 { 476 int rc; 477 478 if (BNXT_HAS_RING_GRPS(bp)) { 479 rc = bnxt_init_ring_grps(bp); 480 if (rc) 481 return rc; 482 } 483 484 bnxt_init_vnics(bp); 485 bnxt_init_filters(bp); 486 487 return 0; 488 } 489 490 /* 491 * Device configuration and status function 492 */ 493 494 static int bnxt_dev_info_get_op(struct rte_eth_dev *eth_dev, 495 struct rte_eth_dev_info *dev_info) 496 { 497 struct rte_pci_device *pdev = RTE_DEV_TO_PCI(eth_dev->device); 498 struct bnxt *bp = eth_dev->data->dev_private; 499 uint16_t max_vnics, i, j, vpool, vrxq; 500 unsigned int max_rx_rings; 501 int rc; 502 503 rc = is_bnxt_in_error(bp); 504 if (rc) 505 return rc; 506 507 /* MAC Specifics */ 508 dev_info->max_mac_addrs = bp->max_l2_ctx; 509 dev_info->max_hash_mac_addrs = 0; 510 511 /* PF/VF specifics */ 512 if (BNXT_PF(bp)) 513 dev_info->max_vfs = pdev->max_vfs; 514 515 max_rx_rings = RTE_MIN(bp->max_rx_rings, bp->max_stat_ctx); 516 /* For the sake of symmetry, max_rx_queues = max_tx_queues */ 517 dev_info->max_rx_queues = max_rx_rings; 518 dev_info->max_tx_queues = max_rx_rings; 519 dev_info->reta_size = bnxt_rss_hash_tbl_size(bp); 520 dev_info->hash_key_size = 40; 521 max_vnics = bp->max_vnics; 522 523 /* MTU specifics */ 524 dev_info->min_mtu = RTE_ETHER_MIN_MTU; 525 dev_info->max_mtu = BNXT_MAX_MTU; 526 527 /* Fast path specifics */ 528 dev_info->min_rx_bufsize = 1; 529 dev_info->max_rx_pktlen = BNXT_MAX_PKT_LEN; 530 531 dev_info->rx_offload_capa = BNXT_DEV_RX_OFFLOAD_SUPPORT; 532 if (bp->flags & BNXT_FLAG_PTP_SUPPORTED) 533 dev_info->rx_offload_capa |= DEV_RX_OFFLOAD_TIMESTAMP; 534 dev_info->tx_offload_capa = BNXT_DEV_TX_OFFLOAD_SUPPORT; 535 dev_info->flow_type_rss_offloads = BNXT_ETH_RSS_SUPPORT; 536 537 /* *INDENT-OFF* */ 538 dev_info->default_rxconf = (struct rte_eth_rxconf) { 539 .rx_thresh = { 540 .pthresh = 8, 541 .hthresh = 8, 542 .wthresh = 0, 543 }, 544 .rx_free_thresh = 32, 545 /* If no descriptors available, pkts are dropped by default */ 546 .rx_drop_en = 1, 547 }; 548 549 dev_info->default_txconf = (struct rte_eth_txconf) { 550 .tx_thresh = { 551 .pthresh = 32, 552 .hthresh = 0, 553 .wthresh = 0, 554 }, 555 .tx_free_thresh = 32, 556 .tx_rs_thresh = 32, 557 }; 558 eth_dev->data->dev_conf.intr_conf.lsc = 1; 559 560 eth_dev->data->dev_conf.intr_conf.rxq = 1; 561 dev_info->rx_desc_lim.nb_min = BNXT_MIN_RING_DESC; 562 dev_info->rx_desc_lim.nb_max = BNXT_MAX_RX_RING_DESC; 563 dev_info->tx_desc_lim.nb_min = BNXT_MIN_RING_DESC; 564 dev_info->tx_desc_lim.nb_max = BNXT_MAX_TX_RING_DESC; 565 566 /* *INDENT-ON* */ 567 568 /* 569 * TODO: default_rxconf, default_txconf, rx_desc_lim, and tx_desc_lim 570 * need further investigation. 571 */ 572 573 /* VMDq resources */ 574 vpool = 64; /* ETH_64_POOLS */ 575 vrxq = 128; /* ETH_VMDQ_DCB_NUM_QUEUES */ 576 for (i = 0; i < 4; vpool >>= 1, i++) { 577 if (max_vnics > vpool) { 578 for (j = 0; j < 5; vrxq >>= 1, j++) { 579 if (dev_info->max_rx_queues > vrxq) { 580 if (vpool > vrxq) 581 vpool = vrxq; 582 goto found; 583 } 584 } 585 /* Not enough resources to support VMDq */ 586 break; 587 } 588 } 589 /* Not enough resources to support VMDq */ 590 vpool = 0; 591 vrxq = 0; 592 found: 593 dev_info->max_vmdq_pools = vpool; 594 dev_info->vmdq_queue_num = vrxq; 595 596 dev_info->vmdq_pool_base = 0; 597 dev_info->vmdq_queue_base = 0; 598 599 return 0; 600 } 601 602 /* Configure the device based on the configuration provided */ 603 static int bnxt_dev_configure_op(struct rte_eth_dev *eth_dev) 604 { 605 struct bnxt *bp = eth_dev->data->dev_private; 606 uint64_t rx_offloads = eth_dev->data->dev_conf.rxmode.offloads; 607 int rc; 608 609 bp->rx_queues = (void *)eth_dev->data->rx_queues; 610 bp->tx_queues = (void *)eth_dev->data->tx_queues; 611 bp->tx_nr_rings = eth_dev->data->nb_tx_queues; 612 bp->rx_nr_rings = eth_dev->data->nb_rx_queues; 613 614 rc = is_bnxt_in_error(bp); 615 if (rc) 616 return rc; 617 618 if (BNXT_VF(bp) && (bp->flags & BNXT_FLAG_NEW_RM)) { 619 rc = bnxt_hwrm_check_vf_rings(bp); 620 if (rc) { 621 PMD_DRV_LOG(ERR, "HWRM insufficient resources\n"); 622 return -ENOSPC; 623 } 624 625 /* If a resource has already been allocated - in this case 626 * it is the async completion ring, free it. Reallocate it after 627 * resource reservation. This will ensure the resource counts 628 * are calculated correctly. 629 */ 630 if (!BNXT_HAS_NQ(bp) && bp->async_cp_ring) { 631 bnxt_disable_int(bp); 632 bnxt_free_cp_ring(bp, bp->async_cp_ring); 633 } 634 635 rc = bnxt_hwrm_func_reserve_vf_resc(bp, false); 636 if (rc) { 637 PMD_DRV_LOG(ERR, "HWRM resource alloc fail:%x\n", rc); 638 return -ENOSPC; 639 } 640 641 if (!BNXT_HAS_NQ(bp) && bp->async_cp_ring) { 642 rc = bnxt_alloc_async_cp_ring(bp); 643 if (rc) 644 return rc; 645 bnxt_enable_int(bp); 646 } 647 } else { 648 /* legacy driver needs to get updated values */ 649 rc = bnxt_hwrm_func_qcaps(bp); 650 if (rc) { 651 PMD_DRV_LOG(ERR, "hwrm func qcaps fail:%d\n", rc); 652 return rc; 653 } 654 } 655 656 /* Inherit new configurations */ 657 if (eth_dev->data->nb_rx_queues > bp->max_rx_rings || 658 eth_dev->data->nb_tx_queues > bp->max_tx_rings || 659 eth_dev->data->nb_rx_queues + eth_dev->data->nb_tx_queues 660 + BNXT_NUM_ASYNC_CPR(bp) > bp->max_cp_rings || 661 eth_dev->data->nb_rx_queues + eth_dev->data->nb_tx_queues > 662 bp->max_stat_ctx) 663 goto resource_error; 664 665 if (BNXT_HAS_RING_GRPS(bp) && 666 (uint32_t)(eth_dev->data->nb_rx_queues) > bp->max_ring_grps) 667 goto resource_error; 668 669 if (!(eth_dev->data->dev_conf.rxmode.mq_mode & ETH_MQ_RX_RSS) && 670 bp->max_vnics < eth_dev->data->nb_rx_queues) 671 goto resource_error; 672 673 bp->rx_cp_nr_rings = bp->rx_nr_rings; 674 bp->tx_cp_nr_rings = bp->tx_nr_rings; 675 676 if (rx_offloads & DEV_RX_OFFLOAD_JUMBO_FRAME) { 677 eth_dev->data->mtu = 678 eth_dev->data->dev_conf.rxmode.max_rx_pkt_len - 679 RTE_ETHER_HDR_LEN - RTE_ETHER_CRC_LEN - VLAN_TAG_SIZE * 680 BNXT_NUM_VLANS; 681 bnxt_mtu_set_op(eth_dev, eth_dev->data->mtu); 682 } 683 return 0; 684 685 resource_error: 686 PMD_DRV_LOG(ERR, 687 "Insufficient resources to support requested config\n"); 688 PMD_DRV_LOG(ERR, 689 "Num Queues Requested: Tx %d, Rx %d\n", 690 eth_dev->data->nb_tx_queues, 691 eth_dev->data->nb_rx_queues); 692 PMD_DRV_LOG(ERR, 693 "MAX: TxQ %d, RxQ %d, CQ %d Stat %d, Grp %d, Vnic %d\n", 694 bp->max_tx_rings, bp->max_rx_rings, bp->max_cp_rings, 695 bp->max_stat_ctx, bp->max_ring_grps, bp->max_vnics); 696 return -ENOSPC; 697 } 698 699 static void bnxt_print_link_info(struct rte_eth_dev *eth_dev) 700 { 701 struct rte_eth_link *link = ð_dev->data->dev_link; 702 703 if (link->link_status) 704 PMD_DRV_LOG(INFO, "Port %d Link Up - speed %u Mbps - %s\n", 705 eth_dev->data->port_id, 706 (uint32_t)link->link_speed, 707 (link->link_duplex == ETH_LINK_FULL_DUPLEX) ? 708 ("full-duplex") : ("half-duplex\n")); 709 else 710 PMD_DRV_LOG(INFO, "Port %d Link Down\n", 711 eth_dev->data->port_id); 712 } 713 714 /* 715 * Determine whether the current configuration requires support for scattered 716 * receive; return 1 if scattered receive is required and 0 if not. 717 */ 718 static int bnxt_scattered_rx(struct rte_eth_dev *eth_dev) 719 { 720 uint16_t buf_size; 721 int i; 722 723 if (eth_dev->data->dev_conf.rxmode.offloads & DEV_RX_OFFLOAD_SCATTER) 724 return 1; 725 726 for (i = 0; i < eth_dev->data->nb_rx_queues; i++) { 727 struct bnxt_rx_queue *rxq = eth_dev->data->rx_queues[i]; 728 729 buf_size = (uint16_t)(rte_pktmbuf_data_room_size(rxq->mb_pool) - 730 RTE_PKTMBUF_HEADROOM); 731 if (eth_dev->data->dev_conf.rxmode.max_rx_pkt_len > buf_size) 732 return 1; 733 } 734 return 0; 735 } 736 737 static eth_rx_burst_t 738 bnxt_receive_function(__rte_unused struct rte_eth_dev *eth_dev) 739 { 740 #ifdef RTE_ARCH_X86 741 #ifndef RTE_LIBRTE_IEEE1588 742 /* 743 * Vector mode receive can be enabled only if scatter rx is not 744 * in use and rx offloads are limited to VLAN stripping and 745 * CRC stripping. 746 */ 747 if (!eth_dev->data->scattered_rx && 748 !(eth_dev->data->dev_conf.rxmode.offloads & 749 ~(DEV_RX_OFFLOAD_VLAN_STRIP | 750 DEV_RX_OFFLOAD_KEEP_CRC | 751 DEV_RX_OFFLOAD_JUMBO_FRAME | 752 DEV_RX_OFFLOAD_IPV4_CKSUM | 753 DEV_RX_OFFLOAD_UDP_CKSUM | 754 DEV_RX_OFFLOAD_TCP_CKSUM | 755 DEV_RX_OFFLOAD_OUTER_IPV4_CKSUM | 756 DEV_RX_OFFLOAD_VLAN_FILTER))) { 757 PMD_DRV_LOG(INFO, "Using vector mode receive for port %d\n", 758 eth_dev->data->port_id); 759 return bnxt_recv_pkts_vec; 760 } 761 PMD_DRV_LOG(INFO, "Vector mode receive disabled for port %d\n", 762 eth_dev->data->port_id); 763 PMD_DRV_LOG(INFO, 764 "Port %d scatter: %d rx offload: %" PRIX64 "\n", 765 eth_dev->data->port_id, 766 eth_dev->data->scattered_rx, 767 eth_dev->data->dev_conf.rxmode.offloads); 768 #endif 769 #endif 770 return bnxt_recv_pkts; 771 } 772 773 static eth_tx_burst_t 774 bnxt_transmit_function(__rte_unused struct rte_eth_dev *eth_dev) 775 { 776 #ifdef RTE_ARCH_X86 777 #ifndef RTE_LIBRTE_IEEE1588 778 /* 779 * Vector mode transmit can be enabled only if not using scatter rx 780 * or tx offloads. 781 */ 782 if (!eth_dev->data->scattered_rx && 783 !eth_dev->data->dev_conf.txmode.offloads) { 784 PMD_DRV_LOG(INFO, "Using vector mode transmit for port %d\n", 785 eth_dev->data->port_id); 786 return bnxt_xmit_pkts_vec; 787 } 788 PMD_DRV_LOG(INFO, "Vector mode transmit disabled for port %d\n", 789 eth_dev->data->port_id); 790 PMD_DRV_LOG(INFO, 791 "Port %d scatter: %d tx offload: %" PRIX64 "\n", 792 eth_dev->data->port_id, 793 eth_dev->data->scattered_rx, 794 eth_dev->data->dev_conf.txmode.offloads); 795 #endif 796 #endif 797 return bnxt_xmit_pkts; 798 } 799 800 static int bnxt_handle_if_change_status(struct bnxt *bp) 801 { 802 int rc; 803 804 /* Since fw has undergone a reset and lost all contexts, 805 * set fatal flag to not issue hwrm during cleanup 806 */ 807 bp->flags |= BNXT_FLAG_FATAL_ERROR; 808 bnxt_uninit_resources(bp, true); 809 810 /* clear fatal flag so that re-init happens */ 811 bp->flags &= ~BNXT_FLAG_FATAL_ERROR; 812 rc = bnxt_init_resources(bp, true); 813 814 bp->flags &= ~BNXT_FLAG_IF_CHANGE_HOT_FW_RESET_DONE; 815 816 return rc; 817 } 818 819 static int bnxt_dev_start_op(struct rte_eth_dev *eth_dev) 820 { 821 struct bnxt *bp = eth_dev->data->dev_private; 822 uint64_t rx_offloads = eth_dev->data->dev_conf.rxmode.offloads; 823 int vlan_mask = 0; 824 int rc; 825 826 if (bp->rx_cp_nr_rings > RTE_ETHDEV_QUEUE_STAT_CNTRS) { 827 PMD_DRV_LOG(ERR, 828 "RxQ cnt %d > CONFIG_RTE_ETHDEV_QUEUE_STAT_CNTRS %d\n", 829 bp->rx_cp_nr_rings, RTE_ETHDEV_QUEUE_STAT_CNTRS); 830 } 831 832 rc = bnxt_hwrm_if_change(bp, 1); 833 if (!rc) { 834 if (bp->flags & BNXT_FLAG_IF_CHANGE_HOT_FW_RESET_DONE) { 835 rc = bnxt_handle_if_change_status(bp); 836 if (rc) 837 return rc; 838 } 839 } 840 bnxt_enable_int(bp); 841 842 rc = bnxt_init_chip(bp); 843 if (rc) 844 goto error; 845 846 eth_dev->data->scattered_rx = bnxt_scattered_rx(eth_dev); 847 848 bnxt_link_update_op(eth_dev, 1); 849 850 if (rx_offloads & DEV_RX_OFFLOAD_VLAN_FILTER) 851 vlan_mask |= ETH_VLAN_FILTER_MASK; 852 if (rx_offloads & DEV_RX_OFFLOAD_VLAN_STRIP) 853 vlan_mask |= ETH_VLAN_STRIP_MASK; 854 rc = bnxt_vlan_offload_set_op(eth_dev, vlan_mask); 855 if (rc) 856 goto error; 857 858 eth_dev->rx_pkt_burst = bnxt_receive_function(eth_dev); 859 eth_dev->tx_pkt_burst = bnxt_transmit_function(eth_dev); 860 861 bp->flags |= BNXT_FLAG_INIT_DONE; 862 eth_dev->data->dev_started = 1; 863 bp->dev_stopped = 0; 864 bnxt_schedule_fw_health_check(bp); 865 return 0; 866 867 error: 868 bnxt_hwrm_if_change(bp, 0); 869 bnxt_shutdown_nic(bp); 870 bnxt_free_tx_mbufs(bp); 871 bnxt_free_rx_mbufs(bp); 872 return rc; 873 } 874 875 static int bnxt_dev_set_link_up_op(struct rte_eth_dev *eth_dev) 876 { 877 struct bnxt *bp = eth_dev->data->dev_private; 878 int rc = 0; 879 880 if (!bp->link_info.link_up) 881 rc = bnxt_set_hwrm_link_config(bp, true); 882 if (!rc) 883 eth_dev->data->dev_link.link_status = 1; 884 885 bnxt_print_link_info(eth_dev); 886 return rc; 887 } 888 889 static int bnxt_dev_set_link_down_op(struct rte_eth_dev *eth_dev) 890 { 891 struct bnxt *bp = eth_dev->data->dev_private; 892 893 eth_dev->data->dev_link.link_status = 0; 894 bnxt_set_hwrm_link_config(bp, false); 895 bp->link_info.link_up = 0; 896 897 return 0; 898 } 899 900 /* Unload the driver, release resources */ 901 static void bnxt_dev_stop_op(struct rte_eth_dev *eth_dev) 902 { 903 struct bnxt *bp = eth_dev->data->dev_private; 904 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(eth_dev); 905 struct rte_intr_handle *intr_handle = &pci_dev->intr_handle; 906 907 eth_dev->data->dev_started = 0; 908 /* Prevent crashes when queues are still in use */ 909 eth_dev->rx_pkt_burst = &bnxt_dummy_recv_pkts; 910 eth_dev->tx_pkt_burst = &bnxt_dummy_xmit_pkts; 911 912 bnxt_disable_int(bp); 913 914 /* disable uio/vfio intr/eventfd mapping */ 915 rte_intr_disable(intr_handle); 916 917 bnxt_cancel_fw_health_check(bp); 918 919 bp->flags &= ~BNXT_FLAG_INIT_DONE; 920 if (bp->eth_dev->data->dev_started) { 921 /* TBD: STOP HW queues DMA */ 922 eth_dev->data->dev_link.link_status = 0; 923 } 924 bnxt_dev_set_link_down_op(eth_dev); 925 926 /* Wait for link to be reset and the async notification to process. 927 * During reset recovery, there is no need to wait 928 */ 929 if (!is_bnxt_in_error(bp)) 930 rte_delay_ms(BNXT_LINK_WAIT_INTERVAL * 2); 931 932 /* Clean queue intr-vector mapping */ 933 rte_intr_efd_disable(intr_handle); 934 if (intr_handle->intr_vec != NULL) { 935 rte_free(intr_handle->intr_vec); 936 intr_handle->intr_vec = NULL; 937 } 938 939 bnxt_hwrm_port_clr_stats(bp); 940 bnxt_free_tx_mbufs(bp); 941 bnxt_free_rx_mbufs(bp); 942 /* Process any remaining notifications in default completion queue */ 943 bnxt_int_handler(eth_dev); 944 bnxt_shutdown_nic(bp); 945 bnxt_hwrm_if_change(bp, 0); 946 bp->dev_stopped = 1; 947 } 948 949 static void bnxt_dev_close_op(struct rte_eth_dev *eth_dev) 950 { 951 struct bnxt *bp = eth_dev->data->dev_private; 952 953 if (bp->dev_stopped == 0) 954 bnxt_dev_stop_op(eth_dev); 955 956 if (eth_dev->data->mac_addrs != NULL) { 957 rte_free(eth_dev->data->mac_addrs); 958 eth_dev->data->mac_addrs = NULL; 959 } 960 if (bp->grp_info != NULL) { 961 rte_free(bp->grp_info); 962 bp->grp_info = NULL; 963 } 964 965 bnxt_dev_uninit(eth_dev); 966 } 967 968 static void bnxt_mac_addr_remove_op(struct rte_eth_dev *eth_dev, 969 uint32_t index) 970 { 971 struct bnxt *bp = eth_dev->data->dev_private; 972 uint64_t pool_mask = eth_dev->data->mac_pool_sel[index]; 973 struct bnxt_vnic_info *vnic; 974 struct bnxt_filter_info *filter, *temp_filter; 975 uint32_t i; 976 977 if (is_bnxt_in_error(bp)) 978 return; 979 980 /* 981 * Loop through all VNICs from the specified filter flow pools to 982 * remove the corresponding MAC addr filter 983 */ 984 for (i = 0; i < bp->nr_vnics; i++) { 985 if (!(pool_mask & (1ULL << i))) 986 continue; 987 988 vnic = &bp->vnic_info[i]; 989 filter = STAILQ_FIRST(&vnic->filter); 990 while (filter) { 991 temp_filter = STAILQ_NEXT(filter, next); 992 if (filter->mac_index == index) { 993 STAILQ_REMOVE(&vnic->filter, filter, 994 bnxt_filter_info, next); 995 bnxt_hwrm_clear_l2_filter(bp, filter); 996 filter->mac_index = INVALID_MAC_INDEX; 997 memset(&filter->l2_addr, 0, RTE_ETHER_ADDR_LEN); 998 STAILQ_INSERT_TAIL(&bp->free_filter_list, 999 filter, next); 1000 } 1001 filter = temp_filter; 1002 } 1003 } 1004 } 1005 1006 static int bnxt_add_mac_filter(struct bnxt *bp, struct bnxt_vnic_info *vnic, 1007 struct rte_ether_addr *mac_addr, uint32_t index) 1008 { 1009 struct bnxt_filter_info *filter; 1010 int rc = 0; 1011 1012 filter = STAILQ_FIRST(&vnic->filter); 1013 /* During bnxt_mac_addr_add_op, default MAC is 1014 * already programmed, so skip it. But, when 1015 * hw-vlan-filter is turned OFF from ON, default 1016 * MAC filter should be restored 1017 */ 1018 if (filter->dflt) 1019 return 0; 1020 1021 filter = bnxt_alloc_filter(bp); 1022 if (!filter) { 1023 PMD_DRV_LOG(ERR, "L2 filter alloc failed\n"); 1024 return -ENODEV; 1025 } 1026 1027 filter->mac_index = index; 1028 /* bnxt_alloc_filter copies default MAC to filter->l2_addr. So, 1029 * if the MAC that's been programmed now is a different one, then, 1030 * copy that addr to filter->l2_addr 1031 */ 1032 if (mac_addr) 1033 memcpy(filter->l2_addr, mac_addr, RTE_ETHER_ADDR_LEN); 1034 filter->flags |= HWRM_CFA_L2_FILTER_ALLOC_INPUT_FLAGS_OUTERMOST; 1035 1036 rc = bnxt_hwrm_set_l2_filter(bp, vnic->fw_vnic_id, filter); 1037 if (!rc) { 1038 if (filter->mac_index == 0) { 1039 filter->dflt = true; 1040 STAILQ_INSERT_HEAD(&vnic->filter, filter, next); 1041 } else { 1042 STAILQ_INSERT_TAIL(&vnic->filter, filter, next); 1043 } 1044 } else { 1045 filter->mac_index = INVALID_MAC_INDEX; 1046 memset(&filter->l2_addr, 0, RTE_ETHER_ADDR_LEN); 1047 bnxt_free_filter(bp, filter); 1048 } 1049 1050 return rc; 1051 } 1052 1053 static int bnxt_mac_addr_add_op(struct rte_eth_dev *eth_dev, 1054 struct rte_ether_addr *mac_addr, 1055 uint32_t index, uint32_t pool) 1056 { 1057 struct bnxt *bp = eth_dev->data->dev_private; 1058 struct bnxt_vnic_info *vnic = &bp->vnic_info[pool]; 1059 struct bnxt_filter_info *filter; 1060 int rc = 0; 1061 1062 rc = is_bnxt_in_error(bp); 1063 if (rc) 1064 return rc; 1065 1066 if (BNXT_VF(bp) & !BNXT_VF_IS_TRUSTED(bp)) { 1067 PMD_DRV_LOG(ERR, "Cannot add MAC address to a VF interface\n"); 1068 return -ENOTSUP; 1069 } 1070 1071 if (!vnic) { 1072 PMD_DRV_LOG(ERR, "VNIC not found for pool %d!\n", pool); 1073 return -EINVAL; 1074 } 1075 /* Attach requested MAC address to the new l2_filter */ 1076 STAILQ_FOREACH(filter, &vnic->filter, next) { 1077 if (filter->mac_index == index) { 1078 PMD_DRV_LOG(ERR, 1079 "MAC addr already existed for pool %d\n", pool); 1080 return 0; 1081 } 1082 } 1083 1084 rc = bnxt_add_mac_filter(bp, vnic, mac_addr, index); 1085 1086 return rc; 1087 } 1088 1089 int bnxt_link_update_op(struct rte_eth_dev *eth_dev, int wait_to_complete) 1090 { 1091 int rc = 0; 1092 struct bnxt *bp = eth_dev->data->dev_private; 1093 struct rte_eth_link new; 1094 unsigned int cnt = BNXT_LINK_WAIT_CNT; 1095 1096 rc = is_bnxt_in_error(bp); 1097 if (rc) 1098 return rc; 1099 1100 memset(&new, 0, sizeof(new)); 1101 do { 1102 /* Retrieve link info from hardware */ 1103 rc = bnxt_get_hwrm_link_config(bp, &new); 1104 if (rc) { 1105 new.link_speed = ETH_LINK_SPEED_100M; 1106 new.link_duplex = ETH_LINK_FULL_DUPLEX; 1107 PMD_DRV_LOG(ERR, 1108 "Failed to retrieve link rc = 0x%x!\n", rc); 1109 goto out; 1110 } 1111 1112 if (!wait_to_complete || new.link_status) 1113 break; 1114 1115 rte_delay_ms(BNXT_LINK_WAIT_INTERVAL); 1116 } while (cnt--); 1117 1118 out: 1119 /* Timed out or success */ 1120 if (new.link_status != eth_dev->data->dev_link.link_status || 1121 new.link_speed != eth_dev->data->dev_link.link_speed) { 1122 rte_eth_linkstatus_set(eth_dev, &new); 1123 1124 _rte_eth_dev_callback_process(eth_dev, 1125 RTE_ETH_EVENT_INTR_LSC, 1126 NULL); 1127 1128 bnxt_print_link_info(eth_dev); 1129 } 1130 1131 return rc; 1132 } 1133 1134 static int bnxt_promiscuous_enable_op(struct rte_eth_dev *eth_dev) 1135 { 1136 struct bnxt *bp = eth_dev->data->dev_private; 1137 struct bnxt_vnic_info *vnic; 1138 uint32_t old_flags; 1139 int rc; 1140 1141 rc = is_bnxt_in_error(bp); 1142 if (rc) 1143 return rc; 1144 1145 if (bp->vnic_info == NULL) 1146 return 0; 1147 1148 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1149 1150 old_flags = vnic->flags; 1151 vnic->flags |= BNXT_VNIC_INFO_PROMISC; 1152 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 1153 if (rc != 0) 1154 vnic->flags = old_flags; 1155 1156 return rc; 1157 } 1158 1159 static int bnxt_promiscuous_disable_op(struct rte_eth_dev *eth_dev) 1160 { 1161 struct bnxt *bp = eth_dev->data->dev_private; 1162 struct bnxt_vnic_info *vnic; 1163 uint32_t old_flags; 1164 int rc; 1165 1166 rc = is_bnxt_in_error(bp); 1167 if (rc) 1168 return rc; 1169 1170 if (bp->vnic_info == NULL) 1171 return 0; 1172 1173 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1174 1175 old_flags = vnic->flags; 1176 vnic->flags &= ~BNXT_VNIC_INFO_PROMISC; 1177 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 1178 if (rc != 0) 1179 vnic->flags = old_flags; 1180 1181 return rc; 1182 } 1183 1184 static int bnxt_allmulticast_enable_op(struct rte_eth_dev *eth_dev) 1185 { 1186 struct bnxt *bp = eth_dev->data->dev_private; 1187 struct bnxt_vnic_info *vnic; 1188 uint32_t old_flags; 1189 int rc; 1190 1191 rc = is_bnxt_in_error(bp); 1192 if (rc) 1193 return rc; 1194 1195 if (bp->vnic_info == NULL) 1196 return 0; 1197 1198 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1199 1200 old_flags = vnic->flags; 1201 vnic->flags |= BNXT_VNIC_INFO_ALLMULTI; 1202 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 1203 if (rc != 0) 1204 vnic->flags = old_flags; 1205 1206 return rc; 1207 } 1208 1209 static int bnxt_allmulticast_disable_op(struct rte_eth_dev *eth_dev) 1210 { 1211 struct bnxt *bp = eth_dev->data->dev_private; 1212 struct bnxt_vnic_info *vnic; 1213 uint32_t old_flags; 1214 int rc; 1215 1216 rc = is_bnxt_in_error(bp); 1217 if (rc) 1218 return rc; 1219 1220 if (bp->vnic_info == NULL) 1221 return 0; 1222 1223 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1224 1225 old_flags = vnic->flags; 1226 vnic->flags &= ~BNXT_VNIC_INFO_ALLMULTI; 1227 rc = bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 1228 if (rc != 0) 1229 vnic->flags = old_flags; 1230 1231 return rc; 1232 } 1233 1234 /* Return bnxt_rx_queue pointer corresponding to a given rxq. */ 1235 static struct bnxt_rx_queue *bnxt_qid_to_rxq(struct bnxt *bp, uint16_t qid) 1236 { 1237 if (qid >= bp->rx_nr_rings) 1238 return NULL; 1239 1240 return bp->eth_dev->data->rx_queues[qid]; 1241 } 1242 1243 /* Return rxq corresponding to a given rss table ring/group ID. */ 1244 static uint16_t bnxt_rss_to_qid(struct bnxt *bp, uint16_t fwr) 1245 { 1246 struct bnxt_rx_queue *rxq; 1247 unsigned int i; 1248 1249 if (!BNXT_HAS_RING_GRPS(bp)) { 1250 for (i = 0; i < bp->rx_nr_rings; i++) { 1251 rxq = bp->eth_dev->data->rx_queues[i]; 1252 if (rxq->rx_ring->rx_ring_struct->fw_ring_id == fwr) 1253 return rxq->index; 1254 } 1255 } else { 1256 for (i = 0; i < bp->rx_nr_rings; i++) { 1257 if (bp->grp_info[i].fw_grp_id == fwr) 1258 return i; 1259 } 1260 } 1261 1262 return INVALID_HW_RING_ID; 1263 } 1264 1265 static int bnxt_reta_update_op(struct rte_eth_dev *eth_dev, 1266 struct rte_eth_rss_reta_entry64 *reta_conf, 1267 uint16_t reta_size) 1268 { 1269 struct bnxt *bp = eth_dev->data->dev_private; 1270 struct rte_eth_conf *dev_conf = &bp->eth_dev->data->dev_conf; 1271 struct bnxt_vnic_info *vnic = &bp->vnic_info[0]; 1272 uint16_t tbl_size = bnxt_rss_hash_tbl_size(bp); 1273 uint16_t idx, sft; 1274 int i, rc; 1275 1276 rc = is_bnxt_in_error(bp); 1277 if (rc) 1278 return rc; 1279 1280 if (!vnic->rss_table) 1281 return -EINVAL; 1282 1283 if (!(dev_conf->rxmode.mq_mode & ETH_MQ_RX_RSS_FLAG)) 1284 return -EINVAL; 1285 1286 if (reta_size != tbl_size) { 1287 PMD_DRV_LOG(ERR, "The configured hash table lookup size " 1288 "(%d) must equal the size supported by the hardware " 1289 "(%d)\n", reta_size, tbl_size); 1290 return -EINVAL; 1291 } 1292 1293 for (i = 0; i < reta_size; i++) { 1294 struct bnxt_rx_queue *rxq; 1295 1296 idx = i / RTE_RETA_GROUP_SIZE; 1297 sft = i % RTE_RETA_GROUP_SIZE; 1298 1299 if (!(reta_conf[idx].mask & (1ULL << sft))) 1300 continue; 1301 1302 rxq = bnxt_qid_to_rxq(bp, reta_conf[idx].reta[sft]); 1303 if (!rxq) { 1304 PMD_DRV_LOG(ERR, "Invalid ring in reta_conf.\n"); 1305 return -EINVAL; 1306 } 1307 1308 if (BNXT_CHIP_THOR(bp)) { 1309 vnic->rss_table[i * 2] = 1310 rxq->rx_ring->rx_ring_struct->fw_ring_id; 1311 vnic->rss_table[i * 2 + 1] = 1312 rxq->cp_ring->cp_ring_struct->fw_ring_id; 1313 } else { 1314 vnic->rss_table[i] = 1315 vnic->fw_grp_ids[reta_conf[idx].reta[sft]]; 1316 } 1317 1318 vnic->rss_table[i] = 1319 vnic->fw_grp_ids[reta_conf[idx].reta[sft]]; 1320 } 1321 1322 bnxt_hwrm_vnic_rss_cfg(bp, vnic); 1323 return 0; 1324 } 1325 1326 static int bnxt_reta_query_op(struct rte_eth_dev *eth_dev, 1327 struct rte_eth_rss_reta_entry64 *reta_conf, 1328 uint16_t reta_size) 1329 { 1330 struct bnxt *bp = eth_dev->data->dev_private; 1331 struct bnxt_vnic_info *vnic = &bp->vnic_info[0]; 1332 uint16_t tbl_size = bnxt_rss_hash_tbl_size(bp); 1333 uint16_t idx, sft, i; 1334 int rc; 1335 1336 rc = is_bnxt_in_error(bp); 1337 if (rc) 1338 return rc; 1339 1340 /* Retrieve from the default VNIC */ 1341 if (!vnic) 1342 return -EINVAL; 1343 if (!vnic->rss_table) 1344 return -EINVAL; 1345 1346 if (reta_size != tbl_size) { 1347 PMD_DRV_LOG(ERR, "The configured hash table lookup size " 1348 "(%d) must equal the size supported by the hardware " 1349 "(%d)\n", reta_size, tbl_size); 1350 return -EINVAL; 1351 } 1352 1353 for (idx = 0, i = 0; i < reta_size; i++) { 1354 idx = i / RTE_RETA_GROUP_SIZE; 1355 sft = i % RTE_RETA_GROUP_SIZE; 1356 1357 if (reta_conf[idx].mask & (1ULL << sft)) { 1358 uint16_t qid; 1359 1360 if (BNXT_CHIP_THOR(bp)) 1361 qid = bnxt_rss_to_qid(bp, 1362 vnic->rss_table[i * 2]); 1363 else 1364 qid = bnxt_rss_to_qid(bp, vnic->rss_table[i]); 1365 1366 if (qid == INVALID_HW_RING_ID) { 1367 PMD_DRV_LOG(ERR, "Inv. entry in rss table.\n"); 1368 return -EINVAL; 1369 } 1370 reta_conf[idx].reta[sft] = qid; 1371 } 1372 } 1373 1374 return 0; 1375 } 1376 1377 static int bnxt_rss_hash_update_op(struct rte_eth_dev *eth_dev, 1378 struct rte_eth_rss_conf *rss_conf) 1379 { 1380 struct bnxt *bp = eth_dev->data->dev_private; 1381 struct rte_eth_conf *dev_conf = &bp->eth_dev->data->dev_conf; 1382 struct bnxt_vnic_info *vnic; 1383 int rc; 1384 1385 rc = is_bnxt_in_error(bp); 1386 if (rc) 1387 return rc; 1388 1389 /* 1390 * If RSS enablement were different than dev_configure, 1391 * then return -EINVAL 1392 */ 1393 if (dev_conf->rxmode.mq_mode & ETH_MQ_RX_RSS_FLAG) { 1394 if (!rss_conf->rss_hf) 1395 PMD_DRV_LOG(ERR, "Hash type NONE\n"); 1396 } else { 1397 if (rss_conf->rss_hf & BNXT_ETH_RSS_SUPPORT) 1398 return -EINVAL; 1399 } 1400 1401 bp->flags |= BNXT_FLAG_UPDATE_HASH; 1402 memcpy(&bp->rss_conf, rss_conf, sizeof(*rss_conf)); 1403 1404 /* Update the default RSS VNIC(s) */ 1405 vnic = &bp->vnic_info[0]; 1406 vnic->hash_type = bnxt_rte_to_hwrm_hash_types(rss_conf->rss_hf); 1407 1408 /* 1409 * If hashkey is not specified, use the previously configured 1410 * hashkey 1411 */ 1412 if (!rss_conf->rss_key) 1413 goto rss_config; 1414 1415 if (rss_conf->rss_key_len != HW_HASH_KEY_SIZE) { 1416 PMD_DRV_LOG(ERR, 1417 "Invalid hashkey length, should be 16 bytes\n"); 1418 return -EINVAL; 1419 } 1420 memcpy(vnic->rss_hash_key, rss_conf->rss_key, rss_conf->rss_key_len); 1421 1422 rss_config: 1423 bnxt_hwrm_vnic_rss_cfg(bp, vnic); 1424 return 0; 1425 } 1426 1427 static int bnxt_rss_hash_conf_get_op(struct rte_eth_dev *eth_dev, 1428 struct rte_eth_rss_conf *rss_conf) 1429 { 1430 struct bnxt *bp = eth_dev->data->dev_private; 1431 struct bnxt_vnic_info *vnic = &bp->vnic_info[0]; 1432 int len, rc; 1433 uint32_t hash_types; 1434 1435 rc = is_bnxt_in_error(bp); 1436 if (rc) 1437 return rc; 1438 1439 /* RSS configuration is the same for all VNICs */ 1440 if (vnic && vnic->rss_hash_key) { 1441 if (rss_conf->rss_key) { 1442 len = rss_conf->rss_key_len <= HW_HASH_KEY_SIZE ? 1443 rss_conf->rss_key_len : HW_HASH_KEY_SIZE; 1444 memcpy(rss_conf->rss_key, vnic->rss_hash_key, len); 1445 } 1446 1447 hash_types = vnic->hash_type; 1448 rss_conf->rss_hf = 0; 1449 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_IPV4) { 1450 rss_conf->rss_hf |= ETH_RSS_IPV4; 1451 hash_types &= ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_IPV4; 1452 } 1453 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_TCP_IPV4) { 1454 rss_conf->rss_hf |= ETH_RSS_NONFRAG_IPV4_TCP; 1455 hash_types &= 1456 ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_TCP_IPV4; 1457 } 1458 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_UDP_IPV4) { 1459 rss_conf->rss_hf |= ETH_RSS_NONFRAG_IPV4_UDP; 1460 hash_types &= 1461 ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_UDP_IPV4; 1462 } 1463 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_IPV6) { 1464 rss_conf->rss_hf |= ETH_RSS_IPV6; 1465 hash_types &= ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_IPV6; 1466 } 1467 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_TCP_IPV6) { 1468 rss_conf->rss_hf |= ETH_RSS_NONFRAG_IPV6_TCP; 1469 hash_types &= 1470 ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_TCP_IPV6; 1471 } 1472 if (hash_types & HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_UDP_IPV6) { 1473 rss_conf->rss_hf |= ETH_RSS_NONFRAG_IPV6_UDP; 1474 hash_types &= 1475 ~HWRM_VNIC_RSS_CFG_INPUT_HASH_TYPE_UDP_IPV6; 1476 } 1477 if (hash_types) { 1478 PMD_DRV_LOG(ERR, 1479 "Unknwon RSS config from firmware (%08x), RSS disabled", 1480 vnic->hash_type); 1481 return -ENOTSUP; 1482 } 1483 } else { 1484 rss_conf->rss_hf = 0; 1485 } 1486 return 0; 1487 } 1488 1489 static int bnxt_flow_ctrl_get_op(struct rte_eth_dev *dev, 1490 struct rte_eth_fc_conf *fc_conf) 1491 { 1492 struct bnxt *bp = dev->data->dev_private; 1493 struct rte_eth_link link_info; 1494 int rc; 1495 1496 rc = is_bnxt_in_error(bp); 1497 if (rc) 1498 return rc; 1499 1500 rc = bnxt_get_hwrm_link_config(bp, &link_info); 1501 if (rc) 1502 return rc; 1503 1504 memset(fc_conf, 0, sizeof(*fc_conf)); 1505 if (bp->link_info.auto_pause) 1506 fc_conf->autoneg = 1; 1507 switch (bp->link_info.pause) { 1508 case 0: 1509 fc_conf->mode = RTE_FC_NONE; 1510 break; 1511 case HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX: 1512 fc_conf->mode = RTE_FC_TX_PAUSE; 1513 break; 1514 case HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX: 1515 fc_conf->mode = RTE_FC_RX_PAUSE; 1516 break; 1517 case (HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_TX | 1518 HWRM_PORT_PHY_QCFG_OUTPUT_PAUSE_RX): 1519 fc_conf->mode = RTE_FC_FULL; 1520 break; 1521 } 1522 return 0; 1523 } 1524 1525 static int bnxt_flow_ctrl_set_op(struct rte_eth_dev *dev, 1526 struct rte_eth_fc_conf *fc_conf) 1527 { 1528 struct bnxt *bp = dev->data->dev_private; 1529 int rc; 1530 1531 rc = is_bnxt_in_error(bp); 1532 if (rc) 1533 return rc; 1534 1535 if (!BNXT_SINGLE_PF(bp) || BNXT_VF(bp)) { 1536 PMD_DRV_LOG(ERR, "Flow Control Settings cannot be modified\n"); 1537 return -ENOTSUP; 1538 } 1539 1540 switch (fc_conf->mode) { 1541 case RTE_FC_NONE: 1542 bp->link_info.auto_pause = 0; 1543 bp->link_info.force_pause = 0; 1544 break; 1545 case RTE_FC_RX_PAUSE: 1546 if (fc_conf->autoneg) { 1547 bp->link_info.auto_pause = 1548 HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_RX; 1549 bp->link_info.force_pause = 0; 1550 } else { 1551 bp->link_info.auto_pause = 0; 1552 bp->link_info.force_pause = 1553 HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_RX; 1554 } 1555 break; 1556 case RTE_FC_TX_PAUSE: 1557 if (fc_conf->autoneg) { 1558 bp->link_info.auto_pause = 1559 HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_TX; 1560 bp->link_info.force_pause = 0; 1561 } else { 1562 bp->link_info.auto_pause = 0; 1563 bp->link_info.force_pause = 1564 HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_TX; 1565 } 1566 break; 1567 case RTE_FC_FULL: 1568 if (fc_conf->autoneg) { 1569 bp->link_info.auto_pause = 1570 HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_TX | 1571 HWRM_PORT_PHY_CFG_INPUT_AUTO_PAUSE_RX; 1572 bp->link_info.force_pause = 0; 1573 } else { 1574 bp->link_info.auto_pause = 0; 1575 bp->link_info.force_pause = 1576 HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_TX | 1577 HWRM_PORT_PHY_CFG_INPUT_FORCE_PAUSE_RX; 1578 } 1579 break; 1580 } 1581 return bnxt_set_hwrm_link_config(bp, true); 1582 } 1583 1584 /* Add UDP tunneling port */ 1585 static int 1586 bnxt_udp_tunnel_port_add_op(struct rte_eth_dev *eth_dev, 1587 struct rte_eth_udp_tunnel *udp_tunnel) 1588 { 1589 struct bnxt *bp = eth_dev->data->dev_private; 1590 uint16_t tunnel_type = 0; 1591 int rc = 0; 1592 1593 rc = is_bnxt_in_error(bp); 1594 if (rc) 1595 return rc; 1596 1597 switch (udp_tunnel->prot_type) { 1598 case RTE_TUNNEL_TYPE_VXLAN: 1599 if (bp->vxlan_port_cnt) { 1600 PMD_DRV_LOG(ERR, "Tunnel Port %d already programmed\n", 1601 udp_tunnel->udp_port); 1602 if (bp->vxlan_port != udp_tunnel->udp_port) { 1603 PMD_DRV_LOG(ERR, "Only one port allowed\n"); 1604 return -ENOSPC; 1605 } 1606 bp->vxlan_port_cnt++; 1607 return 0; 1608 } 1609 tunnel_type = 1610 HWRM_TUNNEL_DST_PORT_ALLOC_INPUT_TUNNEL_TYPE_VXLAN; 1611 bp->vxlan_port_cnt++; 1612 break; 1613 case RTE_TUNNEL_TYPE_GENEVE: 1614 if (bp->geneve_port_cnt) { 1615 PMD_DRV_LOG(ERR, "Tunnel Port %d already programmed\n", 1616 udp_tunnel->udp_port); 1617 if (bp->geneve_port != udp_tunnel->udp_port) { 1618 PMD_DRV_LOG(ERR, "Only one port allowed\n"); 1619 return -ENOSPC; 1620 } 1621 bp->geneve_port_cnt++; 1622 return 0; 1623 } 1624 tunnel_type = 1625 HWRM_TUNNEL_DST_PORT_ALLOC_INPUT_TUNNEL_TYPE_GENEVE; 1626 bp->geneve_port_cnt++; 1627 break; 1628 default: 1629 PMD_DRV_LOG(ERR, "Tunnel type is not supported\n"); 1630 return -ENOTSUP; 1631 } 1632 rc = bnxt_hwrm_tunnel_dst_port_alloc(bp, udp_tunnel->udp_port, 1633 tunnel_type); 1634 return rc; 1635 } 1636 1637 static int 1638 bnxt_udp_tunnel_port_del_op(struct rte_eth_dev *eth_dev, 1639 struct rte_eth_udp_tunnel *udp_tunnel) 1640 { 1641 struct bnxt *bp = eth_dev->data->dev_private; 1642 uint16_t tunnel_type = 0; 1643 uint16_t port = 0; 1644 int rc = 0; 1645 1646 rc = is_bnxt_in_error(bp); 1647 if (rc) 1648 return rc; 1649 1650 switch (udp_tunnel->prot_type) { 1651 case RTE_TUNNEL_TYPE_VXLAN: 1652 if (!bp->vxlan_port_cnt) { 1653 PMD_DRV_LOG(ERR, "No Tunnel port configured yet\n"); 1654 return -EINVAL; 1655 } 1656 if (bp->vxlan_port != udp_tunnel->udp_port) { 1657 PMD_DRV_LOG(ERR, "Req Port: %d. Configured port: %d\n", 1658 udp_tunnel->udp_port, bp->vxlan_port); 1659 return -EINVAL; 1660 } 1661 if (--bp->vxlan_port_cnt) 1662 return 0; 1663 1664 tunnel_type = 1665 HWRM_TUNNEL_DST_PORT_FREE_INPUT_TUNNEL_TYPE_VXLAN; 1666 port = bp->vxlan_fw_dst_port_id; 1667 break; 1668 case RTE_TUNNEL_TYPE_GENEVE: 1669 if (!bp->geneve_port_cnt) { 1670 PMD_DRV_LOG(ERR, "No Tunnel port configured yet\n"); 1671 return -EINVAL; 1672 } 1673 if (bp->geneve_port != udp_tunnel->udp_port) { 1674 PMD_DRV_LOG(ERR, "Req Port: %d. Configured port: %d\n", 1675 udp_tunnel->udp_port, bp->geneve_port); 1676 return -EINVAL; 1677 } 1678 if (--bp->geneve_port_cnt) 1679 return 0; 1680 1681 tunnel_type = 1682 HWRM_TUNNEL_DST_PORT_FREE_INPUT_TUNNEL_TYPE_GENEVE; 1683 port = bp->geneve_fw_dst_port_id; 1684 break; 1685 default: 1686 PMD_DRV_LOG(ERR, "Tunnel type is not supported\n"); 1687 return -ENOTSUP; 1688 } 1689 1690 rc = bnxt_hwrm_tunnel_dst_port_free(bp, port, tunnel_type); 1691 if (!rc) { 1692 if (tunnel_type == 1693 HWRM_TUNNEL_DST_PORT_FREE_INPUT_TUNNEL_TYPE_VXLAN) 1694 bp->vxlan_port = 0; 1695 if (tunnel_type == 1696 HWRM_TUNNEL_DST_PORT_FREE_INPUT_TUNNEL_TYPE_GENEVE) 1697 bp->geneve_port = 0; 1698 } 1699 return rc; 1700 } 1701 1702 static int bnxt_del_vlan_filter(struct bnxt *bp, uint16_t vlan_id) 1703 { 1704 struct bnxt_filter_info *filter; 1705 struct bnxt_vnic_info *vnic; 1706 int rc = 0; 1707 uint32_t chk = HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_IVLAN; 1708 1709 /* if VLAN exists && VLAN matches vlan_id 1710 * remove the MAC+VLAN filter 1711 * add a new MAC only filter 1712 * else 1713 * VLAN filter doesn't exist, just skip and continue 1714 */ 1715 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1716 filter = STAILQ_FIRST(&vnic->filter); 1717 while (filter) { 1718 /* Search for this matching MAC+VLAN filter */ 1719 if ((filter->enables & chk) && 1720 (filter->l2_ivlan == vlan_id && 1721 filter->l2_ivlan_mask != 0) && 1722 !memcmp(filter->l2_addr, bp->mac_addr, 1723 RTE_ETHER_ADDR_LEN)) { 1724 /* Delete the filter */ 1725 rc = bnxt_hwrm_clear_l2_filter(bp, filter); 1726 if (rc) 1727 return rc; 1728 STAILQ_REMOVE(&vnic->filter, filter, 1729 bnxt_filter_info, next); 1730 STAILQ_INSERT_TAIL(&bp->free_filter_list, filter, next); 1731 1732 PMD_DRV_LOG(INFO, 1733 "Del Vlan filter for %d\n", 1734 vlan_id); 1735 return rc; 1736 } 1737 filter = STAILQ_NEXT(filter, next); 1738 } 1739 return -ENOENT; 1740 } 1741 1742 static int bnxt_add_vlan_filter(struct bnxt *bp, uint16_t vlan_id) 1743 { 1744 struct bnxt_filter_info *filter; 1745 struct bnxt_vnic_info *vnic; 1746 int rc = 0; 1747 uint32_t en = HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_IVLAN | 1748 HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_IVLAN_MASK; 1749 uint32_t chk = HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_IVLAN; 1750 1751 /* Implementation notes on the use of VNIC in this command: 1752 * 1753 * By default, these filters belong to default vnic for the function. 1754 * Once these filters are set up, only destination VNIC can be modified. 1755 * If the destination VNIC is not specified in this command, 1756 * then the HWRM shall only create an l2 context id. 1757 */ 1758 1759 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1760 filter = STAILQ_FIRST(&vnic->filter); 1761 /* Check if the VLAN has already been added */ 1762 while (filter) { 1763 if ((filter->enables & chk) && 1764 (filter->l2_ivlan == vlan_id && 1765 filter->l2_ivlan_mask == 0x0FFF) && 1766 !memcmp(filter->l2_addr, bp->mac_addr, 1767 RTE_ETHER_ADDR_LEN)) 1768 return -EEXIST; 1769 1770 filter = STAILQ_NEXT(filter, next); 1771 } 1772 1773 /* No match found. Alloc a fresh filter and issue the L2_FILTER_ALLOC 1774 * command to create MAC+VLAN filter with the right flags, enables set. 1775 */ 1776 filter = bnxt_alloc_filter(bp); 1777 if (!filter) { 1778 PMD_DRV_LOG(ERR, 1779 "MAC/VLAN filter alloc failed\n"); 1780 return -ENOMEM; 1781 } 1782 /* MAC + VLAN ID filter */ 1783 /* If l2_ivlan == 0 and l2_ivlan_mask != 0, only 1784 * untagged packets are received 1785 * 1786 * If l2_ivlan != 0 and l2_ivlan_mask != 0, untagged 1787 * packets and only the programmed vlan's packets are received 1788 */ 1789 filter->l2_ivlan = vlan_id; 1790 filter->l2_ivlan_mask = 0x0FFF; 1791 filter->enables |= en; 1792 filter->flags |= HWRM_CFA_L2_FILTER_ALLOC_INPUT_FLAGS_OUTERMOST; 1793 1794 rc = bnxt_hwrm_set_l2_filter(bp, vnic->fw_vnic_id, filter); 1795 if (rc) { 1796 /* Free the newly allocated filter as we were 1797 * not able to create the filter in hardware. 1798 */ 1799 filter->fw_l2_filter_id = UINT64_MAX; 1800 STAILQ_INSERT_TAIL(&bp->free_filter_list, filter, next); 1801 return rc; 1802 } else { 1803 /* Add this new filter to the list */ 1804 if (vlan_id == 0) { 1805 filter->dflt = true; 1806 STAILQ_INSERT_HEAD(&vnic->filter, filter, next); 1807 } else { 1808 STAILQ_INSERT_TAIL(&vnic->filter, filter, next); 1809 } 1810 } 1811 1812 PMD_DRV_LOG(INFO, 1813 "Added Vlan filter for %d\n", vlan_id); 1814 return rc; 1815 } 1816 1817 static int bnxt_vlan_filter_set_op(struct rte_eth_dev *eth_dev, 1818 uint16_t vlan_id, int on) 1819 { 1820 struct bnxt *bp = eth_dev->data->dev_private; 1821 int rc; 1822 1823 rc = is_bnxt_in_error(bp); 1824 if (rc) 1825 return rc; 1826 1827 /* These operations apply to ALL existing MAC/VLAN filters */ 1828 if (on) 1829 return bnxt_add_vlan_filter(bp, vlan_id); 1830 else 1831 return bnxt_del_vlan_filter(bp, vlan_id); 1832 } 1833 1834 static int bnxt_del_dflt_mac_filter(struct bnxt *bp, 1835 struct bnxt_vnic_info *vnic) 1836 { 1837 struct bnxt_filter_info *filter; 1838 int rc; 1839 1840 filter = STAILQ_FIRST(&vnic->filter); 1841 while (filter) { 1842 if (filter->dflt && 1843 !memcmp(filter->l2_addr, bp->mac_addr, 1844 RTE_ETHER_ADDR_LEN)) { 1845 rc = bnxt_hwrm_clear_l2_filter(bp, filter); 1846 if (rc) 1847 return rc; 1848 filter->dflt = false; 1849 STAILQ_REMOVE(&vnic->filter, filter, 1850 bnxt_filter_info, next); 1851 STAILQ_INSERT_TAIL(&bp->free_filter_list, 1852 filter, next); 1853 filter->fw_l2_filter_id = -1; 1854 break; 1855 } 1856 filter = STAILQ_NEXT(filter, next); 1857 } 1858 return 0; 1859 } 1860 1861 static int 1862 bnxt_vlan_offload_set_op(struct rte_eth_dev *dev, int mask) 1863 { 1864 struct bnxt *bp = dev->data->dev_private; 1865 uint64_t rx_offloads = dev->data->dev_conf.rxmode.offloads; 1866 struct bnxt_vnic_info *vnic; 1867 unsigned int i; 1868 int rc; 1869 1870 rc = is_bnxt_in_error(bp); 1871 if (rc) 1872 return rc; 1873 1874 vnic = BNXT_GET_DEFAULT_VNIC(bp); 1875 if (!(rx_offloads & DEV_RX_OFFLOAD_VLAN_FILTER)) { 1876 /* Remove any VLAN filters programmed */ 1877 for (i = 0; i < 4095; i++) 1878 bnxt_del_vlan_filter(bp, i); 1879 1880 rc = bnxt_add_mac_filter(bp, vnic, NULL, 0); 1881 if (rc) 1882 return rc; 1883 } else { 1884 /* Default filter will allow packets that match the 1885 * dest mac. So, it has to be deleted, otherwise, we 1886 * will endup receiving vlan packets for which the 1887 * filter is not programmed, when hw-vlan-filter 1888 * configuration is ON 1889 */ 1890 bnxt_del_dflt_mac_filter(bp, vnic); 1891 /* This filter will allow only untagged packets */ 1892 bnxt_add_vlan_filter(bp, 0); 1893 } 1894 PMD_DRV_LOG(DEBUG, "VLAN Filtering: %d\n", 1895 !!(rx_offloads & DEV_RX_OFFLOAD_VLAN_FILTER)); 1896 1897 if (mask & ETH_VLAN_STRIP_MASK) { 1898 /* Enable or disable VLAN stripping */ 1899 for (i = 0; i < bp->nr_vnics; i++) { 1900 struct bnxt_vnic_info *vnic = &bp->vnic_info[i]; 1901 if (rx_offloads & DEV_RX_OFFLOAD_VLAN_STRIP) 1902 vnic->vlan_strip = true; 1903 else 1904 vnic->vlan_strip = false; 1905 bnxt_hwrm_vnic_cfg(bp, vnic); 1906 } 1907 PMD_DRV_LOG(DEBUG, "VLAN Strip Offload: %d\n", 1908 !!(rx_offloads & DEV_RX_OFFLOAD_VLAN_STRIP)); 1909 } 1910 1911 if (mask & ETH_VLAN_EXTEND_MASK) { 1912 if (rx_offloads & DEV_RX_OFFLOAD_VLAN_EXTEND) 1913 PMD_DRV_LOG(DEBUG, "Extend VLAN supported\n"); 1914 else 1915 PMD_DRV_LOG(INFO, "Extend VLAN unsupported\n"); 1916 } 1917 1918 return 0; 1919 } 1920 1921 static int 1922 bnxt_vlan_tpid_set_op(struct rte_eth_dev *dev, enum rte_vlan_type vlan_type, 1923 uint16_t tpid) 1924 { 1925 struct bnxt *bp = dev->data->dev_private; 1926 int qinq = dev->data->dev_conf.rxmode.offloads & 1927 DEV_RX_OFFLOAD_VLAN_EXTEND; 1928 1929 if (vlan_type != ETH_VLAN_TYPE_INNER && 1930 vlan_type != ETH_VLAN_TYPE_OUTER) { 1931 PMD_DRV_LOG(ERR, 1932 "Unsupported vlan type."); 1933 return -EINVAL; 1934 } 1935 if (!qinq) { 1936 PMD_DRV_LOG(ERR, 1937 "QinQ not enabled. Needs to be ON as we can " 1938 "accelerate only outer vlan\n"); 1939 return -EINVAL; 1940 } 1941 1942 if (vlan_type == ETH_VLAN_TYPE_OUTER) { 1943 switch (tpid) { 1944 case RTE_ETHER_TYPE_QINQ: 1945 bp->outer_tpid_bd = 1946 TX_BD_LONG_CFA_META_VLAN_TPID_TPID88A8; 1947 break; 1948 case RTE_ETHER_TYPE_VLAN: 1949 bp->outer_tpid_bd = 1950 TX_BD_LONG_CFA_META_VLAN_TPID_TPID8100; 1951 break; 1952 case 0x9100: 1953 bp->outer_tpid_bd = 1954 TX_BD_LONG_CFA_META_VLAN_TPID_TPID9100; 1955 break; 1956 case 0x9200: 1957 bp->outer_tpid_bd = 1958 TX_BD_LONG_CFA_META_VLAN_TPID_TPID9200; 1959 break; 1960 case 0x9300: 1961 bp->outer_tpid_bd = 1962 TX_BD_LONG_CFA_META_VLAN_TPID_TPID9300; 1963 break; 1964 default: 1965 PMD_DRV_LOG(ERR, "Invalid TPID: %x\n", tpid); 1966 return -EINVAL; 1967 } 1968 bp->outer_tpid_bd |= tpid; 1969 PMD_DRV_LOG(INFO, "outer_tpid_bd = %x\n", bp->outer_tpid_bd); 1970 } else if (vlan_type == ETH_VLAN_TYPE_INNER) { 1971 PMD_DRV_LOG(ERR, 1972 "Can accelerate only outer vlan in QinQ\n"); 1973 return -EINVAL; 1974 } 1975 1976 return 0; 1977 } 1978 1979 static int 1980 bnxt_set_default_mac_addr_op(struct rte_eth_dev *dev, 1981 struct rte_ether_addr *addr) 1982 { 1983 struct bnxt *bp = dev->data->dev_private; 1984 /* Default Filter is tied to VNIC 0 */ 1985 struct bnxt_vnic_info *vnic = &bp->vnic_info[0]; 1986 struct bnxt_filter_info *filter; 1987 int rc; 1988 1989 rc = is_bnxt_in_error(bp); 1990 if (rc) 1991 return rc; 1992 1993 if (BNXT_VF(bp) && !BNXT_VF_IS_TRUSTED(bp)) 1994 return -EPERM; 1995 1996 if (rte_is_zero_ether_addr(addr)) 1997 return -EINVAL; 1998 1999 STAILQ_FOREACH(filter, &vnic->filter, next) { 2000 /* Default Filter is at Index 0 */ 2001 if (filter->mac_index != 0) 2002 continue; 2003 2004 memcpy(filter->l2_addr, addr, RTE_ETHER_ADDR_LEN); 2005 memset(filter->l2_addr_mask, 0xff, RTE_ETHER_ADDR_LEN); 2006 filter->flags |= HWRM_CFA_L2_FILTER_ALLOC_INPUT_FLAGS_PATH_RX | 2007 HWRM_CFA_L2_FILTER_ALLOC_INPUT_FLAGS_OUTERMOST; 2008 filter->enables |= 2009 HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_ADDR | 2010 HWRM_CFA_L2_FILTER_ALLOC_INPUT_ENABLES_L2_ADDR_MASK; 2011 2012 rc = bnxt_hwrm_set_l2_filter(bp, vnic->fw_vnic_id, filter); 2013 if (rc) { 2014 memcpy(filter->l2_addr, bp->mac_addr, 2015 RTE_ETHER_ADDR_LEN); 2016 return rc; 2017 } 2018 2019 memcpy(bp->mac_addr, addr, RTE_ETHER_ADDR_LEN); 2020 PMD_DRV_LOG(DEBUG, "Set MAC addr\n"); 2021 return 0; 2022 } 2023 2024 return 0; 2025 } 2026 2027 static int 2028 bnxt_dev_set_mc_addr_list_op(struct rte_eth_dev *eth_dev, 2029 struct rte_ether_addr *mc_addr_set, 2030 uint32_t nb_mc_addr) 2031 { 2032 struct bnxt *bp = eth_dev->data->dev_private; 2033 char *mc_addr_list = (char *)mc_addr_set; 2034 struct bnxt_vnic_info *vnic; 2035 uint32_t off = 0, i = 0; 2036 int rc; 2037 2038 rc = is_bnxt_in_error(bp); 2039 if (rc) 2040 return rc; 2041 2042 vnic = BNXT_GET_DEFAULT_VNIC(bp); 2043 2044 if (nb_mc_addr > BNXT_MAX_MC_ADDRS) { 2045 vnic->flags |= BNXT_VNIC_INFO_ALLMULTI; 2046 goto allmulti; 2047 } 2048 2049 /* TODO Check for Duplicate mcast addresses */ 2050 vnic->flags &= ~BNXT_VNIC_INFO_ALLMULTI; 2051 for (i = 0; i < nb_mc_addr; i++) { 2052 memcpy(vnic->mc_list + off, &mc_addr_list[i], 2053 RTE_ETHER_ADDR_LEN); 2054 off += RTE_ETHER_ADDR_LEN; 2055 } 2056 2057 vnic->mc_addr_cnt = i; 2058 if (vnic->mc_addr_cnt) 2059 vnic->flags |= BNXT_VNIC_INFO_MCAST; 2060 else 2061 vnic->flags &= ~BNXT_VNIC_INFO_MCAST; 2062 2063 allmulti: 2064 return bnxt_hwrm_cfa_l2_set_rx_mask(bp, vnic, 0, NULL); 2065 } 2066 2067 static int 2068 bnxt_fw_version_get(struct rte_eth_dev *dev, char *fw_version, size_t fw_size) 2069 { 2070 struct bnxt *bp = dev->data->dev_private; 2071 uint8_t fw_major = (bp->fw_ver >> 24) & 0xff; 2072 uint8_t fw_minor = (bp->fw_ver >> 16) & 0xff; 2073 uint8_t fw_updt = (bp->fw_ver >> 8) & 0xff; 2074 int ret; 2075 2076 ret = snprintf(fw_version, fw_size, "%d.%d.%d", 2077 fw_major, fw_minor, fw_updt); 2078 2079 ret += 1; /* add the size of '\0' */ 2080 if (fw_size < (uint32_t)ret) 2081 return ret; 2082 else 2083 return 0; 2084 } 2085 2086 static void 2087 bnxt_rxq_info_get_op(struct rte_eth_dev *dev, uint16_t queue_id, 2088 struct rte_eth_rxq_info *qinfo) 2089 { 2090 struct bnxt_rx_queue *rxq; 2091 2092 rxq = dev->data->rx_queues[queue_id]; 2093 2094 qinfo->mp = rxq->mb_pool; 2095 qinfo->scattered_rx = dev->data->scattered_rx; 2096 qinfo->nb_desc = rxq->nb_rx_desc; 2097 2098 qinfo->conf.rx_free_thresh = rxq->rx_free_thresh; 2099 qinfo->conf.rx_drop_en = 0; 2100 qinfo->conf.rx_deferred_start = rxq->rx_deferred_start; 2101 } 2102 2103 static void 2104 bnxt_txq_info_get_op(struct rte_eth_dev *dev, uint16_t queue_id, 2105 struct rte_eth_txq_info *qinfo) 2106 { 2107 struct bnxt_tx_queue *txq; 2108 2109 txq = dev->data->tx_queues[queue_id]; 2110 2111 qinfo->nb_desc = txq->nb_tx_desc; 2112 2113 qinfo->conf.tx_thresh.pthresh = txq->pthresh; 2114 qinfo->conf.tx_thresh.hthresh = txq->hthresh; 2115 qinfo->conf.tx_thresh.wthresh = txq->wthresh; 2116 2117 qinfo->conf.tx_free_thresh = txq->tx_free_thresh; 2118 qinfo->conf.tx_rs_thresh = 0; 2119 qinfo->conf.tx_deferred_start = txq->tx_deferred_start; 2120 } 2121 2122 static int bnxt_mtu_set_op(struct rte_eth_dev *eth_dev, uint16_t new_mtu) 2123 { 2124 struct bnxt *bp = eth_dev->data->dev_private; 2125 uint32_t new_pkt_size; 2126 uint32_t rc = 0; 2127 uint32_t i; 2128 2129 rc = is_bnxt_in_error(bp); 2130 if (rc) 2131 return rc; 2132 2133 new_pkt_size = new_mtu + RTE_ETHER_HDR_LEN + RTE_ETHER_CRC_LEN + 2134 VLAN_TAG_SIZE * BNXT_NUM_VLANS; 2135 2136 #ifdef RTE_ARCH_X86 2137 /* 2138 * If vector-mode tx/rx is active, disallow any MTU change that would 2139 * require scattered receive support. 2140 */ 2141 if (eth_dev->data->dev_started && 2142 (eth_dev->rx_pkt_burst == bnxt_recv_pkts_vec || 2143 eth_dev->tx_pkt_burst == bnxt_xmit_pkts_vec) && 2144 (new_pkt_size > 2145 eth_dev->data->min_rx_buf_size - RTE_PKTMBUF_HEADROOM)) { 2146 PMD_DRV_LOG(ERR, 2147 "MTU change would require scattered rx support. "); 2148 PMD_DRV_LOG(ERR, "Stop port before changing MTU.\n"); 2149 return -EINVAL; 2150 } 2151 #endif 2152 2153 if (new_mtu > RTE_ETHER_MTU) { 2154 bp->flags |= BNXT_FLAG_JUMBO; 2155 bp->eth_dev->data->dev_conf.rxmode.offloads |= 2156 DEV_RX_OFFLOAD_JUMBO_FRAME; 2157 } else { 2158 bp->eth_dev->data->dev_conf.rxmode.offloads &= 2159 ~DEV_RX_OFFLOAD_JUMBO_FRAME; 2160 bp->flags &= ~BNXT_FLAG_JUMBO; 2161 } 2162 2163 eth_dev->data->dev_conf.rxmode.max_rx_pkt_len = new_pkt_size; 2164 2165 for (i = 0; i < bp->nr_vnics; i++) { 2166 struct bnxt_vnic_info *vnic = &bp->vnic_info[i]; 2167 uint16_t size = 0; 2168 2169 vnic->mru = new_mtu + RTE_ETHER_HDR_LEN + 2170 RTE_ETHER_CRC_LEN + VLAN_TAG_SIZE * 2; 2171 rc = bnxt_hwrm_vnic_cfg(bp, vnic); 2172 if (rc) 2173 break; 2174 2175 size = rte_pktmbuf_data_room_size(bp->rx_queues[0]->mb_pool); 2176 size -= RTE_PKTMBUF_HEADROOM; 2177 2178 if (size < new_mtu) { 2179 rc = bnxt_hwrm_vnic_plcmode_cfg(bp, vnic); 2180 if (rc) 2181 return rc; 2182 } 2183 } 2184 2185 PMD_DRV_LOG(INFO, "New MTU is %d\n", new_mtu); 2186 2187 return rc; 2188 } 2189 2190 static int 2191 bnxt_vlan_pvid_set_op(struct rte_eth_dev *dev, uint16_t pvid, int on) 2192 { 2193 struct bnxt *bp = dev->data->dev_private; 2194 uint16_t vlan = bp->vlan; 2195 int rc; 2196 2197 rc = is_bnxt_in_error(bp); 2198 if (rc) 2199 return rc; 2200 2201 if (!BNXT_SINGLE_PF(bp) || BNXT_VF(bp)) { 2202 PMD_DRV_LOG(ERR, 2203 "PVID cannot be modified for this function\n"); 2204 return -ENOTSUP; 2205 } 2206 bp->vlan = on ? pvid : 0; 2207 2208 rc = bnxt_hwrm_set_default_vlan(bp, 0, 0); 2209 if (rc) 2210 bp->vlan = vlan; 2211 return rc; 2212 } 2213 2214 static int 2215 bnxt_dev_led_on_op(struct rte_eth_dev *dev) 2216 { 2217 struct bnxt *bp = dev->data->dev_private; 2218 int rc; 2219 2220 rc = is_bnxt_in_error(bp); 2221 if (rc) 2222 return rc; 2223 2224 return bnxt_hwrm_port_led_cfg(bp, true); 2225 } 2226 2227 static int 2228 bnxt_dev_led_off_op(struct rte_eth_dev *dev) 2229 { 2230 struct bnxt *bp = dev->data->dev_private; 2231 int rc; 2232 2233 rc = is_bnxt_in_error(bp); 2234 if (rc) 2235 return rc; 2236 2237 return bnxt_hwrm_port_led_cfg(bp, false); 2238 } 2239 2240 static uint32_t 2241 bnxt_rx_queue_count_op(struct rte_eth_dev *dev, uint16_t rx_queue_id) 2242 { 2243 struct bnxt *bp = (struct bnxt *)dev->data->dev_private; 2244 uint32_t desc = 0, raw_cons = 0, cons; 2245 struct bnxt_cp_ring_info *cpr; 2246 struct bnxt_rx_queue *rxq; 2247 struct rx_pkt_cmpl *rxcmp; 2248 int rc; 2249 2250 rc = is_bnxt_in_error(bp); 2251 if (rc) 2252 return rc; 2253 2254 rxq = dev->data->rx_queues[rx_queue_id]; 2255 cpr = rxq->cp_ring; 2256 raw_cons = cpr->cp_raw_cons; 2257 2258 while (1) { 2259 cons = RING_CMP(cpr->cp_ring_struct, raw_cons); 2260 rte_prefetch0(&cpr->cp_desc_ring[cons]); 2261 rxcmp = (struct rx_pkt_cmpl *)&cpr->cp_desc_ring[cons]; 2262 2263 if (!CMP_VALID(rxcmp, raw_cons, cpr->cp_ring_struct)) { 2264 break; 2265 } else { 2266 raw_cons++; 2267 desc++; 2268 } 2269 } 2270 2271 return desc; 2272 } 2273 2274 static int 2275 bnxt_rx_descriptor_status_op(void *rx_queue, uint16_t offset) 2276 { 2277 struct bnxt_rx_queue *rxq = (struct bnxt_rx_queue *)rx_queue; 2278 struct bnxt_rx_ring_info *rxr; 2279 struct bnxt_cp_ring_info *cpr; 2280 struct bnxt_sw_rx_bd *rx_buf; 2281 struct rx_pkt_cmpl *rxcmp; 2282 uint32_t cons, cp_cons; 2283 int rc; 2284 2285 if (!rxq) 2286 return -EINVAL; 2287 2288 rc = is_bnxt_in_error(rxq->bp); 2289 if (rc) 2290 return rc; 2291 2292 cpr = rxq->cp_ring; 2293 rxr = rxq->rx_ring; 2294 2295 if (offset >= rxq->nb_rx_desc) 2296 return -EINVAL; 2297 2298 cons = RING_CMP(cpr->cp_ring_struct, offset); 2299 cp_cons = cpr->cp_raw_cons; 2300 rxcmp = (struct rx_pkt_cmpl *)&cpr->cp_desc_ring[cons]; 2301 2302 if (cons > cp_cons) { 2303 if (CMPL_VALID(rxcmp, cpr->valid)) 2304 return RTE_ETH_RX_DESC_DONE; 2305 } else { 2306 if (CMPL_VALID(rxcmp, !cpr->valid)) 2307 return RTE_ETH_RX_DESC_DONE; 2308 } 2309 rx_buf = &rxr->rx_buf_ring[cons]; 2310 if (rx_buf->mbuf == NULL) 2311 return RTE_ETH_RX_DESC_UNAVAIL; 2312 2313 2314 return RTE_ETH_RX_DESC_AVAIL; 2315 } 2316 2317 static int 2318 bnxt_tx_descriptor_status_op(void *tx_queue, uint16_t offset) 2319 { 2320 struct bnxt_tx_queue *txq = (struct bnxt_tx_queue *)tx_queue; 2321 struct bnxt_tx_ring_info *txr; 2322 struct bnxt_cp_ring_info *cpr; 2323 struct bnxt_sw_tx_bd *tx_buf; 2324 struct tx_pkt_cmpl *txcmp; 2325 uint32_t cons, cp_cons; 2326 int rc; 2327 2328 if (!txq) 2329 return -EINVAL; 2330 2331 rc = is_bnxt_in_error(txq->bp); 2332 if (rc) 2333 return rc; 2334 2335 cpr = txq->cp_ring; 2336 txr = txq->tx_ring; 2337 2338 if (offset >= txq->nb_tx_desc) 2339 return -EINVAL; 2340 2341 cons = RING_CMP(cpr->cp_ring_struct, offset); 2342 txcmp = (struct tx_pkt_cmpl *)&cpr->cp_desc_ring[cons]; 2343 cp_cons = cpr->cp_raw_cons; 2344 2345 if (cons > cp_cons) { 2346 if (CMPL_VALID(txcmp, cpr->valid)) 2347 return RTE_ETH_TX_DESC_UNAVAIL; 2348 } else { 2349 if (CMPL_VALID(txcmp, !cpr->valid)) 2350 return RTE_ETH_TX_DESC_UNAVAIL; 2351 } 2352 tx_buf = &txr->tx_buf_ring[cons]; 2353 if (tx_buf->mbuf == NULL) 2354 return RTE_ETH_TX_DESC_DONE; 2355 2356 return RTE_ETH_TX_DESC_FULL; 2357 } 2358 2359 static struct bnxt_filter_info * 2360 bnxt_match_and_validate_ether_filter(struct bnxt *bp, 2361 struct rte_eth_ethertype_filter *efilter, 2362 struct bnxt_vnic_info *vnic0, 2363 struct bnxt_vnic_info *vnic, 2364 int *ret) 2365 { 2366 struct bnxt_filter_info *mfilter = NULL; 2367 int match = 0; 2368 *ret = 0; 2369 2370 if (efilter->ether_type == RTE_ETHER_TYPE_IPV4 || 2371 efilter->ether_type == RTE_ETHER_TYPE_IPV6) { 2372 PMD_DRV_LOG(ERR, "invalid ether_type(0x%04x) in" 2373 " ethertype filter.", efilter->ether_type); 2374 *ret = -EINVAL; 2375 goto exit; 2376 } 2377 if (efilter->queue >= bp->rx_nr_rings) { 2378 PMD_DRV_LOG(ERR, "Invalid queue %d\n", efilter->queue); 2379 *ret = -EINVAL; 2380 goto exit; 2381 } 2382 2383 vnic0 = &bp->vnic_info[0]; 2384 vnic = &bp->vnic_info[efilter->queue]; 2385 if (vnic == NULL) { 2386 PMD_DRV_LOG(ERR, "Invalid queue %d\n", efilter->queue); 2387 *ret = -EINVAL; 2388 goto exit; 2389 } 2390 2391 if (efilter->flags & RTE_ETHTYPE_FLAGS_DROP) { 2392 STAILQ_FOREACH(mfilter, &vnic0->filter, next) { 2393 if ((!memcmp(efilter->mac_addr.addr_bytes, 2394 mfilter->l2_addr, RTE_ETHER_ADDR_LEN) && 2395 mfilter->flags == 2396 HWRM_CFA_NTUPLE_FILTER_ALLOC_INPUT_FLAGS_DROP && 2397 mfilter->ethertype == efilter->ether_type)) { 2398 match = 1; 2399 break; 2400 } 2401 } 2402 } else { 2403 STAILQ_FOREACH(mfilter, &vnic->filter, next) 2404 if ((!memcmp(efilter->mac_addr.addr_bytes, 2405 mfilter->l2_addr, RTE_ETHER_ADDR_LEN) && 2406 mfilter->ethertype == efilter->ether_type && 2407 mfilter->flags == 2408 HWRM_CFA_L2_FILTER_CFG_INPUT_FLAGS_PATH_RX)) { 2409 match = 1; 2410 break; 2411 } 2412 } 2413 2414 if (match) 2415 *ret = -EEXIST; 2416 2417 exit: 2418 return mfilter; 2419 } 2420 2421 static int 2422 bnxt_ethertype_filter(struct rte_eth_dev *dev, 2423 enum rte_filter_op filter_op, 2424 void *arg) 2425 { 2426 struct bnxt *bp = dev->data->dev_private; 2427 struct rte_eth_ethertype_filter *efilter = 2428 (struct rte_eth_ethertype_filter *)arg; 2429 struct bnxt_filter_info *bfilter, *filter1; 2430 struct bnxt_vnic_info *vnic, *vnic0; 2431 int ret; 2432 2433 if (filter_op == RTE_ETH_FILTER_NOP) 2434 return 0; 2435 2436 if (arg == NULL) { 2437 PMD_DRV_LOG(ERR, "arg shouldn't be NULL for operation %u.", 2438 filter_op); 2439 return -EINVAL; 2440 } 2441 2442 vnic0 = &bp->vnic_info[0]; 2443 vnic = &bp->vnic_info[efilter->queue]; 2444 2445 switch (filter_op) { 2446 case RTE_ETH_FILTER_ADD: 2447 bnxt_match_and_validate_ether_filter(bp, efilter, 2448 vnic0, vnic, &ret); 2449 if (ret < 0) 2450 return ret; 2451 2452 bfilter = bnxt_get_unused_filter(bp); 2453 if (bfilter == NULL) { 2454 PMD_DRV_LOG(ERR, 2455 "Not enough resources for a new filter.\n"); 2456 return -ENOMEM; 2457 } 2458 bfilter->filter_type = HWRM_CFA_NTUPLE_FILTER; 2459 memcpy(bfilter->l2_addr, efilter->mac_addr.addr_bytes, 2460 RTE_ETHER_ADDR_LEN); 2461 memcpy(bfilter->dst_macaddr, efilter->mac_addr.addr_bytes, 2462 RTE_ETHER_ADDR_LEN); 2463 bfilter->enables |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_MACADDR; 2464 bfilter->ethertype = efilter->ether_type; 2465 bfilter->enables |= NTUPLE_FLTR_ALLOC_INPUT_EN_ETHERTYPE; 2466 2467 filter1 = bnxt_get_l2_filter(bp, bfilter, vnic0); 2468 if (filter1 == NULL) { 2469 ret = -EINVAL; 2470 goto cleanup; 2471 } 2472 bfilter->enables |= 2473 HWRM_CFA_NTUPLE_FILTER_ALLOC_INPUT_ENABLES_L2_FILTER_ID; 2474 bfilter->fw_l2_filter_id = filter1->fw_l2_filter_id; 2475 2476 bfilter->dst_id = vnic->fw_vnic_id; 2477 2478 if (efilter->flags & RTE_ETHTYPE_FLAGS_DROP) { 2479 bfilter->flags = 2480 HWRM_CFA_NTUPLE_FILTER_ALLOC_INPUT_FLAGS_DROP; 2481 } 2482 2483 ret = bnxt_hwrm_set_ntuple_filter(bp, bfilter->dst_id, bfilter); 2484 if (ret) 2485 goto cleanup; 2486 STAILQ_INSERT_TAIL(&vnic->filter, bfilter, next); 2487 break; 2488 case RTE_ETH_FILTER_DELETE: 2489 filter1 = bnxt_match_and_validate_ether_filter(bp, efilter, 2490 vnic0, vnic, &ret); 2491 if (ret == -EEXIST) { 2492 ret = bnxt_hwrm_clear_ntuple_filter(bp, filter1); 2493 2494 STAILQ_REMOVE(&vnic->filter, filter1, bnxt_filter_info, 2495 next); 2496 bnxt_free_filter(bp, filter1); 2497 } else if (ret == 0) { 2498 PMD_DRV_LOG(ERR, "No matching filter found\n"); 2499 } 2500 break; 2501 default: 2502 PMD_DRV_LOG(ERR, "unsupported operation %u.", filter_op); 2503 ret = -EINVAL; 2504 goto error; 2505 } 2506 return ret; 2507 cleanup: 2508 bnxt_free_filter(bp, bfilter); 2509 error: 2510 return ret; 2511 } 2512 2513 static inline int 2514 parse_ntuple_filter(struct bnxt *bp, 2515 struct rte_eth_ntuple_filter *nfilter, 2516 struct bnxt_filter_info *bfilter) 2517 { 2518 uint32_t en = 0; 2519 2520 if (nfilter->queue >= bp->rx_nr_rings) { 2521 PMD_DRV_LOG(ERR, "Invalid queue %d\n", nfilter->queue); 2522 return -EINVAL; 2523 } 2524 2525 switch (nfilter->dst_port_mask) { 2526 case UINT16_MAX: 2527 bfilter->dst_port_mask = -1; 2528 bfilter->dst_port = nfilter->dst_port; 2529 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT | 2530 NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT_MASK; 2531 break; 2532 default: 2533 PMD_DRV_LOG(ERR, "invalid dst_port mask."); 2534 return -EINVAL; 2535 } 2536 2537 bfilter->ip_addr_type = NTUPLE_FLTR_ALLOC_INPUT_IP_ADDR_TYPE_IPV4; 2538 en |= NTUPLE_FLTR_ALLOC_IN_EN_IP_PROTO; 2539 2540 switch (nfilter->proto_mask) { 2541 case UINT8_MAX: 2542 if (nfilter->proto == 17) /* IPPROTO_UDP */ 2543 bfilter->ip_protocol = 17; 2544 else if (nfilter->proto == 6) /* IPPROTO_TCP */ 2545 bfilter->ip_protocol = 6; 2546 else 2547 return -EINVAL; 2548 en |= NTUPLE_FLTR_ALLOC_IN_EN_IP_PROTO; 2549 break; 2550 default: 2551 PMD_DRV_LOG(ERR, "invalid protocol mask."); 2552 return -EINVAL; 2553 } 2554 2555 switch (nfilter->dst_ip_mask) { 2556 case UINT32_MAX: 2557 bfilter->dst_ipaddr_mask[0] = -1; 2558 bfilter->dst_ipaddr[0] = nfilter->dst_ip; 2559 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR | 2560 NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR_MASK; 2561 break; 2562 default: 2563 PMD_DRV_LOG(ERR, "invalid dst_ip mask."); 2564 return -EINVAL; 2565 } 2566 2567 switch (nfilter->src_ip_mask) { 2568 case UINT32_MAX: 2569 bfilter->src_ipaddr_mask[0] = -1; 2570 bfilter->src_ipaddr[0] = nfilter->src_ip; 2571 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR | 2572 NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR_MASK; 2573 break; 2574 default: 2575 PMD_DRV_LOG(ERR, "invalid src_ip mask."); 2576 return -EINVAL; 2577 } 2578 2579 switch (nfilter->src_port_mask) { 2580 case UINT16_MAX: 2581 bfilter->src_port_mask = -1; 2582 bfilter->src_port = nfilter->src_port; 2583 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT | 2584 NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT_MASK; 2585 break; 2586 default: 2587 PMD_DRV_LOG(ERR, "invalid src_port mask."); 2588 return -EINVAL; 2589 } 2590 2591 //TODO Priority 2592 //nfilter->priority = (uint8_t)filter->priority; 2593 2594 bfilter->enables = en; 2595 return 0; 2596 } 2597 2598 static struct bnxt_filter_info* 2599 bnxt_match_ntuple_filter(struct bnxt *bp, 2600 struct bnxt_filter_info *bfilter, 2601 struct bnxt_vnic_info **mvnic) 2602 { 2603 struct bnxt_filter_info *mfilter = NULL; 2604 int i; 2605 2606 for (i = bp->nr_vnics - 1; i >= 0; i--) { 2607 struct bnxt_vnic_info *vnic = &bp->vnic_info[i]; 2608 STAILQ_FOREACH(mfilter, &vnic->filter, next) { 2609 if (bfilter->src_ipaddr[0] == mfilter->src_ipaddr[0] && 2610 bfilter->src_ipaddr_mask[0] == 2611 mfilter->src_ipaddr_mask[0] && 2612 bfilter->src_port == mfilter->src_port && 2613 bfilter->src_port_mask == mfilter->src_port_mask && 2614 bfilter->dst_ipaddr[0] == mfilter->dst_ipaddr[0] && 2615 bfilter->dst_ipaddr_mask[0] == 2616 mfilter->dst_ipaddr_mask[0] && 2617 bfilter->dst_port == mfilter->dst_port && 2618 bfilter->dst_port_mask == mfilter->dst_port_mask && 2619 bfilter->flags == mfilter->flags && 2620 bfilter->enables == mfilter->enables) { 2621 if (mvnic) 2622 *mvnic = vnic; 2623 return mfilter; 2624 } 2625 } 2626 } 2627 return NULL; 2628 } 2629 2630 static int 2631 bnxt_cfg_ntuple_filter(struct bnxt *bp, 2632 struct rte_eth_ntuple_filter *nfilter, 2633 enum rte_filter_op filter_op) 2634 { 2635 struct bnxt_filter_info *bfilter, *mfilter, *filter1; 2636 struct bnxt_vnic_info *vnic, *vnic0, *mvnic; 2637 int ret; 2638 2639 if (nfilter->flags != RTE_5TUPLE_FLAGS) { 2640 PMD_DRV_LOG(ERR, "only 5tuple is supported."); 2641 return -EINVAL; 2642 } 2643 2644 if (nfilter->flags & RTE_NTUPLE_FLAGS_TCP_FLAG) { 2645 PMD_DRV_LOG(ERR, "Ntuple filter: TCP flags not supported\n"); 2646 return -EINVAL; 2647 } 2648 2649 bfilter = bnxt_get_unused_filter(bp); 2650 if (bfilter == NULL) { 2651 PMD_DRV_LOG(ERR, 2652 "Not enough resources for a new filter.\n"); 2653 return -ENOMEM; 2654 } 2655 ret = parse_ntuple_filter(bp, nfilter, bfilter); 2656 if (ret < 0) 2657 goto free_filter; 2658 2659 vnic = &bp->vnic_info[nfilter->queue]; 2660 vnic0 = &bp->vnic_info[0]; 2661 filter1 = STAILQ_FIRST(&vnic0->filter); 2662 if (filter1 == NULL) { 2663 ret = -EINVAL; 2664 goto free_filter; 2665 } 2666 2667 bfilter->dst_id = vnic->fw_vnic_id; 2668 bfilter->fw_l2_filter_id = filter1->fw_l2_filter_id; 2669 bfilter->enables |= 2670 HWRM_CFA_NTUPLE_FILTER_ALLOC_INPUT_ENABLES_L2_FILTER_ID; 2671 bfilter->ethertype = 0x800; 2672 bfilter->enables |= NTUPLE_FLTR_ALLOC_INPUT_EN_ETHERTYPE; 2673 2674 mfilter = bnxt_match_ntuple_filter(bp, bfilter, &mvnic); 2675 2676 if (mfilter != NULL && filter_op == RTE_ETH_FILTER_ADD && 2677 bfilter->dst_id == mfilter->dst_id) { 2678 PMD_DRV_LOG(ERR, "filter exists.\n"); 2679 ret = -EEXIST; 2680 goto free_filter; 2681 } else if (mfilter != NULL && filter_op == RTE_ETH_FILTER_ADD && 2682 bfilter->dst_id != mfilter->dst_id) { 2683 mfilter->dst_id = vnic->fw_vnic_id; 2684 ret = bnxt_hwrm_set_ntuple_filter(bp, mfilter->dst_id, mfilter); 2685 STAILQ_REMOVE(&mvnic->filter, mfilter, bnxt_filter_info, next); 2686 STAILQ_INSERT_TAIL(&vnic->filter, mfilter, next); 2687 PMD_DRV_LOG(ERR, "filter with matching pattern exists.\n"); 2688 PMD_DRV_LOG(ERR, " Updated it to the new destination queue\n"); 2689 goto free_filter; 2690 } 2691 if (mfilter == NULL && filter_op == RTE_ETH_FILTER_DELETE) { 2692 PMD_DRV_LOG(ERR, "filter doesn't exist."); 2693 ret = -ENOENT; 2694 goto free_filter; 2695 } 2696 2697 if (filter_op == RTE_ETH_FILTER_ADD) { 2698 bfilter->filter_type = HWRM_CFA_NTUPLE_FILTER; 2699 ret = bnxt_hwrm_set_ntuple_filter(bp, bfilter->dst_id, bfilter); 2700 if (ret) 2701 goto free_filter; 2702 STAILQ_INSERT_TAIL(&vnic->filter, bfilter, next); 2703 } else { 2704 if (mfilter == NULL) { 2705 /* This should not happen. But for Coverity! */ 2706 ret = -ENOENT; 2707 goto free_filter; 2708 } 2709 ret = bnxt_hwrm_clear_ntuple_filter(bp, mfilter); 2710 2711 STAILQ_REMOVE(&vnic->filter, mfilter, bnxt_filter_info, next); 2712 bnxt_free_filter(bp, mfilter); 2713 mfilter->fw_l2_filter_id = -1; 2714 bnxt_free_filter(bp, bfilter); 2715 bfilter->fw_l2_filter_id = -1; 2716 } 2717 2718 return 0; 2719 free_filter: 2720 bfilter->fw_l2_filter_id = -1; 2721 bnxt_free_filter(bp, bfilter); 2722 return ret; 2723 } 2724 2725 static int 2726 bnxt_ntuple_filter(struct rte_eth_dev *dev, 2727 enum rte_filter_op filter_op, 2728 void *arg) 2729 { 2730 struct bnxt *bp = dev->data->dev_private; 2731 int ret; 2732 2733 if (filter_op == RTE_ETH_FILTER_NOP) 2734 return 0; 2735 2736 if (arg == NULL) { 2737 PMD_DRV_LOG(ERR, "arg shouldn't be NULL for operation %u.", 2738 filter_op); 2739 return -EINVAL; 2740 } 2741 2742 switch (filter_op) { 2743 case RTE_ETH_FILTER_ADD: 2744 ret = bnxt_cfg_ntuple_filter(bp, 2745 (struct rte_eth_ntuple_filter *)arg, 2746 filter_op); 2747 break; 2748 case RTE_ETH_FILTER_DELETE: 2749 ret = bnxt_cfg_ntuple_filter(bp, 2750 (struct rte_eth_ntuple_filter *)arg, 2751 filter_op); 2752 break; 2753 default: 2754 PMD_DRV_LOG(ERR, "unsupported operation %u.", filter_op); 2755 ret = -EINVAL; 2756 break; 2757 } 2758 return ret; 2759 } 2760 2761 static int 2762 bnxt_parse_fdir_filter(struct bnxt *bp, 2763 struct rte_eth_fdir_filter *fdir, 2764 struct bnxt_filter_info *filter) 2765 { 2766 enum rte_fdir_mode fdir_mode = 2767 bp->eth_dev->data->dev_conf.fdir_conf.mode; 2768 struct bnxt_vnic_info *vnic0, *vnic; 2769 struct bnxt_filter_info *filter1; 2770 uint32_t en = 0; 2771 int i; 2772 2773 if (fdir_mode == RTE_FDIR_MODE_PERFECT_TUNNEL) 2774 return -EINVAL; 2775 2776 filter->l2_ovlan = fdir->input.flow_ext.vlan_tci; 2777 en |= EM_FLOW_ALLOC_INPUT_EN_OVLAN_VID; 2778 2779 switch (fdir->input.flow_type) { 2780 case RTE_ETH_FLOW_IPV4: 2781 case RTE_ETH_FLOW_NONFRAG_IPV4_OTHER: 2782 /* FALLTHROUGH */ 2783 filter->src_ipaddr[0] = fdir->input.flow.ip4_flow.src_ip; 2784 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR; 2785 filter->dst_ipaddr[0] = fdir->input.flow.ip4_flow.dst_ip; 2786 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR; 2787 filter->ip_protocol = fdir->input.flow.ip4_flow.proto; 2788 en |= NTUPLE_FLTR_ALLOC_IN_EN_IP_PROTO; 2789 filter->ip_addr_type = 2790 NTUPLE_FLTR_ALLOC_INPUT_IP_ADDR_TYPE_IPV4; 2791 filter->src_ipaddr_mask[0] = 0xffffffff; 2792 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR_MASK; 2793 filter->dst_ipaddr_mask[0] = 0xffffffff; 2794 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR_MASK; 2795 filter->ethertype = 0x800; 2796 filter->enables |= NTUPLE_FLTR_ALLOC_INPUT_EN_ETHERTYPE; 2797 break; 2798 case RTE_ETH_FLOW_NONFRAG_IPV4_TCP: 2799 filter->src_port = fdir->input.flow.tcp4_flow.src_port; 2800 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT; 2801 filter->dst_port = fdir->input.flow.tcp4_flow.dst_port; 2802 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT; 2803 filter->dst_port_mask = 0xffff; 2804 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT_MASK; 2805 filter->src_port_mask = 0xffff; 2806 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT_MASK; 2807 filter->src_ipaddr[0] = fdir->input.flow.tcp4_flow.ip.src_ip; 2808 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR; 2809 filter->dst_ipaddr[0] = fdir->input.flow.tcp4_flow.ip.dst_ip; 2810 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR; 2811 filter->ip_protocol = 6; 2812 en |= NTUPLE_FLTR_ALLOC_IN_EN_IP_PROTO; 2813 filter->ip_addr_type = 2814 NTUPLE_FLTR_ALLOC_INPUT_IP_ADDR_TYPE_IPV4; 2815 filter->src_ipaddr_mask[0] = 0xffffffff; 2816 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR_MASK; 2817 filter->dst_ipaddr_mask[0] = 0xffffffff; 2818 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR_MASK; 2819 filter->ethertype = 0x800; 2820 filter->enables |= NTUPLE_FLTR_ALLOC_INPUT_EN_ETHERTYPE; 2821 break; 2822 case RTE_ETH_FLOW_NONFRAG_IPV4_UDP: 2823 filter->src_port = fdir->input.flow.udp4_flow.src_port; 2824 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT; 2825 filter->dst_port = fdir->input.flow.udp4_flow.dst_port; 2826 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT; 2827 filter->dst_port_mask = 0xffff; 2828 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT_MASK; 2829 filter->src_port_mask = 0xffff; 2830 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT_MASK; 2831 filter->src_ipaddr[0] = fdir->input.flow.udp4_flow.ip.src_ip; 2832 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR; 2833 filter->dst_ipaddr[0] = fdir->input.flow.udp4_flow.ip.dst_ip; 2834 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR; 2835 filter->ip_protocol = 17; 2836 en |= NTUPLE_FLTR_ALLOC_IN_EN_IP_PROTO; 2837 filter->ip_addr_type = 2838 NTUPLE_FLTR_ALLOC_INPUT_IP_ADDR_TYPE_IPV4; 2839 filter->src_ipaddr_mask[0] = 0xffffffff; 2840 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR_MASK; 2841 filter->dst_ipaddr_mask[0] = 0xffffffff; 2842 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR_MASK; 2843 filter->ethertype = 0x800; 2844 filter->enables |= NTUPLE_FLTR_ALLOC_INPUT_EN_ETHERTYPE; 2845 break; 2846 case RTE_ETH_FLOW_IPV6: 2847 case RTE_ETH_FLOW_NONFRAG_IPV6_OTHER: 2848 /* FALLTHROUGH */ 2849 filter->ip_addr_type = 2850 NTUPLE_FLTR_ALLOC_INPUT_IP_ADDR_TYPE_IPV6; 2851 filter->ip_protocol = fdir->input.flow.ipv6_flow.proto; 2852 en |= NTUPLE_FLTR_ALLOC_IN_EN_IP_PROTO; 2853 rte_memcpy(filter->src_ipaddr, 2854 fdir->input.flow.ipv6_flow.src_ip, 16); 2855 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR; 2856 rte_memcpy(filter->dst_ipaddr, 2857 fdir->input.flow.ipv6_flow.dst_ip, 16); 2858 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR; 2859 memset(filter->dst_ipaddr_mask, 0xff, 16); 2860 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR_MASK; 2861 memset(filter->src_ipaddr_mask, 0xff, 16); 2862 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR_MASK; 2863 filter->ethertype = 0x86dd; 2864 filter->enables |= NTUPLE_FLTR_ALLOC_INPUT_EN_ETHERTYPE; 2865 break; 2866 case RTE_ETH_FLOW_NONFRAG_IPV6_TCP: 2867 filter->src_port = fdir->input.flow.tcp6_flow.src_port; 2868 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT; 2869 filter->dst_port = fdir->input.flow.tcp6_flow.dst_port; 2870 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT; 2871 filter->dst_port_mask = 0xffff; 2872 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT_MASK; 2873 filter->src_port_mask = 0xffff; 2874 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT_MASK; 2875 filter->ip_addr_type = 2876 NTUPLE_FLTR_ALLOC_INPUT_IP_ADDR_TYPE_IPV6; 2877 filter->ip_protocol = fdir->input.flow.tcp6_flow.ip.proto; 2878 en |= NTUPLE_FLTR_ALLOC_IN_EN_IP_PROTO; 2879 rte_memcpy(filter->src_ipaddr, 2880 fdir->input.flow.tcp6_flow.ip.src_ip, 16); 2881 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR; 2882 rte_memcpy(filter->dst_ipaddr, 2883 fdir->input.flow.tcp6_flow.ip.dst_ip, 16); 2884 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR; 2885 memset(filter->dst_ipaddr_mask, 0xff, 16); 2886 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR_MASK; 2887 memset(filter->src_ipaddr_mask, 0xff, 16); 2888 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR_MASK; 2889 filter->ethertype = 0x86dd; 2890 filter->enables |= NTUPLE_FLTR_ALLOC_INPUT_EN_ETHERTYPE; 2891 break; 2892 case RTE_ETH_FLOW_NONFRAG_IPV6_UDP: 2893 filter->src_port = fdir->input.flow.udp6_flow.src_port; 2894 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT; 2895 filter->dst_port = fdir->input.flow.udp6_flow.dst_port; 2896 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT; 2897 filter->dst_port_mask = 0xffff; 2898 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_PORT_MASK; 2899 filter->src_port_mask = 0xffff; 2900 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_PORT_MASK; 2901 filter->ip_addr_type = 2902 NTUPLE_FLTR_ALLOC_INPUT_IP_ADDR_TYPE_IPV6; 2903 filter->ip_protocol = fdir->input.flow.udp6_flow.ip.proto; 2904 en |= NTUPLE_FLTR_ALLOC_IN_EN_IP_PROTO; 2905 rte_memcpy(filter->src_ipaddr, 2906 fdir->input.flow.udp6_flow.ip.src_ip, 16); 2907 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR; 2908 rte_memcpy(filter->dst_ipaddr, 2909 fdir->input.flow.udp6_flow.ip.dst_ip, 16); 2910 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR; 2911 memset(filter->dst_ipaddr_mask, 0xff, 16); 2912 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_IPADDR_MASK; 2913 memset(filter->src_ipaddr_mask, 0xff, 16); 2914 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_SRC_IPADDR_MASK; 2915 filter->ethertype = 0x86dd; 2916 filter->enables |= NTUPLE_FLTR_ALLOC_INPUT_EN_ETHERTYPE; 2917 break; 2918 case RTE_ETH_FLOW_L2_PAYLOAD: 2919 filter->ethertype = fdir->input.flow.l2_flow.ether_type; 2920 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_ETHERTYPE; 2921 break; 2922 case RTE_ETH_FLOW_VXLAN: 2923 if (fdir->action.behavior == RTE_ETH_FDIR_REJECT) 2924 return -EINVAL; 2925 filter->vni = fdir->input.flow.tunnel_flow.tunnel_id; 2926 filter->tunnel_type = 2927 CFA_NTUPLE_FILTER_ALLOC_REQ_TUNNEL_TYPE_VXLAN; 2928 en |= HWRM_CFA_NTUPLE_FILTER_ALLOC_INPUT_ENABLES_TUNNEL_TYPE; 2929 break; 2930 case RTE_ETH_FLOW_NVGRE: 2931 if (fdir->action.behavior == RTE_ETH_FDIR_REJECT) 2932 return -EINVAL; 2933 filter->vni = fdir->input.flow.tunnel_flow.tunnel_id; 2934 filter->tunnel_type = 2935 CFA_NTUPLE_FILTER_ALLOC_REQ_TUNNEL_TYPE_NVGRE; 2936 en |= HWRM_CFA_NTUPLE_FILTER_ALLOC_INPUT_ENABLES_TUNNEL_TYPE; 2937 break; 2938 case RTE_ETH_FLOW_UNKNOWN: 2939 case RTE_ETH_FLOW_RAW: 2940 case RTE_ETH_FLOW_FRAG_IPV4: 2941 case RTE_ETH_FLOW_NONFRAG_IPV4_SCTP: 2942 case RTE_ETH_FLOW_FRAG_IPV6: 2943 case RTE_ETH_FLOW_NONFRAG_IPV6_SCTP: 2944 case RTE_ETH_FLOW_IPV6_EX: 2945 case RTE_ETH_FLOW_IPV6_TCP_EX: 2946 case RTE_ETH_FLOW_IPV6_UDP_EX: 2947 case RTE_ETH_FLOW_GENEVE: 2948 /* FALLTHROUGH */ 2949 default: 2950 return -EINVAL; 2951 } 2952 2953 vnic0 = &bp->vnic_info[0]; 2954 vnic = &bp->vnic_info[fdir->action.rx_queue]; 2955 if (vnic == NULL) { 2956 PMD_DRV_LOG(ERR, "Invalid queue %d\n", fdir->action.rx_queue); 2957 return -EINVAL; 2958 } 2959 2960 if (fdir_mode == RTE_FDIR_MODE_PERFECT_MAC_VLAN) { 2961 rte_memcpy(filter->dst_macaddr, 2962 fdir->input.flow.mac_vlan_flow.mac_addr.addr_bytes, 6); 2963 en |= NTUPLE_FLTR_ALLOC_INPUT_EN_DST_MACADDR; 2964 } 2965 2966 if (fdir->action.behavior == RTE_ETH_FDIR_REJECT) { 2967 filter->flags = HWRM_CFA_NTUPLE_FILTER_ALLOC_INPUT_FLAGS_DROP; 2968 filter1 = STAILQ_FIRST(&vnic0->filter); 2969 //filter1 = bnxt_get_l2_filter(bp, filter, vnic0); 2970 } else { 2971 filter->dst_id = vnic->fw_vnic_id; 2972 for (i = 0; i < RTE_ETHER_ADDR_LEN; i++) 2973 if (filter->dst_macaddr[i] == 0x00) 2974 filter1 = STAILQ_FIRST(&vnic0->filter); 2975 else 2976 filter1 = bnxt_get_l2_filter(bp, filter, vnic); 2977 } 2978 2979 if (filter1 == NULL) 2980 return -EINVAL; 2981 2982 en |= HWRM_CFA_NTUPLE_FILTER_ALLOC_INPUT_ENABLES_L2_FILTER_ID; 2983 filter->fw_l2_filter_id = filter1->fw_l2_filter_id; 2984 2985 filter->enables = en; 2986 2987 return 0; 2988 } 2989 2990 static struct bnxt_filter_info * 2991 bnxt_match_fdir(struct bnxt *bp, struct bnxt_filter_info *nf, 2992 struct bnxt_vnic_info **mvnic) 2993 { 2994 struct bnxt_filter_info *mf = NULL; 2995 int i; 2996 2997 for (i = bp->nr_vnics - 1; i >= 0; i--) { 2998 struct bnxt_vnic_info *vnic = &bp->vnic_info[i]; 2999 3000 STAILQ_FOREACH(mf, &vnic->filter, next) { 3001 if (mf->filter_type == nf->filter_type && 3002 mf->flags == nf->flags && 3003 mf->src_port == nf->src_port && 3004 mf->src_port_mask == nf->src_port_mask && 3005 mf->dst_port == nf->dst_port && 3006 mf->dst_port_mask == nf->dst_port_mask && 3007 mf->ip_protocol == nf->ip_protocol && 3008 mf->ip_addr_type == nf->ip_addr_type && 3009 mf->ethertype == nf->ethertype && 3010 mf->vni == nf->vni && 3011 mf->tunnel_type == nf->tunnel_type && 3012 mf->l2_ovlan == nf->l2_ovlan && 3013 mf->l2_ovlan_mask == nf->l2_ovlan_mask && 3014 mf->l2_ivlan == nf->l2_ivlan && 3015 mf->l2_ivlan_mask == nf->l2_ivlan_mask && 3016 !memcmp(mf->l2_addr, nf->l2_addr, 3017 RTE_ETHER_ADDR_LEN) && 3018 !memcmp(mf->l2_addr_mask, nf->l2_addr_mask, 3019 RTE_ETHER_ADDR_LEN) && 3020 !memcmp(mf->src_macaddr, nf->src_macaddr, 3021 RTE_ETHER_ADDR_LEN) && 3022 !memcmp(mf->dst_macaddr, nf->dst_macaddr, 3023 RTE_ETHER_ADDR_LEN) && 3024 !memcmp(mf->src_ipaddr, nf->src_ipaddr, 3025 sizeof(nf->src_ipaddr)) && 3026 !memcmp(mf->src_ipaddr_mask, nf->src_ipaddr_mask, 3027 sizeof(nf->src_ipaddr_mask)) && 3028 !memcmp(mf->dst_ipaddr, nf->dst_ipaddr, 3029 sizeof(nf->dst_ipaddr)) && 3030 !memcmp(mf->dst_ipaddr_mask, nf->dst_ipaddr_mask, 3031 sizeof(nf->dst_ipaddr_mask))) { 3032 if (mvnic) 3033 *mvnic = vnic; 3034 return mf; 3035 } 3036 } 3037 } 3038 return NULL; 3039 } 3040 3041 static int 3042 bnxt_fdir_filter(struct rte_eth_dev *dev, 3043 enum rte_filter_op filter_op, 3044 void *arg) 3045 { 3046 struct bnxt *bp = dev->data->dev_private; 3047 struct rte_eth_fdir_filter *fdir = (struct rte_eth_fdir_filter *)arg; 3048 struct bnxt_filter_info *filter, *match; 3049 struct bnxt_vnic_info *vnic, *mvnic; 3050 int ret = 0, i; 3051 3052 if (filter_op == RTE_ETH_FILTER_NOP) 3053 return 0; 3054 3055 if (arg == NULL && filter_op != RTE_ETH_FILTER_FLUSH) 3056 return -EINVAL; 3057 3058 switch (filter_op) { 3059 case RTE_ETH_FILTER_ADD: 3060 case RTE_ETH_FILTER_DELETE: 3061 /* FALLTHROUGH */ 3062 filter = bnxt_get_unused_filter(bp); 3063 if (filter == NULL) { 3064 PMD_DRV_LOG(ERR, 3065 "Not enough resources for a new flow.\n"); 3066 return -ENOMEM; 3067 } 3068 3069 ret = bnxt_parse_fdir_filter(bp, fdir, filter); 3070 if (ret != 0) 3071 goto free_filter; 3072 filter->filter_type = HWRM_CFA_NTUPLE_FILTER; 3073 3074 if (fdir->action.behavior == RTE_ETH_FDIR_REJECT) 3075 vnic = &bp->vnic_info[0]; 3076 else 3077 vnic = &bp->vnic_info[fdir->action.rx_queue]; 3078 3079 match = bnxt_match_fdir(bp, filter, &mvnic); 3080 if (match != NULL && filter_op == RTE_ETH_FILTER_ADD) { 3081 if (match->dst_id == vnic->fw_vnic_id) { 3082 PMD_DRV_LOG(ERR, "Flow already exists.\n"); 3083 ret = -EEXIST; 3084 goto free_filter; 3085 } else { 3086 match->dst_id = vnic->fw_vnic_id; 3087 ret = bnxt_hwrm_set_ntuple_filter(bp, 3088 match->dst_id, 3089 match); 3090 STAILQ_REMOVE(&mvnic->filter, match, 3091 bnxt_filter_info, next); 3092 STAILQ_INSERT_TAIL(&vnic->filter, match, next); 3093 PMD_DRV_LOG(ERR, 3094 "Filter with matching pattern exist\n"); 3095 PMD_DRV_LOG(ERR, 3096 "Updated it to new destination q\n"); 3097 goto free_filter; 3098 } 3099 } 3100 if (match == NULL && filter_op == RTE_ETH_FILTER_DELETE) { 3101 PMD_DRV_LOG(ERR, "Flow does not exist.\n"); 3102 ret = -ENOENT; 3103 goto free_filter; 3104 } 3105 3106 if (filter_op == RTE_ETH_FILTER_ADD) { 3107 ret = bnxt_hwrm_set_ntuple_filter(bp, 3108 filter->dst_id, 3109 filter); 3110 if (ret) 3111 goto free_filter; 3112 STAILQ_INSERT_TAIL(&vnic->filter, filter, next); 3113 } else { 3114 ret = bnxt_hwrm_clear_ntuple_filter(bp, match); 3115 STAILQ_REMOVE(&vnic->filter, match, 3116 bnxt_filter_info, next); 3117 bnxt_free_filter(bp, match); 3118 filter->fw_l2_filter_id = -1; 3119 bnxt_free_filter(bp, filter); 3120 } 3121 break; 3122 case RTE_ETH_FILTER_FLUSH: 3123 for (i = bp->nr_vnics - 1; i >= 0; i--) { 3124 struct bnxt_vnic_info *vnic = &bp->vnic_info[i]; 3125 3126 STAILQ_FOREACH(filter, &vnic->filter, next) { 3127 if (filter->filter_type == 3128 HWRM_CFA_NTUPLE_FILTER) { 3129 ret = 3130 bnxt_hwrm_clear_ntuple_filter(bp, 3131 filter); 3132 STAILQ_REMOVE(&vnic->filter, filter, 3133 bnxt_filter_info, next); 3134 } 3135 } 3136 } 3137 return ret; 3138 case RTE_ETH_FILTER_UPDATE: 3139 case RTE_ETH_FILTER_STATS: 3140 case RTE_ETH_FILTER_INFO: 3141 PMD_DRV_LOG(ERR, "operation %u not implemented", filter_op); 3142 break; 3143 default: 3144 PMD_DRV_LOG(ERR, "unknown operation %u", filter_op); 3145 ret = -EINVAL; 3146 break; 3147 } 3148 return ret; 3149 3150 free_filter: 3151 filter->fw_l2_filter_id = -1; 3152 bnxt_free_filter(bp, filter); 3153 return ret; 3154 } 3155 3156 static int 3157 bnxt_filter_ctrl_op(struct rte_eth_dev *dev __rte_unused, 3158 enum rte_filter_type filter_type, 3159 enum rte_filter_op filter_op, void *arg) 3160 { 3161 int ret = 0; 3162 3163 ret = is_bnxt_in_error(dev->data->dev_private); 3164 if (ret) 3165 return ret; 3166 3167 switch (filter_type) { 3168 case RTE_ETH_FILTER_TUNNEL: 3169 PMD_DRV_LOG(ERR, 3170 "filter type: %d: To be implemented\n", filter_type); 3171 break; 3172 case RTE_ETH_FILTER_FDIR: 3173 ret = bnxt_fdir_filter(dev, filter_op, arg); 3174 break; 3175 case RTE_ETH_FILTER_NTUPLE: 3176 ret = bnxt_ntuple_filter(dev, filter_op, arg); 3177 break; 3178 case RTE_ETH_FILTER_ETHERTYPE: 3179 ret = bnxt_ethertype_filter(dev, filter_op, arg); 3180 break; 3181 case RTE_ETH_FILTER_GENERIC: 3182 if (filter_op != RTE_ETH_FILTER_GET) 3183 return -EINVAL; 3184 *(const void **)arg = &bnxt_flow_ops; 3185 break; 3186 default: 3187 PMD_DRV_LOG(ERR, 3188 "Filter type (%d) not supported", filter_type); 3189 ret = -EINVAL; 3190 break; 3191 } 3192 return ret; 3193 } 3194 3195 static const uint32_t * 3196 bnxt_dev_supported_ptypes_get_op(struct rte_eth_dev *dev) 3197 { 3198 static const uint32_t ptypes[] = { 3199 RTE_PTYPE_L2_ETHER_VLAN, 3200 RTE_PTYPE_L3_IPV4_EXT_UNKNOWN, 3201 RTE_PTYPE_L3_IPV6_EXT_UNKNOWN, 3202 RTE_PTYPE_L4_ICMP, 3203 RTE_PTYPE_L4_TCP, 3204 RTE_PTYPE_L4_UDP, 3205 RTE_PTYPE_INNER_L3_IPV4_EXT_UNKNOWN, 3206 RTE_PTYPE_INNER_L3_IPV6_EXT_UNKNOWN, 3207 RTE_PTYPE_INNER_L4_ICMP, 3208 RTE_PTYPE_INNER_L4_TCP, 3209 RTE_PTYPE_INNER_L4_UDP, 3210 RTE_PTYPE_UNKNOWN 3211 }; 3212 3213 if (!dev->rx_pkt_burst) 3214 return NULL; 3215 3216 return ptypes; 3217 } 3218 3219 static int bnxt_map_regs(struct bnxt *bp, uint32_t *reg_arr, int count, 3220 int reg_win) 3221 { 3222 uint32_t reg_base = *reg_arr & 0xfffff000; 3223 uint32_t win_off; 3224 int i; 3225 3226 for (i = 0; i < count; i++) { 3227 if ((reg_arr[i] & 0xfffff000) != reg_base) 3228 return -ERANGE; 3229 } 3230 win_off = BNXT_GRCPF_REG_WINDOW_BASE_OUT + (reg_win - 1) * 4; 3231 rte_write32(reg_base, (uint8_t *)bp->bar0 + win_off); 3232 return 0; 3233 } 3234 3235 static int bnxt_map_ptp_regs(struct bnxt *bp) 3236 { 3237 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3238 uint32_t *reg_arr; 3239 int rc, i; 3240 3241 reg_arr = ptp->rx_regs; 3242 rc = bnxt_map_regs(bp, reg_arr, BNXT_PTP_RX_REGS, 5); 3243 if (rc) 3244 return rc; 3245 3246 reg_arr = ptp->tx_regs; 3247 rc = bnxt_map_regs(bp, reg_arr, BNXT_PTP_TX_REGS, 6); 3248 if (rc) 3249 return rc; 3250 3251 for (i = 0; i < BNXT_PTP_RX_REGS; i++) 3252 ptp->rx_mapped_regs[i] = 0x5000 + (ptp->rx_regs[i] & 0xfff); 3253 3254 for (i = 0; i < BNXT_PTP_TX_REGS; i++) 3255 ptp->tx_mapped_regs[i] = 0x6000 + (ptp->tx_regs[i] & 0xfff); 3256 3257 return 0; 3258 } 3259 3260 static void bnxt_unmap_ptp_regs(struct bnxt *bp) 3261 { 3262 rte_write32(0, (uint8_t *)bp->bar0 + 3263 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 16); 3264 rte_write32(0, (uint8_t *)bp->bar0 + 3265 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 20); 3266 } 3267 3268 static uint64_t bnxt_cc_read(struct bnxt *bp) 3269 { 3270 uint64_t ns; 3271 3272 ns = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3273 BNXT_GRCPF_REG_SYNC_TIME)); 3274 ns |= (uint64_t)(rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3275 BNXT_GRCPF_REG_SYNC_TIME + 4))) << 32; 3276 return ns; 3277 } 3278 3279 static int bnxt_get_tx_ts(struct bnxt *bp, uint64_t *ts) 3280 { 3281 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3282 uint32_t fifo; 3283 3284 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3285 ptp->tx_mapped_regs[BNXT_PTP_TX_FIFO])); 3286 if (fifo & BNXT_PTP_TX_FIFO_EMPTY) 3287 return -EAGAIN; 3288 3289 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3290 ptp->tx_mapped_regs[BNXT_PTP_TX_FIFO])); 3291 *ts = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3292 ptp->tx_mapped_regs[BNXT_PTP_TX_TS_L])); 3293 *ts |= (uint64_t)rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3294 ptp->tx_mapped_regs[BNXT_PTP_TX_TS_H])) << 32; 3295 3296 return 0; 3297 } 3298 3299 static int bnxt_get_rx_ts(struct bnxt *bp, uint64_t *ts) 3300 { 3301 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3302 struct bnxt_pf_info *pf = &bp->pf; 3303 uint16_t port_id; 3304 uint32_t fifo; 3305 3306 if (!ptp) 3307 return -ENODEV; 3308 3309 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3310 ptp->rx_mapped_regs[BNXT_PTP_RX_FIFO])); 3311 if (!(fifo & BNXT_PTP_RX_FIFO_PENDING)) 3312 return -EAGAIN; 3313 3314 port_id = pf->port_id; 3315 rte_write32(1 << port_id, (uint8_t *)bp->bar0 + 3316 ptp->rx_mapped_regs[BNXT_PTP_RX_FIFO_ADV]); 3317 3318 fifo = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3319 ptp->rx_mapped_regs[BNXT_PTP_RX_FIFO])); 3320 if (fifo & BNXT_PTP_RX_FIFO_PENDING) { 3321 /* bnxt_clr_rx_ts(bp); TBD */ 3322 return -EBUSY; 3323 } 3324 3325 *ts = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3326 ptp->rx_mapped_regs[BNXT_PTP_RX_TS_L])); 3327 *ts |= (uint64_t)rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3328 ptp->rx_mapped_regs[BNXT_PTP_RX_TS_H])) << 32; 3329 3330 return 0; 3331 } 3332 3333 static int 3334 bnxt_timesync_write_time(struct rte_eth_dev *dev, const struct timespec *ts) 3335 { 3336 uint64_t ns; 3337 struct bnxt *bp = dev->data->dev_private; 3338 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3339 3340 if (!ptp) 3341 return 0; 3342 3343 ns = rte_timespec_to_ns(ts); 3344 /* Set the timecounters to a new value. */ 3345 ptp->tc.nsec = ns; 3346 3347 return 0; 3348 } 3349 3350 static int 3351 bnxt_timesync_read_time(struct rte_eth_dev *dev, struct timespec *ts) 3352 { 3353 struct bnxt *bp = dev->data->dev_private; 3354 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3355 uint64_t ns, systime_cycles = 0; 3356 int rc = 0; 3357 3358 if (!ptp) 3359 return 0; 3360 3361 if (BNXT_CHIP_THOR(bp)) 3362 rc = bnxt_hwrm_port_ts_query(bp, BNXT_PTP_FLAGS_CURRENT_TIME, 3363 &systime_cycles); 3364 else 3365 systime_cycles = bnxt_cc_read(bp); 3366 3367 ns = rte_timecounter_update(&ptp->tc, systime_cycles); 3368 *ts = rte_ns_to_timespec(ns); 3369 3370 return rc; 3371 } 3372 static int 3373 bnxt_timesync_enable(struct rte_eth_dev *dev) 3374 { 3375 struct bnxt *bp = dev->data->dev_private; 3376 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3377 uint32_t shift = 0; 3378 int rc; 3379 3380 if (!ptp) 3381 return 0; 3382 3383 ptp->rx_filter = 1; 3384 ptp->tx_tstamp_en = 1; 3385 ptp->rxctl = BNXT_PTP_MSG_EVENTS; 3386 3387 rc = bnxt_hwrm_ptp_cfg(bp); 3388 if (rc) 3389 return rc; 3390 3391 memset(&ptp->tc, 0, sizeof(struct rte_timecounter)); 3392 memset(&ptp->rx_tstamp_tc, 0, sizeof(struct rte_timecounter)); 3393 memset(&ptp->tx_tstamp_tc, 0, sizeof(struct rte_timecounter)); 3394 3395 ptp->tc.cc_mask = BNXT_CYCLECOUNTER_MASK; 3396 ptp->tc.cc_shift = shift; 3397 ptp->tc.nsec_mask = (1ULL << shift) - 1; 3398 3399 ptp->rx_tstamp_tc.cc_mask = BNXT_CYCLECOUNTER_MASK; 3400 ptp->rx_tstamp_tc.cc_shift = shift; 3401 ptp->rx_tstamp_tc.nsec_mask = (1ULL << shift) - 1; 3402 3403 ptp->tx_tstamp_tc.cc_mask = BNXT_CYCLECOUNTER_MASK; 3404 ptp->tx_tstamp_tc.cc_shift = shift; 3405 ptp->tx_tstamp_tc.nsec_mask = (1ULL << shift) - 1; 3406 3407 if (!BNXT_CHIP_THOR(bp)) 3408 bnxt_map_ptp_regs(bp); 3409 3410 return 0; 3411 } 3412 3413 static int 3414 bnxt_timesync_disable(struct rte_eth_dev *dev) 3415 { 3416 struct bnxt *bp = dev->data->dev_private; 3417 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3418 3419 if (!ptp) 3420 return 0; 3421 3422 ptp->rx_filter = 0; 3423 ptp->tx_tstamp_en = 0; 3424 ptp->rxctl = 0; 3425 3426 bnxt_hwrm_ptp_cfg(bp); 3427 3428 if (!BNXT_CHIP_THOR(bp)) 3429 bnxt_unmap_ptp_regs(bp); 3430 3431 return 0; 3432 } 3433 3434 static int 3435 bnxt_timesync_read_rx_timestamp(struct rte_eth_dev *dev, 3436 struct timespec *timestamp, 3437 uint32_t flags __rte_unused) 3438 { 3439 struct bnxt *bp = dev->data->dev_private; 3440 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3441 uint64_t rx_tstamp_cycles = 0; 3442 uint64_t ns; 3443 3444 if (!ptp) 3445 return 0; 3446 3447 if (BNXT_CHIP_THOR(bp)) 3448 rx_tstamp_cycles = ptp->rx_timestamp; 3449 else 3450 bnxt_get_rx_ts(bp, &rx_tstamp_cycles); 3451 3452 ns = rte_timecounter_update(&ptp->rx_tstamp_tc, rx_tstamp_cycles); 3453 *timestamp = rte_ns_to_timespec(ns); 3454 return 0; 3455 } 3456 3457 static int 3458 bnxt_timesync_read_tx_timestamp(struct rte_eth_dev *dev, 3459 struct timespec *timestamp) 3460 { 3461 struct bnxt *bp = dev->data->dev_private; 3462 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3463 uint64_t tx_tstamp_cycles = 0; 3464 uint64_t ns; 3465 int rc = 0; 3466 3467 if (!ptp) 3468 return 0; 3469 3470 if (BNXT_CHIP_THOR(bp)) 3471 rc = bnxt_hwrm_port_ts_query(bp, BNXT_PTP_FLAGS_PATH_TX, 3472 &tx_tstamp_cycles); 3473 else 3474 rc = bnxt_get_tx_ts(bp, &tx_tstamp_cycles); 3475 3476 ns = rte_timecounter_update(&ptp->tx_tstamp_tc, tx_tstamp_cycles); 3477 *timestamp = rte_ns_to_timespec(ns); 3478 3479 return rc; 3480 } 3481 3482 static int 3483 bnxt_timesync_adjust_time(struct rte_eth_dev *dev, int64_t delta) 3484 { 3485 struct bnxt *bp = dev->data->dev_private; 3486 struct bnxt_ptp_cfg *ptp = bp->ptp_cfg; 3487 3488 if (!ptp) 3489 return 0; 3490 3491 ptp->tc.nsec += delta; 3492 3493 return 0; 3494 } 3495 3496 static int 3497 bnxt_get_eeprom_length_op(struct rte_eth_dev *dev) 3498 { 3499 struct bnxt *bp = dev->data->dev_private; 3500 int rc; 3501 uint32_t dir_entries; 3502 uint32_t entry_length; 3503 3504 rc = is_bnxt_in_error(bp); 3505 if (rc) 3506 return rc; 3507 3508 PMD_DRV_LOG(INFO, "%04x:%02x:%02x:%02x\n", 3509 bp->pdev->addr.domain, bp->pdev->addr.bus, 3510 bp->pdev->addr.devid, bp->pdev->addr.function); 3511 3512 rc = bnxt_hwrm_nvm_get_dir_info(bp, &dir_entries, &entry_length); 3513 if (rc != 0) 3514 return rc; 3515 3516 return dir_entries * entry_length; 3517 } 3518 3519 static int 3520 bnxt_get_eeprom_op(struct rte_eth_dev *dev, 3521 struct rte_dev_eeprom_info *in_eeprom) 3522 { 3523 struct bnxt *bp = dev->data->dev_private; 3524 uint32_t index; 3525 uint32_t offset; 3526 int rc; 3527 3528 rc = is_bnxt_in_error(bp); 3529 if (rc) 3530 return rc; 3531 3532 PMD_DRV_LOG(INFO, "%04x:%02x:%02x:%02x in_eeprom->offset = %d " 3533 "len = %d\n", bp->pdev->addr.domain, 3534 bp->pdev->addr.bus, bp->pdev->addr.devid, 3535 bp->pdev->addr.function, in_eeprom->offset, in_eeprom->length); 3536 3537 if (in_eeprom->offset == 0) /* special offset value to get directory */ 3538 return bnxt_get_nvram_directory(bp, in_eeprom->length, 3539 in_eeprom->data); 3540 3541 index = in_eeprom->offset >> 24; 3542 offset = in_eeprom->offset & 0xffffff; 3543 3544 if (index != 0) 3545 return bnxt_hwrm_get_nvram_item(bp, index - 1, offset, 3546 in_eeprom->length, in_eeprom->data); 3547 3548 return 0; 3549 } 3550 3551 static bool bnxt_dir_type_is_ape_bin_format(uint16_t dir_type) 3552 { 3553 switch (dir_type) { 3554 case BNX_DIR_TYPE_CHIMP_PATCH: 3555 case BNX_DIR_TYPE_BOOTCODE: 3556 case BNX_DIR_TYPE_BOOTCODE_2: 3557 case BNX_DIR_TYPE_APE_FW: 3558 case BNX_DIR_TYPE_APE_PATCH: 3559 case BNX_DIR_TYPE_KONG_FW: 3560 case BNX_DIR_TYPE_KONG_PATCH: 3561 case BNX_DIR_TYPE_BONO_FW: 3562 case BNX_DIR_TYPE_BONO_PATCH: 3563 /* FALLTHROUGH */ 3564 return true; 3565 } 3566 3567 return false; 3568 } 3569 3570 static bool bnxt_dir_type_is_other_exec_format(uint16_t dir_type) 3571 { 3572 switch (dir_type) { 3573 case BNX_DIR_TYPE_AVS: 3574 case BNX_DIR_TYPE_EXP_ROM_MBA: 3575 case BNX_DIR_TYPE_PCIE: 3576 case BNX_DIR_TYPE_TSCF_UCODE: 3577 case BNX_DIR_TYPE_EXT_PHY: 3578 case BNX_DIR_TYPE_CCM: 3579 case BNX_DIR_TYPE_ISCSI_BOOT: 3580 case BNX_DIR_TYPE_ISCSI_BOOT_IPV6: 3581 case BNX_DIR_TYPE_ISCSI_BOOT_IPV4N6: 3582 /* FALLTHROUGH */ 3583 return true; 3584 } 3585 3586 return false; 3587 } 3588 3589 static bool bnxt_dir_type_is_executable(uint16_t dir_type) 3590 { 3591 return bnxt_dir_type_is_ape_bin_format(dir_type) || 3592 bnxt_dir_type_is_other_exec_format(dir_type); 3593 } 3594 3595 static int 3596 bnxt_set_eeprom_op(struct rte_eth_dev *dev, 3597 struct rte_dev_eeprom_info *in_eeprom) 3598 { 3599 struct bnxt *bp = dev->data->dev_private; 3600 uint8_t index, dir_op; 3601 uint16_t type, ext, ordinal, attr; 3602 int rc; 3603 3604 rc = is_bnxt_in_error(bp); 3605 if (rc) 3606 return rc; 3607 3608 PMD_DRV_LOG(INFO, "%04x:%02x:%02x:%02x in_eeprom->offset = %d " 3609 "len = %d\n", bp->pdev->addr.domain, 3610 bp->pdev->addr.bus, bp->pdev->addr.devid, 3611 bp->pdev->addr.function, in_eeprom->offset, in_eeprom->length); 3612 3613 if (!BNXT_PF(bp)) { 3614 PMD_DRV_LOG(ERR, "NVM write not supported from a VF\n"); 3615 return -EINVAL; 3616 } 3617 3618 type = in_eeprom->magic >> 16; 3619 3620 if (type == 0xffff) { /* special value for directory operations */ 3621 index = in_eeprom->magic & 0xff; 3622 dir_op = in_eeprom->magic >> 8; 3623 if (index == 0) 3624 return -EINVAL; 3625 switch (dir_op) { 3626 case 0x0e: /* erase */ 3627 if (in_eeprom->offset != ~in_eeprom->magic) 3628 return -EINVAL; 3629 return bnxt_hwrm_erase_nvram_directory(bp, index - 1); 3630 default: 3631 return -EINVAL; 3632 } 3633 } 3634 3635 /* Create or re-write an NVM item: */ 3636 if (bnxt_dir_type_is_executable(type) == true) 3637 return -EOPNOTSUPP; 3638 ext = in_eeprom->magic & 0xffff; 3639 ordinal = in_eeprom->offset >> 16; 3640 attr = in_eeprom->offset & 0xffff; 3641 3642 return bnxt_hwrm_flash_nvram(bp, type, ordinal, ext, attr, 3643 in_eeprom->data, in_eeprom->length); 3644 } 3645 3646 /* 3647 * Initialization 3648 */ 3649 3650 static const struct eth_dev_ops bnxt_dev_ops = { 3651 .dev_infos_get = bnxt_dev_info_get_op, 3652 .dev_close = bnxt_dev_close_op, 3653 .dev_configure = bnxt_dev_configure_op, 3654 .dev_start = bnxt_dev_start_op, 3655 .dev_stop = bnxt_dev_stop_op, 3656 .dev_set_link_up = bnxt_dev_set_link_up_op, 3657 .dev_set_link_down = bnxt_dev_set_link_down_op, 3658 .stats_get = bnxt_stats_get_op, 3659 .stats_reset = bnxt_stats_reset_op, 3660 .rx_queue_setup = bnxt_rx_queue_setup_op, 3661 .rx_queue_release = bnxt_rx_queue_release_op, 3662 .tx_queue_setup = bnxt_tx_queue_setup_op, 3663 .tx_queue_release = bnxt_tx_queue_release_op, 3664 .rx_queue_intr_enable = bnxt_rx_queue_intr_enable_op, 3665 .rx_queue_intr_disable = bnxt_rx_queue_intr_disable_op, 3666 .reta_update = bnxt_reta_update_op, 3667 .reta_query = bnxt_reta_query_op, 3668 .rss_hash_update = bnxt_rss_hash_update_op, 3669 .rss_hash_conf_get = bnxt_rss_hash_conf_get_op, 3670 .link_update = bnxt_link_update_op, 3671 .promiscuous_enable = bnxt_promiscuous_enable_op, 3672 .promiscuous_disable = bnxt_promiscuous_disable_op, 3673 .allmulticast_enable = bnxt_allmulticast_enable_op, 3674 .allmulticast_disable = bnxt_allmulticast_disable_op, 3675 .mac_addr_add = bnxt_mac_addr_add_op, 3676 .mac_addr_remove = bnxt_mac_addr_remove_op, 3677 .flow_ctrl_get = bnxt_flow_ctrl_get_op, 3678 .flow_ctrl_set = bnxt_flow_ctrl_set_op, 3679 .udp_tunnel_port_add = bnxt_udp_tunnel_port_add_op, 3680 .udp_tunnel_port_del = bnxt_udp_tunnel_port_del_op, 3681 .vlan_filter_set = bnxt_vlan_filter_set_op, 3682 .vlan_offload_set = bnxt_vlan_offload_set_op, 3683 .vlan_tpid_set = bnxt_vlan_tpid_set_op, 3684 .vlan_pvid_set = bnxt_vlan_pvid_set_op, 3685 .mtu_set = bnxt_mtu_set_op, 3686 .mac_addr_set = bnxt_set_default_mac_addr_op, 3687 .xstats_get = bnxt_dev_xstats_get_op, 3688 .xstats_get_names = bnxt_dev_xstats_get_names_op, 3689 .xstats_reset = bnxt_dev_xstats_reset_op, 3690 .fw_version_get = bnxt_fw_version_get, 3691 .set_mc_addr_list = bnxt_dev_set_mc_addr_list_op, 3692 .rxq_info_get = bnxt_rxq_info_get_op, 3693 .txq_info_get = bnxt_txq_info_get_op, 3694 .dev_led_on = bnxt_dev_led_on_op, 3695 .dev_led_off = bnxt_dev_led_off_op, 3696 .xstats_get_by_id = bnxt_dev_xstats_get_by_id_op, 3697 .xstats_get_names_by_id = bnxt_dev_xstats_get_names_by_id_op, 3698 .rx_queue_count = bnxt_rx_queue_count_op, 3699 .rx_descriptor_status = bnxt_rx_descriptor_status_op, 3700 .tx_descriptor_status = bnxt_tx_descriptor_status_op, 3701 .rx_queue_start = bnxt_rx_queue_start, 3702 .rx_queue_stop = bnxt_rx_queue_stop, 3703 .tx_queue_start = bnxt_tx_queue_start, 3704 .tx_queue_stop = bnxt_tx_queue_stop, 3705 .filter_ctrl = bnxt_filter_ctrl_op, 3706 .dev_supported_ptypes_get = bnxt_dev_supported_ptypes_get_op, 3707 .get_eeprom_length = bnxt_get_eeprom_length_op, 3708 .get_eeprom = bnxt_get_eeprom_op, 3709 .set_eeprom = bnxt_set_eeprom_op, 3710 .timesync_enable = bnxt_timesync_enable, 3711 .timesync_disable = bnxt_timesync_disable, 3712 .timesync_read_time = bnxt_timesync_read_time, 3713 .timesync_write_time = bnxt_timesync_write_time, 3714 .timesync_adjust_time = bnxt_timesync_adjust_time, 3715 .timesync_read_rx_timestamp = bnxt_timesync_read_rx_timestamp, 3716 .timesync_read_tx_timestamp = bnxt_timesync_read_tx_timestamp, 3717 }; 3718 3719 static uint32_t bnxt_map_reset_regs(struct bnxt *bp, uint32_t reg) 3720 { 3721 uint32_t offset; 3722 3723 /* Only pre-map the reset GRC registers using window 3 */ 3724 rte_write32(reg & 0xfffff000, (uint8_t *)bp->bar0 + 3725 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 8); 3726 3727 offset = BNXT_GRCP_WINDOW_3_BASE + (reg & 0xffc); 3728 3729 return offset; 3730 } 3731 3732 int bnxt_map_fw_health_status_regs(struct bnxt *bp) 3733 { 3734 struct bnxt_error_recovery_info *info = bp->recovery_info; 3735 uint32_t reg_base = 0xffffffff; 3736 int i; 3737 3738 /* Only pre-map the monitoring GRC registers using window 2 */ 3739 for (i = 0; i < BNXT_FW_STATUS_REG_CNT; i++) { 3740 uint32_t reg = info->status_regs[i]; 3741 3742 if (BNXT_FW_STATUS_REG_TYPE(reg) != BNXT_FW_STATUS_REG_TYPE_GRC) 3743 continue; 3744 3745 if (reg_base == 0xffffffff) 3746 reg_base = reg & 0xfffff000; 3747 if ((reg & 0xfffff000) != reg_base) 3748 return -ERANGE; 3749 3750 /* Use mask 0xffc as the Lower 2 bits indicates 3751 * address space location 3752 */ 3753 info->mapped_status_regs[i] = BNXT_GRCP_WINDOW_2_BASE + 3754 (reg & 0xffc); 3755 } 3756 3757 if (reg_base == 0xffffffff) 3758 return 0; 3759 3760 rte_write32(reg_base, (uint8_t *)bp->bar0 + 3761 BNXT_GRCPF_REG_WINDOW_BASE_OUT + 4); 3762 3763 return 0; 3764 } 3765 3766 static void bnxt_write_fw_reset_reg(struct bnxt *bp, uint32_t index) 3767 { 3768 struct bnxt_error_recovery_info *info = bp->recovery_info; 3769 uint32_t delay = info->delay_after_reset[index]; 3770 uint32_t val = info->reset_reg_val[index]; 3771 uint32_t reg = info->reset_reg[index]; 3772 uint32_t type, offset; 3773 3774 type = BNXT_FW_STATUS_REG_TYPE(reg); 3775 offset = BNXT_FW_STATUS_REG_OFF(reg); 3776 3777 switch (type) { 3778 case BNXT_FW_STATUS_REG_TYPE_CFG: 3779 rte_pci_write_config(bp->pdev, &val, sizeof(val), offset); 3780 break; 3781 case BNXT_FW_STATUS_REG_TYPE_GRC: 3782 offset = bnxt_map_reset_regs(bp, offset); 3783 rte_write32(val, (uint8_t *)bp->bar0 + offset); 3784 break; 3785 case BNXT_FW_STATUS_REG_TYPE_BAR0: 3786 rte_write32(val, (uint8_t *)bp->bar0 + offset); 3787 break; 3788 } 3789 /* wait on a specific interval of time until core reset is complete */ 3790 if (delay) 3791 rte_delay_ms(delay); 3792 } 3793 3794 static void bnxt_dev_cleanup(struct bnxt *bp) 3795 { 3796 bnxt_set_hwrm_link_config(bp, false); 3797 bp->link_info.link_up = 0; 3798 if (bp->dev_stopped == 0) 3799 bnxt_dev_stop_op(bp->eth_dev); 3800 3801 bnxt_uninit_resources(bp, true); 3802 } 3803 3804 static int bnxt_restore_filters(struct bnxt *bp) 3805 { 3806 struct rte_eth_dev *dev = bp->eth_dev; 3807 int ret = 0; 3808 3809 if (dev->data->all_multicast) 3810 ret = bnxt_allmulticast_enable_op(dev); 3811 if (dev->data->promiscuous) 3812 ret = bnxt_promiscuous_enable_op(dev); 3813 3814 /* TODO restore other filters as well */ 3815 return ret; 3816 } 3817 3818 static void bnxt_dev_recover(void *arg) 3819 { 3820 struct bnxt *bp = arg; 3821 int timeout = bp->fw_reset_max_msecs; 3822 int rc = 0; 3823 3824 /* Clear Error flag so that device re-init should happen */ 3825 bp->flags &= ~BNXT_FLAG_FATAL_ERROR; 3826 3827 do { 3828 rc = bnxt_hwrm_ver_get(bp); 3829 if (rc == 0) 3830 break; 3831 rte_delay_ms(BNXT_FW_READY_WAIT_INTERVAL); 3832 timeout -= BNXT_FW_READY_WAIT_INTERVAL; 3833 } while (rc && timeout); 3834 3835 if (rc) { 3836 PMD_DRV_LOG(ERR, "FW is not Ready after reset\n"); 3837 goto err; 3838 } 3839 3840 rc = bnxt_init_resources(bp, true); 3841 if (rc) { 3842 PMD_DRV_LOG(ERR, 3843 "Failed to initialize resources after reset\n"); 3844 goto err; 3845 } 3846 /* clear reset flag as the device is initialized now */ 3847 bp->flags &= ~BNXT_FLAG_FW_RESET; 3848 3849 rc = bnxt_dev_start_op(bp->eth_dev); 3850 if (rc) { 3851 PMD_DRV_LOG(ERR, "Failed to start port after reset\n"); 3852 goto err; 3853 } 3854 3855 rc = bnxt_restore_filters(bp); 3856 if (rc) 3857 goto err; 3858 3859 PMD_DRV_LOG(INFO, "Recovered from FW reset\n"); 3860 return; 3861 err: 3862 bp->flags |= BNXT_FLAG_FATAL_ERROR; 3863 bnxt_uninit_resources(bp, false); 3864 PMD_DRV_LOG(ERR, "Failed to recover from FW reset\n"); 3865 } 3866 3867 void bnxt_dev_reset_and_resume(void *arg) 3868 { 3869 struct bnxt *bp = arg; 3870 int rc; 3871 3872 bnxt_dev_cleanup(bp); 3873 3874 bnxt_wait_for_device_shutdown(bp); 3875 3876 rc = rte_eal_alarm_set(US_PER_MS * bp->fw_reset_min_msecs, 3877 bnxt_dev_recover, (void *)bp); 3878 if (rc) 3879 PMD_DRV_LOG(ERR, "Error setting recovery alarm"); 3880 } 3881 3882 uint32_t bnxt_read_fw_status_reg(struct bnxt *bp, uint32_t index) 3883 { 3884 struct bnxt_error_recovery_info *info = bp->recovery_info; 3885 uint32_t reg = info->status_regs[index]; 3886 uint32_t type, offset, val = 0; 3887 3888 type = BNXT_FW_STATUS_REG_TYPE(reg); 3889 offset = BNXT_FW_STATUS_REG_OFF(reg); 3890 3891 switch (type) { 3892 case BNXT_FW_STATUS_REG_TYPE_CFG: 3893 rte_pci_read_config(bp->pdev, &val, sizeof(val), offset); 3894 break; 3895 case BNXT_FW_STATUS_REG_TYPE_GRC: 3896 offset = info->mapped_status_regs[index]; 3897 /* FALLTHROUGH */ 3898 case BNXT_FW_STATUS_REG_TYPE_BAR0: 3899 val = rte_le_to_cpu_32(rte_read32((uint8_t *)bp->bar0 + 3900 offset)); 3901 break; 3902 } 3903 3904 return val; 3905 } 3906 3907 static int bnxt_fw_reset_all(struct bnxt *bp) 3908 { 3909 struct bnxt_error_recovery_info *info = bp->recovery_info; 3910 uint32_t i; 3911 int rc = 0; 3912 3913 if (info->flags & BNXT_FLAG_ERROR_RECOVERY_HOST) { 3914 /* Reset through master function driver */ 3915 for (i = 0; i < info->reg_array_cnt; i++) 3916 bnxt_write_fw_reset_reg(bp, i); 3917 /* Wait for time specified by FW after triggering reset */ 3918 rte_delay_ms(info->master_func_wait_period_after_reset); 3919 } else if (info->flags & BNXT_FLAG_ERROR_RECOVERY_CO_CPU) { 3920 /* Reset with the help of Kong processor */ 3921 rc = bnxt_hwrm_fw_reset(bp); 3922 if (rc) 3923 PMD_DRV_LOG(ERR, "Failed to reset FW\n"); 3924 } 3925 3926 return rc; 3927 } 3928 3929 static void bnxt_fw_reset_cb(void *arg) 3930 { 3931 struct bnxt *bp = arg; 3932 struct bnxt_error_recovery_info *info = bp->recovery_info; 3933 int rc = 0; 3934 3935 /* Only Master function can do FW reset */ 3936 if (bnxt_is_master_func(bp) && 3937 bnxt_is_recovery_enabled(bp)) { 3938 rc = bnxt_fw_reset_all(bp); 3939 if (rc) { 3940 PMD_DRV_LOG(ERR, "Adapter recovery failed\n"); 3941 return; 3942 } 3943 } 3944 3945 /* if recovery method is ERROR_RECOVERY_CO_CPU, KONG will send 3946 * EXCEPTION_FATAL_ASYNC event to all the functions 3947 * (including MASTER FUNC). After receiving this Async, all the active 3948 * drivers should treat this case as FW initiated recovery 3949 */ 3950 if (info->flags & BNXT_FLAG_ERROR_RECOVERY_HOST) { 3951 bp->fw_reset_min_msecs = BNXT_MIN_FW_READY_TIMEOUT; 3952 bp->fw_reset_max_msecs = BNXT_MAX_FW_RESET_TIMEOUT; 3953 3954 /* To recover from error */ 3955 rte_eal_alarm_set(US_PER_MS, bnxt_dev_reset_and_resume, 3956 (void *)bp); 3957 } 3958 } 3959 3960 /* Driver should poll FW heartbeat, reset_counter with the frequency 3961 * advertised by FW in HWRM_ERROR_RECOVERY_QCFG. 3962 * When the driver detects heartbeat stop or change in reset_counter, 3963 * it has to trigger a reset to recover from the error condition. 3964 * A “master PF” is the function who will have the privilege to 3965 * initiate the chimp reset. The master PF will be elected by the 3966 * firmware and will be notified through async message. 3967 */ 3968 static void bnxt_check_fw_health(void *arg) 3969 { 3970 struct bnxt *bp = arg; 3971 struct bnxt_error_recovery_info *info = bp->recovery_info; 3972 uint32_t val = 0, wait_msec; 3973 3974 if (!info || !bnxt_is_recovery_enabled(bp) || 3975 is_bnxt_in_error(bp)) 3976 return; 3977 3978 val = bnxt_read_fw_status_reg(bp, BNXT_FW_HEARTBEAT_CNT_REG); 3979 if (val == info->last_heart_beat) 3980 goto reset; 3981 3982 info->last_heart_beat = val; 3983 3984 val = bnxt_read_fw_status_reg(bp, BNXT_FW_RECOVERY_CNT_REG); 3985 if (val != info->last_reset_counter) 3986 goto reset; 3987 3988 info->last_reset_counter = val; 3989 3990 rte_eal_alarm_set(US_PER_MS * info->driver_polling_freq, 3991 bnxt_check_fw_health, (void *)bp); 3992 3993 return; 3994 reset: 3995 /* Stop DMA to/from device */ 3996 bp->flags |= BNXT_FLAG_FATAL_ERROR; 3997 bp->flags |= BNXT_FLAG_FW_RESET; 3998 3999 PMD_DRV_LOG(ERR, "Detected FW dead condition\n"); 4000 4001 if (bnxt_is_master_func(bp)) 4002 wait_msec = info->master_func_wait_period; 4003 else 4004 wait_msec = info->normal_func_wait_period; 4005 4006 rte_eal_alarm_set(US_PER_MS * wait_msec, 4007 bnxt_fw_reset_cb, (void *)bp); 4008 } 4009 4010 void bnxt_schedule_fw_health_check(struct bnxt *bp) 4011 { 4012 uint32_t polling_freq; 4013 4014 if (!bnxt_is_recovery_enabled(bp)) 4015 return; 4016 4017 if (bp->flags & BNXT_FLAG_FW_HEALTH_CHECK_SCHEDULED) 4018 return; 4019 4020 polling_freq = bp->recovery_info->driver_polling_freq; 4021 4022 rte_eal_alarm_set(US_PER_MS * polling_freq, 4023 bnxt_check_fw_health, (void *)bp); 4024 bp->flags |= BNXT_FLAG_FW_HEALTH_CHECK_SCHEDULED; 4025 } 4026 4027 static void bnxt_cancel_fw_health_check(struct bnxt *bp) 4028 { 4029 if (!bnxt_is_recovery_enabled(bp)) 4030 return; 4031 4032 rte_eal_alarm_cancel(bnxt_check_fw_health, (void *)bp); 4033 bp->flags &= ~BNXT_FLAG_FW_HEALTH_CHECK_SCHEDULED; 4034 } 4035 4036 static bool bnxt_vf_pciid(uint16_t id) 4037 { 4038 if (id == BROADCOM_DEV_ID_57304_VF || 4039 id == BROADCOM_DEV_ID_57406_VF || 4040 id == BROADCOM_DEV_ID_5731X_VF || 4041 id == BROADCOM_DEV_ID_5741X_VF || 4042 id == BROADCOM_DEV_ID_57414_VF || 4043 id == BROADCOM_DEV_ID_STRATUS_NIC_VF1 || 4044 id == BROADCOM_DEV_ID_STRATUS_NIC_VF2 || 4045 id == BROADCOM_DEV_ID_58802_VF || 4046 id == BROADCOM_DEV_ID_57500_VF1 || 4047 id == BROADCOM_DEV_ID_57500_VF2) 4048 return true; 4049 return false; 4050 } 4051 4052 bool bnxt_stratus_device(struct bnxt *bp) 4053 { 4054 uint16_t id = bp->pdev->id.device_id; 4055 4056 if (id == BROADCOM_DEV_ID_STRATUS_NIC || 4057 id == BROADCOM_DEV_ID_STRATUS_NIC_VF1 || 4058 id == BROADCOM_DEV_ID_STRATUS_NIC_VF2) 4059 return true; 4060 return false; 4061 } 4062 4063 static int bnxt_init_board(struct rte_eth_dev *eth_dev) 4064 { 4065 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(eth_dev); 4066 struct bnxt *bp = eth_dev->data->dev_private; 4067 4068 /* enable device (incl. PCI PM wakeup), and bus-mastering */ 4069 bp->bar0 = (void *)pci_dev->mem_resource[0].addr; 4070 bp->doorbell_base = (void *)pci_dev->mem_resource[2].addr; 4071 if (!bp->bar0 || !bp->doorbell_base) { 4072 PMD_DRV_LOG(ERR, "Unable to access Hardware\n"); 4073 return -ENODEV; 4074 } 4075 4076 bp->eth_dev = eth_dev; 4077 bp->pdev = pci_dev; 4078 4079 return 0; 4080 } 4081 4082 static int bnxt_alloc_ctx_mem_blk(__rte_unused struct bnxt *bp, 4083 struct bnxt_ctx_pg_info *ctx_pg, 4084 uint32_t mem_size, 4085 const char *suffix, 4086 uint16_t idx) 4087 { 4088 struct bnxt_ring_mem_info *rmem = &ctx_pg->ring_mem; 4089 const struct rte_memzone *mz = NULL; 4090 char mz_name[RTE_MEMZONE_NAMESIZE]; 4091 rte_iova_t mz_phys_addr; 4092 uint64_t valid_bits = 0; 4093 uint32_t sz; 4094 int i; 4095 4096 if (!mem_size) 4097 return 0; 4098 4099 rmem->nr_pages = RTE_ALIGN_MUL_CEIL(mem_size, BNXT_PAGE_SIZE) / 4100 BNXT_PAGE_SIZE; 4101 rmem->page_size = BNXT_PAGE_SIZE; 4102 rmem->pg_arr = ctx_pg->ctx_pg_arr; 4103 rmem->dma_arr = ctx_pg->ctx_dma_arr; 4104 rmem->flags = BNXT_RMEM_VALID_PTE_FLAG; 4105 4106 valid_bits = PTU_PTE_VALID; 4107 4108 if (rmem->nr_pages > 1) { 4109 snprintf(mz_name, RTE_MEMZONE_NAMESIZE, 4110 "bnxt_ctx_pg_tbl%s_%x_%d", 4111 suffix, idx, bp->eth_dev->data->port_id); 4112 mz_name[RTE_MEMZONE_NAMESIZE - 1] = 0; 4113 mz = rte_memzone_lookup(mz_name); 4114 if (!mz) { 4115 mz = rte_memzone_reserve_aligned(mz_name, 4116 rmem->nr_pages * 8, 4117 SOCKET_ID_ANY, 4118 RTE_MEMZONE_2MB | 4119 RTE_MEMZONE_SIZE_HINT_ONLY | 4120 RTE_MEMZONE_IOVA_CONTIG, 4121 BNXT_PAGE_SIZE); 4122 if (mz == NULL) 4123 return -ENOMEM; 4124 } 4125 4126 memset(mz->addr, 0, mz->len); 4127 mz_phys_addr = mz->iova; 4128 if ((unsigned long)mz->addr == mz_phys_addr) { 4129 PMD_DRV_LOG(DEBUG, 4130 "physical address same as virtual\n"); 4131 PMD_DRV_LOG(DEBUG, "Using rte_mem_virt2iova()\n"); 4132 mz_phys_addr = rte_mem_virt2iova(mz->addr); 4133 if (mz_phys_addr == RTE_BAD_IOVA) { 4134 PMD_DRV_LOG(ERR, 4135 "unable to map addr to phys memory\n"); 4136 return -ENOMEM; 4137 } 4138 } 4139 rte_mem_lock_page(((char *)mz->addr)); 4140 4141 rmem->pg_tbl = mz->addr; 4142 rmem->pg_tbl_map = mz_phys_addr; 4143 rmem->pg_tbl_mz = mz; 4144 } 4145 4146 snprintf(mz_name, RTE_MEMZONE_NAMESIZE, "bnxt_ctx_%s_%x_%d", 4147 suffix, idx, bp->eth_dev->data->port_id); 4148 mz = rte_memzone_lookup(mz_name); 4149 if (!mz) { 4150 mz = rte_memzone_reserve_aligned(mz_name, 4151 mem_size, 4152 SOCKET_ID_ANY, 4153 RTE_MEMZONE_1GB | 4154 RTE_MEMZONE_SIZE_HINT_ONLY | 4155 RTE_MEMZONE_IOVA_CONTIG, 4156 BNXT_PAGE_SIZE); 4157 if (mz == NULL) 4158 return -ENOMEM; 4159 } 4160 4161 memset(mz->addr, 0, mz->len); 4162 mz_phys_addr = mz->iova; 4163 if ((unsigned long)mz->addr == mz_phys_addr) { 4164 PMD_DRV_LOG(DEBUG, 4165 "Memzone physical address same as virtual.\n"); 4166 PMD_DRV_LOG(DEBUG, "Using rte_mem_virt2iova()\n"); 4167 for (sz = 0; sz < mem_size; sz += BNXT_PAGE_SIZE) 4168 rte_mem_lock_page(((char *)mz->addr) + sz); 4169 mz_phys_addr = rte_mem_virt2iova(mz->addr); 4170 if (mz_phys_addr == RTE_BAD_IOVA) { 4171 PMD_DRV_LOG(ERR, 4172 "unable to map addr to phys memory\n"); 4173 return -ENOMEM; 4174 } 4175 } 4176 4177 for (sz = 0, i = 0; sz < mem_size; sz += BNXT_PAGE_SIZE, i++) { 4178 rte_mem_lock_page(((char *)mz->addr) + sz); 4179 rmem->pg_arr[i] = ((char *)mz->addr) + sz; 4180 rmem->dma_arr[i] = mz_phys_addr + sz; 4181 4182 if (rmem->nr_pages > 1) { 4183 if (i == rmem->nr_pages - 2 && 4184 (rmem->flags & BNXT_RMEM_RING_PTE_FLAG)) 4185 valid_bits |= PTU_PTE_NEXT_TO_LAST; 4186 else if (i == rmem->nr_pages - 1 && 4187 (rmem->flags & BNXT_RMEM_RING_PTE_FLAG)) 4188 valid_bits |= PTU_PTE_LAST; 4189 4190 rmem->pg_tbl[i] = rte_cpu_to_le_64(rmem->dma_arr[i] | 4191 valid_bits); 4192 } 4193 } 4194 4195 rmem->mz = mz; 4196 if (rmem->vmem_size) 4197 rmem->vmem = (void **)mz->addr; 4198 rmem->dma_arr[0] = mz_phys_addr; 4199 return 0; 4200 } 4201 4202 static void bnxt_free_ctx_mem(struct bnxt *bp) 4203 { 4204 int i; 4205 4206 if (!bp->ctx || !(bp->ctx->flags & BNXT_CTX_FLAG_INITED)) 4207 return; 4208 4209 bp->ctx->flags &= ~BNXT_CTX_FLAG_INITED; 4210 rte_memzone_free(bp->ctx->qp_mem.ring_mem.mz); 4211 rte_memzone_free(bp->ctx->srq_mem.ring_mem.mz); 4212 rte_memzone_free(bp->ctx->cq_mem.ring_mem.mz); 4213 rte_memzone_free(bp->ctx->vnic_mem.ring_mem.mz); 4214 rte_memzone_free(bp->ctx->stat_mem.ring_mem.mz); 4215 rte_memzone_free(bp->ctx->qp_mem.ring_mem.pg_tbl_mz); 4216 rte_memzone_free(bp->ctx->srq_mem.ring_mem.pg_tbl_mz); 4217 rte_memzone_free(bp->ctx->cq_mem.ring_mem.pg_tbl_mz); 4218 rte_memzone_free(bp->ctx->vnic_mem.ring_mem.pg_tbl_mz); 4219 rte_memzone_free(bp->ctx->stat_mem.ring_mem.pg_tbl_mz); 4220 4221 for (i = 0; i < BNXT_MAX_Q; i++) { 4222 if (bp->ctx->tqm_mem[i]) 4223 rte_memzone_free(bp->ctx->tqm_mem[i]->ring_mem.mz); 4224 } 4225 4226 rte_free(bp->ctx); 4227 bp->ctx = NULL; 4228 } 4229 4230 #define bnxt_roundup(x, y) ((((x) + ((y) - 1)) / (y)) * (y)) 4231 4232 #define min_t(type, x, y) ({ \ 4233 type __min1 = (x); \ 4234 type __min2 = (y); \ 4235 __min1 < __min2 ? __min1 : __min2; }) 4236 4237 #define max_t(type, x, y) ({ \ 4238 type __max1 = (x); \ 4239 type __max2 = (y); \ 4240 __max1 > __max2 ? __max1 : __max2; }) 4241 4242 #define clamp_t(type, _x, min, max) min_t(type, max_t(type, _x, min), max) 4243 4244 int bnxt_alloc_ctx_mem(struct bnxt *bp) 4245 { 4246 struct bnxt_ctx_pg_info *ctx_pg; 4247 struct bnxt_ctx_mem_info *ctx; 4248 uint32_t mem_size, ena, entries; 4249 int i, rc; 4250 4251 rc = bnxt_hwrm_func_backing_store_qcaps(bp); 4252 if (rc) { 4253 PMD_DRV_LOG(ERR, "Query context mem capability failed\n"); 4254 return rc; 4255 } 4256 ctx = bp->ctx; 4257 if (!ctx || (ctx->flags & BNXT_CTX_FLAG_INITED)) 4258 return 0; 4259 4260 ctx_pg = &ctx->qp_mem; 4261 ctx_pg->entries = ctx->qp_min_qp1_entries + ctx->qp_max_l2_entries; 4262 mem_size = ctx->qp_entry_size * ctx_pg->entries; 4263 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "qp_mem", 0); 4264 if (rc) 4265 return rc; 4266 4267 ctx_pg = &ctx->srq_mem; 4268 ctx_pg->entries = ctx->srq_max_l2_entries; 4269 mem_size = ctx->srq_entry_size * ctx_pg->entries; 4270 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "srq_mem", 0); 4271 if (rc) 4272 return rc; 4273 4274 ctx_pg = &ctx->cq_mem; 4275 ctx_pg->entries = ctx->cq_max_l2_entries; 4276 mem_size = ctx->cq_entry_size * ctx_pg->entries; 4277 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "cq_mem", 0); 4278 if (rc) 4279 return rc; 4280 4281 ctx_pg = &ctx->vnic_mem; 4282 ctx_pg->entries = ctx->vnic_max_vnic_entries + 4283 ctx->vnic_max_ring_table_entries; 4284 mem_size = ctx->vnic_entry_size * ctx_pg->entries; 4285 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "vnic_mem", 0); 4286 if (rc) 4287 return rc; 4288 4289 ctx_pg = &ctx->stat_mem; 4290 ctx_pg->entries = ctx->stat_max_entries; 4291 mem_size = ctx->stat_entry_size * ctx_pg->entries; 4292 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "stat_mem", 0); 4293 if (rc) 4294 return rc; 4295 4296 entries = ctx->qp_max_l2_entries + 4297 ctx->vnic_max_vnic_entries + 4298 ctx->tqm_min_entries_per_ring; 4299 entries = bnxt_roundup(entries, ctx->tqm_entries_multiple); 4300 entries = clamp_t(uint32_t, entries, ctx->tqm_min_entries_per_ring, 4301 ctx->tqm_max_entries_per_ring); 4302 for (i = 0, ena = 0; i < BNXT_MAX_Q; i++) { 4303 ctx_pg = ctx->tqm_mem[i]; 4304 /* use min tqm entries for now. */ 4305 ctx_pg->entries = entries; 4306 mem_size = ctx->tqm_entry_size * ctx_pg->entries; 4307 rc = bnxt_alloc_ctx_mem_blk(bp, ctx_pg, mem_size, "tqm_mem", i); 4308 if (rc) 4309 return rc; 4310 ena |= HWRM_FUNC_BACKING_STORE_CFG_INPUT_ENABLES_TQM_SP << i; 4311 } 4312 4313 ena |= FUNC_BACKING_STORE_CFG_INPUT_DFLT_ENABLES; 4314 rc = bnxt_hwrm_func_backing_store_cfg(bp, ena); 4315 if (rc) 4316 PMD_DRV_LOG(ERR, 4317 "Failed to configure context mem: rc = %d\n", rc); 4318 else 4319 ctx->flags |= BNXT_CTX_FLAG_INITED; 4320 4321 return rc; 4322 } 4323 4324 static int bnxt_alloc_stats_mem(struct bnxt *bp) 4325 { 4326 struct rte_pci_device *pci_dev = bp->pdev; 4327 char mz_name[RTE_MEMZONE_NAMESIZE]; 4328 const struct rte_memzone *mz = NULL; 4329 uint32_t total_alloc_len; 4330 rte_iova_t mz_phys_addr; 4331 4332 if (pci_dev->id.device_id == BROADCOM_DEV_ID_NS2) 4333 return 0; 4334 4335 snprintf(mz_name, RTE_MEMZONE_NAMESIZE, 4336 "bnxt_" PCI_PRI_FMT "-%s", pci_dev->addr.domain, 4337 pci_dev->addr.bus, pci_dev->addr.devid, 4338 pci_dev->addr.function, "rx_port_stats"); 4339 mz_name[RTE_MEMZONE_NAMESIZE - 1] = 0; 4340 mz = rte_memzone_lookup(mz_name); 4341 total_alloc_len = 4342 RTE_CACHE_LINE_ROUNDUP(sizeof(struct rx_port_stats) + 4343 sizeof(struct rx_port_stats_ext) + 512); 4344 if (!mz) { 4345 mz = rte_memzone_reserve(mz_name, total_alloc_len, 4346 SOCKET_ID_ANY, 4347 RTE_MEMZONE_2MB | 4348 RTE_MEMZONE_SIZE_HINT_ONLY | 4349 RTE_MEMZONE_IOVA_CONTIG); 4350 if (mz == NULL) 4351 return -ENOMEM; 4352 } 4353 memset(mz->addr, 0, mz->len); 4354 mz_phys_addr = mz->iova; 4355 if ((unsigned long)mz->addr == mz_phys_addr) { 4356 PMD_DRV_LOG(DEBUG, 4357 "Memzone physical address same as virtual.\n"); 4358 PMD_DRV_LOG(DEBUG, 4359 "Using rte_mem_virt2iova()\n"); 4360 mz_phys_addr = rte_mem_virt2iova(mz->addr); 4361 if (mz_phys_addr == RTE_BAD_IOVA) { 4362 PMD_DRV_LOG(ERR, 4363 "Can't map address to physical memory\n"); 4364 return -ENOMEM; 4365 } 4366 } 4367 4368 bp->rx_mem_zone = (const void *)mz; 4369 bp->hw_rx_port_stats = mz->addr; 4370 bp->hw_rx_port_stats_map = mz_phys_addr; 4371 4372 snprintf(mz_name, RTE_MEMZONE_NAMESIZE, 4373 "bnxt_" PCI_PRI_FMT "-%s", pci_dev->addr.domain, 4374 pci_dev->addr.bus, pci_dev->addr.devid, 4375 pci_dev->addr.function, "tx_port_stats"); 4376 mz_name[RTE_MEMZONE_NAMESIZE - 1] = 0; 4377 mz = rte_memzone_lookup(mz_name); 4378 total_alloc_len = 4379 RTE_CACHE_LINE_ROUNDUP(sizeof(struct tx_port_stats) + 4380 sizeof(struct tx_port_stats_ext) + 512); 4381 if (!mz) { 4382 mz = rte_memzone_reserve(mz_name, 4383 total_alloc_len, 4384 SOCKET_ID_ANY, 4385 RTE_MEMZONE_2MB | 4386 RTE_MEMZONE_SIZE_HINT_ONLY | 4387 RTE_MEMZONE_IOVA_CONTIG); 4388 if (mz == NULL) 4389 return -ENOMEM; 4390 } 4391 memset(mz->addr, 0, mz->len); 4392 mz_phys_addr = mz->iova; 4393 if ((unsigned long)mz->addr == mz_phys_addr) { 4394 PMD_DRV_LOG(DEBUG, 4395 "Memzone physical address same as virtual\n"); 4396 PMD_DRV_LOG(DEBUG, "Using rte_mem_virt2iova()\n"); 4397 mz_phys_addr = rte_mem_virt2iova(mz->addr); 4398 if (mz_phys_addr == RTE_BAD_IOVA) { 4399 PMD_DRV_LOG(ERR, 4400 "Can't map address to physical memory\n"); 4401 return -ENOMEM; 4402 } 4403 } 4404 4405 bp->tx_mem_zone = (const void *)mz; 4406 bp->hw_tx_port_stats = mz->addr; 4407 bp->hw_tx_port_stats_map = mz_phys_addr; 4408 bp->flags |= BNXT_FLAG_PORT_STATS; 4409 4410 /* Display extended statistics if FW supports it */ 4411 if (bp->hwrm_spec_code < HWRM_SPEC_CODE_1_8_4 || 4412 bp->hwrm_spec_code == HWRM_SPEC_CODE_1_9_0 || 4413 !(bp->flags & BNXT_FLAG_EXT_STATS_SUPPORTED)) 4414 return 0; 4415 4416 bp->hw_rx_port_stats_ext = (void *) 4417 ((uint8_t *)bp->hw_rx_port_stats + 4418 sizeof(struct rx_port_stats)); 4419 bp->hw_rx_port_stats_ext_map = bp->hw_rx_port_stats_map + 4420 sizeof(struct rx_port_stats); 4421 bp->flags |= BNXT_FLAG_EXT_RX_PORT_STATS; 4422 4423 if (bp->hwrm_spec_code < HWRM_SPEC_CODE_1_9_2 || 4424 bp->flags & BNXT_FLAG_EXT_STATS_SUPPORTED) { 4425 bp->hw_tx_port_stats_ext = (void *) 4426 ((uint8_t *)bp->hw_tx_port_stats + 4427 sizeof(struct tx_port_stats)); 4428 bp->hw_tx_port_stats_ext_map = 4429 bp->hw_tx_port_stats_map + 4430 sizeof(struct tx_port_stats); 4431 bp->flags |= BNXT_FLAG_EXT_TX_PORT_STATS; 4432 } 4433 4434 return 0; 4435 } 4436 4437 static int bnxt_setup_mac_addr(struct rte_eth_dev *eth_dev) 4438 { 4439 struct bnxt *bp = eth_dev->data->dev_private; 4440 int rc = 0; 4441 4442 eth_dev->data->mac_addrs = rte_zmalloc("bnxt_mac_addr_tbl", 4443 RTE_ETHER_ADDR_LEN * 4444 bp->max_l2_ctx, 4445 0); 4446 if (eth_dev->data->mac_addrs == NULL) { 4447 PMD_DRV_LOG(ERR, "Failed to alloc MAC addr tbl\n"); 4448 return -ENOMEM; 4449 } 4450 4451 if (bnxt_check_zero_bytes(bp->dflt_mac_addr, RTE_ETHER_ADDR_LEN)) { 4452 if (BNXT_PF(bp)) 4453 return -EINVAL; 4454 4455 /* Generate a random MAC address, if none was assigned by PF */ 4456 PMD_DRV_LOG(INFO, "VF MAC address not assigned by Host PF\n"); 4457 bnxt_eth_hw_addr_random(bp->mac_addr); 4458 PMD_DRV_LOG(INFO, 4459 "Assign random MAC:%02X:%02X:%02X:%02X:%02X:%02X\n", 4460 bp->mac_addr[0], bp->mac_addr[1], bp->mac_addr[2], 4461 bp->mac_addr[3], bp->mac_addr[4], bp->mac_addr[5]); 4462 4463 rc = bnxt_hwrm_set_mac(bp); 4464 if (!rc) 4465 memcpy(&bp->eth_dev->data->mac_addrs[0], bp->mac_addr, 4466 RTE_ETHER_ADDR_LEN); 4467 return rc; 4468 } 4469 4470 /* Copy the permanent MAC from the FUNC_QCAPS response */ 4471 memcpy(bp->mac_addr, bp->dflt_mac_addr, RTE_ETHER_ADDR_LEN); 4472 memcpy(ð_dev->data->mac_addrs[0], bp->mac_addr, RTE_ETHER_ADDR_LEN); 4473 4474 return rc; 4475 } 4476 4477 static int bnxt_restore_dflt_mac(struct bnxt *bp) 4478 { 4479 int rc = 0; 4480 4481 /* MAC is already configured in FW */ 4482 if (!bnxt_check_zero_bytes(bp->dflt_mac_addr, RTE_ETHER_ADDR_LEN)) 4483 return 0; 4484 4485 /* Restore the old MAC configured */ 4486 rc = bnxt_hwrm_set_mac(bp); 4487 if (rc) 4488 PMD_DRV_LOG(ERR, "Failed to restore MAC address\n"); 4489 4490 return rc; 4491 } 4492 4493 static void bnxt_config_vf_req_fwd(struct bnxt *bp) 4494 { 4495 if (!BNXT_PF(bp)) 4496 return; 4497 4498 #define ALLOW_FUNC(x) \ 4499 { \ 4500 uint32_t arg = (x); \ 4501 bp->pf.vf_req_fwd[((arg) >> 5)] &= \ 4502 ~rte_cpu_to_le_32(1 << ((arg) & 0x1f)); \ 4503 } 4504 4505 /* Forward all requests if firmware is new enough */ 4506 if (((bp->fw_ver >= ((20 << 24) | (6 << 16) | (100 << 8))) && 4507 (bp->fw_ver < ((20 << 24) | (7 << 16)))) || 4508 ((bp->fw_ver >= ((20 << 24) | (8 << 16))))) { 4509 memset(bp->pf.vf_req_fwd, 0xff, sizeof(bp->pf.vf_req_fwd)); 4510 } else { 4511 PMD_DRV_LOG(WARNING, 4512 "Firmware too old for VF mailbox functionality\n"); 4513 memset(bp->pf.vf_req_fwd, 0, sizeof(bp->pf.vf_req_fwd)); 4514 } 4515 4516 /* 4517 * The following are used for driver cleanup. If we disallow these, 4518 * VF drivers can't clean up cleanly. 4519 */ 4520 ALLOW_FUNC(HWRM_FUNC_DRV_UNRGTR); 4521 ALLOW_FUNC(HWRM_VNIC_FREE); 4522 ALLOW_FUNC(HWRM_RING_FREE); 4523 ALLOW_FUNC(HWRM_RING_GRP_FREE); 4524 ALLOW_FUNC(HWRM_VNIC_RSS_COS_LB_CTX_FREE); 4525 ALLOW_FUNC(HWRM_CFA_L2_FILTER_FREE); 4526 ALLOW_FUNC(HWRM_STAT_CTX_FREE); 4527 ALLOW_FUNC(HWRM_PORT_PHY_QCFG); 4528 ALLOW_FUNC(HWRM_VNIC_TPA_CFG); 4529 } 4530 4531 static int bnxt_init_fw(struct bnxt *bp) 4532 { 4533 uint16_t mtu; 4534 int rc = 0; 4535 4536 rc = bnxt_hwrm_ver_get(bp); 4537 if (rc) 4538 return rc; 4539 4540 rc = bnxt_hwrm_func_reset(bp); 4541 if (rc) 4542 return -EIO; 4543 4544 rc = bnxt_hwrm_vnic_qcaps(bp); 4545 if (rc) 4546 return rc; 4547 4548 rc = bnxt_hwrm_queue_qportcfg(bp); 4549 if (rc) 4550 return rc; 4551 4552 /* Get the MAX capabilities for this function. 4553 * This function also allocates context memory for TQM rings and 4554 * informs the firmware about this allocated backing store memory. 4555 */ 4556 rc = bnxt_hwrm_func_qcaps(bp); 4557 if (rc) 4558 return rc; 4559 4560 rc = bnxt_hwrm_func_qcfg(bp, &mtu); 4561 if (rc) 4562 return rc; 4563 4564 rc = bnxt_hwrm_cfa_adv_flow_mgmt_qcaps(bp); 4565 if (rc) 4566 return rc; 4567 4568 /* Get the adapter error recovery support info */ 4569 rc = bnxt_hwrm_error_recovery_qcfg(bp); 4570 if (rc) 4571 bp->flags &= ~BNXT_FLAG_FW_CAP_ERROR_RECOVERY; 4572 4573 if (mtu >= RTE_ETHER_MIN_MTU && mtu <= BNXT_MAX_MTU && 4574 mtu != bp->eth_dev->data->mtu) 4575 bp->eth_dev->data->mtu = mtu; 4576 4577 bnxt_hwrm_port_led_qcaps(bp); 4578 4579 return 0; 4580 } 4581 4582 static int 4583 bnxt_init_locks(struct bnxt *bp) 4584 { 4585 int err; 4586 4587 err = pthread_mutex_init(&bp->flow_lock, NULL); 4588 if (err) 4589 PMD_DRV_LOG(ERR, "Unable to initialize flow_lock\n"); 4590 return err; 4591 } 4592 4593 static int bnxt_init_resources(struct bnxt *bp, bool reconfig_dev) 4594 { 4595 int rc; 4596 4597 rc = bnxt_init_fw(bp); 4598 if (rc) 4599 return rc; 4600 4601 if (!reconfig_dev) { 4602 rc = bnxt_setup_mac_addr(bp->eth_dev); 4603 if (rc) 4604 return rc; 4605 } else { 4606 rc = bnxt_restore_dflt_mac(bp); 4607 if (rc) 4608 return rc; 4609 } 4610 4611 bnxt_config_vf_req_fwd(bp); 4612 4613 rc = bnxt_hwrm_func_driver_register(bp); 4614 if (rc) { 4615 PMD_DRV_LOG(ERR, "Failed to register driver"); 4616 return -EBUSY; 4617 } 4618 4619 if (BNXT_PF(bp)) { 4620 if (bp->pdev->max_vfs) { 4621 rc = bnxt_hwrm_allocate_vfs(bp, bp->pdev->max_vfs); 4622 if (rc) { 4623 PMD_DRV_LOG(ERR, "Failed to allocate VFs\n"); 4624 return rc; 4625 } 4626 } else { 4627 rc = bnxt_hwrm_allocate_pf_only(bp); 4628 if (rc) { 4629 PMD_DRV_LOG(ERR, 4630 "Failed to allocate PF resources"); 4631 return rc; 4632 } 4633 } 4634 } 4635 4636 rc = bnxt_alloc_mem(bp, reconfig_dev); 4637 if (rc) 4638 return rc; 4639 4640 rc = bnxt_setup_int(bp); 4641 if (rc) 4642 return rc; 4643 4644 bnxt_init_nic(bp); 4645 4646 rc = bnxt_request_int(bp); 4647 if (rc) 4648 return rc; 4649 4650 rc = bnxt_init_locks(bp); 4651 if (rc) 4652 return rc; 4653 4654 return 0; 4655 } 4656 4657 static int 4658 bnxt_dev_init(struct rte_eth_dev *eth_dev) 4659 { 4660 struct rte_pci_device *pci_dev = RTE_ETH_DEV_TO_PCI(eth_dev); 4661 static int version_printed; 4662 struct bnxt *bp; 4663 int rc; 4664 4665 if (version_printed++ == 0) 4666 PMD_DRV_LOG(INFO, "%s\n", bnxt_version); 4667 4668 eth_dev->dev_ops = &bnxt_dev_ops; 4669 eth_dev->rx_pkt_burst = &bnxt_recv_pkts; 4670 eth_dev->tx_pkt_burst = &bnxt_xmit_pkts; 4671 4672 /* 4673 * For secondary processes, we don't initialise any further 4674 * as primary has already done this work. 4675 */ 4676 if (rte_eal_process_type() != RTE_PROC_PRIMARY) 4677 return 0; 4678 4679 rte_eth_copy_pci_info(eth_dev, pci_dev); 4680 4681 bp = eth_dev->data->dev_private; 4682 4683 bp->dev_stopped = 1; 4684 4685 if (bnxt_vf_pciid(pci_dev->id.device_id)) 4686 bp->flags |= BNXT_FLAG_VF; 4687 4688 if (pci_dev->id.device_id == BROADCOM_DEV_ID_57508 || 4689 pci_dev->id.device_id == BROADCOM_DEV_ID_57504 || 4690 pci_dev->id.device_id == BROADCOM_DEV_ID_57502 || 4691 pci_dev->id.device_id == BROADCOM_DEV_ID_57500_VF1 || 4692 pci_dev->id.device_id == BROADCOM_DEV_ID_57500_VF2) 4693 bp->flags |= BNXT_FLAG_THOR_CHIP; 4694 4695 if (pci_dev->id.device_id == BROADCOM_DEV_ID_58802 || 4696 pci_dev->id.device_id == BROADCOM_DEV_ID_58804 || 4697 pci_dev->id.device_id == BROADCOM_DEV_ID_58808 || 4698 pci_dev->id.device_id == BROADCOM_DEV_ID_58802_VF) 4699 bp->flags |= BNXT_FLAG_STINGRAY; 4700 4701 rc = bnxt_init_board(eth_dev); 4702 if (rc) { 4703 PMD_DRV_LOG(ERR, 4704 "Failed to initialize board rc: %x\n", rc); 4705 return rc; 4706 } 4707 4708 rc = bnxt_alloc_hwrm_resources(bp); 4709 if (rc) { 4710 PMD_DRV_LOG(ERR, 4711 "Failed to allocate hwrm resource rc: %x\n", rc); 4712 goto error_free; 4713 } 4714 rc = bnxt_init_resources(bp, false); 4715 if (rc) 4716 goto error_free; 4717 4718 rc = bnxt_alloc_stats_mem(bp); 4719 if (rc) 4720 goto error_free; 4721 4722 PMD_DRV_LOG(INFO, 4723 DRV_MODULE_NAME "found at mem %" PRIX64 ", node addr %pM\n", 4724 pci_dev->mem_resource[0].phys_addr, 4725 pci_dev->mem_resource[0].addr); 4726 4727 return 0; 4728 4729 error_free: 4730 bnxt_dev_uninit(eth_dev); 4731 return rc; 4732 } 4733 4734 static void 4735 bnxt_uninit_locks(struct bnxt *bp) 4736 { 4737 pthread_mutex_destroy(&bp->flow_lock); 4738 } 4739 4740 static int 4741 bnxt_uninit_resources(struct bnxt *bp, bool reconfig_dev) 4742 { 4743 int rc; 4744 4745 bnxt_free_int(bp); 4746 bnxt_free_mem(bp, reconfig_dev); 4747 bnxt_hwrm_func_buf_unrgtr(bp); 4748 rc = bnxt_hwrm_func_driver_unregister(bp, 0); 4749 bp->flags &= ~BNXT_FLAG_REGISTERED; 4750 bnxt_free_ctx_mem(bp); 4751 if (!reconfig_dev) { 4752 bnxt_free_hwrm_resources(bp); 4753 4754 if (bp->recovery_info != NULL) { 4755 rte_free(bp->recovery_info); 4756 bp->recovery_info = NULL; 4757 } 4758 } 4759 4760 rte_free(bp->ptp_cfg); 4761 bp->ptp_cfg = NULL; 4762 return rc; 4763 } 4764 4765 static int 4766 bnxt_dev_uninit(struct rte_eth_dev *eth_dev) 4767 { 4768 struct bnxt *bp = eth_dev->data->dev_private; 4769 int rc; 4770 4771 if (rte_eal_process_type() != RTE_PROC_PRIMARY) 4772 return -EPERM; 4773 4774 PMD_DRV_LOG(DEBUG, "Calling Device uninit\n"); 4775 4776 rc = bnxt_uninit_resources(bp, false); 4777 4778 if (bp->grp_info != NULL) { 4779 rte_free(bp->grp_info); 4780 bp->grp_info = NULL; 4781 } 4782 4783 if (bp->tx_mem_zone) { 4784 rte_memzone_free((const struct rte_memzone *)bp->tx_mem_zone); 4785 bp->tx_mem_zone = NULL; 4786 } 4787 4788 if (bp->rx_mem_zone) { 4789 rte_memzone_free((const struct rte_memzone *)bp->rx_mem_zone); 4790 bp->rx_mem_zone = NULL; 4791 } 4792 4793 if (bp->dev_stopped == 0) 4794 bnxt_dev_close_op(eth_dev); 4795 if (bp->pf.vf_info) 4796 rte_free(bp->pf.vf_info); 4797 eth_dev->dev_ops = NULL; 4798 eth_dev->rx_pkt_burst = NULL; 4799 eth_dev->tx_pkt_burst = NULL; 4800 4801 bnxt_uninit_locks(bp); 4802 4803 return rc; 4804 } 4805 4806 static int bnxt_pci_probe(struct rte_pci_driver *pci_drv __rte_unused, 4807 struct rte_pci_device *pci_dev) 4808 { 4809 return rte_eth_dev_pci_generic_probe(pci_dev, sizeof(struct bnxt), 4810 bnxt_dev_init); 4811 } 4812 4813 static int bnxt_pci_remove(struct rte_pci_device *pci_dev) 4814 { 4815 if (rte_eal_process_type() == RTE_PROC_PRIMARY) 4816 return rte_eth_dev_pci_generic_remove(pci_dev, 4817 bnxt_dev_uninit); 4818 else 4819 return rte_eth_dev_pci_generic_remove(pci_dev, NULL); 4820 } 4821 4822 static struct rte_pci_driver bnxt_rte_pmd = { 4823 .id_table = bnxt_pci_id_map, 4824 .drv_flags = RTE_PCI_DRV_NEED_MAPPING | RTE_PCI_DRV_INTR_LSC, 4825 .probe = bnxt_pci_probe, 4826 .remove = bnxt_pci_remove, 4827 }; 4828 4829 static bool 4830 is_device_supported(struct rte_eth_dev *dev, struct rte_pci_driver *drv) 4831 { 4832 if (strcmp(dev->device->driver->name, drv->driver.name)) 4833 return false; 4834 4835 return true; 4836 } 4837 4838 bool is_bnxt_supported(struct rte_eth_dev *dev) 4839 { 4840 return is_device_supported(dev, &bnxt_rte_pmd); 4841 } 4842 4843 RTE_INIT(bnxt_init_log) 4844 { 4845 bnxt_logtype_driver = rte_log_register("pmd.net.bnxt.driver"); 4846 if (bnxt_logtype_driver >= 0) 4847 rte_log_set_level(bnxt_logtype_driver, RTE_LOG_NOTICE); 4848 } 4849 4850 RTE_PMD_REGISTER_PCI(net_bnxt, bnxt_rte_pmd); 4851 RTE_PMD_REGISTER_PCI_TABLE(net_bnxt, bnxt_pci_id_map); 4852 RTE_PMD_REGISTER_KMOD_DEP(net_bnxt, "* igb_uio | uio_pci_generic | vfio-pci"); 4853