source of highlighter
plain | download
    1 diff --git a/drivers/net/dsa/mv88e6xxx/chip.c b/drivers/net/dsa/mv88e6xxx/chip.c
    2 index 5c235b5b7022..a285041d0eba 100644
    3 --- a/drivers/net/dsa/mv88e6xxx/chip.c
    4 +++ b/drivers/net/dsa/mv88e6xxx/chip.c
    5 @@ -6538,6 +6538,104 @@ static int __maybe_unused mv88e6xxx_resume(struct device *dev)
    6  
    7  static SIMPLE_DEV_PM_OPS(mv88e6xxx_pm_ops, mv88e6xxx_suspend, mv88e6xxx_resume);
    8  
    9 +#define XXX(n)                                                                 \
   10 +static ssize_t n##_show(struct device *dev, struct device_attribute *a,                \
   11 +                        char *buf)                                             \
   12 +{                                                                              \
   13 +       struct dsa_switch *ds = dev_get_drvdata(dev);                           \
   14 +       struct mv88e6xxx_chip *chip = ds->priv;                                 \
   15 +                                                                               \
   16 +       return sprintf(buf, "0x%04x\n", chip->regacc_##n);                      \
   17 +}                                                                              \
   18 +                                                                               \
   19 +static ssize_t n##_store(struct device *dev, struct device_attribute *a,       \
   20 +                               const char *buf, size_t count)                  \
   21 +{                                                                              \
   22 +       struct dsa_switch *ds = dev_get_drvdata(dev);                           \
   23 +       struct mv88e6xxx_chip *chip = ds->priv;                                 \
   24 +       unsigned long val;                                                      \
   25 +                                                                               \
   26 +       if (kstrtoul(buf, 16, &val))                                            \
   27 +               return -EINVAL;                                                 \
   28 +                                                                               \
   29 +       chip->regacc_##n = val;                                                 \
   30 +                                                                               \
   31 +       return count;                                                           \
   32 +}                                                                              \
   33 +static DEVICE_ATTR_RW(n);
   34 +
   35 +XXX(lane)
   36 +XXX(dev)
   37 +XXX(reg)
   38 +
   39 +int mv88e6390_serdes_read(struct mv88e6xxx_chip *chip, int lane, int device, int reg, u16 *val);
   40 +int mv88e6390_serdes_write(struct mv88e6xxx_chip *chip, int lane, int device, int reg, u16 val);
   41 +
   42 +static ssize_t val_show(struct device *dev, struct device_attribute *a, char *buf)
   43 +{
   44 +       struct dsa_switch *ds = dev_get_drvdata(dev);
   45 +       struct mv88e6xxx_chip *chip = ds->priv;
   46 +       u16 val;
   47 +       int ret;
   48 +
   49 +       mv88e6xxx_reg_lock(chip);
   50 +       ret = mv88e6390_serdes_read(chip, chip->regacc_lane, chip->regacc_dev, chip->regacc_reg, &val);
   51 +       mv88e6xxx_reg_unlock(chip);
   52 +
   53 +       if (ret)
   54 +               return ret;
   55 +
   56 +       return sprintf(buf, "0x%04x\n", val);
   57 +}
   58 +
   59 +static ssize_t val_store(struct device *dev, struct device_attribute *a, const char *buf, size_t count)
   60 +{
   61 +       struct dsa_switch *ds = dev_get_drvdata(dev);
   62 +       struct mv88e6xxx_chip *chip = ds->priv;
   63 +       unsigned long val;
   64 +       int ret;
   65 +
   66 +       if (kstrtoul(buf, 16, &val))
   67 +               return -EINVAL;
   68 +
   69 +       mv88e6xxx_reg_lock(chip);
   70 +       ret = mv88e6390_serdes_write(chip, chip->regacc_lane, chip->regacc_dev, chip->regacc_reg, val);
   71 +       mv88e6xxx_reg_unlock(chip);
   72 +
   73 +       return ret < 0 ? ret : count;
   74 +}
   75 +static DEVICE_ATTR_RW(val);
   76 +
   77 +static ssize_t phy_mode_port_9_store(struct device *dev, struct device_attribute *a, const char *buf, size_t count)
   78 +{
   79 +       struct dsa_switch *ds = dev_get_drvdata(dev);
   80 +       struct mv88e6xxx_chip *chip = ds->priv;
   81 +       unsigned long val;
   82 +       int ret;
   83 +
   84 +       if (kstrtoul(buf, 16, &val) || !val || val >= PHY_INTERFACE_MODE_MAX)
   85 +               return -EINVAL;
   86 +
   87 +       dev_err(dev, "setting port 9 mode to %s\n", phy_modes(val));
   88 +
   89 +       mv88e6xxx_reg_lock(chip);
   90 +       ret = mv88e6xxx_port_setup_mac(chip, 9, LINK_UNFORCED, SPEED_UNFORCED, DUPLEX_UNFORCED, PAUSE_ON, val);
   91 +       mv88e6xxx_reg_unlock(chip);
   92 +
   93 +       return ret < 0 ? ret : count;
   94 +}
   95 +static DEVICE_ATTR_WO(phy_mode_port_9);
   96 +
   97 +static struct attribute *mv88e6xxx_attrs[] = {
   98 +       &dev_attr_lane.attr,
   99 +       &dev_attr_dev.attr,
  100 +       &dev_attr_reg.attr,
  101 +       &dev_attr_val.attr,
  102 +       &dev_attr_phy_mode_port_9.attr,
  103 +       NULL,
  104 +};
  105 +ATTRIBUTE_GROUPS(mv88e6xxx);
  106 +
  107  static int mv88e6xxx_probe(struct mdio_device *mdiodev)
  108  {
  109         struct dsa_mv88e6xxx_pdata *pdata = mdiodev->dev.platform_data;
  110 @@ -6665,6 +6763,9 @@ static int mv88e6xxx_probe(struct mdio_device *mdiodev)
  111         if (err)
  112                 goto out_mdio;
  113  
  114 +       if (devm_device_add_groups(dev, mv88e6xxx_groups))
  115 +               dev_warn(dev, "Could not add attribute group!\n");
  116 +
  117         return 0;
  118  
  119  out_mdio:
  120 diff --git a/drivers/net/dsa/mv88e6xxx/chip.h b/drivers/net/dsa/mv88e6xxx/chip.h
  121 index 73b337478378..0e3b2449b7f7 100644
  122 --- a/drivers/net/dsa/mv88e6xxx/chip.h
  123 +++ b/drivers/net/dsa/mv88e6xxx/chip.h
  124 @@ -290,6 +290,8 @@ struct mv88e6xxx_region_priv {
  125  struct mv88e6xxx_chip {
  126         const struct mv88e6xxx_info *info;
  127  
  128 +       u16 regacc_lane, regacc_dev, regacc_reg;
  129 +
  130         /* Currently configured tagging protocol */
  131         enum dsa_tag_protocol tag_protocol;
  132  
  133 diff --git a/drivers/net/dsa/mv88e6xxx/port.c b/drivers/net/dsa/mv88e6xxx/port.c
  134 index d9817b20ea64..8814538e4dd3 100644
  135 --- a/drivers/net/dsa/mv88e6xxx/port.c
  136 +++ b/drivers/net/dsa/mv88e6xxx/port.c
  137 @@ -555,6 +555,7 @@ static int mv88e6xxx_port_set_cmode(struct mv88e6xxx_chip *chip, int port,
  138                 break;
  139         case PHY_INTERFACE_MODE_SGMII:
  140                 cmode = MV88E6XXX_PORT_STS_CMODE_SGMII;
  141 +               cmode = MV88E6XXX_PORT_STS_CMODE_1000BASEX;
  142                 break;
  143         case PHY_INTERFACE_MODE_2500BASEX:
  144                 cmode = MV88E6XXX_PORT_STS_CMODE_2500BASEX;
  145 @@ -588,9 +589,9 @@ static int mv88e6xxx_port_set_cmode(struct mv88e6xxx_chip *chip, int port,
  146                                 return err;
  147                 }
  148  
  149 -               err = mv88e6xxx_serdes_power_down(chip, port, lane);
  150 -               if (err)
  151 -                       return err;
  152 +//             err = mv88e6xxx_serdes_power_down(chip, port, lane);
  153 +//             if (err)
  154 +//                     return err;
  155         }
  156  
  157         chip->ports[port].cmode = 0;
  158 @@ -613,6 +614,9 @@ static int mv88e6xxx_port_set_cmode(struct mv88e6xxx_chip *chip, int port,
  159                 if (lane < 0)
  160                         return lane;
  161  
  162 +               err = mv88e6xxx_serdes_power_down(chip, port, lane);
  163 +               if (err)
  164 +                       return err;
  165                 err = mv88e6xxx_serdes_power_up(chip, port, lane);
  166                 if (err)
  167                         return err;
  168 diff --git a/drivers/net/dsa/mv88e6xxx/serdes.c b/drivers/net/dsa/mv88e6xxx/serdes.c
  169 index b70979bd07df..21cb56db08e4 100644
  170 --- a/drivers/net/dsa/mv88e6xxx/serdes.c
  171 +++ b/drivers/net/dsa/mv88e6xxx/serdes.c
  172 @@ -33,7 +33,8 @@ static int mv88e6352_serdes_write(struct mv88e6xxx_chip *chip, int reg,
  173                                         reg, val);
  174  }
  175  
  176 -static int mv88e6390_serdes_read(struct mv88e6xxx_chip *chip,
  177 +//static
  178 +int mv88e6390_serdes_read(struct mv88e6xxx_chip *chip,
  179                                  int lane, int device, int reg, u16 *val)
  180  {
  181         int reg_c45 = MII_ADDR_C45 | device << 16 | reg;
  182 @@ -41,7 +42,8 @@ static int mv88e6390_serdes_read(struct mv88e6xxx_chip *chip,
  183         return mv88e6xxx_phy_read(chip, lane, reg_c45, val);
  184  }
  185  
  186 -static int mv88e6390_serdes_write(struct mv88e6xxx_chip *chip,
  187 +//static
  188 +int mv88e6390_serdes_write(struct mv88e6xxx_chip *chip,
  189                                   int lane, int device, int reg, u16 val)
  190  {
  191         int reg_c45 = MII_ADDR_C45 | device << 16 | reg;