Skip to contentSkip to conversation

phy: Add phy driver support for xilinx PCS/PMA core

PATCH New Michal Simek 3 participants 7 messages Feb 15, 2016 – Apr 26, 2016

Subsystems (3)
lore
Share & tools
lore
#0 lore raw

PATCH 1/3 phy: Add phy driver support for xilinx PCS/PMA core

From: Siva Durga Prasad Paladugu <[email protected]>

Add phy driver support for xilinx PCS/PMA core

---

 drivers/net/phy/Makefile     |   1 +
 drivers/net/phy/phy.c        |   3 +
 drivers/net/phy/xilinx_phy.c | 144 +++++++++++++++++++++++++++++++++++++++++++
 include/phy.h                |   1 +
 4 files changed, 149 insertions(+)
 create mode 100644 drivers/net/phy/xilinx_phy.c
drivers/net/phy/Makefile +1 -0
index 9e4d4927e676..1e299b97b961 100644
@@ -25,4 +25,5 @@ obj-$(CONFIG_PHY_REALTEK) += realtek.o
 obj-$(CONFIG_PHY_SMSC) += smsc.o
 obj-$(CONFIG_PHY_TERANETICS) += teranetics.o
 obj-$(CONFIG_PHY_TI) += ti.o
+obj-$(CONFIG_PHY_XILINX) += xilinx_phy.o
 obj-$(CONFIG_PHY_VITESSE) += vitesse.o
drivers/net/phy/phy.c +3 -0
index 17866a244b3a..23c82bb36e93 100644
@@ -503,6 +503,9 @@ int phy_init(void)
 #ifdef CONFIG_PHY_VITESSE
 	phy_vitesse_init();
 #endif
+#ifdef CONFIG_PHY_XILINX
+	phy_xilinx_init();
+#endif
 
 	return 0;
 }
drivers/net/phy/xilinx_phy.c new file +144 -0

144 lines not on this page · raw message

include/phy.h +1 -0
index 09bbe483a4b1..21459a8c8093 100644
@@ -264,6 +264,7 @@ int phy_smsc_init(void);
 int phy_teranetics_init(void);
 int phy_ti_init(void);
 int phy_vitesse_init(void);
+int phy_xilinx_init(void);
 
 int board_phy_config(struct phy_device *phydev);
 int get_phy_id(struct mii_dev *bus, int addr, int devad, u32 *phy_id);
Signature · 1 line
1.9.1
#1 lore raw

PATCH 2/3 net: zynq_gem: Add support for SGMII interface

From: Siva Durga Prasad Paladugu <[email protected]>

Add support of SGMII interface for zynq GEM.
Read xlnx,emio property from DT.

---

 drivers/net/zynq_gem.c | 26 +++++++++++++++++++-------
 1 file changed, 19 insertions(+), 7 deletions(-)
drivers/net/zynq_gem.c +19 -7
index b3821c31a91d..4049e1cb94e8 100644
@@ -57,6 +57,8 @@ DECLARE_GLOBAL_DATA_PTR;
 #define ZYNQ_GEM_NWCFG_SPEED1000	0x000000400 /* 1Gbps operation */
 #define ZYNQ_GEM_NWCFG_FDEN		0x000000002 /* Full Duplex mode */
 #define ZYNQ_GEM_NWCFG_FSREM		0x000020000 /* FCS removal */
+#define ZYNQ_GEM_NWCFG_SGMII_ENBL	0x080000000 /* SGMII Enable */
+#define ZYNQ_GEM_NWCFG_PCS_SEL		0x000000800 /* PCS select */
 #ifdef CONFIG_ARM64
 #define ZYNQ_GEM_NWCFG_MDCCLKDIV	0x000100000 /* Div pclk by 64, max 160MHz */
 #else
@@ -330,10 +332,12 @@ static int zynq_phy_init(struct udevice *dev)
 	/* Enable only MDIO bus */
 	writel(ZYNQ_GEM_NWCTRL_MDEN_MASK, &regs->nwctrl);
 
