lkml.org 
[lkml]   [2020]   [Jan]   [24]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    From
    Subject[PATCH AUTOSEL 5.4 078/107] mlxsw: spectrum: Wipe xstats.backlog of down ports
    Date
    From: Petr Machata <petrm@mellanox.com>

    [ Upstream commit ca7609ff3680c51d6c29897f3117aa2ad904f92a ]

    Per-port counter cache used by Qdiscs is updated periodically, unless the
    port is down. The fact that the cache is not updated for down ports is no
    problem for most counters, which are relative in nature. However, backlog
    is absolute in nature, and if there is a non-zero value in the cache around
    the time that the port goes down, that value just stays there. This value
    then leaks to offloaded Qdiscs that report non-zero backlog even if
    there (obviously) is no traffic.

    The HW does not keep backlog of a downed port, so do likewise: as the port
    goes down, wipe the backlog value from xstats.

    Fixes: 075ab8adaf4e ("mlxsw: spectrum: Collect tclass related stats periodically")
    Signed-off-by: Petr Machata <petrm@mellanox.com>
    Acked-by: Jiri Pirko <jiri@mellanox.com>
    Signed-off-by: Ido Schimmel <idosch@mellanox.com>
    Signed-off-by: David S. Miller <davem@davemloft.net>
    Signed-off-by: Sasha Levin <sashal@kernel.org>
    ---
    drivers/net/ethernet/mellanox/mlxsw/spectrum.c | 13 +++++++++++++
    1 file changed, 13 insertions(+)

    diff --git a/drivers/net/ethernet/mellanox/mlxsw/spectrum.c b/drivers/net/ethernet/mellanox/mlxsw/spectrum.c
    index 45f6836fcc629..a806c6190bb1e 100644
    --- a/drivers/net/ethernet/mellanox/mlxsw/spectrum.c
    +++ b/drivers/net/ethernet/mellanox/mlxsw/spectrum.c
    @@ -1161,6 +1161,9 @@ static void update_stats_cache(struct work_struct *work)
    periodic_hw_stats.update_dw.work);

    if (!netif_carrier_ok(mlxsw_sp_port->dev))
    + /* Note: mlxsw_sp_port_down_wipe_counters() clears the cache as
    + * necessary when port goes down.
    + */
    goto out;

    mlxsw_sp_port_get_hw_stats(mlxsw_sp_port->dev,
    @@ -4170,6 +4173,15 @@ static int mlxsw_sp_port_unsplit(struct mlxsw_core *mlxsw_core, u8 local_port,
    return 0;
    }

    +static void
    +mlxsw_sp_port_down_wipe_counters(struct mlxsw_sp_port *mlxsw_sp_port)
    +{
    + int i;
    +
    + for (i = 0; i < TC_MAX_QUEUE; i++)
    + mlxsw_sp_port->periodic_hw_stats.xstats.backlog[i] = 0;
    +}
    +
    static void mlxsw_sp_pude_event_func(const struct mlxsw_reg_info *reg,
    char *pude_pl, void *priv)
    {
    @@ -4191,6 +4203,7 @@ static void mlxsw_sp_pude_event_func(const struct mlxsw_reg_info *reg,
    } else {
    netdev_info(mlxsw_sp_port->dev, "link down\n");
    netif_carrier_off(mlxsw_sp_port->dev);
    + mlxsw_sp_port_down_wipe_counters(mlxsw_sp_port);
    }
    }

    --
    2.20.1
    \
     
     \ /
      Last update: 2020-01-24 15:34    [W:4.088 / U:0.052 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site