Skip to content

Commit

Permalink
mlxsw: spectrum_ethtool: Introduce ptys_max_speed callback
Browse files Browse the repository at this point in the history
The SBIB register configures the size of an internal buffer that the
Spectrum ASICs use when mirroring traffic on egress. This size should be
taken into account when validating that the port headroom buffers are not
larger than the chip can handle. Up until now this was not done, which is
incidentally not a problem, because the priority group buffers that mlxsw
auto-configures are small enough that the boundary condition could not be
violated.

When dcbnl_setbuffer is implemented, the user gets control over sizes of PG
buffers, and they might overshoot the headroom capacity. However the size
of the SBIB buffer depends on port speed, which cannot be vetoed. There is
obviously no way to retroactively push back on requests for overlarge PG
buffers, or reject an overlarge MTU, or cancel losslessness of a certain
PG.

Therefore, instead of taking into account the current speed when
calculating SBIB buffer size, take into account the maximum speed that a
port with given Ethernet protocol capabilities can have.

To that end, add a new ethtool callback, ptys_max_speed, which determines
this maximum speed.

Signed-off-by: Petr Machata <petrm@nvidia.com>
Signed-off-by: Ido Schimmel <idosch@nvidia.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
  • Loading branch information
Petr Machata authored and David S. Miller committed Sep 14, 2020
1 parent d24ca6c commit 60fbc52
Show file tree
Hide file tree
Showing 2 changed files with 45 additions and 0 deletions.
1 change: 1 addition & 0 deletions drivers/net/ethernet/mellanox/mlxsw/spectrum.h
Original file line number Diff line number Diff line change
Expand Up @@ -331,6 +331,7 @@ struct mlxsw_sp_port_type_speed_ops {
void (*from_ptys_speed_duplex)(struct mlxsw_sp *mlxsw_sp,
bool carrier_ok, u32 ptys_eth_proto,
struct ethtool_link_ksettings *cmd);
int (*ptys_max_speed)(struct mlxsw_sp_port *mlxsw_sp_port, u32 *p_max_speed);
u32 (*to_ptys_advert_link)(struct mlxsw_sp *mlxsw_sp, u8 width,
const struct ethtool_link_ksettings *cmd);
u32 (*to_ptys_speed)(struct mlxsw_sp *mlxsw_sp, u8 width, u32 speed);
Expand Down
44 changes: 44 additions & 0 deletions drivers/net/ethernet/mellanox/mlxsw/spectrum_ethtool.c
Original file line number Diff line number Diff line change
Expand Up @@ -1162,6 +1162,27 @@ mlxsw_sp1_from_ptys_speed_duplex(struct mlxsw_sp *mlxsw_sp, bool carrier_ok,
cmd->base.duplex = DUPLEX_FULL;
}

static int mlxsw_sp1_ptys_max_speed(struct mlxsw_sp_port *mlxsw_sp_port, u32 *p_max_speed)
{
u32 eth_proto_cap;
u32 max_speed = 0;
int err;
int i;

err = mlxsw_sp_port_ptys_query(mlxsw_sp_port, &eth_proto_cap, NULL, NULL, NULL);
if (err)
return err;

for (i = 0; i < MLXSW_SP1_PORT_LINK_MODE_LEN; i++) {
if ((eth_proto_cap & mlxsw_sp1_port_link_mode[i].mask) &&
mlxsw_sp1_port_link_mode[i].speed > max_speed)
max_speed = mlxsw_sp1_port_link_mode[i].speed;
}

*p_max_speed = max_speed;
return 0;
}

static u32
mlxsw_sp1_to_ptys_advert_link(struct mlxsw_sp *mlxsw_sp, u8 width,
const struct ethtool_link_ksettings *cmd)
Expand Down Expand Up @@ -1211,6 +1232,7 @@ const struct mlxsw_sp_port_type_speed_ops mlxsw_sp1_port_type_speed_ops = {
.from_ptys_link = mlxsw_sp1_from_ptys_link,
.from_ptys_speed = mlxsw_sp1_from_ptys_speed,
.from_ptys_speed_duplex = mlxsw_sp1_from_ptys_speed_duplex,
.ptys_max_speed = mlxsw_sp1_ptys_max_speed,
.to_ptys_advert_link = mlxsw_sp1_to_ptys_advert_link,
.to_ptys_speed = mlxsw_sp1_to_ptys_speed,
.reg_ptys_eth_pack = mlxsw_sp1_reg_ptys_eth_pack,
Expand Down Expand Up @@ -1548,6 +1570,27 @@ mlxsw_sp2_from_ptys_speed_duplex(struct mlxsw_sp *mlxsw_sp, bool carrier_ok,
cmd->base.duplex = DUPLEX_FULL;
}

static int mlxsw_sp2_ptys_max_speed(struct mlxsw_sp_port *mlxsw_sp_port, u32 *p_max_speed)
{
u32 eth_proto_cap;
u32 max_speed = 0;
int err;
int i;

err = mlxsw_sp_port_ptys_query(mlxsw_sp_port, &eth_proto_cap, NULL, NULL, NULL);
if (err)
return err;

for (i = 0; i < MLXSW_SP2_PORT_LINK_MODE_LEN; i++) {
if ((eth_proto_cap & mlxsw_sp2_port_link_mode[i].mask) &&
mlxsw_sp2_port_link_mode[i].speed > max_speed)
max_speed = mlxsw_sp2_port_link_mode[i].speed;
}

*p_max_speed = max_speed;
return 0;
}

static bool
mlxsw_sp2_test_bit_ethtool(const struct mlxsw_sp2_port_link_mode *link_mode,
const unsigned long *mode)
Expand Down Expand Up @@ -1617,6 +1660,7 @@ const struct mlxsw_sp_port_type_speed_ops mlxsw_sp2_port_type_speed_ops = {
.from_ptys_link = mlxsw_sp2_from_ptys_link,
.from_ptys_speed = mlxsw_sp2_from_ptys_speed,
.from_ptys_speed_duplex = mlxsw_sp2_from_ptys_speed_duplex,
.ptys_max_speed = mlxsw_sp2_ptys_max_speed,
.to_ptys_advert_link = mlxsw_sp2_to_ptys_advert_link,
.to_ptys_speed = mlxsw_sp2_to_ptys_speed,
.reg_ptys_eth_pack = mlxsw_sp2_reg_ptys_eth_pack,
Expand Down

0 comments on commit 60fbc52

Please sign in to comment.