]> git.ipfire.org Git - thirdparty/openwrt.git/commitdiff
ipq40xx: decouple mdio-ipq40xx and ar40xx
authorChristian Lamparter <chunkeey@gmail.com>
Sat, 9 Mar 2019 15:19:26 +0000 (16:19 +0100)
committerChristian Lamparter <chunkeey@gmail.com>
Fri, 2 Aug 2019 21:18:25 +0000 (23:18 +0200)
This makes it possible to delete the ar40xx driver in the
future by just removing the file.

Signed-off-by: Christian Lamparter <chunkeey@gmail.com>
target/linux/ipq40xx/patches-4.19/700-net-add-qualcomm-mdio.patch [new file with mode: 0644]
target/linux/ipq40xx/patches-4.19/705-net-add-qualcomm-ar40xx-phy.patch [moved from target/linux/ipq40xx/patches-4.19/700-net-add-qualcomm-mdio-and-phy.patch with 90% similarity]

diff --git a/target/linux/ipq40xx/patches-4.19/700-net-add-qualcomm-mdio.patch b/target/linux/ipq40xx/patches-4.19/700-net-add-qualcomm-mdio.patch
new file mode 100644 (file)
index 0000000..d67e59a
--- /dev/null
@@ -0,0 +1,230 @@
+--- a/drivers/net/phy/Kconfig
++++ b/drivers/net/phy/Kconfig
+@@ -519,6 +519,13 @@ config XILINX_GMII2RGMII
+         the Reduced Gigabit Media Independent Interface(RGMII) between
+         Ethernet physical media devices and the Gigabit Ethernet controller.
++config MDIO_IPQ40XX
++      tristate "Qualcomm Atheros ipq40xx MDIO interface"
++      depends on HAS_IOMEM && OF
++      ---help---
++        This driver supports the MDIO interface found in Qualcomm
++        Atheros ipq40xx Soc chip.
++
+ endif # PHYLIB
+ config MICREL_KS8995MA
+--- a/drivers/net/phy/Makefile
++++ b/drivers/net/phy/Makefile
+@@ -48,6 +48,7 @@ obj-$(CONFIG_MDIO_CAVIUM)    += mdio-cavium
+ obj-$(CONFIG_MDIO_GPIO)               += mdio-gpio.o
+ obj-$(CONFIG_MDIO_HISI_FEMAC) += mdio-hisi-femac.o
+ obj-$(CONFIG_MDIO_I2C)                += mdio-i2c.o
++obj-$(CONFIG_MDIO_IPQ40XX)    += mdio-ipq40xx.o
+ obj-$(CONFIG_MDIO_MOXART)     += mdio-moxart.o
+ obj-$(CONFIG_MDIO_MSCC_MIIM)  += mdio-mscc-miim.o
+ obj-$(CONFIG_MDIO_OCTEON)     += mdio-octeon.o
+--- /dev/null
++++ b/drivers/net/phy/mdio-ipq40xx.c
+@@ -0,0 +1,201 @@
++/*
++ * Copyright (c) 2015-2016, The Linux Foundation. All rights reserved.
++ *
++ * Permission to use, copy, modify, and/or distribute this software for
++ * any purpose with or without fee is hereby granted, provided that the
++ * above copyright notice and this permission notice appear in all copies.
++ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
++ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
++ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
++ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
++ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
++ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
++ * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
++ */
++
++#include <linux/delay.h>
++#include <linux/kernel.h>
++#include <linux/module.h>
++#include <linux/mutex.h>
++#include <linux/io.h>
++#include <linux/of_address.h>
++#include <linux/of_mdio.h>
++#include <linux/phy.h>
++#include <linux/platform_device.h>
++
++#define MDIO_CTRL_0_REG               0x40
++#define MDIO_CTRL_1_REG               0x44
++#define MDIO_CTRL_2_REG               0x48
++#define MDIO_CTRL_3_REG               0x4c
++#define MDIO_CTRL_4_REG               0x50
++#define MDIO_CTRL_4_ACCESS_BUSY               BIT(16)
++#define MDIO_CTRL_4_ACCESS_START              BIT(8)
++#define MDIO_CTRL_4_ACCESS_CODE_READ          0
++#define MDIO_CTRL_4_ACCESS_CODE_WRITE 1
++#define CTRL_0_REG_DEFAULT_VALUE      0x150FF
++
++#define IPQ40XX_MDIO_RETRY    1000
++#define IPQ40XX_MDIO_DELAY    10
++
++struct ipq40xx_mdio_data {
++      struct mii_bus  *mii_bus;
++      void __iomem    *membase;
++      int             phy_irq[PHY_MAX_ADDR];
++      struct device   *dev;
++};
++
++static int ipq40xx_mdio_wait_busy(struct ipq40xx_mdio_data *am)
++{
++      int i;
++
++      for (i = 0; i < IPQ40XX_MDIO_RETRY; i++) {
++              unsigned int busy;
++
++              busy = readl(am->membase + MDIO_CTRL_4_REG) &
++                      MDIO_CTRL_4_ACCESS_BUSY;
++              if (!busy)
++                      return 0;
++
++              /* BUSY might take to be cleard by 15~20 times of loop */
++              udelay(IPQ40XX_MDIO_DELAY);
++      }
++
++      dev_err(am->dev, "%s: MDIO operation timed out\n", am->mii_bus->name);
++
++      return -ETIMEDOUT;
++}
++
++static int ipq40xx_mdio_read(struct mii_bus *bus, int mii_id, int regnum)
++{
++      struct ipq40xx_mdio_data *am = bus->priv;
++      int value = 0;
++      unsigned int cmd = 0;
++
++      lockdep_assert_held(&bus->mdio_lock);
++
++      if (ipq40xx_mdio_wait_busy(am))
++              return -ETIMEDOUT;
++
++      /* issue the phy address and reg */
++      writel((mii_id << 8) | regnum, am->membase + MDIO_CTRL_1_REG);
++
++      cmd = MDIO_CTRL_4_ACCESS_START|MDIO_CTRL_4_ACCESS_CODE_READ;
++
++      /* issue read command */
++      writel(cmd, am->membase + MDIO_CTRL_4_REG);
++
++      /* Wait read complete */
++      if (ipq40xx_mdio_wait_busy(am))
++              return -ETIMEDOUT;
++
++      /* Read data */
++      value = readl(am->membase + MDIO_CTRL_3_REG);
++
++      return value;
++}
++
++static int ipq40xx_mdio_write(struct mii_bus *bus, int mii_id, int regnum,
++                          u16 value)
++{
++      struct ipq40xx_mdio_data *am = bus->priv;
++      unsigned int cmd = 0;
++
++      lockdep_assert_held(&bus->mdio_lock);
++
++      if (ipq40xx_mdio_wait_busy(am))
++              return -ETIMEDOUT;
++
++      /* issue the phy address and reg */
++      writel((mii_id << 8) | regnum, am->membase + MDIO_CTRL_1_REG);
++
++      /* issue write data */
++      writel(value, am->membase + MDIO_CTRL_2_REG);
++
++      cmd = MDIO_CTRL_4_ACCESS_START|MDIO_CTRL_4_ACCESS_CODE_WRITE;
++      /* issue write command */
++      writel(cmd, am->membase + MDIO_CTRL_4_REG);
++
++      /* Wait write complete */
++      if (ipq40xx_mdio_wait_busy(am))
++              return -ETIMEDOUT;
++
++      return 0;
++}
++
++static int ipq40xx_mdio_probe(struct platform_device *pdev)
++{
++      struct ipq40xx_mdio_data *am;
++      struct resource *res;
++      int i;
++
++      am = devm_kzalloc(&pdev->dev, sizeof(*am), GFP_KERNEL);
++      if (!am)
++              return -ENOMEM;
++
++      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
++      if (!res) {
++              dev_err(&pdev->dev, "no iomem resource found\n");
++              return -ENXIO;
++      }
++
++      am->membase = devm_ioremap_resource(&pdev->dev, res);
++      if (IS_ERR(am->membase)) {
++              dev_err(&pdev->dev, "unable to ioremap registers\n");
++              return PTR_ERR(am->membase);
++      }
++
++      am->mii_bus = devm_mdiobus_alloc(&pdev->dev);
++      if (!am->mii_bus)
++              return  -ENOMEM;
++
++      writel(CTRL_0_REG_DEFAULT_VALUE, am->membase + MDIO_CTRL_0_REG);
++
++      am->mii_bus->name = "ipq40xx_mdio";
++      am->mii_bus->read = ipq40xx_mdio_read;
++      am->mii_bus->write = ipq40xx_mdio_write;
++      am->mii_bus->priv = am;
++      am->mii_bus->parent = &pdev->dev;
++      snprintf(am->mii_bus->id, MII_BUS_ID_SIZE, "%s", dev_name(&pdev->dev));
++
++      for (i = 0; i < PHY_MAX_ADDR; i++)
++              am->phy_irq[i] = PHY_POLL;
++
++      memcpy(am->mii_bus->irq, am->phy_irq, sizeof(am->phy_irq));
++      am->dev = &pdev->dev;
++      platform_set_drvdata(pdev, am);
++
++      return of_mdiobus_register(am->mii_bus, pdev->dev.of_node);
++}
++
++static int ipq40xx_mdio_remove(struct platform_device *pdev)
++{
++      struct ipq40xx_mdio_data *am = platform_get_drvdata(pdev);
++
++      mdiobus_unregister(am->mii_bus);
++
++      return 0;
++}
++
++static const struct of_device_id ipq40xx_mdio_dt_ids[] = {
++      { .compatible = "qcom,ipq4019-mdio" },
++      { }
++};
++MODULE_DEVICE_TABLE(of, ipq40xx_mdio_dt_ids);
++
++static struct platform_driver ipq40xx_mdio_driver = {
++      .probe = ipq40xx_mdio_probe,
++      .remove = ipq40xx_mdio_remove,
++      .driver = {
++              .name = "ipq40xx-mdio",
++              .of_match_table = ipq40xx_mdio_dt_ids,
++      },
++};
++
++module_platform_driver(ipq40xx_mdio_driver);
++
++#define DRV_VERSION     "1.0"
++
++MODULE_DESCRIPTION("IPQ40XX MDIO interface driver");
++MODULE_AUTHOR("Qualcomm Atheros");
++MODULE_VERSION(DRV_VERSION);
++MODULE_LICENSE("Dual BSD/GPL");
similarity index 90%
rename from target/linux/ipq40xx/patches-4.19/700-net-add-qualcomm-mdio-and-phy.patch
rename to target/linux/ipq40xx/patches-4.19/705-net-add-qualcomm-ar40xx-phy.patch
index 37b88bb8acaa45e56ae9a9384ee111c47ce815d8..5feea6d4e02b4fbc5b82adfe96c1703063d2f846 100644 (file)
@@ -1,26 +1,9 @@
-From 5a71a2005a2e1e6bbe36f00386c495ad6626beb2 Mon Sep 17 00:00:00 2001
-From: Christian Lamparter <chunkeey@googlemail.com>
-Date: Thu, 19 Jan 2017 01:59:43 +0100
-Subject: [PATCH 30/38] NET: add qualcomm mdio and PHY
-
----
- drivers/net/phy/Kconfig  | 14 ++++++++++++++
- drivers/net/phy/Makefile |  2 ++
- 2 files changed, 16 insertions(+)
-
 --- a/drivers/net/phy/Kconfig
 +++ b/drivers/net/phy/Kconfig
