icplus.c 8.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352
  1. // SPDX-License-Identifier: GPL-2.0+
  2. /*
  3. * Driver for ICPlus PHYs
  4. *
  5. * Copyright (c) 2007 Freescale Semiconductor, Inc.
  6. */
  7. #include <linux/kernel.h>
  8. #include <linux/string.h>
  9. #include <linux/errno.h>
  10. #include <linux/unistd.h>
  11. #include <linux/interrupt.h>
  12. #include <linux/init.h>
  13. #include <linux/delay.h>
  14. #include <linux/netdevice.h>
  15. #include <linux/etherdevice.h>
  16. #include <linux/skbuff.h>
  17. #include <linux/spinlock.h>
  18. #include <linux/mm.h>
  19. #include <linux/module.h>
  20. #include <linux/mii.h>
  21. #include <linux/ethtool.h>
  22. #include <linux/phy.h>
  23. #include <linux/property.h>
  24. #include <asm/io.h>
  25. #include <asm/irq.h>
  26. #include <linux/uaccess.h>
  27. MODULE_DESCRIPTION("ICPlus IP175C/IP101A/IP101G/IC1001 PHY drivers");
  28. MODULE_AUTHOR("Michael Barkowski");
  29. MODULE_LICENSE("GPL");
  30. /* IP101A/G - IP1001 */
  31. #define IP10XX_SPEC_CTRL_STATUS 16 /* Spec. Control Register */
  32. #define IP1001_RXPHASE_SEL BIT(0) /* Add delay on RX_CLK */
  33. #define IP1001_TXPHASE_SEL BIT(1) /* Add delay on TX_CLK */
  34. #define IP1001_SPEC_CTRL_STATUS_2 20 /* IP1001 Spec. Control Reg 2 */
  35. #define IP1001_APS_ON 11 /* IP1001 APS Mode bit */
  36. #define IP101A_G_APS_ON BIT(1) /* IP101A/G APS Mode bit */
  37. #define IP101A_G_IRQ_CONF_STATUS 0x11 /* Conf Info IRQ & Status Reg */
  38. #define IP101A_G_IRQ_PIN_USED BIT(15) /* INTR pin used */
  39. #define IP101A_G_IRQ_ALL_MASK BIT(11) /* IRQ's inactive */
  40. #define IP101A_G_IRQ_SPEED_CHANGE BIT(2)
  41. #define IP101A_G_IRQ_DUPLEX_CHANGE BIT(1)
  42. #define IP101A_G_IRQ_LINK_CHANGE BIT(0)
  43. #define IP101G_DIGITAL_IO_SPEC_CTRL 0x1d
  44. #define IP101G_DIGITAL_IO_SPEC_CTRL_SEL_INTR32 BIT(2)
  45. /* The 32-pin IP101GR package can re-configure the mode of the RXER/INTR_32 pin
  46. * (pin number 21). The hardware default is RXER (receive error) mode. But it
  47. * can be configured to interrupt mode manually.
  48. */
  49. enum ip101gr_sel_intr32 {
  50. IP101GR_SEL_INTR32_KEEP,
  51. IP101GR_SEL_INTR32_INTR,
  52. IP101GR_SEL_INTR32_RXER,
  53. };
  54. struct ip101a_g_phy_priv {
  55. enum ip101gr_sel_intr32 sel_intr32;
  56. };
  57. static int ip175c_config_init(struct phy_device *phydev)
  58. {
  59. int err, i;
  60. static int full_reset_performed;
  61. if (full_reset_performed == 0) {
  62. /* master reset */
  63. err = mdiobus_write(phydev->mdio.bus, 30, 0, 0x175c);
  64. if (err < 0)
  65. return err;
  66. /* ensure no bus delays overlap reset period */
  67. err = mdiobus_read(phydev->mdio.bus, 30, 0);
  68. /* data sheet specifies reset period is 2 msec */
  69. mdelay(2);
  70. /* enable IP175C mode */
  71. err = mdiobus_write(phydev->mdio.bus, 29, 31, 0x175c);
  72. if (err < 0)
  73. return err;
  74. /* Set MII0 speed and duplex (in PHY mode) */
  75. err = mdiobus_write(phydev->mdio.bus, 29, 22, 0x420);
  76. if (err < 0)
  77. return err;
  78. /* reset switch ports */
  79. for (i = 0; i < 5; i++) {
  80. err = mdiobus_write(phydev->mdio.bus, i,
  81. MII_BMCR, BMCR_RESET);
  82. if (err < 0)
  83. return err;
  84. }
  85. for (i = 0; i < 5; i++)
  86. err = mdiobus_read(phydev->mdio.bus, i, MII_BMCR);
  87. mdelay(2);
  88. full_reset_performed = 1;
  89. }
  90. if (phydev->mdio.addr != 4) {
  91. phydev->state = PHY_RUNNING;
  92. phydev->speed = SPEED_100;
  93. phydev->duplex = DUPLEX_FULL;
  94. phydev->link = 1;
  95. netif_carrier_on(phydev->attached_dev);
  96. }
  97. return 0;
  98. }
  99. static int ip1xx_reset(struct phy_device *phydev)
  100. {
  101. int bmcr;
  102. /* Software Reset PHY */
  103. bmcr = phy_read(phydev, MII_BMCR);
  104. if (bmcr < 0)
  105. return bmcr;
  106. bmcr |= BMCR_RESET;
  107. bmcr = phy_write(phydev, MII_BMCR, bmcr);
  108. if (bmcr < 0)
  109. return bmcr;
  110. do {
  111. bmcr = phy_read(phydev, MII_BMCR);
  112. if (bmcr < 0)
  113. return bmcr;
  114. } while (bmcr & BMCR_RESET);
  115. return 0;
  116. }
  117. static int ip1001_config_init(struct phy_device *phydev)
  118. {
  119. int c;
  120. c = ip1xx_reset(phydev);
  121. if (c < 0)
  122. return c;
  123. /* Enable Auto Power Saving mode */
  124. c = phy_read(phydev, IP1001_SPEC_CTRL_STATUS_2);
  125. if (c < 0)
  126. return c;
  127. c |= IP1001_APS_ON;
  128. c = phy_write(phydev, IP1001_SPEC_CTRL_STATUS_2, c);
  129. if (c < 0)
  130. return c;
  131. if (phy_interface_is_rgmii(phydev)) {
  132. c = phy_read(phydev, IP10XX_SPEC_CTRL_STATUS);
  133. if (c < 0)
  134. return c;
  135. c &= ~(IP1001_RXPHASE_SEL | IP1001_TXPHASE_SEL);
  136. if (phydev->interface == PHY_INTERFACE_MODE_RGMII_ID)
  137. c |= (IP1001_RXPHASE_SEL | IP1001_TXPHASE_SEL);
  138. else if (phydev->interface == PHY_INTERFACE_MODE_RGMII_RXID)
  139. c |= IP1001_RXPHASE_SEL;
  140. else if (phydev->interface == PHY_INTERFACE_MODE_RGMII_TXID)
  141. c |= IP1001_TXPHASE_SEL;
  142. c = phy_write(phydev, IP10XX_SPEC_CTRL_STATUS, c);
  143. if (c < 0)
  144. return c;
  145. }
  146. return 0;
  147. }
  148. static int ip175c_read_status(struct phy_device *phydev)
  149. {
  150. if (phydev->mdio.addr == 4) /* WAN port */
  151. genphy_read_status(phydev);
  152. else
  153. /* Don't need to read status for switch ports */
  154. phydev->irq = PHY_IGNORE_INTERRUPT;
  155. return 0;
  156. }
  157. static int ip175c_config_aneg(struct phy_device *phydev)
  158. {
  159. if (phydev->mdio.addr == 4) /* WAN port */
  160. genphy_config_aneg(phydev);
  161. return 0;
  162. }
  163. static int ip101a_g_probe(struct phy_device *phydev)
  164. {
  165. struct device *dev = &phydev->mdio.dev;
  166. struct ip101a_g_phy_priv *priv;
  167. priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
  168. if (!priv)
  169. return -ENOMEM;
  170. /* Both functions (RX error and interrupt status) are sharing the same
  171. * pin on the 32-pin IP101GR, so this is an exclusive choice.
  172. */
  173. if (device_property_read_bool(dev, "icplus,select-rx-error") &&
  174. device_property_read_bool(dev, "icplus,select-interrupt")) {
  175. dev_err(dev,
  176. "RXER and INTR mode cannot be selected together\n");
  177. return -EINVAL;
  178. }
  179. if (device_property_read_bool(dev, "icplus,select-rx-error"))
  180. priv->sel_intr32 = IP101GR_SEL_INTR32_RXER;
  181. else if (device_property_read_bool(dev, "icplus,select-interrupt"))
  182. priv->sel_intr32 = IP101GR_SEL_INTR32_INTR;
  183. else
  184. priv->sel_intr32 = IP101GR_SEL_INTR32_KEEP;
  185. phydev->priv = priv;
  186. return 0;
  187. }
  188. static int ip101a_g_config_init(struct phy_device *phydev)
  189. {
  190. struct ip101a_g_phy_priv *priv = phydev->priv;
  191. int err, c;
  192. c = ip1xx_reset(phydev);
  193. if (c < 0)
  194. return c;
  195. /* configure the RXER/INTR_32 pin of the 32-pin IP101GR if needed: */
  196. switch (priv->sel_intr32) {
  197. case IP101GR_SEL_INTR32_RXER:
  198. err = phy_modify(phydev, IP101G_DIGITAL_IO_SPEC_CTRL,
  199. IP101G_DIGITAL_IO_SPEC_CTRL_SEL_INTR32, 0);
  200. if (err < 0)
  201. return err;
  202. break;
  203. case IP101GR_SEL_INTR32_INTR:
  204. err = phy_modify(phydev, IP101G_DIGITAL_IO_SPEC_CTRL,
  205. IP101G_DIGITAL_IO_SPEC_CTRL_SEL_INTR32,
  206. IP101G_DIGITAL_IO_SPEC_CTRL_SEL_INTR32);
  207. if (err < 0)
  208. return err;
  209. break;
  210. default:
  211. /* Don't touch IP101G_DIGITAL_IO_SPEC_CTRL because it's not
  212. * documented on IP101A and it's not clear whether this would
  213. * cause problems.
  214. * For the 32-pin IP101GR we simply keep the SEL_INTR32
  215. * configuration as set by the bootloader when not configured
  216. * to one of the special functions.
  217. */
  218. break;
  219. }
  220. /* Enable Auto Power Saving mode */
  221. c = phy_read(phydev, IP10XX_SPEC_CTRL_STATUS);
  222. c |= IP101A_G_APS_ON;
  223. return phy_write(phydev, IP10XX_SPEC_CTRL_STATUS, c);
  224. }
  225. static int ip101a_g_config_intr(struct phy_device *phydev)
  226. {
  227. u16 val;
  228. if (phydev->interrupts == PHY_INTERRUPT_ENABLED)
  229. /* INTR pin used: Speed/link/duplex will cause an interrupt */
  230. val = IP101A_G_IRQ_PIN_USED;
  231. else
  232. val = IP101A_G_IRQ_ALL_MASK;
  233. return phy_write(phydev, IP101A_G_IRQ_CONF_STATUS, val);
  234. }
  235. static int ip101a_g_did_interrupt(struct phy_device *phydev)
  236. {
  237. int val = phy_read(phydev, IP101A_G_IRQ_CONF_STATUS);
  238. if (val < 0)
  239. return 0;
  240. return val & (IP101A_G_IRQ_SPEED_CHANGE |
  241. IP101A_G_IRQ_DUPLEX_CHANGE |
  242. IP101A_G_IRQ_LINK_CHANGE);
  243. }
  244. static int ip101a_g_ack_interrupt(struct phy_device *phydev)
  245. {
  246. int err = phy_read(phydev, IP101A_G_IRQ_CONF_STATUS);
  247. if (err < 0)
  248. return err;
  249. return 0;
  250. }
  251. static struct phy_driver icplus_driver[] = {
  252. {
  253. .phy_id = 0x02430d80,
  254. .name = "ICPlus IP175C",
  255. .phy_id_mask = 0x0ffffff0,
  256. /* PHY_BASIC_FEATURES */
  257. .config_init = &ip175c_config_init,
  258. .config_aneg = &ip175c_config_aneg,
  259. .read_status = &ip175c_read_status,
  260. .suspend = genphy_suspend,
  261. .resume = genphy_resume,
  262. }, {
  263. .phy_id = 0x02430d90,
  264. .name = "ICPlus IP1001",
  265. .phy_id_mask = 0x0ffffff0,
  266. /* PHY_GBIT_FEATURES */
  267. .config_init = &ip1001_config_init,
  268. .suspend = genphy_suspend,
  269. .resume = genphy_resume,
  270. }, {
  271. .phy_id = 0x02430c54,
  272. .name = "ICPlus IP101A/G",
  273. .phy_id_mask = 0x0ffffff0,
  274. /* PHY_BASIC_FEATURES */
  275. .probe = ip101a_g_probe,
  276. .config_intr = ip101a_g_config_intr,
  277. .did_interrupt = ip101a_g_did_interrupt,
  278. .ack_interrupt = ip101a_g_ack_interrupt,
  279. .config_init = &ip101a_g_config_init,
  280. .suspend = genphy_suspend,
  281. .resume = genphy_resume,
  282. } };
  283. module_phy_driver(icplus_driver);
  284. static struct mdio_device_id __maybe_unused icplus_tbl[] = {
  285. { 0x02430d80, 0x0ffffff0 },
  286. { 0x02430d90, 0x0ffffff0 },
  287. { 0x02430c54, 0x0ffffff0 },
  288. { }
  289. };
  290. MODULE_DEVICE_TABLE(mdio, icplus_tbl);