linux-arm-kernel.lists.infradead.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v2 0/3] Support Samsung Exynos OHCI device and driver
@ 2011-12-06  6:30 Jingoo Han
  2011-12-06  6:31 ` [PATCH v2 1/3] ARM: EXYNOS: Add USB OHCI device Jingoo Han
                   ` (2 more replies)
  0 siblings, 3 replies; 6+ messages in thread
From: Jingoo Han @ 2011-12-06  6:30 UTC (permalink / raw)
  To: linux-arm-kernel

Hello.

This patch series adds USB OHCI device and initial driver for Samsung
Exynos SoCs and is based from linux-samsung for-next branch.
I have tested on SMDKV310 board using EXYNOS4.

Thanks.

Jingoo Han (3) :
       ARM: EXYNOS: Add USB OHCI device
	   ARM: EXYNOS: Add USB OHCI support to SMDKV310 board
	   USB: Add Samsung Exynos OHCI diver

Changes since v1:
	- Replace ohci-s5p with ohci-exynos
	- Check phy control

^ permalink raw reply	[flat|nested] 6+ messages in thread

* [PATCH v2 1/3] ARM: EXYNOS: Add USB OHCI device
  2011-12-06  6:30 [PATCH v2 0/3] Support Samsung Exynos OHCI device and driver Jingoo Han
@ 2011-12-06  6:31 ` Jingoo Han
  2011-12-06  9:13   ` Tushar Behera
  2011-12-06  6:32 ` [PATCH v2 2/3] ARM: EXYNOS: Add USB OHCI support to SMDKV310 board Jingoo Han
  2011-12-06  6:32 ` [PATCH v2 3/3] USB: Add Samsung Exynos OHCI diver Jingoo Han
  2 siblings, 1 reply; 6+ messages in thread
From: Jingoo Han @ 2011-12-06  6:31 UTC (permalink / raw)
  To: linux-arm-kernel

This patch adds USB ohci device definition for Exynos SoCs.

Signed-off-by: Jingoo Han <jg1.han@samsung.com>
---
 arch/arm/mach-exynos/Kconfig              |    5 +++
 arch/arm/mach-exynos/Makefile             |    1 +
 arch/arm/mach-exynos/dev-ohci.c           |   52 +++++++++++++++++++++++++++++
 arch/arm/mach-exynos/include/mach/map.h   |    1 +
 arch/arm/mach-exynos/include/mach/ohci.h  |   21 +++++++++++
 arch/arm/mach-exynos/setup-usb-phy.c      |   15 ++++++++
 arch/arm/plat-samsung/include/plat/devs.h |    1 +
 7 files changed, 96 insertions(+), 0 deletions(-)
 create mode 100644 arch/arm/mach-exynos/dev-ohci.c
 create mode 100644 arch/arm/mach-exynos/include/mach/ohci.h

diff --git a/arch/arm/mach-exynos/Kconfig b/arch/arm/mach-exynos/Kconfig
index 0afcc3b..dec3ee3 100644
--- a/arch/arm/mach-exynos/Kconfig
+++ b/arch/arm/mach-exynos/Kconfig
@@ -87,6 +87,11 @@ config EXYNOS4_DEV_DWMCI
 	help
 	  Compile in platform device definitions for DWMCI
 
+config EXYNOS4_DEV_USB_OHCI
+	bool
+	help
+	  Compile in platform device definition for USB OHCI
+
 config EXYNOS4_SETUP_I2C1
 	bool
 	help
diff --git a/arch/arm/mach-exynos/Makefile b/arch/arm/mach-exynos/Makefile
index 57e5296..a81a1c1 100644
--- a/arch/arm/mach-exynos/Makefile
+++ b/arch/arm/mach-exynos/Makefile
@@ -46,6 +46,7 @@ obj-$(CONFIG_EXYNOS4_DEV_AHCI)		+= dev-ahci.o
 obj-$(CONFIG_EXYNOS4_DEV_PD)		+= dev-pd.o
 obj-$(CONFIG_EXYNOS4_DEV_SYSMMU)	+= dev-sysmmu.o
 obj-$(CONFIG_EXYNOS4_DEV_DWMCI)		+= dev-dwmci.o
