mirror of
https://mirrors.bfsu.edu.cn/git/linux.git
synced 2024-11-26 21:54:11 +08:00
net: dsa: mv88e6xxx: Add ATU occupancy via devlink resources
The ATU can report how many entries it contains. It does this per bin, there being 4 bins in total. Export the ATU as a devlink resource, and provide a method the needed callback to get the resource occupancy. Signed-off-by: Andrew Lunn <andrew@lunn.ch> Acked-by: Jiri Pirko <jiri@mellanox.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
c5f299d592
commit
e0c69ca7df
@ -2720,9 +2720,179 @@ static void mv88e6xxx_teardown_devlink_params(struct dsa_switch *ds)
|
||||
ARRAY_SIZE(mv88e6xxx_devlink_params));
|
||||
}
|
||||
|
||||
enum mv88e6xxx_devlink_resource_id {
|
||||
MV88E6XXX_RESOURCE_ID_ATU,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_0,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_1,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_2,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_3,
|
||||
};
|
||||
|
||||
static u64 mv88e6xxx_devlink_atu_bin_get(struct mv88e6xxx_chip *chip,
|
||||
u16 bin)
|
||||
{
|
||||
u16 occupancy = 0;
|
||||
int err;
|
||||
|
||||
mv88e6xxx_reg_lock(chip);
|
||||
|
||||
err = mv88e6xxx_g2_atu_stats_set(chip, MV88E6XXX_G2_ATU_STATS_MODE_ALL,
|
||||
bin);
|
||||
if (err) {
|
||||
dev_err(chip->dev, "failed to set ATU stats kind/bin\n");
|
||||
goto unlock;
|
||||
}
|
||||
|
||||
err = mv88e6xxx_g1_atu_get_next(chip, 0);
|
||||
if (err) {
|
||||
dev_err(chip->dev, "failed to perform ATU get next\n");
|
||||
goto unlock;
|
||||
}
|
||||
|
||||
err = mv88e6xxx_g2_atu_stats_get(chip, &occupancy);
|
||||
if (err) {
|
||||
dev_err(chip->dev, "failed to get ATU stats\n");
|
||||
goto unlock;
|
||||
}
|
||||
|
||||
unlock:
|
||||
mv88e6xxx_reg_unlock(chip);
|
||||
|
||||
return occupancy;
|
||||
}
|
||||
|
||||
static u64 mv88e6xxx_devlink_atu_bin_0_get(void *priv)
|
||||
{
|
||||
struct mv88e6xxx_chip *chip = priv;
|
||||
|
||||
return mv88e6xxx_devlink_atu_bin_get(chip,
|
||||
MV88E6XXX_G2_ATU_STATS_BIN_0);
|
||||
}
|
||||
|
||||
static u64 mv88e6xxx_devlink_atu_bin_1_get(void *priv)
|
||||
{
|
||||
struct mv88e6xxx_chip *chip = priv;
|
||||
|
||||
return mv88e6xxx_devlink_atu_bin_get(chip,
|
||||
MV88E6XXX_G2_ATU_STATS_BIN_1);
|
||||
}
|
||||
|
||||
static u64 mv88e6xxx_devlink_atu_bin_2_get(void *priv)
|
||||
{
|
||||
struct mv88e6xxx_chip *chip = priv;
|
||||
|
||||
return mv88e6xxx_devlink_atu_bin_get(chip,
|
||||
MV88E6XXX_G2_ATU_STATS_BIN_2);
|
||||
}
|
||||
|
||||
static u64 mv88e6xxx_devlink_atu_bin_3_get(void *priv)
|
||||
{
|
||||
struct mv88e6xxx_chip *chip = priv;
|
||||
|
||||
return mv88e6xxx_devlink_atu_bin_get(chip,
|
||||
MV88E6XXX_G2_ATU_STATS_BIN_3);
|
||||
}
|
||||
|
||||
static u64 mv88e6xxx_devlink_atu_get(void *priv)
|
||||
{
|
||||
return mv88e6xxx_devlink_atu_bin_0_get(priv) +
|
||||
mv88e6xxx_devlink_atu_bin_1_get(priv) +
|
||||
mv88e6xxx_devlink_atu_bin_2_get(priv) +
|
||||
mv88e6xxx_devlink_atu_bin_3_get(priv);
|
||||
}
|
||||
|
||||
static int mv88e6xxx_setup_devlink_resources(struct dsa_switch *ds)
|
||||
{
|
||||
struct devlink_resource_size_params size_params;
|
||||
struct mv88e6xxx_chip *chip = ds->priv;
|
||||
int err;
|
||||
|
||||
devlink_resource_size_params_init(&size_params,
|
||||
mv88e6xxx_num_macs(chip),
|
||||
mv88e6xxx_num_macs(chip),
|
||||
1, DEVLINK_RESOURCE_UNIT_ENTRY);
|
||||
|
||||
err = dsa_devlink_resource_register(ds, "ATU",
|
||||
mv88e6xxx_num_macs(chip),
|
||||
MV88E6XXX_RESOURCE_ID_ATU,
|
||||
DEVLINK_RESOURCE_ID_PARENT_TOP,
|
||||
&size_params);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
devlink_resource_size_params_init(&size_params,
|
||||
mv88e6xxx_num_macs(chip) / 4,
|
||||
mv88e6xxx_num_macs(chip) / 4,
|
||||
1, DEVLINK_RESOURCE_UNIT_ENTRY);
|
||||
|
||||
err = dsa_devlink_resource_register(ds, "ATU_bin_0",
|
||||
mv88e6xxx_num_macs(chip) / 4,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_0,
|
||||
MV88E6XXX_RESOURCE_ID_ATU,
|
||||
&size_params);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
err = dsa_devlink_resource_register(ds, "ATU_bin_1",
|
||||
mv88e6xxx_num_macs(chip) / 4,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_1,
|
||||
MV88E6XXX_RESOURCE_ID_ATU,
|
||||
&size_params);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
err = dsa_devlink_resource_register(ds, "ATU_bin_2",
|
||||
mv88e6xxx_num_macs(chip) / 4,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_2,
|
||||
MV88E6XXX_RESOURCE_ID_ATU,
|
||||
&size_params);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
err = dsa_devlink_resource_register(ds, "ATU_bin_3",
|
||||
mv88e6xxx_num_macs(chip) / 4,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_3,
|
||||
MV88E6XXX_RESOURCE_ID_ATU,
|
||||
&size_params);
|
||||
if (err)
|
||||
goto out;
|
||||
|
||||
dsa_devlink_resource_occ_get_register(ds,
|
||||
MV88E6XXX_RESOURCE_ID_ATU,
|
||||
mv88e6xxx_devlink_atu_get,
|
||||
chip);
|
||||
|
||||
dsa_devlink_resource_occ_get_register(ds,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_0,
|
||||
mv88e6xxx_devlink_atu_bin_0_get,
|
||||
chip);
|
||||
|
||||
dsa_devlink_resource_occ_get_register(ds,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_1,
|
||||
mv88e6xxx_devlink_atu_bin_1_get,
|
||||
chip);
|
||||
|
||||
dsa_devlink_resource_occ_get_register(ds,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_2,
|
||||
mv88e6xxx_devlink_atu_bin_2_get,
|
||||
chip);
|
||||
|
||||
dsa_devlink_resource_occ_get_register(ds,
|
||||
MV88E6XXX_RESOURCE_ID_ATU_BIN_3,
|
||||
mv88e6xxx_devlink_atu_bin_3_get,
|
||||
chip);
|
||||
|
||||
return 0;
|
||||
|
||||
out:
|
||||
dsa_devlink_resources_unregister(ds);
|
||||
return err;
|
||||
}
|
||||
|
||||
static void mv88e6xxx_teardown(struct dsa_switch *ds)
|
||||
{
|
||||
mv88e6xxx_teardown_devlink_params(ds);
|
||||
dsa_devlink_resources_unregister(ds);
|
||||
}
|
||||
|
||||
static int mv88e6xxx_setup(struct dsa_switch *ds)
|
||||
@ -2841,11 +3011,23 @@ static int mv88e6xxx_setup(struct dsa_switch *ds)
|
||||
unlock:
|
||||
mv88e6xxx_reg_unlock(chip);
|
||||
|
||||
/* Has to be called without holding the register lock, since
|
||||
* it takes the devlink lock, and we later take the locks in
|
||||
* the reverse order when getting/setting parameters.
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
/* Have to be called without holding the register lock, since
|
||||
* they take the devlink lock, and we later take the locks in
|
||||
* the reverse order when getting/setting parameters or
|
||||
* resource occupancy.
|
||||
*/
|
||||
return mv88e6xxx_setup_devlink_params(ds);
|
||||
err = mv88e6xxx_setup_devlink_resources(ds);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
err = mv88e6xxx_setup_devlink_params(ds);
|
||||
if (err)
|
||||
dsa_devlink_resources_unregister(ds);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
static int mv88e6xxx_mdio_read(struct mii_bus *bus, int phy, int reg)
|
||||
|
Loading…
Reference in New Issue
Block a user