U-Boot
Threads by month
- ----- 2025 -----
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2010 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2009 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2008 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2007 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2006 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2005 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2004 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2003 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2002 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2001 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2000 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
May 2017
- 189 participants
- 640 discussions

[U-Boot] [PATCH] Add support for Microchip LAN75xx and LAN78xx
by Yuiko.Oshino@microchip.com 30 May '17
by Yuiko.Oshino@microchip.com 30 May '17
30 May '17
From: Yuiko Oshino <yuiko.oshino(a)microchip.com>
Add support for Microchip LAN7500, LAN7800 and 7850, USB to 10/100/1000 Ethernet Controllers
Signed-off-by: Yuiko Oshino <yuiko.oshino(a)microchip.com>
Cc: Marek Vasut <marex(a)denx.de>
---
drivers/usb/Kconfig | 2 +
drivers/usb/eth/Kconfig | 18 ++
drivers/usb/eth/Makefile | 2 +
drivers/usb/eth/lan75xx.c | 463 ++++++++++++++++++++++++++++++
drivers/usb/eth/lan78xx.c | 611 +++++++++++++++++++++++++++++++++++++++
drivers/usb/eth/lan7x.c | 680 ++++++++++++++++++++++++++++++++++++++++++++
drivers/usb/eth/lan7x.h | 189 ++++++++++++
drivers/usb/eth/usb_ether.c | 14 +
include/usb_ether.h | 12 +
9 files changed, 1991 insertions(+)
create mode 100644 drivers/usb/eth/Kconfig
create mode 100644 drivers/usb/eth/lan75xx.c
create mode 100644 drivers/usb/eth/lan78xx.c
create mode 100644 drivers/usb/eth/lan7x.c
create mode 100644 drivers/usb/eth/lan7x.h
diff --git a/drivers/usb/Kconfig b/drivers/usb/Kconfig
index da3ec2f..62126aa 100644
--- a/drivers/usb/Kconfig
+++ b/drivers/usb/Kconfig
@@ -94,4 +94,6 @@ endif
source "drivers/usb/gadget/Kconfig"
+source "drivers/usb/eth/Kconfig"
+
endif
diff --git a/drivers/usb/eth/Kconfig b/drivers/usb/eth/Kconfig
new file mode 100644
index 0000000..a07243f
--- /dev/null
+++ b/drivers/usb/eth/Kconfig
@@ -0,0 +1,18 @@
+comment "USB to Ethernet Controller Drivers"
+
+config USB_ETHER_LAN75XX
+ bool "Microchip LAN75XX support"
+ ---help---
+ Say Y here if you would like to support Microchip LAN75XX Hi-Speed
+ USB 2.0 to 10/100/1000 Gigabit Ethernet controller.
+ Supports 10Base-T/ 100Base-TX/1000Base-T.
+ This driver supports the internal PHY.
+
+config USB_ETHER_LAN78XX
+ bool "Microchip LAN78XX support"
+ ---help---
+ Say Y here if you would like to support Microchip LAN78XX USB 3.1
+ Gen 1 to 10/100/1000 Gigabit Ethernet controller.
+ Supports 10Base-T/ 100Base-TX/1000Base-T.
+ This driver supports the internal PHY.
+
diff --git a/drivers/usb/eth/Makefile b/drivers/usb/eth/Makefile
index 4c44efc..4b935a3 100644
--- a/drivers/usb/eth/Makefile
+++ b/drivers/usb/eth/Makefile
@@ -9,4 +9,6 @@ obj-$(CONFIG_USB_ETHER_ASIX) += asix.o
obj-$(CONFIG_USB_ETHER_ASIX88179) += asix88179.o
obj-$(CONFIG_USB_ETHER_MCS7830) += mcs7830.o
obj-$(CONFIG_USB_ETHER_SMSC95XX) += smsc95xx.o
+obj-$(CONFIG_USB_ETHER_LAN75XX) += lan7x.o lan75xx.o
+obj-$(CONFIG_USB_ETHER_LAN78XX) += lan7x.o lan78xx.o
obj-$(CONFIG_USB_ETHER_RTL8152) += r8152.o r8152_fw.o
diff --git a/drivers/usb/eth/lan75xx.c b/drivers/usb/eth/lan75xx.c
new file mode 100644
index 0000000..f67b216
--- /dev/null
+++ b/drivers/usb/eth/lan75xx.c
@@ -0,0 +1,463 @@
+/*
+ * Copyright (c) 2017 Microchip Technology Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <dm.h>
+#include <usb.h>
+#include <linux/mii.h>
+#include "usb_ether.h"
+#include "lan7x.h"
+
+/* SCSRs */
+#define LAN75XX_HW_CFG_BIR BIT(7)
+
+#define LAN75XX_BURST_CAP 0x034
+
+#define LAN75XX_BULK_IN_DLY 0x03C
+
+#define LAN75XX_RFE_CTL 0x060
+
+#define LAN75XX_FCT_RX_CTL 0x090
+
+#define LAN75XX_FCT_TX_CTL 0x094
+
+#define LAN75XX_FCT_RX_FIFO_END 0x098
+
+#define LAN75XX_FCT_TX_FIFO_END 0x09C
+
+#define LAN75XX_FCT_FLOW 0x0A0
+
+/* MAC ADDRESS PERFECT FILTER For LAN75xx */
+#define LAN75XX_ADDR_FILTX 0x300
+#define LAN75XX_ADDR_FILTX_FB_VALID BIT(31)
+
+#ifndef CONFIG_DM_ETH
+/* local vars */
+static int curr_eth_dev; /* index for name of next device detected */
+
+/* local defines */
+#define LAN75XX_BASE_NAME "lan75xx"
+#endif
+
+/*
+ * Lan75xx infrastructure commands
+ */
+static int lan75xx_phy_gig_workaround(struct usb_device *udev,
+ struct ueth_data *dev)
+{
+ int ret = 0;
+
+ /* Only internal phy */
+ /* Set the phy in Gig loopback */
+ lan7x_mdio_write(udev, dev->phy_id, MII_BMCR,
+ (BMCR_LOOPBACK | BMCR_SPEED1000));
+
+ /* Wait for the link up */
+ ret = lan7x_mdio_wait_for_bit(udev, "BMSR_LSTATUS",
+ dev->phy_id, MII_BMSR, BMSR_LSTATUS,
+ true, PHY_CONNECT_TIMEOUT_MS);
+ if (ret)
+ return ret;
+
+ /* phy reset */
+ ret = lan7x_pmt_phy_reset(udev, dev);
+ return ret;
+}
+
+static int lan75xx_update_flowcontrol(struct usb_device *udev,
+ struct ueth_data *dev)
+{
+ uint32_t flow = 0, fct_flow = 0;
+ int ret;
+
+ ret = lan7x_update_flowcontrol(udev, dev, &flow, &fct_flow);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, FLOW, flow);
+ ret = lan7x_write_reg(udev, LAN75XX_FCT_FLOW, fct_flow);
+ return ret;
+}
+
+static int lan75xx_read_mac(unsigned char *enetaddr,
+ struct usb_device *udev)
+{
+ /*
+ * Refer to the doc/README.enetaddr and doc/README.usb for
+ * the U-Boot MAC address policy
+ */
+ return lan7x_read_eeprom_mac(enetaddr, udev);
+}
+
+static int lan75xx_write_hwaddr_common(struct usb_device *udev,
+ struct lan7x_private *priv,
+ unsigned char *enetaddr)
+{
+ u32 addr_lo = get_unaligned_le32(&enetaddr[0]);
+ u32 addr_hi = (u32)get_unaligned_le16(&enetaddr[4]);
+ int ret;
+
+ /* set hardware address */
+ ret = lan7x_write_reg(udev, RX_ADDRL, addr_lo);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, RX_ADDRH, addr_hi);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, LAN75XX_ADDR_FILTX + 4, addr_lo);
+ if (ret)
+ return ret;
+
+ addr_hi |= LAN75XX_ADDR_FILTX_FB_VALID;
+ ret = lan7x_write_reg(udev, LAN75XX_ADDR_FILTX, addr_hi);
+ if (ret)
+ return ret;
+
+ debug("MAC addr %pM written\n", enetaddr);
+ priv->have_hwaddr = 1;
+
+ return 0;
+}
+
+static int lan75xx_set_multicast(struct usb_device *udev)
+{
+ int ret;
+ u32 write_buf;
+
+ /* No multicast in u-boot */
+ write_buf = RFE_CTL_BCAST_EN | RFE_CTL_DA_PERFECT;
+ ret = lan7x_write_reg(udev, LAN75XX_RFE_CTL, write_buf);
+
+ return ret;
+}
+
+/* starts the TX path */
+static void lan75xx_start_tx_path(struct usb_device *udev)
+{
+ u32 reg_val;
+
+ /* Enable Tx at MAC */
+ reg_val = MAC_TX_TXEN;
+ lan7x_write_reg(udev, MAC_TX, reg_val);
+
+ /* Enable Tx at SCSRs */
+ reg_val = FCT_TX_CTL_EN;
+ lan7x_write_reg(udev, LAN75XX_FCT_TX_CTL, reg_val);
+}
+
+/* Starts the Receive path */
+static void lan75xx_start_rx_path(struct usb_device *udev)
+{
+ u32 reg_val;
+
+ /* Enable Rx at MAC */
+ reg_val = LAN7X_MAC_RX_MAX_SIZE_DEFAULT |
+ MAC_RX_FCS_STRIP | MAC_RX_RXEN;
+ lan7x_write_reg(udev, MAC_RX, reg_val);
+
+ /* Enable Rx at SCSRs */
+ reg_val = FCT_RX_CTL_EN;
+ lan7x_write_reg(udev, LAN75XX_FCT_RX_CTL, reg_val);
+}
+
+static int lan75xx_basic_reset(struct usb_device *udev,
+ struct ueth_data *dev,
+ struct lan7x_private *priv)
+{
+ int ret;
+ u32 write_buf;
+
+ ret = lan7x_basic_reset(udev, dev);
+ if (ret)
+ return ret;
+
+ /* Keep the chip ID */
+ ret = lan7x_read_reg(udev, ID_REV, &priv->chipid);
+ if (ret)
+ return ret;
+ debug("LAN75xx ID_REV = 0x%08x\n", priv->chipid);
+
+ priv->chipid = (priv->chipid & ID_REV_CHIP_ID_MASK) >> 16;
+
+ /* Respond to the IN token with a NAK */
+ ret = lan7x_read_reg(udev, HW_CFG, &write_buf);
+ if (ret)
+ return ret;
+ write_buf |= LAN75XX_HW_CFG_BIR;
+ ret = lan7x_write_reg(udev, HW_CFG, write_buf);
+
+ return ret;
+}
+
+static int lan75xx_init_common(struct usb_device *udev,
+ struct ueth_data *dev,
+ struct lan7x_private *priv,
+ unsigned char *enetaddr)
+{
+ int ret;
+ u32 write_buf;
+
+ /* Reset and read Mac addr were done in get_info() or in probe() */
+
+#ifndef CONFIG_DM_ETH
+ if (!priv->have_hwaddr && is_valid_ethaddr(enetaddr)) {
+ priv->have_hwaddr = 1;
+ debug("LAN75xx: MAC address found and set %pM\n", enetaddr);
+ }
+#endif
+ if (!priv->have_hwaddr) {
+ printf("Error: LAN75xx: No MAC address set - set usbethaddr\n");
+ return -EADDRNOTAVAIL;
+ }
+ ret = lan75xx_write_hwaddr_common(udev, priv, enetaddr);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, INT_STS, 0xFFFFFFFF);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, LAN75XX_BURST_CAP, 0);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, LAN75XX_BULK_IN_DLY, DEFAULT_BULK_IN_DELAY);
+ if (ret)
+ return ret;
+
+ /* set FIFO sizes */
+ write_buf = (MAX_RX_FIFO_SIZE - 512) / 512;
+ ret = lan7x_write_reg(udev, LAN75XX_FCT_RX_FIFO_END, write_buf);
+ if (ret)
+ return ret;
+
+ write_buf = (MAX_TX_FIFO_SIZE - 512) / 512;
+ ret = lan7x_write_reg(udev, LAN75XX_FCT_TX_FIFO_END, write_buf);
+ if (ret)
+ return ret;
+
+ /* Init Tx */
+ ret = lan7x_write_reg(udev, FLOW, 0);
+ if (ret)
+ return ret;
+
+ /* Init Rx. Set Vlan, keep defult for VLAN on 75xx */
+ ret = lan75xx_set_multicast(udev);
+ if (ret)
+ return ret;
+
+ /* phy workaround for gig link */
+ ret = lan75xx_phy_gig_workaround(udev, dev);
+ if (ret)
+ return ret;
+
+ /* Init PHY, autonego, and link */
+ ret = lan7x_phy_initialize(udev, dev);
+ if (ret)
+ return ret;
+
+ /*
+ * MAC_CR has to be set after PHY init.
+ * MAC will auto detect the PHY speed.
+ */
+ ret = lan7x_read_reg(udev, MAC_CR, &write_buf);
+ if (ret)
+ return ret;
+ write_buf |= MAC_CR_AUTO_DUPLEX | MAC_CR_AUTO_SPEED | MAC_CR_ADP;
+ ret = lan7x_write_reg(udev, MAC_CR, write_buf);
+ if (ret)
+ return ret;
+
+ lan75xx_start_tx_path(udev);
+ lan75xx_start_rx_path(udev);
+
+ ret = lan75xx_update_flowcontrol(udev, dev);
+
+ return ret;
+}
+
+#ifndef CONFIG_DM_ETH
+/*
+ * lan75xx callbacks
+ */
+static int lan75xx_init(struct eth_device *eth, bd_t *bd)
+{
+ struct ueth_data *dev = (struct ueth_data *)eth->priv;
+ struct usb_device *udev = dev->pusb_dev;
+ struct lan7x_private *priv = (struct lan7x_private *)dev->dev_priv;
+
+ return lan75xx_init_common(udev, dev, priv, eth->enetaddr);
+}
+
+static int lan75xx_write_hwaddr(struct eth_device *eth)
+{
+ struct ueth_data *dev = eth->priv;
+ struct usb_device *udev = dev->pusb_dev;
+ struct lan7x_private *priv = dev->dev_priv;
+
+ return lan75xx_write_hwaddr_common(udev, priv, eth->enetaddr);
+}
+
+/*
+ * Microchip probing functions
+ */
+void lan75xx_eth_before_probe(void)
+{
+ curr_eth_dev = 0;
+}
+
+static const struct lan7x_dongle lan75xx_dongles[] = {
+ {0x0424, 0x7500}, /* LAN7500 USB Ethernet */
+ {0x0000, 0x0000} /* END - Do not remove */
+};
+
+/* Probe to see if a new device is actually an Microchip device */
+int lan75xx_eth_probe(struct usb_device *dev, unsigned int ifnum,
+ struct ueth_data *ss)
+{
+ int i;
+
+ /* let's examine the device now */
+ for (i = 0; lan75xx_dongles[i].vendor != 0; i++) {
+ if (dev->descriptor.idVendor == lan75xx_dongles[i].vendor &&
+ dev->descriptor.idProduct == lan75xx_dongles[i].product)
+ /* Found a supported dongle */
+ break;
+ }
+ if (lan75xx_dongles[i].vendor == 0)
+ return 0;
+
+ /* At this point, we know we've got a live one */
+ debug("\n\nUSB Ethernet device LAN75xx detected\n");
+
+ /*
+ * Note that this function needs to return 1
+ * for success
+ */
+ return lan7x_eth_probe(dev, ifnum, ss);
+}
+
+int lan75xx_eth_get_info(struct usb_device *dev, struct ueth_data *ss,
+ struct eth_device *eth)
+{
+ struct lan7x_private *priv = ss->dev_priv;
+
+ printf("LAN75xx name: %s%d\n", LAN75XX_BASE_NAME, curr_eth_dev);
+
+ if (!eth) {
+ debug("%s: missing parameter.\n", __func__);
+ return 0;
+ }
+ sprintf(eth->name, "%s%d", LAN75XX_BASE_NAME, curr_eth_dev++);
+ eth->init = lan75xx_init;
+ eth->send = lan7x_send;
+ eth->recv = lan7x_recv;
+ eth->halt = lan7x_halt;
+ eth->write_hwaddr = lan75xx_write_hwaddr;
+ eth->priv = ss;
+
+ /* Do a reset in order to get the MAC address from HW */
+ if (lan75xx_basic_reset(dev, ss, priv))
+ return 0;
+
+ /* Get the MAC address */
+ /*
+ * We must set the eth->enetaddr from HW because the upper layer
+ * will force to use the environmental var (usbethaddr) or random if
+ * there is no valid MAC address in eth->enetaddr.
+ */
+ lan75xx_read_mac(eth->enetaddr, dev);
+ /* Do not return 0 for not finding MAC addr in HW */
+
+ return 1;
+}
+#endif /* !CONFIG_DM_ETH */
+
+#ifdef CONFIG_DM_ETH
+static int lan75xx_eth_start(struct udevice *dev)
+{
+ struct usb_device *udev = dev_get_parent_priv(dev);
+ struct lan7x_private *priv = dev_get_priv(dev);
+ struct eth_pdata *pdata = dev_get_platdata(dev);
+
+ /* Driver-model Ethernet ensures we have this */
+ priv->have_hwaddr = 1;
+
+ return lan75xx_init_common(udev, &priv->ueth, priv, pdata->enetaddr);
+}
+
+int lan75xx_write_hwaddr(struct udevice *dev)
+{
+ struct usb_device *udev = dev_get_parent_priv(dev);
+ struct eth_pdata *pdata = dev_get_platdata(dev);
+ struct lan7x_private *priv = dev_get_priv(dev);
+
+ return lan75xx_write_hwaddr_common(udev, priv, pdata->enetaddr);
+}
+
+int lan75xx_read_rom_hwaddr(struct udevice *dev)
+{
+ struct usb_device *udev = dev_get_parent_priv(dev);
+ struct eth_pdata *pdata = dev_get_platdata(dev);
+ int ret;
+
+ ret = lan75xx_read_mac(pdata->enetaddr, udev);
+ if (ret)
+ memset(pdata->enetaddr, 0, 6);
+
+ return 0;
+}
+
+static int lan75xx_eth_probe(struct udevice *dev)
+{
+ struct usb_device *udev = dev_get_parent_priv(dev);
+ struct lan7x_private *priv = dev_get_priv(dev);
+ struct ueth_data *ueth = &priv->ueth;
+ struct eth_pdata *pdata = dev_get_platdata(dev);
+
+ /* Do a reset in order to get the MAC address from HW */
+ if (lan75xx_basic_reset(udev, ueth, priv))
+ return 0;
+
+ /* Get the MAC address */
+ /*
+ * We must set the eth->enetaddr from HW because the upper layer
+ * will force to use the environmental var (usbethaddr) or random if
+ * there is no valid MAC address in eth->enetaddr.
+ */
+ lan75xx_read_mac(pdata->enetaddr, udev);
+ /* Do not return 0 for not finding MAC addr in HW */
+
+ return usb_ether_register(dev, ueth, RX_URB_SIZE);
+}
+
+static const struct eth_ops lan75xx_eth_ops = {
+ .start = lan75xx_eth_start,
+ .send = lan7x_eth_send,
+ .recv = lan7x_eth_recv,
+ .free_pkt = lan7x_free_pkt,
+ .stop = lan7x_eth_stop,
+ .write_hwaddr = lan75xx_write_hwaddr,
+ .read_rom_hwaddr = lan75xx_read_rom_hwaddr,
+};
+
+U_BOOT_DRIVER(lan75xx_eth) = {
+ .name = "lan75xx_eth",
+ .id = UCLASS_ETH,
+ .probe = lan75xx_eth_probe,
+ .ops = &lan75xx_eth_ops,
+ .priv_auto_alloc_size = sizeof(struct lan7x_private),
+ .platdata_auto_alloc_size = sizeof(struct eth_pdata),
+};
+
+static const struct usb_device_id lan75xx_eth_id_table[] = {
+ { USB_DEVICE(0x0424, 0x7500) }, /* LAN7500 USB Ethernet */
+ { } /* Terminating entry */
+};
+
+U_BOOT_USB_DEVICE(lan75xx_eth, lan75xx_eth_id_table);
+#endif
diff --git a/drivers/usb/eth/lan78xx.c b/drivers/usb/eth/lan78xx.c
new file mode 100644
index 0000000..e450f2c
--- /dev/null
+++ b/drivers/usb/eth/lan78xx.c
@@ -0,0 +1,611 @@
+/*
+ * Copyright (c) 2017 Microchip Technology Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <dm.h>
+#include <usb.h>
+#include "usb_ether.h"
+#include "lan7x.h"
+
+/* LAN78xx specific register/bit defines */
+#define LAN78XX_HW_CFG_LED1_EN BIT(21) /* Muxed with EEDO */
+#define LAN78XX_HW_CFG_LED0_EN BIT(20) /* Muxed with EECLK */
+
+#define LAN78XX_USB_CFG0 0x080
+#define LAN78XX_USB_CFG0_BIR BIT(6)
+
+#define LAN78XX_BURST_CAP 0x090
+
+#define LAN78XX_BULK_IN_DLY 0x094
+
+#define LAN78XX_RFE_CTL 0x0B0
+
+#define LAN78XX_FCT_RX_CTL 0x0C0
+
+#define LAN78XX_FCT_TX_CTL 0x0C4
+
+#define LAN78XX_FCT_RX_FIFO_END 0x0C8
+
+#define LAN78XX_FCT_TX_FIFO_END 0x0CC
+
+#define LAN78XX_FCT_FLOW 0x0D0
+
+#define LAN78XX_MAF_BASE 0x400
+#define LAN78XX_MAF_HIX 0x00
+#define LAN78XX_MAF_LOX 0x04
+#define LAN78XX_MAF_HI_BEGIN (LAN78XX_MAF_BASE + LAN78XX_MAF_HIX)
+#define LAN78XX_MAF_LO_BEGIN (LAN78XX_MAF_BASE + LAN78XX_MAF_LOX)
+#define LAN78XX_MAF_HI(index) (LAN78XX_MAF_BASE + (8 * (index)) + \
+ (LAN78XX_MAF_HIX))
+#define LAN78XX_MAF_LO(index) (LAN78XX_MAF_BASE + (8 * (index)) + \
+ (LAN78XX_MAF_LOX))
+#define LAN78XX_MAF_HI_VALID BIT(31)
+
+/* OTP registers */
+#define LAN78XX_OTP_BASE_ADDR 0x00001000
+
+#define LAN78XX_OTP_PWR_DN (LAN78XX_OTP_BASE_ADDR + 4 * 0x00)
+#define LAN78XX_OTP_PWR_DN_PWRDN_N BIT(0)
+
+#define LAN78XX_OTP_ADDR1 (LAN78XX_OTP_BASE_ADDR + 4 * 0x01)
+#define LAN78XX_OTP_ADDR1_15_11 0x1F
+
+#define LAN78XX_OTP_ADDR2 (LAN78XX_OTP_BASE_ADDR + 4 * 0x02)
+#define LAN78XX_OTP_ADDR2_10_3 0xFF
+
+#define LAN78XX_OTP_RD_DATA (LAN78XX_OTP_BASE_ADDR + 4 * 0x06)
+
+#define LAN78XX_OTP_FUNC_CMD (LAN78XX_OTP_BASE_ADDR + 4 * 0x08)
+#define LAN78XX_OTP_FUNC_CMD_READ BIT(0)
+
+#define LAN78XX_OTP_CMD_GO (LAN78XX_OTP_BASE_ADDR + 4 * 0x0A)
+#define LAN78XX_OTP_CMD_GO_GO BIT(0)
+
+#define LAN78XX_OTP_STATUS (LAN78XX_OTP_BASE_ADDR + 4 * 0x0C)
+#define LAN78XX_OTP_STATUS_BUSY BIT(0)
+
+#define LAN78XX_OTP_INDICATOR_1 0xF3
+#define LAN78XX_OTP_INDICATOR_2 0xF7
+
+#ifndef CONFIG_DM_ETH
+/* local vars */
+static int curr_eth_dev; /* index for name of next device detected */
+
+/* local defines */
+#define LAN78XX_BASE_NAME "lan78xx"
+#endif
+
+/*
+ * Lan78xx infrastructure commands
+ */
+static int lan78xx_read_raw_otp(struct usb_device *udev, u32 offset,
+ u32 length, u8 *data)
+{
+ int i;
+ int ret;
+ u32 buf;
+
+ ret = lan7x_read_reg(udev, LAN78XX_OTP_PWR_DN, &buf);
+ if (ret)
+ return ret;
+
+ if (buf & LAN78XX_OTP_PWR_DN_PWRDN_N) {
+ /* clear it and wait to be cleared */
+ ret = lan7x_write_reg(udev, LAN78XX_OTP_PWR_DN, 0);
+
+ ret = lan7x_wait_for_bit(udev, "LAN78XX_OTP_PWR_DN_PWRDN_N",
+ LAN78XX_OTP_PWR_DN,
+ LAN78XX_OTP_PWR_DN_PWRDN_N,
+ false, 1000);
+ if (ret)
+ return ret;
+ }
+
+ for (i = 0; i < length; i++) {
+ ret = lan7x_write_reg(udev, LAN78XX_OTP_ADDR1,
+ ((offset + i) >> 8) &
+ LAN78XX_OTP_ADDR1_15_11);
+ ret = lan7x_write_reg(udev, LAN78XX_OTP_ADDR2,
+ ((offset + i) & LAN78XX_OTP_ADDR2_10_3));
+
+ ret = lan7x_write_reg(udev, LAN78XX_OTP_FUNC_CMD,
+ LAN78XX_OTP_FUNC_CMD_READ);
+ ret = lan7x_write_reg(udev, LAN78XX_OTP_CMD_GO,
+ LAN78XX_OTP_CMD_GO_GO);
+
+ if (ret)
+ return ret;
+
+ ret = lan7x_wait_for_bit(udev, "LAN78XX_OTP_STATUS_BUSY",
+ LAN78XX_OTP_STATUS,
+ LAN78XX_OTP_STATUS_BUSY,
+ false, 1000);
+ if (ret)
+ return ret;
+
+ ret = lan7x_read_reg(udev, LAN78XX_OTP_RD_DATA, &buf);
+
+ data[i] = (u8)(buf & 0xFF);
+ }
+
+ return 0;
+}
+
+static int lan78xx_read_otp(struct usb_device *udev, u32 offset,
+ u32 length, u8 *data)
+{
+ u8 sig;
+ int ret;
+
+ ret = lan78xx_read_raw_otp(udev, 0, 1, &sig);
+
+ if (!ret) {
+ if (sig == LAN78XX_OTP_INDICATOR_1)
+ offset = offset;
+ else if (sig == LAN78XX_OTP_INDICATOR_2)
+ offset += 0x100;
+ else
+ return -EINVAL;
+ ret = lan78xx_read_raw_otp(udev, offset, length, data);
+ }
+ debug("LAN78x: MAC address from OTP = %pM\n", data);
+
+ return ret;
+}
+
+static int lan78xx_read_otp_mac(unsigned char *enetaddr,
+ struct usb_device *udev)
+{
+ int ret;
+
+ memset(enetaddr, 0, 6);
+
+ ret = lan78xx_read_otp(udev,
+ EEPROM_MAC_OFFSET,
+ ETH_ALEN,
+ enetaddr);
+ if (!ret && is_valid_ethaddr(enetaddr)) {
+ /* eeprom values are valid so use them */
+ debug("MAC address read from OTP %pM\n", enetaddr);
+ return 0;
+ }
+ debug("MAC address read from OTP invalid %pM\n", enetaddr);
+
+ memset(enetaddr, 0, 6);
+ return -1;
+}
+
+static int lan78xx_update_flowcontrol(struct usb_device *udev,
+ struct ueth_data *dev)
+{
+ uint32_t flow = 0, fct_flow = 0;
+ int ret;
+
+ ret = lan7x_update_flowcontrol(udev, dev, &flow, &fct_flow);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, FLOW, flow);
+ ret = lan7x_write_reg(udev, LAN78XX_FCT_FLOW, fct_flow);
+ return ret;
+}
+
+static int lan78xx_read_mac(unsigned char *enetaddr,
+ struct usb_device *udev,
+ struct lan7x_private *priv)
+{
+ u32 val;
+ int ret;
+ int saved = 0, done = 0;
+
+ /*
+ * Depends on chip, some EEPROM pins are muxed with LED function.
+ * disable & restore LED function to access EEPROM.
+ */
+ if ((priv->chipid == ID_REV_CHIP_ID_7800) ||
+ (priv->chipid == ID_REV_CHIP_ID_7850)) {
+ ret = lan7x_read_reg(udev, HW_CFG, &val);
+ saved = val;
+ val &= ~(LAN78XX_HW_CFG_LED1_EN | LAN78XX_HW_CFG_LED0_EN);
+ ret = lan7x_write_reg(udev, HW_CFG, val);
+ if (ret)
+ goto restore;
+ }
+
+ /*
+ * Refer to the doc/README.enetaddr and doc/README.usb for
+ * the U-Boot MAC address policy
+ */
+ /* try reading mac address from EEPROM, then from OTP */
+ ret = lan7x_read_eeprom_mac(enetaddr, udev);
+ if (!ret)
+ done = 1;
+
+restore:
+ if ((priv->chipid == ID_REV_CHIP_ID_7800) ||
+ (priv->chipid == ID_REV_CHIP_ID_7850)) {
+ ret = lan7x_write_reg(udev, HW_CFG, saved);
+ }
+ /* if the EEPROM mac address is good, then exit */
+ if (done)
+ return 0;
+
+ /* try reading mac address from OTP if the device is LAN78xx */
+ ret = lan78xx_read_otp_mac(enetaddr, udev);
+
+ return ret;
+}
+
+static int lan78xx_write_hwaddr_common(struct usb_device *udev,
+ struct lan7x_private *priv,
+ unsigned char *enetaddr)
+{
+ u32 addr_lo = get_unaligned_le32(&enetaddr[0]);
+ u32 addr_hi = (u32)get_unaligned_le16(&enetaddr[4]);
+ int ret;
+
+ /* set hardware address */
+ ret = lan7x_write_reg(udev, RX_ADDRL, addr_lo);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, RX_ADDRH, addr_hi);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, LAN78XX_MAF_LO(0), addr_lo);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, LAN78XX_MAF_HI(0),
+ addr_hi | LAN78XX_MAF_HI_VALID);
+ if (ret)
+ return ret;
+
+ debug("MAC addr %pM written\n", enetaddr);
+ priv->have_hwaddr = 1;
+
+ return 0;
+}
+
+static int lan78xx_set_multicast(struct usb_device *udev)
+{
+ int ret;
+ u32 write_buf;
+
+ /* No multicast in u-boot */
+ write_buf = RFE_CTL_BCAST_EN | RFE_CTL_DA_PERFECT;
+ ret = lan7x_write_reg(udev, LAN78XX_RFE_CTL, write_buf);
+ if (ret)
+ return ret;
+
+ return 0;
+}
+
+/* starts the TX path */
+static void lan78xx_start_tx_path(struct usb_device *udev)
+{
+ u32 reg_val;
+
+ /* Enable Tx at MAC */
+ reg_val = MAC_TX_TXEN;
+ lan7x_write_reg(udev, MAC_TX, reg_val);
+
+ /* Enable Tx at SCSRs */
+ reg_val = FCT_TX_CTL_EN;
+ lan7x_write_reg(udev, LAN78XX_FCT_TX_CTL, reg_val);
+}
+
+/* Starts the Receive path */
+static void lan78xx_start_rx_path(struct usb_device *udev)
+{
+ u32 reg_val;
+
+ /* Enable Rx at MAC */
+ reg_val = LAN7X_MAC_RX_MAX_SIZE_DEFAULT |
+ MAC_RX_FCS_STRIP | MAC_RX_RXEN;
+ lan7x_write_reg(udev, MAC_RX, reg_val);
+
+ /* Enable Rx at SCSRs */
+ reg_val = FCT_RX_CTL_EN;
+ lan7x_write_reg(udev, LAN78XX_FCT_RX_CTL, reg_val);
+}
+
+static int lan78xx_basic_reset(struct usb_device *udev,
+ struct ueth_data *dev,
+ struct lan7x_private *priv)
+{
+ int ret;
+ u32 write_buf;
+
+ ret = lan7x_basic_reset(udev, dev);
+ if (ret)
+ return ret;
+
+ /* Keep the chip ID */
+ ret = lan7x_read_reg(udev, ID_REV, &priv->chipid);
+ if (ret)
+ return ret;
+ debug("LAN78xx ID_REV = 0x%08x\n", priv->chipid);
+
+ priv->chipid = (priv->chipid & ID_REV_CHIP_ID_MASK) >> 16;
+
+ /* Respond to the IN token with a NAK */
+ ret = lan7x_read_reg(udev, LAN78XX_USB_CFG0, &write_buf);
+ if (ret)
+ return ret;
+ write_buf |= LAN78XX_USB_CFG0_BIR;
+ ret = lan7x_write_reg(udev, LAN78XX_USB_CFG0, write_buf);
+
+ return ret;
+}
+
+static int lan78xx_init_common(struct usb_device *udev,
+ struct ueth_data *dev,
+ struct lan7x_private *priv,
+ unsigned char *enetaddr)
+{
+ int ret;
+ u32 write_buf;
+
+ /* Reset and read Mac addr were done in get_info() or in probe() */
+
+#ifndef CONFIG_DM_ETH
+ if (!priv->have_hwaddr && is_valid_ethaddr(enetaddr)) {
+ priv->have_hwaddr = 1;
+ debug("LAN78xx: MAC address found and set %pM\n", enetaddr);
+ }
+#endif
+ if (!priv->have_hwaddr) {
+ printf("Error: LAN78xx: No MAC address set - set usbethaddr\n");
+ return -EADDRNOTAVAIL;
+ }
+ ret = lan78xx_write_hwaddr_common(udev, priv, enetaddr);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, LAN78XX_BURST_CAP, 0);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, LAN78XX_BULK_IN_DLY, DEFAULT_BULK_IN_DELAY);
+ if (ret)
+ return ret;
+
+ ret = lan7x_write_reg(udev, INT_STS, 0xFFFFFFFF);
+ if (ret)
+ return ret;
+
+ /* set FIFO sizes */
+ write_buf = (MAX_RX_FIFO_SIZE - 512) / 512;
+ ret = lan7x_write_reg(udev, LAN78XX_FCT_RX_FIFO_END, write_buf);
+ if (ret)
+ return ret;
+
+ write_buf = (MAX_TX_FIFO_SIZE - 512) / 512;
+ ret = lan7x_write_reg(udev, LAN78XX_FCT_TX_FIFO_END, write_buf);
+ if (ret)
+ return ret;
+
+ /* Init Tx */
+ ret = lan7x_write_reg(udev, FLOW, 0);
+ if (ret)
+ return ret;
+
+ /* Init Rx. Set Vlan, keep defult for VLAN on 78xx */
+ ret = lan78xx_set_multicast(udev);
+ if (ret < 0)
+ return ret;
+
+ /* Init PHY, autonego, and link */
+ ret = lan7x_phy_initialize(udev, dev);
+ if (ret < 0)
+ return ret;
+
+ /*
+ * MAC_CR has to be set after PHY init.
+ * MAC will auto detect the PHY speed.
+ */
+ ret = lan7x_read_reg(udev, MAC_CR, &write_buf);
+ if (ret)
+ return ret;
+ write_buf |= MAC_CR_AUTO_DUPLEX | MAC_CR_AUTO_SPEED | MAC_CR_ADP;
+ ret = lan7x_write_reg(udev, MAC_CR, write_buf);
+ if (ret)
+ return ret;
+
+ lan78xx_start_tx_path(udev);
+ lan78xx_start_rx_path(udev);
+
+ ret = lan78xx_update_flowcontrol(udev, dev);
+
+ return ret;
+}
+
+#ifndef CONFIG_DM_ETH
+/*
+ * lan78xx callbacks
+ */
+static int lan78xx_init(struct eth_device *eth, bd_t *bd)
+{
+ struct ueth_data *dev = (struct ueth_data *)eth->priv;
+ struct usb_device *udev = dev->pusb_dev;
+ struct lan7x_private *priv = (struct lan7x_private *)dev->dev_priv;
+
+ return lan78xx_init_common(udev, dev, priv, eth->enetaddr);
+}
+
+static int lan78xx_write_hwaddr(struct eth_device *eth)
+{
+ struct ueth_data *dev = eth->priv;
+ struct usb_device *udev = dev->pusb_dev;
+ struct lan7x_private *priv = dev->dev_priv;
+
+ return lan78xx_write_hwaddr_common(udev, priv, eth->enetaddr);
+}
+
+/*
+ * Microchip probing functions
+ */
+void lan78xx_eth_before_probe(void)
+{
+ curr_eth_dev = 0;
+}
+
+static const struct lan7x_dongle lan78xx_dongles[] = {
+ {0x0424, 0x7800}, /* LAN7800 USB Ethernet */
+ {0x0424, 0x7850}, /* LAN7850 USB Ethernet */
+ {0x0000, 0x0000} /* END - Do not remove */
+};
+
+/* Probe to see if a new device is actually an Microchip device */
+int lan78xx_eth_probe(struct usb_device *dev, unsigned int ifnum,
+ struct ueth_data *ss)
+{
+ int i;
+
+ /* let's examine the device now */
+
+ for (i = 0; lan78xx_dongles[i].vendor != 0; i++) {
+ if (dev->descriptor.idVendor == lan78xx_dongles[i].vendor &&
+ dev->descriptor.idProduct == lan78xx_dongles[i].product)
+ /* Found a supported dongle */
+ break;
+ }
+ if (lan78xx_dongles[i].vendor == 0)
+ return 0;
+
+ /* At this point, we know we've got a live one */
+ debug("\n\nUSB Ethernet device LAN78xx detected\n");
+
+ /*
+ * Note that this function needs to return 1
+ * for success
+ */
+ return lan7x_eth_probe(dev, ifnum, ss);
+}
+
+int lan78xx_eth_get_info(struct usb_device *dev, struct ueth_data *ss,
+ struct eth_device *eth)
+{
+ struct lan7x_private *priv = ss->dev_priv;
+
+ printf("LAN78xx name: %s%d\n", LAN78XX_BASE_NAME, curr_eth_dev);
+
+ if (!eth) {
+ debug("%s: missing parameter.\n", __func__);
+ return 0;
+ }
+ sprintf(eth->name, "%s%d", LAN78XX_BASE_NAME, curr_eth_dev++);
+ eth->init = lan78xx_init;
+ eth->send = lan7x_send;
+ eth->recv = lan7x_recv;
+ eth->halt = lan7x_halt;
+ eth->write_hwaddr = lan78xx_write_hwaddr;
+ eth->priv = ss;
+
+ /* Do a reset in order to get the MAC address from HW */
+ if (lan78xx_basic_reset(dev, ss, priv))
+ return 0;
+
+ /* Get the MAC address */
+ /*
+ * We must set the eth->enetaddr from HW because the upper layer
+ * will force to use the environmental var (usbethaddr) or random if
+ * there is no valid MAC address in eth->enetaddr.
+ */
+ lan78xx_read_mac(eth->enetaddr, dev, priv);
+ /* Do not return 0 for not finding MAC addr in HW */
+
+ return 1;
+}
+#endif /* !CONFIG_DM_ETH */
+
+#ifdef CONFIG_DM_ETH
+static int lan78xx_eth_start(struct udevice *dev)
+{
+ struct usb_device *udev = dev_get_parent_priv(dev);
+ struct lan7x_private *priv = dev_get_priv(dev);
+ struct eth_pdata *pdata = dev_get_platdata(dev);
+
+ /* Driver-model Ethernet ensures we have this */
+ priv->have_hwaddr = 1;
+
+ return lan78xx_init_common(udev, &priv->ueth, priv, pdata->enetaddr);
+}
+
+int lan78xx_write_hwaddr(struct udevice *dev)
+{
+ struct usb_device *udev = dev_get_parent_priv(dev);
+ struct eth_pdata *pdata = dev_get_platdata(dev);
+ struct lan7x_private *priv = dev_get_priv(dev);
+
+ return lan78xx_write_hwaddr_common(udev, priv, pdata->enetaddr);
+}
+
+int lan78xx_read_rom_hwaddr(struct udevice *dev)
+{
+ struct usb_device *udev = dev_get_parent_priv(dev);
+ struct eth_pdata *pdata = dev_get_platdata(dev);
+ struct lan7x_private *priv = dev_get_priv(dev);
+ int ret;
+
+ ret = lan78xx_read_mac(pdata->enetaddr, udev, priv);
+ if (ret)
+ memset(pdata->enetaddr, 0, 6);
+
+ return 0;
+}
+
+static int lan78xx_eth_probe(struct udevice *dev)
+{
+ struct usb_device *udev = dev_get_parent_priv(dev);
+ struct lan7x_private *priv = dev_get_priv(dev);
+ struct ueth_data *ueth = &priv->ueth;
+ struct eth_pdata *pdata = dev_get_platdata(dev);
+
+ /* Do a reset in order to get the MAC address from HW */
+ if (lan78xx_basic_reset(udev, ueth, priv))
+ return 0;
+
+ /* Get the MAC address */
+ /*
+ * We must set the eth->enetaddr from HW because the upper layer
+ * will force to use the environmental var (usbethaddr) or random if
+ * there is no valid MAC address in eth->enetaddr.
+ */
+ lan78xx_read_mac(pdata->enetaddr, udev, priv);
+ /* Do not return 0 for not finding MAC addr in HW */
+
+ return usb_ether_register(dev, ueth, RX_URB_SIZE);
+}
+
+static const struct eth_ops lan78xx_eth_ops = {
+ .start = lan78xx_eth_start,
+ .send = lan7x_eth_send,
+ .recv = lan7x_eth_recv,
+ .free_pkt = lan7x_free_pkt,
+ .stop = lan7x_eth_stop,
+ .write_hwaddr = lan78xx_write_hwaddr,
+ .read_rom_hwaddr = lan78xx_read_rom_hwaddr,
+};
+
+U_BOOT_DRIVER(lan78xx_eth) = {
+ .name = "lan78xx_eth",
+ .id = UCLASS_ETH,
+ .probe = lan78xx_eth_probe,
+ .ops = &lan78xx_eth_ops,
+ .priv_auto_alloc_size = sizeof(struct lan7x_private),
+ .platdata_auto_alloc_size = sizeof(struct eth_pdata),
+};
+
+static const struct usb_device_id lan78xx_eth_id_table[] = {
+ { USB_DEVICE(0x0424, 0x7800) }, /* LAN7800 USB Ethernet */
+ { USB_DEVICE(0x0424, 0x7850) }, /* LAN7850 USB Ethernet */
+ { } /* Terminating entry */
+};
+
+U_BOOT_USB_DEVICE(lan78xx_eth, lan78xx_eth_id_table);
+#endif
diff --git a/drivers/usb/eth/lan7x.c b/drivers/usb/eth/lan7x.c
new file mode 100644
index 0000000..baa778f
--- /dev/null
+++ b/drivers/usb/eth/lan7x.c
@@ -0,0 +1,680 @@
+/*
+ * Copyright (c) 2017 Microchip Technology Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#include <dm.h>
+#include <malloc.h>
+#include <memalign.h>
+#include <usb.h>
+#include <linux/mii.h>
+#include <linux/ethtool.h>
+#include "usb_ether.h"
+#include "lan7x.h"
+
+/*
+ * Lan7x infrastructure commands
+ */
+int lan7x_write_reg(struct usb_device *udev, u32 index, u32 data)
+{
+ int len;
+ ALLOC_CACHE_ALIGN_BUFFER(u32, tmpbuf, 1);
+
+ cpu_to_le32s(&data);
+ tmpbuf[0] = data;
+
+ len = usb_control_msg(udev, usb_sndctrlpipe(udev, 0),
+ USB_VENDOR_REQUEST_WRITE_REGISTER,
+ USB_DIR_OUT | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
+ 0, index, tmpbuf, sizeof(data),
+ USB_CTRL_SET_TIMEOUT_MS);
+ if (len != sizeof(data)) {
+ debug("%s failed: index=%d, data=%d, len=%d",
+ __func__, index, data, len);
+ return -EIO;
+ }
+ return 0;
+}
+
+int lan7x_read_reg(struct usb_device *udev, u32 index, u32 *data)
+{
+ int len;
+ ALLOC_CACHE_ALIGN_BUFFER(u32, tmpbuf, 1);
+
+ len = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0),
+ USB_VENDOR_REQUEST_READ_REGISTER,
+ USB_DIR_IN | USB_TYPE_VENDOR | USB_RECIP_DEVICE,
+ 0, index, tmpbuf, sizeof(*data),
+ USB_CTRL_GET_TIMEOUT_MS);
+ *data = tmpbuf[0];
+ if (len != sizeof(*data)) {
+ debug("%s failed: index=%d, len=%d", __func__, index, len);
+ return -EIO;
+ }
+
+ le32_to_cpus(data);
+ return 0;
+}
+
+/* Loop until the read is completed with timeout */
+int lan7x_wait_for_bit(struct usb_device *udev,
+ const char *prefix, const u32 index,
+ const u32 mask, const bool set,
+ unsigned int timeout_ms)
+{
+ u32 val;
+
+ while (--timeout_ms) {
+ lan7x_read_reg(udev, index, &val);
+
+ if (!set)
+ val = ~val;
+
+ if ((val & mask) == mask)
+ return 0;
+
+ mdelay(1);
+ }
+
+ debug("%s: Timeout (reg=0x%x mask=%08x wait_set=%i)\n",
+ prefix, index, mask, set);
+
+ return -ETIMEDOUT;
+}
+
+static int lan7x_phy_wait_not_busy(struct usb_device *udev)
+{
+ return lan7x_wait_for_bit(udev, __func__,
+ MII_ACC, MII_ACC_MII_BUSY,
+ false, 100);
+}
+
+int lan7x_mdio_read(struct usb_device *udev, int phy_id, int idx)
+{
+ u32 val, addr;
+
+ /* confirm MII not busy */
+ if (lan7x_phy_wait_not_busy(udev)) {
+ debug("MII is busy in %s\n", __func__);
+ return -ETIMEDOUT;
+ }
+
+ /* set the address, index & direction (read from PHY) */
+ addr = (phy_id << 11) | (idx << 6) |
+ MII_ACC_MII_READ | MII_ACC_MII_BUSY;
+ lan7x_write_reg(udev, MII_ACC, addr);
+
+ if (lan7x_phy_wait_not_busy(udev)) {
+ debug("Timed out reading MII reg %02X\n", idx);
+ return -ETIMEDOUT;
+ }
+
+ lan7x_read_reg(udev, MII_DATA, &val);
+
+ return (u16) (val & 0xFFFF);
+}
+
+int lan7x_mdio_wait_for_bit(struct usb_device *udev,
+ const char *prefix,
+ int phy_id, const u32 index,
+ const u32 mask, const bool set,
+ unsigned int timeout_ms)
+{
+ u32 val;
+
+ while (--timeout_ms) {
+ val = lan7x_mdio_read(udev, phy_id, index);
+
+ if (!set)
+ val = ~val;
+
+ if ((val & mask) == mask)
+ return 0;
+
+ mdelay(1);
+ }
+
+ debug("%s: Timeout (reg=0x%x mask=%08x wait_set=%i)\n",
+ prefix, index, mask, set);
+
+ return -ETIMEDOUT;
+}
+
+void lan7x_mdio_write(struct usb_device *udev, int phy_id, int idx, int regval)
+{
+ u32 val, addr;
+
+ /* confirm MII not busy */
+ if (lan7x_phy_wait_not_busy(udev)) {
+ debug("MII is busy in %s\n", __func__);
+ return;
+ }
+
+ val = regval;
+ lan7x_write_reg(udev, MII_DATA, val);
+
+ /* set the address, index & direction (write to PHY) */
+ addr = (phy_id << 11) | (idx << 6) |
+ MII_ACC_MII_WRITE | MII_ACC_MII_BUSY;
+ lan7x_write_reg(udev, MII_ACC, addr);
+
+ if (lan7x_phy_wait_not_busy(udev))
+ debug("Timed out writing MII reg %02X\n", idx);
+}
+
+static int lan7x_eeprom_confirm_not_busy(struct usb_device *udev)
+{
+ return lan7x_wait_for_bit(udev, __func__,
+ E2P_CMD, E2P_CMD_EPC_BUSY,
+ false, 100);
+}
+
+static int lan7x_wait_eeprom(struct usb_device *udev)
+{
+ return lan7x_wait_for_bit(udev, __func__,
+ E2P_CMD,
+ (E2P_CMD_EPC_BUSY | E2P_CMD_EPC_TIMEOUT),
+ false, 100);
+}
+
+static int lan7x_read_eeprom(struct usb_device *udev,
+ u32 offset, u32 length, u8 *data)
+{
+ u32 val;
+ int i, ret;
+
+ ret = lan7x_eeprom_confirm_not_busy(udev);
+ if (ret)
+ return ret;
+
+ for (i = 0; i < length; i++) {
+ val = E2P_CMD_EPC_BUSY | E2P_CMD_EPC_CMD_READ |
+ (offset & E2P_CMD_EPC_ADDR_MASK);
+ lan7x_write_reg(udev, E2P_CMD, val);
+
+ ret = lan7x_wait_eeprom(udev);
+ if (ret)
+ return ret;
+
+ lan7x_read_reg(udev, E2P_DATA, &val);
+ data[i] = val & 0xFF;
+ offset++;
+ }
+
+ return ret;
+}
+
+/*
+ * mii_nway_restart - restart NWay (autonegotiation) for this interface
+ *
+ * Returns 0 on success, negative on error.
+ */
+static int mii_nway_restart(struct usb_device *udev, struct ueth_data *dev)
+{
+ int bmcr;
+ int r = -1;
+
+ /* if autoneg is off, it's an error */
+ bmcr = lan7x_mdio_read(udev, dev->phy_id, MII_BMCR);
+
+ if (bmcr & BMCR_ANENABLE) {
+ bmcr = BMCR_ANENABLE | BMCR_ANRESTART;
+ lan7x_mdio_write(udev, dev->phy_id, MII_BMCR, bmcr);
+ r = 0;
+ } else {
+ debug("ERROR! phy autoneg is off. BMCR = 0x%04x\n", bmcr);
+ }
+ return r;
+}
+
+int lan7x_phy_initialize(struct usb_device *udev,
+ struct ueth_data *dev)
+{
+ int r, link_detected;
+
+ lan7x_mdio_write(udev, dev->phy_id, MII_BMCR, BMCR_RESET);
+ r = lan7x_mdio_wait_for_bit(udev, "BMCR_RESET",
+ dev->phy_id, MII_BMCR, BMCR_RESET,
+ false, 1000);
+
+ lan7x_mdio_write(udev, dev->phy_id, MII_ADVERTISE,
+ ADVERTISE_ALL | ADVERTISE_CSMA |
+ ADVERTISE_PAUSE_CAP | ADVERTISE_PAUSE_ASYM);
+
+ lan7x_mdio_write(udev, dev->phy_id, MII_CTRL1000,
+ ADVERTISE_1000FULL);
+
+ r = mii_nway_restart(udev, dev);
+ r = lan7x_mdio_wait_for_bit(udev, "BMSR_ANEGCOMPLETE",
+ dev->phy_id, MII_BMSR, BMSR_ANEGCOMPLETE,
+ true, PHY_CONNECT_TIMEOUT_MS);
+
+ if (r == 0) {
+ debug("phy initialised succesfully\n");
+ } else {
+ debug("phy initialised failed id=%d\n", dev->phy_id);
+ return r;
+ }
+
+ printf("LAN7x: Waiting for Ethernet connection... ");
+ r = lan7x_mdio_wait_for_bit(udev, "BMSR_LSTATUS",
+ dev->phy_id, MII_BMSR, BMSR_LSTATUS,
+ true, PHY_CONNECT_TIMEOUT_MS);
+
+ if (r < 0) {
+ printf("unable to connect.\n");
+ return -EIO;
+ }
+ printf("done.\n");
+
+ link_detected = lan7x_mdio_read(udev, dev->phy_id, MII_BMSR);
+ debug("MII_BMSR=0x%04x\n", link_detected);
+
+ return 0;
+}
+
+static int lan7x_mii_get_an(uint32_t advertising_reg)
+{
+ int advertising = 0;
+
+ if (advertising_reg & LPA_LPACK)
+ advertising |= ADVERTISED_Autoneg;
+ if (advertising_reg & ADVERTISE_10HALF)
+ advertising |= ADVERTISED_10baseT_Half;
+ if (advertising_reg & ADVERTISE_10FULL)
+ advertising |= ADVERTISED_10baseT_Full;
+ if (advertising_reg & ADVERTISE_100HALF)
+ advertising |= ADVERTISED_100baseT_Half;
+ if (advertising_reg & ADVERTISE_100FULL)
+ advertising |= ADVERTISED_100baseT_Full;
+
+ return advertising;
+}
+
+int lan7x_update_flowcontrol(struct usb_device *udev,
+ struct ueth_data *dev,
+ uint32_t *flow, uint32_t *fct_flow)
+{
+ uint32_t lcladv, rmtadv, ctrl1000, stat1000;
+ uint32_t advertising = 0, lp_advertising = 0, nego = 0;
+ uint32_t duplex = 0;
+ u8 cap = 0;
+
+ lcladv = lan7x_mdio_read(udev, dev->phy_id, MII_ADVERTISE);
+ advertising = lan7x_mii_get_an(lcladv);
+
+ rmtadv = lan7x_mdio_read(udev, dev->phy_id, MII_LPA);
+ lp_advertising = lan7x_mii_get_an(rmtadv);
+
+ ctrl1000 = lan7x_mdio_read(udev, dev->phy_id, MII_CTRL1000);
+ stat1000 = lan7x_mdio_read(udev, dev->phy_id, MII_STAT1000);
+
+ if (ctrl1000 & ADVERTISE_1000HALF)
+ advertising |= ADVERTISED_1000baseT_Half;
+
+ if (ctrl1000 & ADVERTISE_1000FULL)
+ advertising |= ADVERTISED_1000baseT_Full;
+
+ if (stat1000 & LPA_1000HALF)
+ lp_advertising |= ADVERTISED_1000baseT_Half;
+
+ if (stat1000 & LPA_1000FULL)
+ lp_advertising |= ADVERTISED_1000baseT_Full;
+
+ nego = advertising & lp_advertising;
+
+ debug("LAN7x linked at ");
+
+ if (nego & (ADVERTISED_1000baseT_Full | ADVERTISED_1000baseT_Half)) {
+ debug("1000 ");
+ duplex = !!(nego & ADVERTISED_1000baseT_Full);
+
+ } else if (nego & (ADVERTISED_100baseT_Full |
+ ADVERTISED_100baseT_Half)) {
+ debug("100 ");
+ duplex = !!(nego & ADVERTISED_100baseT_Full);
+ } else {
+ debug("10 ");
+ duplex = !!(nego & ADVERTISED_10baseT_Full);
+ }
+
+ if (duplex == DUPLEX_FULL)
+ debug("full dup ");
+ else
+ debug("half dup ");
+
+ if (duplex == DUPLEX_FULL) {
+ if (lcladv & rmtadv & ADVERTISE_PAUSE_CAP) {
+ cap = FLOW_CTRL_TX | FLOW_CTRL_RX;
+ } else if (lcladv & rmtadv & ADVERTISE_PAUSE_ASYM) {
+ if (lcladv & ADVERTISE_PAUSE_CAP)
+ cap = FLOW_CTRL_RX;
+ else if (rmtadv & LPA_PAUSE_CAP)
+ cap = FLOW_CTRL_TX;
+ }
+ debug("TX Flow ");
+ if (cap & FLOW_CTRL_TX) {
+ *flow = (FLOW_CR_TX_FCEN | 0xFFFF);
+ /* set fct_flow thresholds to 20% and 80% */
+ *fct_flow = (((MAX_RX_FIFO_SIZE * 2) / (10 * 512))
+ & 0x7FUL);
+ *fct_flow <<= 8UL;
+ *fct_flow |= (((MAX_RX_FIFO_SIZE * 8) / (10 * 512))
+ & 0x7FUL);
+ debug("EN ");
+ } else {
+ debug("DIS ");
+ }
+ debug("RX Flow ");
+ if (cap & FLOW_CTRL_RX) {
+ *flow |= FLOW_CR_RX_FCEN;
+ debug("EN");
+ } else {
+ debug("DIS");
+ }
+ }
+ debug("\n");
+ return 0;
+}
+
+int lan7x_read_eeprom_mac(unsigned char *enetaddr, struct usb_device *udev)
+{
+ int ret;
+
+ memset(enetaddr, 0, 6);
+
+ ret = lan7x_read_eeprom(udev, 0, 1, enetaddr);
+
+ if ((ret == 0) && (enetaddr[0] == EEPROM_INDICATOR)) {
+ ret = lan7x_read_eeprom(udev,
+ EEPROM_MAC_OFFSET, ETH_ALEN,
+ enetaddr);
+ if ((ret == 0) && is_valid_ethaddr(enetaddr)) {
+ /* eeprom values are valid so use them */
+ debug("MAC address read from EEPROM %pM\n",
+ enetaddr);
+ return 0;
+ }
+ }
+ debug("MAC address read from EEPROM invalid %pM\n", enetaddr);
+
+ memset(enetaddr, 0, 6);
+ return -1;
+}
+
+int lan7x_pmt_phy_reset(struct usb_device *udev,
+ struct ueth_data *dev)
+{
+ int ret;
+ u32 data;
+
+ ret = lan7x_read_reg(udev, PMT_CTL, &data);
+ ret = lan7x_write_reg(udev, PMT_CTL, data | PMT_CTL_PHY_RST);
+ if (ret)
+ return ret;
+
+ /* for LAN7x, we need to check PMT_CTL_READY asserted */
+ ret = lan7x_wait_for_bit(udev, "PMT_CTL_PHY_RST",
+ PMT_CTL, PMT_CTL_PHY_RST,
+ false, 1000); /* could take over 125mS */
+ if (ret)
+ return ret;
+
+ ret = lan7x_wait_for_bit(udev, "PMT_CTL_READY",
+ PMT_CTL, PMT_CTL_READY,
+ true, 1000);
+ return ret;
+}
+
+int lan7x_basic_reset(struct usb_device *udev,
+ struct ueth_data *dev)
+{
+ int ret;
+
+ dev->phy_id = LAN7X_INTERNAL_PHY_ID; /* fixed phy id */
+
+ ret = lan7x_write_reg(udev, HW_CFG, HW_CFG_LRST);
+ if (ret)
+ return ret;
+
+ ret = lan7x_wait_for_bit(udev, "HW_CFG_LRST",
+ HW_CFG, HW_CFG_LRST,
+ false, 1000);
+ if (ret)
+ return ret;
+
+ ret = lan7x_pmt_phy_reset(udev, dev);
+ if (ret)
+ return ret;
+
+ return 0;
+}
+
+int lan7x_send_common(struct ueth_data *dev, void *packet, int length)
+{
+ int err;
+ int actual_len;
+ u32 tx_cmd_a;
+ u32 tx_cmd_b;
+ ALLOC_CACHE_ALIGN_BUFFER(unsigned char, msg,
+ PKTSIZE + sizeof(tx_cmd_a) + sizeof(tx_cmd_b));
+
+ debug("** %s(), len %d, buf %#x\n", __func__, length,
+ (unsigned int)(ulong) msg);
+ if (length > PKTSIZE)
+ return -ENOSPC;
+
+ /* LAN7x disable all TX offload features for u-boot */
+ tx_cmd_a = (u32) (length & TX_CMD_A_LEN_MASK) | TX_CMD_A_FCS;
+ tx_cmd_b = 0;
+ cpu_to_le32s(&tx_cmd_a);
+ cpu_to_le32s(&tx_cmd_b);
+
+ /* prepend cmd_a and cmd_b */
+ memcpy(msg, &tx_cmd_a, sizeof(tx_cmd_a));
+ memcpy(msg + sizeof(tx_cmd_a), &tx_cmd_b, sizeof(tx_cmd_b));
+ memcpy(msg + sizeof(tx_cmd_a) + sizeof(tx_cmd_b), (void *)packet,
+ length);
+ err = usb_bulk_msg(dev->pusb_dev,
+ usb_sndbulkpipe(dev->pusb_dev, dev->ep_out),
+ (void *)msg,
+ length + sizeof(tx_cmd_a) +
+ sizeof(tx_cmd_b),
+ &actual_len, USB_BULK_SEND_TIMEOUT_MS);
+ debug("Tx: len = %u, actual = %u, err = %d\n",
+ (unsigned int)(length + sizeof(tx_cmd_a) + sizeof(tx_cmd_b)),
+ (unsigned int)actual_len, err);
+
+ return err;
+}
+
+int lan7x_recv_common(struct ueth_data *dev)
+{
+ DEFINE_CACHE_ALIGN_BUFFER(unsigned char, recv_buf, RX_URB_SIZE);
+ unsigned char *buf_ptr;
+ int err;
+ int actual_len = 0;
+ u32 packet_len = 0;
+ u32 rx_cmd_a = 0;
+
+ err = usb_bulk_msg(dev->pusb_dev,
+ usb_rcvbulkpipe(dev->pusb_dev, dev->ep_in),
+ (void *)recv_buf, RX_URB_SIZE, &actual_len,
+ USB_BULK_RECV_TIMEOUT_MS);
+ if (actual_len == 0) {
+ debug("Rx: actual_len = 0\n");
+ return -err;
+ }
+
+ debug("Rx: RX_URB_SIZE = %u, actual = %u, err = %d\n", RX_URB_SIZE,
+ actual_len, err);
+ if (err != 0) {
+ debug("Rx: failed to receive\n");
+ return -err;
+ }
+ if (actual_len > RX_URB_SIZE) {
+ debug("Rx: received too many bytes %d\n", actual_len);
+ return -ENOSPC;
+ }
+
+ buf_ptr = recv_buf;
+
+ /*
+ * No multiple Ethernet Frames per USB Packet (MEF) used
+ * for the U-boot for now.
+ */
+ if (actual_len > 0) {
+ if (actual_len < sizeof(rx_cmd_a)) {
+ debug("Rx: incomplete packet length\n");
+ return -EIO;
+ }
+ memcpy(&rx_cmd_a, buf_ptr, sizeof(rx_cmd_a));
+ le32_to_cpus(&rx_cmd_a);
+ if (rx_cmd_a & RX_CMD_A_RXE) {
+ debug("Rx: Error header=%#x", rx_cmd_a);
+ return -EIO;
+ }
+ packet_len = (u16) (rx_cmd_a & RX_CMD_A_LEN_MASK);
+
+ if (packet_len > actual_len - sizeof(packet_len)) {
+ debug("Rx: too large packet: %d\n", packet_len);
+ return -EIO;
+ }
+
+ /*
+ * For LAN7x, the length in command A does not
+ * include command A, B, and C length.
+ * So use it as is.
+ */
+
+ debug("Rx: cmd_a 0x%08X packet_len %d\n", rx_cmd_a, packet_len);
+
+ /* Notify net stack */
+ net_process_received_packet(buf_ptr + 10, packet_len);
+ }
+
+ return err;
+}
+
+int lan7x_eth_probe(struct usb_device *dev, unsigned int ifnum,
+ struct ueth_data *ss)
+{
+ struct usb_interface *iface;
+ struct usb_interface_descriptor *iface_desc;
+ int i;
+
+ iface = &dev->config.if_desc[ifnum];
+ iface_desc = &dev->config.if_desc[ifnum].desc;
+
+ memset(ss, '\0', sizeof(struct ueth_data));
+
+ /* Initialize the ueth_data structure with some useful info */
+ ss->ifnum = ifnum;
+ ss->pusb_dev = dev;
+ ss->subclass = iface_desc->bInterfaceSubClass;
+ ss->protocol = iface_desc->bInterfaceProtocol;
+
+ /*
+ * We are expecting a minimum of 3 endpoints
+ * - in, out (bulk), and int.
+ * We will ignore any others.
+ */
+ for (i = 0; i < iface_desc->bNumEndpoints; i++) {
+ /* is it an BULK endpoint? */
+ if ((iface->ep_desc[i].bmAttributes &
+ USB_ENDPOINT_XFERTYPE_MASK) == USB_ENDPOINT_XFER_BULK) {
+ if (iface->ep_desc[i].bEndpointAddress & USB_DIR_IN)
+ ss->ep_in =
+ iface->ep_desc[i].bEndpointAddress &
+ USB_ENDPOINT_NUMBER_MASK;
+ else
+ ss->ep_out =
+ iface->ep_desc[i].bEndpointAddress &
+ USB_ENDPOINT_NUMBER_MASK;
+ }
+
+ /* is it an interrupt endpoint? */
+ if ((iface->ep_desc[i].bmAttributes &
+ USB_ENDPOINT_XFERTYPE_MASK) == USB_ENDPOINT_XFER_INT) {
+ ss->ep_int = iface->ep_desc[i].bEndpointAddress &
+ USB_ENDPOINT_NUMBER_MASK;
+ ss->irqinterval = iface->ep_desc[i].bInterval;
+ }
+ }
+ debug("Endpoints In %d Out %d Int %d\n",
+ ss->ep_in, ss->ep_out, ss->ep_int);
+
+ /* Do some basic sanity checks, and bail if we find a problem */
+ if (usb_set_interface(dev, iface_desc->bInterfaceNumber, 0) ||
+ !ss->ep_in || !ss->ep_out || !ss->ep_int) {
+ debug("Problems with device\n");
+ return 0;
+ }
+ dev->privptr = (void *)ss;
+
+#ifndef CONFIG_DM_ETH
+ /* alloc driver private */
+ ss->dev_priv = calloc(1, sizeof(struct lan7x_private));
+ if (!ss->dev_priv)
+ return 0;
+#endif
+
+ return 1;
+}
+
+#ifndef CONFIG_DM_ETH
+/*
+ * lan7x callbacks
+ */
+int lan7x_send(struct eth_device *eth, void *packet, int length)
+{
+ struct ueth_data *dev = (struct ueth_data *)eth->priv;
+
+ return lan7x_send_common(dev, packet, length);
+}
+
+int lan7x_recv(struct eth_device *eth)
+{
+ struct ueth_data *dev = (struct ueth_data *)eth->priv;
+
+ return lan7x_recv_common(dev);
+}
+
+void lan7x_halt(struct eth_device *eth)
+{
+ debug("** %s()\n", __func__);
+}
+#endif /* !CONFIG_DM_ETH */
+
+#ifdef CONFIG_DM_ETH
+void lan7x_eth_stop(struct udevice *dev)
+{
+ debug("** %s()\n", __func__);
+}
+
+int lan7x_eth_send(struct udevice *dev, void *packet, int length)
+{
+ struct lan7x_private *priv = dev_get_priv(dev);
+
+ return lan7x_send_common(&priv->ueth, packet, length);
+}
+
+int lan7x_eth_recv(struct udevice *dev, int flags, uchar **packetp)
+{
+ struct lan7x_private *priv = dev_get_priv(dev);
+
+ return lan7x_recv_common(&priv->ueth);
+}
+
+int lan7x_free_pkt(struct udevice *dev, uchar *packet, int packet_len)
+{
+ struct lan7x_private *priv = dev_get_priv(dev);
+
+ packet_len = ALIGN(packet_len, 4);
+ usb_ether_advance_rxbuf(&priv->ueth, sizeof(u32) + packet_len);
+
+ return 0;
+}
+#endif /* CONFIG_DM_ETH */
+
diff --git a/drivers/usb/eth/lan7x.h b/drivers/usb/eth/lan7x.h
new file mode 100644
index 0000000..b5c1b39
--- /dev/null
+++ b/drivers/usb/eth/lan7x.h
@@ -0,0 +1,189 @@
+/*
+ * Copyright (c) 2017 Microchip Technology Inc. All rights reserved.
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+
+/* USB Vendor Requests */
+#define USB_VENDOR_REQUEST_WRITE_REGISTER 0xA0
+#define USB_VENDOR_REQUEST_READ_REGISTER 0xA1
+#define USB_VENDOR_REQUEST_GET_STATS 0xA2
+
+/* Tx Command A */
+#define TX_CMD_A_FCS BIT(22)
+#define TX_CMD_A_LEN_MASK 0x000FFFFF
+
+/* Rx Command A */
+#define RX_CMD_A_RXE BIT(18)
+#define RX_CMD_A_LEN_MASK 0x00003FFF
+
+/* SCSRs */
+#define ID_REV 0x00
+#define ID_REV_CHIP_ID_MASK 0xFFFF0000
+#define ID_REV_CHIP_ID_7500 0x7500
+#define ID_REV_CHIP_ID_7800 0x7800
+#define ID_REV_CHIP_ID_7850 0x7850
+
+#define INT_STS 0x0C
+
+#define HW_CFG 0x010
+#define HW_CFG_LRST BIT(1)
+
+#define PMT_CTL 0x014
+#define PMT_CTL_PHY_PWRUP BIT(10)
+#define PMT_CTL_READY BIT(7)
+#define PMT_CTL_PHY_RST BIT(4)
+
+#define E2P_CMD 0x040
+#define E2P_CMD_EPC_BUSY BIT(31)
+#define E2P_CMD_EPC_CMD_READ 0x00000000
+#define E2P_CMD_EPC_TIMEOUT BIT(10)
+#define E2P_CMD_EPC_ADDR_MASK 0x000001FF
+
+#define E2P_DATA 0x044
+
+#define RFE_CTL_BCAST_EN BIT(10)
+#define RFE_CTL_DA_PERFECT BIT(1)
+
+#define FCT_RX_CTL_EN BIT(31)
+
+#define FCT_TX_CTL_EN BIT(31)
+
+#define MAC_CR 0x100
+#define MAC_CR_ADP BIT(13)
+#define MAC_CR_AUTO_DUPLEX BIT(12)
+#define MAC_CR_AUTO_SPEED BIT(11)
+
+#define MAC_RX 0x104
+#define MAC_RX_FCS_STRIP BIT(4)
+#define MAC_RX_RXEN BIT(0)
+
+#define MAC_TX 0x108
+#define MAC_TX_TXEN BIT(0)
+
+#define FLOW 0x10C
+#define FLOW_CR_TX_FCEN BIT(30)
+#define FLOW_CR_RX_FCEN BIT(29)
+
+#define RX_ADDRH 0x118
+#define RX_ADDRL 0x11C
+
+#define MII_ACC 0x120
+#define MII_ACC_MII_READ 0x00000000
+#define MII_ACC_MII_WRITE 0x00000002
+#define MII_ACC_MII_BUSY BIT(0)
+
+#define MII_DATA 0x124
+
+#define SS_USB_PKT_SIZE 1024
+#define HS_USB_PKT_SIZE 512
+#define FS_USB_PKT_SIZE 64
+
+#define MAX_RX_FIFO_SIZE (12 * 1024)
+#define MAX_TX_FIFO_SIZE (12 * 1024)
+#define DEFAULT_BULK_IN_DELAY 0x0800
+
+#define EEPROM_INDICATOR 0xA5
+#define EEPROM_MAC_OFFSET 0x01
+
+/* Some extra defines */
+#define LAN7X_INTERNAL_PHY_ID 1
+
+#define LAN7X_MAC_RX_MAX_SIZE(mtu) \
+ ((mtu) << 16) /**< Max frame size */
+#define LAN7X_MAC_RX_MAX_SIZE_DEFAULT \
+ LAN7X_MAC_RX_MAX_SIZE(ETH_FRAME_LEN + 4 /* VLAN */ + 4 /* CRC */)
+
+/* Timeouts */
+#define USB_CTRL_SET_TIMEOUT_MS 5000
+#define USB_CTRL_GET_TIMEOUT_MS 5000
+#define USB_BULK_SEND_TIMEOUT_MS 5000
+#define USB_BULK_RECV_TIMEOUT_MS 5000
+#define TIMEOUT_RESOLUTION_MS 50
+#define PHY_CONNECT_TIMEOUT_MS 5000
+
+#define RX_URB_SIZE 2048
+
+/* driver private */
+struct lan7x_private {
+#ifdef CONFIG_DM_ETH
+ struct ueth_data ueth;
+#endif
+ int have_hwaddr; /* 1 if we have a hardware MAC address */
+ u32 chipid; /* Chip or device ID */
+};
+
+#ifndef CONFIG_DM_ETH
+struct lan7x_dongle {
+ unsigned short vendor;
+ unsigned short product;
+};
+#endif
+
+/*
+ * Lan7x infrastructure commands
+ */
+int lan7x_write_reg(struct usb_device *udev, u32 index, u32 data);
+
+int lan7x_read_reg(struct usb_device *udev, u32 index, u32 *data);
+
+int lan7x_wait_for_bit(struct usb_device *udev,
+ const char *prefix, const u32 index,
+ const u32 mask, const bool set,
+ const unsigned int timeout_ms);
+
+int lan7x_mdio_read(struct usb_device *udev, int phy_id, int idx);
+
+int lan7x_mdio_wait_for_bit(struct usb_device *udev,
+ const char *prefix,
+ int phy_id, const u32 index,
+ const u32 mask, const bool set,
+ const unsigned int timeout_ms);
+
+void lan7x_mdio_write(struct usb_device *udev, int phy_id, int idx,
+ int regval);
+
+int lan7x_pmt_phy_reset(struct usb_device *udev,
+ struct ueth_data *dev);
+
+int lan7x_phy_initialize(struct usb_device *udev,
+ struct ueth_data *dev);
+
+int lan7x_update_flowcontrol(struct usb_device *udev,
+ struct ueth_data *dev,
+ uint32_t *flow, uint32_t *fct_flow);
+
+int lan7x_read_eeprom_mac(unsigned char *enetaddr, struct usb_device *udev);
+
+int lan7x_basic_reset(struct usb_device *udev,
+ struct ueth_data *dev);
+
+int lan7x_send_common(struct ueth_data *dev, void *packet, int length);
+
+int lan7x_recv_common(struct ueth_data *dev);
+
+int lan7x_eth_probe(struct usb_device *dev, unsigned int ifnum,
+ struct ueth_data *ss);
+
+#ifndef CONFIG_DM_ETH
+/*
+ * lan7x callbacks
+ */
+int lan7x_send(struct eth_device *eth, void *packet, int length);
+
+int lan7x_recv(struct eth_device *eth);
+
+void lan7x_halt(struct eth_device *eth);
+#endif /* !CONFIG_DM_ETH */
+
+#ifdef CONFIG_DM_ETH
+void lan7x_eth_stop(struct udevice *dev);
+
+int lan7x_eth_send(struct udevice *dev, void *packet, int length);
+
+int lan7x_eth_recv(struct udevice *dev, int flags, uchar **packetp);
+
+int lan7x_free_pkt(struct udevice *dev, uchar *packet, int packet_len);
+#endif /* CONFIG_DM_ETH */
+
diff --git a/drivers/usb/eth/usb_ether.c b/drivers/usb/eth/usb_ether.c
index 36734e2..8f4b5e9 100644
--- a/drivers/usb/eth/usb_ether.c
+++ b/drivers/usb/eth/usb_ether.c
@@ -180,6 +180,20 @@ static const struct usb_eth_prob_dev prob_dev[] = {
.get_info = smsc95xx_eth_get_info,
},
#endif
+#ifdef CONFIG_USB_ETHER_LAN75XX
+ {
+ .before_probe = lan75xx_eth_before_probe,
+ .probe = lan75xx_eth_probe,
+ .get_info = lan75xx_eth_get_info,
+ },
+#endif
+#ifdef CONFIG_USB_ETHER_LAN78XX
+ {
+ .before_probe = lan78xx_eth_before_probe,
+ .probe = lan78xx_eth_probe,
+ .get_info = lan78xx_eth_get_info,
+ },
+#endif
#ifdef CONFIG_USB_ETHER_RTL8152
{
.before_probe = r8152_eth_before_probe,
diff --git a/include/usb_ether.h b/include/usb_ether.h
index 51fce4e..1990b0d 100644
--- a/include/usb_ether.h
+++ b/include/usb_ether.h
@@ -132,6 +132,18 @@ int smsc95xx_eth_probe(struct usb_device *dev, unsigned int ifnum,
int smsc95xx_eth_get_info(struct usb_device *dev, struct ueth_data *ss,
struct eth_device *eth);
+void lan75xx_eth_before_probe(void);
+int lan75xx_eth_probe(struct usb_device *dev, unsigned int ifnum,
+ struct ueth_data *ss);
+int lan75xx_eth_get_info(struct usb_device *dev, struct ueth_data *ss,
+ struct eth_device *eth);
+
+void lan78xx_eth_before_probe(void);
+int lan78xx_eth_probe(struct usb_device *dev, unsigned int ifnum,
+ struct ueth_data *ss);
+int lan78xx_eth_get_info(struct usb_device *dev, struct ueth_data *ss,
+ struct eth_device *eth);
+
void r8152_eth_before_probe(void);
int r8152_eth_probe(struct usb_device *dev, unsigned int ifnum,
struct ueth_data *ss);
--
2.7.4
4
10

30 May '17
From: Siva Durga Prasad Paladugu <siva.durga.paladugu(a)xilinx.com>
Define routines of mmio write and read functionalities
for zynqmp platform.
Also do not call SMC from SPL because SPL is running before ATF in EL3
that's why SMCs can't be called because there is nothing to call.
zynqmp_mmio*() are doing direct read/write accesses and this patch does
the same. PMUFW is up and running at this time and there is a way to talk
to pmufw via IPI but there is no reason to implement IPI stuff in SPL if
we need just simple read for getting clock driver to work.
Also make invoke_smc as global so that it can be reused in
multile places where ever possible.
Signed-off-by: Siva Durga Prasad Paladugu <sivadur(a)xilinx.com>
Signed-off-by: Michal Simek <michal.simek(a)xilinx.com>
---
arch/arm/cpu/armv8/zynqmp/cpu.c | 73 ++++++++++++++++++++++++++++
arch/arm/include/asm/arch-zynqmp/sys_proto.h | 7 +++
2 files changed, 80 insertions(+)
diff --git a/arch/arm/cpu/armv8/zynqmp/cpu.c b/arch/arm/cpu/armv8/zynqmp/cpu.c
index 280e07ad3695..f7ed179c1866 100644
--- a/arch/arm/cpu/armv8/zynqmp/cpu.c
+++ b/arch/arm/cpu/armv8/zynqmp/cpu.c
@@ -98,3 +98,76 @@ unsigned int zynqmp_get_silicon_version(void)
return ZYNQMP_CSU_VERSION_SILICON;
}
+
+#define ZYNQMP_MMIO_READ 0xC2000014
+#define ZYNQMP_MMIO_WRITE 0xC2000013
+
+#ifndef CONFIG_SPL_BUILD
+int invoke_smc(u32 pm_api_id, u32 arg0, u32 arg1, u32 arg2, u32 arg3,
+ u32 *ret_payload)
+{
+ /*
+ * Added SIP service call Function Identifier
+ * Make sure to stay in x0 register
+ */
+ struct pt_regs regs;
+
+ regs.regs[0] = pm_api_id;
+ regs.regs[1] = ((u64)arg1 << 32) | arg0;
+ regs.regs[2] = ((u64)arg3 << 32) | arg2;
+
+ smc_call(®s);
+
+ if (ret_payload != NULL) {
+ ret_payload[0] = (u32)regs.regs[0];
+ ret_payload[1] = upper_32_bits(regs.regs[0]);
+ ret_payload[2] = (u32)regs.regs[1];
+ ret_payload[3] = upper_32_bits(regs.regs[1]);
+ ret_payload[4] = (u32)regs.regs[2];
+ }
+
+ return regs.regs[0];
+}
+
+int zynqmp_mmio_write(const u32 address,
+ const u32 mask,
+ const u32 value)
+{
+ return invoke_smc(ZYNQMP_MMIO_WRITE, address, mask, value, 0, NULL);
+}
+
+int zynqmp_mmio_read(const u32 address, u32 *value)
+{
+ u32 ret_payload[PAYLOAD_ARG_CNT];
+ u32 ret;
+
+ if (!value)
+ return -EINVAL;
+
+ ret = invoke_smc(ZYNQMP_MMIO_READ, address, 0, 0, 0, ret_payload);
+ *value = ret_payload[1];
+
+ return ret;
+}
+#else
+int zynqmp_mmio_write(const u32 address,
+ const u32 mask,
+ const u32 value)
+{
+ u32 data;
+ u32 value_local = value;
+
+ zynqmp_mmio_read(address, &data);
+ data &= ~mask;
+ value_local &= mask;
+ value_local |= data;
+ writel(value_local, (ulong)address);
+ return 0;
+}
+
+int zynqmp_mmio_read(const u32 address, u32 *value)
+{
+ *value = readl((ulong)address);
+ return 0;
+}
+#endif
diff --git a/arch/arm/include/asm/arch-zynqmp/sys_proto.h b/arch/arm/include/asm/arch-zynqmp/sys_proto.h
index 7b11895481be..4ae1bb6eef7c 100644
--- a/arch/arm/include/asm/arch-zynqmp/sys_proto.h
+++ b/arch/arm/include/asm/arch-zynqmp/sys_proto.h
@@ -8,6 +8,8 @@
#ifndef _ASM_ARCH_SYS_PROTO_H
#define _ASM_ARCH_SYS_PROTO_H
+#define PAYLOAD_ARG_CNT 5
+
int zynq_slcr_get_mio_pin_status(const char *periph);
unsigned int zynqmp_get_silicon_version(void);
@@ -16,4 +18,9 @@ void psu_init(void);
void handoff_setup(void);
+int zynqmp_mmio_write(const u32 address, const u32 mask, const u32 value);
+int zynqmp_mmio_read(const u32 address, u32 *value);
+int invoke_smc(u32 pm_api_id, u32 arg0, u32 arg1, u32 arg2, u32 arg3,
+ u32 *ret_payload);
+
#endif /* _ASM_ARCH_SYS_PROTO_H */
--
1.9.1
1
2

30 May '17
When OCM or TCM is protected this mapping still exist and it is causing access
violation.
Signed-off-by: Michal Simek <michal.simek(a)xilinx.com>
---
arch/arm/cpu/armv8/zynqmp/cpu.c | 6 ------
1 file changed, 6 deletions(-)
diff --git a/arch/arm/cpu/armv8/zynqmp/cpu.c b/arch/arm/cpu/armv8/zynqmp/cpu.c
index b0f12955a1ff..280e07ad3695 100644
--- a/arch/arm/cpu/armv8/zynqmp/cpu.c
+++ b/arch/arm/cpu/armv8/zynqmp/cpu.c
@@ -38,12 +38,6 @@ static struct mm_region zynqmp_mem_map[] = {
PTE_BLOCK_NON_SHARE |
PTE_BLOCK_PXN | PTE_BLOCK_UXN
}, {
- .virt = 0xffe00000UL,
- .phys = 0xffe00000UL,
- .size = 0x00200000UL,
- .attrs = PTE_BLOCK_MEMTYPE(MT_NORMAL) |
- PTE_BLOCK_INNER_SHARE
- }, {
.virt = 0x400000000UL,
.phys = 0x400000000UL,
.size = 0x200000000UL,
--
1.9.1
1
1

30 May '17
Silicon v1 didn't support SD boot mode with level shifter.
Because system can't boot any error message is not shown
that's why comment is just a record if someone tries to debug it.
Signed-off-by: Michal Simek <michal.simek(a)xilinx.com>
---
arch/arm/cpu/armv8/zynqmp/spl.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/arch/arm/cpu/armv8/zynqmp/spl.c b/arch/arm/cpu/armv8/zynqmp/spl.c
index e5a413954a5b..779497ca6d0b 100644
--- a/arch/arm/cpu/armv8/zynqmp/spl.c
+++ b/arch/arm/cpu/armv8/zynqmp/spl.c
@@ -84,7 +84,7 @@ u32 spl_boot_device(void)
return BOOT_DEVICE_RAM;
#ifdef CONFIG_SPL_MMC_SUPPORT
case SD_MODE1:
- case SD1_LSHFT_MODE:
+ case SD1_LSHFT_MODE: /* not working on silicon v1 */
/* if both controllers enabled, then these two are the second controller */
#if defined(CONFIG_ZYNQ_SDHCI0) && defined(CONFIG_ZYNQ_SDHCI1)
return BOOT_DEVICE_MMC2;
--
1.9.1
1
0
From: Jagan Teki <jagan(a)amarulasolutions.com>
NanoPi A64 is a new board of high performance with low cost
designed by FriendlyElec., using the Allwinner A64 SOC.
Nanopi A64 features
- Allwinner A64, 64-bit Quad-core Cortex-A53@648MHz to 1.152GHz, DVFS
- 1GB DDR3 RAM
- MicroSD
- Gigabit Ethernet (RTL8211E)
- Wi-Fi 802.11b/g/n
- IR receiver
- Audio In/Out
- Video In/Out
- Serial Debug Port
- microUSB 5V 2A DC power-supply
Signed-off-by: Jagan Teki <jagan(a)amarulasolutions.com>
---
Note: Not tested yet, board is on-the-way to reach.
arch/arm/dts/Makefile | 1 +
arch/arm/dts/sun50i-a64-nanopi-a64.dts | 94 ++++++++++++++++++++++++++++++++++
board/sunxi/MAINTAINERS | 5 ++
configs/nanopi_a64_defconfig | 16 ++++++
4 files changed, 116 insertions(+)
create mode 100644 arch/arm/dts/sun50i-a64-nanopi-a64.dts
create mode 100644 configs/nanopi_a64_defconfig
diff --git a/arch/arm/dts/Makefile b/arch/arm/dts/Makefile
index 242b329..07e81b5 100644
--- a/arch/arm/dts/Makefile
+++ b/arch/arm/dts/Makefile
@@ -320,6 +320,7 @@ dtb-$(CONFIG_MACH_SUN50I_H5) += \
sun50i-h5-orangepi-zero-plus2.dtb
dtb-$(CONFIG_MACH_SUN50I) += \
sun50i-a64-bananapi-m64.dtb \
+ sun50i-a64-nanopi-a64.dtb \
sun50i-a64-orangepi-win.dtb \
sun50i-a64-pine64-plus.dtb \
sun50i-a64-pine64.dtb
diff --git a/arch/arm/dts/sun50i-a64-nanopi-a64.dts b/arch/arm/dts/sun50i-a64-nanopi-a64.dts
new file mode 100644
index 0000000..17a571a
--- /dev/null
+++ b/arch/arm/dts/sun50i-a64-nanopi-a64.dts
@@ -0,0 +1,94 @@
+/*
+ * Copyright (C) 2017 Jagan Teki <jteki(a)openedev.com>
+ *
+ * This file is dual-licensed: you can use it either under the terms
+ * of the GPL or the X11 license, at your option. Note that this dual
+ * licensing only applies to this file, and not this project as a
+ * whole.
+ *
+ * a) This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * Or, alternatively,
+ *
+ * b) Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use,
+ * copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following
+ * conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
+ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+ * OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+/dts-v1/;
+
+#include "sun50i-a64.dtsi"
+
+#include <dt-bindings/gpio/gpio.h>
+
+/ {
+ model = "FriendlyARM NanoPi A64";
+ compatible = "friendlyarm,nanopi-a64", "allwinner,sun50i-a64";
+
+ aliases {
+ serial0 = &uart0;
+ };
+
+ chosen {
+ stdout-path = "serial0:115200n8";
+ };
+
+ reg_vcc3v3: vcc3v3 {
+ compatible = "regulator-fixed";
+ regulator-name = "vcc3v3";
+ regulator-min-microvolt = <3300000>;
+ regulator-max-microvolt = <3300000>;
+ };
+};
+
+&i2c1 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&i2c1_pins>;
+ status = "okay";
+};
+
+&i2c1_pins {
+ bias-pull-up;
+};
+
+&mmc0 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&mmc0_pins>;
+ vmmc-supply = <®_vcc3v3>;
+ cd-gpios = <&pio 5 6 GPIO_ACTIVE_HIGH>;
+ cd-inverted;
+ disable-wp;
+ bus-width = <4>;
+ status = "okay";
+};
+
+&uart0 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&uart0_pins_a>;
+ status = "okay";
+};
diff --git a/board/sunxi/MAINTAINERS b/board/sunxi/MAINTAINERS
index 0bdff84..76696bb 100644
--- a/board/sunxi/MAINTAINERS
+++ b/board/sunxi/MAINTAINERS
@@ -257,6 +257,11 @@ M: Jelle van der Waa <jelle(a)vdwaa.nl>
S: Maintained
F: configs/nanopi_neo_air_defconfig
+NANOPI-A64 BOARD
+M: Jagan Teki <jagan(a)amarulasolutions.com>
+S: Maintained
+F: configs/nanopi_a64_defconfig
+
NINTENDO NES CLASSIC EDITION BOARD
M: FUKAUMI Naoki <naobsd(a)gmail.com>
S: Maintained
diff --git a/configs/nanopi_a64_defconfig b/configs/nanopi_a64_defconfig
new file mode 100644
index 0000000..9e5efe6
--- /dev/null
+++ b/configs/nanopi_a64_defconfig
@@ -0,0 +1,16 @@
+CONFIG_ARM=y
+CONFIG_ARCH_SUNXI=y
+CONFIG_MACH_SUN50I=y
+CONFIG_RESERVE_ALLWINNER_BOOT0_HEADER=y
+CONFIG_DEFAULT_DEVICE_TREE="sun50i-a64-nanopi-a64"
+# CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set
+CONFIG_CONSOLE_MUX=y
+CONFIG_SPL=y
+# CONFIG_CMD_IMLS is not set
+# CONFIG_CMD_FLASH is not set
+# CONFIG_CMD_FPGA is not set
+# CONFIG_SPL_DOS_PARTITION is not set
+# CONFIG_SPL_ISO_PARTITION is not set
+# CONFIG_SPL_EFI_PARTITION is not set
+CONFIG_SUN8I_EMAC=y
+CONFIG_USB_EHCI_HCD=y
--
1.9.1
1
0

Re: [U-Boot] [linux-sunxi] [PATCH v2 1/2] sunxi: Rename bananapi board as bananapi m1
by Chen-Yu Tsai 30 May '17
by Chen-Yu Tsai 30 May '17
30 May '17
Hi,
On Tue, May 30, 2017 at 5:58 AM, Karsten Merker <merker(a)debian.org> wrote:
> On Tue, May 30, 2017 at 01:06:54AM +0530, Jagan Teki wrote:
>> From: Jagan Teki <jagan(a)amarulasolutions.com>
>>
>> from BPI(BIPAI KEJI LIMITED) products the Bananapi board
>> is named as 'Bananapi M1' and this is the starting
>> bananapi board from M1 series.
>>
>> So rename the board defconfig, dts and suffix 'M1' on
>> model for the same so-that next sequence on bananapi starts
>> like M1 Plus, M2 and so.on
>
> Hello,
>
> the equivalent change in the kernel has been NACKed by me as with
> the proposed change the installation of a newer kernel would
> break a large number of existing end user systems (which rely on
> the old dts file name and on the old model string).
>
> U-Boot should keep the same dts as the kernel, so this
> effectively means a NACK to this change for u-boot as well.
Do the distros also keep a list of defconfig targets to build
for U-boot? It seems that way for Debian. I imagine just
changing the defconfig names would be troublesome for the
maintainers.
ChenYu
2
1
Hi everyone,
Here is a V2 of the support of the Sun8i NanoPi M1 platform.
I created a patch serie instead on a standalone patch
because the kernel device tree for Nanopi uses a dtsi file
that does not exist in u-boot. This dtsi will be added in
this serie.
Changes since V1:
- Added the NanoPi dtsi from the kernel device tree
- Updated the NanoPi Neo device tree to use the dtsi
- Updated the dtsi from the kernel reference to remove the
gpio-keys to be able to use this dtsi file for the
NanoPi Neo Air. I will send this patch to the kernel if this
modification make sense.
- Updated the NanoPi Neo Air to use the dtsi
Patch01: Add the support of the NanoPi M1 platform. Based from the kernel
device tree so the NanoPi dtsi file is also added.
Patch02: Update the NanoPi Neo to use the dtsi to be close to the one from
the kernel.
Patch03: Move the gpio-keys to the dts file to have a generic dtsi file and
be able to use it for the NanoPi Neo Air.
Patch04: Update the NanoPi Neo Air device tree file to use the dtsi one.
Thank you in advance for your reviews/comments.
Best regards,
Mylène Josserand (4):
sunxi: Add support for NanoPi M1
sunxi: Update NanoPi Neo to use dtsi
sunxi: Move gpio-keys from NanoPi dtsi to dts
sunxi: Update NanoPi Neo Air to use dtsi
arch/arm/dts/Makefile | 1 +
arch/arm/dts/sun8i-h3-nanopi-m1.dts | 77 +++++++++++++++++++
arch/arm/dts/sun8i-h3-nanopi-neo-air.dts | 51 +------------
arch/arm/dts/sun8i-h3-nanopi-neo.dts | 82 +++-----------------
arch/arm/dts/sun8i-h3-nanopi.dtsi | 124 +++++++++++++++++++++++++++++++
board/sunxi/MAINTAINERS | 5 ++
configs/nanopi_m1_defconfig | 16 ++++
7 files changed, 233 insertions(+), 123 deletions(-)
create mode 100644 arch/arm/dts/sun8i-h3-nanopi-m1.dts
create mode 100644 arch/arm/dts/sun8i-h3-nanopi.dtsi
create mode 100644 configs/nanopi_m1_defconfig
--
2.11.0
3
7

29 May '17
From: Jagan Teki <jagan(a)amarulasolutions.com>
from BPI(BIPAI KEJI LIMITED) products the Bananapi board
is named as 'Bananapi M1' and this is the starting
bananapi board from M1 series.
So rename the board defconfig, dts and suffix 'M1' on
model for the same so-that next sequence on bananapi starts
like M1 Plus, M2 and so.on
Cc: Icenowy Zheng <icenowy(a)aosc.io>
Signed-off-by: Jagan Teki <jagan(a)amarulasolutions.com>
---
Changes for v2:
- Newly added patch
arch/arm/dts/sun7i-a20-bananapi-m1.dts | 293 +++++++++++++++++++++++++++++++++
arch/arm/dts/sun7i-a20-bananapi.dts | 293 ---------------------------------
board/sunxi/MAINTAINERS | 2 +-
configs/Bananapi_M1_defconfig | 23 +++
configs/Bananapi_defconfig | 23 ---
5 files changed, 317 insertions(+), 317 deletions(-)
create mode 100644 arch/arm/dts/sun7i-a20-bananapi-m1.dts
delete mode 100644 arch/arm/dts/sun7i-a20-bananapi.dts
create mode 100644 configs/Bananapi_M1_defconfig
delete mode 100644 configs/Bananapi_defconfig
diff --git a/arch/arm/dts/sun7i-a20-bananapi-m1.dts b/arch/arm/dts/sun7i-a20-bananapi-m1.dts
new file mode 100644
index 0000000..4a1d7d7
--- /dev/null
+++ b/arch/arm/dts/sun7i-a20-bananapi-m1.dts
@@ -0,0 +1,293 @@
+/*
+ * Copyright 2014 Hans de Goede <hdegoede(a)redhat.com>
+ *
+ * Hans de Goede <hdegoede(a)redhat.com>
+ *
+ * This file is dual-licensed: you can use it either under the terms
+ * of the GPL or the X11 license, at your option. Note that this dual
+ * licensing only applies to this file, and not this project as a
+ * whole.
+ *
+ * a) This file is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of the
+ * License, or (at your option) any later version.
+ *
+ * This file is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * Or, alternatively,
+ *
+ * b) Permission is hereby granted, free of charge, to any person
+ * obtaining a copy of this software and associated documentation
+ * files (the "Software"), to deal in the Software without
+ * restriction, including without limitation the rights to use,
+ * copy, modify, merge, publish, distribute, sublicense, and/or
+ * sell copies of the Software, and to permit persons to whom the
+ * Software is furnished to do so, subject to the following
+ * conditions:
+ *
+ * The above copyright notice and this permission notice shall be
+ * included in all copies or substantial portions of the Software.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+ * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
+ * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
+ * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
+ * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
+ * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
+ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
+ * OTHER DEALINGS IN THE SOFTWARE.
+ */
+
+/dts-v1/;
+#include "sun7i-a20.dtsi"
+#include "sunxi-common-regulators.dtsi"
+
+#include <dt-bindings/gpio/gpio.h>
+#include <dt-bindings/interrupt-controller/irq.h>
+#include <dt-bindings/pinctrl/sun4i-a10.h>
+
+/ {
+ model = "LeMaker Banana Pi M1";
+ compatible = "lemaker,bananapi", "allwinner,sun7i-a20";
+
+ aliases {
+ serial0 = &uart0;
+ serial1 = &uart3;
+ serial2 = &uart7;
+ };
+
+ chosen {
+ stdout-path = "serial0:115200n8";
+ };
+
+ leds {
+ compatible = "gpio-leds";
+ pinctrl-names = "default";
+ pinctrl-0 = <&led_pins_bananapi>;
+
+ green {
+ label = "bananapi:green:usr";
+ gpios = <&pio 7 24 GPIO_ACTIVE_HIGH>;
+ };
+ };
+
+ reg_gmac_3v3: gmac-3v3 {
+ compatible = "regulator-fixed";
+ pinctrl-names = "default";
+ pinctrl-0 = <&gmac_power_pin_bananapi>;
+ regulator-name = "gmac-3v3";
+ regulator-min-microvolt = <3300000>;
+ regulator-max-microvolt = <3300000>;
+ startup-delay-us = <100000>;
+ enable-active-high;
+ gpio = <&pio 7 23 GPIO_ACTIVE_HIGH>;
+ };
+};
+
+&ahci {
+ status = "okay";
+};
+
+&codec {
+ status = "okay";
+};
+
+&cpu0 {
+ cpu-supply = <®_dcdc2>;
+ operating-points = <
+ /* kHz uV */
+ 960000 1400000
+ 912000 1400000
+ 864000 1350000
+ 720000 1250000
+ 528000 1150000
+ 312000 1100000
+ 144000 1050000
+ >;
+};
+
+&ehci0 {
+ status = "okay";
+};
+
+&ehci1 {
+ status = "okay";
+};
+
+&gmac {
+ pinctrl-names = "default";
+ pinctrl-0 = <&gmac_pins_rgmii_a>;
+ phy = <&phy1>;
+ phy-mode = "rgmii";
+ phy-supply = <®_gmac_3v3>;
+ status = "okay";
+
+ phy1: ethernet-phy@1 {
+ reg = <1>;
+ };
+};
+
+&i2c0 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&i2c0_pins_a>;
+ status = "okay";
+
+ axp209: pmic@34 {
+ reg = <0x34>;
+ interrupt-parent = <&nmi_intc>;
+ interrupts = <0 IRQ_TYPE_LEVEL_LOW>;
+ };
+};
+
+&i2c2 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&i2c2_pins_a>;
+ status = "okay";
+};
+
+&ir0 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&ir0_rx_pins_a>;
+ status = "okay";
+};
+
+&mmc0 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&mmc0_pins_a>, <&mmc0_cd_pin_bananapi>;
+ vmmc-supply = <®_vcc3v3>;
+ bus-width = <4>;
+ cd-gpios = <&pio 7 10 GPIO_ACTIVE_HIGH>; /* PH10 */
+ cd-inverted;
+ status = "okay";
+};
+
+&ohci0 {
+ status = "okay";
+};
+
+&ohci1 {
+ status = "okay";
+};
+
+&otg_sram {
+ status = "okay";
+};
+
+&pio {
+ usb0_id_detect_pin: usb0_id_detect_pin@0 {
+ allwinner,pins = "PH4";
+ allwinner,function = "gpio_in";
+ allwinner,drive = <SUN4I_PINCTRL_10_MA>;
+ allwinner,pull = <SUN4I_PINCTRL_PULL_UP>;
+ };
+
+ mmc0_cd_pin_bananapi: mmc0_cd_pin@0 {
+ allwinner,pins = "PH10";
+ allwinner,function = "gpio_in";
+ allwinner,drive = <SUN4I_PINCTRL_10_MA>;
+ allwinner,pull = <SUN4I_PINCTRL_PULL_UP>;
+ };
+
+ gmac_power_pin_bananapi: gmac_power_pin@0 {
+ allwinner,pins = "PH23";
+ allwinner,function = "gpio_out";
+ allwinner,drive = <SUN4I_PINCTRL_10_MA>;
+ allwinner,pull = <SUN4I_PINCTRL_NO_PULL>;
+ };
+
+ led_pins_bananapi: led_pins@0 {
+ allwinner,pins = "PH24";
+ allwinner,function = "gpio_out";
+ allwinner,drive = <SUN4I_PINCTRL_10_MA>;
+ allwinner,pull = <SUN4I_PINCTRL_NO_PULL>;
+ };
+};
+
+#include "axp209.dtsi"
+
+®_dcdc2 {
+ regulator-always-on;
+ regulator-min-microvolt = <1000000>;
+ regulator-max-microvolt = <1400000>;
+ regulator-name = "vdd-cpu";
+};
+
+®_dcdc3 {
+ regulator-always-on;
+ regulator-min-microvolt = <1000000>;
+ regulator-max-microvolt = <1400000>;
+ regulator-name = "vdd-int-dll";
+};
+
+®_ldo1 {
+ regulator-name = "vdd-rtc";
+};
+
+®_ldo2 {
+ regulator-always-on;
+ regulator-min-microvolt = <3000000>;
+ regulator-max-microvolt = <3000000>;
+ regulator-name = "avcc";
+};
+
+®_usb0_vbus {
+ status = "okay";
+};
+
+®_usb1_vbus {
+ status = "okay";
+};
+
+®_usb2_vbus {
+ status = "okay";
+};
+
+&spi0 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&spi0_pins_a>,
+ <&spi0_cs0_pins_a>,
+ <&spi0_cs1_pins_a>;
+ status = "okay";
+};
+
+&uart0 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&uart0_pins_a>;
+ status = "okay";
+};
+
+&uart3 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&uart3_pins_b>;
+ status = "okay";
+};
+
+&uart7 {
+ pinctrl-names = "default";
+ pinctrl-0 = <&uart7_pins_a>;
+ status = "okay";
+};
+
+&usb_otg {
+ dr_mode = "otg";
+ status = "okay";
+};
+
+&usb_power_supply {
+ status = "okay";
+};
+
+&usbphy {
+ pinctrl-names = "default";
+ pinctrl-0 = <&usb0_id_detect_pin>;
+ usb0_id_det-gpio = <&pio 7 4 GPIO_ACTIVE_HIGH>; /* PH4 */
+ usb0_vbus_power-supply = <&usb_power_supply>;
+ usb0_vbus-supply = <®_usb0_vbus>;
+ usb1_vbus-supply = <®_usb1_vbus>;
+ usb2_vbus-supply = <®_usb2_vbus>;
+ status = "okay";
+};
diff --git a/arch/arm/dts/sun7i-a20-bananapi.dts b/arch/arm/dts/sun7i-a20-bananapi.dts
deleted file mode 100644
index 67c8a76..0000000
--- a/arch/arm/dts/sun7i-a20-bananapi.dts
+++ /dev/null
@@ -1,293 +0,0 @@
-/*
- * Copyright 2014 Hans de Goede <hdegoede(a)redhat.com>
- *
- * Hans de Goede <hdegoede(a)redhat.com>
- *
- * This file is dual-licensed: you can use it either under the terms
- * of the GPL or the X11 license, at your option. Note that this dual
- * licensing only applies to this file, and not this project as a
- * whole.
- *
- * a) This file is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License as
- * published by the Free Software Foundation; either version 2 of the
- * License, or (at your option) any later version.
- *
- * This file is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * Or, alternatively,
- *
- * b) Permission is hereby granted, free of charge, to any person
- * obtaining a copy of this software and associated documentation
- * files (the "Software"), to deal in the Software without
- * restriction, including without limitation the rights to use,
- * copy, modify, merge, publish, distribute, sublicense, and/or
- * sell copies of the Software, and to permit persons to whom the
- * Software is furnished to do so, subject to the following
- * conditions:
- *
- * The above copyright notice and this permission notice shall be
- * included in all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
- * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
- * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
- * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
- * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
- * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
- * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
- * OTHER DEALINGS IN THE SOFTWARE.
- */
-
-/dts-v1/;
-#include "sun7i-a20.dtsi"
-#include "sunxi-common-regulators.dtsi"
-
-#include <dt-bindings/gpio/gpio.h>
-#include <dt-bindings/interrupt-controller/irq.h>
-#include <dt-bindings/pinctrl/sun4i-a10.h>
-
-/ {
- model = "LeMaker Banana Pi";
- compatible = "lemaker,bananapi", "allwinner,sun7i-a20";
-
- aliases {
- serial0 = &uart0;
- serial1 = &uart3;
- serial2 = &uart7;
- };
-
- chosen {
- stdout-path = "serial0:115200n8";
- };
-
- leds {
- compatible = "gpio-leds";
- pinctrl-names = "default";
- pinctrl-0 = <&led_pins_bananapi>;
-
- green {
- label = "bananapi:green:usr";
- gpios = <&pio 7 24 GPIO_ACTIVE_HIGH>;
- };
- };
-
- reg_gmac_3v3: gmac-3v3 {
- compatible = "regulator-fixed";
- pinctrl-names = "default";
- pinctrl-0 = <&gmac_power_pin_bananapi>;
- regulator-name = "gmac-3v3";
- regulator-min-microvolt = <3300000>;
- regulator-max-microvolt = <3300000>;
- startup-delay-us = <100000>;
- enable-active-high;
- gpio = <&pio 7 23 GPIO_ACTIVE_HIGH>;
- };
-};
-
-&ahci {
- status = "okay";
-};
-
-&codec {
- status = "okay";
-};
-
-&cpu0 {
- cpu-supply = <®_dcdc2>;
- operating-points = <
- /* kHz uV */
- 960000 1400000
- 912000 1400000
- 864000 1350000
- 720000 1250000
- 528000 1150000
- 312000 1100000
- 144000 1050000
- >;
-};
-
-&ehci0 {
- status = "okay";
-};
-
-&ehci1 {
- status = "okay";
-};
-
-&gmac {
- pinctrl-names = "default";
- pinctrl-0 = <&gmac_pins_rgmii_a>;
- phy = <&phy1>;
- phy-mode = "rgmii";
- phy-supply = <®_gmac_3v3>;
- status = "okay";
-
- phy1: ethernet-phy@1 {
- reg = <1>;
- };
-};
-
-&i2c0 {
- pinctrl-names = "default";
- pinctrl-0 = <&i2c0_pins_a>;
- status = "okay";
-
- axp209: pmic@34 {
- reg = <0x34>;
- interrupt-parent = <&nmi_intc>;
- interrupts = <0 IRQ_TYPE_LEVEL_LOW>;
- };
-};
-
-&i2c2 {
- pinctrl-names = "default";
- pinctrl-0 = <&i2c2_pins_a>;
- status = "okay";
-};
-
-&ir0 {
- pinctrl-names = "default";
- pinctrl-0 = <&ir0_rx_pins_a>;
- status = "okay";
-};
-
-&mmc0 {
- pinctrl-names = "default";
- pinctrl-0 = <&mmc0_pins_a>, <&mmc0_cd_pin_bananapi>;
- vmmc-supply = <®_vcc3v3>;
- bus-width = <4>;
- cd-gpios = <&pio 7 10 GPIO_ACTIVE_HIGH>; /* PH10 */
- cd-inverted;
- status = "okay";
-};
-
-&ohci0 {
- status = "okay";
-};
-
-&ohci1 {
- status = "okay";
-};
-
-&otg_sram {
- status = "okay";
-};
-
-&pio {
- usb0_id_detect_pin: usb0_id_detect_pin@0 {
- allwinner,pins = "PH4";
- allwinner,function = "gpio_in";
- allwinner,drive = <SUN4I_PINCTRL_10_MA>;
- allwinner,pull = <SUN4I_PINCTRL_PULL_UP>;
- };
-
- mmc0_cd_pin_bananapi: mmc0_cd_pin@0 {
- allwinner,pins = "PH10";
- allwinner,function = "gpio_in";
- allwinner,drive = <SUN4I_PINCTRL_10_MA>;
- allwinner,pull = <SUN4I_PINCTRL_PULL_UP>;
- };
-
- gmac_power_pin_bananapi: gmac_power_pin@0 {
- allwinner,pins = "PH23";
- allwinner,function = "gpio_out";
- allwinner,drive = <SUN4I_PINCTRL_10_MA>;
- allwinner,pull = <SUN4I_PINCTRL_NO_PULL>;
- };
-
- led_pins_bananapi: led_pins@0 {
- allwinner,pins = "PH24";
- allwinner,function = "gpio_out";
- allwinner,drive = <SUN4I_PINCTRL_10_MA>;
- allwinner,pull = <SUN4I_PINCTRL_NO_PULL>;
- };
-};
-
-#include "axp209.dtsi"
-
-®_dcdc2 {
- regulator-always-on;
- regulator-min-microvolt = <1000000>;
- regulator-max-microvolt = <1400000>;
- regulator-name = "vdd-cpu";
-};
-
-®_dcdc3 {
- regulator-always-on;
- regulator-min-microvolt = <1000000>;
- regulator-max-microvolt = <1400000>;
- regulator-name = "vdd-int-dll";
-};
-
-®_ldo1 {
- regulator-name = "vdd-rtc";
-};
-
-®_ldo2 {
- regulator-always-on;
- regulator-min-microvolt = <3000000>;
- regulator-max-microvolt = <3000000>;
- regulator-name = "avcc";
-};
-
-®_usb0_vbus {
- status = "okay";
-};
-
-®_usb1_vbus {
- status = "okay";
-};
-
-®_usb2_vbus {
- status = "okay";
-};
-
-&spi0 {
- pinctrl-names = "default";
- pinctrl-0 = <&spi0_pins_a>,
- <&spi0_cs0_pins_a>,
- <&spi0_cs1_pins_a>;
- status = "okay";
-};
-
-&uart0 {
- pinctrl-names = "default";
- pinctrl-0 = <&uart0_pins_a>;
- status = "okay";
-};
-
-&uart3 {
- pinctrl-names = "default";
- pinctrl-0 = <&uart3_pins_b>;
- status = "okay";
-};
-
-&uart7 {
- pinctrl-names = "default";
- pinctrl-0 = <&uart7_pins_a>;
- status = "okay";
-};
-
-&usb_otg {
- dr_mode = "otg";
- status = "okay";
-};
-
-&usb_power_supply {
- status = "okay";
-};
-
-&usbphy {
- pinctrl-names = "default";
- pinctrl-0 = <&usb0_id_detect_pin>;
- usb0_id_det-gpio = <&pio 7 4 GPIO_ACTIVE_HIGH>; /* PH4 */
- usb0_vbus_power-supply = <&usb_power_supply>;
- usb0_vbus-supply = <®_usb0_vbus>;
- usb1_vbus-supply = <®_usb1_vbus>;
- usb2_vbus-supply = <®_usb2_vbus>;
- status = "okay";
-};
diff --git a/board/sunxi/MAINTAINERS b/board/sunxi/MAINTAINERS
index a512a20..c2f0227 100644
--- a/board/sunxi/MAINTAINERS
+++ b/board/sunxi/MAINTAINERS
@@ -44,7 +44,7 @@ F: configs/Mele_M9_defconfig
F: configs/Sinovoip_BPI_M2_defconfig
F: include/configs/sun7i.h
F: configs/A20-OLinuXino_MICRO_defconfig
-F: configs/Bananapi_defconfig
+F: configs/Bananapi_M1_defconfig
F: configs/Bananapro_defconfig
F: configs/i12-tvbox_defconfig
F: configs/Linksprite_pcDuino3_defconfig
diff --git a/configs/Bananapi_M1_defconfig b/configs/Bananapi_M1_defconfig
new file mode 100644
index 0000000..1f8e37b
--- /dev/null
+++ b/configs/Bananapi_M1_defconfig
@@ -0,0 +1,23 @@
+CONFIG_ARM=y
+CONFIG_ARCH_SUNXI=y
+CONFIG_MACH_SUN7I=y
+CONFIG_DRAM_CLK=432
+CONFIG_MACPWR="PH23"
+CONFIG_VIDEO_COMPOSITE=y
+CONFIG_GMAC_TX_DELAY=3
+CONFIG_DEFAULT_DEVICE_TREE="sun7i-a20-bananapi-m1"
+CONFIG_AHCI=y
+# CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set
+CONFIG_SPL=y
+CONFIG_SPL_I2C_SUPPORT=y
+# CONFIG_CMD_IMLS is not set
+# CONFIG_CMD_FLASH is not set
+# CONFIG_CMD_FPGA is not set
+# CONFIG_SPL_DOS_PARTITION is not set
+# CONFIG_SPL_ISO_PARTITION is not set
+# CONFIG_SPL_EFI_PARTITION is not set
+CONFIG_NETCONSOLE=y
+CONFIG_ETH_DESIGNWARE=y
+CONFIG_RGMII=y
+CONFIG_SUN7I_GMAC=y
+CONFIG_USB_EHCI_HCD=y
diff --git a/configs/Bananapi_defconfig b/configs/Bananapi_defconfig
deleted file mode 100644
index fe75eef..0000000
--- a/configs/Bananapi_defconfig
+++ /dev/null
@@ -1,23 +0,0 @@
-CONFIG_ARM=y
-CONFIG_ARCH_SUNXI=y
-CONFIG_MACH_SUN7I=y
-CONFIG_DRAM_CLK=432
-CONFIG_MACPWR="PH23"
-CONFIG_VIDEO_COMPOSITE=y
-CONFIG_GMAC_TX_DELAY=3
-CONFIG_DEFAULT_DEVICE_TREE="sun7i-a20-bananapi"
-CONFIG_AHCI=y
-# CONFIG_SYS_MALLOC_CLEAR_ON_INIT is not set
-CONFIG_SPL=y
-CONFIG_SPL_I2C_SUPPORT=y
-# CONFIG_CMD_IMLS is not set
-# CONFIG_CMD_FLASH is not set
-# CONFIG_CMD_FPGA is not set
-# CONFIG_SPL_DOS_PARTITION is not set
-# CONFIG_SPL_ISO_PARTITION is not set
-# CONFIG_SPL_EFI_PARTITION is not set
-CONFIG_NETCONSOLE=y
-CONFIG_ETH_DESIGNWARE=y
-CONFIG_RGMII=y
-CONFIG_SUN7I_GMAC=y
-CONFIG_USB_EHCI_HCD=y
--
1.9.1
1
1

