aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--drivers/net/fsl_pq_mdio.c59
-rw-r--r--drivers/net/fsl_pq_mdio.h11
2 files changed, 57 insertions, 13 deletions
diff --git a/drivers/net/fsl_pq_mdio.c b/drivers/net/fsl_pq_mdio.c
index 6ac46486697..4065b7c01ec 100644
--- a/drivers/net/fsl_pq_mdio.c
+++ b/drivers/net/fsl_pq_mdio.c
@@ -3,8 +3,9 @@
3 * Provides Bus interface for MIIM regs 3 * Provides Bus interface for MIIM regs
4 * 4 *
5 * Author: Andy Fleming <afleming@freescale.com> 5 * Author: Andy Fleming <afleming@freescale.com>
6 * Modifier: Sandeep Gopalpet <sandeep.kumar@freescale.com>
6 * 7 *
7 * Copyright (c) 2002-2004,2008 Freescale Semiconductor, Inc. 8 * Copyright 2002-2004, 2008-2009 Freescale Semiconductor, Inc.
8 * 9 *
9 * Based on gianfar_mii.c and ucc_geth_mii.c (Li Yang, Kim Phillips) 10 * Based on gianfar_mii.c and ucc_geth_mii.c (Li Yang, Kim Phillips)
10 * 11 *
@@ -189,19 +190,29 @@ static int fsl_pq_mdio_find_free(struct mii_bus *new_bus)
189 190
190 191
191#if defined(CONFIG_GIANFAR) || defined(CONFIG_GIANFAR_MODULE) 192#if defined(CONFIG_GIANFAR) || defined(CONFIG_GIANFAR_MODULE)
192static u32 __iomem *get_gfar_tbipa(struct fsl_pq_mdio __iomem *regs) 193static u32 __iomem *get_gfar_tbipa(struct fsl_pq_mdio __iomem *regs, struct device_node *np)
193{ 194{
194 struct gfar __iomem *enet_regs; 195 struct gfar __iomem *enet_regs;
196 u32 __iomem *ioremap_tbipa;
197 u64 addr, size;
195 198
196 /* 199 /*
197 * This is mildly evil, but so is our hardware for doing this. 200 * This is mildly evil, but so is our hardware for doing this.
198 * Also, we have to cast back to struct gfar because of 201 * Also, we have to cast back to struct gfar because of
199 * definition weirdness done in gianfar.h. 202 * definition weirdness done in gianfar.h.
200 */ 203 */
201 enet_regs = (struct gfar __iomem *) 204 if(of_device_is_compatible(np, "fsl,gianfar-mdio") ||
202 ((char __iomem *)regs - offsetof(struct gfar, gfar_mii_regs)); 205 of_device_is_compatible(np, "fsl,gianfar-tbi") ||
203 206 of_device_is_compatible(np, "gianfar")) {
204 return &enet_regs->tbipa; 207 enet_regs = (struct gfar __iomem *)regs;
208 return &enet_regs->tbipa;
209 } else if (of_device_is_compatible(np, "fsl,etsec2-mdio") ||
210 of_device_is_compatible(np, "fsl,etsec2-tbi")) {
211 addr = of_translate_address(np, of_get_address(np, 1, &size, NULL));
212 ioremap_tbipa = ioremap(addr, size);
213 return ioremap_tbipa;
214 } else
215 return NULL;
205} 216}
206#endif 217#endif
207 218
@@ -250,11 +261,11 @@ static int fsl_pq_mdio_probe(struct of_device *ofdev,
250{ 261{
251 struct device_node *np = ofdev->node; 262 struct device_node *np = ofdev->node;
252 struct device_node *tbi; 263 struct device_node *tbi;
253 struct fsl_pq_mdio __iomem *regs; 264 struct fsl_pq_mdio __iomem *regs = NULL;
254 u32 __iomem *tbipa; 265 u32 __iomem *tbipa;
255 struct mii_bus *new_bus; 266 struct mii_bus *new_bus;
256 int tbiaddr = -1; 267 int tbiaddr = -1;
257 u64 addr, size; 268 u64 addr = 0, size = 0, ioremap_miimcfg = 0;
258 int err = 0; 269 int err = 0;
259 270
260 new_bus = mdiobus_alloc(); 271 new_bus = mdiobus_alloc();
@@ -268,8 +279,22 @@ static int fsl_pq_mdio_probe(struct of_device *ofdev,
268 fsl_pq_mdio_bus_name(new_bus->id, np); 279 fsl_pq_mdio_bus_name(new_bus->id, np);
269 280
270 /* Set the PHY base address */ 281 /* Set the PHY base address */
271 addr = of_translate_address(np, of_get_address(np, 0, &size, NULL)); 282 if (of_device_is_compatible(np,"fsl,gianfar-mdio") ||
272 regs = ioremap(addr, size); 283 of_device_is_compatible(np, "fsl,gianfar-tbi") ||
284 of_device_is_compatible(np, "fsl,ucc-mdio") ||
285 of_device_is_compatible(np,"ucc_geth_phy" )) {
286 addr = of_translate_address(np, of_get_address(np, 0, &size, NULL));
287 ioremap_miimcfg = container_of(addr, struct fsl_pq_mdio, miimcfg);
288 regs = ioremap(ioremap_miimcfg, size +
289 offsetof(struct fsl_pq_mdio, miimcfg));
290 } else if (of_device_is_compatible(np,"fsl,etsec2-mdio") ||
291 of_device_is_compatible(np, "fsl,etsec2-tbi")) {
292 addr = of_translate_address(np, of_get_address(np, 0, &size, NULL));
293 regs = ioremap(addr, size);
294 } else {
295 err = -EINVAL;
296 goto err_free_bus;
297 }
273 298
274 if (NULL == regs) { 299 if (NULL == regs) {
275 err = -ENOMEM; 300 err = -ENOMEM;
@@ -290,9 +315,15 @@ static int fsl_pq_mdio_probe(struct of_device *ofdev,
290 315
291 if (of_device_is_compatible(np, "fsl,gianfar-mdio") || 316 if (of_device_is_compatible(np, "fsl,gianfar-mdio") ||
292 of_device_is_compatible(np, "fsl,gianfar-tbi") || 317 of_device_is_compatible(np, "fsl,gianfar-tbi") ||
318 of_device_is_compatible(np, "fsl,etsec2-mdio") ||
319 of_device_is_compatible(np, "fsl,etsec2-tbi") ||
293 of_device_is_compatible(np, "gianfar")) { 320 of_device_is_compatible(np, "gianfar")) {
294#if defined(CONFIG_GIANFAR) || defined(CONFIG_GIANFAR_MODULE) 321#if defined(CONFIG_GIANFAR) || defined(CONFIG_GIANFAR_MODULE)
295 tbipa = get_gfar_tbipa(regs); 322 tbipa = get_gfar_tbipa(regs, np);
323 if (!tbipa) {
324 err = -EINVAL;
325 goto err_free_irqs;
326 }
296#else 327#else
297 err = -ENODEV; 328 err = -ENODEV;
298 goto err_free_irqs; 329 goto err_free_irqs;
@@ -405,6 +436,12 @@ static struct of_device_id fsl_pq_mdio_match[] = {
405 { 436 {
406 .compatible = "fsl,gianfar-mdio", 437 .compatible = "fsl,gianfar-mdio",
407 }, 438 },
439 {
440 .compatible = "fsl,etsec2-tbi",
441 },
442 {
443 .compatible = "fsl,etsec2-mdio",
444 },
408 {}, 445 {},
409}; 446};
410MODULE_DEVICE_TABLE(of, fsl_pq_mdio_match); 447MODULE_DEVICE_TABLE(of, fsl_pq_mdio_match);
diff --git a/drivers/net/fsl_pq_mdio.h b/drivers/net/fsl_pq_mdio.h
index 36dad527410..1f7d865cedb 100644
--- a/drivers/net/fsl_pq_mdio.h
+++ b/drivers/net/fsl_pq_mdio.h
@@ -3,8 +3,9 @@
3 * Driver for the MDIO bus controller on Freescale PowerQUICC processors 3 * Driver for the MDIO bus controller on Freescale PowerQUICC processors
4 * 4 *
5 * Author: Andy Fleming 5 * Author: Andy Fleming
6 * Modifier: Sandeep Gopalpet
6 * 7 *
7 * Copyright (c) 2002-2004,2008 Freescale Semiconductor, Inc. 8 * Copyright 2002-2004, 2008-2009 Freescale Semiconductor, Inc.
8 * 9 *
9 * This program is free software; you can redistribute it and/or modify it 10 * This program is free software; you can redistribute it and/or modify it
10 * under the terms of the GNU General Public License as published by the 11 * under the terms of the GNU General Public License as published by the
@@ -23,6 +24,12 @@
23#define MII_READ_COMMAND 0x00000001 24#define MII_READ_COMMAND 0x00000001
24 25
25struct fsl_pq_mdio { 26struct fsl_pq_mdio {
27 u8 res1[16];
28 u32 ieventm; /* MDIO Interrupt event register (for etsec2)*/
29 u32 imaskm; /* MDIO Interrupt mask register (for etsec2)*/
30 u8 res2[4];
31 u32 emapm; /* MDIO Event mapping register (for etsec2)*/
32 u8 res3[1280];
26 u32 miimcfg; /* MII management configuration reg */ 33 u32 miimcfg; /* MII management configuration reg */
27 u32 miimcom; /* MII management command reg */ 34 u32 miimcom; /* MII management command reg */
28 u32 miimadd; /* MII management address reg */ 35 u32 miimadd; /* MII management address reg */
@@ -31,9 +38,9 @@ struct fsl_pq_mdio {
31 u32 miimind; /* MII management indication reg */ 38 u32 miimind; /* MII management indication reg */
32 u8 reserved[28]; /* Space holder */ 39 u8 reserved[28]; /* Space holder */
33 u32 utbipar; /* TBI phy address reg (only on UCC) */ 40 u32 utbipar; /* TBI phy address reg (only on UCC) */
41 u8 res4[2728];
34} __attribute__ ((packed)); 42} __attribute__ ((packed));
35 43
36
37int fsl_pq_mdio_read(struct mii_bus *bus, int mii_id, int regnum); 44int fsl_pq_mdio_read(struct mii_bus *bus, int mii_id, int regnum);
38int fsl_pq_mdio_write(struct mii_bus *bus, int mii_id, int regnum, u16 value); 45int fsl_pq_mdio_write(struct mii_bus *bus, int mii_id, int regnum, u16 value);
39int fsl_pq_local_mdio_write(struct fsl_pq_mdio __iomem *regs, int mii_id, 46int fsl_pq_local_mdio_write(struct fsl_pq_mdio __iomem *regs, int mii_id,