Commit 4ae57566 authored by Saeed Mahameed's avatar Saeed Mahameed Committed by David S. Miller
Browse files

net/mlxfw: Generic mlx FW flash status notify



FW flash status notify is currently implemented via a callback to the
caller mlx module, and all it is doing is to call
devlink_flash_update_status_notify with the specific module devlink
instance.

Instead of repeating the whole process for all mlx modules and
re-implement the status_notify callback again and again. Just provide the
devlink instance as part of mlxfw_dev when calling mlxfw_firmware_flash
and let mlxfw do the devlink status updates directly.

This will be very useful for adding status notify support to mlx5, as
already done in this patch, with a simple one line of just providing the
devlink instance to mlxfw_firmware_flash.

mlxfw now depends on NET_DEVLINK as all other mlx modules.

Signed-off-by: default avatarSaeed Mahameed <saeedm@mellanox.com>
Reviewed-by: default avatarIdo Schimmel <idosch@mellanox.com>
Acked-by: default avatarJiri Pirko <jiri@mellanox.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent b105e8e2
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -634,6 +634,7 @@ int mlx5_firmware_flash(struct mlx5_core_dev *dev,
			.ops = &mlx5_mlxfw_dev_ops,
			.psid = dev->board_id,
			.psid_size = strlen(dev->board_id),
			.devlink = priv_to_devlink(dev),
		},
		.mlx5_core_dev = dev
	};
+1 −0
Original line number Diff line number Diff line
@@ -12,3 +12,4 @@ config MLXFW
	  To compile this driver as a module, choose M here: the
	  module will be called mlxfw.
	select XZ_DEC
	select NET_DEVLINK
+2 −4
Original line number Diff line number Diff line
@@ -6,6 +6,7 @@

#include <linux/firmware.h>
#include <linux/netlink.h>
#include <net/devlink.h>

enum mlxfw_fsm_state {
	MLXFW_FSM_STATE_IDLE,
@@ -58,16 +59,13 @@ struct mlxfw_dev_ops {
	void (*fsm_cancel)(struct mlxfw_dev *mlxfw_dev, u32 fwhandle);

	void (*fsm_release)(struct mlxfw_dev *mlxfw_dev, u32 fwhandle);

	void (*status_notify)(struct mlxfw_dev *mlxfw_dev,
			      const char *msg, const char *comp_name,
			      u32 done_bytes, u32 total_bytes);
};

struct mlxfw_dev {
	const struct mlxfw_dev_ops *ops;
	const char *psid;
	u16 psid_size;
	struct devlink *devlink;
};

#if IS_REACHABLE(CONFIG_MLXFW)
+11 −10
Original line number Diff line number Diff line
@@ -39,16 +39,6 @@ static const char * const mlxfw_fsm_state_err_str[] = {
		"unknown error"
};

static void mlxfw_status_notify(struct mlxfw_dev *mlxfw_dev,
				const char *msg, const char *comp_name,
				u32 done_bytes, u32 total_bytes)
{
	if (!mlxfw_dev->ops->status_notify)
		return;
	mlxfw_dev->ops->status_notify(mlxfw_dev, msg, comp_name,
				      done_bytes, total_bytes);
}

static int mlxfw_fsm_state_wait(struct mlxfw_dev *mlxfw_dev, u32 fwhandle,
				enum mlxfw_fsm_state fsm_state,
				struct netlink_ext_ack *extack)
@@ -85,6 +75,14 @@ retry:
	return 0;
}

static void mlxfw_status_notify(struct mlxfw_dev *mlxfw_dev,
				const char *msg, const char *comp_name,
				u32 done_bytes, u32 total_bytes)
{
	devlink_flash_update_status_notify(mlxfw_dev->devlink, msg, comp_name,
					   done_bytes, total_bytes);
}

#define MLXFW_ALIGN_DOWN(x, align_bits) ((x) & ~((1 << (align_bits)) - 1))
#define MLXFW_ALIGN_UP(x, align_bits) \
		MLXFW_ALIGN_DOWN((x) + ((1 << (align_bits)) - 1), (align_bits))
