MXC: mach_armadillo5x0: Add USB Host support.

This add USB Host capability. The Armadillo 500 board is supplied
with two USB Host connectors driven by the USB OTG and USB Host 2
ports, through two NXP isp 1504 transceivers.

Signed-off-by: Alberto Panizzo <maramaopercheseimorto@gmail.com>
Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>

authored by Alberto Panizzo and committed by Sascha Hauer b3aa111f 17669fd6

+167
+1
arch/arm/mach-mx3/Kconfig
··· 104 104 config MACH_ARMADILLO5X0 105 105 bool "Support Atmark Armadillo-500 Development Base Board" 106 106 select ARCH_MX31 107 + select MXC_ULPI if USB_ULPI 107 108 help 108 109 Include support for Atmark Armadillo-500 platform. This includes 109 110 specific configurations for the board and its peripherals.
+166
arch/arm/mach-mx3/mach-armadillo5x0.c
··· 36 36 #include <linux/input.h> 37 37 #include <linux/gpio_keys.h> 38 38 #include <linux/i2c.h> 39 + #include <linux/usb/otg.h> 40 + #include <linux/usb/ulpi.h> 41 + #include <linux/delay.h> 39 42 40 43 #include <mach/hardware.h> 41 44 #include <asm/mach-types.h> ··· 55 52 #include <mach/ipu.h> 56 53 #include <mach/mx3fb.h> 57 54 #include <mach/mxc_nand.h> 55 + #include <mach/mxc_ehci.h> 56 + #include <mach/ulpi.h> 58 57 59 58 #include "devices.h" 60 59 #include "crm_regs.h" ··· 108 103 /* I2C2 */ 109 104 MX31_PIN_CSPI2_MOSI__SCL, 110 105 MX31_PIN_CSPI2_MISO__SDA, 106 + /* OTG */ 107 + MX31_PIN_USBOTG_DATA0__USBOTG_DATA0, 108 + MX31_PIN_USBOTG_DATA1__USBOTG_DATA1, 109 + MX31_PIN_USBOTG_DATA2__USBOTG_DATA2, 110 + MX31_PIN_USBOTG_DATA3__USBOTG_DATA3, 111 + MX31_PIN_USBOTG_DATA4__USBOTG_DATA4, 112 + MX31_PIN_USBOTG_DATA5__USBOTG_DATA5, 113 + MX31_PIN_USBOTG_DATA6__USBOTG_DATA6, 114 + MX31_PIN_USBOTG_DATA7__USBOTG_DATA7, 115 + MX31_PIN_USBOTG_CLK__USBOTG_CLK, 116 + MX31_PIN_USBOTG_DIR__USBOTG_DIR, 117 + MX31_PIN_USBOTG_NXT__USBOTG_NXT, 118 + MX31_PIN_USBOTG_STP__USBOTG_STP, 119 + /* USB host 2 */ 120 + IOMUX_MODE(MX31_PIN_USBH2_CLK, IOMUX_CONFIG_FUNC), 121 + IOMUX_MODE(MX31_PIN_USBH2_DIR, IOMUX_CONFIG_FUNC), 122 + IOMUX_MODE(MX31_PIN_USBH2_NXT, IOMUX_CONFIG_FUNC), 123 + IOMUX_MODE(MX31_PIN_USBH2_STP, IOMUX_CONFIG_FUNC), 124 + IOMUX_MODE(MX31_PIN_USBH2_DATA0, IOMUX_CONFIG_FUNC), 125 + IOMUX_MODE(MX31_PIN_USBH2_DATA1, IOMUX_CONFIG_FUNC), 126 + IOMUX_MODE(MX31_PIN_STXD3, IOMUX_CONFIG_FUNC), 127 + IOMUX_MODE(MX31_PIN_SRXD3, IOMUX_CONFIG_FUNC), 128 + IOMUX_MODE(MX31_PIN_SCK3, IOMUX_CONFIG_FUNC), 129 + IOMUX_MODE(MX31_PIN_SFS3, IOMUX_CONFIG_FUNC), 130 + IOMUX_MODE(MX31_PIN_STXD6, IOMUX_CONFIG_FUNC), 131 + IOMUX_MODE(MX31_PIN_SRXD6, IOMUX_CONFIG_FUNC), 111 132 }; 133 + 134 + /* USB */ 135 + #if defined(CONFIG_USB_ULPI) 136 + 137 + #define OTG_RESET IOMUX_TO_GPIO(MX31_PIN_STXD4) 138 + #define USBH2_RESET IOMUX_TO_GPIO(MX31_PIN_SCK6) 139 + #define USBH2_CS IOMUX_TO_GPIO(MX31_PIN_GPIO1_3) 140 + 141 + #define USB_PAD_CFG (PAD_CTL_DRV_MAX | PAD_CTL_SRE_FAST | PAD_CTL_HYS_CMOS | \ 142 + PAD_CTL_ODE_CMOS | PAD_CTL_100K_PU) 143 + 144 + static int usbotg_init(struct platform_device *pdev) 145 + { 146 + int err; 147 + 148 + mxc_iomux_set_pad(MX31_PIN_USBOTG_DATA0, USB_PAD_CFG); 149 + mxc_iomux_set_pad(MX31_PIN_USBOTG_DATA1, USB_PAD_CFG); 150 + mxc_iomux_set_pad(MX31_PIN_USBOTG_DATA2, USB_PAD_CFG); 151 + mxc_iomux_set_pad(MX31_PIN_USBOTG_DATA3, USB_PAD_CFG); 152 + mxc_iomux_set_pad(MX31_PIN_USBOTG_DATA4, USB_PAD_CFG); 153 + mxc_iomux_set_pad(MX31_PIN_USBOTG_DATA5, USB_PAD_CFG); 154 + mxc_iomux_set_pad(MX31_PIN_USBOTG_DATA6, USB_PAD_CFG); 155 + mxc_iomux_set_pad(MX31_PIN_USBOTG_DATA7, USB_PAD_CFG); 156 + mxc_iomux_set_pad(MX31_PIN_USBOTG_CLK, USB_PAD_CFG); 157 + mxc_iomux_set_pad(MX31_PIN_USBOTG_DIR, USB_PAD_CFG); 158 + mxc_iomux_set_pad(MX31_PIN_USBOTG_NXT, USB_PAD_CFG); 159 + mxc_iomux_set_pad(MX31_PIN_USBOTG_STP, USB_PAD_CFG); 160 + 161 + /* Chip already enabled by hardware */ 162 + /* OTG phy reset*/ 163 + err = gpio_request(OTG_RESET, "USB-OTG-RESET"); 164 + if (err) { 165 + pr_err("Failed to request the usb otg reset gpio\n"); 166 + return err; 167 + } 168 + 169 + err = gpio_direction_output(OTG_RESET, 1/*HIGH*/); 170 + if (err) { 171 + pr_err("Failed to reset the usb otg phy\n"); 172 + goto otg_free_reset; 173 + } 174 + 175 + gpio_set_value(OTG_RESET, 0/*LOW*/); 176 + mdelay(5); 177 + gpio_set_value(OTG_RESET, 1/*HIGH*/); 178 + 179 + return 0; 180 + 181 + otg_free_reset: 182 + gpio_free(OTG_RESET); 183 + return err; 184 + } 185 + 186 + static int usbh2_init(struct platform_device *pdev) 187 + { 188 + int err; 189 + 190 + mxc_iomux_set_pad(MX31_PIN_USBH2_CLK, USB_PAD_CFG); 191 + mxc_iomux_set_pad(MX31_PIN_USBH2_DIR, USB_PAD_CFG); 192 + mxc_iomux_set_pad(MX31_PIN_USBH2_NXT, USB_PAD_CFG); 193 + mxc_iomux_set_pad(MX31_PIN_USBH2_STP, USB_PAD_CFG); 194 + mxc_iomux_set_pad(MX31_PIN_USBH2_DATA0, USB_PAD_CFG); 195 + mxc_iomux_set_pad(MX31_PIN_USBH2_DATA1, USB_PAD_CFG); 196 + mxc_iomux_set_pad(MX31_PIN_SRXD6, USB_PAD_CFG); 197 + mxc_iomux_set_pad(MX31_PIN_STXD6, USB_PAD_CFG); 198 + mxc_iomux_set_pad(MX31_PIN_SFS3, USB_PAD_CFG); 199 + mxc_iomux_set_pad(MX31_PIN_SCK3, USB_PAD_CFG); 200 + mxc_iomux_set_pad(MX31_PIN_SRXD3, USB_PAD_CFG); 201 + mxc_iomux_set_pad(MX31_PIN_STXD3, USB_PAD_CFG); 202 + 203 + mxc_iomux_set_gpr(MUX_PGP_UH2, true); 204 + 205 + 206 + /* Enable the chip */ 207 + err = gpio_request(USBH2_CS, "USB-H2-CS"); 208 + if (err) { 209 + pr_err("Failed to request the usb host 2 CS gpio\n"); 210 + return err; 211 + } 212 + 213 + err = gpio_direction_output(USBH2_CS, 0/*Enabled*/); 214 + if (err) { 215 + pr_err("Failed to drive the usb host 2 CS gpio\n"); 216 + goto h2_free_cs; 217 + } 218 + 219 + /* H2 phy reset*/ 220 + err = gpio_request(USBH2_RESET, "USB-H2-RESET"); 221 + if (err) { 222 + pr_err("Failed to request the usb host 2 reset gpio\n"); 223 + goto h2_free_cs; 224 + } 225 + 226 + err = gpio_direction_output(USBH2_RESET, 1/*HIGH*/); 227 + if (err) { 228 + pr_err("Failed to reset the usb host 2 phy\n"); 229 + goto h2_free_reset; 230 + } 231 + 232 + gpio_set_value(USBH2_RESET, 0/*LOW*/); 233 + mdelay(5); 234 + gpio_set_value(USBH2_RESET, 1/*HIGH*/); 235 + 236 + return 0; 237 + 238 + h2_free_reset: 239 + gpio_free(USBH2_RESET); 240 + h2_free_cs: 241 + gpio_free(USBH2_CS); 242 + return err; 243 + } 244 + 245 + static struct mxc_usbh_platform_data usbotg_pdata = { 246 + .init = usbotg_init, 247 + .portsc = MXC_EHCI_MODE_ULPI | MXC_EHCI_UTMI_8BIT, 248 + .flags = MXC_EHCI_POWER_PINS_ENABLED | MXC_EHCI_INTERFACE_DIFF_UNI, 249 + }; 250 + 251 + static struct mxc_usbh_platform_data usbh2_pdata = { 252 + .init = usbh2_init, 253 + .portsc = MXC_EHCI_MODE_ULPI | MXC_EHCI_UTMI_8BIT, 254 + .flags = MXC_EHCI_POWER_PINS_ENABLED | MXC_EHCI_INTERFACE_DIFF_UNI, 255 + }; 256 + #endif /* CONFIG_USB_ULPI */ 112 257 113 258 /* RTC over I2C*/ 114 259 #define ARMADILLO5X0_RTC_GPIO IOMUX_TO_GPIO(MX31_PIN_SRXD4) ··· 548 393 if (armadillo5x0_i2c_rtc.irq == 0) 549 394 pr_warning("armadillo5x0_init: failed to get RTC IRQ\n"); 550 395 i2c_register_board_info(1, &armadillo5x0_i2c_rtc, 1); 396 + 397 + /* USB */ 398 + #if defined(CONFIG_USB_ULPI) 399 + usbotg_pdata.otg = otg_ulpi_create(&mxc_ulpi_access_ops, 400 + USB_OTG_DRV_VBUS | USB_OTG_DRV_VBUS_EXT); 401 + usbh2_pdata.otg = otg_ulpi_create(&mxc_ulpi_access_ops, 402 + USB_OTG_DRV_VBUS | USB_OTG_DRV_VBUS_EXT); 403 + 404 + mxc_register_device(&mxc_otg_host, &usbotg_pdata); 405 + mxc_register_device(&mxc_usbh2, &usbh2_pdata); 406 + #endif 551 407 } 552 408 553 409 static void __init armadillo5x0_timer_init(void)