Commit b5ce611f authored by Ido Schimmel's avatar Ido Schimmel Committed by David S. Miller
Browse files

mlxsw: spectrum: Add devlink-trap support



Register supported packet traps (layer 2 drops only, currently) and
associated trap group with devlink during driver initialization.

The amount of traffic generated by these packet drop traps is capped at
10Kpps to ensure the CPU is not overwhelmed by incoming packets.

Signed-off-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 9e6290c7
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -29,7 +29,7 @@ mlxsw_spectrum-objs := spectrum.o spectrum_buffers.o \
				   spectrum_mr_tcam.o spectrum_mr.o \
				   spectrum_qdisc.o spectrum_span.o \
				   spectrum_nve.o spectrum_nve_vxlan.o \
				   spectrum_dpipe.o
				   spectrum_dpipe.o spectrum_trap.o
mlxsw_spectrum-$(CONFIG_MLXSW_SPECTRUM_DCB)	+= spectrum_dcb.o
mlxsw_spectrum-$(CONFIG_PTP_1588_CLOCK)		+= spectrum_ptp.o
obj-$(CONFIG_MLXSW_MINIMAL)	+= mlxsw_minimal.o
+52 −0
Original line number Diff line number Diff line
@@ -1017,6 +1017,54 @@ static int mlxsw_devlink_flash_update(struct devlink *devlink,
					  component, extack);
}

static int mlxsw_devlink_trap_init(struct devlink *devlink,
				   const struct devlink_trap *trap,
				   void *trap_ctx)
{
	struct mlxsw_core *mlxsw_core = devlink_priv(devlink);
	struct mlxsw_driver *mlxsw_driver = mlxsw_core->driver;

	if (!mlxsw_driver->trap_init)
		return -EOPNOTSUPP;
	return mlxsw_driver->trap_init(mlxsw_core, trap, trap_ctx);
}

static void mlxsw_devlink_trap_fini(struct devlink *devlink,
				    const struct devlink_trap *trap,
				    void *trap_ctx)
{
	struct mlxsw_core *mlxsw_core = devlink_priv(devlink);
	struct mlxsw_driver *mlxsw_driver = mlxsw_core->driver;

	if (!mlxsw_driver->trap_fini)
		return;
	mlxsw_driver->trap_fini(mlxsw_core, trap, trap_ctx);
}

static int mlxsw_devlink_trap_action_set(struct devlink *devlink,
					 const struct devlink_trap *trap,
					 enum devlink_trap_action action)
{
	struct mlxsw_core *mlxsw_core = devlink_priv(devlink);
	struct mlxsw_driver *mlxsw_driver = mlxsw_core->driver;

	if (!mlxsw_driver->trap_action_set)
		return -EOPNOTSUPP;
	return mlxsw_driver->trap_action_set(mlxsw_core, trap, action);
}

static int
mlxsw_devlink_trap_group_init(struct devlink *devlink,
			      const struct devlink_trap_group *group)
{
	struct mlxsw_core *mlxsw_core = devlink_priv(devlink);
	struct mlxsw_driver *mlxsw_driver = mlxsw_core->driver;

	if (!mlxsw_driver->trap_group_init)
		return -EOPNOTSUPP;
	return mlxsw_driver->trap_group_init(mlxsw_core, group);
}

