Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit f121e0ea authored by Bodong Wang's avatar Bodong Wang Committed by Saeed Mahameed
Browse files

net/mlx5: E-Switch, Add state to eswitch vport representors



Currently the eswitch vport reps have a valid indicator, which is
set on register and unset on unregister. However, a rep can be loaded
or not loaded when doing unregister, current driver checks if the
vport of that rep is enabled as a flag to imply the rep is loaded.
However, for ECPF, this is not valid as the host PF will enable the
vports for its VFs instead.

Add three states: {unregistered, registered, loaded}, with the
following state changes across different operations:

	create: (none)       -> unregistered
	reg:    unregistered -> registered
	load:   registered   -> loaded
	unload: loaded       -> registered
	unreg:  registered   -> unregistered

Note that the state shall only be updated inside eswitch driver rather
than individual drivers such as ETH or IB.

Signed-off-by: default avatarBodong Wang <bodong@mellanox.com>
Signed-off-by: default avatarOr Gerlitz <ogerlitz@mellanox.com>
Suggested-by: default avatarMark Bloch <markb@mellanox.com>
Reviewed-by: default avatarOr Gerlitz <ogerlitz@mellanox.com>
Signed-off-by: default avatarSaeed Mahameed <saeedm@mellanox.com>
parent 879c8f84
Loading
Loading
Loading
Loading
+22 −9
Original line number Diff line number Diff line
@@ -364,7 +364,7 @@ static int esw_set_global_vlan_pop(struct mlx5_eswitch *esw, u8 val)
	esw_debug(esw->dev, "%s applying global %s policy\n", __func__, val ? "pop" : "none");
	for (vf_vport = 1; vf_vport < esw->enabled_vports; vf_vport++) {
		rep = &esw->offloads.vport_reps[vf_vport];
		if (!rep->rep_if[REP_ETH].valid)
		if (rep->rep_if[REP_ETH].state != REP_LOADED)
			continue;

		err = __mlx5_eswitch_set_vport_vlan(esw, rep->vport, 0, 0, val);
@@ -1256,7 +1256,7 @@ int esw_offloads_init_reps(struct mlx5_eswitch *esw)
	struct mlx5_core_dev *dev = esw->dev;
	struct mlx5_esw_offload *offloads;
	struct mlx5_eswitch_rep *rep;
	u8 hw_id[ETH_ALEN];
	u8 hw_id[ETH_ALEN], rep_type;
	int vport;

	esw->offloads.vport_reps = kcalloc(total_vfs,
@@ -1271,6 +1271,9 @@ int esw_offloads_init_reps(struct mlx5_eswitch *esw)
	mlx5_esw_for_all_reps(esw, vport, rep) {
		rep->vport = vport;
		ether_addr_copy(rep->hw_id, hw_id);

		for (rep_type = 0; rep_type < NUM_REP_TYPES; rep_type++)
			rep->rep_if[rep_type].state = REP_UNREGISTERED;
	}

	offloads->vport_reps[0].vport = MLX5_VPORT_UPLINK;
@@ -1281,10 +1284,11 @@ int esw_offloads_init_reps(struct mlx5_eswitch *esw)
static void __esw_offloads_unload_rep(struct mlx5_eswitch *esw,
				      struct mlx5_eswitch_rep *rep, u8 rep_type)
{
	if (!rep->rep_if[rep_type].valid)
	if (rep->rep_if[rep_type].state != REP_LOADED)
		return;

	rep->rep_if[rep_type].unload(rep);
	rep->rep_if[rep_type].state = REP_REGISTERED;
}

static void esw_offloads_unload_reps_type(struct mlx5_eswitch *esw, int nvports,
@@ -1311,10 +1315,18 @@ static void esw_offloads_unload_reps(struct mlx5_eswitch *esw, int nvports)
static int __esw_offloads_load_rep(struct mlx5_eswitch *esw,
				   struct mlx5_eswitch_rep *rep, u8 rep_type)
{
	if (!rep->rep_if[rep_type].valid)
	int err = 0;

	if (rep->rep_if[rep_type].state != REP_REGISTERED)
		return 0;

	return rep->rep_if[rep_type].load(esw->dev, rep);
	err = rep->rep_if[rep_type].load(esw->dev, rep);
	if (err)
		return err;

	rep->rep_if[rep_type].state = REP_LOADED;

	return 0;
}

static int esw_offloads_load_reps_type(struct mlx5_eswitch *esw, int nvports,
@@ -1861,7 +1873,7 @@ void mlx5_eswitch_register_vport_rep(struct mlx5_eswitch *esw,
	rep_if->get_proto_dev = __rep_if->get_proto_dev;
	rep_if->priv = __rep_if->priv;

	rep_if->valid = true;
	rep_if->state = REP_REGISTERED;
}
EXPORT_SYMBOL(mlx5_eswitch_register_vport_rep);

@@ -1873,10 +1885,11 @@ void mlx5_eswitch_unregister_vport_rep(struct mlx5_eswitch *esw,

	rep = &offloads->vport_reps[vport_index];

	if (esw->mode == SRIOV_OFFLOADS && esw->vports[vport_index].enabled)
	if (esw->mode == SRIOV_OFFLOADS &&
	    rep->rep_if[rep_type].state == REP_LOADED)
		rep->rep_if[rep_type].unload(rep);

	rep->rep_if[rep_type].valid = false;
	rep->rep_if[rep_type].state = REP_UNREGISTERED;
}
EXPORT_SYMBOL(mlx5_eswitch_unregister_vport_rep);

@@ -1896,7 +1909,7 @@ void *mlx5_eswitch_get_proto_dev(struct mlx5_eswitch *esw,

	rep = mlx5_eswitch_get_rep(esw, vport);

	if (rep->rep_if[rep_type].valid &&
	if (rep->rep_if[rep_type].state == REP_LOADED &&
	    rep->rep_if[rep_type].get_proto_dev)
		return rep->rep_if[rep_type].get_proto_dev(rep);
	return NULL;
+7 −1
Original line number Diff line number Diff line
@@ -22,6 +22,12 @@ enum {
	NUM_REP_TYPES,
};

enum {
	REP_UNREGISTERED,
	REP_REGISTERED,
	REP_LOADED,
};

struct mlx5_eswitch_rep;
struct mlx5_eswitch_rep_if {
	int		       (*load)(struct mlx5_core_dev *dev,
@@ -29,7 +35,7 @@ struct mlx5_eswitch_rep_if {
	void		       (*unload)(struct mlx5_eswitch_rep *rep);
	void		       *(*get_proto_dev)(struct mlx5_eswitch_rep *rep);
	void			*priv;
	bool		       valid;
	u8			state;
};

struct mlx5_eswitch_rep {