1 /* 2 * da8xx.c - TI's DA8xx platform specific usb wrapper functions. 3 * 4 * Author: Ajay Kumar Gupta <ajay.gupta@ti.com> 5 * 6 * Based on drivers/usb/musb/davinci.c 7 * 8 * Copyright (C) 2009 Texas Instruments Incorporated 9 * 10 * This program is free software; you can redistribute it and/or modify 11 * it under the terms of the GNU General Public License as published by 12 * the Free Software Foundation; either version 2 of the License, or 13 * (at your option) any later version. 14 * 15 * This program is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU General Public License for more details. 19 * 20 * You should have received a copy of the GNU General Public License 21 * along with this program; if not, write to the Free Software 22 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 23 */ 24 #include <common.h> 25 26 #include "da8xx.h" 27 28 /* MUSB platform configuration */ 29 struct musb_config musb_cfg = { 30 .regs = (struct musb_regs *)DA8XX_USB_OTG_CORE_BASE, 31 .timeout = DA8XX_USB_OTG_TIMEOUT, 32 .musb_speed = 0, 33 }; 34 35 /* 36 * This function enables VBUS by driving the GPIO Bank4 Pin 15 high. 37 */ 38 static void enable_vbus(void) 39 { 40 u32 value; 41 42 /* configure GPIO bank4 pin 15 in output direction */ 43 value = readl(&davinci_gpio_bank45->dir); 44 writel((value & (~DA8XX_USB_VBUS_GPIO)), &davinci_gpio_bank45->dir); 45 46 /* set GPIO bank4 pin 15 high to drive VBUS */ 47 value = readl(&davinci_gpio_bank45->set_data); 48 writel((value | DA8XX_USB_VBUS_GPIO), &davinci_gpio_bank45->set_data); 49 } 50 51 /* 52 * Enable the usb0 phy. This initialization procedure is explained in 53 * the DA8xx USB user guide document. 54 */ 55 static u8 phy_on(void) 56 { 57 u32 timeout; 58 u32 cfgchip2; 59 60 cfgchip2 = readl(&davinci_syscfg_regs->cfgchip2); 61 62 cfgchip2 &= ~(CFGCHIP2_RESET | CFGCHIP2_PHYPWRDN | CFGCHIP2_OTGPWRDN | 63 CFGCHIP2_OTGMODE | CFGCHIP2_REFFREQ); 64 cfgchip2 |= CFGCHIP2_SESENDEN | CFGCHIP2_VBDTCTEN | CFGCHIP2_PHY_PLLON | 65 CFGCHIP2_REFFREQ_24MHZ; 66 67 writel(cfgchip2, &davinci_syscfg_regs->cfgchip2); 68 69 /* wait until the usb phy pll locks */ 70 timeout = musb_cfg.timeout; 71 while (timeout--) 72 if (readl(&davinci_syscfg_regs->cfgchip2) & CFGCHIP2_PHYCLKGD) 73 return 1; 74 75 /* USB phy was not turned on */ 76 return 0; 77 } 78 79 /* 80 * Disable the usb phy 81 */ 82 static void phy_off(void) 83 { 84 u32 cfgchip2; 85 86 /* 87 * Power down the on-chip PHY. 88 */ 89 cfgchip2 = readl(&davinci_syscfg_regs->cfgchip2); 90 cfgchip2 &= ~CFGCHIP2_PHY_PLLON; 91 cfgchip2 |= CFGCHIP2_PHYPWRDN | CFGCHIP2_OTGPWRDN; 92 writel(cfgchip2, &davinci_syscfg_regs->cfgchip2); 93 } 94 95 /* 96 * This function performs DA8xx platform specific initialization for usb0. 97 */ 98 int musb_platform_init(void) 99 { 100 u32 revision; 101 102 /* enable psc for usb2.0 */ 103 lpsc_on(33); 104 105 /* enable usb vbus */ 106 enable_vbus(); 107 108 /* reset the controller */ 109 writel(0x1, &da8xx_usb_regs->control); 110 udelay(5000); 111 112 /* start the on-chip usb phy and its pll */ 113 if (phy_on() == 0) 114 return -1; 115 116 /* Returns zero if e.g. not clocked */ 117 revision = readl(&da8xx_usb_regs->revision); 118 if (revision == 0) 119 return -1; 120 121 /* Disable all interrupts */ 122 writel((DA8XX_USB_USBINT_MASK | DA8XX_USB_TXINT_MASK | 123 DA8XX_USB_RXINT_MASK), &da8xx_usb_regs->intmsk_set); 124 return 0; 125 } 126 127 /* 128 * This function performs DA8xx platform specific deinitialization for usb0. 129 */ 130 void musb_platform_deinit(void) 131 { 132 /* Turn of the phy */ 133 phy_off(); 134 135 /* flush any interrupts */ 136 writel((DA8XX_USB_USBINT_MASK | DA8XX_USB_TXINT_MASK | 137 DA8XX_USB_RXINT_MASK), &da8xx_usb_regs->intmsk_clr); 138 writel(0, &da8xx_usb_regs->eoi); 139 } 140