-	ret = phy_detection(dev);
-	if (ret) {
-		printf("GEM PHY init failed\n");
-		return ret;
+	if (priv->interface != PHY_INTERFACE_MODE_SGMII) {
+		ret = phy_detection(dev);
+		if (ret) {
+			printf("GEM PHY init failed\n");
+			return ret;
+		}
 	}
 
 	priv->phydev = phy_connect(priv->bus, priv->phyaddr, dev,
@@ -351,7 +355,7 @@ static int zynq_phy_init(struct udevice *dev)
 
 static int zynq_gem_init(struct udevice *dev)
 {
-	u32 i;
+	u32 i, nwconfig;
 	unsigned long clk_rate = 0;
 	struct zynq_gem_priv *priv = dev_get_priv(dev);
 	struct zynq_gem_regs *regs = priv->iobase;
@@ -426,14 +430,20 @@ static int zynq_gem_init(struct udevice *dev)
 		return -1;
 	}
 
+	nwconfig = ZYNQ_GEM_NWCFG_INIT;
+
+	if (priv->interface == PHY_INTERFACE_MODE_SGMII)
+		nwconfig |= ZYNQ_GEM_NWCFG_SGMII_ENBL |
+			    ZYNQ_GEM_NWCFG_PCS_SEL;
+
 	switch (priv->phydev->speed) {
 	case SPEED_1000:
-		writel(ZYNQ_GEM_NWCFG_INIT | ZYNQ_GEM_NWCFG_SPEED1000,
+		writel(nwconfig | ZYNQ_GEM_NWCFG_SPEED1000,
 		       &regs->nwcfg);
 		clk_rate = ZYNQ_GEM_FREQUENCY_1000;
 		break;
 	case SPEED_100:
-		writel(ZYNQ_GEM_NWCFG_INIT | ZYNQ_GEM_NWCFG_SPEED100,
+		writel(nwconfig | ZYNQ_GEM_NWCFG_SPEED100,
 		       &regs->nwcfg);
 		clk_rate = ZYNQ_GEM_FREQUENCY_100;
 		break;
@@ -663,6 +673,8 @@ static int zynq_gem_ofdata_to_platdata(struct udevice *dev)
 	}
 	priv->interface = pdata->phy_interface;
 
+	priv->emio = fdtdec_get_bool(gd->fdt_blob, dev->of_offset, "xlnx,emio");
+
 	printf("ZYNQ GEM: %lx, phyaddr %d, interface %s\n", (ulong)priv->iobase,
 	       priv->phyaddr, phy_string_for_interface(priv->interface));
 
Signature · 1 line
1.9.1
#2 lore raw

PATCH 2/3 net: zynq_gem: Add support for SGMII interface

Quoted 17 lines · Michal Simek

From: Siva Durga Prasad Paladugu <[email protected]>

Add support of SGMII interface for zynq GEM.
Read xlnx,emio property from DT.

---

 drivers/net/zynq_gem.c | 26 +++++++++++++++++++-------
 1 file changed, 19 insertions(+), 7 deletions(-)
drivers/net/zynq_gem.c +0 -0
index b3821c31a91d..4049e1cb94e8 100644

drivers/net/zynq_gem.c DECLARE_GLOBAL_DATA_PTR; · line 61

Quoted 5 lines
drivers/net/zynq_gem.c +2 -0
@@ -57,6 +57,8 @@ DECLARE_GLOBAL_DATA_PTR;
 #define ZYNQ_GEM_NWCFG_SPEED1000       0x000000400 /* 1Gbps operation */
 #define ZYNQ_GEM_NWCFG_FDEN            0x000000002 /* Full Duplex mode */
 #define ZYNQ_GEM_NWCFG_FSREM           0x000020000 /* FCS removal */
+#define ZYNQ_GEM_NWCFG_SGMII_ENBL      0x080000000 /* SGMII Enable */
+#define ZYNQ_GEM_NWCFG_PCS_SEL         0x000000800 /* PCS select */

Use BIT() macro.

Quoted 53 lines
drivers/net/zynq_gem.c +15 -7
 #ifdef CONFIG_ARM64
 #define ZYNQ_GEM_NWCFG_MDCCLKDIV       0x000100000 /* Div pclk by 64, max 160MHz */
 #else
@@ -330,10 +332,12 @@ static int zynq_phy_init(struct udevice *dev)
        /* Enable only MDIO bus */
        writel(ZYNQ_GEM_NWCTRL_MDEN_MASK, &regs->nwctrl);
 
-       ret = phy_detection(dev);
-       if (ret) {
-               printf("GEM PHY init failed\n");
-               return ret;
+       if (priv->interface != PHY_INTERFACE_MODE_SGMII) {
+               ret = phy_detection(dev);
+               if (ret) {
+                       printf("GEM PHY init failed\n");
+                       return ret;
+               }
        }
 
        priv->phydev = phy_connect(priv->bus, priv->phyaddr, dev,
@@ -351,7 +355,7 @@ static int zynq_phy_init(struct udevice *dev)
 
 static int zynq_gem_init(struct udevice *dev)
 {
-       u32 i;
+       u32 i, nwconfig;
        unsigned long clk_rate = 0;
        struct zynq_gem_priv *priv = dev_get_priv(dev);
        struct zynq_gem_regs *regs = priv->iobase;
@@ -426,14 +430,20 @@ static int zynq_gem_init(struct udevice *dev)
                return -1;
        }
 
+       nwconfig = ZYNQ_GEM_NWCFG_INIT;
+
+       if (priv->interface == PHY_INTERFACE_MODE_SGMII)
+               nwconfig |= ZYNQ_GEM_NWCFG_SGMII_ENBL |
+                           ZYNQ_GEM_NWCFG_PCS_SEL;
+
        switch (priv->phydev->speed) {
        case SPEED_1000:
-               writel(ZYNQ_GEM_NWCFG_INIT | ZYNQ_GEM_NWCFG_SPEED1000,
+               writel(nwconfig | ZYNQ_GEM_NWCFG_SPEED1000,
                       &regs->nwcfg);
                clk_rate = ZYNQ_GEM_FREQUENCY_1000;
                break;
        case SPEED_100:
-               writel(ZYNQ_GEM_NWCFG_INIT | ZYNQ_GEM_NWCFG_SPEED100,
+               writel(nwconfig | ZYNQ_GEM_NWCFG_SPEED100,
                       &regs->nwcfg);
                clk_rate = ZYNQ_GEM_FREQUENCY_100;
                break;

drivers/net/zynq_gem.c static int zynq_gem_ofdata_to_platdata(struct udevice *dev) · line 677

Quoted 5 lines
drivers/net/zynq_gem.c +2 -0
@@ -663,6 +673,8 @@ static int zynq_gem_ofdata_to_platdata(struct udevice *dev)
        }
        priv->interface = pdata->phy_interface;
 
+       priv->emio = fdtdec_get_bool(gd->fdt_blob, dev->of_offset, "xlnx,emio");
+

It seems this belongs in a separate patch.

Quoted 10 lines
drivers/net/zynq_gem.c +0 -1
        printf("ZYNQ GEM: %lx, phyaddr %d, interface %s\n", (ulong)priv->iobase,
               priv->phyaddr, phy_string_for_interface(priv->interface));
 
--

1.9.1

_______________________________________________
U-Boot mailing list
U-Boot at lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

#3 lore raw

PATCH 3/3 zynq-common: Enable phy driver for Xilinx PCS/PMA core

In reply to Michal Simek

From: Siva Durga Prasad Paladugu <[email protected]>

Add support of Xilinx PCS/PMA core phy for Zynq

---

 include/configs/zynq-common.h | 1 +
 1 file changed, 1 insertion(+)
include/configs/zynq-common.h +1 -0
index e8c3ef0c3872..ea273b8d54b7 100644
@@ -50,6 +50,7 @@
 # define CONFIG_MII
 # define CONFIG_SYS_FAULT_ECHO_LINK_DOWN
 # define CONFIG_PHY_MARVELL
+# define CONFIG_PHY_XILINX
 # define CONFIG_BOOTP_SERVERIP
 # define CONFIG_BOOTP_BOOTPATH
 # define CONFIG_BOOTP_GATEWAY
Signature · 1 line
1.9.1
#4 lore raw

PATCH 1/3 phy: Add phy driver support for xilinx PCS/PMA core

In reply to Michal Simek
Quoted 55 lines · Michal Simek

From: Siva Durga Prasad Paladugu <[email protected]>

Add phy driver support for xilinx PCS/PMA core

---

 drivers/net/phy/Makefile     |   1 +
 drivers/net/phy/phy.c        |   3 +
 drivers/net/phy/xilinx_phy.c | 144 +++++++++++++++++++++++++++++++++++++++++++
 include/phy.h                |   1 +
 4 files changed, 149 insertions(+)
 create mode 100644 drivers/net/phy/xilinx_phy.c
drivers/net/phy/Makefile +1 -0
index 9e4d4927e676..1e299b97b961 100644
@@ -25,4 +25,5 @@ obj-$(CONFIG_PHY_REALTEK) += realtek.o
 obj-$(CONFIG_PHY_SMSC) += smsc.o
 obj-$(CONFIG_PHY_TERANETICS) += teranetics.o
 obj-$(CONFIG_PHY_TI) += ti.o
+obj-$(CONFIG_PHY_XILINX) += xilinx_phy.o
 obj-$(CONFIG_PHY_VITESSE) += vitesse.o
drivers/net/phy/phy.c +3 -0
index 17866a244b3a..23c82bb36e93 100644
@@ -503,6 +503,9 @@ int phy_init(void)
 #ifdef CONFIG_PHY_VITESSE
        phy_vitesse_init();
 #endif
+#ifdef CONFIG_PHY_XILINX
+       phy_xilinx_init();
+#endif
 
        return 0;
 }
drivers/net/phy/xilinx_phy.c new file +9 -0
new file mode 100644
index 000000000000..f3eaf2e97ced
@@ -0,0 +1,144 @@
+/*
+ * Xilinx PCS/PMA Core phy driver
+ *
+ * Copyright (C) 2015 - 2016 Xilinx, Inc.
+ *
+ * SPDX-License-Identifier:    GPL-2.0+
+ */
+
+#include <config.h>

drivers/net/phy/xilinx_phy.c line 19

Quoted 10 lines
drivers/net/phy/xilinx_phy.c new file +10 -0
+#include <common.h>
+#include <phy.h>
+#include <dm.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+#define MII_PHY_STATUS_SPD_MASK                0x0C00
+#define MII_PHY_STATUS_FULLDUPLEX      0x1000
+#define MII_PHY_STATUS_1000            0x0800
+#define MII_PHY_STATUS_100             0x0400

Use the BIT() macro where appropriate.

Quoted 79 lines
drivers/net/phy/xilinx_phy.c new file +79 -0
+#define XPCSPMA_PHY_CTRL_ISOLATE_DISABLE 0xFBFF
+
+/* Mask used for ID comparisons */
+#define XILINX_PHY_ID_MASK             0xfffffff0
+
+/* Known PHY IDs */
+#define XILINX_PHY_ID                  0x01740c00
+
+/* struct phy_device dev_flags definitions */
+#define XAE_PHY_TYPE_MII               0
+#define XAE_PHY_TYPE_GMII              1
+#define XAE_PHY_TYPE_RGMII_1_3         2
+#define XAE_PHY_TYPE_RGMII_2_0         3
+#define XAE_PHY_TYPE_SGMII             4
+#define XAE_PHY_TYPE_1000BASE_X                5
+
+static int xilinxphy_startup(struct phy_device *phydev)
+{
+       int err;
+       int status = 0;
+
+       debug("%s\n", __func__);
+       /* Update the link, but return if there
+        * was an error
+        */
+       err = genphy_update_link(phydev);
+       if (err)
+               return err;
+
+       if (AUTONEG_ENABLE == phydev->autoneg) {
+               status = phy_read(phydev, MDIO_DEVAD_NONE, MII_LPA);
+               status = status & MII_PHY_STATUS_SPD_MASK;
+
+               if (status & MII_PHY_STATUS_FULLDUPLEX)
+                       phydev->duplex = DUPLEX_FULL;
+               else
+                       phydev->duplex = DUPLEX_HALF;
+
+               switch (status) {
+               case MII_PHY_STATUS_1000:
+                       phydev->speed = SPEED_1000;
+                       break;
+
+               case MII_PHY_STATUS_100:
+                       phydev->speed = SPEED_100;
+                       break;
+
+               default:
+                       phydev->speed = SPEED_10;
+                       break;
+               }
+       } else {
+               int bmcr = phy_read(phydev, MDIO_DEVAD_NONE, MII_BMCR);
+
+               if (bmcr < 0)
+                       return bmcr;
+
+               if (bmcr & BMCR_FULLDPLX)
+                       phydev->duplex = DUPLEX_FULL;
+               else
+                       phydev->duplex = DUPLEX_HALF;
+
+               if (bmcr & BMCR_SPEED1000)
+                       phydev->speed = SPEED_1000;
+               else if (bmcr & BMCR_SPEED100)
+                       phydev->speed = SPEED_100;
+               else
+                       phydev->speed = SPEED_10;
+       }
+
+       /*
+        * For 1000BASE-X Phy Mode the speed/duplex will always be
+        * 1000Mbps/fullduplex
+        */
+       if (phydev->flags == XAE_PHY_TYPE_1000BASE_X) {
+               phydev->duplex = DUPLEX_FULL;
+               phydev->speed = SPEED_1000;
+       }
+

drivers/net/phy/xilinx_phy.c line 108

Quoted 10 lines
drivers/net/phy/xilinx_phy.c new file +10 -0
+       return 0;
+}
+
+static int xilinxphy_of_init(struct phy_device *phydev)
+{
+       struct udevice *dev = (struct udevice *)&phydev->dev;
+       u32 phytype;
+
+       debug("%s\n", __func__);
+       phytype = fdtdec_get_int(gd->fdt_blob, dev->of_offset, "phy-type", -1);

Is there a bindings document that can be included to describe this?

Quoted 55 lines
drivers/net/phy/xilinx_phy.c new file +36 -0
+       if (phytype == XAE_PHY_TYPE_1000BASE_X)
+               phydev->flags |= XAE_PHY_TYPE_1000BASE_X;
+
+       return 0;
+}
+
+static int xilinxphy_config(struct phy_device *phydev)
+{
+       int temp;
+
+       debug("%s\n", __func__);
+       xilinxphy_of_init(phydev);
+       temp = phy_read(phydev, MDIO_DEVAD_NONE, MII_BMCR);
+       temp &= XPCSPMA_PHY_CTRL_ISOLATE_DISABLE;
+       phy_write(phydev, MDIO_DEVAD_NONE, MII_BMCR, temp);
+
+       return 0;
+}
+
+static struct phy_driver xilinxphy_driver = {
+       .uid = XILINX_PHY_ID,
+       .mask = XILINX_PHY_ID_MASK,
+       .name = "Xilinx PCS/PMA PHY",
+       .features = PHY_GBIT_FEATURES,
+       .config = &xilinxphy_config,
+       .startup = &xilinxphy_startup,
+       .shutdown = &genphy_shutdown,
+};
+
+int phy_xilinx_init(void)
+{
+       debug("%s\n", __func__);
+       phy_register(&xilinxphy_driver);
+
+       return 0;
+}
include/phy.h +1 -1
index 09bbe483a4b1..21459a8c8093 100644
@@ -264,6 +264,7 @@ int phy_smsc_init(void);
 int phy_teranetics_init(void);
 int phy_ti_init(void);
 int phy_vitesse_init(void);
+int phy_xilinx_init(void);
 
 int board_phy_config(struct phy_device *phydev);
 int get_phy_id(struct mii_dev *bus, int addr, int devad, u32 *phy_id);
--

1.9.1

_______________________________________________
U-Boot mailing list
U-Boot at lists.denx.de
http://lists.denx.de/mailman/listinfo/u-boot

#5 lore raw

PATCH 1/3 phy: Add phy driver support for xilinx PCS/PMA core

Quoted 9 lines · Joe Hershberger
Quoted 8 lines · Michal Simek

From: Siva Durga Prasad Paladugu <[email protected]>

Add phy driver support for xilinx PCS/PMA core

---

[snip]

Quoted 9 lines

drivers/net/phy/xilinx_phy.c line 108

Quoted 7 lines
drivers/net/phy/xilinx_phy.c new file +7 -0
+static int xilinxphy_of_init(struct phy_device *phydev)
+{
+       struct udevice *dev = (struct udevice *)&phydev->dev;
+       u32 phytype;
+
+       debug("%s\n", __func__);
+       phytype = fdtdec_get_int(gd->fdt_blob, dev->of_offset, "phy-type", -1);

Is there a bindings document that can be included to describe this?

If that is meant to be the PHY type (MII, RGMII etc.) the standard property name is either 'phy-mode' or 'phy-connection-type', the latter being the one described in ePAPR, while the former has been widely adopted by Linux nowadays (and other OSes possibly).

My 2 cents since I don't typically review u-boot changes.

Signature · 1 line
Florian
#6 lore raw

PATCH 1/3 phy: Add phy driver support for xilinx PCS/PMA core

In reply to Joe Hershberger
Quoted 152 lines · Joe Hershberger
Quoted 55 lines · Michal Simek

From: Siva Durga Prasad Paladugu <[email protected]>

Add phy driver support for xilinx PCS/PMA core

---

 drivers/net/phy/Makefile     |   1 +
 drivers/net/phy/phy.c        |   3 +
 drivers/net/phy/xilinx_phy.c | 144 +++++++++++++++++++++++++++++++++++++++++++
 include/phy.h                |   1 +
 4 files changed, 149 insertions(+)
 create mode 100644 drivers/net/phy/xilinx_phy.c
drivers/net/phy/Makefile +1 -0
index 9e4d4927e676..1e299b97b961 100644
@@ -25,4 +25,5 @@ obj-$(CONFIG_PHY_REALTEK) += realtek.o
 obj-$(CONFIG_PHY_SMSC) += smsc.o
 obj-$(CONFIG_PHY_TERANETICS) += teranetics.o
 obj-$(CONFIG_PHY_TI) += ti.o
+obj-$(CONFIG_PHY_XILINX) += xilinx_phy.o
 obj-$(CONFIG_PHY_VITESSE) += vitesse.o
drivers/net/phy/phy.c +3 -0
index 17866a244b3a..23c82bb36e93 100644
@@ -503,6 +503,9 @@ int phy_init(void)
 #ifdef CONFIG_PHY_VITESSE
        phy_vitesse_init();
 #endif
+#ifdef CONFIG_PHY_XILINX
+       phy_xilinx_init();
+#endif
 
        return 0;
 }
drivers/net/phy/xilinx_phy.c new file +9 -0
new file mode 100644
index 000000000000..f3eaf2e97ced
@@ -0,0 +1,144 @@
+/*
+ * Xilinx PCS/PMA Core phy driver
+ *
+ * Copyright (C) 2015 - 2016 Xilinx, Inc.
+ *
+ * SPDX-License-Identifier:    GPL-2.0+
+ */
+
+#include <config.h>

drivers/net/phy/xilinx_phy.c line 19

Quoted 10 lines
drivers/net/phy/xilinx_phy.c new file +10 -0
+#include <common.h>
+#include <phy.h>
+#include <dm.h>
+
+DECLARE_GLOBAL_DATA_PTR;
+
+#define MII_PHY_STATUS_SPD_MASK                0x0C00
+#define MII_PHY_STATUS_FULLDUPLEX      0x1000
+#define MII_PHY_STATUS_1000            0x0800
+#define MII_PHY_STATUS_100             0x0400

Use the BIT() macro where appropriate.

Quoted 83 lines
drivers/net/phy/xilinx_phy.c new file +83 -0
+#define XPCSPMA_PHY_CTRL_ISOLATE_DISABLE 0xFBFF
+
+/* Mask used for ID comparisons */
+#define XILINX_PHY_ID_MASK             0xfffffff0
+
+/* Known PHY IDs */
+#define XILINX_PHY_ID                  0x01740c00
+
+/* struct phy_device dev_flags definitions */
+#define XAE_PHY_TYPE_MII               0
+#define XAE_PHY_TYPE_GMII              1
+#define XAE_PHY_TYPE_RGMII_1_3         2
+#define XAE_PHY_TYPE_RGMII_2_0         3
+#define XAE_PHY_TYPE_SGMII             4
+#define XAE_PHY_TYPE_1000BASE_X                5
+
+static int xilinxphy_startup(struct phy_device *phydev)
+{
+       int err;
+       int status = 0;
+
+       debug("%s\n", __func__);
+       /* Update the link, but return if there
+        * was an error
+        */
+       err = genphy_update_link(phydev);
+       if (err)
+               return err;
+
+       if (AUTONEG_ENABLE == phydev->autoneg) {
+               status = phy_read(phydev, MDIO_DEVAD_NONE, MII_LPA);
+               status = status & MII_PHY_STATUS_SPD_MASK;
+
+               if (status & MII_PHY_STATUS_FULLDUPLEX)
+                       phydev->duplex = DUPLEX_FULL;
+               else
+                       phydev->duplex = DUPLEX_HALF;
+
+               switch (status) {
+               case MII_PHY_STATUS_1000:
+                       phydev->speed = SPEED_1000;
+                       break;
+
+               case MII_PHY_STATUS_100:
+                       phydev->speed = SPEED_100;
+                       break;
+
+               default:
+                       phydev->speed = SPEED_10;
+                       break;
+               }
+       } else {
+               int bmcr = phy_read(phydev, MDIO_DEVAD_NONE, MII_BMCR);
+
+               if (bmcr < 0)
+                       return bmcr;
+
+               if (bmcr & BMCR_FULLDPLX)
+                       phydev->duplex = DUPLEX_FULL;
+               else
+                       phydev->duplex = DUPLEX_HALF;
+
+               if (bmcr & BMCR_SPEED1000)
+                       phydev->speed = SPEED_1000;
+               else if (bmcr & BMCR_SPEED100)
+                       phydev->speed = SPEED_100;
+               else
+                       phydev->speed = SPEED_10;
+       }
+
+       /*
+        * For 1000BASE-X Phy Mode the speed/duplex will always be
+        * 1000Mbps/fullduplex
+        */
+       if (phydev->flags == XAE_PHY_TYPE_1000BASE_X) {
+               phydev->duplex = DUPLEX_FULL;
+               phydev->speed = SPEED_1000;
+       }
+
+       return 0;
+}
+
+static int xilinxphy_of_init(struct phy_device *phydev)
Quoted 8 lines

drivers/net/phy/xilinx_phy.c line 108

Quoted 6 lines
drivers/net/phy/xilinx_phy.c new file +6 -0
+{
+       struct udevice *dev = (struct udevice *)&phydev->dev;
+       u32 phytype;
+
+       debug("%s\n", __func__);
+       phytype = fdtdec_get_int(gd->fdt_blob, dev->of_offset, "phy-type", -1);

Is there a bindings document that can be included to describe this?

It should be added.

Siva: Can you please look at it?

Thanks,
Michal