aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/phy
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/phy')
-rw-r--r--drivers/net/phy/Kconfig5
-rw-r--r--drivers/net/phy/Makefile1
-rw-r--r--drivers/net/phy/bcm63xx.c8
-rw-r--r--drivers/net/phy/broadcom.c16
-rw-r--r--drivers/net/phy/cicada.c9
-rw-r--r--drivers/net/phy/davicom.c10
-rw-r--r--drivers/net/phy/et1011c.c8
-rw-r--r--drivers/net/phy/fixed.c1
-rw-r--r--drivers/net/phy/icplus.c8
-rw-r--r--drivers/net/phy/lxt.c9
-rw-r--r--drivers/net/phy/marvell.c14
-rw-r--r--drivers/net/phy/mdio-bitbang.c61
-rw-r--r--drivers/net/phy/mdio-octeon.c11
-rw-r--r--drivers/net/phy/mdio_bus.c4
-rw-r--r--drivers/net/phy/micrel.c114
-rw-r--r--drivers/net/phy/national.c7
-rw-r--r--drivers/net/phy/phy.c1
-rw-r--r--drivers/net/phy/phy_device.c12
-rw-r--r--drivers/net/phy/qsemi.c8
-rw-r--r--drivers/net/phy/realtek.c7
-rw-r--r--drivers/net/phy/smsc.c11
-rw-r--r--drivers/net/phy/ste10Xp.c8
-rw-r--r--drivers/net/phy/vitesse.c8
23 files changed, 321 insertions, 20 deletions
diff --git a/drivers/net/phy/Kconfig b/drivers/net/phy/Kconfig
index fc5938ba3d78..a527e37728cd 100644
--- a/drivers/net/phy/Kconfig
+++ b/drivers/net/phy/Kconfig
@@ -88,6 +88,11 @@ config LSI_ET1011C_PHY
88 ---help--- 88 ---help---
89 Supports the LSI ET1011C PHY. 89 Supports the LSI ET1011C PHY.
90 90
91config MICREL_PHY
92 tristate "Driver for Micrel PHYs"
93 ---help---
94 Supports the KSZ9021, VSC8201, KS8001 PHYs.
95
91config FIXED_PHY 96config FIXED_PHY
92 bool "Driver for MDIO Bus/PHY emulation with fixed speed/link PHYs" 97 bool "Driver for MDIO Bus/PHY emulation with fixed speed/link PHYs"
93 depends on PHYLIB=y 98 depends on PHYLIB=y
diff --git a/drivers/net/phy/Makefile b/drivers/net/phy/Makefile
index 1342585af381..13bebab65d02 100644
--- a/drivers/net/phy/Makefile
+++ b/drivers/net/phy/Makefile
@@ -20,4 +20,5 @@ obj-$(CONFIG_MDIO_BITBANG) += mdio-bitbang.o
20obj-$(CONFIG_MDIO_GPIO) += mdio-gpio.o 20obj-$(CONFIG_MDIO_GPIO) += mdio-gpio.o
21obj-$(CONFIG_NATIONAL_PHY) += national.o 21obj-$(CONFIG_NATIONAL_PHY) += national.o
22obj-$(CONFIG_STE10XP) += ste10Xp.o 22obj-$(CONFIG_STE10XP) += ste10Xp.o
23obj-$(CONFIG_MICREL_PHY) += micrel.o
23obj-$(CONFIG_MDIO_OCTEON) += mdio-octeon.o 24obj-$(CONFIG_MDIO_OCTEON) += mdio-octeon.o
diff --git a/drivers/net/phy/bcm63xx.c b/drivers/net/phy/bcm63xx.c
index 4fed95e8350e..c12815679837 100644
--- a/drivers/net/phy/bcm63xx.c
+++ b/drivers/net/phy/bcm63xx.c
@@ -130,3 +130,11 @@ static void __exit bcm63xx_phy_exit(void)
130 130
131module_init(bcm63xx_phy_init); 131module_init(bcm63xx_phy_init);
132module_exit(bcm63xx_phy_exit); 132module_exit(bcm63xx_phy_exit);
133
134static struct mdio_device_id bcm63xx_tbl[] = {
135 { 0x00406000, 0xfffffc00 },
136 { 0x002bdc00, 0xfffffc00 },
137 { }
138};
139
140MODULE_DEVICE_TABLE(mdio, bcm63xx_tbl);
diff --git a/drivers/net/phy/broadcom.c b/drivers/net/phy/broadcom.c
index f482fc4f8cf1..cecdbbd549ec 100644
--- a/drivers/net/phy/broadcom.c
+++ b/drivers/net/phy/broadcom.c
@@ -908,3 +908,19 @@ static void __exit broadcom_exit(void)
908 908
909module_init(broadcom_init); 909module_init(broadcom_init);
910module_exit(broadcom_exit); 910module_exit(broadcom_exit);
911
912static struct mdio_device_id broadcom_tbl[] = {
913 { 0x00206070, 0xfffffff0 },
914 { 0x002060e0, 0xfffffff0 },
915 { 0x002060c0, 0xfffffff0 },
916 { 0x002060b0, 0xfffffff0 },
917 { 0x0143bca0, 0xfffffff0 },
918 { 0x0143bcb0, 0xfffffff0 },
919 { PHY_ID_BCM50610, 0xfffffff0 },
920 { PHY_ID_BCM50610M, 0xfffffff0 },
921 { PHY_ID_BCM57780, 0xfffffff0 },
922 { PHY_ID_BCMAC131, 0xfffffff0 },
923 { }
924};
925
926MODULE_DEVICE_TABLE(mdio, broadcom_tbl);
diff --git a/drivers/net/phy/cicada.c b/drivers/net/phy/cicada.c
index a1bd599c8a5b..1a325d63756b 100644
--- a/drivers/net/phy/cicada.c
+++ b/drivers/net/phy/cicada.c
@@ -17,7 +17,6 @@
17#include <linux/string.h> 17#include <linux/string.h>
18#include <linux/errno.h> 18#include <linux/errno.h>
19#include <linux/unistd.h> 19#include <linux/unistd.h>
20#include <linux/slab.h>
21#include <linux/interrupt.h> 20#include <linux/interrupt.h>
22#include <linux/init.h> 21#include <linux/init.h>
23#include <linux/delay.h> 22#include <linux/delay.h>
@@ -159,3 +158,11 @@ static void __exit cicada_exit(void)
159 158
160module_init(cicada_init); 159module_init(cicada_init);
161module_exit(cicada_exit); 160module_exit(cicada_exit);
161
162static struct mdio_device_id cicada_tbl[] = {
163 { 0x000fc410, 0x000ffff0 },
164 { 0x000fc440, 0x000fffc0 },
165 { }
166};
167
168MODULE_DEVICE_TABLE(mdio, cicada_tbl);
diff --git a/drivers/net/phy/davicom.c b/drivers/net/phy/davicom.c
index d926168bc780..29c17617a2ec 100644
--- a/drivers/net/phy/davicom.c
+++ b/drivers/net/phy/davicom.c
@@ -17,7 +17,6 @@
17#include <linux/string.h> 17#include <linux/string.h>
18#include <linux/errno.h> 18#include <linux/errno.h>
19#include <linux/unistd.h> 19#include <linux/unistd.h>
20#include <linux/slab.h>
21#include <linux/interrupt.h> 20#include <linux/interrupt.h>
22#include <linux/init.h> 21#include <linux/init.h>
23#include <linux/delay.h> 22#include <linux/delay.h>
@@ -219,3 +218,12 @@ static void __exit davicom_exit(void)
219 218
220module_init(davicom_init); 219module_init(davicom_init);
221module_exit(davicom_exit); 220module_exit(davicom_exit);
221
222static struct mdio_device_id davicom_tbl[] = {
223 { 0x0181b880, 0x0ffffff0 },
224 { 0x0181b8a0, 0x0ffffff0 },
225 { 0x00181b80, 0x0ffffff0 },
226 { }
227};
228
229MODULE_DEVICE_TABLE(mdio, davicom_tbl);
diff --git a/drivers/net/phy/et1011c.c b/drivers/net/phy/et1011c.c
index b031fa21f1aa..13995f52d6af 100644
--- a/drivers/net/phy/et1011c.c
+++ b/drivers/net/phy/et1011c.c
@@ -17,7 +17,6 @@
17#include <linux/string.h> 17#include <linux/string.h>
18#include <linux/errno.h> 18#include <linux/errno.h>
19#include <linux/unistd.h> 19#include <linux/unistd.h>
20#include <linux/slab.h>
21#include <linux/interrupt.h> 20#include <linux/interrupt.h>
22#include <linux/init.h> 21#include <linux/init.h>
23#include <linux/delay.h> 22#include <linux/delay.h>
@@ -111,3 +110,10 @@ static void __exit et1011c_exit(void)
111 110
112module_init(et1011c_init); 111module_init(et1011c_init);
113module_exit(et1011c_exit); 112module_exit(et1011c_exit);
113
114static struct mdio_device_id et1011c_tbl[] = {
115 { 0x0282f014, 0xfffffff0 },
116 { }
117};
118
119MODULE_DEVICE_TABLE(mdio, et1011c_tbl);
diff --git a/drivers/net/phy/fixed.c b/drivers/net/phy/fixed.c
index e7070515d2e3..1fa4d73c3cca 100644
--- a/drivers/net/phy/fixed.c
+++ b/drivers/net/phy/fixed.c
@@ -20,6 +20,7 @@
20#include <linux/phy.h> 20#include <linux/phy.h>
21#include <linux/phy_fixed.h> 21#include <linux/phy_fixed.h>
22#include <linux/err.h> 22#include <linux/err.h>
23#include <linux/slab.h>
23 24
24#define MII_REGS_NUM 29 25#define MII_REGS_NUM 29
25 26
diff --git a/drivers/net/phy/icplus.c b/drivers/net/phy/icplus.c
index af3f1f2a9f87..439adafeacb1 100644
--- a/drivers/net/phy/icplus.c
+++ b/drivers/net/phy/icplus.c
@@ -13,7 +13,6 @@
13#include <linux/string.h> 13#include <linux/string.h>
14#include <linux/errno.h> 14#include <linux/errno.h>
15#include <linux/unistd.h> 15#include <linux/unistd.h>
16#include <linux/slab.h>
17#include <linux/interrupt.h> 16#include <linux/interrupt.h>
18#include <linux/init.h> 17#include <linux/init.h>
19#include <linux/delay.h> 18#include <linux/delay.h>
@@ -132,3 +131,10 @@ static void __exit ip175c_exit(void)
132 131
133module_init(ip175c_init); 132module_init(ip175c_init);
134module_exit(ip175c_exit); 133module_exit(ip175c_exit);
134
135static struct mdio_device_id icplus_tbl[] = {
136 { 0x02430d80, 0x0ffffff0 },
137 { }
138};
139
140MODULE_DEVICE_TABLE(mdio, icplus_tbl);
diff --git a/drivers/net/phy/lxt.c b/drivers/net/phy/lxt.c
index 4cf3324ba166..8ee929b796d8 100644
--- a/drivers/net/phy/lxt.c
+++ b/drivers/net/phy/lxt.c
@@ -17,7 +17,6 @@
17#include <linux/string.h> 17#include <linux/string.h>
18#include <linux/errno.h> 18#include <linux/errno.h>
19#include <linux/unistd.h> 19#include <linux/unistd.h>
20#include <linux/slab.h>
21#include <linux/interrupt.h> 20#include <linux/interrupt.h>
22#include <linux/init.h> 21#include <linux/init.h>
23#include <linux/delay.h> 22#include <linux/delay.h>
@@ -174,3 +173,11 @@ static void __exit lxt_exit(void)
174 173
175module_init(lxt_init); 174module_init(lxt_init);
176module_exit(lxt_exit); 175module_exit(lxt_exit);
176
177static struct mdio_device_id lxt_tbl[] = {
178 { 0x78100000, 0xfffffff0 },
179 { 0x001378e0, 0xfffffff0 },
180 { }
181};
182
183MODULE_DEVICE_TABLE(mdio, lxt_tbl);
diff --git a/drivers/net/phy/marvell.c b/drivers/net/phy/marvell.c
index 65ed385c2ceb..78b74e83ce5d 100644
--- a/drivers/net/phy/marvell.c
+++ b/drivers/net/phy/marvell.c
@@ -17,7 +17,6 @@
17#include <linux/string.h> 17#include <linux/string.h>
18#include <linux/errno.h> 18#include <linux/errno.h>
19#include <linux/unistd.h> 19#include <linux/unistd.h>
20#include <linux/slab.h>
21#include <linux/interrupt.h> 20#include <linux/interrupt.h>
22#include <linux/init.h> 21#include <linux/init.h>
23#include <linux/delay.h> 22#include <linux/delay.h>
@@ -649,3 +648,16 @@ static void __exit marvell_exit(void)
649 648
650module_init(marvell_init); 649module_init(marvell_init);
651module_exit(marvell_exit); 650module_exit(marvell_exit);
651
652static struct mdio_device_id marvell_tbl[] = {
653 { 0x01410c60, 0xfffffff0 },
654 { 0x01410c90, 0xfffffff0 },
655 { 0x01410cc0, 0xfffffff0 },
656 { 0x01410e10, 0xfffffff0 },
657 { 0x01410cb0, 0xfffffff0 },
658 { 0x01410cd0, 0xfffffff0 },
659 { 0x01410e30, 0xfffffff0 },
660 { }
661};
662
663MODULE_DEVICE_TABLE(mdio, marvell_tbl);
diff --git a/drivers/net/phy/mdio-bitbang.c b/drivers/net/phy/mdio-bitbang.c
index 2576055b350b..65391891d8c4 100644
--- a/drivers/net/phy/mdio-bitbang.c
+++ b/drivers/net/phy/mdio-bitbang.c
@@ -19,12 +19,16 @@
19 19
20#include <linux/module.h> 20#include <linux/module.h>
21#include <linux/mdio-bitbang.h> 21#include <linux/mdio-bitbang.h>
22#include <linux/slab.h>
23#include <linux/types.h> 22#include <linux/types.h>
24#include <linux/delay.h> 23#include <linux/delay.h>
25 24
26#define MDIO_READ 1 25#define MDIO_READ 2
27#define MDIO_WRITE 0 26#define MDIO_WRITE 1
27
28#define MDIO_C45 (1<<15)
29#define MDIO_C45_ADDR (MDIO_C45 | 0)
30#define MDIO_C45_READ (MDIO_C45 | 3)
31#define MDIO_C45_WRITE (MDIO_C45 | 1)
28 32
29#define MDIO_SETUP_TIME 10 33#define MDIO_SETUP_TIME 10
30#define MDIO_HOLD_TIME 10 34#define MDIO_HOLD_TIME 10
@@ -90,7 +94,7 @@ static u16 mdiobb_get_num(struct mdiobb_ctrl *ctrl, int bits)
90/* Utility to send the preamble, address, and 94/* Utility to send the preamble, address, and
91 * register (common to read and write). 95 * register (common to read and write).
92 */ 96 */
93static void mdiobb_cmd(struct mdiobb_ctrl *ctrl, int read, u8 phy, u8 reg) 97static void mdiobb_cmd(struct mdiobb_ctrl *ctrl, int op, u8 phy, u8 reg)
94{ 98{
95 const struct mdiobb_ops *ops = ctrl->ops; 99 const struct mdiobb_ops *ops = ctrl->ops;
96 int i; 100 int i;
@@ -109,23 +113,56 @@ static void mdiobb_cmd(struct mdiobb_ctrl *ctrl, int read, u8 phy, u8 reg)
109 for (i = 0; i < 32; i++) 113 for (i = 0; i < 32; i++)
110 mdiobb_send_bit(ctrl, 1); 114 mdiobb_send_bit(ctrl, 1);
111 115
112 /* send the start bit (01) and the read opcode (10) or write (10) */ 116 /* send the start bit (01) and the read opcode (10) or write (10).
117 Clause 45 operation uses 00 for the start and 11, 10 for
118 read/write */
113 mdiobb_send_bit(ctrl, 0); 119 mdiobb_send_bit(ctrl, 0);
114 mdiobb_send_bit(ctrl, 1); 120 if (op & MDIO_C45)
115 mdiobb_send_bit(ctrl, read); 121 mdiobb_send_bit(ctrl, 0);
116 mdiobb_send_bit(ctrl, !read); 122 else
123 mdiobb_send_bit(ctrl, 1);
124 mdiobb_send_bit(ctrl, (op >> 1) & 1);
125 mdiobb_send_bit(ctrl, (op >> 0) & 1);
117 126
118 mdiobb_send_num(ctrl, phy, 5); 127 mdiobb_send_num(ctrl, phy, 5);
119 mdiobb_send_num(ctrl, reg, 5); 128 mdiobb_send_num(ctrl, reg, 5);
120} 129}
121 130
131/* In clause 45 mode all commands are prefixed by MDIO_ADDR to specify the
132 lower 16 bits of the 21 bit address. This transfer is done identically to a
133 MDIO_WRITE except for a different code. To enable clause 45 mode or
134 MII_ADDR_C45 into the address. Theoretically clause 45 and normal devices
135 can exist on the same bus. Normal devices should ignore the MDIO_ADDR
136 phase. */
137static int mdiobb_cmd_addr(struct mdiobb_ctrl *ctrl, int phy, u32 addr)
138{
139 unsigned int dev_addr = (addr >> 16) & 0x1F;
140 unsigned int reg = addr & 0xFFFF;
141 mdiobb_cmd(ctrl, MDIO_C45_ADDR, phy, dev_addr);
142
143 /* send the turnaround (10) */
144 mdiobb_send_bit(ctrl, 1);
145 mdiobb_send_bit(ctrl, 0);
146
147 mdiobb_send_num(ctrl, reg, 16);
148
149 ctrl->ops->set_mdio_dir(ctrl, 0);
150 mdiobb_get_bit(ctrl);
151
152 return dev_addr;
153}
122 154
123static int mdiobb_read(struct mii_bus *bus, int phy, int reg) 155static int mdiobb_read(struct mii_bus *bus, int phy, int reg)
124{ 156{
125 struct mdiobb_ctrl *ctrl = bus->priv; 157 struct mdiobb_ctrl *ctrl = bus->priv;
126 int ret, i; 158 int ret, i;
127 159
128 mdiobb_cmd(ctrl, MDIO_READ, phy, reg); 160 if (reg & MII_ADDR_C45) {
161 reg = mdiobb_cmd_addr(ctrl, phy, reg);
162 mdiobb_cmd(ctrl, MDIO_C45_READ, phy, reg);
163 } else
164 mdiobb_cmd(ctrl, MDIO_READ, phy, reg);
165
129 ctrl->ops->set_mdio_dir(ctrl, 0); 166 ctrl->ops->set_mdio_dir(ctrl, 0);
130 167
131 /* check the turnaround bit: the PHY should be driving it to zero */ 168 /* check the turnaround bit: the PHY should be driving it to zero */
@@ -148,7 +185,11 @@ static int mdiobb_write(struct mii_bus *bus, int phy, int reg, u16 val)
148{ 185{
149 struct mdiobb_ctrl *ctrl = bus->priv; 186 struct mdiobb_ctrl *ctrl = bus->priv;
150 187
151 mdiobb_cmd(ctrl, MDIO_WRITE, phy, reg); 188 if (reg & MII_ADDR_C45) {
189 reg = mdiobb_cmd_addr(ctrl, phy, reg);
190 mdiobb_cmd(ctrl, MDIO_C45_WRITE, phy, reg);
191 } else
192 mdiobb_cmd(ctrl, MDIO_WRITE, phy, reg);
152 193
153 /* send the turnaround (10) */ 194 /* send the turnaround (10) */
154 mdiobb_send_bit(ctrl, 1); 195 mdiobb_send_bit(ctrl, 1);
diff --git a/drivers/net/phy/mdio-octeon.c b/drivers/net/phy/mdio-octeon.c
index 61a4461cbda5..f443d43edd80 100644
--- a/drivers/net/phy/mdio-octeon.c
+++ b/drivers/net/phy/mdio-octeon.c
@@ -6,6 +6,7 @@
6 * Copyright (C) 2009 Cavium Networks 6 * Copyright (C) 2009 Cavium Networks
7 */ 7 */
8 8
9#include <linux/gfp.h>
9#include <linux/init.h> 10#include <linux/init.h>
10#include <linux/module.h> 11#include <linux/module.h>
11#include <linux/platform_device.h> 12#include <linux/platform_device.h>
@@ -87,6 +88,7 @@ static int octeon_mdiobus_write(struct mii_bus *bus, int phy_id,
87static int __init octeon_mdiobus_probe(struct platform_device *pdev) 88static int __init octeon_mdiobus_probe(struct platform_device *pdev)
88{ 89{
89 struct octeon_mdiobus *bus; 90 struct octeon_mdiobus *bus;
91 union cvmx_smix_en smi_en;
90 int i; 92 int i;
91 int err = -ENOENT; 93 int err = -ENOENT;
92 94
@@ -102,6 +104,10 @@ static int __init octeon_mdiobus_probe(struct platform_device *pdev)
102 if (!bus->mii_bus) 104 if (!bus->mii_bus)
103 goto err; 105 goto err;
104 106
107 smi_en.u64 = 0;
108 smi_en.s.en = 1;
109 cvmx_write_csr(CVMX_SMIX_EN(bus->unit), smi_en.u64);
110
105 /* 111 /*
106 * Standard Octeon evaluation boards don't support phy 112 * Standard Octeon evaluation boards don't support phy
107 * interrupts, we need to poll. 113 * interrupts, we need to poll.
@@ -132,17 +138,22 @@ err_register:
132 138
133err: 139err:
134 devm_kfree(&pdev->dev, bus); 140 devm_kfree(&pdev->dev, bus);
141 smi_en.u64 = 0;
142 cvmx_write_csr(CVMX_SMIX_EN(bus->unit), smi_en.u64);
135 return err; 143 return err;
136} 144}
137 145
138static int __exit octeon_mdiobus_remove(struct platform_device *pdev) 146static int __exit octeon_mdiobus_remove(struct platform_device *pdev)
139{ 147{
140 struct octeon_mdiobus *bus; 148 struct octeon_mdiobus *bus;
149 union cvmx_smix_en smi_en;
141 150
142 bus = dev_get_drvdata(&pdev->dev); 151 bus = dev_get_drvdata(&pdev->dev);
143 152
144 mdiobus_unregister(bus->mii_bus); 153 mdiobus_unregister(bus->mii_bus);
145 mdiobus_free(bus->mii_bus); 154 mdiobus_free(bus->mii_bus);
155 smi_en.u64 = 0;
156 cvmx_write_csr(CVMX_SMIX_EN(bus->unit), smi_en.u64);
146 return 0; 157 return 0;
147} 158}
148 159
diff --git a/drivers/net/phy/mdio_bus.c b/drivers/net/phy/mdio_bus.c
index e17b70291bbc..6a6b8199a0d6 100644
--- a/drivers/net/phy/mdio_bus.c
+++ b/drivers/net/phy/mdio_bus.c
@@ -208,7 +208,7 @@ EXPORT_SYMBOL(mdiobus_scan);
208 * because the bus read/write functions may wait for an interrupt 208 * because the bus read/write functions may wait for an interrupt
209 * to conclude the operation. 209 * to conclude the operation.
210 */ 210 */
211int mdiobus_read(struct mii_bus *bus, int addr, u16 regnum) 211int mdiobus_read(struct mii_bus *bus, int addr, u32 regnum)
212{ 212{
213 int retval; 213 int retval;
214 214
@@ -233,7 +233,7 @@ EXPORT_SYMBOL(mdiobus_read);
233 * because the bus read/write functions may wait for an interrupt 233 * because the bus read/write functions may wait for an interrupt
234 * to conclude the operation. 234 * to conclude the operation.
235 */ 235 */
236int mdiobus_write(struct mii_bus *bus, int addr, u16 regnum, u16 val) 236int mdiobus_write(struct mii_bus *bus, int addr, u32 regnum, u16 val)
237{ 237{
238 int err; 238 int err;
239 239
diff --git a/drivers/net/phy/micrel.c b/drivers/net/phy/micrel.c
new file mode 100644
index 000000000000..0692f750c404
--- /dev/null
+++ b/drivers/net/phy/micrel.c
@@ -0,0 +1,114 @@
1/*
2 * drivers/net/phy/micrel.c
3 *
4 * Driver for Micrel PHYs
5 *
6 * Author: David J. Choi
7 *
8 * Copyright (c) 2010 Micrel, Inc.
9 *
10 * This program is free software; you can redistribute it and/or modify it
11 * under the terms of the GNU General Public License as published by the
12 * Free Software Foundation; either version 2 of the License, or (at your
13 * option) any later version.
14 *
15 * Support : ksz9021 , vsc8201, ks8001
16 */
17
18#include <linux/kernel.h>
19#include <linux/module.h>
20#include <linux/phy.h>
21
22#define PHY_ID_KSZ9021 0x00221611
23#define PHY_ID_VSC8201 0x000FC413
24#define PHY_ID_KS8001 0x0022161A
25
26
27static int kszphy_config_init(struct phy_device *phydev)
28{
29 return 0;
30}
31
32
33static struct phy_driver ks8001_driver = {
34 .phy_id = PHY_ID_KS8001,
35 .name = "Micrel KS8001",
36 .phy_id_mask = 0x00fffff0,
37 .features = PHY_BASIC_FEATURES,
38 .flags = PHY_POLL,
39 .config_init = kszphy_config_init,
40 .config_aneg = genphy_config_aneg,
41 .read_status = genphy_read_status,
42 .driver = { .owner = THIS_MODULE,},
43};
44
45static struct phy_driver vsc8201_driver = {
46 .phy_id = PHY_ID_VSC8201,
47 .name = "Micrel VSC8201",
48 .phy_id_mask = 0x00fffff0,
49 .features = PHY_BASIC_FEATURES,
50 .flags = PHY_POLL,
51 .config_init = kszphy_config_init,
52 .config_aneg = genphy_config_aneg,
53 .read_status = genphy_read_status,
54 .driver = { .owner = THIS_MODULE,},
55};
56
57static struct phy_driver ksz9021_driver = {
58 .phy_id = PHY_ID_KSZ9021,
59 .phy_id_mask = 0x000fff10,
60 .name = "Micrel KSZ9021 Gigabit PHY",
61 .features = PHY_GBIT_FEATURES | SUPPORTED_Pause,
62 .flags = PHY_POLL,
63 .config_init = kszphy_config_init,
64 .config_aneg = genphy_config_aneg,
65 .read_status = genphy_read_status,
66 .driver = { .owner = THIS_MODULE, },
67};
68
69static int __init ksphy_init(void)
70{
71 int ret;
72
73 ret = phy_driver_register(&ks8001_driver);
74 if (ret)
75 goto err1;
76 ret = phy_driver_register(&vsc8201_driver);
77 if (ret)
78 goto err2;
79
80 ret = phy_driver_register(&ksz9021_driver);
81 if (ret)
82 goto err3;
83 return 0;
84
85err3:
86 phy_driver_unregister(&vsc8201_driver);
87err2:
88 phy_driver_unregister(&ks8001_driver);
89err1:
90 return ret;
91}
92
93static void __exit ksphy_exit(void)
94{
95 phy_driver_unregister(&ks8001_driver);
96 phy_driver_unregister(&vsc8201_driver);
97 phy_driver_unregister(&ksz9021_driver);
98}
99
100module_init(ksphy_init);
101module_exit(ksphy_exit);
102
103MODULE_DESCRIPTION("Micrel PHY driver");
104MODULE_AUTHOR("David J. Choi");
105MODULE_LICENSE("GPL");
106
107static struct mdio_device_id micrel_tbl[] = {
108 { PHY_ID_KSZ9021, 0x000fff10 },
109 { PHY_ID_VSC8201, 0x00fffff0 },
110 { PHY_ID_KS8001, 0x00fffff0 },
111 { }
112};
113
114MODULE_DEVICE_TABLE(mdio, micrel_tbl);
diff --git a/drivers/net/phy/national.c b/drivers/net/phy/national.c
index 6c636eb72089..729ab29ba28c 100644
--- a/drivers/net/phy/national.c
+++ b/drivers/net/phy/national.c
@@ -153,3 +153,10 @@ MODULE_LICENSE("GPL");
153 153
154module_init(ns_init); 154module_init(ns_init);
155module_exit(ns_exit); 155module_exit(ns_exit);
156
157static struct mdio_device_id ns_tbl[] = {
158 { DP83865_PHY_ID, 0xfffffff0 },
159 { }
160};
161
162MODULE_DEVICE_TABLE(mdio, ns_tbl);
diff --git a/drivers/net/phy/phy.c b/drivers/net/phy/phy.c
index 0295097d6c44..64be4664ccab 100644
--- a/drivers/net/phy/phy.c
+++ b/drivers/net/phy/phy.c
@@ -19,7 +19,6 @@
19#include <linux/string.h> 19#include <linux/string.h>
20#include <linux/errno.h> 20#include <linux/errno.h>
21#include <linux/unistd.h> 21#include <linux/unistd.h>
22#include <linux/slab.h>
23#include <linux/interrupt.h> 22#include <linux/interrupt.h>
24#include <linux/init.h> 23#include <linux/init.h>
25#include <linux/delay.h> 24#include <linux/delay.h>
diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c
index db1794546c56..1a99bb244106 100644
--- a/drivers/net/phy/phy_device.c
+++ b/drivers/net/phy/phy_device.c
@@ -149,6 +149,7 @@ EXPORT_SYMBOL(phy_scan_fixups);
149struct phy_device* phy_device_create(struct mii_bus *bus, int addr, int phy_id) 149struct phy_device* phy_device_create(struct mii_bus *bus, int addr, int phy_id)
150{ 150{
151 struct phy_device *dev; 151 struct phy_device *dev;
152
152 /* We allocate the device, and initialize the 153 /* We allocate the device, and initialize the
153 * default values */ 154 * default values */
154 dev = kzalloc(sizeof(*dev), GFP_KERNEL); 155 dev = kzalloc(sizeof(*dev), GFP_KERNEL);
@@ -179,6 +180,17 @@ struct phy_device* phy_device_create(struct mii_bus *bus, int addr, int phy_id)
179 mutex_init(&dev->lock); 180 mutex_init(&dev->lock);
180 INIT_DELAYED_WORK(&dev->state_queue, phy_state_machine); 181 INIT_DELAYED_WORK(&dev->state_queue, phy_state_machine);
181 182
183 /* Request the appropriate module unconditionally; don't
184 bother trying to do so only if it isn't already loaded,
185 because that gets complicated. A hotplug event would have
186 done an unconditional modprobe anyway.
187 We don't do normal hotplug because it won't work for MDIO
188 -- because it relies on the device staying around for long
189 enough for the driver to get loaded. With MDIO, the NIC
190 driver will get bored and give up as soon as it finds that
191 there's no driver _already_ loaded. */
192 request_module(MDIO_MODULE_PREFIX MDIO_ID_FMT, MDIO_ID_ARGS(phy_id));
193
182 return dev; 194 return dev;
183} 195}
184EXPORT_SYMBOL(phy_device_create); 196EXPORT_SYMBOL(phy_device_create);
diff --git a/drivers/net/phy/qsemi.c b/drivers/net/phy/qsemi.c
index 23062d067231..6736b23f1b28 100644
--- a/drivers/net/phy/qsemi.c
+++ b/drivers/net/phy/qsemi.c
@@ -17,7 +17,6 @@
17#include <linux/string.h> 17#include <linux/string.h>
18#include <linux/errno.h> 18#include <linux/errno.h>
19#include <linux/unistd.h> 19#include <linux/unistd.h>
20#include <linux/slab.h>
21#include <linux/interrupt.h> 20#include <linux/interrupt.h>
22#include <linux/init.h> 21#include <linux/init.h>
23#include <linux/delay.h> 22#include <linux/delay.h>
@@ -138,3 +137,10 @@ static void __exit qs6612_exit(void)
138 137
139module_init(qs6612_init); 138module_init(qs6612_init);
140module_exit(qs6612_exit); 139module_exit(qs6612_exit);
140
141static struct mdio_device_id qs6612_tbl[] = {
142 { 0x00181440, 0xfffffff0 },
143 { }
144};
145
146MODULE_DEVICE_TABLE(mdio, qs6612_tbl);
diff --git a/drivers/net/phy/realtek.c b/drivers/net/phy/realtek.c
index a052a6744a51..f567c0e1aaa1 100644
--- a/drivers/net/phy/realtek.c
+++ b/drivers/net/phy/realtek.c
@@ -78,3 +78,10 @@ static void __exit realtek_exit(void)
78 78
79module_init(realtek_init); 79module_init(realtek_init);
80module_exit(realtek_exit); 80module_exit(realtek_exit);
81
82static struct mdio_device_id realtek_tbl[] = {
83 { 0x001cc912, 0x001fffff },
84 { }
85};
86
87MODULE_DEVICE_TABLE(mdio, realtek_tbl);
diff --git a/drivers/net/phy/smsc.c b/drivers/net/phy/smsc.c
index ed2644a57500..78fa988256fc 100644
--- a/drivers/net/phy/smsc.c
+++ b/drivers/net/phy/smsc.c
@@ -253,3 +253,14 @@ MODULE_LICENSE("GPL");
253 253
254module_init(smsc_init); 254module_init(smsc_init);
255module_exit(smsc_exit); 255module_exit(smsc_exit);
256
257static struct mdio_device_id smsc_tbl[] = {
258 { 0x0007c0a0, 0xfffffff0 },
259 { 0x0007c0b0, 0xfffffff0 },
260 { 0x0007c0c0, 0xfffffff0 },
261 { 0x0007c0d0, 0xfffffff0 },
262 { 0x0007c0f0, 0xfffffff0 },
263 { }
264};
265
266MODULE_DEVICE_TABLE(mdio, smsc_tbl);
diff --git a/drivers/net/phy/ste10Xp.c b/drivers/net/phy/ste10Xp.c
index 6bdb0d53aaf9..72290099e5e1 100644
--- a/drivers/net/phy/ste10Xp.c
+++ b/drivers/net/phy/ste10Xp.c
@@ -132,6 +132,14 @@ static void __exit ste10Xp_exit(void)
132module_init(ste10Xp_init); 132module_init(ste10Xp_init);
133module_exit(ste10Xp_exit); 133module_exit(ste10Xp_exit);
134 134
135static struct mdio_device_id ste10Xp_tbl[] = {
136 { STE101P_PHY_ID, 0xfffffff0 },
137 { STE100P_PHY_ID, 0xffffffff },
138 { }
139};
140
141MODULE_DEVICE_TABLE(mdio, ste10Xp_tbl);
142
135MODULE_DESCRIPTION("STMicroelectronics STe10Xp PHY driver"); 143MODULE_DESCRIPTION("STMicroelectronics STe10Xp PHY driver");
136MODULE_AUTHOR("Giuseppe Cavallaro <peppe.cavallaro@st.com>"); 144MODULE_AUTHOR("Giuseppe Cavallaro <peppe.cavallaro@st.com>");
137MODULE_LICENSE("GPL"); 145MODULE_LICENSE("GPL");
diff --git a/drivers/net/phy/vitesse.c b/drivers/net/phy/vitesse.c
index dd3b2447e85a..45cce50a2799 100644
--- a/drivers/net/phy/vitesse.c
+++ b/drivers/net/phy/vitesse.c
@@ -191,3 +191,11 @@ static void __exit vsc82xx_exit(void)
191 191
192module_init(vsc82xx_init); 192module_init(vsc82xx_init);
193module_exit(vsc82xx_exit); 193module_exit(vsc82xx_exit);
194
195static struct mdio_device_id vitesse_tbl[] = {
196 { PHY_ID_VSC8244, 0x000fffc0 },
197 { PHY_ID_VSC8221, 0x000ffff0 },
198 { }
199};
200
201MODULE_DEVICE_TABLE(mdio, vitesse_tbl);