+obj-$(CONFIG_EXYNOS4_DEV_USB_OHCI)	+= dev-ohci.o
 obj-$(CONFIG_EXYNOS4_DEV_DMA)		+= dma.o
 
 obj-$(CONFIG_EXYNOS4_SETUP_FIMC)	+= setup-fimc.o
diff --git a/arch/arm/mach-exynos/dev-ohci.c b/arch/arm/mach-exynos/dev-ohci.c
new file mode 100644
index 0000000..b8e7530
--- /dev/null
+++ b/arch/arm/mach-exynos/dev-ohci.c
@@ -0,0 +1,52 @@
+/* linux/arch/arm/mach-exynos/dev-ohci.c
+ *
+ * Copyright (c) 2011 Samsung Electronics Co., Ltd.
+ *		http://www.samsung.com
+ *
+ * EXYNOS - OHCI support
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+
+#include <linux/dma-mapping.h>
+#include <linux/platform_device.h>
+
+#include <mach/irqs.h>
+#include <mach/map.h>
+#include <mach/ohci.h>
+
+#include <plat/devs.h>
+#include <plat/usb-phy.h>
+
+static struct resource exynos4_ohci_resource[] = {
+	[0] = DEFINE_RES_MEM(EXYNOS4_PA_OHCI, SZ_256),
+	[1] = DEFINE_RES_IRQ(IRQ_USB_HOST),
+};
+
+static u64 exynos4_ohci_dma_mask = DMA_BIT_MASK(32);
+
+struct platform_device exynos4_device_ohci = {
+	.name		= "exynos-ohci",
+	.id		= -1,
+	.num_resources	= ARRAY_SIZE(exynos4_ohci_resource),
+	.resource	= exynos4_ohci_resource,
+	.dev		= {
+		.dma_mask		= &exynos4_ohci_dma_mask,
+		.coherent_dma_mask	= DMA_BIT_MASK(32),
+	}
+};
+
+void __init exynos4_ohci_set_platdata(struct exynos4_ohci_platdata *pd)
+{
+	struct exynos4_ohci_platdata *npd;
+
+	npd = s3c_set_platdata(pd, sizeof(struct exynos4_ohci_platdata),
+			&exynos4_device_ohci);
+
+	if (!npd->phy_init)
+		npd->phy_init = s5p_usb_phy_init;
+	if (!npd->phy_exit)
+		npd->phy_exit = s5p_usb_phy_exit;
+}
diff --git a/arch/arm/mach-exynos/include/mach/map.h b/arch/arm/mach-exynos/include/mach/map.h
index 03e2c99..a9897b4 100644
--- a/arch/arm/mach-exynos/include/mach/map.h
+++ b/arch/arm/mach-exynos/include/mach/map.h
@@ -108,6 +108,7 @@
 #define EXYNOS4_PA_SROMC		0x12570000
 
 #define EXYNOS4_PA_EHCI			0x12580000
+#define EXYNOS4_PA_OHCI			0x12590000
 #define EXYNOS4_PA_HSPHY		0x125B0000
 #define EXYNOS4_PA_MFC			0x13400000
 
diff --git a/arch/arm/mach-exynos/include/mach/ohci.h b/arch/arm/mach-exynos/include/mach/ohci.h
new file mode 100644
index 0000000..c256c59
--- /dev/null
+++ b/arch/arm/mach-exynos/include/mach/ohci.h
@@ -0,0 +1,21 @@
+/*
+ * Copyright (C) 2011 Samsung Electronics Co.Ltd
+ *		http://www.samsung.com/
+ *
+ * This program is free software; you can redistribute  it and/or modify it
+ * under  the terms of  the GNU General  Public License as published by the
+ * Free Software Foundation;  either version 2 of the  License, or (at your
+ * option) any later version.
+ */
+
+#ifndef __MACH_EXYNOS_OHCI_H
+#define __MACH_EXYNOS_OHCI_H
+
+struct exynos4_ohci_platdata {
+	int (*phy_init)(struct platform_device *pdev, int type);
+	int (*phy_exit)(struct platform_device *pdev, int type);
+};
+
+extern void exynos4_ohci_set_platdata(struct exynos4_ohci_platdata *pd);
+
+#endif /* __MACH_EXYNOS_OHCI_H */
diff --git a/arch/arm/mach-exynos/setup-usb-phy.c b/arch/arm/mach-exynos/setup-usb-phy.c
index 39aca04..41743d2 100644
--- a/arch/arm/mach-exynos/setup-usb-phy.c
+++ b/arch/arm/mach-exynos/setup-usb-phy.c
@@ -19,6 +19,13 @@
 #include <plat/cpu.h>
 #include <plat/usb-phy.h>
 
+static atomic_t host_usage;
+
+static int exynos4_usb_host_phy_is_on(void)
+{
+	return (readl(EXYNOS4_PHYPWR) & PHY1_STD_ANALOG_POWERDOWN) ? 0 : 1;
+}
+
 static int exynos4_usb_phy1_init(struct platform_device *pdev)
 {
 	struct clk *otg_clk;
@@ -27,6 +34,8 @@ static int exynos4_usb_phy1_init(struct platform_device *pdev)
 	u32 rstcon;
 	int err;
 
+	atomic_inc(&host_usage);
+
 	otg_clk = clk_get(&pdev->dev, "otg");
 	if (IS_ERR(otg_clk)) {
 		dev_err(&pdev->dev, "Failed to get otg clock\n");
@@ -39,6 +48,9 @@ static int exynos4_usb_phy1_init(struct platform_device *pdev)
 		return err;
 	}
 
+	if (exynos4_usb_host_phy_is_on())
+		return 0;
+
 	writel(readl(S5P_USBHOST_PHY_CONTROL) | S5P_USBHOST_PHY_ENABLE,
 			S5P_USBHOST_PHY_CONTROL);
 
@@ -95,6 +107,9 @@ static int exynos4_usb_phy1_exit(struct platform_device *pdev)
 	struct clk *otg_clk;
 	int err;
 
+	if (atomic_dec_return(&host_usage) > 0)
+		return 0;
+
 	otg_clk = clk_get(&pdev->dev, "otg");
 	if (IS_ERR(otg_clk)) {
 		dev_err(&pdev->dev, "Failed to get otg clock\n");
diff --git a/arch/arm/plat-samsung/include/plat/devs.h b/arch/arm/plat-samsung/include/plat/devs.h
index ab633c9..a2ff27e 100644
--- a/arch/arm/plat-samsung/include/plat/devs.h
+++ b/arch/arm/plat-samsung/include/plat/devs.h
@@ -129,6 +129,7 @@ extern struct platform_device exynos4_device_dwmci;
 extern struct platform_device exynos4_device_i2s0;
 extern struct platform_device exynos4_device_i2s1;
 extern struct platform_device exynos4_device_i2s2;
+extern struct platform_device exynos4_device_ohci;
 extern struct platform_device exynos4_device_pcm0;
 extern struct platform_device exynos4_device_pcm1;
 extern struct platform_device exynos4_device_pcm2;
-- 
1.7.1

^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH v2 2/3] ARM: EXYNOS: Add USB OHCI support to SMDKV310 board
  2011-12-06  6:30 [PATCH v2 0/3] Support Samsung Exynos OHCI device and driver Jingoo Han
  2011-12-06  6:31 ` [PATCH v2 1/3] ARM: EXYNOS: Add USB OHCI device Jingoo Han
@ 2011-12-06  6:32 ` Jingoo Han
  2011-12-06  6:32 ` [PATCH v2 3/3] USB: Add Samsung Exynos OHCI diver Jingoo Han
  2 siblings, 0 replies; 6+ messages in thread
From: Jingoo Han @ 2011-12-06  6:32 UTC (permalink / raw)
  To: linux-arm-kernel

This patch adds USB OHCI support to SMDKV310 board.

Signed-off-by: Jingoo Han <jg1.han@samsung.com>
---
 arch/arm/mach-exynos/Kconfig         |    1 +
 arch/arm/mach-exynos/mach-smdkv310.c |   13 +++++++++++++
 2 files changed, 14 insertions(+), 0 deletions(-)

diff --git a/arch/arm/mach-exynos/Kconfig b/arch/arm/mach-exynos/Kconfig
index dec3ee3..bd1bb9f 100644
--- a/arch/arm/mach-exynos/Kconfig
+++ b/arch/arm/mach-exynos/Kconfig
@@ -190,6 +190,7 @@ config MACH_SMDKV310
 	select EXYNOS4_DEV_DMA
 	select EXYNOS4_DEV_PD
 	select SAMSUNG_DEV_PWM
+	select EXYNOS4_DEV_USB_OHCI
 	select EXYNOS4_DEV_SYSMMU
 	select EXYNOS4_SETUP_FIMD0
 	select EXYNOS4_SETUP_I2C1
diff --git a/arch/arm/mach-exynos/mach-smdkv310.c b/arch/arm/mach-exynos/mach-smdkv310.c
index cec2afa..25a5a40 100644
--- a/arch/arm/mach-exynos/mach-smdkv310.c
+++ b/arch/arm/mach-exynos/mach-smdkv310.c
@@ -42,6 +42,7 @@
 #include <plat/clock.h>
 
 #include <mach/map.h>
+#include <mach/ohci.h>
 
 /* Following are default values for UCON, ULCON and UFCON UART registers */
 #define SMDKV310_UCON_DEFAULT	(S3C2410_UCON_TXILEVEL |	\
@@ -245,6 +246,16 @@ static void __init smdkv310_ehci_init(void)
 	s5p_ehci_set_platdata(pdata);
 }
 
+/* USB OHCI */
+static struct exynos4_ohci_platdata smdkv310_ohci_pdata;
+
+static void __init smdkv310_ohci_init(void)
+{
+	struct exynos4_ohci_platdata *pdata = &smdkv310_ohci_pdata;
+
+	exynos4_ohci_set_platdata(pdata);
+}
+
 static struct platform_device *smdkv310_devices[] __initdata = {
 	&s3c_device_hsmmc0,
 	&s3c_device_hsmmc1,
@@ -261,6 +272,7 @@ static struct platform_device *smdkv310_devices[] __initdata = {
 	&s5p_device_fimc3,
 	&exynos4_device_ac97,
 	&exynos4_device_i2s0,
+	&exynos4_device_ohci,
 	&samsung_device_keypad,
 	&s5p_device_mfc,
 	&s5p_device_mfc_l,
@@ -363,6 +375,7 @@ static void __init smdkv310_machine_init(void)
 	s5p_fimd0_set_platdata(&smdkv310_lcd0_pdata);
 
 	smdkv310_ehci_init();
+	smdkv310_ohci_init();
 	clk_xusbxti.rate = 24000000;
 
 	platform_add_devices(smdkv310_devices, ARRAY_SIZE(smdkv310_devices));
-- 
1.7.1

^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH v2 3/3] USB: Add Samsung Exynos OHCI diver
  2011-12-06  6:30 [PATCH v2 0/3] Support Samsung Exynos OHCI device and driver Jingoo Han
  2011-12-06  6:31 ` [PATCH v2 1/3] ARM: EXYNOS: Add USB OHCI device Jingoo Han
  2011-12-06  6:32 ` [PATCH v2 2/3] ARM: EXYNOS: Add USB OHCI support to SMDKV310 board Jingoo Han
@ 2011-12-06  6:32 ` Jingoo Han
  2 siblings, 0 replies; 6+ messages in thread
From: Jingoo Han @ 2011-12-06  6:32 UTC (permalink / raw)
  To: linux-arm-kernel

This patch adds USB OHCI driver for Samsung Exynos SoCs.

Signed-off-by: Jingoo Han <jg1.han@samsung.com>
---
 drivers/usb/Kconfig            |    1 +
 drivers/usb/host/Kconfig       |    6 +
 drivers/usb/host/ohci-exynos.c |  274 ++++++++++++++++++++++++++++++++++++++++
 drivers/usb/host/ohci-hcd.c    |    5 +
 4 files changed, 286 insertions(+), 0 deletions(-)
 create mode 100644 drivers/usb/host/ohci-exynos.c

diff --git a/drivers/usb/Kconfig b/drivers/usb/Kconfig
index 791f11b..75823a1 100644
--- a/drivers/usb/Kconfig
+++ b/drivers/usb/Kconfig
@@ -48,6 +48,7 @@ config USB_ARCH_HAS_OHCI
 	default y if ARCH_DAVINCI_DA8XX
 	default y if ARCH_CNS3XXX
 	default y if PLAT_SPEAR
+	default y if ARCH_EXYNOS
 	# PPC:
 	default y if STB03xxx
 	default y if PPC_MPC52xx
diff --git a/drivers/usb/host/Kconfig b/drivers/usb/host/Kconfig
index 060e0e2..eea85dc 100644
--- a/drivers/usb/host/Kconfig
+++ b/drivers/usb/host/Kconfig
@@ -371,6 +371,12 @@ config USB_OHCI_SH
 	  Enables support for the on-chip OHCI controller on the SuperH.
 	  If you use the PCI OHCI controller, this option is not necessary.
 
+config USB_OHCI_EXYNOS
+	boolean "OHCI support for Samsung EXYNOS SoC Series"
+	depends on USB_OHCI_HCD && ARCH_EXYNOS
+	help
+	 Enable support for the Samsung Exynos SOC's on-chip OHCI controller.
+
 config USB_CNS3XXX_OHCI
 	bool "Cavium CNS3XXX OHCI Module"
 	depends on USB_OHCI_HCD && ARCH_CNS3XXX
diff --git a/drivers/usb/host/ohci-exynos.c b/drivers/usb/host/ohci-exynos.c
new file mode 100644
index 0000000..55aa35a
--- /dev/null
+++ b/drivers/usb/host/ohci-exynos.c
@@ -0,0 +1,274 @@
+/*
+ * SAMSUNG EXYNOS USB HOST OHCI Controller
+ *
+ * Copyright (C) 2011 Samsung Electronics Co.Ltd
+ * Author: Jingoo Han <jg1.han@samsung.com>
+ *
+ * This program is free software; you can redistribute  it and/or modify it
+ * under  the terms of  the GNU General  Public License as published by the
+ * Free Software Foundation;  either version 2 of the  License, or (at your
+ * option) any later version.
+ *
+ */
+
+#include <linux/clk.h>
+#include <linux/platform_device.h>
+#include <mach/ohci.h>
+#include <plat/usb-phy.h>
+
+struct exynos_ohci_hcd {
+	struct device *dev;
+	struct usb_hcd *hcd;
+	struct clk *clk;
+};
+
+static int ohci_exynos_start(struct usb_hcd *hcd)
+{
+	struct ohci_hcd *ohci = hcd_to_ohci(hcd);
+	int ret;
+
+	ohci_dbg(ohci, "ohci_exynos_start, ohci:%p", ohci);
+
+	ret = ohci_init(ohci);
+	if (ret < 0)
+		return ret;
+
+	ret = ohci_run(ohci);
+	if (ret < 0) {
+		err("can't start %s", hcd->self.bus_name);
+		ohci_stop(hcd);
+		return ret;
+	}
+
+	return 0;
+}
+
+static const struct hc_driver exynos_ohci_hc_driver = {
+	.description		= hcd_name,
+	.product_desc		= "EXYNOS OHCI Host Controller",
+	.hcd_priv_size		= sizeof(struct ohci_hcd),
+
+	.irq			= ohci_irq,
+	.flags			= HCD_MEMORY|HCD_USB11,
+
+	.start			= ohci_exynos_start,
+	.stop			= ohci_stop,
+	.shutdown		= ohci_shutdown,
+
+	.get_frame_number	= ohci_get_frame,
+
+	.urb_enqueue		= ohci_urb_enqueue,
+	.urb_dequeue		= ohci_urb_dequeue,
+	.endpoint_disable	= ohci_endpoint_disable,
+
+	.hub_status_data	= ohci_hub_status_data,
+	.hub_control		= ohci_hub_control,
+#ifdef	CONFIG_PM
+	.bus_suspend		= ohci_bus_suspend,
+	.bus_resume		= ohci_bus_resume,
+#endif
+	.start_port_reset	= ohci_start_port_reset,
+};
+
+static int __devinit exynos_ohci_probe(struct platform_device *pdev)
+{
+	struct exynos4_ohci_platdata *pdata;
+	struct exynos_ohci_hcd *exynos_ohci;
+	struct usb_hcd *hcd;
+	struct ohci_hcd *ohci;
+	struct resource *res;
+	int irq;
+	int err;
+
+	pdata = pdev->dev.platform_data;
+	if (!pdata) {
+		dev_err(&pdev->dev, "No platform data defined\n");
+		return -EINVAL;
+	}
+
+	exynos_ohci = kzalloc(sizeof(struct exynos_ohci_hcd), GFP_KERNEL);
+	if (!exynos_ohci)
+		return -ENOMEM;
+
+	exynos_ohci->dev = &pdev->dev;
+
+	hcd = usb_create_hcd(&exynos_ohci_hc_driver, &pdev->dev,
+					dev_name(&pdev->dev));
+	if (!hcd) {
+		dev_err(&pdev->dev, "Unable to create HCD\n");
+		err = -ENOMEM;
+		goto fail_hcd;
+	}
+
+	exynos_ohci->hcd = hcd;
+	exynos_ohci->clk = clk_get(&pdev->dev, "usbhost");
+
+	if (IS_ERR(exynos_ohci->clk)) {
+		dev_err(&pdev->dev, "Failed to get usbhost clock\n");
+		err = PTR_ERR(exynos_ohci->clk);
+		goto fail_clk;
+	}
+
+	err = clk_enable(exynos_ohci->clk);
+	if (err)
+		goto fail_clken;
+
+	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
+	if (!res) {
+		dev_err(&pdev->dev, "Failed to get I/O memory\n");
+		err = -ENXIO;
+		goto fail_io;
+	}
+
+	hcd->rsrc_start = res->start;
+	hcd->rsrc_len = resource_size(res);
+	hcd->regs = ioremap(res->start, resource_size(res));
+	if (!hcd->regs) {
+		dev_err(&pdev->dev, "Failed to remap I/O memory\n");
+		err = -ENOMEM;
+		goto fail_io;
+	}
+
+	irq = platform_get_irq(pdev, 0);
+	if (!irq) {
+		dev_err(&pdev->dev, "Failed to get IRQ\n");
+		err = -ENODEV;
+		goto fail;
+	}
+
+	if (pdata->phy_init)
+		pdata->phy_init(pdev, S5P_USB_PHY_HOST);
+
+	ohci = hcd_to_ohci(hcd);
+	ohci_hcd_init(ohci);
+
+	err = usb_add_hcd(hcd, irq, IRQF_SHARED);
+	if (err) {
+		dev_err(&pdev->dev, "Failed to add USB HCD\n");
+		goto fail;
+	}
+
+	platform_set_drvdata(pdev, exynos_ohci);
+
+	return 0;
+
+fail:
+	iounmap(hcd->regs);
+fail_io:
+	clk_disable(exynos_ohci->clk);
+fail_clken:
+	clk_put(exynos_ohci->clk);
+fail_clk:
+	usb_put_hcd(hcd);
+fail_hcd:
+	kfree(exynos_ohci);
+	return err;
+}
+
+static int __devexit exynos_ohci_remove(struct platform_device *pdev)
+{
+	struct exynos4_ohci_platdata *pdata = pdev->dev.platform_data;
+	struct exynos_ohci_hcd *exynos_ohci = platform_get_drvdata(pdev);
+	struct usb_hcd *hcd = exynos_ohci->hcd;
+
+	usb_remove_hcd(hcd);
+
+	if (pdata && pdata->phy_exit)
+		pdata->phy_exit(pdev, S5P_USB_PHY_HOST);
+
+	iounmap(hcd->regs);
+
+	clk_disable(exynos_ohci->clk);
+	clk_put(exynos_ohci->clk);
+
+	usb_put_hcd(hcd);
+	kfree(exynos_ohci);
+
+	return 0;
+}
+
+static void exynos_ohci_shutdown(struct platform_device *pdev)
+{
+	struct exynos_ohci_hcd *exynos_ohci = platform_get_drvdata(pdev);
+	struct usb_hcd *hcd = exynos_ohci->hcd;
+
+	if (hcd->driver->shutdown)
+		hcd->driver->shutdown(hcd);
+}
+
+#ifdef CONFIG_PM
+static int exynos_ohci_suspend(struct device *dev)
+{
+	struct exynos_ohci_hcd *exynos_ohci = dev_get_drvdata(dev);
+	struct usb_hcd *hcd = exynos_ohci->hcd;
+	struct ohci_hcd *ohci = hcd_to_ohci(hcd);
+	struct platform_device *pdev = to_platform_device(dev);
+	struct exynos4_ohci_platdata *pdata = pdev->dev.platform_data;
+	unsigned long flags;
+	int rc = 0;
+
+	/*
+	 * Root hub was already suspended. Disable irq emission and
+	 * mark HW unaccessible, bail out if RH has been resumed. Use
+	 * the spinlock to properly synchronize with possible pending
+	 * RH suspend or resume activity.
+	 *
+	 * This is still racy as hcd->state is manipulated outside of
+	 * any locks =P But that will be a different fix.
+	 */
+	spin_lock_irqsave(&ohci->lock, flags);
+	if (hcd->state != HC_STATE_SUSPENDED && hcd->state != HC_STATE_HALT) {
+		rc = -EINVAL;
+		goto fail;
+	}
+
+	clear_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags);
+
+	if (pdata && pdata->phy_exit)
+		pdata->phy_exit(pdev, S5P_USB_PHY_HOST);
+fail:
+	spin_unlock_irqrestore(&ohci->lock, flags);
+
+	return rc;
+}
+
+static int exynos_ohci_resume(struct device *dev)
+{
+	struct exynos_ohci_hcd *exynos_ohci = dev_get_drvdata(dev);
+	struct usb_hcd *hcd = exynos_ohci->hcd;
+	struct platform_device *pdev = to_platform_device(dev);
+	struct exynos4_ohci_platdata *pdata = pdev->dev.platform_data;
+
+	if (pdata && pdata->phy_init)
+		pdata->phy_init(pdev, S5P_USB_PHY_HOST);
+
+	/* Mark hardware accessible again as we are out of D3 state by now */
+	set_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags);
+
+	ohci_finish_controller_resume(hcd);
+
+	return 0;
+}
+#else
+#define exynos_ohci_suspend	NULL
+#define exynos_ohci_resume	NULL
+#endif
+
+static const struct dev_pm_ops exynos_ohci_pm_ops = {
+	.suspend	= exynos_ohci_suspend,
+	.resume		= exynos_ohci_resume,
+};
+
+static struct platform_driver exynos_ohci_driver = {
+	.probe		= exynos_ohci_probe,
+	.remove		= __devexit_p(exynos_ohci_remove),
+	.shutdown	= exynos_ohci_shutdown,
+	.driver = {
+		.name	= "exynos-ohci",
+		.owner	= THIS_MODULE,
+		.pm	= &exynos_ohci_pm_ops,
+	}
+};
+
+MODULE_ALIAS("platform:exynos-ohci");
+MODULE_AUTHOR("Jingoo Han <jg1.han@samsung.com>");
diff --git a/drivers/usb/host/ohci-hcd.c b/drivers/usb/host/ohci-hcd.c
index b263919..a1006ff 100644
--- a/drivers/usb/host/ohci-hcd.c
+++ b/drivers/usb/host/ohci-hcd.c
@@ -1005,6 +1005,11 @@ MODULE_LICENSE ("GPL");
 #define PLATFORM_DRIVER		ohci_hcd_s3c2410_driver
 #endif
 
+#ifdef CONFIG_USB_OHCI_EXYNOS
+#include "ohci-exynos.c"
+#define PLATFORM_DRIVER		exynos_ohci_driver
+#endif
+
 #ifdef CONFIG_USB_OHCI_HCD_OMAP1
 #include "ohci-omap.c"
 #define OMAP1_PLATFORM_DRIVER	ohci_hcd_omap_driver
-- 
1.7.1

^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH v2 1/3] ARM: EXYNOS: Add USB OHCI device
  2011-12-06  6:31 ` [PATCH v2 1/3] ARM: EXYNOS: Add USB OHCI device Jingoo Han
@ 2011-12-06  9:13   ` Tushar Behera
  2011-12-06  9:30     ` Jingoo Han
  0 siblings, 1 reply; 6+ messages in thread
From: Tushar Behera @ 2011-12-06  9:13 UTC (permalink / raw)
  To: linux-arm-kernel

On Tuesday 06 December 2011 12:01 PM, Jingoo Han wrote:
> This patch adds USB ohci device definition for Exynos SoCs.
>
> Signed-off-by: Jingoo Han<jg1.han@samsung.com>
> ---
>   arch/arm/mach-exynos/Kconfig              |    5 +++
>   arch/arm/mach-exynos/Makefile             |    1 +
>   arch/arm/mach-exynos/dev-ohci.c           |   52 +++++++++++++++++++++++++++++
>   arch/arm/mach-exynos/include/mach/map.h   |    1 +
>   arch/arm/mach-exynos/include/mach/ohci.h  |   21 +++++++++++

In the earlier patchset, platform_device struct for ohci was defined 
within plat-samsung, and ohci.h was located in 
plat-samsung/include/plat. These are still the locations where ehci 
related definitions are located.

What is the reason for movement of ohci related definitions to mach folder?

-- 
Tushar Behera

^ permalink raw reply	[flat|nested] 6+ messages in thread

* [PATCH v2 1/3] ARM: EXYNOS: Add USB OHCI device
  2011-12-06  9:13   ` Tushar Behera