-@@ -519,6 +519,20 @@ config XILINX_GMII2RGMII
-         the Reduced Gigabit Media Independent Interface(RGMII) between
-         Ethernet physical media devices and the Gigabit Ethernet controller.
+@@ -526,6 +526,13 @@ config MDIO_IPQ40XX
+         This driver supports the MDIO interface found in Qualcomm
+         Atheros ipq40xx Soc chip.
  
-+config MDIO_IPQ40XX
-+      tristate "Qualcomm Atheros ipq40xx MDIO interface"
-+      depends on HAS_IOMEM && OF
-+      ---help---
-+        This driver supports the MDIO interface found in Qualcomm
-+        Atheros ipq40xx Soc chip.
-+
 +config AR40XX_PHY
 +      tristate "Driver for Qualcomm Atheros IPQ40XX switches"
 +      depends on HAS_IOMEM && OF
@@ -33,15 +16,7 @@ Subject: [PATCH 30/38] NET: add qualcomm mdio and PHY
  config MICREL_KS8995MA
 --- a/drivers/net/phy/Makefile
 +++ b/drivers/net/phy/Makefile
-@@ -48,6 +48,7 @@ obj-$(CONFIG_MDIO_CAVIUM)    += mdio-cavium
- obj-$(CONFIG_MDIO_GPIO)               += mdio-gpio.o
- obj-$(CONFIG_MDIO_HISI_FEMAC) += mdio-hisi-femac.o
- obj-$(CONFIG_MDIO_I2C)                += mdio-i2c.o
-+obj-$(CONFIG_MDIO_IPQ40XX)    += mdio-ipq40xx.o
- obj-$(CONFIG_MDIO_MOXART)     += mdio-moxart.o
- obj-$(CONFIG_MDIO_MSCC_MIIM)  += mdio-mscc-miim.o
- obj-$(CONFIG_MDIO_OCTEON)     += mdio-octeon.o
-@@ -61,6 +62,7 @@ obj-y                                += $(sfp-obj-y) $(sfp-obj-m)
+@@ -62,6 +62,7 @@ obj-y                                += $(sfp-obj-y) $(sfp-obj-m)
  
  obj-$(CONFIG_AMD_PHY)         += amd.o
  obj-$(CONFIG_AQUANTIA_PHY)    += aquantia.o
