aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorWolfgang Denk <wd@denx.de>2009-07-16 22:27:07 -0400
committerDavid S. Miller <davem@davemloft.net>2009-07-17 12:47:29 -0400
commit652f6787c082a174f0bbfa7f895b65b03d8d46c9 (patch)
treed131b92e10357adad9322ec9a89246fca2ce12fb /drivers
parentda8120355e80ddaf534adb8ed910871d97512d56 (diff)
fs_enet/mii-fec.c: fix MII speed calculation
The MII speed calculation was based on the CPU clock (ppc_proc_freq), but for MPC512x we must use the bus clock instead. This patch makes it use the correct clock and makes sure we don't clobber reserved bits in the MII_SPEED register. Signed-off-by: Wolfgang Denk <wd@denx.de> Cc: Grant Likely <grant.likely@secretlab.ca> Cc: Kumar Gala <galak@kernel.crashing.org> Cc: <netdev@vger.kernel.org> Acked-by: Grant Likely <grant.likely@secretlab.ca> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/net/fs_enet/mii-fec.c37
1 files changed, 33 insertions, 4 deletions
diff --git a/drivers/net/fs_enet/mii-fec.c b/drivers/net/fs_enet/mii-fec.c
index 75a09994d665..a2d69c1cd07e 100644
--- a/drivers/net/fs_enet/mii-fec.c
+++ b/drivers/net/fs_enet/mii-fec.c
@@ -36,6 +36,7 @@
36#include <asm/pgtable.h> 36#include <asm/pgtable.h>
37#include <asm/irq.h> 37#include <asm/irq.h>
38#include <asm/uaccess.h> 38#include <asm/uaccess.h>
39#include <asm/mpc5xxx.h>
39 40
40#include "fs_enet.h" 41#include "fs_enet.h"
41#include "fec.h" 42#include "fec.h"
@@ -103,11 +104,11 @@ static int fs_enet_fec_mii_reset(struct mii_bus *bus)
103static int __devinit fs_enet_mdio_probe(struct of_device *ofdev, 104static int __devinit fs_enet_mdio_probe(struct of_device *ofdev,
104 const struct of_device_id *match) 105 const struct of_device_id *match)
105{ 106{
106 struct device_node *np = NULL;
107 struct resource res; 107 struct resource res;
108 struct mii_bus *new_bus; 108 struct mii_bus *new_bus;
109 struct fec_info *fec; 109 struct fec_info *fec;
110 int ret = -ENOMEM, i; 110 int (*get_bus_freq)(struct device_node *) = match->data;
111 int ret = -ENOMEM, clock, speed;
111 112
112 new_bus = mdiobus_alloc(); 113 new_bus = mdiobus_alloc();
113 if (!new_bus) 114 if (!new_bus)
@@ -133,13 +134,35 @@ static int __devinit fs_enet_mdio_probe(struct of_device *ofdev,
133 if (!fec->fecp) 134 if (!fec->fecp)
134 goto out_fec; 135 goto out_fec;
135 136
136 fec->mii_speed = ((ppc_proc_freq + 4999999) / 5000000) << 1; 137 if (get_bus_freq) {
138 clock = get_bus_freq(ofdev->node);
139 if (!clock) {
140 /* Use maximum divider if clock is unknown */
141 dev_warn(&ofdev->dev, "could not determine IPS clock\n");
142 clock = 0x3F * 5000000;
143 }
144 } else
145 clock = ppc_proc_freq;
146
147 /*
148 * Scale for a MII clock <= 2.5 MHz
149 * Note that only 6 bits (25:30) are available for MII speed.
150 */
151 speed = (clock + 4999999) / 5000000;
152 if (speed > 0x3F) {
153 speed = 0x3F;
154 dev_err(&ofdev->dev,
155 "MII clock (%d Hz) exceeds max (2.5 MHz)\n",
156 clock / speed);
157 }
158
159 fec->mii_speed = speed << 1;
137 160
138 setbits32(&fec->fecp->fec_r_cntrl, FEC_RCNTRL_MII_MODE); 161 setbits32(&fec->fecp->fec_r_cntrl, FEC_RCNTRL_MII_MODE);
139 setbits32(&fec->fecp->fec_ecntrl, FEC_ECNTRL_PINMUX | 162 setbits32(&fec->fecp->fec_ecntrl, FEC_ECNTRL_PINMUX |
140 FEC_ECNTRL_ETHER_EN); 163 FEC_ECNTRL_ETHER_EN);
141 out_be32(&fec->fecp->fec_ievent, FEC_ENET_MII); 164 out_be32(&fec->fecp->fec_ievent, FEC_ENET_MII);
142 out_be32(&fec->fecp->fec_mii_speed, fec->mii_speed); 165 clrsetbits_be32(&fec->fecp->fec_mii_speed, 0x7E, fec->mii_speed);
143 166
144 new_bus->phy_mask = ~0; 167 new_bus->phy_mask = ~0;
145 new_bus->irq = kmalloc(sizeof(int) * PHY_MAX_ADDR, GFP_KERNEL); 168 new_bus->irq = kmalloc(sizeof(int) * PHY_MAX_ADDR, GFP_KERNEL);
@@ -188,6 +211,12 @@ static struct of_device_id fs_enet_mdio_fec_match[] = {
188 { 211 {
189 .compatible = "fsl,pq1-fec-mdio", 212 .compatible = "fsl,pq1-fec-mdio",
190 }, 213 },
214#if defined(CONFIG_PPC_MPC512x)
215 {
216 .compatible = "fsl,mpc5121-fec-mdio",
217 .data = mpc5xxx_get_bus_frequency,
218 },
219#endif
191 {}, 220 {},
192}; 221};
193 222