mirror of
https://github.com/torvalds/linux.git
synced 2026-11-07 06:17:02 +01:00
Merge branch 'net-dsa-motorcomm-mib-fixup'
David Yang says: ==================== net: dsa: motorcomm: MIB fixup Fix (theoretical) MIB inconsistency and prepare for new devices. No new features are introduced. ==================== Link: https://patch.msgid.link/20261004160622.948037-1-mmyangfl@gmail.com Signed-off-by: Jakub Kicinski <kuba@kernel.org>
This commit is contained in:
commit
3fa7e831b8
|
|
@ -3,5 +3,6 @@ obj-$(CONFIG_NET_DSA_YT921X) += yt921x.o
|
|||
yt921x-objs := chip.o
|
||||
yt921x-$(CONFIG_NET_DSA_YT921X_LEDS) += leds.o
|
||||
yt921x-objs += mdio_bus.o
|
||||
yt921x-objs += mib.o
|
||||
yt921x-objs += pcs-921x.o
|
||||
yt921x-objs += smi.o
|
||||
|
|
|
|||
|
|
@ -19,6 +19,7 @@
|
|||
#include <linux/of_mdio.h>
|
||||
#include <linux/of_net.h>
|
||||
#include <linux/sort.h>
|
||||
#include <linux/u64_stats_sync.h>
|
||||
|
||||
#include <net/dsa.h>
|
||||
#include <net/dscp.h>
|
||||
|
|
@ -28,76 +29,10 @@
|
|||
#include "chip.h"
|
||||
#include "leds.h"
|
||||
#include "mdio_bus.h"
|
||||
#include "mib.h"
|
||||
#include "pcs.h"
|
||||
#include "smi.h"
|
||||
|
||||
struct yt921x_mib_desc {
|
||||
unsigned int size;
|
||||
unsigned int offset;
|
||||
const char *name;
|
||||
};
|
||||
|
||||
#define MIB_DESC(_size, _offset, _name) \
|
||||
{_size, _offset, _name}
|
||||
|
||||
/* Must agree with yt921x_mib
|
||||
*
|
||||
* Unstructured fields (name != NULL) will appear in get_ethtool_stats(),
|
||||
* structured go to their *_stats() methods, but we need their sizes and offsets
|
||||
* to perform 32bit MIB overflow wraparound.
|
||||
*/
|
||||
static const struct yt921x_mib_desc yt921x_mib_descs[] = {
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_BROADCAST, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PAUSE, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_MULTICAST, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_CRC_ERR, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_ALIGN_ERR, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_UNDERSIZE_ERR, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_FRAG_ERR, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_64, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_65_TO_127, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_128_TO_255, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_256_TO_511, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_512_TO_1023, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_1024_TO_1518, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_1519_TO_MAX, NULL),
|
||||
MIB_DESC(2, YT921X_MIB_DATA_RX_GOOD_BYTES, NULL),
|
||||
|
||||
MIB_DESC(2, YT921X_MIB_DATA_RX_BAD_BYTES, "RxBadBytes"),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_OVERSIZE_ERR, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_DROPPED, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_BROADCAST, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PAUSE, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_MULTICAST, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_UNDERSIZE_ERR, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_64, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_65_TO_127, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_128_TO_255, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_256_TO_511, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_512_TO_1023, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_1024_TO_1518, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_1519_TO_MAX, NULL),
|
||||
|
||||
MIB_DESC(2, YT921X_MIB_DATA_TX_GOOD_BYTES, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_COLLISION, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_EXCESSIVE_COLLISION, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_MULTIPLE_COLLISION, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_SINGLE_COLLISION, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_DEFERRED, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_LATE_COLLISION, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_OAM, "RxOAM"),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_OAM, "TxOAM"),
|
||||
};
|
||||
|
||||
static const struct yt921x_info yt921x_infos[] = {
|
||||
{
|
||||
"YT9215SC", YT9215_MAJOR, 1, 0,
|
||||
|
|
@ -146,14 +81,6 @@ static const struct yt921x_info yt921x_infos[] = {
|
|||
|
||||
#define YT921X_VID_UNWARE 4095
|
||||
|
||||
/* The interval should be small enough to avoid overflow of 32bit MIBs.
|
||||
*
|
||||
* Until we can read MIBs from stats64 call directly (i.e. sleep
|
||||
* there), we have to poll stats more frequently then it is actually needed.
|
||||
* For overflow protection, normally, 100 sec interval should have been OK.
|
||||
*/
|
||||
#define YT921X_STATS_INTERVAL_JIFFIES (3 * HZ)
|
||||
|
||||
struct yt921x_reg_mdio {
|
||||
struct mii_bus *bus;
|
||||
int addr;
|
||||
|
|
@ -171,9 +98,6 @@ struct yt921x_reg_mdio {
|
|||
|
||||
/* TODO: SPI/I2C */
|
||||
|
||||
#define to_yt921x_priv(_ds) container_of_const(_ds, struct yt921x_priv, ds)
|
||||
#define to_device(priv) ((priv)->ds.dev)
|
||||
|
||||
static u32 ethaddr_hi4_to_u32(const unsigned char *addr)
|
||||
{
|
||||
return (addr[0] << 24) | (addr[1] << 16) | (addr[2] << 8) | addr[3];
|
||||
|
|
@ -268,293 +192,6 @@ static const struct yt921x_reg_ops yt921x_reg_ops_mdio = {
|
|||
|
||||
/* TODO: SPI/I2C */
|
||||
|
||||
/* Read and handle overflow of 32bit MIBs. MIB buffer must be zeroed before. */
|
||||
static int yt921x_read_mib(struct yt921x_priv *priv, int port)
|
||||
{
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct device *dev = to_device(priv);
|
||||
struct yt921x_mib *mib = &pp->mib;
|
||||
int res = 0;
|
||||
|
||||
/* Reading of yt921x_port::mib is not protected by a lock and it's vain
|
||||
* to keep its consistency, since we have to read registers one by one
|
||||
* and there is no way to make a snapshot of MIB stats.
|
||||
*
|
||||
* Writing (by this function only) is and should be protected by
|
||||
* reg_lock.
|
||||
*/
|
||||
|
||||
for (size_t i = 0; i < ARRAY_SIZE(yt921x_mib_descs); i++) {
|
||||
const struct yt921x_mib_desc *desc = &yt921x_mib_descs[i];
|
||||
u32 reg = YT921X_MIBn_DATA0(port) + desc->offset;
|
||||
u64 *valp = &((u64 *)mib)[i];
|
||||
u32 val0;
|
||||
u64 val;
|
||||
|
||||
res = yt921x_reg_read(priv, reg, &val0);
|
||||
if (res)
|
||||
break;
|
||||
|
||||
if (desc->size <= 1) {
|
||||
u64 old_val = *valp;
|
||||
|
||||
val = (old_val & ~(u64)U32_MAX) | val0;
|
||||
if (val < old_val)
|
||||
val += 1ull << 32;
|
||||
} else {
|
||||
u32 val1;
|
||||
|
||||
res = yt921x_reg_read(priv, reg + 4, &val1);
|
||||
if (res)
|
||||
break;
|
||||
val = ((u64)val1 << 32) | val0;
|
||||
}
|
||||
|
||||
WRITE_ONCE(*valp, val);
|
||||
}
|
||||
|
||||
pp->rx_frames = mib->rx_64byte + mib->rx_65_127byte +
|
||||
mib->rx_128_255byte + mib->rx_256_511byte +
|
||||
mib->rx_512_1023byte + mib->rx_1024_1518byte +
|
||||
mib->rx_jumbo;
|
||||
pp->tx_frames = mib->tx_64byte + mib->tx_65_127byte +
|
||||
mib->tx_128_255byte + mib->tx_256_511byte +
|
||||
mib->tx_512_1023byte + mib->tx_1024_1518byte +
|
||||
mib->tx_jumbo;
|
||||
|
||||
if (res)
|
||||
dev_err(dev, "Failed to %s port %d: %i\n", "read stats for",
|
||||
port, res);
|
||||
return res;
|
||||
}
|
||||
|
||||
static void yt921x_poll_mib(struct work_struct *work)
|
||||
{
|
||||
struct yt921x_port *pp = container_of_const(work, struct yt921x_port,
|
||||
mib_read.work);
|
||||
unsigned long delay = YT921X_STATS_INTERVAL_JIFFIES;
|
||||
struct yt921x_priv *priv = yt921x_port_to_priv(pp);
|
||||
int port = pp->index;
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
res = yt921x_read_mib(priv, port);
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
if (res)
|
||||
delay *= 4;
|
||||
|
||||
schedule_delayed_work(&pp->mib_read, delay);
|
||||
}
|
||||
|
||||
static void
|
||||
yt921x_dsa_get_strings(struct dsa_switch *ds, int port, u32 stringset,
|
||||
uint8_t *data)
|
||||
{
|
||||
if (stringset != ETH_SS_STATS)
|
||||
return;
|
||||
|
||||
for (size_t i = 0; i < ARRAY_SIZE(yt921x_mib_descs); i++) {
|
||||
const struct yt921x_mib_desc *desc = &yt921x_mib_descs[i];
|
||||
|
||||
if (desc->name)
|
||||
ethtool_puts(&data, desc->name);
|
||||
}
|
||||
}
|
||||
|
||||
static void
|
||||
yt921x_dsa_get_ethtool_stats(struct dsa_switch *ds, int port, uint64_t *data)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *mib = &pp->mib;
|
||||
size_t j;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
yt921x_read_mib(priv, port);
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
|
||||
j = 0;
|
||||
for (size_t i = 0; i < ARRAY_SIZE(yt921x_mib_descs); i++) {
|
||||
const struct yt921x_mib_desc *desc = &yt921x_mib_descs[i];
|
||||
|
||||
if (!desc->name)
|
||||
continue;
|
||||
|
||||
data[j] = ((u64 *)mib)[i];
|
||||
j++;
|
||||
}
|
||||
}
|
||||
|
||||
static int yt921x_dsa_get_sset_count(struct dsa_switch *ds, int port, int sset)
|
||||
{
|
||||
int cnt = 0;
|
||||
|
||||
if (sset != ETH_SS_STATS)
|
||||
return 0;
|
||||
|
||||
for (size_t i = 0; i < ARRAY_SIZE(yt921x_mib_descs); i++) {
|
||||
const struct yt921x_mib_desc *desc = &yt921x_mib_descs[i];
|
||||
|
||||
if (desc->name)
|
||||
cnt++;
|
||||
}
|
||||
|
||||
return cnt;
|
||||
}
|
||||
|
||||
static void
|
||||
yt921x_dsa_get_eth_mac_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_eth_mac_stats *mac_stats)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *mib = &pp->mib;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
yt921x_read_mib(priv, port);
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
|
||||
mac_stats->FramesTransmittedOK = pp->tx_frames;
|
||||
mac_stats->SingleCollisionFrames = mib->tx_single_collisions;
|
||||
mac_stats->MultipleCollisionFrames = mib->tx_multiple_collisions;
|
||||
mac_stats->FramesReceivedOK = pp->rx_frames;
|
||||
mac_stats->FrameCheckSequenceErrors = mib->rx_crc_errors;
|
||||
mac_stats->AlignmentErrors = mib->rx_alignment_errors;
|
||||
mac_stats->OctetsTransmittedOK = mib->tx_good_bytes;
|
||||
mac_stats->FramesWithDeferredXmissions = mib->tx_deferred;
|
||||
mac_stats->LateCollisions = mib->tx_late_collisions;
|
||||
mac_stats->FramesAbortedDueToXSColls = mib->tx_aborted_errors;
|
||||
/* mac_stats->FramesLostDueToIntMACXmitError */
|
||||
/* mac_stats->CarrierSenseErrors */
|
||||
mac_stats->OctetsReceivedOK = mib->rx_good_bytes;
|
||||
/* mac_stats->FramesLostDueToIntMACRcvError */
|
||||
mac_stats->MulticastFramesXmittedOK = mib->tx_multicast;
|
||||
mac_stats->BroadcastFramesXmittedOK = mib->tx_broadcast;
|
||||
/* mac_stats->FramesWithExcessiveDeferral */
|
||||
mac_stats->MulticastFramesReceivedOK = mib->rx_multicast;
|
||||
mac_stats->BroadcastFramesReceivedOK = mib->rx_broadcast;
|
||||
/* mac_stats->InRangeLengthErrors */
|
||||
/* mac_stats->OutOfRangeLengthField */
|
||||
mac_stats->FrameTooLongErrors = mib->rx_oversize_errors;
|
||||
}
|
||||
|
||||
static void
|
||||
yt921x_dsa_get_eth_ctrl_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_eth_ctrl_stats *ctrl_stats)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *mib = &pp->mib;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
yt921x_read_mib(priv, port);
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
|
||||
ctrl_stats->MACControlFramesTransmitted = mib->tx_pause;
|
||||
ctrl_stats->MACControlFramesReceived = mib->rx_pause;
|
||||
/* ctrl_stats->UnsupportedOpcodesReceived */
|
||||
}
|
||||
|
||||
static const struct ethtool_rmon_hist_range yt921x_rmon_ranges[] = {
|
||||
{ 0, 64 },
|
||||
{ 65, 127 },
|
||||
{ 128, 255 },
|
||||
{ 256, 511 },
|
||||
{ 512, 1023 },
|
||||
{ 1024, 1518 },
|
||||
{ 1519, YT921X_FRAME_SIZE_MAX },
|
||||
{}
|
||||
};
|
||||
|
||||
static void
|
||||
yt921x_dsa_get_rmon_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_rmon_stats *rmon_stats,
|
||||
const struct ethtool_rmon_hist_range **ranges)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *mib = &pp->mib;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
yt921x_read_mib(priv, port);
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
|
||||
*ranges = yt921x_rmon_ranges;
|
||||
|
||||
rmon_stats->undersize_pkts = mib->rx_undersize_errors;
|
||||
rmon_stats->oversize_pkts = mib->rx_oversize_errors;
|
||||
rmon_stats->fragments = mib->rx_alignment_errors;
|
||||
/* rmon_stats->jabbers */
|
||||
|
||||
rmon_stats->hist[0] = mib->rx_64byte;
|
||||
rmon_stats->hist[1] = mib->rx_65_127byte;
|
||||
rmon_stats->hist[2] = mib->rx_128_255byte;
|
||||
rmon_stats->hist[3] = mib->rx_256_511byte;
|
||||
rmon_stats->hist[4] = mib->rx_512_1023byte;
|
||||
rmon_stats->hist[5] = mib->rx_1024_1518byte;
|
||||
rmon_stats->hist[6] = mib->rx_jumbo;
|
||||
|
||||
rmon_stats->hist_tx[0] = mib->tx_64byte;
|
||||
rmon_stats->hist_tx[1] = mib->tx_65_127byte;
|
||||
rmon_stats->hist_tx[2] = mib->tx_128_255byte;
|
||||
rmon_stats->hist_tx[3] = mib->tx_256_511byte;
|
||||
rmon_stats->hist_tx[4] = mib->tx_512_1023byte;
|
||||
rmon_stats->hist_tx[5] = mib->tx_1024_1518byte;
|
||||
rmon_stats->hist_tx[6] = mib->tx_jumbo;
|
||||
}
|
||||
|
||||
static void
|
||||
yt921x_dsa_get_stats64(struct dsa_switch *ds, int port,
|
||||
struct rtnl_link_stats64 *stats)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *mib = &pp->mib;
|
||||
|
||||
stats->rx_length_errors = mib->rx_undersize_errors +
|
||||
mib->rx_fragment_errors;
|
||||
stats->rx_over_errors = mib->rx_oversize_errors;
|
||||
stats->rx_crc_errors = mib->rx_crc_errors;
|
||||
stats->rx_frame_errors = mib->rx_alignment_errors;
|
||||
/* stats->rx_fifo_errors */
|
||||
/* stats->rx_missed_errors */
|
||||
|
||||
stats->tx_aborted_errors = mib->tx_aborted_errors;
|
||||
/* stats->tx_carrier_errors */
|
||||
stats->tx_fifo_errors = mib->tx_undersize_errors;
|
||||
/* stats->tx_heartbeat_errors */
|
||||
stats->tx_window_errors = mib->tx_late_collisions;
|
||||
|
||||
stats->rx_packets = pp->rx_frames;
|
||||
stats->tx_packets = pp->tx_frames;
|
||||
stats->rx_bytes = mib->rx_good_bytes - ETH_FCS_LEN * stats->rx_packets;
|
||||
stats->tx_bytes = mib->tx_good_bytes - ETH_FCS_LEN * stats->tx_packets;
|
||||
stats->rx_errors = stats->rx_length_errors + stats->rx_over_errors +
|
||||
stats->rx_crc_errors + stats->rx_frame_errors;
|
||||
stats->tx_errors = stats->tx_aborted_errors + stats->tx_fifo_errors +
|
||||
stats->tx_window_errors;
|
||||
stats->rx_dropped = mib->rx_dropped;
|
||||
/* stats->tx_dropped */
|
||||
stats->multicast = mib->rx_multicast;
|
||||
stats->collisions = mib->tx_collisions;
|
||||
}
|
||||
|
||||
static void
|
||||
yt921x_dsa_get_pause_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_pause_stats *pause_stats)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *mib = &pp->mib;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
yt921x_read_mib(priv, port);
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
|
||||
pause_stats->tx_pause_frames = mib->tx_pause;
|
||||
pause_stats->rx_pause_frames = mib->rx_pause;
|
||||
}
|
||||
|
||||
static int
|
||||
yt921x_set_eee(struct yt921x_priv *priv, int port, struct ethtool_keee *e)
|
||||
{
|
||||
|
|
@ -598,7 +235,7 @@ yt921x_set_eee(struct yt921x_priv *priv, int port, struct ethtool_keee *e)
|
|||
static int
|
||||
yt921x_dsa_set_mac_eee(struct dsa_switch *ds, int port, struct ethtool_keee *e)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
|
@ -622,7 +259,7 @@ yt921x_dsa_port_change_mtu(struct dsa_switch *ds, int port, int new_mtu)
|
|||
* maximum after reset
|
||||
*/
|
||||
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct dsa_port *dp = dsa_to_port(ds, port);
|
||||
int frame_size;
|
||||
int res;
|
||||
|
|
@ -697,7 +334,7 @@ yt921x_marker_tfm(struct yt921x_marker *marker, u64 rate, u64 burst,
|
|||
{
|
||||
const int C = flags & YT921X_MARKER_PKT_MODE ? YT921X_TOKEN_PKT_C :
|
||||
YT921X_TOKEN_BYTE_C;
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct yt921x_marker m;
|
||||
u64 burst_est;
|
||||
u64 burst_sug;
|
||||
|
|
@ -873,8 +510,8 @@ yt921x_meter_config(struct yt921x_priv *priv, unsigned int id,
|
|||
|
||||
static void yt921x_dsa_port_policer_del(struct dsa_switch *ds, int port)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct device *dev = to_device(priv);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
|
@ -891,7 +528,7 @@ yt921x_dsa_port_policer_add(struct dsa_switch *ds, int port,
|
|||
const struct flow_action_police *police,
|
||||
struct netlink_ext_ack *extack)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_marker marker;
|
||||
u32 ctrl;
|
||||
int res;
|
||||
|
|
@ -921,7 +558,7 @@ static int
|
|||
yt921x_dsa_port_setup_tc_tbf_port(struct dsa_switch *ds, int port,
|
||||
const struct tc_tbf_qopt_offload *qopt)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct netlink_ext_ack *extack = qopt->extack;
|
||||
u32 ctrls[2];
|
||||
int res;
|
||||
|
|
@ -1970,7 +1607,7 @@ static int
|
|||
yt921x_dsa_cls_flower_del(struct dsa_switch *ds, int port,
|
||||
struct flow_cls_offload *cls, bool ingress)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
|
@ -1985,7 +1622,7 @@ yt921x_dsa_cls_flower_add(struct dsa_switch *ds, int port,
|
|||
struct flow_cls_offload *cls, bool ingress)
|
||||
{
|
||||
struct netlink_ext_ack *extack = cls->common.extack;
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_acl_rule_ext ruleext;
|
||||
int res;
|
||||
|
||||
|
|
@ -2056,8 +1693,8 @@ static void
|
|||
yt921x_dsa_port_mirror_del(struct dsa_switch *ds, int port,
|
||||
struct dsa_mall_mirror_tc_entry *mirror)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct device *dev = to_device(priv);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
|
@ -2074,7 +1711,7 @@ yt921x_dsa_port_mirror_add(struct dsa_switch *ds, int port,
|
|||
struct dsa_mall_mirror_tc_entry *mirror,
|
||||
bool ingress, struct netlink_ext_ack *extack)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
|
@ -2143,7 +1780,7 @@ static int yt921x_lag_set(struct yt921x_priv *priv, u8 index, u16 ports_mask)
|
|||
static int
|
||||
yt921x_dsa_port_lag_leave(struct dsa_switch *ds, int port, struct dsa_lag lag)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct dsa_port *dp;
|
||||
u32 ctrl;
|
||||
int res;
|
||||
|
|
@ -2206,7 +1843,7 @@ yt921x_dsa_port_lag_join(struct dsa_switch *ds, int port, struct dsa_lag lag,
|
|||
struct netdev_lag_upper_info *info,
|
||||
struct netlink_ext_ack *extack)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct dsa_port *dp;
|
||||
bool unique_lag;
|
||||
unsigned int i;
|
||||
|
|
@ -2269,7 +1906,7 @@ yt921x_dsa_port_lag_join(struct dsa_switch *ds, int port, struct dsa_lag lag,
|
|||
|
||||
static int yt921x_fdb_wait(struct yt921x_priv *priv, u32 *valp)
|
||||
{
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
u32 val = YT921X_FDB_RESULT_DONE;
|
||||
int res;
|
||||
|
||||
|
|
@ -2338,7 +1975,7 @@ static int
|
|||
yt921x_fdb_read(struct yt921x_priv *priv, unsigned char *addr, u16 *vidp,
|
||||
u16 *ports_maskp, u16 *indexp, u8 *statusp)
|
||||
{
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
u16 index;
|
||||
u32 data0;
|
||||
u32 data1;
|
||||
|
|
@ -2629,7 +2266,7 @@ static int
|
|||
yt921x_dsa_port_fdb_dump(struct dsa_switch *ds, int port,
|
||||
dsa_fdb_dump_cb_t *cb, void *data)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
|
@ -2644,8 +2281,8 @@ yt921x_dsa_port_fdb_dump(struct dsa_switch *ds, int port,
|
|||
|
||||
static void yt921x_dsa_port_fast_age(struct dsa_switch *ds, int port)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct device *dev = to_device(priv);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
|
@ -2660,7 +2297,7 @@ static void yt921x_dsa_port_fast_age(struct dsa_switch *ds, int port)
|
|||
static int
|
||||
yt921x_dsa_set_ageing_time(struct dsa_switch *ds, unsigned int msecs)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u32 ctrl;
|
||||
int res;
|
||||
|
||||
|
|
@ -2678,7 +2315,7 @@ static int
|
|||
yt921x_dsa_port_fdb_del(struct dsa_switch *ds, int port,
|
||||
const unsigned char *addr, u16 vid, struct dsa_db db)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
|
@ -2692,7 +2329,7 @@ static int
|
|||
yt921x_dsa_port_fdb_add(struct dsa_switch *ds, int port,
|
||||
const unsigned char *addr, u16 vid, struct dsa_db db)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
|
@ -2707,7 +2344,7 @@ yt921x_dsa_port_mdb_del(struct dsa_switch *ds, int port,
|
|||
const struct switchdev_obj_port_mdb *mdb,
|
||||
struct dsa_db db)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
const unsigned char *addr = mdb->addr;
|
||||
u16 vid = mdb->vid;
|
||||
int res;
|
||||
|
|
@ -2724,7 +2361,7 @@ yt921x_dsa_port_mdb_add(struct dsa_switch *ds, int port,
|
|||
const struct switchdev_obj_port_mdb *mdb,
|
||||
struct dsa_db db)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
const unsigned char *addr = mdb->addr;
|
||||
u16 vid = mdb->vid;
|
||||
int res;
|
||||
|
|
@ -2889,7 +2526,7 @@ yt921x_dsa_port_vlan_filtering(struct dsa_switch *ds, int port,
|
|||
bool vlan_filtering,
|
||||
struct netlink_ext_ack *extack)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
int res;
|
||||
|
||||
if (dsa_is_cpu_port(ds, port))
|
||||
|
|
@ -2906,7 +2543,7 @@ static int
|
|||
yt921x_dsa_port_vlan_del(struct dsa_switch *ds, int port,
|
||||
const struct switchdev_obj_port_vlan *vlan)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u16 vid = vlan->vid;
|
||||
u16 pvid;
|
||||
int res;
|
||||
|
|
@ -2940,7 +2577,7 @@ yt921x_dsa_port_vlan_add(struct dsa_switch *ds, int port,
|
|||
const struct switchdev_obj_port_vlan *vlan,
|
||||
struct netlink_ext_ack *extack)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u16 vid = vlan->vid;
|
||||
u16 pvid;
|
||||
int res;
|
||||
|
|
@ -3185,7 +2822,7 @@ yt921x_dsa_port_bridge_flags(struct dsa_switch *ds, int port,
|
|||
struct switchdev_brport_flags flags,
|
||||
struct netlink_ext_ack *extack)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
int res;
|
||||
|
||||
if (dsa_is_cpu_port(ds, port))
|
||||
|
|
@ -3202,8 +2839,8 @@ static void
|
|||
yt921x_dsa_port_bridge_leave(struct dsa_switch *ds, int port,
|
||||
struct dsa_bridge bridge)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct device *dev = to_device(priv);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
int res;
|
||||
|
||||
if (dsa_is_cpu_port(ds, port))
|
||||
|
|
@ -3223,7 +2860,7 @@ yt921x_dsa_port_bridge_join(struct dsa_switch *ds, int port,
|
|||
struct dsa_bridge bridge, bool *tx_fwd_offload,
|
||||
struct netlink_ext_ack *extack)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u16 ports_mask;
|
||||
int res;
|
||||
|
||||
|
|
@ -3244,7 +2881,7 @@ static int
|
|||
yt921x_dsa_port_mst_state_set(struct dsa_switch *ds, int port,
|
||||
const struct switchdev_mst_state *st)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u32 mask;
|
||||
u32 ctrl;
|
||||
int res;
|
||||
|
|
@ -3278,7 +2915,7 @@ static int
|
|||
yt921x_dsa_vlan_msti_set(struct dsa_switch *ds, struct dsa_bridge bridge,
|
||||
const struct switchdev_vlan_msti *msti)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u32 masks[2];
|
||||
u32 ctrls[2];
|
||||
int res;
|
||||
|
|
@ -3304,9 +2941,9 @@ yt921x_dsa_vlan_msti_set(struct dsa_switch *ds, struct dsa_bridge bridge,
|
|||
static void
|
||||
yt921x_dsa_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct dsa_port *dp = dsa_to_port(ds, port);
|
||||
struct device *dev = to_device(priv);
|
||||
bool learning;
|
||||
u32 mask;
|
||||
u32 ctrl;
|
||||
|
|
@ -3356,7 +2993,7 @@ yt921x_dsa_port_stp_state_set(struct dsa_switch *ds, int port, u8 state)
|
|||
static int __maybe_unused
|
||||
yt921x_dsa_port_get_default_prio(struct dsa_switch *ds, int port)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u32 val;
|
||||
int res;
|
||||
|
||||
|
|
@ -3373,7 +3010,7 @@ yt921x_dsa_port_get_default_prio(struct dsa_switch *ds, int port)
|
|||
static int __maybe_unused
|
||||
yt921x_dsa_port_set_default_prio(struct dsa_switch *ds, int port, u8 prio)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u32 mask;
|
||||
u32 ctrl;
|
||||
int res;
|
||||
|
|
@ -3399,7 +3036,7 @@ static int __maybe_unused
|
|||
yt921x_dsa_port_get_apptrust(struct dsa_switch *ds, int port, u8 *sel,
|
||||
int *nselp)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u8 appprios[2][2] = {};
|
||||
int nsel;
|
||||
u32 val;
|
||||
|
|
@ -3433,8 +3070,8 @@ static int __maybe_unused
|
|||
yt921x_dsa_port_set_apptrust(struct dsa_switch *ds, int port, const u8 *sel,
|
||||
int nsel)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct device *dev = to_device(priv);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
u32 ctrl;
|
||||
int res;
|
||||
|
||||
|
|
@ -3574,9 +3211,9 @@ static int
|
|||
yt921x_port_config(struct yt921x_priv *priv, int port, unsigned int mode,
|
||||
phy_interface_t interface)
|
||||
{
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
const struct yt921x_info *info = priv->info;
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct device *dev = to_device(priv);
|
||||
u32 mask;
|
||||
int res;
|
||||
|
||||
|
|
@ -3628,7 +3265,7 @@ yt921x_phylink_mac_select_pcs(struct phylink_config *config,
|
|||
phy_interface_t interface)
|
||||
{
|
||||
struct dsa_port *dp = dsa_phylink_to_port(config);
|
||||
struct yt921x_priv *priv = to_yt921x_priv(dp->ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(dp->ds);
|
||||
const struct yt921x_info *info = priv->info;
|
||||
int port = dp->index;
|
||||
|
||||
|
|
@ -3651,12 +3288,15 @@ yt921x_phylink_mac_link_down(struct phylink_config *config, unsigned int mode,
|
|||
phy_interface_t interface)
|
||||
{
|
||||
struct dsa_port *dp = dsa_phylink_to_port(config);
|
||||
struct yt921x_priv *priv = to_yt921x_priv(dp->ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(dp->ds);
|
||||
struct yt921x_mib *pm;
|
||||
int port = dp->index;
|
||||
int res;
|
||||
|
||||
/* No need to sync; port control block is hold until device remove */
|
||||
cancel_delayed_work(&priv->ports[port].mib_read);
|
||||
pm = priv->ports[port].mib;
|
||||
if (pm)
|
||||
cancel_delayed_work(&pm->work);
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
res = yt921x_port_down(priv, port);
|
||||
|
|
@ -3674,7 +3314,8 @@ yt921x_phylink_mac_link_up(struct phylink_config *config,
|
|||
bool tx_pause, bool rx_pause)
|
||||
{
|
||||
struct dsa_port *dp = dsa_phylink_to_port(config);
|
||||
struct yt921x_priv *priv = to_yt921x_priv(dp->ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(dp->ds);
|
||||
struct yt921x_mib *pm;
|
||||
int port = dp->index;
|
||||
int res;
|
||||
|
||||
|
|
@ -3687,7 +3328,9 @@ yt921x_phylink_mac_link_up(struct phylink_config *config,
|
|||
dev_err(dp->ds->dev, "Failed to %s port %d: %i\n", "bring up",
|
||||
port, res);
|
||||
|
||||
schedule_delayed_work(&priv->ports[port].mib_read, 0);
|
||||
pm = priv->ports[port].mib;
|
||||
if (pm)
|
||||
schedule_delayed_work(&pm->work, 0);
|
||||
}
|
||||
|
||||
static void
|
||||
|
|
@ -3695,7 +3338,7 @@ yt921x_phylink_mac_config(struct phylink_config *config, unsigned int mode,
|
|||
const struct phylink_link_state *state)
|
||||
{
|
||||
struct dsa_port *dp = dsa_phylink_to_port(config);
|
||||
struct yt921x_priv *priv = to_yt921x_priv(dp->ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(dp->ds);
|
||||
int port = dp->index;
|
||||
int res;
|
||||
|
||||
|
|
@ -3712,7 +3355,7 @@ static void
|
|||
yt921x_dsa_phylink_get_caps(struct dsa_switch *ds, int port,
|
||||
struct phylink_config *config)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
const struct yt921x_info *info = priv->info;
|
||||
|
||||
config->mac_capabilities = MAC_ASYM_PAUSE | MAC_SYM_PAUSE |
|
||||
|
|
@ -3801,23 +3444,60 @@ yt921x_dsa_get_tag_protocol(struct dsa_switch *ds, int port,
|
|||
return DSA_TAG_PROTO_YT921X;
|
||||
}
|
||||
|
||||
static void yt921x_dsa_port_teardown(struct dsa_switch *ds, int port)
|
||||
{
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *pm = pp->mib;
|
||||
|
||||
/* get_stats64() might not be synchronized with port_teardown(), hold
|
||||
* the MIB block till the device teardown
|
||||
*/
|
||||
if (pm)
|
||||
disable_delayed_work_sync(&pm->work);
|
||||
}
|
||||
|
||||
static int yt921x_dsa_port_setup(struct dsa_switch *ds, int port)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
const struct yt921x_info *info = priv->info;
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct yt921x_mib *pm = pp->mib;
|
||||
int res;
|
||||
|
||||
if (!pm && (BIT(port) & yt921x_info_ports_mask(info))) {
|
||||
pm = devm_kzalloc(dev, sizeof(*pm), GFP_KERNEL);
|
||||
if (!pm)
|
||||
return -ENOMEM;
|
||||
pp->mib = pm;
|
||||
|
||||
pm->port = pp;
|
||||
u64_stats_init(&pm->syncp);
|
||||
INIT_DELAYED_WORK(&pm->work, yt921x_mib_poll);
|
||||
/* Start disabled, so that the enable below always pairs with
|
||||
* either this disable or the one from a previous teardown
|
||||
*/
|
||||
disable_delayed_work_sync(&pm->work);
|
||||
}
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
res = yt921x_port_setup(priv, port);
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
if (res)
|
||||
return res;
|
||||
|
||||
return res;
|
||||
if (pm)
|
||||
enable_delayed_work(&pm->work);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/* Not "port" - DSCP mapping is global */
|
||||
static int __maybe_unused
|
||||
yt921x_dsa_port_get_dscp_prio(struct dsa_switch *ds, int port, u8 dscp)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u32 val;
|
||||
int res;
|
||||
|
||||
|
|
@ -3834,7 +3514,7 @@ yt921x_dsa_port_get_dscp_prio(struct dsa_switch *ds, int port, u8 dscp)
|
|||
static int __maybe_unused
|
||||
yt921x_dsa_port_del_dscp_prio(struct dsa_switch *ds, int port, u8 dscp, u8 prio)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
u32 val;
|
||||
int res;
|
||||
|
||||
|
|
@ -3859,7 +3539,7 @@ yt921x_dsa_port_del_dscp_prio(struct dsa_switch *ds, int port, u8 dscp, u8 prio)
|
|||
static int __maybe_unused
|
||||
yt921x_dsa_port_add_dscp_prio(struct dsa_switch *ds, int port, u8 dscp, u8 prio)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
int res;
|
||||
|
||||
if (prio >= YT921X_PRIO_NUM)
|
||||
|
|
@ -3920,7 +3600,7 @@ static int yt921x_edata_read(struct yt921x_priv *priv, u8 addr, u8 *valp)
|
|||
static void yt921x_dsa_teardown(struct dsa_switch *ds)
|
||||
{
|
||||
#if IS_ENABLED(CONFIG_NET_DSA_YT921X_LEDS)
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
|
||||
yt921x_leds_remove(priv);
|
||||
#endif
|
||||
|
|
@ -3928,7 +3608,7 @@ static void yt921x_dsa_teardown(struct dsa_switch *ds)
|
|||
|
||||
static int yt921x_chip_detect(struct yt921x_priv *priv)
|
||||
{
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
const struct yt921x_info *info;
|
||||
u8 extmode;
|
||||
u32 chipid;
|
||||
|
|
@ -3995,7 +3675,7 @@ static int yt921x_chip_detect(struct yt921x_priv *priv)
|
|||
|
||||
static int yt921x_chip_reset(struct yt921x_priv *priv)
|
||||
{
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
u16 eth_p_tag;
|
||||
u32 val;
|
||||
int res;
|
||||
|
|
@ -4243,8 +3923,8 @@ static int yt921x_chip_setup(struct yt921x_priv *priv)
|
|||
|
||||
static int yt921x_dsa_setup(struct dsa_switch *ds)
|
||||
{
|
||||
struct yt921x_priv *priv = to_yt921x_priv(ds);
|
||||
struct device *dev = to_device(priv);
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct device_node *np = dev->of_node;
|
||||
struct device_node *child;
|
||||
unsigned long mask;
|
||||
|
|
@ -4385,6 +4065,7 @@ static const struct dsa_switch_ops yt921x_dsa_switch_ops = {
|
|||
/* port */
|
||||
.get_tag_protocol = yt921x_dsa_get_tag_protocol,
|
||||
.phylink_get_caps = yt921x_dsa_phylink_get_caps,
|
||||
.port_teardown = yt921x_dsa_port_teardown,
|
||||
.port_setup = yt921x_dsa_port_setup,
|
||||
#if IS_ENABLED(CONFIG_DCB)
|
||||
/* dscp */
|
||||
|
|
@ -4414,12 +4095,6 @@ static void yt921x_mdio_remove(struct mdio_device *mdiodev)
|
|||
if (!priv)
|
||||
return;
|
||||
|
||||
for (size_t i = ARRAY_SIZE(priv->ports); i-- > 0; ) {
|
||||
struct yt921x_port *pp = &priv->ports[i];
|
||||
|
||||
disable_delayed_work_sync(&pp->mib_read);
|
||||
}
|
||||
|
||||
dsa_unregister_switch(&priv->ds);
|
||||
|
||||
for (unsigned int i = 0; i < ARRAY_SIZE(priv->acl_blks); i++) {
|
||||
|
|
@ -4467,7 +4142,6 @@ static int yt921x_mdio_probe(struct mdio_device *mdiodev)
|
|||
struct yt921x_port *pp = &priv->ports[i];
|
||||
|
||||
pp->index = i;
|
||||
INIT_DELAYED_WORK(&pp->mib_read, yt921x_poll_mib);
|
||||
}
|
||||
|
||||
ds = &priv->ds;
|
||||
|
|
|
|||
|
|
@ -163,69 +163,6 @@ enum yt921x_speed {
|
|||
#define YT921X_EEE_CTRL 0xb0000
|
||||
#define YT921X_EEE_CTRL_ENn(port) BIT(port)
|
||||
|
||||
#define YT921X_MIB_CTRL 0xc0004
|
||||
#define YT921X_MIB_CTRL_CLEAN BIT(30)
|
||||
#define YT921X_MIB_CTRL_PORT_M GENMASK(6, 3)
|
||||
#define YT921X_MIB_CTRL_PORT(x) FIELD_PREP(YT921X_MIB_CTRL_PORT_M, (x))
|
||||
#define YT921X_MIB_CTRL_ONE_PORT BIT(1)
|
||||
#define YT921X_MIB_CTRL_ALL_PORT BIT(0)
|
||||
#define YT921X_MIBn_DATA0(port) (0xc0100 + 0x100 * (port))
|
||||
#define YT921X_MIBn_DATAm(port, x) (YT921X_MIBn_DATA0(port) + 4 * (x))
|
||||
#define YT921X_MIB_DATA_RX_BROADCAST 0x00
|
||||
#define YT921X_MIB_DATA_RX_PAUSE 0x04
|
||||
#define YT921X_MIB_DATA_RX_MULTICAST 0x08
|
||||
#define YT921X_MIB_DATA_RX_CRC_ERR 0x0c
|
||||
|
||||
#define YT921X_MIB_DATA_RX_ALIGN_ERR 0x10
|
||||
#define YT921X_MIB_DATA_RX_UNDERSIZE_ERR 0x14
|
||||
#define YT921X_MIB_DATA_RX_FRAG_ERR 0x18
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_64 0x1c
|
||||
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_65_TO_127 0x20
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_128_TO_255 0x24
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_256_TO_511 0x28
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_512_TO_1023 0x2c
|
||||
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_1024_TO_1518 0x30
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_1519_TO_MAX 0x34
|
||||
/* 0x38: unused */
|
||||
#define YT921X_MIB_DATA_RX_GOOD_BYTES 0x3c
|
||||
|
||||
/* 0x40: 64 bytes */
|
||||
#define YT921X_MIB_DATA_RX_BAD_BYTES 0x44
|
||||
/* 0x48: 64 bytes */
|
||||
#define YT921X_MIB_DATA_RX_OVERSIZE_ERR 0x4c
|
||||
|
||||
#define YT921X_MIB_DATA_RX_DROPPED 0x50
|
||||
#define YT921X_MIB_DATA_TX_BROADCAST 0x54
|
||||
#define YT921X_MIB_DATA_TX_PAUSE 0x58
|
||||
#define YT921X_MIB_DATA_TX_MULTICAST 0x5c
|
||||
|
||||
#define YT921X_MIB_DATA_TX_UNDERSIZE_ERR 0x60
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_64 0x64
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_65_TO_127 0x68
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_128_TO_255 0x6c
|
||||
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_256_TO_511 0x70
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_512_TO_1023 0x74
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_1024_TO_1518 0x78
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_1519_TO_MAX 0x7c
|
||||
|
||||
/* 0x80: unused */
|
||||
#define YT921X_MIB_DATA_TX_GOOD_BYTES 0x84
|
||||
/* 0x88: 64 bytes */
|
||||
#define YT921X_MIB_DATA_TX_COLLISION 0x8c
|
||||
|
||||
#define YT921X_MIB_DATA_TX_EXCESSIVE_COLLISION 0x90
|
||||
#define YT921X_MIB_DATA_TX_MULTIPLE_COLLISION 0x94
|
||||
#define YT921X_MIB_DATA_TX_SINGLE_COLLISION 0x98
|
||||
#define YT921X_MIB_DATA_TX_PKT 0x9c
|
||||
|
||||
#define YT921X_MIB_DATA_TX_DEFERRED 0xa0
|
||||
#define YT921X_MIB_DATA_TX_LATE_COLLISION 0xa4
|
||||
#define YT921X_MIB_DATA_RX_OAM 0xa8
|
||||
#define YT921X_MIB_DATA_TX_OAM 0xac
|
||||
|
||||
#define YT921X_EDATA_CTRL 0xe0000
|
||||
#define YT921X_EDATA_CTRL_ADDR_M GENMASK(15, 8)
|
||||
#define YT921X_EDATA_CTRL_ADDR(x) FIELD_PREP(YT921X_EDATA_CTRL_ADDR_M, (x))
|
||||
|
|
@ -833,58 +770,6 @@ enum yt921x_fdb_entry_status {
|
|||
|
||||
#define YT921X_NAME "yt921x"
|
||||
|
||||
struct yt921x_mib {
|
||||
u64 rx_broadcast;
|
||||
u64 rx_pause;
|
||||
u64 rx_multicast;
|
||||
u64 rx_crc_errors;
|
||||
|
||||
u64 rx_alignment_errors;
|
||||
u64 rx_undersize_errors;
|
||||
u64 rx_fragment_errors;
|
||||
u64 rx_64byte;
|
||||
|
||||
u64 rx_65_127byte;
|
||||
u64 rx_128_255byte;
|
||||
u64 rx_256_511byte;
|
||||
u64 rx_512_1023byte;
|
||||
|
||||
u64 rx_1024_1518byte;
|
||||
u64 rx_jumbo;
|
||||
u64 rx_good_bytes;
|
||||
|
||||
u64 rx_bad_bytes;
|
||||
u64 rx_oversize_errors;
|
||||
|
||||
u64 rx_dropped;
|
||||
u64 tx_broadcast;
|
||||
u64 tx_pause;
|
||||
u64 tx_multicast;
|
||||
|
||||
u64 tx_undersize_errors;
|
||||
u64 tx_64byte;
|
||||
u64 tx_65_127byte;
|
||||
u64 tx_128_255byte;
|
||||
|
||||
u64 tx_256_511byte;
|
||||
u64 tx_512_1023byte;
|
||||
u64 tx_1024_1518byte;
|
||||
u64 tx_jumbo;
|
||||
|
||||
u64 tx_good_bytes;
|
||||
u64 tx_collisions;
|
||||
|
||||
u64 tx_aborted_errors;
|
||||
u64 tx_multiple_collisions;
|
||||
u64 tx_single_collisions;
|
||||
u64 tx_good;
|
||||
|
||||
u64 tx_deferred;
|
||||
u64 tx_late_collisions;
|
||||
u64 rx_oam;
|
||||
u64 tx_oam;
|
||||
};
|
||||
|
||||
struct yt921x_acl_entry {
|
||||
u32 key[2];
|
||||
u32 mask[2];
|
||||
|
|
@ -917,11 +802,6 @@ struct yt921x_port {
|
|||
/* BR_ISOLATED */
|
||||
bool isolated:1;
|
||||
|
||||
struct delayed_work mib_read;
|
||||
struct yt921x_mib mib;
|
||||
u64 rx_frames;
|
||||
u64 tx_frames;
|
||||
|
||||
#if IS_ENABLED(CONFIG_NET_DSA_YT921X_LEDS)
|
||||
unsigned char led_duty;
|
||||
unsigned short led_cycle;
|
||||
|
|
@ -932,6 +812,7 @@ struct yt921x_port {
|
|||
struct yt921x_led *leds[YT921X_LED_GROUP_NUM];
|
||||
#endif
|
||||
|
||||
struct yt921x_mib *mib;
|
||||
struct phylink_pcs pcs;
|
||||
};
|
||||
|
||||
|
|
@ -955,6 +836,11 @@ struct yt921x_info {
|
|||
u16 serdes_mask;
|
||||
};
|
||||
|
||||
static inline u16 yt921x_info_ports_mask(const struct yt921x_info *info)
|
||||
{
|
||||
return info->internal_mask | info->xmii_mask | info->serdes_mask;
|
||||
}
|
||||
|
||||
struct yt921x_priv {
|
||||
struct dsa_switch ds;
|
||||
|
||||
|
|
@ -984,8 +870,10 @@ struct yt921x_priv {
|
|||
struct yt921x_acl_blk *acl_blks[YT921X_ACL_BLK_NUM];
|
||||
};
|
||||
|
||||
#define dsa_to_yt921x_priv(_ds) container_of_const(_ds, struct yt921x_priv, ds)
|
||||
#define yt921x_port_to_priv(pp) \
|
||||
container_of_const((pp), struct yt921x_priv, ports[(pp)->index])
|
||||
#define yt921x_priv_to_device(priv) ((priv)->ds.dev)
|
||||
|
||||
static inline int ethtool_speed_to_yt921x(int speed)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -12,7 +12,6 @@
|
|||
#define to_yt921x_led(led_cdev) \
|
||||
container_of_const((led_cdev), struct yt921x_led, cdev)
|
||||
#define to_yt921x_port(led) ((led)->port)
|
||||
#define to_device(priv) ((priv)->ds.dev)
|
||||
|
||||
static u32 yt921x_led_regaddr(struct yt921x_priv *priv, int port, int group)
|
||||
{
|
||||
|
|
@ -413,8 +412,8 @@ static int
|
|||
yt921x_led_setup(struct yt921x_priv *priv, int port,
|
||||
struct fwnode_handle *fwnode)
|
||||
{
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct device *dev = to_device(priv);
|
||||
struct led_init_data init_data;
|
||||
struct led_classdev *led_cdev;
|
||||
char name[LED_MAX_NAME_SIZE];
|
||||
|
|
@ -583,8 +582,8 @@ yt921x_led_setup(struct yt921x_priv *priv, int port,
|
|||
|
||||
static void yt921x_leds_remove_port(struct yt921x_priv *priv, int port)
|
||||
{
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct device *dev = to_device(priv);
|
||||
|
||||
for (int group = 0; group < YT921X_LED_GROUP_NUM; group++) {
|
||||
struct yt921x_led *led = pp->leds[group];
|
||||
|
|
@ -602,7 +601,7 @@ static void yt921x_leds_remove_port(struct yt921x_priv *priv, int port)
|
|||
|
||||
static int yt921x_leds_setup_port(struct yt921x_priv *priv, int port)
|
||||
{
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct dsa_switch *ds = &priv->ds;
|
||||
struct device_node *leds_np;
|
||||
struct dsa_port *dp;
|
||||
|
|
|
|||
|
|
@ -9,8 +9,6 @@
|
|||
#include "mdio_bus.h"
|
||||
#include "smi.h"
|
||||
|
||||
#define to_device(priv) ((priv)->ds.dev)
|
||||
|
||||
static int yt921x_intif_wait(struct yt921x_priv *priv)
|
||||
{
|
||||
u32 val = 0;
|
||||
|
|
@ -21,7 +19,7 @@ static int yt921x_intif_wait(struct yt921x_priv *priv)
|
|||
|
||||
int yt921x_intif_read(struct yt921x_priv *priv, int port, int reg, u16 *valp)
|
||||
{
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
u32 mask;
|
||||
u32 ctrl;
|
||||
u32 val;
|
||||
|
|
@ -145,7 +143,7 @@ yt921x_mbus_int_write(struct mii_bus *mbus, int port, int reg, u16 data)
|
|||
|
||||
int yt921x_mbus_int_init(struct yt921x_priv *priv, struct device_node *mnp)
|
||||
{
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct mii_bus *mbus;
|
||||
int res;
|
||||
|
||||
|
|
@ -181,7 +179,7 @@ static int yt921x_extif_wait(struct yt921x_priv *priv)
|
|||
static int
|
||||
yt921x_extif_read(struct yt921x_priv *priv, int port, int reg, u16 *valp)
|
||||
{
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
u32 mask;
|
||||
u32 ctrl;
|
||||
u32 val;
|
||||
|
|
@ -275,7 +273,7 @@ yt921x_mbus_ext_write(struct mii_bus *mbus, int port, int reg, u16 data)
|
|||
|
||||
int yt921x_mbus_ext_init(struct yt921x_priv *priv, struct device_node *mnp)
|
||||
{
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct mii_bus *mbus;
|
||||
int res;
|
||||
|
||||
|
|
|
|||
431
drivers/net/dsa/motorcomm/mib.c
Normal file
431
drivers/net/dsa/motorcomm/mib.c
Normal file
|
|
@ -0,0 +1,431 @@
|
|||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
/*
|
||||
* Copyright (c) 2026 David Yang
|
||||
*/
|
||||
|
||||
#include "chip.h"
|
||||
#include "mib.h"
|
||||
#include "smi.h"
|
||||
|
||||
struct yt921x_mib_desc {
|
||||
unsigned int size;
|
||||
unsigned int offset;
|
||||
const char *name;
|
||||
};
|
||||
|
||||
#define MIB_DESC(_size, _offset, _name) \
|
||||
{_size, _offset, _name}
|
||||
|
||||
/* Must agree with yt921x_mib_stats
|
||||
*
|
||||
* Unstructured fields (name != NULL) will appear in get_ethtool_stats(),
|
||||
* structured go to their *_stats() methods, but we need their sizes and offsets
|
||||
* to perform 32bit MIB overflow wraparound.
|
||||
*/
|
||||
static const struct yt921x_mib_desc yt921x_mib_descs[] = {
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_BROADCAST, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PAUSE, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_MULTICAST, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_CRC_ERR, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_ALIGN_ERR, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_UNDERSIZE_ERR, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_FRAG_ERR, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_64, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_65_TO_127, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_128_TO_255, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_256_TO_511, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_512_TO_1023, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_1024_TO_1518, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_PKT_SZ_1519_TO_MAX, NULL),
|
||||
MIB_DESC(2, YT921X_MIB_DATA_RX_GOOD_BYTES, NULL),
|
||||
|
||||
MIB_DESC(2, YT921X_MIB_DATA_RX_BAD_BYTES, "RxBadBytes"),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_OVERSIZE_ERR, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_DROPPED, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_BROADCAST, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PAUSE, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_MULTICAST, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_UNDERSIZE_ERR, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_64, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_65_TO_127, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_128_TO_255, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_256_TO_511, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_512_TO_1023, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_1024_TO_1518, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT_SZ_1519_TO_MAX, NULL),
|
||||
|
||||
MIB_DESC(2, YT921X_MIB_DATA_TX_GOOD_BYTES, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_COLLISION, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_EXCESSIVE_COLLISION, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_MULTIPLE_COLLISION, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_SINGLE_COLLISION, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_PKT, NULL),
|
||||
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_DEFERRED, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_LATE_COLLISION, NULL),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_RX_OAM, "RxOAM"),
|
||||
MIB_DESC(1, YT921X_MIB_DATA_TX_OAM, "TxOAM"),
|
||||
};
|
||||
|
||||
static_assert(ARRAY_SIZE(yt921x_mib_descs) == YT921X_MIB_STAT_NUM);
|
||||
|
||||
/* The interval should be small enough to avoid overflow of 32bit MIBs.
|
||||
*
|
||||
* Until we can read MIBs from stats64 call directly (i.e. sleep
|
||||
* there), we have to poll stats more frequently then it is actually needed.
|
||||
* For overflow protection, normally, 100 sec interval should have been OK.
|
||||
*/
|
||||
#define YT921X_STATS_INTERVAL_JIFFIES (3 * HZ)
|
||||
|
||||
/* Read and handle overflow of 32bit MIBs. MIB buffer must be zeroed before. */
|
||||
static int yt921x_mib_read(struct yt921x_priv *priv, int port)
|
||||
{
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *pm = pp->mib;
|
||||
struct yt921x_mib_stats *mib;
|
||||
u64 *buf = pm->data;
|
||||
unsigned long flags;
|
||||
u64 rx_frames;
|
||||
u64 tx_frames;
|
||||
int res = 0;
|
||||
|
||||
mib = &pm->stats;
|
||||
|
||||
for (size_t i = 0; i < ARRAY_SIZE(yt921x_mib_descs); i++) {
|
||||
const struct yt921x_mib_desc *desc = &yt921x_mib_descs[i];
|
||||
u32 reg = YT921X_MIBn_DATA0(port) + desc->offset;
|
||||
u32 val0;
|
||||
u64 val;
|
||||
|
||||
res = yt921x_reg_read(priv, reg, &val0);
|
||||
if (res)
|
||||
break;
|
||||
|
||||
if (desc->size <= 1) {
|
||||
u64 old_val = buf[i];
|
||||
|
||||
val = (old_val & ~(u64)U32_MAX) | val0;
|
||||
if (val < old_val)
|
||||
val += 1ull << 32;
|
||||
} else {
|
||||
u32 val1;
|
||||
|
||||
res = yt921x_reg_read(priv, reg + 4, &val1);
|
||||
if (res)
|
||||
break;
|
||||
val = ((u64)val1 << 32) | val0;
|
||||
}
|
||||
|
||||
buf[i] = val;
|
||||
}
|
||||
|
||||
flags = u64_stats_update_begin_irqsave(&pm->syncp);
|
||||
for (size_t i = 0; i < ARRAY_SIZE(yt921x_mib_descs); i++)
|
||||
u64_stats_set(&((u64_stats_t *)mib)[i], buf[i]);
|
||||
rx_frames = u64_stats_read(&mib->rx_64byte) +
|
||||
u64_stats_read(&mib->rx_65_127byte) +
|
||||
u64_stats_read(&mib->rx_128_255byte) +
|
||||
u64_stats_read(&mib->rx_256_511byte) +
|
||||
u64_stats_read(&mib->rx_512_1023byte) +
|
||||
u64_stats_read(&mib->rx_1024_1518byte) +
|
||||
u64_stats_read(&mib->rx_jumbo);
|
||||
tx_frames = u64_stats_read(&mib->tx_64byte) +
|
||||
u64_stats_read(&mib->tx_65_127byte) +
|
||||
u64_stats_read(&mib->tx_128_255byte) +
|
||||
u64_stats_read(&mib->tx_256_511byte) +
|
||||
u64_stats_read(&mib->tx_512_1023byte) +
|
||||
u64_stats_read(&mib->tx_1024_1518byte) +
|
||||
u64_stats_read(&mib->tx_jumbo);
|
||||
u64_stats_set(&pm->rx_frames, rx_frames);
|
||||
u64_stats_set(&pm->tx_frames, tx_frames);
|
||||
u64_stats_update_end_irqrestore(&pm->syncp, flags);
|
||||
|
||||
if (res)
|
||||
dev_err(dev, "Failed to %s port %d: %i\n", "read stats for",
|
||||
port, res);
|
||||
return res;
|
||||
}
|
||||
|
||||
void yt921x_mib_poll(struct work_struct *work)
|
||||
{
|
||||
struct yt921x_mib *pm = container_of_const(work, struct yt921x_mib,
|
||||
work.work);
|
||||
struct yt921x_port *pp = pm->port;
|
||||
unsigned long delay = YT921X_STATS_INTERVAL_JIFFIES;
|
||||
struct yt921x_priv *priv = yt921x_port_to_priv(pp);
|
||||
int port = pp->index;
|
||||
int res;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
res = yt921x_mib_read(priv, port);
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
if (res)
|
||||
delay *= 4;
|
||||
|
||||
schedule_delayed_work(&pm->work, delay);
|
||||
}
|
||||
|
||||
void
|
||||
yt921x_dsa_get_strings(struct dsa_switch *ds, int port, u32 stringset,
|
||||
uint8_t *data)
|
||||
{
|
||||
if (stringset != ETH_SS_STATS)
|
||||
return;
|
||||
|
||||
for (size_t i = 0; i < ARRAY_SIZE(yt921x_mib_descs); i++) {
|
||||
const struct yt921x_mib_desc *desc = &yt921x_mib_descs[i];
|
||||
|
||||
if (desc->name)
|
||||
ethtool_puts(&data, desc->name);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
yt921x_dsa_get_ethtool_stats(struct dsa_switch *ds, int port, uint64_t *data)
|
||||
{
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *pm = pp->mib;
|
||||
u64 *buf;
|
||||
size_t j;
|
||||
|
||||
if (!pm)
|
||||
return;
|
||||
buf = pm->data;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
||||
yt921x_mib_read(priv, port);
|
||||
|
||||
j = 0;
|
||||
for (size_t i = 0; i < ARRAY_SIZE(yt921x_mib_descs); i++) {
|
||||
const struct yt921x_mib_desc *desc = &yt921x_mib_descs[i];
|
||||
|
||||
if (!desc->name)
|
||||
continue;
|
||||
|
||||
data[j] = buf[i];
|
||||
j++;
|
||||
}
|
||||
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
}
|
||||
|
||||
int yt921x_dsa_get_sset_count(struct dsa_switch *ds, int port, int sset)
|
||||
{
|
||||
int cnt = 0;
|
||||
|
||||
if (sset != ETH_SS_STATS)
|
||||
return 0;
|
||||
|
||||
for (size_t i = 0; i < ARRAY_SIZE(yt921x_mib_descs); i++) {
|
||||
const struct yt921x_mib_desc *desc = &yt921x_mib_descs[i];
|
||||
|
||||
if (desc->name)
|
||||
cnt++;
|
||||
}
|
||||
|
||||
return cnt;
|
||||
}
|
||||
|
||||
void
|
||||
yt921x_dsa_get_eth_mac_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_eth_mac_stats *mac_stats)
|
||||
{
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *pm = pp->mib;
|
||||
struct yt921x_mib_stats *mib;
|
||||
|
||||
if (!pm)
|
||||
return;
|
||||
mib = &pm->stats;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
||||
yt921x_mib_read(priv, port);
|
||||
|
||||
mac_stats->FramesTransmittedOK = u64_stats_read(&pm->tx_frames);
|
||||
mac_stats->SingleCollisionFrames = u64_stats_read(&mib->tx_single_collisions);
|
||||
mac_stats->MultipleCollisionFrames = u64_stats_read(&mib->tx_multiple_collisions);
|
||||
mac_stats->FramesReceivedOK = u64_stats_read(&pm->rx_frames);
|
||||
mac_stats->FrameCheckSequenceErrors = u64_stats_read(&mib->rx_crc_errors);
|
||||
mac_stats->AlignmentErrors = u64_stats_read(&mib->rx_alignment_errors);
|
||||
mac_stats->OctetsTransmittedOK = u64_stats_read(&mib->tx_good_bytes);
|
||||
mac_stats->FramesWithDeferredXmissions = u64_stats_read(&mib->tx_deferred);
|
||||
mac_stats->LateCollisions = u64_stats_read(&mib->tx_late_collisions);
|
||||
mac_stats->FramesAbortedDueToXSColls = u64_stats_read(&mib->tx_aborted_errors);
|
||||
/* mac_stats->FramesLostDueToIntMACXmitError */
|
||||
/* mac_stats->CarrierSenseErrors */
|
||||
mac_stats->OctetsReceivedOK = u64_stats_read(&mib->rx_good_bytes);
|
||||
/* mac_stats->FramesLostDueToIntMACRcvError */
|
||||
mac_stats->MulticastFramesXmittedOK = u64_stats_read(&mib->tx_multicast);
|
||||
mac_stats->BroadcastFramesXmittedOK = u64_stats_read(&mib->tx_broadcast);
|
||||
/* mac_stats->FramesWithExcessiveDeferral */
|
||||
mac_stats->MulticastFramesReceivedOK = u64_stats_read(&mib->rx_multicast);
|
||||
mac_stats->BroadcastFramesReceivedOK = u64_stats_read(&mib->rx_broadcast);
|
||||
/* mac_stats->InRangeLengthErrors */
|
||||
/* mac_stats->OutOfRangeLengthField */
|
||||
mac_stats->FrameTooLongErrors = u64_stats_read(&mib->rx_oversize_errors);
|
||||
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
}
|
||||
|
||||
void
|
||||
yt921x_dsa_get_eth_ctrl_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_eth_ctrl_stats *ctrl_stats)
|
||||
{
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *pm = pp->mib;
|
||||
struct yt921x_mib_stats *mib;
|
||||
|
||||
if (!pm)
|
||||
return;
|
||||
mib = &pm->stats;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
||||
yt921x_mib_read(priv, port);
|
||||
|
||||
ctrl_stats->MACControlFramesTransmitted = u64_stats_read(&mib->tx_pause);
|
||||
ctrl_stats->MACControlFramesReceived = u64_stats_read(&mib->rx_pause);
|
||||
/* ctrl_stats->UnsupportedOpcodesReceived */
|
||||
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
}
|
||||
|
||||
static const struct ethtool_rmon_hist_range yt921x_rmon_ranges[] = {
|
||||
{ 0, 64 },
|
||||
{ 65, 127 },
|
||||
{ 128, 255 },
|
||||
{ 256, 511 },
|
||||
{ 512, 1023 },
|
||||
{ 1024, 1518 },
|
||||
{ 1519, YT921X_FRAME_SIZE_MAX },
|
||||
{}
|
||||
};
|
||||
|
||||
void
|
||||
yt921x_dsa_get_rmon_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_rmon_stats *rmon_stats,
|
||||
const struct ethtool_rmon_hist_range **ranges)
|
||||
{
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *pm = pp->mib;
|
||||
struct yt921x_mib_stats *mib;
|
||||
|
||||
if (!pm)
|
||||
return;
|
||||
mib = &pm->stats;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
||||
yt921x_mib_read(priv, port);
|
||||
|
||||
*ranges = yt921x_rmon_ranges;
|
||||
|
||||
rmon_stats->undersize_pkts = u64_stats_read(&mib->rx_undersize_errors);
|
||||
rmon_stats->oversize_pkts = u64_stats_read(&mib->rx_oversize_errors);
|
||||
rmon_stats->fragments = u64_stats_read(&mib->rx_alignment_errors);
|
||||
/* rmon_stats->jabbers */
|
||||
|
||||
rmon_stats->hist[0] = u64_stats_read(&mib->rx_64byte);
|
||||
rmon_stats->hist[1] = u64_stats_read(&mib->rx_65_127byte);
|
||||
rmon_stats->hist[2] = u64_stats_read(&mib->rx_128_255byte);
|
||||
rmon_stats->hist[3] = u64_stats_read(&mib->rx_256_511byte);
|
||||
rmon_stats->hist[4] = u64_stats_read(&mib->rx_512_1023byte);
|
||||
rmon_stats->hist[5] = u64_stats_read(&mib->rx_1024_1518byte);
|
||||
rmon_stats->hist[6] = u64_stats_read(&mib->rx_jumbo);
|
||||
|
||||
rmon_stats->hist_tx[0] = u64_stats_read(&mib->tx_64byte);
|
||||
rmon_stats->hist_tx[1] = u64_stats_read(&mib->tx_65_127byte);
|
||||
rmon_stats->hist_tx[2] = u64_stats_read(&mib->tx_128_255byte);
|
||||
rmon_stats->hist_tx[3] = u64_stats_read(&mib->tx_256_511byte);
|
||||
rmon_stats->hist_tx[4] = u64_stats_read(&mib->tx_512_1023byte);
|
||||
rmon_stats->hist_tx[5] = u64_stats_read(&mib->tx_1024_1518byte);
|
||||
rmon_stats->hist_tx[6] = u64_stats_read(&mib->tx_jumbo);
|
||||
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
}
|
||||
|
||||
void
|
||||
yt921x_dsa_get_stats64(struct dsa_switch *ds, int port,
|
||||
struct rtnl_link_stats64 *stats)
|
||||
{
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *pm = pp->mib;
|
||||
struct yt921x_mib_stats *mib;
|
||||
unsigned int start;
|
||||
|
||||
if (!pm)
|
||||
return;
|
||||
mib = &pm->stats;
|
||||
|
||||
do {
|
||||
start = u64_stats_fetch_begin(&pm->syncp);
|
||||
|
||||
stats->rx_length_errors = u64_stats_read(&mib->rx_undersize_errors) +
|
||||
u64_stats_read(&mib->rx_fragment_errors);
|
||||
stats->rx_over_errors = u64_stats_read(&mib->rx_oversize_errors);
|
||||
stats->rx_crc_errors = u64_stats_read(&mib->rx_crc_errors);
|
||||
stats->rx_frame_errors = u64_stats_read(&mib->rx_alignment_errors);
|
||||
/* stats->rx_fifo_errors */
|
||||
/* stats->rx_missed_errors */
|
||||
|
||||
stats->tx_aborted_errors = u64_stats_read(&mib->tx_aborted_errors);
|
||||
/* stats->tx_carrier_errors */
|
||||
stats->tx_fifo_errors = u64_stats_read(&mib->tx_undersize_errors);
|
||||
/* stats->tx_heartbeat_errors */
|
||||
stats->tx_window_errors = u64_stats_read(&mib->tx_late_collisions);
|
||||
|
||||
stats->rx_packets = u64_stats_read(&pm->rx_frames);
|
||||
stats->tx_packets = u64_stats_read(&pm->tx_frames);
|
||||
stats->rx_bytes = u64_stats_read(&mib->rx_good_bytes) -
|
||||
ETH_FCS_LEN * stats->rx_packets;
|
||||
stats->tx_bytes = u64_stats_read(&mib->tx_good_bytes) -
|
||||
ETH_FCS_LEN * stats->tx_packets;
|
||||
stats->rx_dropped = u64_stats_read(&mib->rx_dropped);
|
||||
/* stats->tx_dropped */
|
||||
stats->multicast = u64_stats_read(&mib->rx_multicast);
|
||||
stats->collisions = u64_stats_read(&mib->tx_collisions);
|
||||
} while (u64_stats_fetch_retry(&pm->syncp, start));
|
||||
|
||||
stats->rx_errors = stats->rx_length_errors + stats->rx_over_errors +
|
||||
stats->rx_crc_errors + stats->rx_frame_errors;
|
||||
stats->tx_errors = stats->tx_aborted_errors + stats->tx_fifo_errors +
|
||||
stats->tx_window_errors;
|
||||
}
|
||||
|
||||
void
|
||||
yt921x_dsa_get_pause_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_pause_stats *pause_stats)
|
||||
{
|
||||
struct yt921x_priv *priv = dsa_to_yt921x_priv(ds);
|
||||
struct yt921x_port *pp = &priv->ports[port];
|
||||
struct yt921x_mib *pm = pp->mib;
|
||||
struct yt921x_mib_stats *mib;
|
||||
|
||||
if (!pm)
|
||||
return;
|
||||
mib = &pm->stats;
|
||||
|
||||
mutex_lock(&priv->reg_lock);
|
||||
|
||||
yt921x_mib_read(priv, port);
|
||||
|
||||
pause_stats->tx_pause_frames = u64_stats_read(&mib->tx_pause);
|
||||
pause_stats->rx_pause_frames = u64_stats_read(&mib->rx_pause);
|
||||
|
||||
mutex_unlock(&priv->reg_lock);
|
||||
}
|
||||
167
drivers/net/dsa/motorcomm/mib.h
Normal file
167
drivers/net/dsa/motorcomm/mib.h
Normal file
|
|
@ -0,0 +1,167 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-or-later */
|
||||
/*
|
||||
* Copyright (c) 2026 David Yang
|
||||
*/
|
||||
|
||||
#ifndef _YT_MIB_H
|
||||
#define _YT_MIB_H
|
||||
|
||||
#include <linux/u64_stats_sync.h>
|
||||
|
||||
#include <net/dsa.h>
|
||||
|
||||
#define YT921X_MIB_CTRL 0xc0004
|
||||
#define YT921X_MIB_CTRL_CLEAN BIT(30)
|
||||
#define YT921X_MIB_CTRL_PORT_M GENMASK(6, 3)
|
||||
#define YT921X_MIB_CTRL_PORT(x) FIELD_PREP(YT921X_MIB_CTRL_PORT_M, (x))
|
||||
#define YT921X_MIB_CTRL_ONE_PORT BIT(1)
|
||||
#define YT921X_MIB_CTRL_ALL_PORT BIT(0)
|
||||
#define YT921X_MIBn_DATA0(port) (0xc0100 + 0x100 * (port))
|
||||
#define YT921X_MIBn_DATAm(port, x) (YT921X_MIBn_DATA0(port) + 4 * (x))
|
||||
#define YT921X_MIB_DATA_RX_BROADCAST 0x00
|
||||
#define YT921X_MIB_DATA_RX_PAUSE 0x04
|
||||
#define YT921X_MIB_DATA_RX_MULTICAST 0x08
|
||||
#define YT921X_MIB_DATA_RX_CRC_ERR 0x0c
|
||||
|
||||
#define YT921X_MIB_DATA_RX_ALIGN_ERR 0x10
|
||||
#define YT921X_MIB_DATA_RX_UNDERSIZE_ERR 0x14
|
||||
#define YT921X_MIB_DATA_RX_FRAG_ERR 0x18
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_64 0x1c
|
||||
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_65_TO_127 0x20
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_128_TO_255 0x24
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_256_TO_511 0x28
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_512_TO_1023 0x2c
|
||||
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_1024_TO_1518 0x30
|
||||
#define YT921X_MIB_DATA_RX_PKT_SZ_1519_TO_MAX 0x34
|
||||
/* 0x38: unused */
|
||||
#define YT921X_MIB_DATA_RX_GOOD_BYTES 0x3c
|
||||
|
||||
/* 0x40: 64 bytes */
|
||||
#define YT921X_MIB_DATA_RX_BAD_BYTES 0x44
|
||||
/* 0x48: 64 bytes */
|
||||
#define YT921X_MIB_DATA_RX_OVERSIZE_ERR 0x4c
|
||||
|
||||
#define YT921X_MIB_DATA_RX_DROPPED 0x50
|
||||
#define YT921X_MIB_DATA_TX_BROADCAST 0x54
|
||||
#define YT921X_MIB_DATA_TX_PAUSE 0x58
|
||||
#define YT921X_MIB_DATA_TX_MULTICAST 0x5c
|
||||
|
||||
#define YT921X_MIB_DATA_TX_UNDERSIZE_ERR 0x60
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_64 0x64
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_65_TO_127 0x68
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_128_TO_255 0x6c
|
||||
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_256_TO_511 0x70
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_512_TO_1023 0x74
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_1024_TO_1518 0x78
|
||||
#define YT921X_MIB_DATA_TX_PKT_SZ_1519_TO_MAX 0x7c
|
||||
|
||||
/* 0x80: unused */
|
||||
#define YT921X_MIB_DATA_TX_GOOD_BYTES 0x84
|
||||
/* 0x88: 64 bytes */
|
||||
#define YT921X_MIB_DATA_TX_COLLISION 0x8c
|
||||
|
||||
#define YT921X_MIB_DATA_TX_EXCESSIVE_COLLISION 0x90
|
||||
#define YT921X_MIB_DATA_TX_MULTIPLE_COLLISION 0x94
|
||||
#define YT921X_MIB_DATA_TX_SINGLE_COLLISION 0x98
|
||||
#define YT921X_MIB_DATA_TX_PKT 0x9c
|
||||
|
||||
#define YT921X_MIB_DATA_TX_DEFERRED 0xa0
|
||||
#define YT921X_MIB_DATA_TX_LATE_COLLISION 0xa4
|
||||
#define YT921X_MIB_DATA_RX_OAM 0xa8
|
||||
#define YT921X_MIB_DATA_TX_OAM 0xac
|
||||
|
||||
struct yt921x_mib_stats {
|
||||
u64_stats_t rx_broadcast;
|
||||
u64_stats_t rx_pause;
|
||||
u64_stats_t rx_multicast;
|
||||
u64_stats_t rx_crc_errors;
|
||||
|
||||
u64_stats_t rx_alignment_errors;
|
||||
u64_stats_t rx_undersize_errors;
|
||||
u64_stats_t rx_fragment_errors;
|
||||
u64_stats_t rx_64byte;
|
||||
|
||||
u64_stats_t rx_65_127byte;
|
||||
u64_stats_t rx_128_255byte;
|
||||
u64_stats_t rx_256_511byte;
|
||||
u64_stats_t rx_512_1023byte;
|
||||
|
||||
u64_stats_t rx_1024_1518byte;
|
||||
u64_stats_t rx_jumbo;
|
||||
u64_stats_t rx_good_bytes;
|
||||
|
||||
u64_stats_t rx_bad_bytes;
|
||||
u64_stats_t rx_oversize_errors;
|
||||
|
||||
u64_stats_t rx_dropped;
|
||||
u64_stats_t tx_broadcast;
|
||||
u64_stats_t tx_pause;
|
||||
u64_stats_t tx_multicast;
|
||||
|
||||
u64_stats_t tx_undersize_errors;
|
||||
u64_stats_t tx_64byte;
|
||||
u64_stats_t tx_65_127byte;
|
||||
u64_stats_t tx_128_255byte;
|
||||
|
||||
u64_stats_t tx_256_511byte;
|
||||
u64_stats_t tx_512_1023byte;
|
||||
u64_stats_t tx_1024_1518byte;
|
||||
u64_stats_t tx_jumbo;
|
||||
|
||||
u64_stats_t tx_good_bytes;
|
||||
u64_stats_t tx_collisions;
|
||||
|
||||
u64_stats_t tx_aborted_errors;
|
||||
u64_stats_t tx_multiple_collisions;
|
||||
u64_stats_t tx_single_collisions;
|
||||
u64_stats_t tx_good;
|
||||
|
||||
u64_stats_t tx_deferred;
|
||||
u64_stats_t tx_late_collisions;
|
||||
u64_stats_t rx_oam;
|
||||
u64_stats_t tx_oam;
|
||||
};
|
||||
|
||||
#define YT921X_MIB_STAT_NUM (sizeof(struct yt921x_mib_stats) / sizeof(u64_stats_t))
|
||||
|
||||
struct yt921x_mib {
|
||||
struct yt921x_port *port;
|
||||
|
||||
struct delayed_work work;
|
||||
struct u64_stats_sync syncp;
|
||||
/* writers: priv->reg_lock + syncp; readers: priv->reg_lock or syncp */
|
||||
struct yt921x_mib_stats stats;
|
||||
u64_stats_t rx_frames;
|
||||
u64_stats_t tx_frames;
|
||||
/* protected by priv->reg_lock */
|
||||
u64 data[YT921X_MIB_STAT_NUM];
|
||||
};
|
||||
|
||||
void yt921x_mib_poll(struct work_struct *work);
|
||||
void
|
||||
yt921x_dsa_get_strings(struct dsa_switch *ds, int port, u32 stringset,
|
||||
uint8_t *data);
|
||||
void
|
||||
yt921x_dsa_get_ethtool_stats(struct dsa_switch *ds, int port, uint64_t *data);
|
||||
int yt921x_dsa_get_sset_count(struct dsa_switch *ds, int port, int sset);
|
||||
void
|
||||
yt921x_dsa_get_eth_mac_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_eth_mac_stats *mac_stats);
|
||||
void
|
||||
yt921x_dsa_get_eth_ctrl_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_eth_ctrl_stats *ctrl_stats);
|
||||
void
|
||||
yt921x_dsa_get_rmon_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_rmon_stats *rmon_stats,
|
||||
const struct ethtool_rmon_hist_range **ranges);
|
||||
void
|
||||
yt921x_dsa_get_stats64(struct dsa_switch *ds, int port,
|
||||
struct rtnl_link_stats64 *stats);
|
||||
void
|
||||
yt921x_dsa_get_pause_stats(struct dsa_switch *ds, int port,
|
||||
struct ethtool_pause_stats *pause_stats);
|
||||
|
||||
#endif
|
||||
|
|
@ -8,8 +8,6 @@
|
|||
#include "pcs.h"
|
||||
#include "smi.h"
|
||||
|
||||
#define to_device(priv) ((priv)->ds.dev)
|
||||
|
||||
static int
|
||||
yt921x_serdes_config(struct yt921x_priv *priv, int port, unsigned int neg_mode,
|
||||
phy_interface_t interface,
|
||||
|
|
@ -116,7 +114,7 @@ yt921x_phylink_pcs_get_state(struct phylink_pcs *pcs, unsigned int neg_mode,
|
|||
{
|
||||
struct yt921x_port *pp = pcs_to_yt921x_port(pcs);
|
||||
struct yt921x_priv *priv = yt921x_port_to_priv(pp);
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
int port = pp->index;
|
||||
u16 bmsr;
|
||||
u16 lpa;
|
||||
|
|
@ -155,7 +153,7 @@ static void yt921x_phylink_pcs_an_restart(struct phylink_pcs *pcs)
|
|||
{
|
||||
struct yt921x_port *pp = pcs_to_yt921x_port(pcs);
|
||||
struct yt921x_priv *priv = yt921x_port_to_priv(pp);
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
int port = pp->index;
|
||||
u16 val;
|
||||
int res;
|
||||
|
|
@ -181,7 +179,7 @@ static void yt921x_phylink_pcs_disable(struct phylink_pcs *pcs)
|
|||
{
|
||||
struct yt921x_port *pp = pcs_to_yt921x_port(pcs);
|
||||
struct yt921x_priv *priv = yt921x_port_to_priv(pp);
|
||||
struct device *dev = to_device(priv);
|
||||
struct device *dev = yt921x_priv_to_device(priv);
|
||||
int port = pp->index;
|
||||
int res;
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user