Commit 5c74c54c authored by Iwan R Timmer's avatar Iwan R Timmer Committed by David S. Miller

net: dsa: mv88e6xxx: Split monitor port configuration

Separate the configuration of the egress and ingress monitor port.
This allows the port mirror functionality to do ingress and egress
port mirroring to separate ports.
Signed-off-by: default avatarIwan R Timmer <irtimmer@gmail.com>
Reviewed-by: default avatarAndrew Lunn <andrew@lunn.ch>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 22820017
...@@ -2390,7 +2390,14 @@ static int mv88e6xxx_setup_upstream_port(struct mv88e6xxx_chip *chip, int port) ...@@ -2390,7 +2390,14 @@ static int mv88e6xxx_setup_upstream_port(struct mv88e6xxx_chip *chip, int port)
if (chip->info->ops->set_egress_port) { if (chip->info->ops->set_egress_port) {
err = chip->info->ops->set_egress_port(chip, err = chip->info->ops->set_egress_port(chip,
upstream_port); MV88E6XXX_EGRESS_DIR_INGRESS,
upstream_port);
if (err)
return err;
err = chip->info->ops->set_egress_port(chip,
MV88E6XXX_EGRESS_DIR_EGRESS,
upstream_port);
if (err) if (err)
return err; return err;
} }
......
...@@ -33,6 +33,11 @@ enum mv88e6xxx_egress_mode { ...@@ -33,6 +33,11 @@ enum mv88e6xxx_egress_mode {
MV88E6XXX_EGRESS_MODE_ETHERTYPE, MV88E6XXX_EGRESS_MODE_ETHERTYPE,
}; };
enum mv88e6xxx_egress_direction {
MV88E6XXX_EGRESS_DIR_INGRESS,
MV88E6XXX_EGRESS_DIR_EGRESS,
};
enum mv88e6xxx_frame_mode { enum mv88e6xxx_frame_mode {
MV88E6XXX_FRAME_MODE_NORMAL, MV88E6XXX_FRAME_MODE_NORMAL,
MV88E6XXX_FRAME_MODE_DSA, MV88E6XXX_FRAME_MODE_DSA,
...@@ -465,7 +470,9 @@ struct mv88e6xxx_ops { ...@@ -465,7 +470,9 @@ struct mv88e6xxx_ops {
int (*stats_get_stats)(struct mv88e6xxx_chip *chip, int port, int (*stats_get_stats)(struct mv88e6xxx_chip *chip, int port,
uint64_t *data); uint64_t *data);
int (*set_cpu_port)(struct mv88e6xxx_chip *chip, int port); int (*set_cpu_port)(struct mv88e6xxx_chip *chip, int port);
int (*set_egress_port)(struct mv88e6xxx_chip *chip, int port); int (*set_egress_port)(struct mv88e6xxx_chip *chip,
enum mv88e6xxx_egress_direction direction,
int port);
#define MV88E6XXX_CASCADE_PORT_NONE 0xe #define MV88E6XXX_CASCADE_PORT_NONE 0xe
#define MV88E6XXX_CASCADE_PORT_MULTIPLE 0xf #define MV88E6XXX_CASCADE_PORT_MULTIPLE 0xf
......
...@@ -263,7 +263,9 @@ int mv88e6250_g1_ieee_pri_map(struct mv88e6xxx_chip *chip) ...@@ -263,7 +263,9 @@ int mv88e6250_g1_ieee_pri_map(struct mv88e6xxx_chip *chip)
/* Offset 0x1a: Monitor Control */ /* Offset 0x1a: Monitor Control */
/* Offset 0x1a: Monitor & MGMT Control on some devices */ /* Offset 0x1a: Monitor & MGMT Control on some devices */
int mv88e6095_g1_set_egress_port(struct mv88e6xxx_chip *chip, int port) int mv88e6095_g1_set_egress_port(struct mv88e6xxx_chip *chip,
enum mv88e6xxx_egress_direction direction,
int port)
{ {
u16 reg; u16 reg;
int err; int err;
...@@ -272,11 +274,20 @@ int mv88e6095_g1_set_egress_port(struct mv88e6xxx_chip *chip, int port) ...@@ -272,11 +274,20 @@ int mv88e6095_g1_set_egress_port(struct mv88e6xxx_chip *chip, int port)
if (err) if (err)
return err; return err;
reg &= ~(MV88E6185_G1_MONITOR_CTL_INGRESS_DEST_MASK | switch (direction) {
MV88E6185_G1_MONITOR_CTL_EGRESS_DEST_MASK); case MV88E6XXX_EGRESS_DIR_INGRESS:
reg &= MV88E6185_G1_MONITOR_CTL_INGRESS_DEST_MASK;
reg |= port << __bf_shf(MV88E6185_G1_MONITOR_CTL_INGRESS_DEST_MASK) | reg |= port <<
port << __bf_shf(MV88E6185_G1_MONITOR_CTL_EGRESS_DEST_MASK); __bf_shf(MV88E6185_G1_MONITOR_CTL_INGRESS_DEST_MASK);
break;
case MV88E6XXX_EGRESS_DIR_EGRESS:
reg &= MV88E6185_G1_MONITOR_CTL_EGRESS_DEST_MASK;
reg |= port <<
__bf_shf(MV88E6185_G1_MONITOR_CTL_EGRESS_DEST_MASK);
break;
default:
return -EINVAL;
}
return mv88e6xxx_g1_write(chip, MV88E6185_G1_MONITOR_CTL, reg); return mv88e6xxx_g1_write(chip, MV88E6185_G1_MONITOR_CTL, reg);
} }
...@@ -310,17 +321,24 @@ static int mv88e6390_g1_monitor_write(struct mv88e6xxx_chip *chip, ...@@ -310,17 +321,24 @@ static int mv88e6390_g1_monitor_write(struct mv88e6xxx_chip *chip,
return mv88e6xxx_g1_write(chip, MV88E6390_G1_MONITOR_MGMT_CTL, reg); return mv88e6xxx_g1_write(chip, MV88E6390_G1_MONITOR_MGMT_CTL, reg);
} }
int mv88e6390_g1_set_egress_port(struct mv88e6xxx_chip *chip, int port) int mv88e6390_g1_set_egress_port(struct mv88e6xxx_chip *chip,
enum mv88e6xxx_egress_direction direction,
int port)
{ {
u16 ptr; u16 ptr;
int err; int err;
ptr = MV88E6390_G1_MONITOR_MGMT_CTL_PTR_INGRESS_DEST; switch (direction) {
err = mv88e6390_g1_monitor_write(chip, ptr, port); case MV88E6XXX_EGRESS_DIR_INGRESS:
if (err) ptr = MV88E6390_G1_MONITOR_MGMT_CTL_PTR_INGRESS_DEST;
return err; break;
case MV88E6XXX_EGRESS_DIR_EGRESS:
ptr = MV88E6390_G1_MONITOR_MGMT_CTL_PTR_EGRESS_DEST;
break;
default:
return -EINVAL;
}
ptr = MV88E6390_G1_MONITOR_MGMT_CTL_PTR_EGRESS_DEST;
err = mv88e6390_g1_monitor_write(chip, ptr, port); err = mv88e6390_g1_monitor_write(chip, ptr, port);
if (err) if (err)
return err; return err;
......
...@@ -288,8 +288,12 @@ int mv88e6095_g1_stats_set_histogram(struct mv88e6xxx_chip *chip); ...@@ -288,8 +288,12 @@ int mv88e6095_g1_stats_set_histogram(struct mv88e6xxx_chip *chip);
int mv88e6390_g1_stats_set_histogram(struct mv88e6xxx_chip *chip); int mv88e6390_g1_stats_set_histogram(struct mv88e6xxx_chip *chip);
void mv88e6xxx_g1_stats_read(struct mv88e6xxx_chip *chip, int stat, u32 *val); void mv88e6xxx_g1_stats_read(struct mv88e6xxx_chip *chip, int stat, u32 *val);
int mv88e6xxx_g1_stats_clear(struct mv88e6xxx_chip *chip); int mv88e6xxx_g1_stats_clear(struct mv88e6xxx_chip *chip);
int mv88e6095_g1_set_egress_port(struct mv88e6xxx_chip *chip, int port); int mv88e6095_g1_set_egress_port(struct mv88e6xxx_chip *chip,
int mv88e6390_g1_set_egress_port(struct mv88e6xxx_chip *chip, int port); enum mv88e6xxx_egress_direction direction,
int port);
int mv88e6390_g1_set_egress_port(struct mv88e6xxx_chip *chip,
enum mv88e6xxx_egress_direction direction,
int port);
int mv88e6095_g1_set_cpu_port(struct mv88e6xxx_chip *chip, int port); int mv88e6095_g1_set_cpu_port(struct mv88e6xxx_chip *chip, int port);
int mv88e6390_g1_set_cpu_port(struct mv88e6xxx_chip *chip, int port); int mv88e6390_g1_set_cpu_port(struct mv88e6xxx_chip *chip, int port);
int mv88e6390_g1_mgmt_rsvd2cpu(struct mv88e6xxx_chip *chip); int mv88e6390_g1_mgmt_rsvd2cpu(struct mv88e6xxx_chip *chip);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment