blob: 350f286e501dc43727c2f72a171babf6ae4bc89a [file] [log] [blame]
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +05301/* ehci-msm-hsic.c - HSUSB Host Controller Driver Implementation
2 *
3 * Copyright (c) 2011, Code Aurora Forum. All rights reserved.
4 *
5 * Partly derived from ehci-fsl.c and ehci-hcd.c
6 * Copyright (c) 2000-2004 by David Brownell
7 * Copyright (c) 2005 MontaVista Software
8 *
9 * All source code in this file is licensed under the following license except
10 * where indicated.
11 *
12 * This program is free software; you can redistribute it and/or modify it
13 * under the terms of the GNU General Public License version 2 as published
14 * by the Free Software Foundation.
15 *
16 * This program is distributed in the hope that it will be useful,
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
19 *
20 * See the GNU General Public License for more details.
21 * You should have received a copy of the GNU General Public License
22 * along with this program; if not, you can find it at http://www.fsf.org
23 */
24
25#include <linux/platform_device.h>
26#include <linux/clk.h>
27#include <linux/err.h>
28#include <linux/wakelock.h>
29#include <linux/pm_runtime.h>
30#include <linux/regulator/consumer.h>
31
32#include <linux/usb/msm_hsusb_hw.h>
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +053033#include <linux/usb/msm_hsusb.h>
34#include <linux/gpio.h>
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +053035#include <mach/clk.h>
36#include <mach/msm_iomap.h>
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +053037#include <mach/msm_xo.h>
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +053038
39#define MSM_USB_BASE (hcd->regs)
40
41struct msm_hsic_hcd {
42 struct ehci_hcd ehci;
43 struct device *dev;
44 struct clk *ahb_clk;
45 struct clk *sys_clk;
46 struct clk *fs_xcvr_clk;
47 struct clk *hsic_clk;
48 struct clk *cal_clk;
49 struct regulator *hsic_vddcx;
50 bool async_int;
51 atomic_t in_lpm;
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +053052 struct msm_xo_voter *xo_handle;
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +053053 struct wake_lock wlock;
54};
55
56static inline struct msm_hsic_hcd *hcd_to_hsic(struct usb_hcd *hcd)
57{
58 return (struct msm_hsic_hcd *) (hcd->hcd_priv);
59}
60
61static inline struct usb_hcd *hsic_to_hcd(struct msm_hsic_hcd *mehci)
62{
63 return container_of((void *) mehci, struct usb_hcd, hcd_priv);
64}
65
66#define ULPI_IO_TIMEOUT_USEC (10 * 1000)
67
Vamsi Krishna45d88fa2011-11-02 13:28:42 -070068#define USB_PHY_VDD_DIG_VOL_SUSP_MIN 500000 /* uV */
69#define USB_PHY_VDD_DIG_VOL_MIN 1000000 /* uV */
70#define USB_PHY_VDD_DIG_VOL_MAX 1320000 /* uV */
71#define USB_PHY_VDD_DIG_LOAD 49360 /* uA */
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +053072
73static int msm_hsic_init_vddcx(struct msm_hsic_hcd *mehci, int init)
74{
75 int ret = 0;
76
77 if (!init)
78 goto disable_reg;
79
80 mehci->hsic_vddcx = regulator_get(mehci->dev, "HSIC_VDDCX");
81 if (IS_ERR(mehci->hsic_vddcx)) {
82 dev_err(mehci->dev, "unable to get hsic vddcx\n");
83 return PTR_ERR(mehci->hsic_vddcx);
84 }
85
86 ret = regulator_set_voltage(mehci->hsic_vddcx,
87 USB_PHY_VDD_DIG_VOL_MIN,
88 USB_PHY_VDD_DIG_VOL_MAX);
89 if (ret) {
90 dev_err(mehci->dev, "unable to set the voltage"
91 "for hsic vddcx\n");
92 goto reg_set_voltage_err;
93 }
94
95 ret = regulator_set_optimum_mode(mehci->hsic_vddcx,
96 USB_PHY_VDD_DIG_LOAD);
97 if (ret < 0) {
98 pr_err("%s: Unable to set optimum mode of the regulator:"
99 "VDDCX\n", __func__);
100 goto reg_optimum_mode_err;
101 }
102
103 ret = regulator_enable(mehci->hsic_vddcx);
104 if (ret) {
105 dev_err(mehci->dev, "unable to enable hsic vddcx\n");
106 goto reg_enable_err;
107 }
108
109 return 0;
110
111disable_reg:
112 regulator_disable(mehci->hsic_vddcx);
113reg_enable_err:
114 regulator_set_optimum_mode(mehci->hsic_vddcx, 0);
115reg_optimum_mode_err:
116 regulator_set_voltage(mehci->hsic_vddcx, 0,
117 USB_PHY_VDD_DIG_VOL_MIN);
118reg_set_voltage_err:
119 regulator_put(mehci->hsic_vddcx);
120
121 return ret;
122
123}
124
125static int ulpi_write(struct msm_hsic_hcd *mehci, u32 val, u32 reg)
126{
127 struct usb_hcd *hcd = hsic_to_hcd(mehci);
128 int cnt = 0;
129
130 /* initiate write operation */
131 writel_relaxed(ULPI_RUN | ULPI_WRITE |
132 ULPI_ADDR(reg) | ULPI_DATA(val),
133 USB_ULPI_VIEWPORT);
134
135 /* wait for completion */
136 while (cnt < ULPI_IO_TIMEOUT_USEC) {
137 if (!(readl_relaxed(USB_ULPI_VIEWPORT) & ULPI_RUN))
138 break;
139 udelay(1);
140 cnt++;
141 }
142
143 if (cnt >= ULPI_IO_TIMEOUT_USEC) {
144 dev_err(mehci->dev, "ulpi_write: timeout\n");
145 return -ETIMEDOUT;
146 }
147
148 return 0;
149}
150
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530151#define HSIC_HUB_VDD_VOL_MIN 1650000 /* uV */
152#define HSIC_HUB_VDD_VOL_MAX 1950000 /* uV */
153#define HSIC_HUB_VDD_LOAD 36000 /* uA */
154static int msm_hsic_config_hub(struct msm_hsic_hcd *mehci, int init)
155{
156 int ret = 0;
157 struct msm_hsic_host_platform_data *pdata;
158 static struct regulator *hsic_hub_reg;
159
160 pdata = mehci->dev->platform_data;
161 if (!pdata->hub_reset)
162 return ret;
163
164 if (!init)
165 goto disable_reg;
166
167 hsic_hub_reg = regulator_get(mehci->dev, "EXT_HUB_VDDIO");
168 if (IS_ERR(hsic_hub_reg)) {
169 dev_err(mehci->dev, "unable to get ext hub vddcx\n");
170 return PTR_ERR(hsic_hub_reg);
171 }
172
173 ret = gpio_request(pdata->hub_reset, "HSIC_HUB_RESET_GPIO");
174 if (ret < 0) {
175 dev_err(mehci->dev, "gpio request failed for GPIO%d\n",
176 pdata->hub_reset);
177 goto gpio_req_fail;
178 }
179
180 ret = regulator_set_voltage(hsic_hub_reg,
181 HSIC_HUB_VDD_VOL_MIN,
182 HSIC_HUB_VDD_VOL_MAX);
183 if (ret) {
184 dev_err(mehci->dev, "unable to set the voltage"
185 "for hsic hub reg\n");
186 goto reg_set_voltage_fail;
187 }
188
189 ret = regulator_set_optimum_mode(hsic_hub_reg,
190 HSIC_HUB_VDD_LOAD);
191 if (ret < 0) {
192 pr_err("%s: Unable to set optimum mode of the regulator:"
193 "VDDCX\n", __func__);
194 goto reg_optimum_mode_fail;
195 }
196
197 ret = regulator_enable(hsic_hub_reg);
198 if (ret) {
199 dev_err(mehci->dev, "unable to enable ext hub vddcx\n");
200 goto reg_enable_fail;
201 }
202
203 gpio_direction_output(pdata->hub_reset, 0);
204 /* Hub reset should be asserted for minimum 2usec before deasserting */
205 udelay(5);
206 gpio_direction_output(pdata->hub_reset, 1);
207
208 return 0;
209
210disable_reg:
211 regulator_disable(hsic_hub_reg);
212reg_enable_fail:
213 regulator_set_optimum_mode(hsic_hub_reg, 0);
214reg_optimum_mode_fail:
215 regulator_set_voltage(hsic_hub_reg, 0,
216 HSIC_HUB_VDD_VOL_MIN);
217reg_set_voltage_fail:
218 gpio_free(pdata->hub_reset);
219gpio_req_fail:
220 regulator_put(hsic_hub_reg);
221
222 return ret;
223
224}
225
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +0530226static int msm_hsic_config_gpios(struct msm_hsic_hcd *mehci, int gpio_en)
227{
228 int rc = 0;
229 struct msm_hsic_host_platform_data *pdata;
230
231 pdata = mehci->dev->platform_data;
232 /*
233 * In future versions, dedicated lines might be used for HSIC
234 * strobe and data instead of gpios. Hence returning zero value.
235 */
236 if (!pdata->strobe || !pdata->data)
237 return rc;
238
239 if (!gpio_en)
240 goto free_gpio;
241
242 rc = gpio_request(pdata->strobe, "HSIC_STROBE_GPIO");
243 if (rc < 0) {
244 dev_err(mehci->dev, "gpio request failed for HSIC STROBE\n");
245 return rc;
246 }
247
248 rc = gpio_request(pdata->data, "HSIC_DATA_GPIO");
249 if (rc < 0) {
250 dev_err(mehci->dev, "gpio request failed for HSIC DATA\n");
251 goto free_strobe;
252 }
253
254 return 0;
255
256free_gpio:
257 gpio_free(pdata->data);
258free_strobe:
259 gpio_free(pdata->strobe);
260
261 return rc;
262}
263
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530264static int msm_hsic_phy_clk_reset(struct msm_hsic_hcd *mehci)
265{
266 int ret;
267
268 clk_enable(mehci->fs_xcvr_clk);
269
270 ret = clk_reset(mehci->sys_clk, CLK_RESET_ASSERT);
271 if (ret) {
272 clk_disable(mehci->fs_xcvr_clk);
273 dev_err(mehci->dev, "usb phy clk assert failed\n");
274 return ret;
275 }
276 usleep_range(10000, 12000);
277 clk_disable(mehci->fs_xcvr_clk);
278
279 ret = clk_reset(mehci->sys_clk, CLK_RESET_DEASSERT);
280 if (ret)
281 dev_err(mehci->dev, "usb phy clk deassert failed\n");
282
283 return ret;
284}
285
286static int msm_hsic_phy_reset(struct msm_hsic_hcd *mehci)
287{
288 struct usb_hcd *hcd = hsic_to_hcd(mehci);
289 u32 val;
290 int ret;
291
292 ret = msm_hsic_phy_clk_reset(mehci);
293 if (ret)
294 return ret;
295
296 val = readl_relaxed(USB_PORTSC) & ~PORTSC_PTS_MASK;
297 writel_relaxed(val | PORTSC_PTS_ULPI, USB_PORTSC);
298
299 /* Ensure that RESET operation is completed before turning off clock */
300 mb();
301 dev_dbg(mehci->dev, "phy_reset: success\n");
302
303 return 0;
304}
305
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +0530306#define HSIC_GPIO150_PAD_CTL (MSM_TLMM_BASE+0x20C0)
307#define HSIC_GPIO151_PAD_CTL (MSM_TLMM_BASE+0x20C4)
308#define HSIC_CAL_PAD_CTL (MSM_TLMM_BASE+0x20C8)
309#define HSIC_LV_MODE 0x04
310#define HSIC_PAD_CALIBRATION 0xA8
311#define HSIC_GPIO_PAD_VAL 0x0A0AAA10
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530312#define LINK_RESET_TIMEOUT_USEC (250 * 1000)
313static int msm_hsic_reset(struct msm_hsic_hcd *mehci)
314{
315 struct usb_hcd *hcd = hsic_to_hcd(mehci);
316 int cnt = 0;
317 int ret;
318
319 ret = msm_hsic_phy_reset(mehci);
320 if (ret) {
321 dev_err(mehci->dev, "phy_reset failed\n");
322 return ret;
323 }
324
325 writel_relaxed(USBCMD_RESET, USB_USBCMD);
326 while (cnt < LINK_RESET_TIMEOUT_USEC) {
327 if (!(readl_relaxed(USB_USBCMD) & USBCMD_RESET))
328 break;
329 udelay(1);
330 cnt++;
331 }
332 if (cnt >= LINK_RESET_TIMEOUT_USEC)
333 return -ETIMEDOUT;
334
335 /* select ULPI phy */
336 writel_relaxed(0x80000000, USB_PORTSC);
337
338 /* TODO: Need to confirm if HSIC PHY also requires delay after RESET */
339 msleep(100);
340
341 /* HSIC PHY Initialization */
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +0530342 /* Enable LV_MODE in HSIC_CAL_PAD_CTL register */
343 writel_relaxed(HSIC_LV_MODE, HSIC_CAL_PAD_CTL);
344
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530345 /*set periodic calibration interval to ~2.048sec in HSIC_IO_CAL_REG */
346 ulpi_write(mehci, 0xFF, 0x33);
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +0530347
348 /* Enable periodic IO calibration in HSIC_CFG register */
349 ulpi_write(mehci, HSIC_PAD_CALIBRATION, 0x30);
350
351 /* Configure GPIO 150/151 pins for HSIC functionality mode */
352 ret = msm_hsic_config_gpios(mehci, 1);
353 if (ret) {
354 dev_err(mehci->dev, " gpio configuarion failed\n");
355 return ret;
356 }
357
358 /* Set LV_MODE=0x1 and DCC=0x2 in HSIC_GPIO150/151_PAD_CTL register */
359 writel_relaxed(HSIC_GPIO_PAD_VAL, HSIC_GPIO150_PAD_CTL);
360 writel_relaxed(HSIC_GPIO_PAD_VAL, HSIC_GPIO151_PAD_CTL);
361
362 /* Enable HSIC mode in HSIC_CFG register */
363 ulpi_write(mehci, 0x01, 0x31);
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530364
365 return 0;
366}
367
368#define PHY_SUSPEND_TIMEOUT_USEC (500 * 1000)
369#define PHY_RESUME_TIMEOUT_USEC (100 * 1000)
370
371#ifdef CONFIG_PM_SLEEP
372static int msm_hsic_suspend(struct msm_hsic_hcd *mehci)
373{
374 struct usb_hcd *hcd = hsic_to_hcd(mehci);
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530375 int cnt = 0, ret;
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530376 u32 val;
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530377 struct msm_hsic_host_platform_data *pdata;
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530378
379 if (atomic_read(&mehci->in_lpm)) {
380 dev_dbg(mehci->dev, "%s called in lpm\n", __func__);
381 return 0;
382 }
383
384 disable_irq(hcd->irq);
385 /*
386 * PHY may take some time or even fail to enter into low power
387 * mode (LPM). Hence poll for 500 msec and reset the PHY and link
388 * in failure case.
389 */
390 val = readl_relaxed(USB_PORTSC) | PORTSC_PHCD;
391 writel_relaxed(val, USB_PORTSC);
392 while (cnt < PHY_SUSPEND_TIMEOUT_USEC) {
393 if (readl_relaxed(USB_PORTSC) & PORTSC_PHCD)
394 break;
395 udelay(1);
396 cnt++;
397 }
398
399 if (cnt >= PHY_SUSPEND_TIMEOUT_USEC) {
400 dev_err(mehci->dev, "Unable to suspend PHY\n");
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +0530401 msm_hsic_config_gpios(mehci, 0);
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530402 msm_hsic_reset(mehci);
403 enable_irq(hcd->irq);
404 return -ETIMEDOUT;
405 }
406
407 /*
408 * PHY has capability to generate interrupt asynchronously in low
409 * power mode (LPM). This interrupt is level triggered. So USB IRQ
410 * line must be disabled till async interrupt enable bit is cleared
411 * in USBCMD register. Assert STP (ULPI interface STOP signal) to
412 * block data communication from PHY.
413 */
414 writel_relaxed(readl_relaxed(USB_USBCMD) | ASYNC_INTR_CTRL |
415 ULPI_STP_CTRL, USB_USBCMD);
416
417 /*
418 * Ensure that hardware is put in low power mode before
419 * clocks are turned OFF and VDD is allowed to minimize.
420 */
421 mb();
422
423 clk_disable(mehci->sys_clk);
424 clk_disable(mehci->hsic_clk);
425 clk_disable(mehci->cal_clk);
426 clk_disable(mehci->ahb_clk);
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530427 pdata = mehci->dev->platform_data;
428 if (pdata->hub_reset) {
429 ret = msm_xo_mode_vote(mehci->xo_handle, MSM_XO_MODE_OFF);
430 if (ret)
431 pr_err("%s failed to devote for"
432 "TCXO D1 buffer%d\n", __func__, ret);
433 }
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530434
Vamsi Krishna45d88fa2011-11-02 13:28:42 -0700435 ret = regulator_set_voltage(mehci->hsic_vddcx,
436 USB_PHY_VDD_DIG_VOL_SUSP_MIN,
437 USB_PHY_VDD_DIG_VOL_MAX);
438 if (ret < 0)
439 dev_err(mehci->dev, "unable to set vddcx voltage: min:0.5v max:1.3v\n");
440
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530441 atomic_set(&mehci->in_lpm, 1);
442 enable_irq(hcd->irq);
443 wake_unlock(&mehci->wlock);
444
445 dev_info(mehci->dev, "HSIC-USB in low power mode\n");
446
447 return 0;
448}
449
450static int msm_hsic_resume(struct msm_hsic_hcd *mehci)
451{
452 struct usb_hcd *hcd = hsic_to_hcd(mehci);
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530453 int cnt = 0, ret;
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530454 unsigned temp;
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530455 struct msm_hsic_host_platform_data *pdata;
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530456
457 if (!atomic_read(&mehci->in_lpm)) {
458 dev_dbg(mehci->dev, "%s called in !in_lpm\n", __func__);
459 return 0;
460 }
461
462 wake_lock(&mehci->wlock);
463
Vamsi Krishna45d88fa2011-11-02 13:28:42 -0700464 ret = regulator_set_voltage(mehci->hsic_vddcx,
465 USB_PHY_VDD_DIG_VOL_MIN,
466 USB_PHY_VDD_DIG_VOL_MAX);
467 if (ret < 0)
468 dev_err(mehci->dev, "unable to set vddcx voltage: min:1v max:1.3v\n");
469
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530470 pdata = mehci->dev->platform_data;
471 if (pdata->hub_reset) {
472 ret = msm_xo_mode_vote(mehci->xo_handle, MSM_XO_MODE_ON);
473 if (ret)
474 pr_err("%s failed to vote for"
475 "TCXO D1 buffer%d\n", __func__, ret);
476 }
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530477 clk_enable(mehci->sys_clk);
478 clk_enable(mehci->hsic_clk);
479 clk_enable(mehci->cal_clk);
480 clk_enable(mehci->ahb_clk);
481
482 temp = readl_relaxed(USB_USBCMD);
483 temp &= ~ASYNC_INTR_CTRL;
484 temp &= ~ULPI_STP_CTRL;
485 writel_relaxed(temp, USB_USBCMD);
486
487 if (!(readl_relaxed(USB_PORTSC) & PORTSC_PHCD))
488 goto skip_phy_resume;
489
490 temp = readl_relaxed(USB_PORTSC) & ~PORTSC_PHCD;
491 writel_relaxed(temp, USB_PORTSC);
492 while (cnt < PHY_RESUME_TIMEOUT_USEC) {
493 if (!(readl_relaxed(USB_PORTSC) & PORTSC_PHCD) &&
494 (readl_relaxed(USB_ULPI_VIEWPORT) & ULPI_SYNC_STATE))
495 break;
496 udelay(1);
497 cnt++;
498 }
499
500 if (cnt >= PHY_RESUME_TIMEOUT_USEC) {
501 /*
502 * This is a fatal error. Reset the link and
503 * PHY to make hsic working.
504 */
505 dev_err(mehci->dev, "Unable to resume USB. Reset the hsic\n");
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +0530506 msm_hsic_config_gpios(mehci, 0);
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530507 msm_hsic_reset(mehci);
508 }
509
510skip_phy_resume:
511
512 atomic_set(&mehci->in_lpm, 0);
513
514 if (mehci->async_int) {
515 mehci->async_int = false;
516 pm_runtime_put_noidle(mehci->dev);
517 enable_irq(hcd->irq);
518 }
519
520 dev_info(mehci->dev, "HSIC-USB exited from low power mode\n");
521
522 return 0;
523}
524#endif
525
526static irqreturn_t msm_hsic_irq(struct usb_hcd *hcd)
527{
528 struct msm_hsic_hcd *mehci = hcd_to_hsic(hcd);
529
530 if (atomic_read(&mehci->in_lpm)) {
531 disable_irq_nosync(hcd->irq);
532 mehci->async_int = true;
533 pm_runtime_get(mehci->dev);
534 return IRQ_HANDLED;
535 }
536
537 return ehci_irq(hcd);
538}
539
540static int ehci_hsic_reset(struct usb_hcd *hcd)
541{
542 struct ehci_hcd *ehci = hcd_to_ehci(hcd);
543 int retval;
544
545 ehci->caps = USB_CAPLENGTH;
546 ehci->regs = USB_CAPLENGTH +
547 HC_LENGTH(ehci, ehci_readl(ehci, &ehci->caps->hc_capbase));
548 dbg_hcs_params(ehci, "reset");
549 dbg_hcc_params(ehci, "reset");
550
551 /* cache the data to minimize the chip reads*/
552 ehci->hcs_params = ehci_readl(ehci, &ehci->caps->hcs_params);
553
554 hcd->has_tt = 1;
555 ehci->sbrn = HCD_USB2;
556
557 retval = ehci_halt(ehci);
558 if (retval)
559 return retval;
560
561 /* data structure init */
562 retval = ehci_init(hcd);
563 if (retval)
564 return retval;
565
566 retval = ehci_reset(ehci);
567 if (retval)
568 return retval;
569
570 /* bursts of unspecified length. */
571 writel_relaxed(0, USB_AHBBURST);
572 /* Use the AHB transactor */
573 writel_relaxed(0, USB_AHBMODE);
574 /* Disable streaming mode and select host mode */
575 writel_relaxed(0x13, USB_USBMODE);
576
577 ehci_port_power(ehci, 1);
578 return 0;
579}
580
581static struct hc_driver msm_hsic_driver = {
582 .description = hcd_name,
583 .product_desc = "Qualcomm EHCI Host Controller using HSIC",
584 .hcd_priv_size = sizeof(struct msm_hsic_hcd),
585
586 /*
587 * generic hardware linkage
588 */
589 .irq = msm_hsic_irq,
590 .flags = HCD_USB2 | HCD_MEMORY,
591
592 .reset = ehci_hsic_reset,
593 .start = ehci_run,
594
595 .stop = ehci_stop,
596 .shutdown = ehci_shutdown,
597
598 /*
599 * managing i/o requests and associated device resources
600 */
601 .urb_enqueue = ehci_urb_enqueue,
602 .urb_dequeue = ehci_urb_dequeue,
603 .endpoint_disable = ehci_endpoint_disable,
604 .endpoint_reset = ehci_endpoint_reset,
605 .clear_tt_buffer_complete = ehci_clear_tt_buffer_complete,
606
607 /*
608 * scheduling support
609 */
610 .get_frame_number = ehci_get_frame,
611
612 /*
613 * root hub support
614 */
615 .hub_status_data = ehci_hub_status_data,
616 .hub_control = ehci_hub_control,
617 .relinquish_port = ehci_relinquish_port,
618 .port_handed_over = ehci_port_handed_over,
619
620 /*
621 * PM support
622 */
623 .bus_suspend = ehci_bus_suspend,
624 .bus_resume = ehci_bus_resume,
625};
626
627static int msm_hsic_init_clocks(struct msm_hsic_hcd *mehci, u32 init)
628{
629 int ret = 0;
630
631 if (!init)
632 goto put_clocks;
633
634 /*sys_clk is required for LINK protocol engine,it should be at 60MHz */
635 mehci->sys_clk = clk_get(mehci->dev, "usb_hsic_system_clk");
636 if (IS_ERR(mehci->sys_clk)) {
637 dev_err(mehci->dev, "failed to get hsic_sys_clk\n");
638 ret = PTR_ERR(mehci->sys_clk);
639 return ret;
640 }
641 clk_set_rate(mehci->sys_clk, 60000000);
642
643 /* 60MHz fs_xcvr_clk is for LINK to be used during PHY RESET */
644 mehci->fs_xcvr_clk = clk_get(mehci->dev, "usb_hsic_xcvr_fs_clk");
645 if (IS_ERR(mehci->fs_xcvr_clk)) {
646 dev_err(mehci->dev, "failed to get fs_xcvr_clk\n");
647 ret = PTR_ERR(mehci->fs_xcvr_clk);
648 goto put_sys_clk;
649 }
650 clk_set_rate(mehci->fs_xcvr_clk, 60000000);
651
652 /* 480MHz hsic_clk is required for HSIC PHY operation */
653 mehci->hsic_clk = clk_get(mehci->dev, "usb_hsic_hsic_clk");
654 if (IS_ERR(mehci->hsic_clk)) {
655 dev_err(mehci->dev, "failed to get hsic_clk\n");
656 ret = PTR_ERR(mehci->hsic_clk);
657 goto put_fs_xcvr_clk;
658 }
659 clk_set_rate(mehci->hsic_clk, 480000000);
660
661 /* 10MHz cal_clk is required for calibration of I/O pads */
662 mehci->cal_clk = clk_get(mehci->dev, "usb_hsic_hsio_cal_clk");
663 if (IS_ERR(mehci->cal_clk)) {
664 dev_err(mehci->dev, "failed to get hsic_cal_clk\n");
665 ret = PTR_ERR(mehci->cal_clk);
666 goto put_hsic_clk;
667 }
668 clk_set_rate(mehci->cal_clk, 10000000);
669
670 /* ahb_clk is required for data transfers */
671 mehci->ahb_clk = clk_get(mehci->dev, "usb_hsic_p_clk");
672 if (IS_ERR(mehci->ahb_clk)) {
673 dev_err(mehci->dev, "failed to get hsic_ahb_clk\n");
674 ret = PTR_ERR(mehci->ahb_clk);
675 goto put_cal_clk;
676 }
677
678 clk_enable(mehci->sys_clk);
679 clk_enable(mehci->hsic_clk);
680 clk_enable(mehci->cal_clk);
681 clk_enable(mehci->ahb_clk);
682
683 return 0;
684
685put_clocks:
686 clk_disable(mehci->sys_clk);
687 clk_disable(mehci->hsic_clk);
688 clk_disable(mehci->cal_clk);
689 clk_disable(mehci->ahb_clk);
690 clk_put(mehci->ahb_clk);
691put_cal_clk:
692 clk_put(mehci->cal_clk);
693put_hsic_clk:
694 clk_put(mehci->hsic_clk);
695put_fs_xcvr_clk:
696 clk_put(mehci->fs_xcvr_clk);
697put_sys_clk:
698 clk_put(mehci->sys_clk);
699
700 return ret;
701}
702static int __devinit ehci_hsic_msm_probe(struct platform_device *pdev)
703{
704 struct usb_hcd *hcd;
705 struct resource *res;
706 struct msm_hsic_hcd *mehci;
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530707 struct msm_hsic_host_platform_data *pdata;
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530708 int ret;
709
710 dev_dbg(&pdev->dev, "ehci_msm-hsic probe\n");
711
712 hcd = usb_create_hcd(&msm_hsic_driver, &pdev->dev,
713 dev_name(&pdev->dev));
714 if (!hcd) {
715 dev_err(&pdev->dev, "Unable to create HCD\n");
716 return -ENOMEM;
717 }
718
719 hcd->irq = platform_get_irq(pdev, 0);
720 if (hcd->irq < 0) {
721 dev_err(&pdev->dev, "Unable to get IRQ resource\n");
722 ret = hcd->irq;
723 goto put_hcd;
724 }
725
726 res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
727 if (!res) {
728 dev_err(&pdev->dev, "Unable to get memory resource\n");
729 ret = -ENODEV;
730 goto put_hcd;
731 }
732
733 hcd->rsrc_start = res->start;
734 hcd->rsrc_len = resource_size(res);
735 hcd->regs = ioremap(hcd->rsrc_start, hcd->rsrc_len);
736 if (!hcd->regs) {
737 dev_err(&pdev->dev, "ioremap failed\n");
738 ret = -ENOMEM;
739 goto put_hcd;
740 }
741
742 mehci = hcd_to_hsic(hcd);
743 mehci->dev = &pdev->dev;
744
745 ret = msm_hsic_init_clocks(mehci, 1);
746 if (ret) {
747 dev_err(&pdev->dev, "unable to initialize clocks\n");
748 ret = -ENODEV;
749 goto unmap;
750 }
751
752 ret = msm_hsic_init_vddcx(mehci, 1);
753 if (ret) {
754 dev_err(&pdev->dev, "unable to initialize VDDCX\n");
755 ret = -ENODEV;
756 goto deinit_clocks;
757 }
758
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530759 pdata = mehci->dev->platform_data;
760 if (pdata->hub_reset) {
761 mehci->xo_handle = msm_xo_get(MSM_XO_TCXO_D1, "hsic");
762 if (IS_ERR(mehci->xo_handle)) {
763 pr_err(" %s not able to get the handle"
764 "to vote for TCXO D1 buffer\n", __func__);
765 ret = PTR_ERR(mehci->xo_handle);
766 goto deinit_vddcx;
767 }
768
769 ret = msm_xo_mode_vote(mehci->xo_handle, MSM_XO_MODE_ON);
770 if (ret) {
771 pr_err("%s failed to vote for TCXO"
772 "D1 buffer%d\n", __func__, ret);
773 goto free_xo_handle;
774 }
775 }
776
777 ret = msm_hsic_config_hub(mehci, 1);
778 if (ret) {
779 dev_err(&pdev->dev, "unable to initialize hsic hub");
780 goto free_xo_handle;
781 }
782
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530783 ret = msm_hsic_reset(mehci);
784 if (ret) {
785 dev_err(&pdev->dev, "unable to initialize PHY\n");
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530786 goto deinit_hub;
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530787 }
788
789 ret = usb_add_hcd(hcd, hcd->irq, IRQF_SHARED);
790 if (ret) {
791 dev_err(&pdev->dev, "unable to register HCD\n");
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +0530792 goto unconfig_gpio;
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530793 }
794
795 device_init_wakeup(&pdev->dev, 1);
796 wake_lock_init(&mehci->wlock, WAKE_LOCK_SUSPEND, dev_name(&pdev->dev));
797 wake_lock(&mehci->wlock);
798 /*
799 * This pdev->dev is assigned parent of root-hub by USB core,
800 * hence, runtime framework automatically calls this driver's
801 * runtime APIs based on root-hub's state.
802 */
803 pm_runtime_set_active(&pdev->dev);
804 pm_runtime_enable(&pdev->dev);
805
806 return 0;
807
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +0530808unconfig_gpio:
809 msm_hsic_config_gpios(mehci, 0);
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530810deinit_hub:
811 msm_hsic_config_hub(mehci, 0);
812free_xo_handle:
813 if (pdata->hub_reset)
814 msm_xo_put(mehci->xo_handle);
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530815deinit_vddcx:
816 msm_hsic_init_vddcx(mehci, 0);
817deinit_clocks:
818 msm_hsic_init_clocks(mehci, 0);
819unmap:
820 iounmap(hcd->regs);
821put_hcd:
822 usb_put_hcd(hcd);
823
824 return ret;
825}
826
827static int __devexit ehci_hsic_msm_remove(struct platform_device *pdev)
828{
829 struct usb_hcd *hcd = platform_get_drvdata(pdev);
830 struct msm_hsic_hcd *mehci = hcd_to_hsic(hcd);
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530831 struct msm_hsic_host_platform_data *pdata;
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530832
833 device_init_wakeup(&pdev->dev, 0);
834 pm_runtime_disable(&pdev->dev);
835 pm_runtime_set_suspended(&pdev->dev);
836
837 usb_remove_hcd(hcd);
Vijayavardhan Vennapusae3316a12011-10-15 06:05:17 +0530838 msm_hsic_config_gpios(mehci, 0);
Vijayavardhan Vennapusa2b592824f2011-11-02 19:51:32 +0530839 msm_hsic_config_hub(mehci, 0);
840 pdata = mehci->dev->platform_data;
841 if (pdata->hub_reset)
842 msm_xo_put(mehci->xo_handle);
Vijayavardhan Vennapusa39025fe2011-10-15 05:55:10 +0530843 msm_hsic_init_vddcx(mehci, 0);
844
845 msm_hsic_init_clocks(mehci, 0);
846 wake_lock_destroy(&mehci->wlock);
847 iounmap(hcd->regs);
848 usb_put_hcd(hcd);
849
850 return 0;
851}
852
853#ifdef CONFIG_PM_SLEEP
854static int msm_hsic_pm_suspend(struct device *dev)
855{
856 struct usb_hcd *hcd = dev_get_drvdata(dev);
857 struct msm_hsic_hcd *mehci = hcd_to_hsic(hcd);
858
859 dev_dbg(dev, "ehci-msm-hsic PM suspend\n");
860
861 if (device_may_wakeup(dev))
862 enable_irq_wake(hcd->irq);
863
864 return msm_hsic_suspend(mehci);
865
866}
867
868static int msm_hsic_pm_resume(struct device *dev)
869{
870 int ret;
871 struct usb_hcd *hcd = dev_get_drvdata(dev);
872 struct msm_hsic_hcd *mehci = hcd_to_hsic(hcd);
873
874 dev_dbg(dev, "ehci-msm-hsic PM resume\n");
875
876 if (device_may_wakeup(dev))
877 disable_irq_wake(hcd->irq);
878
879 ret = msm_hsic_resume(mehci);
880 if (ret)
881 return ret;
882
883 /* Bring the device to full powered state upon system resume */
884 pm_runtime_disable(dev);
885 pm_runtime_set_active(dev);
886 pm_runtime_enable(dev);
887
888 return 0;
889}
890#endif
891
892#ifdef CONFIG_PM_RUNTIME
893static int msm_hsic_runtime_idle(struct device *dev)
894{
895 dev_dbg(dev, "EHCI runtime idle\n");
896
897 return 0;
898}
899
900static int msm_hsic_runtime_suspend(struct device *dev)
901{
902 struct usb_hcd *hcd = dev_get_drvdata(dev);
903 struct msm_hsic_hcd *mehci = hcd_to_hsic(hcd);
904
905 dev_dbg(dev, "EHCI runtime suspend\n");
906 return msm_hsic_suspend(mehci);
907}
908
909static int msm_hsic_runtime_resume(struct device *dev)
910{
911 struct usb_hcd *hcd = dev_get_drvdata(dev);
912 struct msm_hsic_hcd *mehci = hcd_to_hsic(hcd);
913
914 dev_dbg(dev, "EHCI runtime resume\n");
915 return msm_hsic_resume(mehci);
916}
917#endif
918
919#ifdef CONFIG_PM
920static const struct dev_pm_ops msm_hsic_dev_pm_ops = {
921 SET_SYSTEM_SLEEP_PM_OPS(msm_hsic_pm_suspend, msm_hsic_pm_resume)
922 SET_RUNTIME_PM_OPS(msm_hsic_runtime_suspend, msm_hsic_runtime_resume,
923 msm_hsic_runtime_idle)
924};
925#endif
926
927static struct platform_driver ehci_msm_hsic_driver = {
928 .probe = ehci_hsic_msm_probe,
929 .remove = __devexit_p(ehci_hsic_msm_remove),
930 .driver = {
931 .name = "msm_hsic_host",
932#ifdef CONFIG_PM
933 .pm = &msm_hsic_dev_pm_ops,
934#endif
935 },
936};