@@ -225,6 +223,7 @@ int mlxfw_firmware_flash(struct mlxfw_dev *mlxfw_dev,
		return PTR_ERR(mfa2_file);

	pr_info("Initialize firmware flash process\n");
	devlink_flash_update_begin_notify(mlxfw_dev->devlink);
	mlxfw_status_notify(mlxfw_dev, "Initializing firmware flash process",
			    NULL, 0, 0);
	err = mlxfw_dev->ops->fsm_lock(mlxfw_dev, &fwhandle);
@@ -263,6 +262,7 @@ int mlxfw_firmware_flash(struct mlxfw_dev *mlxfw_dev,
	pr_info("Firmware flash done.\n");
	mlxfw_status_notify(mlxfw_dev, "Firmware flash done", NULL, 0, 0);
	mlxfw_mfa2_file_fini(mfa2_file);
	devlink_flash_update_end_notify(mlxfw_dev->devlink);
	return 0;

err_state_wait_activate_to_locked:
@@ -272,6 +272,7 @@ err_state_wait_idle_to_locked:
	mlxfw_dev->ops->fsm_release(mlxfw_dev, fwhandle);
err_fsm_lock:
	mlxfw_mfa2_file_fini(mfa2_file);
	devlink_flash_update_end_notify(mlxfw_dev->devlink);
	return err;
}
EXPORT_SYMBOL(mlxfw_firmware_flash);
+1 −16
Original line number Diff line number Diff line
@@ -347,19 +347,6 @@ static void mlxsw_sp_fsm_release(struct mlxfw_dev *mlxfw_dev, u32 fwhandle)
	mlxsw_reg_write(mlxsw_sp->core, MLXSW_REG(mcc), mcc_pl);
}

static void mlxsw_sp_status_notify(struct mlxfw_dev *mlxfw_dev,
				   const char *msg, const char *comp_name,
				   u32 done_bytes, u32 total_bytes)
{
	struct mlxsw_sp_mlxfw_dev *mlxsw_sp_mlxfw_dev =
		container_of(mlxfw_dev, struct mlxsw_sp_mlxfw_dev, mlxfw_dev);
	struct mlxsw_sp *mlxsw_sp = mlxsw_sp_mlxfw_dev->mlxsw_sp;

	devlink_flash_update_status_notify(priv_to_devlink(mlxsw_sp->core),
					   msg, comp_name,
					   done_bytes, total_bytes);
}

static const struct mlxfw_dev_ops mlxsw_sp_mlxfw_dev_ops = {
	.component_query	= mlxsw_sp_component_query,
	.fsm_lock		= mlxsw_sp_fsm_lock,
@@ -370,7 +357,6 @@ static const struct mlxfw_dev_ops mlxsw_sp_mlxfw_dev_ops = {
	.fsm_query_state	= mlxsw_sp_fsm_query_state,
	.fsm_cancel		= mlxsw_sp_fsm_cancel,
	.fsm_release		= mlxsw_sp_fsm_release,
	.status_notify		= mlxsw_sp_status_notify,
};

static int mlxsw_sp_firmware_flash(struct mlxsw_sp *mlxsw_sp,
@@ -382,16 +368,15 @@ static int mlxsw_sp_firmware_flash(struct mlxsw_sp *mlxsw_sp,
			.ops = &mlxsw_sp_mlxfw_dev_ops,
			.psid = mlxsw_sp->bus_info->psid,
			.psid_size = strlen(mlxsw_sp->bus_info->psid),
			.devlink = priv_to_devlink(mlxsw_sp->core),
		},
		.mlxsw_sp = mlxsw_sp
	};
	int err;

	mlxsw_core_fw_flash_start(mlxsw_sp->core);
	devlink_flash_update_begin_notify(priv_to_devlink(mlxsw_sp->core));
	err = mlxfw_firmware_flash(&mlxsw_sp_mlxfw_dev.mlxfw_dev,
				   firmware, extack);
	devlink_flash_update_end_notify(priv_to_devlink(mlxsw_sp->core));
	mlxsw_core_fw_flash_end(mlxsw_sp->core);

	return err;