Commit 7527d662 authored by Marek Behún's avatar Marek Behún Committed by David S. Miller

net: dsa: mv88e6xxx: Save power by disabling SerDes trasmitter and receiver

Save power on 88E6393X by disabling SerDes receiver and transmitter
after SerDes is SerDes is disabled.
Signed-off-by: default avatarMarek Behún <kabel@kernel.org>
Cc: stable@vger.kernel.org # de776d0d ("net: dsa: mv88e6xxx: add support for mv88e6393x family")
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 8c3318b4
...@@ -1271,6 +1271,28 @@ void mv88e6390_serdes_get_regs(struct mv88e6xxx_chip *chip, int port, void *_p) ...@@ -1271,6 +1271,28 @@ void mv88e6390_serdes_get_regs(struct mv88e6xxx_chip *chip, int port, void *_p)
} }
} }
static int mv88e6393x_serdes_power_lane(struct mv88e6xxx_chip *chip, int lane,
bool on)
{
u16 reg;
int err;
err = mv88e6390_serdes_read(chip, lane, MDIO_MMD_PHYXS,
MV88E6393X_SERDES_CTRL1, &reg);
if (err)
return err;
if (on)
reg &= ~(MV88E6393X_SERDES_CTRL1_TX_PDOWN |
MV88E6393X_SERDES_CTRL1_RX_PDOWN);
else
reg |= MV88E6393X_SERDES_CTRL1_TX_PDOWN |
MV88E6393X_SERDES_CTRL1_RX_PDOWN;
return mv88e6390_serdes_write(chip, lane, MDIO_MMD_PHYXS,
MV88E6393X_SERDES_CTRL1, reg);
}
static int mv88e6393x_serdes_erratum_4_6(struct mv88e6xxx_chip *chip, int lane) static int mv88e6393x_serdes_erratum_4_6(struct mv88e6xxx_chip *chip, int lane)
{ {
u16 reg; u16 reg;
...@@ -1297,7 +1319,11 @@ static int mv88e6393x_serdes_erratum_4_6(struct mv88e6xxx_chip *chip, int lane) ...@@ -1297,7 +1319,11 @@ static int mv88e6393x_serdes_erratum_4_6(struct mv88e6xxx_chip *chip, int lane)
if (err) if (err)
return err; return err;
return mv88e6390_serdes_power_sgmii(chip, lane, false); err = mv88e6390_serdes_power_sgmii(chip, lane, false);
if (err)
return err;
return mv88e6393x_serdes_power_lane(chip, lane, false);
} }
int mv88e6393x_serdes_setup_errata(struct mv88e6xxx_chip *chip) int mv88e6393x_serdes_setup_errata(struct mv88e6xxx_chip *chip)
...@@ -1362,17 +1388,29 @@ int mv88e6393x_serdes_power(struct mv88e6xxx_chip *chip, int port, int lane, ...@@ -1362,17 +1388,29 @@ int mv88e6393x_serdes_power(struct mv88e6xxx_chip *chip, int port, int lane,
err = mv88e6393x_serdes_erratum_4_8(chip, lane); err = mv88e6393x_serdes_erratum_4_8(chip, lane);
if (err) if (err)
return err; return err;
err = mv88e6393x_serdes_power_lane(chip, lane, true);
if (err)
return err;
} }
switch (cmode) { switch (cmode) {
case MV88E6XXX_PORT_STS_CMODE_SGMII: case MV88E6XXX_PORT_STS_CMODE_SGMII:
case MV88E6XXX_PORT_STS_CMODE_1000BASEX: case MV88E6XXX_PORT_STS_CMODE_1000BASEX:
case MV88E6XXX_PORT_STS_CMODE_2500BASEX: case MV88E6XXX_PORT_STS_CMODE_2500BASEX:
return mv88e6390_serdes_power_sgmii(chip, lane, on); err = mv88e6390_serdes_power_sgmii(chip, lane, on);
break;
case MV88E6393X_PORT_STS_CMODE_5GBASER: case MV88E6393X_PORT_STS_CMODE_5GBASER:
case MV88E6393X_PORT_STS_CMODE_10GBASER: case MV88E6393X_PORT_STS_CMODE_10GBASER:
return mv88e6390_serdes_power_10g(chip, lane, on); err = mv88e6390_serdes_power_10g(chip, lane, on);
break;
} }
return 0; if (err)
return err;
if (!on)
err = mv88e6393x_serdes_power_lane(chip, lane, false);
return err;
} }
...@@ -93,6 +93,9 @@ ...@@ -93,6 +93,9 @@
#define MV88E6393X_SERDES_POC_PCS_MASK 0x0007 #define MV88E6393X_SERDES_POC_PCS_MASK 0x0007
#define MV88E6393X_SERDES_POC_RESET BIT(15) #define MV88E6393X_SERDES_POC_RESET BIT(15)
#define MV88E6393X_SERDES_POC_PDOWN BIT(5) #define MV88E6393X_SERDES_POC_PDOWN BIT(5)
#define MV88E6393X_SERDES_CTRL1 0xf003
#define MV88E6393X_SERDES_CTRL1_TX_PDOWN BIT(9)
#define MV88E6393X_SERDES_CTRL1_RX_PDOWN BIT(8)
#define MV88E6393X_ERRATA_4_8_REG 0xF074 #define MV88E6393X_ERRATA_4_8_REG 0xF074
#define MV88E6393X_ERRATA_4_8_BIT BIT(14) #define MV88E6393X_ERRATA_4_8_BIT BIT(14)
......
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