@@ -2482,209 +2457,3 @@ Subject: [PATCH 30/38] NET: add qualcomm mdio and PHY
 +}
 +
 +#endif
---- /dev/null
-+++ b/drivers/net/phy/mdio-ipq40xx.c
-@@ -0,0 +1,203 @@
-+/*
-+ * Copyright (c) 2015-2016, The Linux Foundation. All rights reserved.
-+ *
-+ * Permission to use, copy, modify, and/or distribute this software for
-+ * any purpose with or without fee is hereby granted, provided that the
-+ * above copyright notice and this permission notice appear in all copies.
-+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
-+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
-+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
-+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
-+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
-+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
-+ * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-+ */
-+
-+#include <linux/delay.h>
-+#include <linux/kernel.h>
-+#include <linux/module.h>
-+#include <linux/mutex.h>
-+#include <linux/io.h>
-+#include <linux/of_address.h>
-+#include <linux/of_mdio.h>
-+#include <linux/phy.h>
-+#include <linux/platform_device.h>
-+
-+#define MDIO_CTRL_0_REG               0x40
-+#define MDIO_CTRL_1_REG               0x44
-+#define MDIO_CTRL_2_REG               0x48
-+#define MDIO_CTRL_3_REG               0x4c
-+#define MDIO_CTRL_4_REG               0x50
-+#define MDIO_CTRL_4_ACCESS_BUSY               BIT(16)
-+#define MDIO_CTRL_4_ACCESS_START              BIT(8)
-+#define MDIO_CTRL_4_ACCESS_CODE_READ          0
-+#define MDIO_CTRL_4_ACCESS_CODE_WRITE 1
-+#define CTRL_0_REG_DEFAULT_VALUE      0x150FF
-+
-+#define IPQ40XX_MDIO_RETRY    1000
-+#define IPQ40XX_MDIO_DELAY    10
-+
-+struct ipq40xx_mdio_data {
-+      struct mii_bus  *mii_bus;
-+      void __iomem    *membase;
-+      int             phy_irq[PHY_MAX_ADDR];
-+      struct device   *dev;
-+};
-+
-+static int ipq40xx_mdio_wait_busy(struct ipq40xx_mdio_data *am)
-+{
-+      int i;
-+
-+      for (i = 0; i < IPQ40XX_MDIO_RETRY; i++) {
-+              unsigned int busy;
-+
-+              busy = readl(am->membase + MDIO_CTRL_4_REG) &
-+                      MDIO_CTRL_4_ACCESS_BUSY;
-+              if (!busy)
-+                      return 0;
-+
-+              /* BUSY might take to be cleard by 15~20 times of loop */
-+              udelay(IPQ40XX_MDIO_DELAY);
-+      }
-+
-+      dev_err(am->dev, "%s: MDIO operation timed out\n", am->mii_bus->name);
-+
-+      return -ETIMEDOUT;
-+}
-+
-+static int ipq40xx_mdio_read(struct mii_bus *bus, int mii_id, int regnum)
-+{
-+      struct ipq40xx_mdio_data *am = bus->priv;
-+      int value = 0;
-+      unsigned int cmd = 0;
-+
-+      lockdep_assert_held(&bus->mdio_lock);
-+
-+      if (ipq40xx_mdio_wait_busy(am))
-+              return -ETIMEDOUT;
-+
-+      /* issue the phy address and reg */
-+      writel((mii_id << 8) | regnum, am->membase + MDIO_CTRL_1_REG);
-+
-+      cmd = MDIO_CTRL_4_ACCESS_START|MDIO_CTRL_4_ACCESS_CODE_READ;
-+
-+      /* issue read command */
-+      writel(cmd, am->membase + MDIO_CTRL_4_REG);
-+
-+      /* Wait read complete */
-+      if (ipq40xx_mdio_wait_busy(am))
-+              return -ETIMEDOUT;
-+
-+      /* Read data */
-+      value = readl(am->membase + MDIO_CTRL_3_REG);
-+
-+      return value;
-+}
-+
-+static int ipq40xx_mdio_write(struct mii_bus *bus, int mii_id, int regnum,
-+                          u16 value)
-+{
-+      struct ipq40xx_mdio_data *am = bus->priv;
-+      unsigned int cmd = 0;
-+
-+      lockdep_assert_held(&bus->mdio_lock);
-+
-+      if (ipq40xx_mdio_wait_busy(am))
-+              return -ETIMEDOUT;
-+
-+      /* issue the phy address and reg */
-+      writel((mii_id << 8) | regnum, am->membase + MDIO_CTRL_1_REG);
-+
-+      /* issue write data */
-+      writel(value, am->membase + MDIO_CTRL_2_REG);
-+
-+      cmd = MDIO_CTRL_4_ACCESS_START|MDIO_CTRL_4_ACCESS_CODE_WRITE;
-+      /* issue write command */
-+      writel(cmd, am->membase + MDIO_CTRL_4_REG);
-+
-+      /* Wait write complete */
-+      if (ipq40xx_mdio_wait_busy(am))
-+              return -ETIMEDOUT;
-+
-+      return 0;
-+}
-+
-+static int ipq40xx_mdio_probe(struct platform_device *pdev)
-+{
-+      struct ipq40xx_mdio_data *am;
-+      struct resource *res;
-+      int i;
-+
-+      am = devm_kzalloc(&pdev->dev, sizeof(*am), GFP_KERNEL);
-+      if (!am)
-+              return -ENOMEM;
-+
-+      res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-+      if (!res) {
-+              dev_err(&pdev->dev, "no iomem resource found\n");
-+              return -ENXIO;
-+      }
-+
-+      am->membase = devm_ioremap_resource(&pdev->dev, res);
-+      if (IS_ERR(am->membase)) {
-+              dev_err(&pdev->dev, "unable to ioremap registers\n");
-+              return PTR_ERR(am->membase);
-+      }
-+
-+      am->mii_bus = devm_mdiobus_alloc(&pdev->dev);
-+      if (!am->mii_bus)
-+              return  -ENOMEM;
-+
-+      writel(CTRL_0_REG_DEFAULT_VALUE, am->membase + MDIO_CTRL_0_REG);
-+
-+      am->mii_bus->name = "ipq40xx_mdio";
-+      am->mii_bus->read = ipq40xx_mdio_read;
-+      am->mii_bus->write = ipq40xx_mdio_write;
-+      am->mii_bus->priv = am;
-+      am->mii_bus->parent = &pdev->dev;
-+      snprintf(am->mii_bus->id, MII_BUS_ID_SIZE, "%s", dev_name(&pdev->dev));
-+
-+      for (i = 0; i < PHY_MAX_ADDR; i++)
-+              am->phy_irq[i] = PHY_POLL;
-+
-+      memcpy(am->mii_bus->irq, am->phy_irq, sizeof(am->phy_irq));
-+      am->dev = &pdev->dev;
-+      platform_set_drvdata(pdev, am);
-+
-+      /* edma_axi_probe() use "am" drvdata.
-+       * ipq40xx_mdio_probe() must be called first.
-+       */
-+      return of_mdiobus_register(am->mii_bus, pdev->dev.of_node);
-+}
-+
-+static int ipq40xx_mdio_remove(struct platform_device *pdev)
-+{
-+      struct ipq40xx_mdio_data *am = platform_get_drvdata(pdev);
-+
-+      mdiobus_unregister(am->mii_bus);
-+      return 0;
-+}
-+
-+static const struct of_device_id ipq40xx_mdio_dt_ids[] = {
-+      { .compatible = "qcom,ipq4019-mdio" },
-+      { }
-+};
-+MODULE_DEVICE_TABLE(of, ipq40xx_mdio_dt_ids);
-+
-+static struct platform_driver ipq40xx_mdio_driver = {
-+      .probe = ipq40xx_mdio_probe,
-+      .remove = ipq40xx_mdio_remove,
-+      .driver = {
-+              .name = "ipq40xx-mdio",
-+              .of_match_table = ipq40xx_mdio_dt_ids,
-+      },
-+};
-+
-+module_platform_driver(ipq40xx_mdio_driver);
-+
-+#define DRV_VERSION     "1.0"
-+
-+MODULE_DESCRIPTION("IPQ40XX MDIO interface driver");
-+MODULE_AUTHOR("Qualcomm Atheros");
-+MODULE_VERSION(DRV_VERSION);
-+MODULE_LICENSE("Dual BSD/GPL");