1// SPDX-License-Identifier: GPL-2.0
2/*
3 * Texas Instruments DSPS platforms "glue layer"
4 *
5 * Copyright (C) 2012, by Texas Instruments
6 *
7 * Based on the am35x "glue layer" code.
8 *
9 * This file is part of the Inventra Controller Driver for Linux.
10 *
11 * musb_dsps.c will be a common file for all the TI DSPS platforms
12 * such as dm64x, dm36x, dm35x, da8x, am35x and ti81x.
13 * For now only ti81x is using this and in future davinci.c, am35x.c
14 * da8xx.c would be merged to this file after testing.
15 */
16
17#ifndef __UBOOT__
18#include <dm/device_compat.h>
19#include <dm/devres.h>
20#include <linux/init.h>
21#include <linux/io.h>
22#include <linux/err.h>
23#include <linux/platform_device.h>
24#include <linux/dma-mapping.h>
25#include <linux/pm_runtime.h>
26#include <linux/module.h>
27
28#include <linux/of.h>
29#include <linux/of_device.h>
30#include <linux/of_address.h>
31
32#include <plat/usb.h>
33#else
34#include <common.h>
35#include <dm.h>
36#include <dm/device_compat.h>
37#include <asm/omap_musb.h>
38#include <linux/printk.h>
39#include "linux-compat.h"
40#endif
41
42#include "musb_core.h"
43
44/**
45 * avoid using musb_readx()/musb_writex() as glue layer should not be
46 * dependent on musb core layer symbols.
47 */
48static inline u8 dsps_readb(const void __iomem *addr, unsigned offset)
49	{ return __raw_readb(addr + offset); }
50
51static inline u32 dsps_readl(const void __iomem *addr, unsigned offset)
52	{ return __raw_readl(addr + offset); }
53
54static inline void dsps_writeb(void __iomem *addr, unsigned offset, u8 data)
55	{ __raw_writeb(data, addr + offset); }
56
57static inline void dsps_writel(void __iomem *addr, unsigned offset, u32 data)
58	{ __raw_writel(data, addr + offset); }
59
60/**
61 * DSPS musb wrapper register offset.
62 * FIXME: This should be expanded to have all the wrapper registers from TI DSPS
63 * musb ips.
64 */
65struct dsps_musb_wrapper {
66	u16	revision;
67	u16	control;
68	u16	status;
69	u16	eoi;
70	u16	epintr_set;
71	u16	epintr_clear;
72	u16	epintr_status;
73	u16	coreintr_set;
74	u16	coreintr_clear;
75	u16	coreintr_status;
76	u16	phy_utmi;
77	u16	mode;
78
79	/* bit positions for control */
80	unsigned	reset:5;
81
82	/* bit positions for interrupt */
83	unsigned	usb_shift:5;
84	u32		usb_mask;
85	u32		usb_bitmap;
86	unsigned	drvvbus:5;
87
88	unsigned	txep_shift:5;
89	u32		txep_mask;
90	u32		txep_bitmap;
91
92	unsigned	rxep_shift:5;
93	u32		rxep_mask;
94	u32		rxep_bitmap;
95
96	/* bit positions for phy_utmi */
97	unsigned	otg_disable:5;
98
99	/* bit positions for mode */
100	unsigned	iddig:5;
101	/* miscellaneous stuff */
102	u32		musb_core_offset;
103	u8		poll_seconds;
104};
105
106static const struct dsps_musb_wrapper ti81xx_driver_data __devinitconst = {
107	.revision		= 0x00,
108	.control		= 0x14,
109	.status			= 0x18,
110	.eoi			= 0x24,
111	.epintr_set		= 0x38,
112	.epintr_clear		= 0x40,
113	.epintr_status		= 0x30,
114	.coreintr_set		= 0x3c,
115	.coreintr_clear		= 0x44,
116	.coreintr_status	= 0x34,
117	.phy_utmi		= 0xe0,
118	.mode			= 0xe8,
119	.reset			= 0,
120	.otg_disable		= 21,
121	.iddig			= 8,
122	.usb_shift		= 0,
123	.usb_mask		= 0x1ff,
124	.usb_bitmap		= (0x1ff << 0),
125	.drvvbus		= 8,
126	.txep_shift		= 0,
127	.txep_mask		= 0xffff,
128	.txep_bitmap		= (0xffff << 0),
129	.rxep_shift		= 16,
130	.rxep_mask		= 0xfffe,
131	.rxep_bitmap		= (0xfffe << 16),
132	.musb_core_offset	= 0x400,
133	.poll_seconds		= 2,
134};
135
136/**
137 * DSPS glue structure.
138 */
139struct dsps_glue {
140	struct device *dev;
141	struct platform_device *musb;	/* child musb pdev */
142	const struct dsps_musb_wrapper *wrp; /* wrapper register offsets */
143	struct timer_list timer;	/* otg_workaround timer */
144};
145
146/**
147 * dsps_musb_enable - enable interrupts
148 */
149#ifndef __UBOOT__
150static void dsps_musb_enable(struct musb *musb)
151#else
152static int dsps_musb_enable(struct musb *musb)
153#endif
154{
155#ifndef __UBOOT__
156	struct device *dev = musb->controller;
157	struct platform_device *pdev = to_platform_device(dev->parent);
158	struct dsps_glue *glue = platform_get_drvdata(pdev);
159	const struct dsps_musb_wrapper *wrp = glue->wrp;
160#else
161	const struct dsps_musb_wrapper *wrp = &ti81xx_driver_data;
162#endif
163	void __iomem *reg_base = musb->ctrl_base;
164	u32 epmask, coremask;
165
166	/* Workaround: setup IRQs through both register sets. */
167	epmask = ((musb->epmask & wrp->txep_mask) << wrp->txep_shift) |
168	       ((musb->epmask & wrp->rxep_mask) << wrp->rxep_shift);
169	coremask = (wrp->usb_bitmap & ~MUSB_INTR_SOF);
170
171	dsps_writel(reg_base, wrp->epintr_set, epmask);
172	dsps_writel(reg_base, wrp->coreintr_set, coremask);
173	/* Force the DRVVBUS IRQ so we can start polling for ID change. */
174#ifndef __UBOOT__
175	if (is_otg_enabled(musb))
176		dsps_writel(reg_base, wrp->coreintr_set,
177			    (1 << wrp->drvvbus) << wrp->usb_shift);
178#else
179	return 0;
180#endif
181}
182
183/**
184 * dsps_musb_disable - disable HDRC and flush interrupts
185 */
186static void dsps_musb_disable(struct musb *musb)
187{
188#ifndef __UBOOT__
189	struct device *dev = musb->controller;
190	struct platform_device *pdev = to_platform_device(dev->parent);
191	struct dsps_glue *glue = platform_get_drvdata(pdev);
192	const struct dsps_musb_wrapper *wrp = glue->wrp;
193	void __iomem *reg_base = musb->ctrl_base;
194
195	dsps_writel(reg_base, wrp->coreintr_clear, wrp->usb_bitmap);
196	dsps_writel(reg_base, wrp->epintr_clear,
197			 wrp->txep_bitmap | wrp->rxep_bitmap);
198	dsps_writeb(musb->mregs, MUSB_DEVCTL, 0);
199	dsps_writel(reg_base, wrp->eoi, 0);
200#endif
201}
202
203#ifndef __UBOOT__
204static void otg_timer(unsigned long _musb)
205{
206	struct musb *musb = (void *)_musb;
207	void __iomem *mregs = musb->mregs;
208	struct device *dev = musb->controller;
209	struct platform_device *pdev = to_platform_device(dev->parent);
210	struct dsps_glue *glue = platform_get_drvdata(pdev);
211	const struct dsps_musb_wrapper *wrp = glue->wrp;
212	u8 devctl;
213	unsigned long flags;
214
215	/*
216	 * We poll because DSPS IP's won't expose several OTG-critical
217	 * status change events (from the transceiver) otherwise.
218	 */
219	devctl = dsps_readb(mregs, MUSB_DEVCTL);
220	dev_dbg(musb->controller, "Poll devctl %02x (%s)\n", devctl,
221				otg_state_string(musb->xceiv->state));
222
223	spin_lock_irqsave(&musb->lock, flags);
224	switch (musb->xceiv->state) {
225	case OTG_STATE_A_WAIT_BCON:
226		devctl &= ~MUSB_DEVCTL_SESSION;
227		dsps_writeb(musb->mregs, MUSB_DEVCTL, devctl);
228
229		devctl = dsps_readb(musb->mregs, MUSB_DEVCTL);
230		if (devctl & MUSB_DEVCTL_BDEVICE) {
231			musb->xceiv->state = OTG_STATE_B_IDLE;
232			MUSB_DEV_MODE(musb);
233		} else {
234			musb->xceiv->state = OTG_STATE_A_IDLE;
235			MUSB_HST_MODE(musb);
236		}
237		break;
238	case OTG_STATE_A_WAIT_VFALL:
239		musb->xceiv->state = OTG_STATE_A_WAIT_VRISE;
240		dsps_writel(musb->ctrl_base, wrp->coreintr_set,
241			    MUSB_INTR_VBUSERROR << wrp->usb_shift);
242		break;
243	case OTG_STATE_B_IDLE:
244		if (!is_peripheral_enabled(musb))
245			break;
246
247		devctl = dsps_readb(mregs, MUSB_DEVCTL);
248		if (devctl & MUSB_DEVCTL_BDEVICE)
249			mod_timer(&glue->timer,
250					jiffies + wrp->poll_seconds * HZ);
251		else
252			musb->xceiv->state = OTG_STATE_A_IDLE;
253		break;
254	default:
255		break;
256	}
257	spin_unlock_irqrestore(&musb->lock, flags);
258}
259
260static void dsps_musb_try_idle(struct musb *musb, unsigned long timeout)
261{
262	struct device *dev = musb->controller;
263	struct platform_device *pdev = to_platform_device(dev->parent);
264	struct dsps_glue *glue = platform_get_drvdata(pdev);
265	static unsigned long last_timer;
266
267	if (!is_otg_enabled(musb))
268		return;
269
270	if (timeout == 0)
271		timeout = jiffies + msecs_to_jiffies(3);
272
273	/* Never idle if active, or when VBUS timeout is not set as host */
274	if (musb->is_active || (musb->a_wait_bcon == 0 &&
275				musb->xceiv->state == OTG_STATE_A_WAIT_BCON)) {
276		dev_dbg(musb->controller, "%s active, deleting timer\n",
277				otg_state_string(musb->xceiv->state));
278		del_timer(&glue->timer);
279		last_timer = jiffies;
280		return;
281	}
282
283	if (time_after(last_timer, timeout) && timer_pending(&glue->timer)) {
284		dev_dbg(musb->controller,
285			"Longer idle timer already pending, ignoring...\n");
286		return;
287	}
288	last_timer = timeout;
289
290	dev_dbg(musb->controller, "%s inactive, starting idle timer for %u ms\n",
291		otg_state_string(musb->xceiv->state),
292			jiffies_to_msecs(timeout - jiffies));
293	mod_timer(&glue->timer, timeout);
294}
295#endif
296
297static irqreturn_t dsps_interrupt(int irq, void *hci)
298{
299	struct musb  *musb = hci;
300	void __iomem *reg_base = musb->ctrl_base;
301#ifndef __UBOOT__
302	struct device *dev = musb->controller;
303	struct platform_device *pdev = to_platform_device(dev->parent);
304	struct dsps_glue *glue = platform_get_drvdata(pdev);
305	const struct dsps_musb_wrapper *wrp = glue->wrp;
306#else
307	const struct dsps_musb_wrapper *wrp = &ti81xx_driver_data;
308#endif
309	unsigned long flags;
310	irqreturn_t ret = IRQ_NONE;
311	u32 epintr, usbintr;
312
313	spin_lock_irqsave(&musb->lock, flags);
314
315	/* Get endpoint interrupts */
316	epintr = dsps_readl(reg_base, wrp->epintr_status);
317	musb->int_rx = (epintr & wrp->rxep_bitmap) >> wrp->rxep_shift;
318	musb->int_tx = (epintr & wrp->txep_bitmap) >> wrp->txep_shift;
319
320	if (epintr)
321		dsps_writel(reg_base, wrp->epintr_status, epintr);
322
323	/* Get usb core interrupts */
324	usbintr = dsps_readl(reg_base, wrp->coreintr_status);
325	if (!usbintr && !epintr)
326		goto eoi;
327
328	musb->int_usb =	(usbintr & wrp->usb_bitmap) >> wrp->usb_shift;
329	if (usbintr)
330		dsps_writel(reg_base, wrp->coreintr_status, usbintr);
331
332	dev_dbg(musb->controller, "usbintr (%x) epintr(%x)\n",
333			usbintr, epintr);
334#ifndef __UBOOT__
335	/*
336	 * DRVVBUS IRQs are the only proxy we have (a very poor one!) for
337	 * DSPS IP's missing ID change IRQ.  We need an ID change IRQ to
338	 * switch appropriately between halves of the OTG state machine.
339	 * Managing DEVCTL.SESSION per Mentor docs requires that we know its
340	 * value but DEVCTL.BDEVICE is invalid without DEVCTL.SESSION set.
341	 * Also, DRVVBUS pulses for SRP (but not at 5V) ...
342	 */
343	if ((usbintr & MUSB_INTR_BABBLE) && is_host_enabled(musb))
344		pr_info("CAUTION: musb: Babble Interrupt Occurred\n");
345
346	if (usbintr & ((1 << wrp->drvvbus) << wrp->usb_shift)) {
347		int drvvbus = dsps_readl(reg_base, wrp->status);
348		void __iomem *mregs = musb->mregs;
349		u8 devctl = dsps_readb(mregs, MUSB_DEVCTL);
350		int err;
351
352		err = is_host_enabled(musb) && (musb->int_usb &
353						MUSB_INTR_VBUSERROR);
354		if (err) {
355			/*
356			 * The Mentor core doesn't debounce VBUS as needed
357			 * to cope with device connect current spikes. This
358			 * means it's not uncommon for bus-powered devices
359			 * to get VBUS errors during enumeration.
360			 *
361			 * This is a workaround, but newer RTL from Mentor
362			 * seems to allow a better one: "re"-starting sessions
363			 * without waiting for VBUS to stop registering in
364			 * devctl.
365			 */
366			musb->int_usb &= ~MUSB_INTR_VBUSERROR;
367			musb->xceiv->state = OTG_STATE_A_WAIT_VFALL;
368			mod_timer(&glue->timer,
369					jiffies + wrp->poll_seconds * HZ);
370			WARNING("VBUS error workaround (delay coming)\n");
371		} else if (is_host_enabled(musb) && drvvbus) {
372			musb->is_active = 1;
373			MUSB_HST_MODE(musb);
374			musb->xceiv->otg->default_a = 1;
375			musb->xceiv->state = OTG_STATE_A_WAIT_VRISE;
376			del_timer(&glue->timer);
377		} else {
378			musb->is_active = 0;
379			MUSB_DEV_MODE(musb);
380			musb->xceiv->otg->default_a = 0;
381			musb->xceiv->state = OTG_STATE_B_IDLE;
382		}
383
384		/* NOTE: this must complete power-on within 100 ms. */
385		dev_dbg(musb->controller, "VBUS %s (%s)%s, devctl %02x\n",
386				drvvbus ? "on" : "off",
387				otg_state_string(musb->xceiv->state),
388				err ? " ERROR" : "",
389				devctl);
390		ret = IRQ_HANDLED;
391	}
392#endif
393
394	if (musb->int_tx || musb->int_rx || musb->int_usb)
395		ret |= musb_interrupt(musb);
396
397 eoi:
398	/* EOI needs to be written for the IRQ to be re-asserted. */
399	if (ret == IRQ_HANDLED || epintr || usbintr)
400		dsps_writel(reg_base, wrp->eoi, 1);
401
402#ifndef __UBOOT__
403	/* Poll for ID change */
404	if (is_otg_enabled(musb) && musb->xceiv->state == OTG_STATE_B_IDLE)
405		mod_timer(&glue->timer, jiffies + wrp->poll_seconds * HZ);
406#endif
407
408	spin_unlock_irqrestore(&musb->lock, flags);
409
410	return ret;
411}
412
413static int dsps_musb_init(struct musb *musb)
414{
415#ifndef __UBOOT__
416	struct device *dev = musb->controller;
417	struct musb_hdrc_platform_data *plat = dev->platform_data;
418	struct platform_device *pdev = to_platform_device(dev->parent);
419	struct dsps_glue *glue = platform_get_drvdata(pdev);
420	const struct dsps_musb_wrapper *wrp = glue->wrp;
421	struct omap_musb_board_data *data = plat->board_data;
422#else
423	struct omap_musb_board_data *data =
424			(struct omap_musb_board_data *)musb->controller;
425	const struct dsps_musb_wrapper *wrp = &ti81xx_driver_data;
426#endif
427	void __iomem *reg_base = musb->ctrl_base;
428	u32 rev, val;
429	int status;
430
431	/* mentor core register starts at offset of 0x400 from musb base */
432	musb->mregs += wrp->musb_core_offset;
433
434#ifndef __UBOOT__
435	/* NOP driver needs change if supporting dual instance */
436	usb_nop_xceiv_register();
437	musb->xceiv = usb_get_phy(USB_PHY_TYPE_USB2);
438	if (IS_ERR_OR_NULL(musb->xceiv))
439		return -ENODEV;
440#endif
441
442	/* Returns zero if e.g. not clocked */
443	rev = dsps_readl(reg_base, wrp->revision);
444	if (!rev) {
445		status = -ENODEV;
446		goto err0;
447	}
448
449#ifndef __UBOOT__
450	if (is_host_enabled(musb))
451		setup_timer(&glue->timer, otg_timer, (unsigned long) musb);
452#endif
453
454	/* Reset the musb */
455	dsps_writel(reg_base, wrp->control, (1 << wrp->reset));
456
457	/* Start the on-chip PHY and its PLL. */
458	if (data && data->set_phy_power)
459		data->set_phy_power(data->dev, 1);
460
461	musb->isr = dsps_interrupt;
462
463	/* reset the otgdisable bit, needed for host mode to work */
464	val = dsps_readl(reg_base, wrp->phy_utmi);
465	val &= ~(1 << wrp->otg_disable);
466	dsps_writel(musb->ctrl_base, wrp->phy_utmi, val);
467
468	/* clear level interrupt */
469	dsps_writel(reg_base, wrp->eoi, 0);
470
471	return 0;
472err0:
473#ifndef __UBOOT__
474	usb_put_phy(musb->xceiv);
475	usb_nop_xceiv_unregister();
476#endif
477	return status;
478}
479
480static int dsps_musb_exit(struct musb *musb)
481{
482#ifndef __UBOOT__
483	struct device *dev = musb->controller;
484	struct musb_hdrc_platform_data *plat = dev->platform_data;
485	struct omap_musb_board_data *data = plat->board_data;
486	struct platform_device *pdev = to_platform_device(dev->parent);
487	struct dsps_glue *glue = platform_get_drvdata(pdev);
488#else
489	struct omap_musb_board_data *data =
490			(struct omap_musb_board_data *)musb->controller;
491#endif
492
493#ifndef __UBOOT__
494	if (is_host_enabled(musb))
495		del_timer_sync(&glue->timer);
496#endif
497
498	/* Shutdown the on-chip PHY and its PLL. */
499	if (data && data->set_phy_power)
500		data->set_phy_power(data->dev, 0);
501
502#ifndef __UBOOT__
503	/* NOP driver needs change if supporting dual instance */
504	usb_put_phy(musb->xceiv);
505	usb_nop_xceiv_unregister();
506#endif
507
508	return 0;
509}
510
511#ifndef __UBOOT__
512static struct musb_platform_ops dsps_ops = {
513#else
514struct musb_platform_ops musb_dsps_ops = {
515#endif
516	.init		= dsps_musb_init,
517	.exit		= dsps_musb_exit,
518
519	.enable		= dsps_musb_enable,
520	.disable	= dsps_musb_disable,
521
522#ifndef __UBOOT__
523	.try_idle	= dsps_musb_try_idle,
524#endif
525};
526
527#ifndef __UBOOT__
528static u64 musb_dmamask = DMA_BIT_MASK(32);
529#endif
530
531#ifndef __UBOOT__
532static int __devinit dsps_create_musb_pdev(struct dsps_glue *glue, u8 id)
533{
534	struct device *dev = glue->dev;
535	struct platform_device *pdev = to_platform_device(dev);
536	struct musb_hdrc_platform_data  *pdata = dev->platform_data;
537	struct platform_device	*musb;
538	struct resource *res;
539	struct resource	resources[2];
540	char res_name[10];
541	int ret;
542
543	/* get memory resource */
544	sprintf(res_name, "musb%d", id);
545	res = platform_get_resource_byname(pdev, IORESOURCE_MEM, res_name);
546	if (!res) {
547		dev_err(dev, "%s get mem resource failed\n", res_name);
548		ret = -ENODEV;
549		goto err0;
550	}
551	res->parent = NULL;
552	resources[0] = *res;
553
554	/* get irq resource */
555	sprintf(res_name, "musb%d-irq", id);
556	res = platform_get_resource_byname(pdev, IORESOURCE_IRQ, res_name);
557	if (!res) {
558		dev_err(dev, "%s get irq resource failed\n", res_name);
559		ret = -ENODEV;
560		goto err0;
561	}
562	res->parent = NULL;
563	resources[1] = *res;
564	resources[1].name = "mc";
565
566	/* allocate the child platform device */
567	musb = platform_device_alloc("musb-hdrc", -1);
568	if (!musb) {
569		dev_err(dev, "failed to allocate musb device\n");
570		ret = -ENOMEM;
571		goto err0;
572	}
573
574	musb->dev.parent		= dev;
575	musb->dev.dma_mask		= &musb_dmamask;
576	musb->dev.coherent_dma_mask	= musb_dmamask;
577
578	glue->musb			= musb;
579
580	pdata->platform_ops		= &dsps_ops;
581
582	ret = platform_device_add_resources(musb, resources, 2);
583	if (ret) {
584		dev_err(dev, "failed to add resources\n");
585		goto err1;
586	}
587
588	ret = platform_device_add_data(musb, pdata, sizeof(*pdata));
589	if (ret) {
590		dev_err(dev, "failed to add platform_data\n");
591		goto err1;
592	}
593
594	ret = platform_device_add(musb);
595	if (ret) {
596		dev_err(dev, "failed to register musb device\n");
597		goto err1;
598	}
599
600	return 0;
601
602err1:
603	platform_device_put(musb);
604err0:
605	return ret;
606}
607
608static void __devexit dsps_delete_musb_pdev(struct dsps_glue *glue)
609{
610	platform_device_del(glue->musb);
611	platform_device_put(glue->musb);
612}
613
614static int __devinit dsps_probe(struct platform_device *pdev)
615{
616	const struct platform_device_id *id = platform_get_device_id(pdev);
617	const struct dsps_musb_wrapper *wrp =
618				(struct dsps_musb_wrapper *)id->driver_data;
619	struct dsps_glue *glue;
620	struct resource *iomem;
621	int ret;
622
623	/* allocate glue */
624	glue = kzalloc(sizeof(*glue), GFP_KERNEL);
625	if (!glue) {
626		dev_err(&pdev->dev, "unable to allocate glue memory\n");
627		ret = -ENOMEM;
628		goto err0;
629	}
630
631	/* get memory resource */
632	iomem = platform_get_resource(pdev, IORESOURCE_MEM, 0);
633	if (!iomem) {
634		dev_err(&pdev->dev, "failed to get usbss mem resource\n");
635		ret = -ENODEV;
636		goto err1;
637	}
638
639	glue->dev = &pdev->dev;
640
641	glue->wrp = kmemdup(wrp, sizeof(*wrp), GFP_KERNEL);
642	if (!glue->wrp) {
643		dev_err(&pdev->dev, "failed to duplicate wrapper struct memory\n");
644		ret = -ENOMEM;
645		goto err1;
646	}
647	platform_set_drvdata(pdev, glue);
648
649	/* enable the usbss clocks */
650	pm_runtime_enable(&pdev->dev);
651
652	ret = pm_runtime_get_sync(&pdev->dev);
653	if (ret < 0) {
654		dev_err(&pdev->dev, "pm_runtime_get_sync FAILED");
655		goto err2;
656	}
657
658	/* create the child platform device for first instances of musb */
659	ret = dsps_create_musb_pdev(glue, 0);
660	if (ret != 0) {
661		dev_err(&pdev->dev, "failed to create child pdev\n");
662		goto err3;
663	}
664
665	return 0;
666
667err3:
668	pm_runtime_put(&pdev->dev);
669err2:
670	pm_runtime_disable(&pdev->dev);
671	kfree(glue->wrp);
672err1:
673	kfree(glue);
674err0:
675	return ret;
676}
677static int __devexit dsps_remove(struct platform_device *pdev)
678{
679	struct dsps_glue *glue = platform_get_drvdata(pdev);
680
681	/* delete the child platform device */
682	dsps_delete_musb_pdev(glue);
683
684	/* disable usbss clocks */
685	pm_runtime_put(&pdev->dev);
686	pm_runtime_disable(&pdev->dev);
687	kfree(glue->wrp);
688	kfree(glue);
689	return 0;
690}
691
692#ifdef CONFIG_PM_SLEEP
693static int dsps_suspend(struct device *dev)
694{
695	struct musb_hdrc_platform_data *plat = dev->platform_data;
696	struct omap_musb_board_data *data = plat->board_data;
697
698	/* Shutdown the on-chip PHY and its PLL. */
699	if (data && data->set_phy_power)
700		data->set_phy_power(data->dev, 0);
701
702	return 0;
703}
704
705static int dsps_resume(struct device *dev)
706{
707	struct musb_hdrc_platform_data *plat = dev->platform_data;
708	struct omap_musb_board_data *data = plat->board_data;
709
710	/* Start the on-chip PHY and its PLL. */
711	if (data && data->set_phy_power)
712		data->set_phy_power(data->dev, 1);
713
714	return 0;
715}
716#endif
717
718static SIMPLE_DEV_PM_OPS(dsps_pm_ops, dsps_suspend, dsps_resume);
719#endif
720
721#ifndef __UBOOT__
722static const struct platform_device_id musb_dsps_id_table[] __devinitconst = {
723	{
724		.name	= "musb-ti81xx",
725		.driver_data	= (kernel_ulong_t) &ti81xx_driver_data,
726	},
727	{  },	/* Terminating Entry */
728};
729MODULE_DEVICE_TABLE(platform, musb_dsps_id_table);
730
731static const struct of_device_id musb_dsps_of_match[] __devinitconst = {
732	{ .compatible = "musb-ti81xx", },
733	{ .compatible = "ti,ti81xx-musb", },
734	{ .compatible = "ti,am335x-musb", },
735	{  },
736};
737MODULE_DEVICE_TABLE(of, musb_dsps_of_match);
738
739static struct platform_driver dsps_usbss_driver = {
740	.probe		= dsps_probe,
741	.remove         = __devexit_p(dsps_remove),
742	.driver         = {
743		.name   = "musb-dsps",
744		.pm	= &dsps_pm_ops,
745		.of_match_table	= musb_dsps_of_match,
746	},
747	.id_table	= musb_dsps_id_table,
748};
749
750MODULE_DESCRIPTION("TI DSPS MUSB Glue Layer");
751MODULE_AUTHOR("Ravi B <ravibabu@ti.com>");
752MODULE_AUTHOR("Ajay Kumar Gupta <ajay.gupta@ti.com>");
753MODULE_LICENSE("GPL v2");
754
755static int __init dsps_init(void)
756{
757	return platform_driver_register(&dsps_usbss_driver);
758}
759subsys_initcall(dsps_init);
760
761static void __exit dsps_exit(void)
762{
763	platform_driver_unregister(&dsps_usbss_driver);
764}
765module_exit(dsps_exit);
766#endif
767