]> Pileus Git - ~andy/linux/blobdiff - drivers/net/ethernet/marvell/mvneta.c
Merge git://git.kernel.org/pub/scm/linux/kernel/git/davem/net
[~andy/linux] / drivers / net / ethernet / marvell / mvneta.c
index 2777c70c603b550676b77027fd96e7b9a79fbe6b..e35bac7cfdf14dc85d2bb55b49a864c29f2ae2c6 100644 (file)
 #define      MVNETA_GMAC_FORCE_LINK_PASS         BIT(1)
 #define      MVNETA_GMAC_CONFIG_MII_SPEED        BIT(5)
 #define      MVNETA_GMAC_CONFIG_GMII_SPEED       BIT(6)
+#define      MVNETA_GMAC_AN_SPEED_EN             BIT(7)
 #define      MVNETA_GMAC_CONFIG_FULL_DUPLEX      BIT(12)
+#define      MVNETA_GMAC_AN_DUPLEX_EN            BIT(13)
 #define MVNETA_MIB_COUNTERS_BASE                 0x3080
 #define      MVNETA_MIB_LATE_COLLISION           0x7c
 #define MVNETA_DA_FILT_SPEC_MCAST                0x3400
@@ -948,6 +950,13 @@ static void mvneta_defaults_set(struct mvneta_port *pp)
        /* Assign port SDMA configuration */
        mvreg_write(pp, MVNETA_SDMA_CONFIG, val);
 
+       /* Disable PHY polling in hardware, since we're using the
+        * kernel phylib to do this.
+        */
+       val = mvreg_read(pp, MVNETA_UNIT_CONTROL);
+       val &= ~MVNETA_PHY_POLLING_ENABLE;
+       mvreg_write(pp, MVNETA_UNIT_CONTROL, val);
+
        mvneta_set_ucast_table(pp, -1);
        mvneta_set_special_mcast_table(pp, -1);
        mvneta_set_other_mcast_table(pp, -1);
@@ -2340,7 +2349,9 @@ static void mvneta_adjust_link(struct net_device *ndev)
                        val = mvreg_read(pp, MVNETA_GMAC_AUTONEG_CONFIG);
                        val &= ~(MVNETA_GMAC_CONFIG_MII_SPEED |
                                 MVNETA_GMAC_CONFIG_GMII_SPEED |
-                                MVNETA_GMAC_CONFIG_FULL_DUPLEX);
+                                MVNETA_GMAC_CONFIG_FULL_DUPLEX |
+                                MVNETA_GMAC_AN_SPEED_EN |
+                                MVNETA_GMAC_AN_DUPLEX_EN);
 
                        if (phydev->duplex)
                                val |= MVNETA_GMAC_CONFIG_FULL_DUPLEX;
@@ -2473,6 +2484,21 @@ static int mvneta_stop(struct net_device *dev)
        return 0;
 }
 
+static int mvneta_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
+{
+       struct mvneta_port *pp = netdev_priv(dev);
+       int ret;
+
+       if (!pp->phy_dev)
+               return -ENOTSUPP;
+
+       ret = phy_mii_ioctl(pp->phy_dev, ifr, cmd);
+       if (!ret)
+               mvneta_adjust_link(dev);
+
+       return ret;
+}
+
 /* Ethtool methods */
 
 /* Get settings (phy address, speed) for ethtools */
@@ -2591,6 +2617,7 @@ static const struct net_device_ops mvneta_netdev_ops = {
        .ndo_change_mtu      = mvneta_change_mtu,
        .ndo_tx_timeout      = mvneta_tx_timeout,
        .ndo_get_stats64     = mvneta_get_stats64,
+       .ndo_do_ioctl        = mvneta_ioctl,
 };
 
 const struct ethtool_ops mvneta_eth_tool_ops = {