Commit 4d94e435 authored by David S. Miller's avatar David S. Miller

Merge branch 'bnxt_en-next'

Michael Chan says:

====================
bnxt_en: Updates for net-next.

This patch-set includes link up and link initialization improvements,
RSS and aRFS improvements, devlink refactoring and registration
improvements, devlink info support including documentation.

v2: Removed the TC ingress rate limiting patch. The developer Harsha needs
to rework some code.
    Use fw.psid suggested by Jakub Kicinski.
====================
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parents db038b1b 92439915
......@@ -39,3 +39,36 @@ parameters.
- Generic Routing Encapsulation (GRE) version check will be enabled in
the device. If disabled, the device will skip the version check for
incoming packets.
Info versions
=============
The ``bnxt_en`` driver reports the following versions
.. list-table:: devlink info versions implemented
:widths: 5 5 90
* - Name
- Type
- Description
* - ``asic.id``
- fixed
- ASIC design identifier
* - ``asic.rev``
- fixed
- ASIC design revision
* - ``fw.psid``
- stored, running
- Firmware parameter set version of the board
* - ``fw``
- stored, running
- Overall board firmware version
* - ``fw.app``
- stored, running
- Data path firmware version
* - ``fw.mgmt``
- stored, running
- Management firmware version
* - ``fw.roce``
- stored, running
- RoCE management firmware version
......@@ -92,3 +92,9 @@ fw.psid
-------
Unique identifier of the firmware parameter set.
fw.roce
-------
RoCE firmware version which is responsible for handling roce
management.
......@@ -6998,7 +6998,6 @@ static int __bnxt_hwrm_func_qcaps(struct bnxt *bp)
pf->fw_fid = le16_to_cpu(resp->fid);
pf->port_id = le16_to_cpu(resp->port_id);
bp->dev->dev_port = pf->port_id;
memcpy(pf->mac_addr, resp->mac_address, ETH_ALEN);
pf->first_vf_id = le16_to_cpu(resp->first_vf_id);
pf->max_vfs = le16_to_cpu(resp->max_vfs);
......@@ -7289,6 +7288,7 @@ static int bnxt_hwrm_ver_get(struct bnxt *bp)
bp->hwrm_max_ext_req_len = HWRM_MAX_REQ_LEN;
bp->chip_num = le16_to_cpu(resp->chip_num);
bp->chip_rev = resp->chip_rev;
if (bp->chip_num == CHIP_NUM_58700 && !resp->chip_rev &&
!resp->chip_metal)
bp->flags |= BNXT_FLAG_CHIP_NITRO_A0;
......@@ -9064,7 +9064,7 @@ static int bnxt_update_phy_setting(struct bnxt *bp)
/* The last close may have shutdown the link, so need to call
* PHY_CFG to bring it back up.
*/
if (!netif_carrier_ok(bp->dev))
if (!bp->link_info.link_up)
update_link = true;
if (!bnxt_eee_config_ok(bp))
......@@ -10041,6 +10041,13 @@ static void bnxt_timer(struct timer_list *t)
bnxt_queue_sp_work(bp);
}
#ifdef CONFIG_RFS_ACCEL
if ((bp->flags & BNXT_FLAG_RFS) && bp->ntp_fltr_count) {
set_bit(BNXT_RX_NTP_FLTR_SP_EVENT, &bp->sp_event);
bnxt_queue_sp_work(bp);
}
#endif /*CONFIG_RFS_ACCEL*/
if (bp->link_info.phy_retry) {
if (time_after(jiffies, bp->link_info.phy_retry_expires)) {
bp->link_info.phy_retry = false;
......@@ -10051,7 +10058,8 @@ static void bnxt_timer(struct timer_list *t)
}
}
if ((bp->flags & BNXT_FLAG_CHIP_P5) && netif_carrier_ok(dev)) {
if ((bp->flags & BNXT_FLAG_CHIP_P5) && !bp->chip_rev &&
netif_carrier_ok(dev)) {
set_bit(BNXT_RING_COAL_NOW_SP_EVENT, &bp->sp_event);
bnxt_queue_sp_work(bp);
}
......@@ -10569,7 +10577,7 @@ static void bnxt_set_dflt_rss_hash_type(struct bnxt *bp)
VNIC_RSS_CFG_REQ_HASH_TYPE_TCP_IPV4 |
VNIC_RSS_CFG_REQ_HASH_TYPE_IPV6 |
VNIC_RSS_CFG_REQ_HASH_TYPE_TCP_IPV6;
if (BNXT_CHIP_P4(bp) && bp->hwrm_spec_code >= 0x10501) {
if (BNXT_CHIP_P4_PLUS(bp) && bp->hwrm_spec_code >= 0x10501) {
bp->flags |= BNXT_FLAG_UDP_RSS_CAP;
bp->rss_hash_cfg |= VNIC_RSS_CFG_REQ_HASH_TYPE_UDP_IPV4 |
VNIC_RSS_CFG_REQ_HASH_TYPE_UDP_IPV6;
......@@ -11101,6 +11109,7 @@ static int bnxt_rx_flow_steer(struct net_device *dev, const struct sk_buff *skb,
struct ethhdr *eth = (struct ethhdr *)skb_mac_header(skb);
int rc = 0, idx, bit_id, l2_idx = 0;
struct hlist_head *head;
u32 flags;
if (!ether_addr_equal(dev->dev_addr, eth->h_dest)) {
struct bnxt_vnic_info *vnic = &bp->vnic_info[0];
......@@ -11140,8 +11149,9 @@ static int bnxt_rx_flow_steer(struct net_device *dev, const struct sk_buff *skb,
rc = -EPROTONOSUPPORT;
goto err_free;
}
if ((fkeys->control.flags & FLOW_DIS_ENCAPSULATION) &&
bp->hwrm_spec_code < 0x10601) {
flags = fkeys->control.flags;
if (((flags & FLOW_DIS_ENCAPSULATION) &&
bp->hwrm_spec_code < 0x10601) || (flags & FLOW_DIS_IS_FRAGMENT)) {
rc = -EPROTONOSUPPORT;
goto err_free;
}
......@@ -11378,8 +11388,8 @@ int bnxt_get_port_parent_id(struct net_device *dev,
if (!BNXT_PF(bp) || !(bp->flags & BNXT_FLAG_DSN_VALID))
return -EOPNOTSUPP;
ppid->id_len = sizeof(bp->switch_id);
memcpy(ppid->id, bp->switch_id, ppid->id_len);
ppid->id_len = sizeof(bp->dsn);
memcpy(ppid->id, bp->dsn, ppid->id_len);
return 0;
}
......@@ -11435,9 +11445,9 @@ static void bnxt_remove_one(struct pci_dev *pdev)
bnxt_sriov_disable(bp);
bnxt_dl_fw_reporters_destroy(bp, true);
bnxt_dl_unregister(bp);
pci_disable_pcie_error_reporting(pdev);
unregister_netdev(dev);
bnxt_dl_unregister(bp);
bnxt_shutdown_tc(bp);
bnxt_cancel_sp_work(bp);
bp->sp_event = 0;
......@@ -11471,6 +11481,9 @@ static int bnxt_probe_phy(struct bnxt *bp, bool fw_dflt)
rc);
return rc;
}
if (!fw_dflt)
return 0;
rc = bnxt_update_link(bp, false);
if (rc) {
netdev_err(bp->dev, "Probe phy can't update link (rc: %x)\n",
......@@ -11484,9 +11497,6 @@ static int bnxt_probe_phy(struct bnxt *bp, bool fw_dflt)
if (link_info->auto_link_speeds && !link_info->support_auto_speeds)
link_info->support_auto_speeds = link_info->support_speeds;
if (!fw_dflt)
return 0;
bnxt_init_ethtool_link_settings(bp);
return 0;
}
......@@ -11860,7 +11870,7 @@ static int bnxt_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
if (BNXT_PF(bp)) {
/* Read the adapter's DSN to use as the eswitch switch_id */
bnxt_pcie_dsn_get(bp, bp->switch_id);
rc = bnxt_pcie_dsn_get(bp, bp->dsn);
}
/* MTU range: 60 - FW defined max */
......@@ -11907,11 +11917,14 @@ static int bnxt_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
bnxt_init_tc(bp);
}
bnxt_dl_register(bp);
rc = register_netdev(dev);
if (rc)
goto init_err_cleanup_tc;
goto init_err_cleanup;
bnxt_dl_register(bp);
if (BNXT_PF(bp))
devlink_port_type_eth_set(&bp->dl_port, bp->dev);
bnxt_dl_fw_reporters_create(bp);
netdev_info(dev, "%s found at mem %lx, node addr %pM\n",
......@@ -11921,7 +11934,8 @@ static int bnxt_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
return 0;
init_err_cleanup_tc:
init_err_cleanup:
bnxt_dl_unregister(bp);
bnxt_shutdown_tc(bp);
bnxt_clear_int_mode(bp);
......
......@@ -1457,6 +1457,8 @@ struct bnxt {
#define CHIP_NUM_58804 0xd804
#define CHIP_NUM_58808 0xd808
u8 chip_rev;
#define BNXT_CHIP_NUM_5730X(chip_num) \
((chip_num) >= CHIP_NUM_57301 && \
(chip_num) <= CHIP_NUM_57304)
......@@ -1846,7 +1848,7 @@ struct bnxt {
enum devlink_eswitch_mode eswitch_mode;
struct bnxt_vf_rep **vf_reps; /* array of vf-rep ptrs */
u16 *cfa_code_map; /* cfa_code -> vf_idx map */
u8 switch_id[8];
u8 dsn[8];
struct bnxt_tc_info *tc_info;
struct list_head tc_indr_block_list;
struct notifier_block tc_netdev_nb;
......
......@@ -21,6 +21,7 @@ bnxt_dl_flash_update(struct devlink *dl, const char *filename,
const char *region, struct netlink_ext_ack *extack)
{
struct bnxt *bp = bnxt_get_bp_from_dl(dl);
int rc;
if (region)
return -EOPNOTSUPP;
......@@ -31,7 +32,18 @@ bnxt_dl_flash_update(struct devlink *dl, const char *filename,
return -EPERM;
}
return bnxt_flash_package_from_file(bp->dev, filename, 0);
devlink_flash_update_begin_notify(dl);
devlink_flash_update_status_notify(dl, "Preparing to flash", region, 0,
0);
rc = bnxt_flash_package_from_file(bp->dev, filename, 0);
if (!rc)
devlink_flash_update_status_notify(dl, "Flashing done", region,
0, 0);
else
devlink_flash_update_status_notify(dl, "Flashing failed",
region, 0, 0);
devlink_flash_update_end_notify(dl);
return rc;
}
static int bnxt_fw_reporter_diagnose(struct devlink_health_reporter *reporter,
......@@ -272,11 +284,15 @@ void bnxt_dl_health_recovery_done(struct bnxt *bp)
devlink_health_reporter_recovery_done(hlth->fw_reset_reporter);
}
static int bnxt_dl_info_get(struct devlink *dl, struct devlink_info_req *req,
struct netlink_ext_ack *extack);
static const struct devlink_ops bnxt_dl_ops = {
#ifdef CONFIG_BNXT_SRIOV
.eswitch_mode_set = bnxt_dl_eswitch_mode_set,
.eswitch_mode_get = bnxt_dl_eswitch_mode_get,
#endif /* CONFIG_BNXT_SRIOV */
.info_get = bnxt_dl_info_get,
.flash_update = bnxt_dl_flash_update,
};
......@@ -343,6 +359,136 @@ static void bnxt_copy_from_nvm_data(union devlink_param_value *dst,
dst->vu8 = (u8)val32;
}
static int bnxt_hwrm_get_nvm_cfg_ver(struct bnxt *bp,
union devlink_param_value *nvm_cfg_ver)
{
struct hwrm_nvm_get_variable_input req = {0};
union bnxt_nvm_data *data;
dma_addr_t data_dma_addr;
int rc;
bnxt_hwrm_cmd_hdr_init(bp, &req, HWRM_NVM_GET_VARIABLE, -1, -1);
data = dma_alloc_coherent(&bp->pdev->dev, sizeof(*data),
&data_dma_addr, GFP_KERNEL);
if (!data)
return -ENOMEM;
req.dest_data_addr = cpu_to_le64(data_dma_addr);
req.data_len = cpu_to_le16(BNXT_NVM_CFG_VER_BITS);
req.option_num = cpu_to_le16(NVM_OFF_NVM_CFG_VER);
rc = hwrm_send_message_silent(bp, &req, sizeof(req), HWRM_CMD_TIMEOUT);
if (!rc)
bnxt_copy_from_nvm_data(nvm_cfg_ver, data,
BNXT_NVM_CFG_VER_BITS,
BNXT_NVM_CFG_VER_BYTES);
dma_free_coherent(&bp->pdev->dev, sizeof(*data), data, data_dma_addr);
return rc;
}
static int bnxt_dl_info_get(struct devlink *dl, struct devlink_info_req *req,
struct netlink_ext_ack *extack)
{
struct bnxt *bp = bnxt_get_bp_from_dl(dl);
union devlink_param_value nvm_cfg_ver;
struct hwrm_ver_get_output *ver_resp;
char mgmt_ver[FW_VER_STR_LEN];
char roce_ver[FW_VER_STR_LEN];
char fw_ver[FW_VER_STR_LEN];
char buf[32];
int rc;
rc = devlink_info_driver_name_put(req, DRV_MODULE_NAME);
if (rc)
return rc;
sprintf(buf, "%X", bp->chip_num);
rc = devlink_info_version_fixed_put(req,
DEVLINK_INFO_VERSION_GENERIC_ASIC_ID, buf);
if (rc)
return rc;
ver_resp = &bp->ver_resp;
sprintf(buf, "%X", ver_resp->chip_rev);
rc = devlink_info_version_fixed_put(req,
DEVLINK_INFO_VERSION_GENERIC_ASIC_REV, buf);
if (rc)
return rc;
if (BNXT_PF(bp)) {
sprintf(buf, "%02X-%02X-%02X-%02X-%02X-%02X-%02X-%02X",
bp->dsn[7], bp->dsn[6], bp->dsn[5], bp->dsn[4],
bp->dsn[3], bp->dsn[2], bp->dsn[1], bp->dsn[0]);
rc = devlink_info_serial_number_put(req, buf);
if (rc)
return rc;
}
if (strlen(ver_resp->active_pkg_name)) {
rc =
devlink_info_version_running_put(req,
DEVLINK_INFO_VERSION_GENERIC_FW,
ver_resp->active_pkg_name);
if (rc)
return rc;
}
if (BNXT_PF(bp) && !bnxt_hwrm_get_nvm_cfg_ver(bp, &nvm_cfg_ver)) {
u32 ver = nvm_cfg_ver.vu32;
sprintf(buf, "%X.%X.%X", (ver >> 16) & 0xF, (ver >> 8) & 0xF,
ver & 0xF);
rc = devlink_info_version_running_put(req,
DEVLINK_INFO_VERSION_GENERIC_FW_PSID, buf);
if (rc)
return rc;
}
if (ver_resp->flags & VER_GET_RESP_FLAGS_EXT_VER_AVAIL) {
snprintf(fw_ver, FW_VER_STR_LEN, "%d.%d.%d.%d",
ver_resp->hwrm_fw_major, ver_resp->hwrm_fw_minor,
ver_resp->hwrm_fw_build, ver_resp->hwrm_fw_patch);
snprintf(mgmt_ver, FW_VER_STR_LEN, "%d.%d.%d.%d",
ver_resp->mgmt_fw_major, ver_resp->mgmt_fw_minor,
ver_resp->mgmt_fw_build, ver_resp->mgmt_fw_patch);
snprintf(roce_ver, FW_VER_STR_LEN, "%d.%d.%d.%d",
ver_resp->roce_fw_major, ver_resp->roce_fw_minor,
ver_resp->roce_fw_build, ver_resp->roce_fw_patch);
} else {
snprintf(fw_ver, FW_VER_STR_LEN, "%d.%d.%d.%d",
ver_resp->hwrm_fw_maj_8b, ver_resp->hwrm_fw_min_8b,
ver_resp->hwrm_fw_bld_8b, ver_resp->hwrm_fw_rsvd_8b);
snprintf(mgmt_ver, FW_VER_STR_LEN, "%d.%d.%d.%d",
ver_resp->mgmt_fw_maj_8b, ver_resp->mgmt_fw_min_8b,
ver_resp->mgmt_fw_bld_8b, ver_resp->mgmt_fw_rsvd_8b);
snprintf(roce_ver, FW_VER_STR_LEN, "%d.%d.%d.%d",
ver_resp->roce_fw_maj_8b, ver_resp->roce_fw_min_8b,
ver_resp->roce_fw_bld_8b, ver_resp->roce_fw_rsvd_8b);
}
rc = devlink_info_version_running_put(req,
DEVLINK_INFO_VERSION_GENERIC_FW_APP, fw_ver);
if (rc)
return rc;
if (!(bp->flags & BNXT_FLAG_CHIP_P5)) {
rc = devlink_info_version_running_put(req,
DEVLINK_INFO_VERSION_GENERIC_FW_MGMT, mgmt_ver);
if (rc)
return rc;
rc = devlink_info_version_running_put(req,
DEVLINK_INFO_VERSION_GENERIC_FW_ROCE, roce_ver);
if (rc)
return rc;
}
return 0;
}
static int bnxt_hwrm_nvm_req(struct bnxt *bp, u32 param_id, void *msg,
int msg_len, union devlink_param_value *val)
{
......@@ -485,15 +631,48 @@ static const struct devlink_param bnxt_dl_params[] = {
static const struct devlink_param bnxt_dl_port_params[] = {
};
int bnxt_dl_register(struct bnxt *bp)
static int bnxt_dl_params_register(struct bnxt *bp)
{
struct devlink *dl;
int rc;
if (bp->hwrm_spec_code < 0x10600) {
netdev_warn(bp->dev, "Firmware does not support NVM params");
return -ENOTSUPP;
if (bp->hwrm_spec_code < 0x10600)
return 0;
rc = devlink_params_register(bp->dl, bnxt_dl_params,
ARRAY_SIZE(bnxt_dl_params));
if (rc) {
netdev_warn(bp->dev, "devlink_params_register failed. rc=%d",
rc);
return rc;
}
rc = devlink_port_params_register(&bp->dl_port, bnxt_dl_port_params,
ARRAY_SIZE(bnxt_dl_port_params));
if (rc) {
netdev_err(bp->dev, "devlink_port_params_register failed");
devlink_params_unregister(bp->dl, bnxt_dl_params,
ARRAY_SIZE(bnxt_dl_params));
return rc;
}
devlink_params_publish(bp->dl);
return 0;
}
static void bnxt_dl_params_unregister(struct bnxt *bp)
{
if (bp->hwrm_spec_code < 0x10600)
return;
devlink_params_unregister(bp->dl, bnxt_dl_params,
ARRAY_SIZE(bnxt_dl_params));
devlink_port_params_unregister(&bp->dl_port, bnxt_dl_port_params,
ARRAY_SIZE(bnxt_dl_port_params));
}
int bnxt_dl_register(struct bnxt *bp)
{
struct devlink *dl;
int rc;
if (BNXT_PF(bp))
dl = devlink_alloc(&bnxt_dl_ops, sizeof(struct bnxt_dl));
......@@ -520,40 +699,23 @@ int bnxt_dl_register(struct bnxt *bp)
if (!BNXT_PF(bp))
return 0;
rc = devlink_params_register(dl, bnxt_dl_params,
ARRAY_SIZE(bnxt_dl_params));
if (rc) {
netdev_warn(bp->dev, "devlink_params_register failed. rc=%d",
rc);
goto err_dl_unreg;
}
devlink_port_attrs_set(&bp->dl_port, DEVLINK_PORT_FLAVOUR_PHYSICAL,
bp->pf.port_id, false, 0,
bp->switch_id, sizeof(bp->switch_id));
bp->pf.port_id, false, 0, bp->dsn,
sizeof(bp->dsn));
rc = devlink_port_register(dl, &bp->dl_port, bp->pf.port_id);
if (rc) {
netdev_err(bp->dev, "devlink_port_register failed");
goto err_dl_param_unreg;
goto err_dl_unreg;
}
devlink_port_type_eth_set(&bp->dl_port, bp->dev);
rc = devlink_port_params_register(&bp->dl_port, bnxt_dl_port_params,
ARRAY_SIZE(bnxt_dl_port_params));
if (rc) {
netdev_err(bp->dev, "devlink_port_params_register failed");
rc = bnxt_dl_params_register(bp);
if (rc)
goto err_dl_port_unreg;
}
devlink_params_publish(dl);
return 0;
err_dl_port_unreg:
devlink_port_unregister(&bp->dl_port);
err_dl_param_unreg:
devlink_params_unregister(dl, bnxt_dl_params,
ARRAY_SIZE(bnxt_dl_params));
err_dl_unreg:
devlink_unregister(dl);
err_dl_free:
......@@ -570,12 +732,8 @@ void bnxt_dl_unregister(struct bnxt *bp)
return;
if (BNXT_PF(bp)) {
devlink_port_params_unregister(&bp->dl_port,
bnxt_dl_port_params,
ARRAY_SIZE(bnxt_dl_port_params));
bnxt_dl_params_unregister(bp);
devlink_port_unregister(&bp->dl_port);
devlink_params_unregister(dl, bnxt_dl_params,
ARRAY_SIZE(bnxt_dl_params));
}
devlink_unregister(dl);
devlink_free(dl);
......
......@@ -38,6 +38,10 @@ static inline void bnxt_link_bp_to_dl(struct bnxt *bp, struct devlink *dl)
#define NVM_OFF_IGNORE_ARI 164
#define NVM_OFF_DIS_GRE_VER_CHECK 171
#define NVM_OFF_ENABLE_SRIOV 401
#define NVM_OFF_NVM_CFG_VER 602
#define BNXT_NVM_CFG_VER_BITS 24
#define BNXT_NVM_CFG_VER_BYTES 4
#define BNXT_MSIX_VEC_MAX 1280
#define BNXT_MSIX_VEC_MIN_MAX 128
......
......@@ -1462,15 +1462,15 @@ static int bnxt_get_link_ksettings(struct net_device *dev,
ethtool_link_ksettings_add_link_mode(lk_ksettings,
advertising, Autoneg);
base->autoneg = AUTONEG_ENABLE;
if (link_info->phy_link_status == BNXT_LINK_LINK)
base->duplex = DUPLEX_UNKNOWN;
if (link_info->phy_link_status == BNXT_LINK_LINK) {
bnxt_fw_to_ethtool_lp_adv(link_info, lk_ksettings);
if (link_info->duplex & BNXT_LINK_DUPLEX_FULL)
base->duplex = DUPLEX_FULL;
else
base->duplex = DUPLEX_HALF;
}
ethtool_speed = bnxt_fw_to_ethtool_speed(link_info->link_speed);
if (!netif_carrier_ok(dev))
base->duplex = DUPLEX_UNKNOWN;
else if (link_info->duplex & BNXT_LINK_DUPLEX_FULL)
base->duplex = DUPLEX_FULL;
else
base->duplex = DUPLEX_HALF;
} else {
base->autoneg = AUTONEG_DISABLE;
ethtool_speed =
......@@ -2707,7 +2707,7 @@ static int bnxt_disable_an_for_lpbk(struct bnxt *bp,
return rc;
fw_speed = PORT_PHY_CFG_REQ_FORCE_LINK_SPEED_1GB;
if (netif_carrier_ok(bp->dev))
if (bp->link_info.link_up)
fw_speed = bp->link_info.link_speed;
else if (fw_advertising & BNXT_LINK_SPEED_MSK_10GB)
fw_speed = PORT_PHY_CFG_REQ_FORCE_LINK_SPEED_10GB;
......
......@@ -487,6 +487,8 @@ enum devlink_param_generic_id {
#define DEVLINK_INFO_VERSION_GENERIC_FW_NCSI "fw.ncsi"
/* FW parameter set id */
#define DEVLINK_INFO_VERSION_GENERIC_FW_PSID "fw.psid"
/* RoCE FW version */
#define DEVLINK_INFO_VERSION_GENERIC_FW_ROCE "fw.roce"
struct devlink_region;
struct devlink_info_req;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment