bgmac.c (a0b68486f6f680c7c0352a47c60042d7d95ffd87) bgmac.c (55954f3bfdacc5908515b0c306cea23e77fab740)
1/*
2 * Driver for (BCM4706)? GBit MAC core on BCMA bus.
3 *
4 * Copyright (C) 2012 Rafał Miłecki <zajec5@gmail.com>
5 *
6 * Licensed under the GNU/GPL. See COPYING for details.
7 */
8

--- 742 unchanged lines hidden (view full) ---

751
752 return 0;
753
754error:
755 bgmac_dma_cleanup(bgmac);
756 return err;
757}
758
1/*
2 * Driver for (BCM4706)? GBit MAC core on BCMA bus.
3 *
4 * Copyright (C) 2012 Rafał Miłecki <zajec5@gmail.com>
5 *
6 * Licensed under the GNU/GPL. See COPYING for details.
7 */
8

--- 742 unchanged lines hidden (view full) ---

751
752 return 0;
753
754error:
755 bgmac_dma_cleanup(bgmac);
756 return err;
757}
758
759/**************************************************
760 * PHY ops
761 **************************************************/
762
759
763static u16 bgmac_phy_read(struct bgmac *bgmac, u8 phyaddr, u8 reg)
764{
765 struct bcma_device *core;
766 u16 phy_access_addr;
767 u16 phy_ctl_addr;
768 u32 tmp;
769
770 BUILD_BUG_ON(BGMAC_PA_DATA_MASK != BCMA_GMAC_CMN_PA_DATA_MASK);
771 BUILD_BUG_ON(BGMAC_PA_ADDR_MASK != BCMA_GMAC_CMN_PA_ADDR_MASK);
772 BUILD_BUG_ON(BGMAC_PA_ADDR_SHIFT != BCMA_GMAC_CMN_PA_ADDR_SHIFT);
773 BUILD_BUG_ON(BGMAC_PA_REG_MASK != BCMA_GMAC_CMN_PA_REG_MASK);
774 BUILD_BUG_ON(BGMAC_PA_REG_SHIFT != BCMA_GMAC_CMN_PA_REG_SHIFT);
775 BUILD_BUG_ON(BGMAC_PA_WRITE != BCMA_GMAC_CMN_PA_WRITE);
776 BUILD_BUG_ON(BGMAC_PA_START != BCMA_GMAC_CMN_PA_START);
777 BUILD_BUG_ON(BGMAC_PC_EPA_MASK != BCMA_GMAC_CMN_PC_EPA_MASK);
778 BUILD_BUG_ON(BGMAC_PC_MCT_MASK != BCMA_GMAC_CMN_PC_MCT_MASK);
779 BUILD_BUG_ON(BGMAC_PC_MCT_SHIFT != BCMA_GMAC_CMN_PC_MCT_SHIFT);
780 BUILD_BUG_ON(BGMAC_PC_MTE != BCMA_GMAC_CMN_PC_MTE);
781
782 if (bgmac->core->id.id == BCMA_CORE_4706_MAC_GBIT) {
783 core = bgmac->core->bus->drv_gmac_cmn.core;
784 phy_access_addr = BCMA_GMAC_CMN_PHY_ACCESS;
785 phy_ctl_addr = BCMA_GMAC_CMN_PHY_CTL;
786 } else {
787 core = bgmac->core;
788 phy_access_addr = BGMAC_PHY_ACCESS;
789 phy_ctl_addr = BGMAC_PHY_CNTL;
790 }
791
792 tmp = bcma_read32(core, phy_ctl_addr);
793 tmp &= ~BGMAC_PC_EPA_MASK;
794 tmp |= phyaddr;
795 bcma_write32(core, phy_ctl_addr, tmp);
796
797 tmp = BGMAC_PA_START;
798 tmp |= phyaddr << BGMAC_PA_ADDR_SHIFT;
799 tmp |= reg << BGMAC_PA_REG_SHIFT;
800 bcma_write32(core, phy_access_addr, tmp);
801
802 if (!bgmac_wait_value(core, phy_access_addr, BGMAC_PA_START, 0, 1000)) {
803 dev_err(bgmac->dev, "Reading PHY %d register 0x%X failed\n",
804 phyaddr, reg);
805 return 0xffff;
806 }
807
808 return bcma_read32(core, phy_access_addr) & BGMAC_PA_DATA_MASK;
809}
810
811/* http://bcm-v4.sipsolutions.net/mac-gbit/gmac/chipphywr */
812static int bgmac_phy_write(struct bgmac *bgmac, u8 phyaddr, u8 reg, u16 value)
813{
814 struct bcma_device *core;
815 u16 phy_access_addr;
816 u16 phy_ctl_addr;
817 u32 tmp;
818
819 if (bgmac->core->id.id == BCMA_CORE_4706_MAC_GBIT) {
820 core = bgmac->core->bus->drv_gmac_cmn.core;
821 phy_access_addr = BCMA_GMAC_CMN_PHY_ACCESS;
822 phy_ctl_addr = BCMA_GMAC_CMN_PHY_CTL;
823 } else {
824 core = bgmac->core;
825 phy_access_addr = BGMAC_PHY_ACCESS;
826 phy_ctl_addr = BGMAC_PHY_CNTL;
827 }
828
829 tmp = bcma_read32(core, phy_ctl_addr);
830 tmp &= ~BGMAC_PC_EPA_MASK;
831 tmp |= phyaddr;
832 bcma_write32(core, phy_ctl_addr, tmp);
833
834 bgmac_write(bgmac, BGMAC_INT_STATUS, BGMAC_IS_MDIO);
835 if (bgmac_read(bgmac, BGMAC_INT_STATUS) & BGMAC_IS_MDIO)
836 dev_warn(bgmac->dev, "Error setting MDIO int\n");
837
838 tmp = BGMAC_PA_START;
839 tmp |= BGMAC_PA_WRITE;
840 tmp |= phyaddr << BGMAC_PA_ADDR_SHIFT;
841 tmp |= reg << BGMAC_PA_REG_SHIFT;
842 tmp |= value;
843 bcma_write32(core, phy_access_addr, tmp);
844
845 if (!bgmac_wait_value(core, phy_access_addr, BGMAC_PA_START, 0, 1000)) {
846 dev_err(bgmac->dev, "Writing to PHY %d register 0x%X failed\n",
847 phyaddr, reg);
848 return -ETIMEDOUT;
849 }
850
851 return 0;
852}
853
854/* http://bcm-v4.sipsolutions.net/mac-gbit/gmac/chipphyinit */
855static void bgmac_phy_init(struct bgmac *bgmac)
856{
857 struct bcma_chipinfo *ci = &bgmac->core->bus->chipinfo;
858 struct bcma_drv_cc *cc = &bgmac->core->bus->drv_cc;
859 u8 i;
860
861 if (ci->id == BCMA_CHIP_ID_BCM5356) {
862 for (i = 0; i < 5; i++) {
863 bgmac_phy_write(bgmac, i, 0x1f, 0x008b);
864 bgmac_phy_write(bgmac, i, 0x15, 0x0100);
865 bgmac_phy_write(bgmac, i, 0x1f, 0x000f);
866 bgmac_phy_write(bgmac, i, 0x12, 0x2aaa);
867 bgmac_phy_write(bgmac, i, 0x1f, 0x000b);
868 }
869 }
870 if ((ci->id == BCMA_CHIP_ID_BCM5357 && ci->pkg != 10) ||
871 (ci->id == BCMA_CHIP_ID_BCM4749 && ci->pkg != 10) ||
872 (ci->id == BCMA_CHIP_ID_BCM53572 && ci->pkg != 9)) {
873 bcma_chipco_chipctl_maskset(cc, 2, ~0xc0000000, 0);
874 bcma_chipco_chipctl_maskset(cc, 4, ~0x80000000, 0);
875 for (i = 0; i < 5; i++) {
876 bgmac_phy_write(bgmac, i, 0x1f, 0x000f);
877 bgmac_phy_write(bgmac, i, 0x16, 0x5284);
878 bgmac_phy_write(bgmac, i, 0x1f, 0x000b);
879 bgmac_phy_write(bgmac, i, 0x17, 0x0010);
880 bgmac_phy_write(bgmac, i, 0x1f, 0x000f);
881 bgmac_phy_write(bgmac, i, 0x16, 0x5296);
882 bgmac_phy_write(bgmac, i, 0x17, 0x1073);
883 bgmac_phy_write(bgmac, i, 0x17, 0x9073);
884 bgmac_phy_write(bgmac, i, 0x16, 0x52b6);
885 bgmac_phy_write(bgmac, i, 0x17, 0x9273);
886 bgmac_phy_write(bgmac, i, 0x1f, 0x000b);
887 }
888 }
889}
890
891/* http://bcm-v4.sipsolutions.net/mac-gbit/gmac/chipphyreset */
892static void bgmac_phy_reset(struct bgmac *bgmac)
893{
894 if (bgmac->phyaddr == BGMAC_PHY_NOREGS)
895 return;
896
897 bgmac_phy_write(bgmac, bgmac->phyaddr, MII_BMCR, BMCR_RESET);
898 udelay(100);
899 if (bgmac_phy_read(bgmac, bgmac->phyaddr, MII_BMCR) & BMCR_RESET)
900 dev_err(bgmac->dev, "PHY reset failed\n");
901 bgmac_phy_init(bgmac);
902}
903
904/**************************************************
905 * Chip ops
906 **************************************************/
907
908/* TODO: can we just drop @force? Can we don't reset MAC at all if there is
909 * nothing to change? Try if after stabilizng driver.
910 */
911static void bgmac_cmdcfg_maskset(struct bgmac *bgmac, u32 mask, u32 set,

--- 239 unchanged lines hidden (view full) ---

1151
1152 bgmac_clear_mib(bgmac);
1153 if (core->id.id == BCMA_CORE_4706_MAC_GBIT)
1154 bcma_maskset32(bgmac->cmn, BCMA_GMAC_CMN_PHY_CTL, ~0,
1155 BCMA_GMAC_CMN_PC_MTE);
1156 else
1157 bgmac_set(bgmac, BGMAC_PHY_CNTL, BGMAC_PC_MTE);
1158 bgmac_miiconfig(bgmac);
760/**************************************************
761 * Chip ops
762 **************************************************/
763
764/* TODO: can we just drop @force? Can we don't reset MAC at all if there is
765 * nothing to change? Try if after stabilizng driver.
766 */
767static void bgmac_cmdcfg_maskset(struct bgmac *bgmac, u32 mask, u32 set,

--- 239 unchanged lines hidden (view full) ---

1007
1008 bgmac_clear_mib(bgmac);
1009 if (core->id.id == BCMA_CORE_4706_MAC_GBIT)
1010 bcma_maskset32(bgmac->cmn, BCMA_GMAC_CMN_PHY_CTL, ~0,
1011 BCMA_GMAC_CMN_PC_MTE);
1012 else
1013 bgmac_set(bgmac, BGMAC_PHY_CNTL, BGMAC_PC_MTE);
1014 bgmac_miiconfig(bgmac);
1159 bgmac_phy_init(bgmac);
1015 if (bgmac->mii_bus)
1016 bgmac->mii_bus->reset(bgmac->mii_bus);
1160
1161 netdev_reset_queue(bgmac->net_dev);
1162}
1163
1164static void bgmac_chip_intrs_on(struct bgmac *bgmac)
1165{
1166 bgmac_write(bgmac, BGMAC_INT_MASK, bgmac->int_mask);
1167}

--- 361 unchanged lines hidden (view full) ---

1529 .get_link_ksettings = phy_ethtool_get_link_ksettings,
1530 .set_link_ksettings = phy_ethtool_set_link_ksettings,
1531};
1532
1533/**************************************************
1534 * MII
1535 **************************************************/
1536
1017
1018 netdev_reset_queue(bgmac->net_dev);
1019}
1020
1021static void bgmac_chip_intrs_on(struct bgmac *bgmac)
1022{
1023 bgmac_write(bgmac, BGMAC_INT_MASK, bgmac->int_mask);
1024}

--- 361 unchanged lines hidden (view full) ---

1386 .get_link_ksettings = phy_ethtool_get_link_ksettings,
1387 .set_link_ksettings = phy_ethtool_set_link_ksettings,
1388};
1389
1390/**************************************************
1391 * MII
1392 **************************************************/
1393
1537static int bgmac_mii_read(struct mii_bus *bus, int mii_id, int regnum)
1538{
1539 return bgmac_phy_read(bus->priv, mii_id, regnum);
1540}
1541
1542static int bgmac_mii_write(struct mii_bus *bus, int mii_id, int regnum,
1543 u16 value)
1544{
1545 return bgmac_phy_write(bus->priv, mii_id, regnum, value);
1546}
1547
1548static void bgmac_adjust_link(struct net_device *net_dev)
1549{
1550 struct bgmac *bgmac = netdev_priv(net_dev);
1551 struct phy_device *phy_dev = net_dev->phydev;
1552 bool update = false;
1553
1554 if (phy_dev->link) {
1555 if (phy_dev->speed != bgmac->mac_speed) {

--- 8 unchanged lines hidden (view full) ---

1564 }
1565
1566 if (update) {
1567 bgmac_mac_speed(bgmac);
1568 phy_print_status(phy_dev);
1569 }
1570}
1571
1394static void bgmac_adjust_link(struct net_device *net_dev)
1395{
1396 struct bgmac *bgmac = netdev_priv(net_dev);
1397 struct phy_device *phy_dev = net_dev->phydev;
1398 bool update = false;
1399
1400 if (phy_dev->link) {
1401 if (phy_dev->speed != bgmac->mac_speed) {

--- 8 unchanged lines hidden (view full) ---

1410 }
1411
1412 if (update) {
1413 bgmac_mac_speed(bgmac);
1414 phy_print_status(phy_dev);
1415 }
1416}
1417
1572static int bgmac_fixed_phy_register(struct bgmac *bgmac)
1418static int bgmac_phy_connect_direct(struct bgmac *bgmac)
1573{
1574 struct fixed_phy_status fphy_status = {
1575 .link = 1,
1576 .speed = SPEED_1000,
1577 .duplex = DUPLEX_FULL,
1578 };
1579 struct phy_device *phy_dev;
1580 int err;

--- 9 unchanged lines hidden (view full) ---

1590 if (err) {
1591 dev_err(bgmac->dev, "Connecting PHY failed\n");
1592 return err;
1593 }
1594
1595 return err;
1596}
1597
1419{
1420 struct fixed_phy_status fphy_status = {
1421 .link = 1,
1422 .speed = SPEED_1000,
1423 .duplex = DUPLEX_FULL,
1424 };
1425 struct phy_device *phy_dev;
1426 int err;

--- 9 unchanged lines hidden (view full) ---

1436 if (err) {
1437 dev_err(bgmac->dev, "Connecting PHY failed\n");
1438 return err;
1439 }
1440
1441 return err;
1442}
1443
1598static int bgmac_mii_register(struct bgmac *bgmac)
1444static int bgmac_phy_connect(struct bgmac *bgmac)
1599{
1445{
1600 struct mii_bus *mii_bus;
1601 struct phy_device *phy_dev;
1602 char bus_id[MII_BUS_ID_SIZE + 3];
1446 struct phy_device *phy_dev;
1447 char bus_id[MII_BUS_ID_SIZE + 3];
1603 int err = 0;
1604
1448
1605 if (bgmac_is_bcm4707_family(bgmac))
1606 return bgmac_fixed_phy_register(bgmac);
1607
1608 mii_bus = mdiobus_alloc();
1609 if (!mii_bus)
1610 return -ENOMEM;
1611
1612 mii_bus->name = "bgmac mii bus";
1613 sprintf(mii_bus->id, "%s-%d-%d", "bgmac", bgmac->core->bus->num,
1614 bgmac->core->core_unit);
1615 mii_bus->priv = bgmac;
1616 mii_bus->read = bgmac_mii_read;
1617 mii_bus->write = bgmac_mii_write;
1618 mii_bus->parent = &bgmac->core->dev;
1619 mii_bus->phy_mask = ~(1 << bgmac->phyaddr);
1620
1621 err = mdiobus_register(mii_bus);
1622 if (err) {
1623 dev_err(bgmac->dev, "Registration of mii bus failed\n");
1624 goto err_free_bus;
1625 }
1626
1627 bgmac->mii_bus = mii_bus;
1628
1629 /* Connect to the PHY */
1449 /* Connect to the PHY */
1630 snprintf(bus_id, sizeof(bus_id), PHY_ID_FMT, mii_bus->id,
1450 snprintf(bus_id, sizeof(bus_id), PHY_ID_FMT, bgmac->mii_bus->id,
1631 bgmac->phyaddr);
1632 phy_dev = phy_connect(bgmac->net_dev, bus_id, &bgmac_adjust_link,
1633 PHY_INTERFACE_MODE_MII);
1634 if (IS_ERR(phy_dev)) {
1635 dev_err(bgmac->dev, "PHY connecton failed\n");
1451 bgmac->phyaddr);
1452 phy_dev = phy_connect(bgmac->net_dev, bus_id, &bgmac_adjust_link,
1453 PHY_INTERFACE_MODE_MII);
1454 if (IS_ERR(phy_dev)) {
1455 dev_err(bgmac->dev, "PHY connecton failed\n");
1636 err = PTR_ERR(phy_dev);
1637 goto err_unregister_bus;
1456 return PTR_ERR(phy_dev);
1638 }
1639
1457 }
1458
1640 return err;
1641
1642err_unregister_bus:
1643 mdiobus_unregister(mii_bus);
1644err_free_bus:
1645 mdiobus_free(mii_bus);
1646 return err;
1459 return 0;
1647}
1648
1460}
1461
1649static void bgmac_mii_unregister(struct bgmac *bgmac)
1650{
1651 struct mii_bus *mii_bus = bgmac->mii_bus;
1652
1653 mdiobus_unregister(mii_bus);
1654 mdiobus_free(mii_bus);
1655}
1656
1657/**************************************************
1658 * BCMA bus ops
1659 **************************************************/
1660
1661/* http://bcm-v4.sipsolutions.net/mac-gbit/gmac/chipattach */
1662static int bgmac_probe(struct bcma_device *core)
1663{
1664 struct net_device *net_dev;
1665 struct bgmac *bgmac;
1666 struct ssb_sprom *sprom = &core->bus->sprom;
1667 u8 *mac;
1668 int err;
1669

--- 104 unchanged lines hidden (view full) ---

1774 dev_err(bgmac->dev, "Unable to alloc memory for DMA\n");
1775 goto err_netdev_free;
1776 }
1777
1778 bgmac->int_mask = BGMAC_IS_ERRMASK | BGMAC_IS_RX | BGMAC_IS_TX_MASK;
1779 if (bcm47xx_nvram_getenv("et0_no_txint", NULL, 0) == 0)
1780 bgmac->int_mask &= ~BGMAC_IS_TX_MASK;
1781
1462static int bgmac_probe(struct bcma_device *core)
1463{
1464 struct net_device *net_dev;
1465 struct bgmac *bgmac;
1466 struct ssb_sprom *sprom = &core->bus->sprom;
1467 u8 *mac;
1468 int err;
1469

--- 104 unchanged lines hidden (view full) ---

1574 dev_err(bgmac->dev, "Unable to alloc memory for DMA\n");
1575 goto err_netdev_free;
1576 }
1577
1578 bgmac->int_mask = BGMAC_IS_ERRMASK | BGMAC_IS_RX | BGMAC_IS_TX_MASK;
1579 if (bcm47xx_nvram_getenv("et0_no_txint", NULL, 0) == 0)
1580 bgmac->int_mask &= ~BGMAC_IS_TX_MASK;
1581
1782 /* TODO: reset the external phy. Specs are needed */
1783 bgmac_phy_reset(bgmac);
1784
1785 bgmac->has_robosw = !!(core->bus->sprom.boardflags_lo &
1786 BGMAC_BFL_ENETROBO);
1787 if (bgmac->has_robosw)
1788 dev_warn(bgmac->dev, "Support for Roboswitch not implemented\n");
1789
1790 if (core->bus->sprom.boardflags_lo & BGMAC_BFL_ENETADM)
1791 dev_warn(bgmac->dev, "Support for ADMtek ethernet switch not implemented\n");
1792
1793 netif_napi_add(net_dev, &bgmac->napi, bgmac_poll, BGMAC_WEIGHT);
1794
1582 bgmac->has_robosw = !!(core->bus->sprom.boardflags_lo &
1583 BGMAC_BFL_ENETROBO);
1584 if (bgmac->has_robosw)
1585 dev_warn(bgmac->dev, "Support for Roboswitch not implemented\n");
1586
1587 if (core->bus->sprom.boardflags_lo & BGMAC_BFL_ENETADM)
1588 dev_warn(bgmac->dev, "Support for ADMtek ethernet switch not implemented\n");
1589
1590 netif_napi_add(net_dev, &bgmac->napi, bgmac_poll, BGMAC_WEIGHT);
1591
1795 err = bgmac_mii_register(bgmac);
1592 if (!bgmac_is_bcm4707_family(bgmac)) {
1593 struct mii_bus *mii_bus;
1594
1595 mii_bus = bcma_mdio_mii_register(core, bgmac->phyaddr);
1596 if (!IS_ERR(mii_bus)) {
1597 err = PTR_ERR(mii_bus);
1598 goto err_dma_free;
1599 }
1600
1601 bgmac->mii_bus = mii_bus;
1602 }
1603
1604 if (!bgmac->mii_bus)
1605 err = bgmac_phy_connect_direct(bgmac);
1606 else
1607 err = bgmac_phy_connect(bgmac);
1796 if (err) {
1797 dev_err(bgmac->dev, "Cannot connect to phy\n");
1608 if (err) {
1609 dev_err(bgmac->dev, "Cannot connect to phy\n");
1798 goto err_dma_free;
1610 goto err_mii_unregister;
1799 }
1800
1801 net_dev->features = NETIF_F_SG | NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM;
1802 net_dev->hw_features = net_dev->features;
1803 net_dev->vlan_features = net_dev->features;
1804
1805 err = register_netdev(bgmac->net_dev);
1806 if (err) {
1807 dev_err(bgmac->dev, "Cannot register net device\n");
1611 }
1612
1613 net_dev->features = NETIF_F_SG | NETIF_F_IP_CSUM | NETIF_F_IPV6_CSUM;
1614 net_dev->hw_features = net_dev->features;
1615 net_dev->vlan_features = net_dev->features;
1616
1617 err = register_netdev(bgmac->net_dev);
1618 if (err) {
1619 dev_err(bgmac->dev, "Cannot register net device\n");
1808 goto err_mii_unregister;
1620 goto err_phy_disconnect;
1809 }
1810
1811 netif_carrier_off(net_dev);
1812
1813 return 0;
1814
1621 }
1622
1623 netif_carrier_off(net_dev);
1624
1625 return 0;
1626
1627err_phy_disconnect:
1628 phy_disconnect(net_dev->phydev);
1815err_mii_unregister:
1629err_mii_unregister:
1816 bgmac_mii_unregister(bgmac);
1630 bcma_mdio_mii_unregister(bgmac->mii_bus);
1817err_dma_free:
1818 bgmac_dma_free(bgmac);
1631err_dma_free:
1632 bgmac_dma_free(bgmac);
1819
1820err_netdev_free:
1821 bcma_set_drvdata(core, NULL);
1822 free_netdev(net_dev);
1823
1824 return err;
1825}
1826
1827static void bgmac_remove(struct bcma_device *core)
1828{
1829 struct bgmac *bgmac = bcma_get_drvdata(core);
1830
1831 unregister_netdev(bgmac->net_dev);
1633err_netdev_free:
1634 bcma_set_drvdata(core, NULL);
1635 free_netdev(net_dev);
1636
1637 return err;
1638}
1639
1640static void bgmac_remove(struct bcma_device *core)
1641{
1642 struct bgmac *bgmac = bcma_get_drvdata(core);
1643
1644 unregister_netdev(bgmac->net_dev);
1832 bgmac_mii_unregister(bgmac);
1645 phy_disconnect(bgmac->net_dev->phydev);
1646 bcma_mdio_mii_unregister(bgmac->mii_bus);
1833 netif_napi_del(&bgmac->napi);
1834 bgmac_dma_free(bgmac);
1835 bcma_set_drvdata(core, NULL);
1836 free_netdev(bgmac->net_dev);
1837}
1838
1839static struct bcma_driver bgmac_bcma_driver = {
1840 .name = KBUILD_MODNAME,

--- 27 unchanged lines hidden ---
1647 netif_napi_del(&bgmac->napi);
1648 bgmac_dma_free(bgmac);
1649 bcma_set_drvdata(core, NULL);
1650 free_netdev(bgmac->net_dev);
1651}
1652
1653static struct bcma_driver bgmac_bcma_driver = {
1654 .name = KBUILD_MODNAME,

--- 27 unchanged lines hidden ---