Skip to contentSkip to conversation

usb: dwc2: Add support for USB OTG on STM32F4x9

PATCH Superseded Bruno Herrera 3 participants 8 messages Jan 17, 2017 – Jan 19, 2017

Subsystems (4)

v3 of 5 Superseded Latest is v5 →

lore
Share & tools
lore
#0 lore raw

v3 cover usb: dwc2: Add support for USB OTG on STM32F4x9

The STM32F4x9 MCU family has two DWC2 USB OTG cores on it. One core is USB OTG FS and other core is USB OTG HS. The USB FS core only works with its internal phy whilst the USF HS core can work in HS with external ulpi phy or in FS/LS speed with the embedded FS PHY.

The goal of this patch series is to enable the use of USB OTG FS/HS cores in FS mode using the internal phy.

Changes since v3:
- Removed commented lines from patch (sent by mistake)
- Split DTS patch by boards and SOC
- Removed unnecessary pinctrl nodes from DTS files

Changes since v2:
- Rename driver variables to meet the driver standard
- Add compatible string for HS core

Changes since v1:
- Add dwc2_core_params structure for stm32f4 otg fs
- Add compatible string for FS core/mode
- Use GGPIO register to deativate power down of the phy

Bruno Herrera (5):
usb: dwc2: Add support for STM32F429/439/469 USB OTG HS/FS in FS mode
(internal PHY)
ARM: dts: stm32: Add USB FS support for STM32F429 MCU
ARM: dts: stm32: Enable USB FS on stm32f469-disco
ARM: dts: stm32: Enable USB HS in FS mode (embedded phy) on

    stm32f429-disco

dt-bindings: Document the STM32 USB OTG DWC2 core binding

 Documentation/devicetree/bindings/usb/dwc2.txt |  4 ++
 arch/arm/boot/dts/stm32f429-disco.dts          | 16 ++++++++
 arch/arm/boot/dts/stm32f429.dtsi               | 31 ++++++++++++++++
 arch/arm/boot/dts/stm32f469-disco.dts          | 16 ++++++++
 drivers/usb/dwc2/core.h                        |  4 ++
 drivers/usb/dwc2/hcd.c                         | 13 ++++++-
 drivers/usb/dwc2/hw.h                          |  2 +
 drivers/usb/dwc2/params.c                      | 51 ++++++++++++++++++++++++++
 8 files changed, 136 insertions(+), 1 deletion(-)
Signature · 1 line
2.10.1 (Apple Git-78)
#1 lore raw

PATCH v3 1/5 usb: dwc2: Add support for STM32F429/439/469 USB OTG HS/FS in FS mode (internal PHY)

This patch introduces a new parameter to activate USB OTG HS/FS core embedded phy transceiver. The STM32F4x9 SoC uses the GGPIO register to enable the transceiver. Also add the dwc2_core_params structure for stm32f4 otg fs.

---
 drivers/usb/dwc2/core.h   |  4 ++++
 drivers/usb/dwc2/hcd.c    | 13 +++++++++++-
 drivers/usb/dwc2/hw.h     |  2 ++
 drivers/usb/dwc2/params.c | 51 +++++++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 69 insertions(+), 1 deletion(-)
drivers/usb/dwc2/core.h +4 -0
index 9548d3e..e3199c5 100644
@@ -430,6 +430,9 @@ enum dwc2_ep0_state {
  *			needed.
  *			0 - No (default)
  *			1 - Yes
+ * @activate_transceiver: Activate internal transceiver using GGPIO register.
+ *			0 - Deactivate the transceiver (default)
+ *			1 - Activate the transceiver
  * @g_dma:              Enables gadget dma usage (default: autodetect).
  * @g_dma_desc:         Enables gadget descriptor DMA (default: autodetect).
  * @g_rx_fifo_size:	The periodic rx fifo size for the device, in
@@ -501,6 +504,7 @@ struct dwc2_core_params {
 	int uframe_sched;
 	int external_id_pin_ctl;
 	int hibernation;
+	int activate_transceiver;
 
 	/*
 	 * The following parameters are *only* set via device
drivers/usb/dwc2/hcd.c +12 -1
index 911c3b3..6bee529 100644
@@ -118,7 +118,7 @@ static void dwc2_init_fs_ls_pclk_sel(struct dwc2_hsotg *hsotg)
 
 static int dwc2_fs_phy_init(struct dwc2_hsotg *hsotg, bool select_phy)
 {
-	u32 usbcfg, i2cctl;
+	u32 usbcfg, ggpio, i2cctl;
 	int retval = 0;
 
 	/*
@@ -142,6 +142,17 @@ static int dwc2_fs_phy_init(struct dwc2_hsotg *hsotg, bool select_phy)
 				return retval;
 			}
 		}
+
+		ggpio = dwc2_readl(hsotg->regs + GGPIO);
+		if (!(ggpio & GGPIO_STM32_OTG_GCCFG_PWRDWN) &&
+		    (hsotg->params.activate_transceiver > 0)) {
+			dev_dbg(hsotg->dev, "Activating transceiver\n");
+			/* STM32F4xx uses the GGPIO register as general core
+			 * configuration register.
+			 */
+			ggpio |= GGPIO_STM32_OTG_GCCFG_PWRDWN;
+			dwc2_writel(ggpio, hsotg->regs + GGPIO);
+		}
 	}
 
 	/*
drivers/usb/dwc2/hw.h +2 -0
index 5be056b..a84e93b 100644
@@ -225,6 +225,8 @@
 
 #define GPVNDCTL			HSOTG_REG(0x0034)
 #define GGPIO				HSOTG_REG(0x0038)
+#define GGPIO_STM32_OTG_GCCFG_PWRDWN	(1 << 16)
+
 #define GUID				HSOTG_REG(0x003c)
 #define GSNPSID				HSOTG_REG(0x0040)
 #define GHWCFG1				HSOTG_REG(0x0044)
drivers/usb/dwc2/params.c +51 -0

75 lines not on this page · raw message

Signature · 1 line
2.10.1 (Apple Git-78)
#3 lore raw

PATCH v3 2/5 ARM: dts: stm32: Add USB FS support for STM32F429 MCU

In reply to Bruno Herrera

This patch adds the USB pins and nodes for USB FS core.

---
 arch/arm/boot/dts/stm32f429.dtsi | 31 +++++++++++++++++++++++++++++++
 1 file changed, 31 insertions(+)
arch/arm/boot/dts/stm32f429.dtsi +31 -0
index e4dae0e..26f2395 100644
@@ -316,6 +316,28 @@
 				};
 			};
 
+			usbotg_fs_pins_a: usbotg_fs at 0 {
+				pins {
+					pinmux = <STM32F429_PA10_FUNC_OTG_FS_ID>,
+						 <STM32F429_PA11_FUNC_OTG_FS_DM>,
+						 <STM32F429_PA12_FUNC_OTG_FS_DP>;
+					bias-disable;
+					drive-push-pull;
+					slew-rate = <2>;
+				};
+			};
+
+			usbotg_fs_pins_b: usbotg_fs at 1 {
+				pins {
+					pinmux = <STM32F429_PB12_FUNC_OTG_HS_ID>,
+						 <STM32F429_PB14_FUNC_OTG_HS_DM>,
+						 <STM32F429_PB15_FUNC_OTG_HS_DP>;
+					bias-disable;
+					drive-push-pull;
+					slew-rate = <2>;
+				};
+			};
+
 			usbotg_hs_pins_a: usbotg_hs at 0 {
 				pins {
 					pinmux = <STM32F429_PH4_FUNC_OTG_HS_ULPI_NXT>,
@@ -420,6 +442,15 @@
 			status = "disabled";
 		};
 
+		usbotg_fs: usb at 50000000 {
+			compatible = "st,stm32f4xx-fsotg";
+			reg = <0x50000000 0x40000>;
+			interrupts = <67>;
+			clocks = <&rcc 0 39>;
+			clock-names = "otg";
+			status = "disabled";
+		};
+
 		rng: rng at 50060800 {
 			compatible = "st,stm32-rng";
 			reg = <0x50060800 0x400>;
Signature · 1 line
2.10.1 (Apple Git-78)
#4 lore raw

PATCH v3 3/5 ARM: dts: stm32: Enable USB FS on stm32f469-disco

In reply to Bruno Herrera

This patch enables USB FS on stm32f469-disco with 5V VBUS enable.

---
 arch/arm/boot/dts/stm32f469-disco.dts | 16 ++++++++++++++++
 1 file changed, 16 insertions(+)
arch/arm/boot/dts/stm32f469-disco.dts +16 -0
index 8877c00..3e0a83e 100644
@@ -68,6 +68,15 @@
 	soc {
 		dma-ranges = <0xc0000000 0x0 0x10000000>;
 	};
+
+	/* This turns on vbus for otg for host mode (dwc2) */
+	vcc5v_otg: vcc5v-otg-regulator {
+		compatible = "regulator-fixed";
+		enable-active-high;
+		gpio = <&gpiob 2 0>;
+		regulator-name = "vcc5_host1";
+		regulator-always-on;
+	};
 };
 
 &rcc {
@@ -81,3 +90,10 @@
 &usart3 {
 	status = "okay";
 };
+
+&usbotg_fs {
+	dr_mode = "host";
+	pinctrl-0 = <&usbotg_fs_pins_a>;
+	pinctrl-names = "default";
+	status = "okay";
+};
Signature · 1 line
2.10.1 (Apple Git-78)
#5 lore raw

PATCH v3 4/5 ARM: dts: stm32: Enable USB HS in FS mode (embedded phy) on stm32f429-disco

In reply to Bruno Herrera

This patch enables USB HS working in FS mode on stm32f429-disco with 5V VBUS enable.

---
 arch/arm/boot/dts/stm32f429-disco.dts | 16 ++++++++++++++++
 1 file changed, 16 insertions(+)
arch/arm/boot/dts/stm32f429-disco.dts +16 -0
index 7d0415e..0b2b017 100644
@@ -88,6 +88,14 @@
 			gpios = <&gpioa 0 0>;
 		};
 	};
+
+	/* This turns on vbus for otg for host mode (dwc2) */
+	vcc5v_otg: vcc5v-otg-regulator {
+		compatible = "regulator-fixed";
+		gpio = <&gpioc 4 0>;
+		regulator-name = "vcc5_host1";
+		regulator-always-on;
+	};
 };
 
 &clk_hse {
@@ -99,3 +107,11 @@
 	pinctrl-names = "default";
 	status = "okay";
 };
+
+&usbotg_hs {
+	compatible = "st,stm32f4xx-fsotg";
+	dr_mode = "host";
+	pinctrl-0 = <&usbotg_fs_pins_b>;
+	pinctrl-names = "default";
+	status = "okay";
+};
Signature · 1 line
2.10.1 (Apple Git-78)
#6 lore raw

PATCH v3 5/5 dt-bindings: Document the STM32 USB OTG DWC2 core binding

In reply to Bruno Herrera

This patch adds the documentation for STM32F4x9 USB OTG FS/HS compatible strings.

---
 Documentation/devicetree/bindings/usb/dwc2.txt | 4 ++++
 1 file changed, 4 insertions(+)
Documentation/devicetree/bindings/usb/dwc2.txt +4 -0
index 6c7c2bce..637223a 100644
@@ -14,6 +14,10 @@ Required properties:
   - "amlogic,meson-gxbb-usb": The DWC2 USB controller instance in Amlogic S905 SoCs;
   - "amcc,dwc-otg": The DWC2 USB controller instance in AMCC Canyonlands 460EX SoCs;
   - snps,dwc2: A generic DWC2 USB controller with default parameters.
+  - "st,stm32f4xx-fsotg": The DWC2 USB FS/HS controller instance in STM32F4xx SoCs
+  configured in FS mode;
+  - "st,stm32f4xx-hsotg": The DWC2 USB HS controller instance in STM32F4xx SoCs
+  configured in HS mode;
 - reg : Should contain 1 register range (address and length)
 - interrupts : Should contain 1 interrupt
 - clocks: clock provider specifier
Signature · 1 line
2.10.1 (Apple Git-78)
#2 lore raw

PATCH v3 1/5 usb: dwc2: Add support for STM32F429/439/469 USB OTG HS/FS in FS mode (internal PHY)

In reply to Bruno Herrera
Quoted 155 lines · Bruno Herrera

This patch introduces a new parameter to activate USB OTG HS/FS core embedded phy transceiver. The STM32F4x9 SoC uses the GGPIO register to enable the transceiver. Also add the dwc2_core_params structure for stm32f4 otg fs.

---
 drivers/usb/dwc2/core.h   |  4 ++++
 drivers/usb/dwc2/hcd.c    | 13 +++++++++++-
 drivers/usb/dwc2/hw.h     |  2 ++
 drivers/usb/dwc2/params.c | 51 +++++++++++++++++++++++++++++++++++++++++++++++
 4 files changed, 69 insertions(+), 1 deletion(-)
drivers/usb/dwc2/core.h +4 -0
index 9548d3e..e3199c5 100644
@@ -430,6 +430,9 @@ enum dwc2_ep0_state {
  *			needed.
  *			0 - No (default)
  *			1 - Yes
+ * @activate_transceiver: Activate internal transceiver using GGPIO register.
+ *			0 - Deactivate the transceiver (default)
+ *			1 - Activate the transceiver
  * @g_dma:              Enables gadget dma usage (default: autodetect).
  * @g_dma_desc:         Enables gadget descriptor DMA (default: autodetect).
  * @g_rx_fifo_size:	The periodic rx fifo size for the device, in
@@ -501,6 +504,7 @@ struct dwc2_core_params {
 	int uframe_sched;
 	int external_id_pin_ctl;
 	int hibernation;
+	int activate_transceiver;
 
 	/*
 	 * The following parameters are *only* set via device
drivers/usb/dwc2/hcd.c +12 -1
index 911c3b3..6bee529 100644
@@ -118,7 +118,7 @@ static void dwc2_init_fs_ls_pclk_sel(struct dwc2_hsotg *hsotg)
 
 static int dwc2_fs_phy_init(struct dwc2_hsotg *hsotg, bool select_phy)
 {
-	u32 usbcfg, i2cctl;
+	u32 usbcfg, ggpio, i2cctl;
 	int retval = 0;
 
 	/*
@@ -142,6 +142,17 @@ static int dwc2_fs_phy_init(struct dwc2_hsotg *hsotg, bool select_phy)
 				return retval;
 			}
 		}
+
+		ggpio = dwc2_readl(hsotg->regs + GGPIO);
+		if (!(ggpio & GGPIO_STM32_OTG_GCCFG_PWRDWN) &&
+		    (hsotg->params.activate_transceiver > 0)) {
+			dev_dbg(hsotg->dev, "Activating transceiver\n");
+			/* STM32F4xx uses the GGPIO register as general core
+			 * configuration register.
+			 */
+			ggpio |= GGPIO_STM32_OTG_GCCFG_PWRDWN;
+			dwc2_writel(ggpio, hsotg->regs + GGPIO);
+		}
 	}
 
 	/*
drivers/usb/dwc2/hw.h +2 -0
index 5be056b..a84e93b 100644
@@ -225,6 +225,8 @@
 
 #define GPVNDCTL			HSOTG_REG(0x0034)
 #define GGPIO				HSOTG_REG(0x0038)
+#define GGPIO_STM32_OTG_GCCFG_PWRDWN	(1 << 16)
+
 #define GUID				HSOTG_REG(0x003c)
 #define GSNPSID				HSOTG_REG(0x0040)
 #define GHWCFG1				HSOTG_REG(0x0044)
drivers/usb/dwc2/params.c +50 -0
index 11fe68a..dbb054d 100644
@@ -192,6 +192,37 @@ static const struct dwc2_core_params params_amlogic = {
 	.hibernation			= -1,
 };
 
+static const struct dwc2_core_params params_stm32f4_otgfs = {
+	.otg_cap			= DWC2_CAP_PARAM_NO_HNP_SRP_CAPABLE,
+	.otg_ver			= -1,
+	.dma_desc_enable		= 0,
+	.dma_desc_fs_enable		= 0,
+	.speed				= DWC2_SPEED_PARAM_FULL,
+	.enable_dynamic_fifo		= -1,
+	.en_multiple_tx_fifo		= -1,
+	.host_rx_fifo_size		= 128,	/* 128 DWORDs */
+	.host_nperio_tx_fifo_size	= 96,	/* 96 DWORDs */
+	.host_perio_tx_fifo_size	= 96,	/* 96 DWORDs */
+	.max_transfer_size		= -1,
+	.max_packet_count		= 256,
+	.host_channels			= -1,
+	.phy_type			= DWC2_PHY_TYPE_PARAM_FS,
+	.phy_utmi_width			= -1,
+	.phy_ulpi_ddr			= -1,
+	.phy_ulpi_ext_vbus		= -1,
+	.i2c_enable			= 0,
+	.ulpi_fs_ls			= -1,
+	.host_support_fs_ls_low_power	= -1,
+	.host_ls_low_power_phy_clk	= -1,
+	.ts_dline			= -1,
+	.reload_ctl			= -1,
+	.ahbcfg				= -1,
+	.uframe_sched			= 0,
+	.external_id_pin_ctl		= -1,
+	.hibernation			= -1,
+	.activate_transceiver		= 1,
+};
+
 static const struct dwc2_core_params params_default = {
 	.otg_cap			= -1,
 	.otg_ver			= -1,
@@ -240,6 +271,8 @@ const struct of_device_id dwc2_of_match_table[] = {
 	{ .compatible = "amlogic,meson8b-usb", .data = &params_amlogic },
 	{ .compatible = "amlogic,meson-gxbb-usb", .data = &params_amlogic },
 	{ .compatible = "amcc,dwc-otg", .data = NULL },
+	{ .compatible = "st,stm32f4xx-fsotg", .data = &params_stm32f4_otgfs },
+	{ .compatible = "st,stm32f4xx-hsotg", .data = NULL },
 	{},
 };
 MODULE_DEVICE_TABLE(of, dwc2_of_match_table);
@@ -1044,6 +1077,23 @@ static void dwc2_set_param_hibernation(struct dwc2_hsotg *hsotg,
 	hsotg->params.hibernation = val;
 }
 
+static void dwc2_set_param_activate_transceiver(struct dwc2_hsotg *hsotg,
+		int val)
+{
+	if (DWC2_OUT_OF_BOUNDS(val, 0, 1)) {
+		if (val >= 0) {
+			dev_err(hsotg->dev,
+				"'%d' invalid for parameter activate transceiver\n",
+				val);
+			dev_err(hsotg->dev, "activate transceiver must be 0 or 1\n");
+		}
+		val = 0;
+		dev_dbg(hsotg->dev, "Setting activate transceiver to %d\n", val);
+	}
+
+	hsotg->params.activate_transceiver = val;
+}
+
 static void dwc2_set_param_tx_fifo_sizes(struct dwc2_hsotg *hsotg)
 {
 	int i;

drivers/usb/dwc2/params.c static void dwc2_set_parameters(struct dwc2_hsotg *hsotg, · line 1214

Quoted 7 lines
drivers/usb/dwc2/params.c +1 -0
@@ -1158,6 +1208,7 @@ static void dwc2_set_parameters(struct dwc2_hsotg *hsotg,
 	dwc2_set_param_uframe_sched(hsotg, params->uframe_sched);
 	dwc2_set_param_external_id_pin_ctl(hsotg, params->external_id_pin_ctl);
 	dwc2_set_param_hibernation(hsotg, params->hibernation);
+	dwc2_set_param_activate_transceiver(hsotg, params->activate_transceiver);
 
 	/*
 	 * Set devicetree-only parameters. These parameters do not

Hi Bruno,

This will conflict with stuff we have pending for 4.11.

Can you rebase this against this series:
https://www.spinics.net/lists/linux-usb/msg152258.html

You can use this repo that has those patches applied:
https://github.com/synopsys-usb/linux.git

Thanks,
John