aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/ethernet/intel/ixgbe/devlink/devlink.c
diff options
context:
space:
mode:
authorJedrzej Jagielski <[email protected]>2025-04-10 13:00:03 +0000
committerTony Nguyen <[email protected]>2025-04-15 14:36:32 +0000
commit6eae2aeb60b6f1cfa97e6e8f296027f15173a67a (patch)
treed067348137d70a9fb61562a839ec02add5d67a0a /drivers/net/ethernet/intel/ixgbe/devlink/devlink.c
parentixgbe: add E610 functions getting PBA and FW ver info (diff)
downloadkernel-6eae2aeb60b6f1cfa97e6e8f296027f15173a67a.tar.gz
kernel-6eae2aeb60b6f1cfa97e6e8f296027f15173a67a.zip
ixgbe: extend .info_get() with stored versions
Add functions reading inactive versions from the inactive flash bank. Print stored versions for the content present in the inactive bank. If there's pending update the versions reflect the ones which are going to be loaded after reload. If there's no pending update both running and stored are the same, which means there won't be any NVM change on reload. Co-developed-by: Slawomir Mrozowicz <[email protected]> Signed-off-by: Slawomir Mrozowicz <[email protected]> Co-developed-by: Piotr Kwapulinski <[email protected]> Signed-off-by: Piotr Kwapulinski <[email protected]> Signed-off-by: Jedrzej Jagielski <[email protected]> Signed-off-by: Tony Nguyen <[email protected]>
Diffstat (limited to 'drivers/net/ethernet/intel/ixgbe/devlink/devlink.c')
-rw-r--r--drivers/net/ethernet/intel/ixgbe/devlink/devlink.c170
1 files changed, 154 insertions, 16 deletions
diff --git a/drivers/net/ethernet/intel/ixgbe/devlink/devlink.c b/drivers/net/ethernet/intel/ixgbe/devlink/devlink.c
index a7c39e951c7b..f7bafc1dad2b 100644
--- a/drivers/net/ethernet/intel/ixgbe/devlink/devlink.c
+++ b/drivers/net/ethernet/intel/ixgbe/devlink/devlink.c
@@ -6,6 +6,15 @@
struct ixgbe_info_ctx {
char buf[128];
+ struct ixgbe_orom_info pending_orom;
+ struct ixgbe_nvm_info pending_nvm;
+ struct ixgbe_netlist_info pending_netlist;
+ struct ixgbe_hw_dev_caps dev_caps;
+};
+
+enum ixgbe_devlink_version_type {
+ IXGBE_DL_VERSION_RUNNING,
+ IXGBE_DL_VERSION_STORED
};
static void ixgbe_info_get_dsn(struct ixgbe_adapter *adapter,
@@ -20,7 +29,8 @@ static void ixgbe_info_get_dsn(struct ixgbe_adapter *adapter,
}
static void ixgbe_info_orom_ver(struct ixgbe_adapter *adapter,
- struct ixgbe_info_ctx *ctx)
+ struct ixgbe_info_ctx *ctx,
+ enum ixgbe_devlink_version_type type)
{
struct ixgbe_hw *hw = &adapter->hw;
struct ixgbe_nvm_version nvm_ver;
@@ -30,6 +40,10 @@ static void ixgbe_info_orom_ver(struct ixgbe_adapter *adapter,
if (hw->mac.type == ixgbe_mac_e610) {
struct ixgbe_orom_info *orom = &adapter->hw.flash.orom;
+ if (type == IXGBE_DL_VERSION_STORED &&
+ ctx->dev_caps.common_cap.nvm_update_pending_orom)
+ orom = &ctx->pending_orom;
+
snprintf(ctx->buf, sizeof(ctx->buf), "%u.%u.%u",
orom->major, orom->build, orom->patch);
return;
@@ -51,14 +65,20 @@ static void ixgbe_info_orom_ver(struct ixgbe_adapter *adapter,
}
static void ixgbe_info_eetrack(struct ixgbe_adapter *adapter,
- struct ixgbe_info_ctx *ctx)
+ struct ixgbe_info_ctx *ctx,
+ enum ixgbe_devlink_version_type type)
{
struct ixgbe_hw *hw = &adapter->hw;
struct ixgbe_nvm_version nvm_ver;
if (hw->mac.type == ixgbe_mac_e610) {
- snprintf(ctx->buf, sizeof(ctx->buf), "0x%08x",
- hw->flash.nvm.eetrack);
+ u32 eetrack = hw->flash.nvm.eetrack;
+
+ if (type == IXGBE_DL_VERSION_STORED &&
+ ctx->dev_caps.common_cap.nvm_update_pending_nvm)
+ eetrack = ctx->pending_nvm.eetrack;
+
+ snprintf(ctx->buf, sizeof(ctx->buf), "0x%08x", eetrack);
return;
}
@@ -92,34 +112,54 @@ static void ixgbe_info_fw_build(struct ixgbe_adapter *adapter,
}
static void ixgbe_info_fw_srev(struct ixgbe_adapter *adapter,
- struct ixgbe_info_ctx *ctx)
+ struct ixgbe_info_ctx *ctx,
+ enum ixgbe_devlink_version_type type)
{
struct ixgbe_nvm_info *nvm = &adapter->hw.flash.nvm;
+ if (type == IXGBE_DL_VERSION_STORED &&
+ ctx->dev_caps.common_cap.nvm_update_pending_nvm)
+ nvm = &ctx->pending_nvm;
+
snprintf(ctx->buf, sizeof(ctx->buf), "%u", nvm->srev);
}
static void ixgbe_info_orom_srev(struct ixgbe_adapter *adapter,
- struct ixgbe_info_ctx *ctx)
+ struct ixgbe_info_ctx *ctx,
+ enum ixgbe_devlink_version_type type)
{
struct ixgbe_orom_info *orom = &adapter->hw.flash.orom;
+ if (type == IXGBE_DL_VERSION_STORED &&
+ ctx->dev_caps.common_cap.nvm_update_pending_orom)
+ orom = &ctx->pending_orom;
+
snprintf(ctx->buf, sizeof(ctx->buf), "%u", orom->srev);
}
static void ixgbe_info_nvm_ver(struct ixgbe_adapter *adapter,
- struct ixgbe_info_ctx *ctx)
+ struct ixgbe_info_ctx *ctx,
+ enum ixgbe_devlink_version_type type)
{
struct ixgbe_nvm_info *nvm = &adapter->hw.flash.nvm;
+ if (type == IXGBE_DL_VERSION_STORED &&
+ ctx->dev_caps.common_cap.nvm_update_pending_nvm)
+ nvm = &ctx->pending_nvm;
+
snprintf(ctx->buf, sizeof(ctx->buf), "%x.%02x", nvm->major, nvm->minor);
}
static void ixgbe_info_netlist_ver(struct ixgbe_adapter *adapter,
- struct ixgbe_info_ctx *ctx)
+ struct ixgbe_info_ctx *ctx,
+ enum ixgbe_devlink_version_type type)
{
struct ixgbe_netlist_info *netlist = &adapter->hw.flash.netlist;
+ if (type == IXGBE_DL_VERSION_STORED &&
+ ctx->dev_caps.common_cap.nvm_update_pending_netlist)
+ netlist = &ctx->pending_netlist;
+
/* The netlist version fields are BCD formatted */
snprintf(ctx->buf, sizeof(ctx->buf), "%x.%x.%x-%x.%x.%x",
netlist->major, netlist->minor,
@@ -128,13 +168,57 @@ static void ixgbe_info_netlist_ver(struct ixgbe_adapter *adapter,
}
static void ixgbe_info_netlist_build(struct ixgbe_adapter *adapter,
- struct ixgbe_info_ctx *ctx)
+ struct ixgbe_info_ctx *ctx,
+ enum ixgbe_devlink_version_type type)
{
struct ixgbe_netlist_info *netlist = &adapter->hw.flash.netlist;
+ if (type == IXGBE_DL_VERSION_STORED &&
+ ctx->dev_caps.common_cap.nvm_update_pending_netlist)
+ netlist = &ctx->pending_netlist;
+
snprintf(ctx->buf, sizeof(ctx->buf), "0x%08x", netlist->hash);
}
+static int ixgbe_set_ctx_dev_caps(struct ixgbe_hw *hw,
+ struct ixgbe_info_ctx *ctx,
+ struct netlink_ext_ack *extack)
+{
+ bool *pending_orom, *pending_nvm, *pending_netlist;
+ int err;
+
+ err = ixgbe_discover_dev_caps(hw, &ctx->dev_caps);
+ if (err) {
+ NL_SET_ERR_MSG_MOD(extack,
+ "Unable to discover device capabilities");
+ return err;
+ }
+
+ pending_orom = &ctx->dev_caps.common_cap.nvm_update_pending_orom;
+ pending_nvm = &ctx->dev_caps.common_cap.nvm_update_pending_nvm;
+ pending_netlist = &ctx->dev_caps.common_cap.nvm_update_pending_netlist;
+
+ if (*pending_orom) {
+ err = ixgbe_get_inactive_orom_ver(hw, &ctx->pending_orom);
+ if (err)
+ *pending_orom = false;
+ }
+
+ if (*pending_nvm) {
+ err = ixgbe_get_inactive_nvm_ver(hw, &ctx->pending_nvm);
+ if (err)
+ *pending_nvm = false;
+ }
+
+ if (*pending_netlist) {
+ err = ixgbe_get_inactive_netlist_ver(hw, &ctx->pending_netlist);
+ if (err)
+ *pending_netlist = false;
+ }
+
+ return 0;
+}
+
static int ixgbe_devlink_info_get_e610(struct ixgbe_adapter *adapter,
struct devlink_info_req *req,
struct ixgbe_info_ctx *ctx)
@@ -153,31 +237,77 @@ static int ixgbe_devlink_info_get_e610(struct ixgbe_adapter *adapter,
if (err)
return err;
- ixgbe_info_fw_srev(adapter, ctx);
+ ixgbe_info_fw_srev(adapter, ctx, IXGBE_DL_VERSION_RUNNING);
err = devlink_info_version_running_put(req, "fw.mgmt.srev", ctx->buf);
if (err)
return err;
- ixgbe_info_orom_srev(adapter, ctx);
+ ixgbe_info_orom_srev(adapter, ctx, IXGBE_DL_VERSION_RUNNING);
err = devlink_info_version_running_put(req, "fw.undi.srev", ctx->buf);
if (err)
return err;
- ixgbe_info_nvm_ver(adapter, ctx);
+ ixgbe_info_nvm_ver(adapter, ctx, IXGBE_DL_VERSION_RUNNING);
err = devlink_info_version_running_put(req, "fw.psid.api", ctx->buf);
if (err)
return err;
- ixgbe_info_netlist_ver(adapter, ctx);
+ ixgbe_info_netlist_ver(adapter, ctx, IXGBE_DL_VERSION_RUNNING);
err = devlink_info_version_running_put(req, "fw.netlist", ctx->buf);
if (err)
return err;
- ixgbe_info_netlist_build(adapter, ctx);
+ ixgbe_info_netlist_build(adapter, ctx, IXGBE_DL_VERSION_RUNNING);
return devlink_info_version_running_put(req, "fw.netlist.build",
ctx->buf);
}
+static int
+ixgbe_devlink_pending_info_get_e610(struct ixgbe_adapter *adapter,
+ struct devlink_info_req *req,
+ struct ixgbe_info_ctx *ctx)
+{
+ int err;
+
+ ixgbe_info_orom_ver(adapter, ctx, IXGBE_DL_VERSION_STORED);
+ err = devlink_info_version_stored_put(req,
+ DEVLINK_INFO_VERSION_GENERIC_FW_UNDI,
+ ctx->buf);
+ if (err)
+ return err;
+
+ ixgbe_info_eetrack(adapter, ctx, IXGBE_DL_VERSION_STORED);
+ err = devlink_info_version_stored_put(req,
+ DEVLINK_INFO_VERSION_GENERIC_FW_BUNDLE_ID,
+ ctx->buf);
+ if (err)
+ return err;
+
+ ixgbe_info_fw_srev(adapter, ctx, IXGBE_DL_VERSION_STORED);
+ err = devlink_info_version_stored_put(req, "fw.mgmt.srev", ctx->buf);
+ if (err)
+ return err;
+
+ ixgbe_info_orom_srev(adapter, ctx, IXGBE_DL_VERSION_STORED);
+ err = devlink_info_version_stored_put(req, "fw.undi.srev", ctx->buf);
+ if (err)
+ return err;
+
+ ixgbe_info_nvm_ver(adapter, ctx, IXGBE_DL_VERSION_STORED);
+ err = devlink_info_version_stored_put(req, "fw.psid.api", ctx->buf);
+ if (err)
+ return err;
+
+ ixgbe_info_netlist_ver(adapter, ctx, IXGBE_DL_VERSION_STORED);
+ err = devlink_info_version_stored_put(req, "fw.netlist", ctx->buf);
+ if (err)
+ return err;
+
+ ixgbe_info_netlist_build(adapter, ctx, IXGBE_DL_VERSION_STORED);
+ return devlink_info_version_stored_put(req, "fw.netlist.build",
+ ctx->buf);
+}
+
static int ixgbe_devlink_info_get(struct devlink *devlink,
struct devlink_info_req *req,
struct netlink_ext_ack *extack)
@@ -206,21 +336,29 @@ static int ixgbe_devlink_info_get(struct devlink *devlink,
if (err)
goto free_ctx;
- ixgbe_info_orom_ver(adapter, ctx);
+ ixgbe_info_orom_ver(adapter, ctx, IXGBE_DL_VERSION_RUNNING);
err = devlink_info_version_running_put(req,
DEVLINK_INFO_VERSION_GENERIC_FW_UNDI,
ctx->buf);
if (err)
goto free_ctx;
- ixgbe_info_eetrack(adapter, ctx);
+ ixgbe_info_eetrack(adapter, ctx, IXGBE_DL_VERSION_RUNNING);
err = devlink_info_version_running_put(req,
DEVLINK_INFO_VERSION_GENERIC_FW_BUNDLE_ID,
ctx->buf);
if (err || hw->mac.type != ixgbe_mac_e610)
goto free_ctx;
+ err = ixgbe_set_ctx_dev_caps(hw, ctx, extack);
+ if (err)
+ goto free_ctx;
+
err = ixgbe_devlink_info_get_e610(adapter, req, ctx);
+ if (err)
+ goto free_ctx;
+
+ err = ixgbe_devlink_pending_info_get_e610(adapter, req, ctx);
free_ctx:
kfree(ctx);
return err;