static const struct devlink_ops mlxsw_devlink_ops = {
	.reload				= mlxsw_devlink_core_bus_device_reload,
	.port_type_set			= mlxsw_devlink_port_type_set,
@@ -1034,6 +1082,10 @@ static const struct devlink_ops mlxsw_devlink_ops = {
	.sb_occ_tc_port_bind_get	= mlxsw_devlink_sb_occ_tc_port_bind_get,
	.info_get			= mlxsw_devlink_info_get,
	.flash_update			= mlxsw_devlink_flash_update,
	.trap_init			= mlxsw_devlink_trap_init,
	.trap_fini			= mlxsw_devlink_trap_fini,
	.trap_action_set		= mlxsw_devlink_trap_action_set,
	.trap_group_init		= mlxsw_devlink_trap_group_init,
};

static int
+9 −0
Original line number Diff line number Diff line
@@ -292,6 +292,15 @@ struct mlxsw_driver {
	int (*flash_update)(struct mlxsw_core *mlxsw_core,
			    const char *file_name, const char *component,
			    struct netlink_ext_ack *extack);
	int (*trap_init)(struct mlxsw_core *mlxsw_core,
			 const struct devlink_trap *trap, void *trap_ctx);
	void (*trap_fini)(struct mlxsw_core *mlxsw_core,
			  const struct devlink_trap *trap, void *trap_ctx);
	int (*trap_action_set)(struct mlxsw_core *mlxsw_core,
			       const struct devlink_trap *trap,
			       enum devlink_trap_action action);
	int (*trap_group_init)(struct mlxsw_core *mlxsw_core,
			       const struct devlink_trap_group *group);
	void (*txhdr_construct)(struct sk_buff *skb,
				const struct mlxsw_tx_info *tx_info);
	int (*resources_register)(struct mlxsw_core *mlxsw_core);
+21 −0
Original line number Diff line number Diff line
@@ -4665,6 +4665,12 @@ static int mlxsw_sp_init(struct mlxsw_core *mlxsw_core,
		goto err_traps_init;
	}

	err = mlxsw_sp_devlink_traps_init(mlxsw_sp);
	if (err) {
		dev_err(mlxsw_sp->bus_info->dev, "Failed to initialize devlink traps\n");
		goto err_devlink_traps_init;
	}

	err = mlxsw_sp_buffers_init(mlxsw_sp);
	if (err) {
		dev_err(mlxsw_sp->bus_info->dev, "Failed to initialize buffers\n");
@@ -4798,6 +4804,8 @@ err_span_init:
err_lag_init:
	mlxsw_sp_buffers_fini(mlxsw_sp);
err_buffers_init:
	mlxsw_sp_devlink_traps_fini(mlxsw_sp);
err_devlink_traps_init:
	mlxsw_sp_traps_fini(mlxsw_sp);
err_traps_init:
	mlxsw_sp_fids_fini(mlxsw_sp);
@@ -4870,6 +4878,7 @@ static void mlxsw_sp_fini(struct mlxsw_core *mlxsw_core)
	mlxsw_sp_span_fini(mlxsw_sp);
	mlxsw_sp_lag_fini(mlxsw_sp);
	mlxsw_sp_buffers_fini(mlxsw_sp);
	mlxsw_sp_devlink_traps_fini(mlxsw_sp);
	mlxsw_sp_traps_fini(mlxsw_sp);
	mlxsw_sp_fids_fini(mlxsw_sp);
	mlxsw_sp_kvdl_fini(mlxsw_sp);
@@ -5251,6 +5260,10 @@ static struct mlxsw_driver mlxsw_sp1_driver = {
	.sb_occ_port_pool_get		= mlxsw_sp_sb_occ_port_pool_get,
	.sb_occ_tc_port_bind_get	= mlxsw_sp_sb_occ_tc_port_bind_get,
	.flash_update			= mlxsw_sp_flash_update,
	.trap_init			= mlxsw_sp_trap_init,
	.trap_fini			= mlxsw_sp_trap_fini,
	.trap_action_set		= mlxsw_sp_trap_action_set,
	.trap_group_init		= mlxsw_sp_trap_group_init,
	.txhdr_construct		= mlxsw_sp_txhdr_construct,
	.resources_register		= mlxsw_sp1_resources_register,
	.kvd_sizes_get			= mlxsw_sp_kvd_sizes_get,
@@ -5281,6 +5294,10 @@ static struct mlxsw_driver mlxsw_sp2_driver = {
	.sb_occ_port_pool_get		= mlxsw_sp_sb_occ_port_pool_get,
	.sb_occ_tc_port_bind_get	= mlxsw_sp_sb_occ_tc_port_bind_get,
	.flash_update			= mlxsw_sp_flash_update,
	.trap_init			= mlxsw_sp_trap_init,
	.trap_fini			= mlxsw_sp_trap_fini,
	.trap_action_set		= mlxsw_sp_trap_action_set,
	.trap_group_init		= mlxsw_sp_trap_group_init,
	.txhdr_construct		= mlxsw_sp_txhdr_construct,
	.resources_register		= mlxsw_sp2_resources_register,
	.params_register		= mlxsw_sp2_params_register,
@@ -5310,6 +5327,10 @@ static struct mlxsw_driver mlxsw_sp3_driver = {
	.sb_occ_port_pool_get		= mlxsw_sp_sb_occ_port_pool_get,
	.sb_occ_tc_port_bind_get	= mlxsw_sp_sb_occ_tc_port_bind_get,
	.flash_update			= mlxsw_sp_flash_update,
	.trap_init			= mlxsw_sp_trap_init,
	.trap_fini			= mlxsw_sp_trap_fini,
	.trap_action_set		= mlxsw_sp_trap_action_set,
	.trap_group_init		= mlxsw_sp_trap_group_init,
	.txhdr_construct		= mlxsw_sp_txhdr_construct,
	.resources_register		= mlxsw_sp2_resources_register,
	.params_register		= mlxsw_sp2_params_register,
+13 −0
Original line number Diff line number Diff line
@@ -958,4 +958,17 @@ void mlxsw_sp_nve_fini(struct mlxsw_sp *mlxsw_sp);
int mlxsw_sp_nve_inc_parsing_depth_get(struct mlxsw_sp *mlxsw_sp);
void mlxsw_sp_nve_inc_parsing_depth_put(struct mlxsw_sp *mlxsw_sp);

/* spectrum_trap.c */
int mlxsw_sp_devlink_traps_init(struct mlxsw_sp *mlxsw_sp);
void mlxsw_sp_devlink_traps_fini(struct mlxsw_sp *mlxsw_sp);
int mlxsw_sp_trap_init(struct mlxsw_core *mlxsw_core,
		       const struct devlink_trap *trap, void *trap_ctx);
void mlxsw_sp_trap_fini(struct mlxsw_core *mlxsw_core,
			const struct devlink_trap *trap, void *trap_ctx);
int mlxsw_sp_trap_action_set(struct mlxsw_core *mlxsw_core,
			     const struct devlink_trap *trap,
			     enum devlink_trap_action action);
int mlxsw_sp_trap_group_init(struct mlxsw_core *mlxsw_core,
			     const struct devlink_trap_group *group);

#endif
Loading