[coreboot-gerrit] New patch to review for coreboot: rockchip: gru: Add USB DRD DWC3 controller support

Martin Roth (martinroth@google.com) gerrit at coreboot.org
Wed Jun 8 23:51:29 CEST 2016


Martin Roth (martinroth at google.com) just uploaded a new patch set to gerrit, which you can find at https://review.coreboot.org/15112

-gerrit

commit 366f978547bf6bc491fb5fea1f9505da305fe148
Author: Liangfeng Wu <wulf at rock-chips.com>
Date:   Thu May 26 16:06:58 2016 +0800

    rockchip: gru: Add USB DRD DWC3 controller support
    
    This patch adds code to initialize the two DWC3 USB
    host controllers, and uses them to initialize USB3.0
    on the gru rk3399 board.
    
    BRANCH=none
    BUG=chrome-os-partner:52684
    TEST=boot from USB3.0 on gru/kevin rk3399 platform
    
    Change-Id: If6a6e56f3a7c7ce8e8b098634cfc2f250a91810d
    Signed-off-by: Martin Roth <martinroth at chromium.org>
    Original-Commit-Id:
    Original-Change-Id: I796fa1133510876f75873d134ea752e1b52e40a8
    Original-Signed-off-by: Liangfeng Wu <wulf at rock-chips.com>
    Original-Signed-off-by: Douglas Anderson <dianders at chromium.org>
    Original-Reviewed-on: https://chromium-review.googlesource.com/347524
    Original-Commit-Ready: Brian Norris <briannorris at chromium.org>
    Original-Reviewed-by: Vadim Bendebury <vbendeb at chromium.org>
    Original-Reviewed-by: Julius Werner <jwerner at chromium.org>
---
 src/mainboard/google/gru/mainboard.c             |   8 ++
 src/soc/rockchip/rk3399/Makefile.inc             |   2 +
 src/soc/rockchip/rk3399/include/soc/addressmap.h |   3 +
 src/soc/rockchip/rk3399/include/soc/usb.h        | 121 +++++++++++++++++++++++
 src/soc/rockchip/rk3399/romstage.c               |  13 +++
 src/soc/rockchip/rk3399/usb.c                    | 107 ++++++++++++++++++++
 6 files changed, 254 insertions(+)

diff --git a/src/mainboard/google/gru/mainboard.c b/src/mainboard/google/gru/mainboard.c
index bbe0224..e6baebe 100644
--- a/src/mainboard/google/gru/mainboard.c
+++ b/src/mainboard/google/gru/mainboard.c
@@ -24,6 +24,7 @@
 #include <soc/emmc.h>
 #include <soc/grf.h>
 #include <soc/i2c.h>
+#include <soc/usb.h>
 
 #include "board.h"
 
@@ -118,12 +119,19 @@ static void configure_display(void)
 	gpio_output(GPIO(4, D, 3), 1); /* CPU3_EDP_VDDEN for P3.3V_DISP */
 }
 
+static void setup_usb(void)
+{
+	setup_usb_drd0_dwc3();
+	setup_usb_drd1_dwc3();
+}
+
 static void mainboard_init(device_t dev)
 {
 	configure_sdmmc();
 	configure_emmc();
 	configure_codec();
 	configure_display();
+	setup_usb();
 }
 
 static void enable_backlight_booster(void)
diff --git a/src/soc/rockchip/rk3399/Makefile.inc b/src/soc/rockchip/rk3399/Makefile.inc
index 77958d5..f35f706 100644
--- a/src/soc/rockchip/rk3399/Makefile.inc
+++ b/src/soc/rockchip/rk3399/Makefile.inc
@@ -47,6 +47,7 @@ romstage-y += ../common/pwm.c
 romstage-y += timer.c
 romstage-y += romstage.c
 romstage-y += tsadc.c
+romstage-y += usb.c
 romstage-y += gpio.c
 romstage-y += ../common/gpio.c
 
@@ -67,6 +68,7 @@ ramstage-y += saradc.c
 ramstage-y += soc.c
 ramstage-y += timer.c
 ramstage-$(CONFIG_MAINBOARD_DO_NATIVE_VGA_INIT) += ../common/vop.c
+ramstage-y += usb.c
 
 BL31_MAKEARGS += PLAT=rk3399
 ################################################################################
diff --git a/src/soc/rockchip/rk3399/include/soc/addressmap.h b/src/soc/rockchip/rk3399/include/soc/addressmap.h
index 77fca9e..e65674c 100644
--- a/src/soc/rockchip/rk3399/include/soc/addressmap.h
+++ b/src/soc/rockchip/rk3399/include/soc/addressmap.h
@@ -70,6 +70,9 @@
 #define DDRC1_BASE_ADDR		0xffa88000
 #define SERVER_MSCH1_BASE_ADDR	0xffa8c000
 
+#define USB_DRD0_DWC3_BASE	0xfe80c100
+#define USB_DRD1_DWC3_BASE	0xfe90c100
+
 #define IC_BASES  { I2C0_BASE, I2C1_BASE, I2C2_BASE, I2C3_BASE,		\
 			I2C4_BASE, I2C5_BASE, I2C6_BASE, I2C7_BASE, I2C8_BASE }
 
diff --git a/src/soc/rockchip/rk3399/include/soc/usb.h b/src/soc/rockchip/rk3399/include/soc/usb.h
new file mode 100644
index 0000000..4276a2b
--- /dev/null
+++ b/src/soc/rockchip/rk3399/include/soc/usb.h
@@ -0,0 +1,121 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2016 Rockchip, Inc.
+ *
+ * This program 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; version 2 of the License.
+ *
+ * This program 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.
+ */
+
+#ifndef __SOC_ROCKCHIP_RK3399_USB_H_
+#define __SOC_ROCKCHIP_RK3399_USB_H_
+
+#include <soc/addressmap.h>
+
+/* Global constants */
+#define DWC3_GSNPSID_MASK			0xffff0000
+#define DWC3_GSNPSID_SHIFT			16
+#define DWC3_GSNPSREV_MASK			0xffff
+
+/* Global Configuration Register */
+#define DWC3_GCTL_PWRDNSCALE(n)			((n) << 19)
+#define DWC3_GCTL_U2RSTECN			(1 << 16)
+#define DWC3_GCTL_RAMCLKSEL(x)			\
+		(((x) & DWC3_GCTL_CLK_MASK) << 6)
+#define DWC3_GCTL_CLK_BUS			(0)
+#define DWC3_GCTL_CLK_PIPE			(1)
+#define DWC3_GCTL_CLK_PIPEHALF			(2)
+#define DWC3_GCTL_CLK_MASK			(3)
+#define DWC3_GCTL_PRTCAP(n)			(((n) & (3 << 12)) >> 12)
+#define DWC3_GCTL_PRTCAPDIR(n)			((n) << 12)
+#define DWC3_GCTL_PRTCAP_HOST			1
+#define DWC3_GCTL_PRTCAP_DEVICE			2
+#define DWC3_GCTL_PRTCAP_OTG			3
+#define DWC3_GCTL_CORESOFTRESET			(1 << 11)
+#define DWC3_GCTL_SCALEDOWN(n)			((n) << 4)
+#define DWC3_GCTL_SCALEDOWN_MASK		DWC3_GCTL_SCALEDOWN(3)
+#define DWC3_GCTL_DISSCRAMBLE			(1 << 3)
+#define DWC3_GCTL_DSBLCLKGTNG			(1 << 0)
+
+/* Global HWPARAMS1 Register */
+#define DWC3_GHWPARAMS1_EN_PWROPT(n)		(((n) & (3 << 24)) >> 24)
+#define DWC3_GHWPARAMS1_EN_PWROPT_NO		0
+#define DWC3_GHWPARAMS1_EN_PWROPT_CLK		1
+
+/* Global USB2 PHY Configuration Register */
+#define DWC3_GUSB2PHYCFG_PHYSOFTRST		(1 << 31)
+#define DWC3_GUSB2PHYCFG_U2_FREECLK_EXISTS	(1 << 30)
+#define DWC3_GUSB2PHYCFG_USBTRDTIM(n)		((n) << 10)
+#define DWC3_GUSB2PHYCFG_USB2TRDTIM_MASK	DWC3_GUSB2PHYCFG_USBTRDTIM(0xf)
+#define DWC3_GUSB2PHYCFG_SUSPHY			(1 << 6)
+#define DWC3_GUSB2PHYCFG_PHYIF(n)		((n) << 3)
+#define DWC3_GUSB2PHYCFG_PHYIF_MASK		DWC3_GUSB2PHYCFG_PHYIF(1)
+#define USBTRDTIM_UTMI_8_BIT			9
+#define USBTRDTIM_UTMI_16_BIT			5
+
+/* Global USB3 PIPE Control Register */
+#define DWC3_GUSB3PIPECTL_PHYSOFTRST		(1 << 31)
+#define DWC3_GUSB3PIPECTL_SUSPHY		(1 << 17)
+
+struct rockchip_usb_drd_dwc3 {
+	uint32_t sbuscfg0;
+	uint32_t sbuscfg1;
+	uint32_t txthrcfg;
+	uint32_t rxthrcfg;
+	uint32_t ctl;
+	uint32_t evten;
+	uint32_t sts;
+	uint8_t reserved0[4];
+	uint32_t snpsid;
+	uint32_t gpio;
+	uint32_t uid;
+	uint32_t uctl;
+	uint64_t buserraddr;
+	uint64_t prtbimap;
+	uint32_t hwparams0;
+	uint32_t hwparams1;
+	uint32_t hwparams2;
+	uint32_t hwparams3;
+	uint32_t hwparams4;
+	uint32_t hwparams5;
+	uint32_t hwparams6;
+	uint32_t hwparams7;
+	uint32_t dbgfifospace;
+	uint32_t dbgltssm;
+	uint32_t dbglnmcc;
+	uint32_t dbgbmu;
+	uint32_t dbglspmux;
+	uint32_t dbglsp;
+	uint32_t dbgepinfo0;
+	uint32_t dbgepinfo1;
+	uint64_t prtbimap_hs;
+	uint64_t prtbimap_fs;
+	uint8_t reserved2[112];
+	uint32_t usb2phycfg;
+	uint8_t reserved3[60];
+	uint32_t usb2i2cctl;
+	uint8_t reserved4[60];
+	uint32_t usb2phyacc;
+	uint8_t reserved5[60];
+	uint32_t usb3pipectl;
+	uint8_t reserved6[60];
+};
+
+static struct rockchip_usb_drd_dwc3 * const rockchip_usb_drd0_dwc3 =
+		(void *)USB_DRD0_DWC3_BASE;
+static struct rockchip_usb_drd_dwc3 * const rockchip_usb_drd1_dwc3 =
+		(void *)USB_DRD1_DWC3_BASE;
+
+/* Call reset _ before setup_ */
+void reset_usb_drd0_dwc3(void);
+void reset_usb_drd1_dwc3(void);
+void setup_usb_drd0_dwc3(void);
+void setup_usb_drd1_dwc3(void);
+
+#endif /* __SOC_ROCKCHIP_RK3399_USB_H_ */
diff --git a/src/soc/rockchip/rk3399/romstage.c b/src/soc/rockchip/rk3399/romstage.c
index ae0264e..3722813 100644
--- a/src/soc/rockchip/rk3399/romstage.c
+++ b/src/soc/rockchip/rk3399/romstage.c
@@ -31,6 +31,7 @@
 #include <soc/tsadc.h>
 #include <soc/sdram.h>
 #include <symbols.h>