@ 2011-12-06  9:30     ` Jingoo Han
  0 siblings, 0 replies; 6+ messages in thread
From: Jingoo Han @ 2011-12-06  9:30 UTC (permalink / raw)
  To: linux-arm-kernel

Tushar Behera wrote:
> Subject: Re: [PATCH v2 1/3] ARM: EXYNOS: Add USB OHCI device
> 
> On Tuesday 06 December 2011 12:01 PM, Jingoo Han wrote:
> > This patch adds USB ohci device definition for Exynos SoCs.
> >
> > Signed-off-by: Jingoo Han<jg1.han@samsung.com>
> > ---
> >   arch/arm/mach-exynos/Kconfig              |    5 +++
> >   arch/arm/mach-exynos/Makefile             |    1 +
> >   arch/arm/mach-exynos/dev-ohci.c           |   52 +++++++++++++++++++++++++++++
> >   arch/arm/mach-exynos/include/mach/map.h   |    1 +
> >   arch/arm/mach-exynos/include/mach/ohci.h  |   21 +++++++++++
> 
> In the earlier patchset, platform_device struct for ohci was defined
> within plat-samsung, and ohci.h was located in
> plat-samsung/include/plat. These are still the locations where ehci
> related definitions are located.
> 
> What is the reason for movement of ohci related definitions to mach folder?
I changed the ohci name from ohci-s5p to ohci-exynos, because the ohci-exynos
is used for exynos series such as Exynos4210 & Exynos4x12.
Therefore, it should be located within mach-exynos/include/mach.

Also, If this patchset is accepted, I will move Samsung ehci definitions
to mach-exynos due to the same reason.

Thanks.
> 
> --
> Tushar Behera

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2011-12-06  9:30 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2011-12-06  6:30 [PATCH v2 0/3] Support Samsung Exynos OHCI device and driver Jingoo Han
2011-12-06  6:31 ` [PATCH v2 1/3] ARM: EXYNOS: Add USB OHCI device Jingoo Han
2011-12-06  9:13   ` Tushar Behera
2011-12-06  9:30     ` Jingoo Han
2011-12-06  6:32 ` [PATCH v2 2/3] ARM: EXYNOS: Add USB OHCI support to SMDKV310 board Jingoo Han
2011-12-06  6:32 ` [PATCH v2 3/3] USB: Add Samsung Exynos OHCI diver Jingoo Han

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).