[U-Boot] [PATCH] sunxi: sinovoip: Use proper naming convention for BPI boards
by Jagan Teki 29 May '17
by Jagan Teki 29 May '17
29 May '17
From: Jagan Teki <jagan(a)amarulasolutions.com>
- Rename Sinovoip BPI defconfigs to use small letter
- To avoid naming conflict with 'LeMaker' add sinovoip
prefix to BPI M2 Ultra defconfig since bananapi is
also name used by 'LeMaker'
- Add 'SINOVOIP' prefix 'BANANAPI M2 ULTRA BOARD' under
board/sunxi/MAINTAINERS file.
Cc: Icenowy Zheng <icenowy(a)aosc.io>
Cc: Chen-Yu Tsai <wens(a)csie.org>
Cc: VishnuPatekar <vishnupatekar0510(a)gmail.com>
Signed-off-by: Jagan Teki <jagan(a)amarulasolutions.com>
---
board/sunxi/MAINTAINERS | 10 +++++-----
.../{Sinovoip_BPI_M2_defconfig => sinovoip_bpi_m2_defconfig} | 0
...ip_BPI_M2_Plus_defconfig => sinovoip_bpi_m2_plus_defconfig} | 0
...napi_M2_Ultra_defconfig => sinovoip_bpi_m2_ultra_defconfig} | 0
.../{Sinovoip_BPI_M3_defconfig => sinovoip_bpi_m3_defconfig} | 0
5 files changed, 5 insertions(+), 5 deletions(-)
rename configs/{Sinovoip_BPI_M2_defconfig => sinovoip_bpi_m2_defconfig} (100%)
rename configs/{Sinovoip_BPI_M2_Plus_defconfig => sinovoip_bpi_m2_plus_defconfig} (100%)
rename configs/{Bananapi_M2_Ultra_defconfig => sinovoip_bpi_m2_ultra_defconfig} (100%)
rename configs/{Sinovoip_BPI_M3_defconfig => sinovoip_bpi_m3_defconfig} (100%)
diff --git a/board/sunxi/MAINTAINERS b/board/sunxi/MAINTAINERS
index a512a20..61d1479 100644
--- a/board/sunxi/MAINTAINERS
+++ b/board/sunxi/MAINTAINERS
@@ -41,7 +41,7 @@ F: configs/CSQ_CS908_defconfig
F: configs/inet_q972_defconfig
F: configs/Mele_A1000G_quad_defconfig
F: configs/Mele_M9_defconfig
-F: configs/Sinovoip_BPI_M2_defconfig
+F: configs/sinovoip_bpi_m2_defconfig
F: include/configs/sun7i.h
F: configs/A20-OLinuXino_MICRO_defconfig
F: configs/Bananapi_defconfig
@@ -108,10 +108,10 @@ M: Paul Kocialkowski <contact(a)paulk.fr>
S: Maintained
F: configs/Ampe_A76_defconfig
-BANANAPI M2 ULTRA BOARD
+SINOVOIP BANANAPI M2 ULTRA BOARD
M: Chen-Yu Tsai <wens(a)csie.org>
S: Maintained
-F: configs/Bananapi_M2_Ultra_defconfig
+F: configs/sinovoip_bpi_m2_ultra_defconfig
F: arch/arm/dts/sun8i-r40-bananapi-m2-ultra.dts
COLOMBUS BOARD
@@ -287,12 +287,12 @@ W: http://linux-sunxi.org/Sinlinx_SinA33
SINOVOIP BPI M2 PLUS H3 BOARD
M: Icenowy Zheng <icenowy(a)aosc.io>
S: Maintained
-F: configs/Sinovoip_BPI_M2_Plus_defconfig
+F: configs/sinovoip_bpi_m2_Plus_defconfig
SINOVOIP BPI M3 A83T BOARD
M: VishnuPatekar <vishnupatekar0510(a)gmail.com>
S: Maintained
-F: configs/Sinovoip_BPI_M3_defconfig
+F: configs/sinovoip_bpi_m3_defconfig
SUNCHIP CX-A99 BOARD
M: Rask Ingemann Lambertsen <rask(a)formelder.dk>
diff --git a/configs/Sinovoip_BPI_M2_defconfig b/configs/sinovoip_bpi_m2_defconfig
similarity index 100%
rename from configs/Sinovoip_BPI_M2_defconfig
rename to configs/sinovoip_bpi_m2_defconfig
diff --git a/configs/Sinovoip_BPI_M2_Plus_defconfig b/configs/sinovoip_bpi_m2_plus_defconfig
similarity index 100%
rename from configs/Sinovoip_BPI_M2_Plus_defconfig
rename to configs/sinovoip_bpi_m2_plus_defconfig
diff --git a/configs/Bananapi_M2_Ultra_defconfig b/configs/sinovoip_bpi_m2_ultra_defconfig
similarity index 100%
rename from configs/Bananapi_M2_Ultra_defconfig
rename to configs/sinovoip_bpi_m2_ultra_defconfig
diff --git a/configs/Sinovoip_BPI_M3_defconfig b/configs/sinovoip_bpi_m3_defconfig
similarity index 100%
rename from configs/Sinovoip_BPI_M3_defconfig
rename to configs/sinovoip_bpi_m3_defconfig
--
1.9.1
3
3
[PATCHv4 1/3] ARM64: dts: hi3798cv200-poplar: add device tree bindings
[PATCHv4 2/3] driver: mmc: update debug info
[PATCHv4 3/3] ARM64: poplar: hi3798cv200: u-boot support for Poplar
The following changes with respect to v3:
- Remove modifications to the linux kernel device tree
- Introduce board specific uboot device tree config
* specify the clock for the console
* define the ehci parameters to allow using the ehci-generic driver
7
52