+#include <soc/usb.h>
 
 static const uint64_t dram_size =
 	(uint64_t)min((uint64_t)CONFIG_DRAM_SIZE_MB * MiB, MAX_DRAM_ADDRESS);
@@ -72,6 +73,16 @@ static void init_dvs_outputs(void)
 		pwm_init(i, 3333, 1904);
 }
 
+static void prepare_usb(void)
+{
+	/*
+	 * Do dwc3 core soft reset and phy reset. Kick these resets
+	 * off early so they get at least 100ms to settle.
+	 */
+	reset_usb_drd0_dwc3();
+	reset_usb_drd1_dwc3();
+}
+
 void main(void)
 {
 	console_init();
@@ -81,6 +92,8 @@ void main(void)
 	/* Init DVS to conservative values. */
 	init_dvs_outputs();
 
+	prepare_usb();
+
 	sdram_init(get_sdram_config());
 
 	mmu_config_range((void *)0, (uintptr_t)dram_size, CACHED_MEM);
diff --git a/src/soc/rockchip/rk3399/usb.c b/src/soc/rockchip/rk3399/usb.c
new file mode 100644
index 0000000..26ed5e3
--- /dev/null
+++ b/src/soc/rockchip/rk3399/usb.c
@@ -0,0 +1,107 @@
+/*
+ * This file is part of the coreboot project.
+ *
+ * Copyright (C) 2016 Rockchip, Inc.
+ *
+ * This program 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; version 2 of the License.
+ *
+ * This program 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.
+ */
+
+#include <arch/io.h>
+#include <console/console.h>
+#include <delay.h>
+#include <soc/usb.h>
+
+static void reset_dwc3(struct rockchip_usb_drd_dwc3 *dwc3_reg)
+{
+	/* Before Resetting PHY, put Core in Reset */
+	setbits_le32(&dwc3_reg->ctl, DWC3_GCTL_CORESOFTRESET);
+	/* Assert USB3 PHY reset */
+	setbits_le32(&dwc3_reg->usb3pipectl, DWC3_GUSB3PIPECTL_PHYSOFTRST);
+	/* Assert USB2 PHY reset */
+	setbits_le32(&dwc3_reg->usb2phycfg, DWC3_GUSB2PHYCFG_PHYSOFTRST);
+}
+
+static void setup_dwc3(struct rockchip_usb_drd_dwc3 *dwc3_reg)
+{
+	u32 reg;
+	u32 revision;
+	u32 dwc3_hwparams1;
+
+	/* Clear USB3 PHY reset */
+	clrbits_le32(&dwc3_reg->usb3pipectl, DWC3_GUSB3PIPECTL_PHYSOFTRST);
+	/* Clear USB2 PHY reset */
+	clrbits_le32(&dwc3_reg->usb2phycfg, DWC3_GUSB2PHYCFG_PHYSOFTRST);
+	/* After PHYs are stable we can take Core out of reset state */
+	clrbits_le32(&dwc3_reg->ctl, DWC3_GCTL_CORESOFTRESET);
+
+	revision = read32(&dwc3_reg->snpsid);
+	/* This should read as U3 followed by revision number */
+	if ((revision & DWC3_GSNPSID_MASK) != 0x55330000) {
+		printk(BIOS_ERR, "ERROR: not a DesignWare USB3 DRD Core\n");
+		return;
+	}
+
+	dwc3_hwparams1 = read32(&dwc3_reg->hwparams1);
+
+	reg = read32(&dwc3_reg->ctl);
+	reg &= ~DWC3_GCTL_SCALEDOWN_MASK;
+	reg &= ~DWC3_GCTL_DISSCRAMBLE;
+	if (DWC3_GHWPARAMS1_EN_PWROPT(dwc3_hwparams1) ==
+	    DWC3_GHWPARAMS1_EN_PWROPT_CLK)
+		reg &= ~DWC3_GCTL_DSBLCLKGTNG;
+	else
+		printk(BIOS_DEBUG, "No power optimization available\n");
+
+	write32(&dwc3_reg->ctl, reg);
+
+	/* We are hard-coding DWC3 core to Host Mode */
+	clrsetbits_le32(&dwc3_reg->ctl,
+			DWC3_GCTL_PRTCAPDIR(DWC3_GCTL_PRTCAP_OTG),
+			DWC3_GCTL_PRTCAPDIR(DWC3_GCTL_PRTCAP_HOST));
+	/*
+	 * Configure USB phy interface of DWC3 core.
+	 * For rockchip rk3399 SOC DWC3 core:
+	 * 1. Clear U2_FREECLK_EXITS.
+	 * 2. Select UTMI+ PHY with 16-bit interface.
+	 * 3. Set USBTRDTIM to the corresponding value
+	 * according to the UTMI+ PHY interface.
+	 */
+	reg = read32(&dwc3_reg->usb2phycfg);
+	reg &= ~(DWC3_GUSB2PHYCFG_U2_FREECLK_EXISTS |
+		DWC3_GUSB2PHYCFG_USB2TRDTIM_MASK |
+		DWC3_GUSB2PHYCFG_PHYIF_MASK);
+	reg |= DWC3_GUSB2PHYCFG_PHYIF(1) |
+	       DWC3_GUSB2PHYCFG_USBTRDTIM(USBTRDTIM_UTMI_16_BIT);
+	write32(&dwc3_reg->usb2phycfg, reg);
+}
+
+void reset_usb_drd0_dwc3(void)
+{
+	printk(BIOS_DEBUG, "Starting DWC3 reset for USB DRD0\n");
+	reset_dwc3(rockchip_usb_drd0_dwc3);
+}
+
+void reset_usb_drd1_dwc3(void)
+{
+	printk(BIOS_DEBUG, "Starting DWC3 reset for USB DRD1\n");
+	reset_dwc3(rockchip_usb_drd1_dwc3);
+}
+
+void setup_usb_drd0_dwc3(void)
+{
+	setup_dwc3(rockchip_usb_drd0_dwc3);
+	printk(BIOS_DEBUG, "DWC3 setup for USB DRD0 finished\n");
+}
+
+void setup_usb_drd1_dwc3(void)
+{
+	setup_dwc3(rockchip_usb_drd1_dwc3);
+	printk(BIOS_DEBUG, "DWC3 setup for USB DRD1 finished\n");
+}



More information about the coreboot-gerrit mailing list