From: Dinh Nguyen <[email protected]>
Update /plat-mxc/gpio.c to support Freescale's MX51 Babbage HW.
This patch applies to 2.6.34-rc4.
Signed-off-by: Dinh Nguyen <[email protected]>
---
arch/arm/mach-mx5/board-mx51_babbage.c | 5 +++-
arch/arm/mach-mx5/devices.c | 33 ++++++++++++++++++++++++++++++-
arch/arm/plat-mxc/gpio.c | 32 +++++++++++++++++++++++++-----
3 files changed, 61 insertions(+), 9 deletions(-)
diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
index ee67a71..afbe400 100644
--- a/arch/arm/mach-mx5/board-mx51_babbage.c
+++ b/arch/arm/mach-mx5/board-mx51_babbage.c
@@ -1,5 +1,5 @@
/*
- * Copyright 2009 Freescale Semiconductor, Inc. All Rights Reserved.
+ * Copyright (C) 2009-2010 Freescale Semiconductor, Inc. All Rights Reserved.
* Copyright (C) 2009-2010 Amit Kucheria <[email protected]>
*
* The code contained herein is licensed under the GNU General Public
@@ -12,6 +12,7 @@
#include <linux/init.h>
#include <linux/platform_device.h>
+#include <linux/gpio.h>
#include <mach/common.h>
#include <mach/hardware.h>
@@ -75,6 +76,8 @@ static void __init mxc_board_init(void)
ARRAY_SIZE(mx51babbage_pads));
mxc_init_imx_uart();
platform_add_devices(devices, ARRAY_SIZE(devices));
+
+ mxc_register_gpios();
}
static void __init mx51_babbage_timer_init(void)
diff --git a/arch/arm/mach-mx5/devices.c b/arch/arm/mach-mx5/devices.c
index d6fd396..73f2342 100644
--- a/arch/arm/mach-mx5/devices.c
+++ b/arch/arm/mach-mx5/devices.c
@@ -1,5 +1,6 @@
/*
* Copyright 2009 Amit Kucheria <[email protected]>
+ * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
*
* The code contained herein is licensed under the GNU General Public
* License. You may obtain a copy of the GNU General Public License
@@ -11,7 +12,9 @@
#include <linux/platform_device.h>
#include <mach/hardware.h>
+#include <mach/gpio.h>
#include <mach/imx-uart.h>
+#include <mach/irqs.h>
static struct resource uart0[] = {
{
@@ -89,8 +92,34 @@ struct platform_device mxc_fec_device = {
.resource = mxc_fec_resources,
};
-/* Dummy definition to allow compiling in AVIC and TZIC simultaneously */
+struct mxc_gpio_port mxc_gpio_ports[] = {
+ {
+ .chip.label = "gpio-0",
+ .base = MX51_IO_ADDRESS(MX51_GPIO1_BASE_ADDR),
+ .irq = MX51_MXC_INT_GPIO1_LOW,
+ .virtual_irq_start = MXC_GPIO_IRQ_START
+ },
+ {
+ .chip.label = "gpio-1",
+ .base = MX51_IO_ADDRESS(MX51_GPIO2_BASE_ADDR),
+ .irq = MX51_MXC_INT_GPIO2_LOW,
+ .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 1
+ },
+ {
+ .chip.label = "gpio-2",
+ .base = MX51_IO_ADDRESS(MX51_GPIO3_BASE_ADDR),
+ .irq = MX51_MXC_INT_GPIO3_LOW,
+ .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 2
+ },
+ {
+ .chip.label = "gpio-3",
+ .base = MX51_IO_ADDRESS(MX51_GPIO4_BASE_ADDR),
+ .irq = MX51_MXC_INT_GPIO4_LOW,
+ .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 3
+ },
+};
+
int __init mxc_register_gpios(void)
{
- return 0;
+ return mxc_gpio_init(mxc_gpio_ports, 4);
}
diff --git a/arch/arm/plat-mxc/gpio.c b/arch/arm/plat-mxc/gpio.c
index 70b2389..1df23b2 100644
--- a/arch/arm/plat-mxc/gpio.c
+++ b/arch/arm/plat-mxc/gpio.c
@@ -3,7 +3,7 @@
* Copyright 2008 Juergen Beisert, [email protected]
*
* Based on code from Freescale,
- * Copyright 2004-2006 Freescale Semiconductor, Inc. All Rights Reserved.
+ * Copyright (C) 2004-2010 Freescale Semiconductor, Inc. All Rights Reserved.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
@@ -38,7 +38,6 @@ static int gpio_table_size;
#define GPIO_ICR2 (cpu_is_mx1_mx2() ? 0x2C : 0x10)
#define GPIO_IMR (cpu_is_mx1_mx2() ? 0x30 : 0x14)
#define GPIO_ISR (cpu_is_mx1_mx2() ? 0x34 : 0x18)
-#define GPIO_ISR (cpu_is_mx1_mx2() ? 0x34 : 0x18)
#define GPIO_INT_LOW_LEV (cpu_is_mx1_mx2() ? 0x3 : 0x0)
#define GPIO_INT_HIGH_LEV (cpu_is_mx1_mx2() ? 0x2 : 0x1)
@@ -171,6 +170,25 @@ static void mxc_gpio_irq_handler(struct mxc_gpio_port *port, u32 irq_stat)
}
}
+/* one interrupt *per* gpio port */
+static void mx5_gpio_irq_handler(u32 irq, struct irq_desc *desc)
+{
+ u32 irq_stat;
+ u32 mask = 0xFFFFFFFF;
+ struct mxc_gpio_port *port = (struct mxc_gpio_port *)get_irq_data(irq);
+
+#ifdef MXC_GPIO_SPLIT_IRQ_2
+ if (irq == port->irq)
+ mask = 0x0000FFFF;
+ else
+ mask = 0xFFFF0000;
+#endif
+
+ irq_stat = __raw_readl(port->base + GPIO_ISR) &
+ (__raw_readl(port->base + GPIO_IMR) & mask);
+ mxc_gpio_irq_handler(port, irq_stat);
+}
+
/* MX1 and MX3 has one interrupt *per* gpio port */
static void mx3_gpio_irq_handler(u32 irq, struct irq_desc *desc)
{
@@ -289,11 +307,13 @@ int __init mxc_gpio_init(struct mxc_gpio_port *port, int cnt)
/* its a serious configuration bug when it fails */
BUG_ON( gpiochip_add(&port[i].chip) < 0 );
- if (cpu_is_mx1() || cpu_is_mx3() || cpu_is_mx25()) {
- /* setup one handler for each entry */
+ /* setup one handler for each entry */
+ if (cpu_is_mx1() || cpu_is_mx3() || cpu_is_mx25())
set_irq_chained_handler(port[i].irq, mx3_gpio_irq_handler);
- set_irq_data(port[i].irq, &port[i]);
- }
+ else if (cpu_is_mx51())
+ set_irq_chained_handler(port[i].irq, mx5_gpio_irq_handler);
+
+ set_irq_data(port[i].irq, &port[i]);
}
if (cpu_is_mx2()) {
--
1.6.0.4
From: Dinh Nguyen <[email protected]>
This patch adds the device platform registration for enabling USB
host functionality on the OTG port on Freescale MX51 Babbage HW. This
file makes platform specific calls to initialize the USB HW.
This patch applies to 2.6.34-rc4.
Signed-off-by: Dinh Nguyen <[email protected]>
---
arch/arm/mach-mx5/Makefile | 2 +-
arch/arm/mach-mx5/board-mx51_babbage.c | 4 ++
arch/arm/mach-mx5/usb_dr.c | 57 ++++++++++++++++++++++++++++++++
3 files changed, 62 insertions(+), 1 deletions(-)
create mode 100644 arch/arm/mach-mx5/usb_dr.c
diff --git a/arch/arm/mach-mx5/Makefile b/arch/arm/mach-mx5/Makefile
index bf23f86..3fca1f1 100644
--- a/arch/arm/mach-mx5/Makefile
+++ b/arch/arm/mach-mx5/Makefile
@@ -3,7 +3,7 @@
#
# Object file lists.
-obj-y := cpu.o mm.o clock-mx51.o devices.o
+obj-y := cpu.o mm.o clock-mx51.o devices.o usb_dr.o
obj-$(CONFIG_MACH_MX51_BABBAGE) += board-mx51_babbage.o
diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
index afbe400..4e196d7 100644
--- a/arch/arm/mach-mx5/board-mx51_babbage.c
+++ b/arch/arm/mach-mx5/board-mx51_babbage.c
@@ -27,6 +27,8 @@
#include "devices.h"
+extern void __init mx5_usb_dr_init(void);
+
static struct platform_device *devices[] __initdata = {
&mxc_fec_device,
};
@@ -78,6 +80,8 @@ static void __init mxc_board_init(void)
platform_add_devices(devices, ARRAY_SIZE(devices));
mxc_register_gpios();
+
+ mx5_usb_dr_init();
}
static void __init mx51_babbage_timer_init(void)
diff --git a/arch/arm/mach-mx5/usb_dr.c b/arch/arm/mach-mx5/usb_dr.c
new file mode 100644
index 0000000..52273ea
--- /dev/null
+++ b/arch/arm/mach-mx5/usb_dr.c
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
+#include <linux/platform_device.h>
+#include <mach/mxc_ehci.h>
+#include <mach/common.h>
+#include "devices.h"
+
+extern int usbotg_init(struct platform_device *pdev);
+extern int usbotg_uninit(struct platform_device *pdev);
+
+static int usbotg_init_ext(struct platform_device *pdev);
+static int usbotg_uninit_ext(struct platform_device *pdev);
+
+/*
+ * platform data structs
+ * - Which one to use is determined by CONFIG options in usb.h
+ * - operating_mode plugged at run time
+ */
+static struct mxc_usbh_platform_data dr_utmi_config = {
+ .init = usbotg_init_ext,
+ .exit = usbotg_uninit_ext,
+ .portsc = MXC_EHCI_UTMI_16BIT,
+ .flags = MXC_EHCI_INTERNAL_PHY,
+};
+
+/* Notes: configure USB clock*/
+static int usbotg_init_ext(struct platform_device *pdev)
+{
+ return usbotg_init(pdev);
+}
+
+static int usbotg_uninit_ext(struct platform_device *pdev)
+{
+ return usbotg_uninit(pdev);
+}
+
+void __init mx5_usb_dr_init(void)
+{
+ mxc_register_device(&mxc_usbdr_host_device, &dr_utmi_config);
+}
--
1.6.0.4
From: Dinh Nguyen <[email protected]>
This patch is part of enabling USB for Freescale MX51 Babbage HW. This
patch updates the iomux pins for USB, and gpio line for reset the
USB hub on the MX51 Babbage HW.
This patch applies to 2.6.34-rc4.
Signed-off-by: Dinh Nguyen <[email protected]>
---
arch/arm/plat-mxc/ehci.c | 4 +++
arch/arm/plat-mxc/include/mach/iomux-mx51.h | 33 ++++++++++++++++----------
2 files changed, 24 insertions(+), 13 deletions(-)
diff --git a/arch/arm/plat-mxc/ehci.c b/arch/arm/plat-mxc/ehci.c
index cb0b638..20eaddc 100644
--- a/arch/arm/plat-mxc/ehci.c
+++ b/arch/arm/plat-mxc/ehci.c
@@ -186,6 +186,10 @@ int mxc_set_usbcontrol(int port, unsigned int flags)
return 0;
}
#endif /* CONFIG_MACH_MX27 */
+#ifdef CONFIG_ARCH_MX5
+ /* Nothing needs to be done for MX5 here */
+ return 0;
+#endif
printk(KERN_WARNING
"%s() unable to setup USBCONTROL for this CPU\n", __func__);
return -EINVAL;
diff --git a/arch/arm/plat-mxc/include/mach/iomux-mx51.h b/arch/arm/plat-mxc/include/mach/iomux-mx51.h
index b4f975e..99de3b3 100644
--- a/arch/arm/plat-mxc/include/mach/iomux-mx51.h
+++ b/arch/arm/plat-mxc/include/mach/iomux-mx51.h
@@ -1,5 +1,6 @@
/*
* Copyright (C) 2009-2010 Amit Kucheria <[email protected]>
+ * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
*
* The code contained herein is licensed under the GNU General Public
* License. You may obtain a copy of the GNU General Public License
@@ -37,6 +38,11 @@ typedef enum iomux_config {
PAD_CTL_SRE_FAST)
#define MX51_UART3_PAD_CTRL (PAD_CTL_PKE | PAD_CTL_DSE_HIGH | \
PAD_CTL_SRE_FAST)
+#define MX51_USBH1_PAD_CTRL (PAD_CTL_SRE_FAST | PAD_CTL_DSE_HIGH | \
+ PAD_CTL_PUS_100K_UP | PAD_CTL_PUE | \
+ PAD_CTL_PKE | PAD_CTL_HYS)
+#define MX51_GPIO_PAD_CTRL ( PAD_CTL_DSE_HIGH | PAD_CTL_PKE | \
+ PAD_CTL_SRE_FAST)
/*
* The naming convention for the pad modes is MX51_PAD_<padname>__<padmode>
@@ -208,18 +214,19 @@ typedef enum iomux_config {
#define MX51_PAD_KEY_COL3__KEY_COL3 IOMUX_PAD(0x658, 0x268, 0, 0x0, 0, NO_PAD_CTRL)
#define MX51_PAD_KEY_COL4__KEY_COL4 IOMUX_PAD(0x65C, 0x26C, 0, 0x0, 0, NO_PAD_CTRL)
#define MX51_PAD_KEY_COL5__KEY_COL5 IOMUX_PAD(0x660, 0x270, 0, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_25__USBH1_CLK IOMUX_PAD(0x678, 0x278, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_26__USBH1_DIR IOMUX_PAD(0x67C, 0x27C, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_27__USBH1_STP IOMUX_PAD(0x680, 0x280, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_28__USBH1_NXT IOMUX_PAD(0x684, 0x284, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_11__USBH1_DATA0 IOMUX_PAD(0x688, 0x288, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_12__USBH1_DATA1 IOMUX_PAD(0x68C, 0x28C, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_13__USBH1_DATA2 IOMUX_PAD(0x690, 0x290, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_14__USBH1_DATA3 IOMUX_PAD(0x694, 0x294, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_15__USBH1_DATA4 IOMUX_PAD(0x698, 0x298, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_16__USBH1_DATA5 IOMUX_PAD(0x69C, 0x29C, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_17__USBH1_DATA6 IOMUX_PAD(0x6A0, 0x2A0, 2, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_18__USBH1_DATA7 IOMUX_PAD(0x6A4, 0x2A4, 2, 0x0, 0, NO_PAD_CTRL)
+#define MX51_PAD_GPIO_1_25__USBH1_CLK IOMUX_PAD(0x678, 0x278, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_26__USBH1_DIR IOMUX_PAD(0x67C, 0x27C, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_27__USBH1_STP IOMUX_PAD(0x680, 0x280, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_27__USBH1_STP_ERR IOMUX_PAD(0x680, 0x280, IOMUX_CONFIG_GPIO, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_28__USBH1_NXT IOMUX_PAD(0x684, 0x284, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_11__USBH1_DATA0 IOMUX_PAD(0x688, 0x288, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_12__USBH1_DATA1 IOMUX_PAD(0x68C, 0x28C, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_13__USBH1_DATA2 IOMUX_PAD(0x690, 0x290, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_14__USBH1_DATA3 IOMUX_PAD(0x694, 0x294, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_15__USBH1_DATA4 IOMUX_PAD(0x698, 0x298, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_16__USBH1_DATA5 IOMUX_PAD(0x69C, 0x29C, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_17__USBH1_DATA6 IOMUX_PAD(0x6A0, 0x2A0, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
+#define MX51_PAD_GPIO_1_18__USBH1_DATA7 IOMUX_PAD(0x6A4, 0x2A4, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
#define MX51_PAD_GPIO_3_0__DI1_PIN11 IOMUX_PAD(0x6A8, 0x2A8, 4, 0x0, 0, NO_PAD_CTRL)
#define MX51_PAD_GPIO_3_1__DI1_PIN12 IOMUX_PAD(0x6AC, 0x2AC, 4, 0x0, 0, NO_PAD_CTRL)
#define MX51_PAD_GPIO_3_2__DI1_PIN13 IOMUX_PAD(0x6B0, 0x2B0, 4, 0x0, 0, NO_PAD_CTRL)
@@ -299,7 +306,7 @@ typedef enum iomux_config {
#define MX51_PAD_GPIO_1_4__GPIO1_4 IOMUX_PAD(0x804, 0x3D8, 0, 0x0, 0, NO_PAD_CTRL)
#define MX51_PAD_GPIO_1_5__GPIO1_5 IOMUX_PAD(0x808, 0x3DC, 0, 0x0, 0, NO_PAD_CTRL)
#define MX51_PAD_GPIO_1_6__GPIO1_6 IOMUX_PAD(0x80C, 0x3E0, 0, 0x0, 0, NO_PAD_CTRL)
-#define MX51_PAD_GPIO_1_7__GPIO1_7 IOMUX_PAD(0x810, 0x3E4, 0, 0x0, 0, NO_PAD_CTRL)
+#define MX51_PAD_GPIO_1_7__GPIO1_7 IOMUX_PAD(0x810, 0x3E4, 0, 0x0, 0, MX51_GPIO_PAD_CTRL)
#define MX51_PAD_GPIO_1_8__GPIO1_8 IOMUX_PAD(0x814, 0x3E8, 0, 0x0, 1, \
(PAD_CTL_SRE_SLOW | PAD_CTL_DSE_MED | PAD_CTL_PUS_100K_UP | PAD_CTL_HYS))
#define MX51_PAD_GPIO_1_9__GPIO1_9 IOMUX_PAD(0x818, 0x3EC, 0, 0x0, 0, NO_PAD_CTRL)
--
1.6.0.4
From: Dinh Nguyen <[email protected]>
This patch is part of enabling USB for Freescale MX51 Babbage HW. This
patch performs some platform specific USB HW initialization, and adds
the necessary defines.
This patch applies to 2.6.34-rc4.
Signed-off-by: Dinh Nguyen <[email protected]>
---
arch/arm/plat-mxc/Makefile | 2 +-
arch/arm/plat-mxc/include/mach/mxc_ehci.h | 48 +++++++
arch/arm/plat-mxc/usb_common.c | 190 +++++++++++++++++++++++++++++
3 files changed, 239 insertions(+), 1 deletions(-)
create mode 100644 arch/arm/plat-mxc/usb_common.c
diff --git a/arch/arm/plat-mxc/Makefile b/arch/arm/plat-mxc/Makefile
index 895bc3c..fa8ed78 100644
--- a/arch/arm/plat-mxc/Makefile
+++ b/arch/arm/plat-mxc/Makefile
@@ -3,7 +3,7 @@
#
# Common support
-obj-y := irq.o clock.o gpio.o time.o devices.o cpu.o system.o
+obj-y := irq.o clock.o gpio.o time.o devices.o cpu.o system.o usb_common.o
# MX51 uses the TZIC interrupt controller, older platforms use AVIC (irq.o)
obj-$(CONFIG_MXC_TZIC) += tzic.o
diff --git a/arch/arm/plat-mxc/include/mach/mxc_ehci.h b/arch/arm/plat-mxc/include/mach/mxc_ehci.h
index 4b9b836..6edf8d7 100644
--- a/arch/arm/plat-mxc/include/mach/mxc_ehci.h
+++ b/arch/arm/plat-mxc/include/mach/mxc_ehci.h
@@ -1,6 +1,30 @@
#ifndef __INCLUDE_ASM_ARCH_MXC_EHCI_H
#define __INCLUDE_ASM_ARCH_MXC_EHCI_H
+#define USBOTG_OFFSET 0
+#define USBH1_OFFSET 0x200
+#define USBH2_OFFSET 0x400
+#define USBH3_OFFSET 0x600
+#define USBOTHER_REGS_OFFSET 0x800
+
+#define USBCMD_OFFSET 0x140
+
+#define ULPI_VIEWPORT_OFFSET 0x170
+#define PORTSC_OFFSET 0x184
+#define USBMODE_OFFSET 0x1a8
+#define USBMODE_CM_HOST 3
+
+#define USBCTRL_OFFSET 0
+#define USB_PHY_CTR_FUNC_OFFSET 0x8
+#define USB_PHY_CTR_FUNC2_OFFSET 0xc
+#define USB_CTRL_1_OFFSET 0x10
+
+
+/* USBCMD */
+#define UCMD_RUN_STOP (1 << 0) /* controller run/stop */
+#define UCMD_RESET (1 << 1) /* controller reset */
+#define UCMD_ITC_NO_THRESHOLD ~(0xff << 16) /* Interrupt Threshold Control */
+
/* values for portsc field */
#define MXC_EHCI_PHY_LOW_POWER_SUSPEND (1 << 23)
#define MXC_EHCI_FORCE_FS (1 << 24)
@@ -26,6 +50,30 @@
#define MXC_EHCI_IPPUE_DOWN (1 << 8)
#define MXC_EHCI_IPPUE_UP (1 << 9)
+/* USB_CTRL */
+#define UCTRL_OUIE (1 << 28) /* OTG ULPI intr enable */
+#define UCTRL_OWIE (1 << 27) /* OTG wakeup intr enable */
+#define UCTRL_OBPVAL_RXDP (1 << 26) /* OTG RxDp status in bypass mode */
+#define UCTRL_OBPVAL_RXDM (1 << 25) /* OTG RxDm status in bypass mode */
+#define UCTRL_OPM (1 << 24) /* OTG power mask */
+#define UCTRL_H1UIE (1 << 12) /* Host1 ULPI interrupt enable */
+#define UCTRL_H1WIE (1 << 11) /* HOST1 wakeup intr enable */
+#define UCTRL_H1PM (1 << 8) /* HOST1 power mask */
+
+/* USB_PHY_CTRL_FUNC */
+#define USB_UTMI_PHYCTRL_OC_DIS (1 << 8) /* OTG Disable Overcurrent Event */
+#define USB_UH1_OC_DIS (1 << 5) /* UH1 Disable Overcurrent Event */
+
+/* USB_CTRL_1 */
+#define USB_CTRL_UH1_EXT_CLK_EN (1 << 25)
+#define USB_CTRL_UH2_EXT_CLK_EN (1 << 26)
+
+/* USB_PHY_CTRL_FUNC2*/
+#define USB_UTMI_PHYCTRL2_PLLDIV_MASK 0x3
+#define USB_UTMI_PHYCTRL2_PLLDIV_SHIFT 0
+#define USB_UTMI_PHYCTRL2_HSDEVSEL_MASK 0x3
+#define USB_UTMI_PHYCTRL2_HSDEVSEL_SHIFT 19
+
struct mxc_usbh_platform_data {
int (*init)(struct platform_device *pdev);
int (*exit)(struct platform_device *pdev);
diff --git a/arch/arm/plat-mxc/usb_common.c b/arch/arm/plat-mxc/usb_common.c
new file mode 100644
index 0000000..b06c66e
--- /dev/null
+++ b/arch/arm/plat-mxc/usb_common.c
@@ -0,0 +1,190 @@
+/*
+ * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
+/*
+ *Include files
+ */
+#include <linux/module.h>
+#include <linux/kernel.h>
+#include <linux/delay.h>
+#include <linux/io.h>
+#include <linux/fsl_devices.h>
+#include <mach/mxc_ehci.h>
+#include <mach/hardware.h>
+
+static void usbh1_set_ulpi_xcvr(void)
+{
+ u32 reg_value;
+ pr_debug("%s: \n", __func__);
+ void __iomem *usb_base = ioremap(MX51_OTG_BASE_ADDR, SZ_4K);
+ u32 usbh1_base = (u32)usb_base + USBH1_OFFSET;
+ u32 usbother_base = (u32)usb_base + USBOTHER_REGS_OFFSET;
+
+ /* Stop then Reset */
+ reg_value = __raw_readl(usbh1_base + USBCMD_OFFSET);
+ reg_value &= ~UCMD_RUN_STOP;
+ __raw_writel(reg_value, usbh1_base + USBCMD_OFFSET);
+ while (__raw_readl(usbh1_base + USBCMD_OFFSET) & UCMD_RUN_STOP);
+
+ reg_value = __raw_readl(usbh1_base + USBCMD_OFFSET);
+ reg_value |= UCMD_RESET;
+ __raw_writel(reg_value, usbh1_base + USBCMD_OFFSET);
+ while (__raw_readl(usbh1_base + USBCMD_OFFSET) & UCMD_RESET);
+
+ reg_value = __raw_readl(usbother_base + USB_CTRL_1_OFFSET);
+ __raw_writel(reg_value | USB_CTRL_UH1_EXT_CLK_EN, usbother_base + USB_CTRL_1_OFFSET);
+
+ /* select ULPI PHY PTS=2 */
+ reg_value = __raw_readl(usbh1_base + PORTSC_OFFSET);
+ reg_value &= ~MXC_EHCI_MODE_SERIAL;
+ __raw_writel(reg_value |= MXC_EHCI_MODE_ULPI, usbh1_base + PORTSC_OFFSET);
+
+ reg_value = __raw_readl(usbother_base + USBCTRL_OFFSET);
+ reg_value &= ~(UCTRL_H1WIE | UCTRL_H1UIE);/* HOST1 wakeup/ULPI intr disable */
+ reg_value |= UCTRL_H1PM; /* HOST1 power mask */
+ __raw_writel(reg_value, usbother_base + USBCTRL_OFFSET);
+
+ reg_value = __raw_readl(usbother_base + USB_PHY_CTR_FUNC_OFFSET);
+ reg_value |= USB_UH1_OC_DIS; /* OC is not used */
+ __raw_writel(reg_value, usbother_base + USB_PHY_CTR_FUNC_OFFSET);
+
+ reg_value = __raw_readl(usbh1_base + USBCMD_OFFSET);
+ /* Interrupt Threshold Control:Immediate (no threshold) */
+ reg_value &= UCMD_ITC_NO_THRESHOLD;
+ __raw_writel(reg_value, usbh1_base + USBCMD_OFFSET);
+
+ /* reset the controller */
+ reg_value = __raw_readl(usbh1_base + USBCMD_OFFSET);
+ reg_value |= UCMD_RESET;
+ __raw_writel(reg_value, usbh1_base + USBCMD_OFFSET);
+
+ iounmap(usb_base);
+
+ /* allow controller to reset, and leave time for
+ * the ULPI transceiver to reset too.
+ */
+ msleep(100);
+}
+
+int fsl_usb_host_init(struct platform_device *pdev)
+{
+ pr_debug("%s: pdev=0x%p\n", __func__, pdev);
+
+ usbh1_set_ulpi_xcvr();
+
+ pr_debug("%s: success\n", __func__);
+ return 0;
+}
+EXPORT_SYMBOL(fsl_usb_host_init);
+
+int fsl_usb_host_uninit(struct fsl_usb2_platform_data *pdata)
+{
+ pr_debug("%s\n", __func__);
+ return 0;
+}
+EXPORT_SYMBOL(fsl_usb_host_uninit);
+
+static void otg_set_utmi_xcvr(void)
+{
+ u32 reg_value;
+ void __iomem *usb_base = ioremap(MX51_OTG_BASE_ADDR, SZ_4K);
+ u32 usbotg_base = (u32)usb_base + USBOTG_OFFSET;
+ u32 usbother_base = (u32)usb_base + USBOTHER_REGS_OFFSET;
+
+ pr_debug("otg_set_utmi_xcvr\n");
+
+ /* Stop then Reset */
+ reg_value = __raw_readl(usbotg_base + USBCMD_OFFSET);
+ reg_value &= ~UCMD_RUN_STOP;
+ __raw_writel(reg_value, usbotg_base + USBCMD_OFFSET);
+ while (__raw_readl(usbotg_base + USBCMD_OFFSET) & UCMD_RUN_STOP);
+
+ reg_value = __raw_readl(usbotg_base + USBCMD_OFFSET);
+ reg_value |= UCMD_RESET;
+ __raw_writel(reg_value, usbotg_base + USBCMD_OFFSET);
+ while (__raw_readl(usbotg_base + USBCMD_OFFSET) & UCMD_RESET);
+
+ reg_value = __raw_readl(usbother_base + USB_PHY_CTR_FUNC_OFFSET);
+ reg_value |= USB_UTMI_PHYCTRL_OC_DIS; /* OC is not used */
+ __raw_writel(reg_value, usbother_base + USB_PHY_CTR_FUNC_OFFSET);
+
+ reg_value = __raw_readl(usbother_base + USBCTRL_OFFSET);
+ reg_value &= ~(UCTRL_OPM | UCTRL_OWIE);/* OTG wakeup/power mask disable */
+ __raw_writel(reg_value, usbother_base + USBCTRL_OFFSET);
+
+ /* set UTMI xcvr */
+ reg_value = __raw_readl(usbotg_base + PORTSC_OFFSET);
+ reg_value &= ~MXC_EHCI_MODE_SERIAL;
+ __raw_writel(reg_value |= MXC_EHCI_MODE_UTMI, usbotg_base + PORTSC_OFFSET);
+
+ /* Set the PHY clock to 19.2MHz */
+ reg_value = __raw_readl(usbother_base + USB_PHY_CTR_FUNC2_OFFSET);
+ reg_value &= ~USB_UTMI_PHYCTRL2_PLLDIV_MASK;
+ reg_value |= 0x01;
+ __raw_writel(reg_value, usbother_base + USB_PHY_CTR_FUNC2_OFFSET);
+
+ /* Workaround an IC issue for ehci driver:
+ * when turn off root hub port power, EHCI set
+ * PORTSC reserved bits to be 0, but PTW with 0
+ * means 8 bits tranceiver width, here change
+ * it back to be 16 bits and do PHY diable and
+ * then enable.
+ */
+ reg_value = __raw_readl(usbotg_base + PORTSC_OFFSET);
+ reg_value |= MXC_EHCI_UTMI_16BIT;
+ __raw_writel(reg_value, usbotg_base + PORTSC_OFFSET);
+
+ /* need to reset the controller here so that the ID pin
+ * is correctly detected.
+ */
+ /* Stop then Reset */
+ reg_value = __raw_readl(usbotg_base + USBCMD_OFFSET);
+ reg_value &= ~UCMD_RUN_STOP;
+ __raw_writel(reg_value, usbotg_base + USBCMD_OFFSET);
+ while (__raw_readl(usbotg_base + USBCMD_OFFSET) & UCMD_RUN_STOP);
+
+ reg_value = __raw_readl(usbotg_base + USBCMD_OFFSET);
+ reg_value |= UCMD_RESET;
+ __raw_writel(reg_value, usbotg_base + USBCMD_OFFSET);
+ while (__raw_readl(usbotg_base + USBCMD_OFFSET) & UCMD_RESET);
+
+ iounmap(usb_base);
+ /* allow controller to reset, and leave time for
+ * the ULPI transceiver to reset too.
+ */
+ msleep(100);
+}
+
+int usbotg_init(struct platform_device *pdev)
+{
+ pr_debug("%s: pdev=0x%p\n", __func__, pdev);
+
+ otg_set_utmi_xcvr();
+
+ pr_debug("%s: success\n", __func__);
+ return 0;
+}
+EXPORT_SYMBOL(usbotg_init);
+
+int usbotg_uninit(struct platform_device *pdev)
+{
+ pr_debug("%s\n", __func__);
+ return 0;
+}
+EXPORT_SYMBOL(usbotg_uninit);
--
1.6.0.4
From: Dinh Nguyen <[email protected]>
Updade mx51_defconfig to include USB host support.
This patch applies to 2.6.34-rc4.
Signed-off-by: Dinh Nguyen <[email protected]>
---
arch/arm/configs/mx51_defconfig | 17 ++++++++++++++++-
1 files changed, 16 insertions(+), 1 deletions(-)
diff --git a/arch/arm/configs/mx51_defconfig b/arch/arm/configs/mx51_defconfig
index c88e952..a708fd6 100644
--- a/arch/arm/configs/mx51_defconfig
+++ b/arch/arm/configs/mx51_defconfig
@@ -809,7 +809,22 @@ CONFIG_SSB_POSSIBLE=y
CONFIG_DUMMY_CONSOLE=y
# CONFIG_SOUND is not set
# CONFIG_HID_SUPPORT is not set
-# CONFIG_USB_SUPPORT is not set
+CONFIG_USB_SUPPORT=y
+CONFIG_USB_ARCH_HAS_HCD=y
+# CONFIG_USB_ARCH_HAS_OHCI is not set
+CONFIG_USB_ARCH_HAS_EHCI=y
+CONFIG_USB=y
+
+#
+# USB Host Controller Drivers
+#
+# CONFIG_USB_C67X00_HCD is not set
+CONFIG_USB_EHCI_HCD=y
+CONFIG_USB_EHCI_ROOT_HUB_TT=y
+# CONFIG_USB_EHCI_TT_NEWSCHED is not set
+CONFIG_USB_EHCI_MXC=y
+
+
CONFIG_MMC=y
# CONFIG_MMC_DEBUG is not set
# CONFIG_MMC_UNSAFE_RESUME is not set
--
1.6.0.4
From: Dinh Nguyen <[email protected]>
This patch adds the device platform registration for enabling USB
host functionality on the Host1 port on Freescale MX51 Babbage HW.
This file makes platform specific calls to initialize the USB HW.
This patch applies to 2.6.34-rc4.
Signed-off-by: Dinh Nguyen <[email protected]>
---
arch/arm/mach-mx5/Makefile | 2 +-
arch/arm/mach-mx5/board-mx51_babbage.c | 2 +
arch/arm/mach-mx5/usb_h1.c | 90 ++++++++++++++++++++++++++++++++
3 files changed, 93 insertions(+), 1 deletions(-)
create mode 100644 arch/arm/mach-mx5/usb_h1.c
diff --git a/arch/arm/mach-mx5/Makefile b/arch/arm/mach-mx5/Makefile
index 3fca1f1..e49be0b 100644
--- a/arch/arm/mach-mx5/Makefile
+++ b/arch/arm/mach-mx5/Makefile
@@ -3,7 +3,7 @@
#
# Object file lists.
-obj-y := cpu.o mm.o clock-mx51.o devices.o usb_dr.o
+obj-y := cpu.o mm.o clock-mx51.o devices.o usb_dr.o usb_h1.o
obj-$(CONFIG_MACH_MX51_BABBAGE) += board-mx51_babbage.o
diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
index 4e196d7..1338d6a 100644
--- a/arch/arm/mach-mx5/board-mx51_babbage.c
+++ b/arch/arm/mach-mx5/board-mx51_babbage.c
@@ -28,6 +28,7 @@
#include "devices.h"
extern void __init mx5_usb_dr_init(void);
+extern void __init mx5_usbh1_init(void);
static struct platform_device *devices[] __initdata = {
&mxc_fec_device,
@@ -82,6 +83,7 @@ static void __init mxc_board_init(void)
mxc_register_gpios();
mx5_usb_dr_init();
+ mx5_usbh1_init();
}
static void __init mx51_babbage_timer_init(void)
diff --git a/arch/arm/mach-mx5/usb_h1.c b/arch/arm/mach-mx5/usb_h1.c
new file mode 100644
index 0000000..23ae336
--- /dev/null
+++ b/arch/arm/mach-mx5/usb_h1.c
@@ -0,0 +1,90 @@
+/*
+ * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02110-1301, USA.
+ */
+
+#include <linux/delay.h>
+#include <linux/gpio.h>
+#include <linux/platform_device.h>
+#include <mach/iomux-mx51.h>
+#include <mach/mxc_ehci.h>
+#include <mach/common.h>
+#include "devices.h"
+
+#define GPIO1_27 (0*32 +27)
+
+extern int fsl_usb_host_init(struct platform_device *pdev);
+extern int fsl_usb_host_uninit(struct fsl_usb2_platform_data *pdata);
+
+static int fsl_usb_host_init_ext(struct platform_device *pdev);
+static int fsl_usb_host_uninit_ext(struct platform_device *pdev);
+
+static struct mxc_usbh_platform_data usbh1_config = {
+ .init = fsl_usb_host_init_ext,
+ .exit = fsl_usb_host_uninit_ext,
+ .portsc = MXC_EHCI_MODE_ULPI,
+ .flags = MXC_EHCI_POWER_PINS_ENABLED,
+};
+
+/*
+ * USB Host1 HS port
+ */
+static int gpio_usbh1_active(void)
+{
+ struct pad_desc usbh1stp_gpio = MX51_PAD_GPIO_1_27__USBH1_STP_ERR;
+ int ret;
+
+ /* Set USBH1_STP to GPIO and toggle it */
+ mxc_iomux_v3_setup_pad(&usbh1stp_gpio);
+ ret = gpio_request(GPIO1_27, "usbh1_stp");
+
+ if (ret) {
+ pr_debug("failed to get USBH1_STP_GPIO1_27: %d\n", ret);
+ return ret;
+ }
+ gpio_direction_output(GPIO1_27, 0);
+ gpio_set_value(GPIO1_27, 1);
+
+ msleep(100);
+ gpio_free(GPIO1_27);
+ return 0;
+}
+
+static int fsl_usb_host_init_ext(struct platform_device *pdev)
+{
+ int ret;
+ struct pad_desc usbh1stp = MX51_PAD_GPIO_1_27__USBH1_STP;
+
+ gpio_usbh1_active();
+ ret = fsl_usb_host_init(pdev);
+ if (ret)
+ return ret;
+
+ /* setback USBH1_STP to be function */
+ mxc_iomux_v3_setup_pad(&usbh1stp);
+ return 0;
+}
+
+static int fsl_usb_host_uninit_ext(struct platform_device *pdev)
+{
+ return fsl_usb_host_uninit(pdev);
+}
+void __init mx5_usbh1_init(void)
+{
+ mxc_register_device(&mxc_usbh1_device, &usbh1_config);
+}
+
--
1.6.0.4
From: Dinh Nguyen <[email protected]>
This patch updates the clocks, gpios, iomuxing and device structures for
enabling USB Host functionality on Freescale MX51 Babbage HW.
This patch applies to 2.6.34-rc4.
Signed-off-by: Dinh Nguyen <[email protected]>
---
arch/arm/mach-mx5/board-mx51_babbage.c | 40 +++++++++++++++++++++++++-
arch/arm/mach-mx5/clock-mx51.c | 8 +++++
arch/arm/mach-mx5/devices.c | 49 ++++++++++++++++++++++++++++++++
arch/arm/mach-mx5/devices.h | 2 +
4 files changed, 98 insertions(+), 1 deletions(-)
diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
index 1338d6a..ddfa48b 100644
--- a/arch/arm/mach-mx5/board-mx51_babbage.c
+++ b/arch/arm/mach-mx5/board-mx51_babbage.c
@@ -13,6 +13,7 @@
#include <linux/init.h>
#include <linux/platform_device.h>
#include <linux/gpio.h>
+#include <linux/delay.h>
#include <mach/common.h>
#include <mach/hardware.h>
@@ -30,6 +31,8 @@
extern void __init mx5_usb_dr_init(void);
extern void __init mx5_usbh1_init(void);
+#define GPIO_1_7 (0*32+7)
+
static struct platform_device *devices[] __initdata = {
&mxc_fec_device,
};
@@ -50,6 +53,22 @@ static struct pad_desc mx51babbage_pads[] = {
MX51_PAD_EIM_D26__UART3_TXD,
MX51_PAD_EIM_D27__UART3_RTS,
MX51_PAD_EIM_D24__UART3_CTS,
+
+ /* USB HOST1 */
+ MX51_PAD_GPIO_1_25__USBH1_CLK,
+ MX51_PAD_GPIO_1_26__USBH1_DIR,
+ MX51_PAD_GPIO_1_28__USBH1_NXT,
+ MX51_PAD_GPIO_1_11__USBH1_DATA0,
+ MX51_PAD_GPIO_1_12__USBH1_DATA1,
+ MX51_PAD_GPIO_1_13__USBH1_DATA2,
+ MX51_PAD_GPIO_1_14__USBH1_DATA3,
+ MX51_PAD_GPIO_1_15__USBH1_DATA4,
+ MX51_PAD_GPIO_1_16__USBH1_DATA5,
+ MX51_PAD_GPIO_1_17__USBH1_DATA6,
+ MX51_PAD_GPIO_1_18__USBH1_DATA7,
+
+ /* USB HUB reset line*/
+ MX51_PAD_GPIO_1_7__GPIO1_7,
};
/* Serial ports */
@@ -64,12 +83,31 @@ static inline void mxc_init_imx_uart(void)
mxc_register_device(&mxc_uart_device1, &uart_pdata);
mxc_register_device(&mxc_uart_device2, &uart_pdata);
}
-#else /* !SERIAL_IMX */
+#else /* SERIAL_IMX */
static inline void mxc_init_imx_uart(void)
{
}
#endif /* SERIAL_IMX */
+static inline void mx5_babbage_usbhub_reset(void)
+{
+ int ret;
+
+ /* Bring USB hub out of reset */
+ ret = gpio_request(GPIO_1_7, "GPIO1_7");
+ if (ret) {
+ printk("failed to get GPIO_1_7: %d\n", ret);
+ return;
+ }
+ gpio_direction_output(GPIO_1_7, 0);
+
+ /* USB HUB RESET - De-assert USB HUB RESET_N */
+ msleep(1);
+ gpio_set_value(GPIO_1_7, 0);
+ msleep(1);
+ gpio_set_value(GPIO_1_7, 1);
+}
+
/*
* Board specific initialization.
*/
diff --git a/arch/arm/mach-mx5/clock-mx51.c b/arch/arm/mach-mx5/clock-mx51.c
index 8f85f73..36684d0 100644
--- a/arch/arm/mach-mx5/clock-mx51.c
+++ b/arch/arm/mach-mx5/clock-mx51.c
@@ -765,6 +765,10 @@ DEFINE_CLOCK(gpt_ipg_clk, 0, MXC_CCM_CCGR2, MXC_CCM_CCGRx_CG10_OFFSET,
DEFINE_CLOCK(fec_clk, 0, MXC_CCM_CCGR2, MXC_CCM_CCGRx_CG12_OFFSET,
NULL, NULL, &ipg_clk, NULL);
+/* USB */
+DEFINE_CLOCK(usboh3_clk, 0, MXC_CCM_CCGR2, MXC_CCM_CCGRx_CG14_OFFSET,
+ NULL, NULL, &pll3_sw_clk, NULL);
+
#define _REGISTER_CLOCK(d, n, c) \
{ \
.dev_id = d, \
@@ -778,6 +782,10 @@ static struct clk_lookup lookups[] = {
_REGISTER_CLOCK("imx-uart.2", NULL, uart3_clk)
_REGISTER_CLOCK(NULL, "gpt", gpt_clk)
_REGISTER_CLOCK("fec.0", NULL, fec_clk)
+ _REGISTER_CLOCK("mxc-ehci.0", "usb", usboh3_clk)
+ _REGISTER_CLOCK("mxc-ehci.0", "usb_ahb", ahb_clk)
+ _REGISTER_CLOCK("mxc-ehci.1", "usb", usboh3_clk)
+ _REGISTER_CLOCK("mxc-ehci.1", "usb_ahb", ahb_clk)
};
static void clk_tree_init(void)
diff --git a/arch/arm/mach-mx5/devices.c b/arch/arm/mach-mx5/devices.c
index 73f2342..3d8f66a 100644
--- a/arch/arm/mach-mx5/devices.c
+++ b/arch/arm/mach-mx5/devices.c
@@ -11,6 +11,7 @@
*/
#include <linux/platform_device.h>
+#include <linux/dma-mapping.h>
#include <mach/hardware.h>
#include <mach/gpio.h>
#include <mach/imx-uart.h>
@@ -92,6 +93,54 @@ struct platform_device mxc_fec_device = {
.resource = mxc_fec_resources,
};
+static u64 usb_dma_mask = DMA_BIT_MASK(32);
+
+static struct resource usbotg_resources[] = {
+ {
+ .start = MX51_OTG_BASE_ADDR,
+ .end = MX51_OTG_BASE_ADDR + 0x1ff,
+ .flags = IORESOURCE_MEM,
+ },
+ {
+ .start = MX51_MXC_INT_USB_OTG,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+struct platform_device mxc_usbdr_host_device = {
+ .name = "mxc-ehci",
+ .id = 0,
+ .num_resources = ARRAY_SIZE(usbotg_resources),
+ .resource = usbotg_resources,
+ .dev = {
+ .dma_mask = &usb_dma_mask,
+ .coherent_dma_mask = DMA_BIT_MASK(32),
+ },
+};
+
+static struct resource usbh1_resources[] = {
+ {
+ .start = MX51_OTG_BASE_ADDR + 0x200,
+ .end = MX51_OTG_BASE_ADDR + 0x200 + 0x1ff,
+ .flags = IORESOURCE_MEM,
+ },
+ {
+ .start = MX51_MXC_INT_USB_H1,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+struct platform_device mxc_usbh1_device = {
+ .name = "mxc-ehci",
+ .id = 1,
+ .num_resources = ARRAY_SIZE(usbh1_resources),
+ .resource = usbh1_resources,
+ .dev = {
+ .dma_mask = &usb_dma_mask,
+ .coherent_dma_mask = DMA_BIT_MASK(32),
+ },
+};
+
struct mxc_gpio_port mxc_gpio_ports[] = {
{
.chip.label = "gpio-0",
diff --git a/arch/arm/mach-mx5/devices.h b/arch/arm/mach-mx5/devices.h
index f339ab8..95c45f9 100644
--- a/arch/arm/mach-mx5/devices.h
+++ b/arch/arm/mach-mx5/devices.h
@@ -2,3 +2,5 @@ extern struct platform_device mxc_uart_device0;
extern struct platform_device mxc_uart_device1;
extern struct platform_device mxc_uart_device2;
extern struct platform_device mxc_fec_device;
+extern struct platform_device mxc_usbdr_host_device;
+extern struct platform_device mxc_usbh1_device;
--
1.6.0.4
First, I'm glad to see Freescale sending patches for mainline code -
thanks for doing this :)
Other people might give more detailed feedback, but I'll still comment
on some things that caught my eye.
On Tue, Apr 13, 2010 at 11:10:24AM -0500, [email protected] wrote:
[...]
> index d6fd396..73f2342 100644
> --- a/arch/arm/mach-mx5/devices.c
> +++ b/arch/arm/mach-mx5/devices.c
> @@ -1,5 +1,6 @@
> /*
> * Copyright 2009 Amit Kucheria <[email protected]>
> + * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
> *
> * The code contained herein is licensed under the GNU General Public
> * License. You may obtain a copy of the GNU General Public License
> @@ -11,7 +12,9 @@
>
> #include <linux/platform_device.h>
> #include <mach/hardware.h>
> +#include <mach/gpio.h>
> #include <mach/imx-uart.h>
> +#include <mach/irqs.h>
>
> static struct resource uart0[] = {
> {
> @@ -89,8 +92,34 @@ struct platform_device mxc_fec_device = {
> .resource = mxc_fec_resources,
> };
>
> -/* Dummy definition to allow compiling in AVIC and TZIC simultaneously */
> +struct mxc_gpio_port mxc_gpio_ports[] = {
> + {
> + .chip.label = "gpio-0",
> + .base = MX51_IO_ADDRESS(MX51_GPIO1_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO1_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START
> + },
> + {
> + .chip.label = "gpio-1",
> + .base = MX51_IO_ADDRESS(MX51_GPIO2_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO2_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 1
> + },
> + {
> + .chip.label = "gpio-2",
> + .base = MX51_IO_ADDRESS(MX51_GPIO3_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO3_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 2
> + },
> + {
> + .chip.label = "gpio-3",
> + .base = MX51_IO_ADDRESS(MX51_GPIO4_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO4_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 3
> + },
> +};
> +
> int __init mxc_register_gpios(void)
> {
> - return 0;
> + return mxc_gpio_init(mxc_gpio_ports, 4);
Use ARRAY_SIZE() instead of the hard-coded constant.
> diff --git a/arch/arm/plat-mxc/gpio.c b/arch/arm/plat-mxc/gpio.c
> index 70b2389..1df23b2 100644
> --- a/arch/arm/plat-mxc/gpio.c
> +++ b/arch/arm/plat-mxc/gpio.c
> @@ -3,7 +3,7 @@
> * Copyright 2008 Juergen Beisert, [email protected]
> *
> * Based on code from Freescale,
> - * Copyright 2004-2006 Freescale Semiconductor, Inc. All Rights Reserved.
> + * Copyright (C) 2004-2010 Freescale Semiconductor, Inc. All Rights Reserved.
> *
> * This program is free software; you can redistribute it and/or
> * modify it under the terms of the GNU General Public License
> @@ -38,7 +38,6 @@ static int gpio_table_size;
> #define GPIO_ICR2 (cpu_is_mx1_mx2() ? 0x2C : 0x10)
> #define GPIO_IMR (cpu_is_mx1_mx2() ? 0x30 : 0x14)
> #define GPIO_ISR (cpu_is_mx1_mx2() ? 0x34 : 0x18)
> -#define GPIO_ISR (cpu_is_mx1_mx2() ? 0x34 : 0x18)
>
> #define GPIO_INT_LOW_LEV (cpu_is_mx1_mx2() ? 0x3 : 0x0)
> #define GPIO_INT_HIGH_LEV (cpu_is_mx1_mx2() ? 0x2 : 0x1)
> @@ -171,6 +170,25 @@ static void mxc_gpio_irq_handler(struct mxc_gpio_port *port, u32 irq_stat)
> }
> }
>
> +/* one interrupt *per* gpio port */
> +static void mx5_gpio_irq_handler(u32 irq, struct irq_desc *desc)
> +{
> + u32 irq_stat;
> + u32 mask = 0xFFFFFFFF;
> + struct mxc_gpio_port *port = (struct mxc_gpio_port *)get_irq_data(irq);
> +
> +#ifdef MXC_GPIO_SPLIT_IRQ_2
Where is that macro defined?
> + if (irq == port->irq)
> + mask = 0x0000FFFF;
> + else
> + mask = 0xFFFF0000;
> +#endif
> +
> + irq_stat = __raw_readl(port->base + GPIO_ISR) &
> + (__raw_readl(port->base + GPIO_IMR) & mask);
> + mxc_gpio_irq_handler(port, irq_stat);
> +}
> +
> /* MX1 and MX3 has one interrupt *per* gpio port */
> static void mx3_gpio_irq_handler(u32 irq, struct irq_desc *desc)
> {
> @@ -289,11 +307,13 @@ int __init mxc_gpio_init(struct mxc_gpio_port *port, int cnt)
> /* its a serious configuration bug when it fails */
> BUG_ON( gpiochip_add(&port[i].chip) < 0 );
>
> - if (cpu_is_mx1() || cpu_is_mx3() || cpu_is_mx25()) {
> - /* setup one handler for each entry */
> + /* setup one handler for each entry */
> + if (cpu_is_mx1() || cpu_is_mx3() || cpu_is_mx25())
> set_irq_chained_handler(port[i].irq, mx3_gpio_irq_handler);
> - set_irq_data(port[i].irq, &port[i]);
> - }
> + else if (cpu_is_mx51())
> + set_irq_chained_handler(port[i].irq, mx5_gpio_irq_handler);
> +
> + set_irq_data(port[i].irq, &port[i]);
> }
>
> if (cpu_is_mx2()) {
> --
> 1.6.0.4
On Tue, Apr 13, 2010 at 11:10:25AM -0500, [email protected] wrote:
> This patch is part of enabling USB for Freescale MX51 Babbage HW. This
> patch updates the iomux pins for USB, and gpio line for reset the
> USB hub on the MX51 Babbage HW.
>
> This patch applies to 2.6.34-rc4.
>
> Signed-off-by: Dinh Nguyen <[email protected]>
> ---
> arch/arm/plat-mxc/ehci.c | 4 +++
> arch/arm/plat-mxc/include/mach/iomux-mx51.h | 33 ++++++++++++++++----------
> 2 files changed, 24 insertions(+), 13 deletions(-)
>
> diff --git a/arch/arm/plat-mxc/ehci.c b/arch/arm/plat-mxc/ehci.c
> index cb0b638..20eaddc 100644
> --- a/arch/arm/plat-mxc/ehci.c
> +++ b/arch/arm/plat-mxc/ehci.c
> @@ -186,6 +186,10 @@ int mxc_set_usbcontrol(int port, unsigned int flags)
> return 0;
> }
> #endif /* CONFIG_MACH_MX27 */
> +#ifdef CONFIG_ARCH_MX5
> + /* Nothing needs to be done for MX5 here */
> + return 0;
> +#endif
This needs a cpu_is_mx5() condition. For now that's just nit-picking,
but once another platform is added, the statement will return where it
shouldn't.
Daniel
On Tue, Apr 13, 2010 at 11:10:24AM -0500, [email protected] wrote:
> From: Dinh Nguyen <[email protected]>
>
> Update /plat-mxc/gpio.c to support Freescale's MX51 Babbage HW.
> This patch applies to 2.6.34-rc4.
>
> Signed-off-by: Dinh Nguyen <[email protected]>
> ---
> arch/arm/mach-mx5/board-mx51_babbage.c | 5 +++-
> arch/arm/mach-mx5/devices.c | 33 ++++++++++++++++++++++++++++++-
> arch/arm/plat-mxc/gpio.c | 32 +++++++++++++++++++++++++-----
> 3 files changed, 61 insertions(+), 9 deletions(-)
>
> diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
> index ee67a71..afbe400 100644
> --- a/arch/arm/mach-mx5/board-mx51_babbage.c
> +++ b/arch/arm/mach-mx5/board-mx51_babbage.c
> @@ -1,5 +1,5 @@
> /*
> - * Copyright 2009 Freescale Semiconductor, Inc. All Rights Reserved.
> + * Copyright (C) 2009-2010 Freescale Semiconductor, Inc. All Rights Reserved.
> * Copyright (C) 2009-2010 Amit Kucheria <[email protected]>
> *
> * The code contained herein is licensed under the GNU General Public
> @@ -12,6 +12,7 @@
>
> #include <linux/init.h>
> #include <linux/platform_device.h>
> +#include <linux/gpio.h>
>
> #include <mach/common.h>
> #include <mach/hardware.h>
> @@ -75,6 +76,8 @@ static void __init mxc_board_init(void)
> ARRAY_SIZE(mx51babbage_pads));
> mxc_init_imx_uart();
> platform_add_devices(devices, ARRAY_SIZE(devices));
> +
> + mxc_register_gpios();
On other i.MXs this is called in plat-mxc/irq.c. It should be called in
plat-mxc/tzic.c then to avoid having this call in every board.
> }
>
> static void __init mx51_babbage_timer_init(void)
> diff --git a/arch/arm/mach-mx5/devices.c b/arch/arm/mach-mx5/devices.c
> index d6fd396..73f2342 100644
> --- a/arch/arm/mach-mx5/devices.c
> +++ b/arch/arm/mach-mx5/devices.c
> @@ -1,5 +1,6 @@
> /*
> * Copyright 2009 Amit Kucheria <[email protected]>
> + * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
> *
> * The code contained herein is licensed under the GNU General Public
> * License. You may obtain a copy of the GNU General Public License
> @@ -11,7 +12,9 @@
>
> #include <linux/platform_device.h>
> #include <mach/hardware.h>
> +#include <mach/gpio.h>
> #include <mach/imx-uart.h>
> +#include <mach/irqs.h>
>
> static struct resource uart0[] = {
> {
> @@ -89,8 +92,34 @@ struct platform_device mxc_fec_device = {
> .resource = mxc_fec_resources,
> };
>
> -/* Dummy definition to allow compiling in AVIC and TZIC simultaneously */
> +struct mxc_gpio_port mxc_gpio_ports[] = {
static please
> + {
> + .chip.label = "gpio-0",
> + .base = MX51_IO_ADDRESS(MX51_GPIO1_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO1_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START
> + },
> + {
> + .chip.label = "gpio-1",
> + .base = MX51_IO_ADDRESS(MX51_GPIO2_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO2_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 1
> + },
> + {
> + .chip.label = "gpio-2",
> + .base = MX51_IO_ADDRESS(MX51_GPIO3_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO3_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 2
> + },
> + {
> + .chip.label = "gpio-3",
> + .base = MX51_IO_ADDRESS(MX51_GPIO4_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO4_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 3
> + },
> +};
> +
> int __init mxc_register_gpios(void)
> {
> - return 0;
> + return mxc_gpio_init(mxc_gpio_ports, 4);
> }
> diff --git a/arch/arm/plat-mxc/gpio.c b/arch/arm/plat-mxc/gpio.c
> index 70b2389..1df23b2 100644
> --- a/arch/arm/plat-mxc/gpio.c
> +++ b/arch/arm/plat-mxc/gpio.c
> @@ -3,7 +3,7 @@
> * Copyright 2008 Juergen Beisert, [email protected]
> *
> * Based on code from Freescale,
> - * Copyright 2004-2006 Freescale Semiconductor, Inc. All Rights Reserved.
> + * Copyright (C) 2004-2010 Freescale Semiconductor, Inc. All Rights Reserved.
> *
> * This program is free software; you can redistribute it and/or
> * modify it under the terms of the GNU General Public License
> @@ -38,7 +38,6 @@ static int gpio_table_size;
> #define GPIO_ICR2 (cpu_is_mx1_mx2() ? 0x2C : 0x10)
> #define GPIO_IMR (cpu_is_mx1_mx2() ? 0x30 : 0x14)
> #define GPIO_ISR (cpu_is_mx1_mx2() ? 0x34 : 0x18)
> -#define GPIO_ISR (cpu_is_mx1_mx2() ? 0x34 : 0x18)
>
> #define GPIO_INT_LOW_LEV (cpu_is_mx1_mx2() ? 0x3 : 0x0)
> #define GPIO_INT_HIGH_LEV (cpu_is_mx1_mx2() ? 0x2 : 0x1)
> @@ -171,6 +170,25 @@ static void mxc_gpio_irq_handler(struct mxc_gpio_port *port, u32 irq_stat)
> }
> }
>
> +/* one interrupt *per* gpio port */
> +static void mx5_gpio_irq_handler(u32 irq, struct irq_desc *desc)
> +{
> + u32 irq_stat;
> + u32 mask = 0xFFFFFFFF;
> + struct mxc_gpio_port *port = (struct mxc_gpio_port *)get_irq_data(irq);
> +
> +#ifdef MXC_GPIO_SPLIT_IRQ_2
> + if (irq == port->irq)
> + mask = 0x0000FFFF;
> + else
> + mask = 0xFFFF0000;
> +#endif
> +
> + irq_stat = __raw_readl(port->base + GPIO_ISR) &
> + (__raw_readl(port->base + GPIO_IMR) & mask);
> + mxc_gpio_irq_handler(port, irq_stat);
> +}
> +
> /* MX1 and MX3 has one interrupt *per* gpio port */
> static void mx3_gpio_irq_handler(u32 irq, struct irq_desc *desc)
> {
> @@ -289,11 +307,13 @@ int __init mxc_gpio_init(struct mxc_gpio_port *port, int cnt)
> /* its a serious configuration bug when it fails */
> BUG_ON( gpiochip_add(&port[i].chip) < 0 );
>
> - if (cpu_is_mx1() || cpu_is_mx3() || cpu_is_mx25()) {
> - /* setup one handler for each entry */
> + /* setup one handler for each entry */
> + if (cpu_is_mx1() || cpu_is_mx3() || cpu_is_mx25())
> set_irq_chained_handler(port[i].irq, mx3_gpio_irq_handler);
> - set_irq_data(port[i].irq, &port[i]);
> - }
> + else if (cpu_is_mx51())
> + set_irq_chained_handler(port[i].irq, mx5_gpio_irq_handler);
> +
> + set_irq_data(port[i].irq, &port[i]);
> }
>
> if (cpu_is_mx2()) {
> --
> 1.6.0.4
>
>
--
Pengutronix e.K. | |
Industrial Linux Solutions | http://www.pengutronix.de/ |
Peiner Str. 6-8, 31137 Hildesheim, Germany | Phone: +49-5121-206917-0 |
Amtsgericht Hildesheim, HRA 2686 | Fax: +49-5121-206917-5555 |
On Tue, Apr 13, 2010 at 11:10:26AM -0500, [email protected] wrote:
> This patch is part of enabling USB for Freescale MX51 Babbage HW. This
> patch performs some platform specific USB HW initialization, and adds
> the necessary defines.
>
> This patch applies to 2.6.34-rc4.
>
> Signed-off-by: Dinh Nguyen <[email protected]>
> ---
> arch/arm/plat-mxc/Makefile | 2 +-
> arch/arm/plat-mxc/include/mach/mxc_ehci.h | 48 +++++++
> arch/arm/plat-mxc/usb_common.c | 190 +++++++++++++++++++++++++++++
> 3 files changed, 239 insertions(+), 1 deletions(-)
> create mode 100644 arch/arm/plat-mxc/usb_common.c
There are several general problems with this.
The functions you implement here are not at all common but purely
specific to mx51, so the name of the file and functions as well as the
location in the tree is plainly wrong.
Also, this code also completely ignores all the work that has been done
to keep things generic as much as possible. See below.
> diff --git a/arch/arm/plat-mxc/Makefile b/arch/arm/plat-mxc/Makefile
> index 895bc3c..fa8ed78 100644
> --- a/arch/arm/plat-mxc/Makefile
> +++ b/arch/arm/plat-mxc/Makefile
> @@ -3,7 +3,7 @@
> #
>
> # Common support
> -obj-y := irq.o clock.o gpio.o time.o devices.o cpu.o system.o
> +obj-y := irq.o clock.o gpio.o time.o devices.o cpu.o system.o usb_common.o
>
> # MX51 uses the TZIC interrupt controller, older platforms use AVIC (irq.o)
> obj-$(CONFIG_MXC_TZIC) += tzic.o
> diff --git a/arch/arm/plat-mxc/include/mach/mxc_ehci.h b/arch/arm/plat-mxc/include/mach/mxc_ehci.h
> index 4b9b836..6edf8d7 100644
> --- a/arch/arm/plat-mxc/include/mach/mxc_ehci.h
> +++ b/arch/arm/plat-mxc/include/mach/mxc_ehci.h
> @@ -1,6 +1,30 @@
> #ifndef __INCLUDE_ASM_ARCH_MXC_EHCI_H
> #define __INCLUDE_ASM_ARCH_MXC_EHCI_H
>
> +#define USBOTG_OFFSET 0
> +#define USBH1_OFFSET 0x200
> +#define USBH2_OFFSET 0x400
> +#define USBH3_OFFSET 0x600
> +#define USBOTHER_REGS_OFFSET 0x800
> +
> +#define USBCMD_OFFSET 0x140
> +
> +#define ULPI_VIEWPORT_OFFSET 0x170
> +#define PORTSC_OFFSET 0x184
> +#define USBMODE_OFFSET 0x1a8
> +#define USBMODE_CM_HOST 3
> +
> +#define USBCTRL_OFFSET 0
> +#define USB_PHY_CTR_FUNC_OFFSET 0x8
> +#define USB_PHY_CTR_FUNC2_OFFSET 0xc
> +#define USB_CTRL_1_OFFSET 0x10
> +
> +
> +/* USBCMD */
> +#define UCMD_RUN_STOP (1 << 0) /* controller run/stop */
> +#define UCMD_RESET (1 << 1) /* controller reset */
> +#define UCMD_ITC_NO_THRESHOLD ~(0xff << 16) /* Interrupt Threshold Control */
> +
> /* values for portsc field */
> #define MXC_EHCI_PHY_LOW_POWER_SUSPEND (1 << 23)
> #define MXC_EHCI_FORCE_FS (1 << 24)
> @@ -26,6 +50,30 @@
> #define MXC_EHCI_IPPUE_DOWN (1 << 8)
> #define MXC_EHCI_IPPUE_UP (1 << 9)
>
> +/* USB_CTRL */
> +#define UCTRL_OUIE (1 << 28) /* OTG ULPI intr enable */
> +#define UCTRL_OWIE (1 << 27) /* OTG wakeup intr enable */
> +#define UCTRL_OBPVAL_RXDP (1 << 26) /* OTG RxDp status in bypass mode */
> +#define UCTRL_OBPVAL_RXDM (1 << 25) /* OTG RxDm status in bypass mode */
> +#define UCTRL_OPM (1 << 24) /* OTG power mask */
> +#define UCTRL_H1UIE (1 << 12) /* Host1 ULPI interrupt enable */
> +#define UCTRL_H1WIE (1 << 11) /* HOST1 wakeup intr enable */
> +#define UCTRL_H1PM (1 << 8) /* HOST1 power mask */
> +
> +/* USB_PHY_CTRL_FUNC */
> +#define USB_UTMI_PHYCTRL_OC_DIS (1 << 8) /* OTG Disable Overcurrent Event */
> +#define USB_UH1_OC_DIS (1 << 5) /* UH1 Disable Overcurrent Event */
> +
> +/* USB_CTRL_1 */
> +#define USB_CTRL_UH1_EXT_CLK_EN (1 << 25)
> +#define USB_CTRL_UH2_EXT_CLK_EN (1 << 26)
> +
> +/* USB_PHY_CTRL_FUNC2*/
> +#define USB_UTMI_PHYCTRL2_PLLDIV_MASK 0x3
> +#define USB_UTMI_PHYCTRL2_PLLDIV_SHIFT 0
> +#define USB_UTMI_PHYCTRL2_HSDEVSEL_MASK 0x3
> +#define USB_UTMI_PHYCTRL2_HSDEVSEL_SHIFT 19
> +
> struct mxc_usbh_platform_data {
> int (*init)(struct platform_device *pdev);
> int (*exit)(struct platform_device *pdev);
> diff --git a/arch/arm/plat-mxc/usb_common.c b/arch/arm/plat-mxc/usb_common.c
> new file mode 100644
> index 0000000..b06c66e
> --- /dev/null
> +++ b/arch/arm/plat-mxc/usb_common.c
> @@ -0,0 +1,190 @@
> +/*
> + * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
> + *
> + * 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.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, write to the Free Software
> + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
> + * MA 02110-1301, USA.
> + */
> +
> +/*
> + *Include files
> + */
> +#include <linux/module.h>
> +#include <linux/kernel.h>
> +#include <linux/delay.h>
> +#include <linux/io.h>
> +#include <linux/fsl_devices.h>
> +#include <mach/mxc_ehci.h>
> +#include <mach/hardware.h>
> +
> +static void usbh1_set_ulpi_xcvr(void)
> +{
> + u32 reg_value;
> + pr_debug("%s: \n", __func__);
> + void __iomem *usb_base = ioremap(MX51_OTG_BASE_ADDR, SZ_4K);
You shouldn't mix declarations and code like this. The compiler should
also have complained.
> + u32 usbh1_base = (u32)usb_base + USBH1_OFFSET;
> + u32 usbother_base = (u32)usb_base + USBOTHER_REGS_OFFSET;
> +
> + /* Stop then Reset */
> + reg_value = __raw_readl(usbh1_base + USBCMD_OFFSET);
> + reg_value &= ~UCMD_RUN_STOP;
> + __raw_writel(reg_value, usbh1_base + USBCMD_OFFSET);
> + while (__raw_readl(usbh1_base + USBCMD_OFFSET) & UCMD_RUN_STOP);
This isn't good. If the above condition will never become true, the
kernel hangs in an endless loop. There should be a timeout and a call to
cpu_relax().
> + reg_value = __raw_readl(usbh1_base + USBCMD_OFFSET);
> + reg_value |= UCMD_RESET;
> + __raw_writel(reg_value, usbh1_base + USBCMD_OFFSET);
> + while (__raw_readl(usbh1_base + USBCMD_OFFSET) & UCMD_RESET);
Dito.
> + reg_value = __raw_readl(usbother_base + USB_CTRL_1_OFFSET);
> + __raw_writel(reg_value | USB_CTRL_UH1_EXT_CLK_EN, usbother_base + USB_CTRL_1_OFFSET);
> +
> + /* select ULPI PHY PTS=2 */
> + reg_value = __raw_readl(usbh1_base + PORTSC_OFFSET);
> + reg_value &= ~MXC_EHCI_MODE_SERIAL;
> + __raw_writel(reg_value |= MXC_EHCI_MODE_ULPI, usbh1_base + PORTSC_OFFSET);
> +
> + reg_value = __raw_readl(usbother_base + USBCTRL_OFFSET);
> + reg_value &= ~(UCTRL_H1WIE | UCTRL_H1UIE);/* HOST1 wakeup/ULPI intr disable */
> + reg_value |= UCTRL_H1PM; /* HOST1 power mask */
> + __raw_writel(reg_value, usbother_base + USBCTRL_OFFSET);
> +
> + reg_value = __raw_readl(usbother_base + USB_PHY_CTR_FUNC_OFFSET);
> + reg_value |= USB_UH1_OC_DIS; /* OC is not used */
> + __raw_writel(reg_value, usbother_base + USB_PHY_CTR_FUNC_OFFSET);
> +
> + reg_value = __raw_readl(usbh1_base + USBCMD_OFFSET);
> + /* Interrupt Threshold Control:Immediate (no threshold) */
> + reg_value &= UCMD_ITC_NO_THRESHOLD;
> + __raw_writel(reg_value, usbh1_base + USBCMD_OFFSET);
> +
> + /* reset the controller */
> + reg_value = __raw_readl(usbh1_base + USBCMD_OFFSET);
> + reg_value |= UCMD_RESET;
> + __raw_writel(reg_value, usbh1_base + USBCMD_OFFSET);
These are all settings specific to the actual board implementation, and
these cases are exactly what the abstract layer was invented for.
In general, the code above should be made a lot more versatile and also
be put in plat-mxc/ehci.c. Look at the implementations of mx2 and mx3
and see how things are done there.
> +
> + iounmap(usb_base);
> +
> + /* allow controller to reset, and leave time for
> + * the ULPI transceiver to reset too.
> + */
> + msleep(100);
> +}
> +
> +int fsl_usb_host_init(struct platform_device *pdev)
> +{
> + pr_debug("%s: pdev=0x%p\n", __func__, pdev);
> +
> + usbh1_set_ulpi_xcvr();
> +
> + pr_debug("%s: success\n", __func__);
> + return 0;
> +}
> +EXPORT_SYMBOL(fsl_usb_host_init);
> +
> +int fsl_usb_host_uninit(struct fsl_usb2_platform_data *pdata)
> +{
> + pr_debug("%s\n", __func__);
> + return 0;
> +}
> +EXPORT_SYMBOL(fsl_usb_host_uninit);
> +
> +static void otg_set_utmi_xcvr(void)
> +{
> + u32 reg_value;
> + void __iomem *usb_base = ioremap(MX51_OTG_BASE_ADDR, SZ_4K);
> + u32 usbotg_base = (u32)usb_base + USBOTG_OFFSET;
> + u32 usbother_base = (u32)usb_base + USBOTHER_REGS_OFFSET;
> +
> + pr_debug("otg_set_utmi_xcvr\n");
> +
> + /* Stop then Reset */
> + reg_value = __raw_readl(usbotg_base + USBCMD_OFFSET);
> + reg_value &= ~UCMD_RUN_STOP;
> + __raw_writel(reg_value, usbotg_base + USBCMD_OFFSET);
> + while (__raw_readl(usbotg_base + USBCMD_OFFSET) & UCMD_RUN_STOP);
> +
> + reg_value = __raw_readl(usbotg_base + USBCMD_OFFSET);
> + reg_value |= UCMD_RESET;
> + __raw_writel(reg_value, usbotg_base + USBCMD_OFFSET);
> + while (__raw_readl(usbotg_base + USBCMD_OFFSET) & UCMD_RESET);
> +
> + reg_value = __raw_readl(usbother_base + USB_PHY_CTR_FUNC_OFFSET);
> + reg_value |= USB_UTMI_PHYCTRL_OC_DIS; /* OC is not used */
> + __raw_writel(reg_value, usbother_base + USB_PHY_CTR_FUNC_OFFSET);
> +
> + reg_value = __raw_readl(usbother_base + USBCTRL_OFFSET);
> + reg_value &= ~(UCTRL_OPM | UCTRL_OWIE);/* OTG wakeup/power mask disable */
> + __raw_writel(reg_value, usbother_base + USBCTRL_OFFSET);
> +
> + /* set UTMI xcvr */
> + reg_value = __raw_readl(usbotg_base + PORTSC_OFFSET);
> + reg_value &= ~MXC_EHCI_MODE_SERIAL;
> + __raw_writel(reg_value |= MXC_EHCI_MODE_UTMI, usbotg_base + PORTSC_OFFSET);
> +
> + /* Set the PHY clock to 19.2MHz */
> + reg_value = __raw_readl(usbother_base + USB_PHY_CTR_FUNC2_OFFSET);
> + reg_value &= ~USB_UTMI_PHYCTRL2_PLLDIV_MASK;
> + reg_value |= 0x01;
> + __raw_writel(reg_value, usbother_base + USB_PHY_CTR_FUNC2_OFFSET);
> +
> + /* Workaround an IC issue for ehci driver:
> + * when turn off root hub port power, EHCI set
> + * PORTSC reserved bits to be 0, but PTW with 0
> + * means 8 bits tranceiver width, here change
> + * it back to be 16 bits and do PHY diable and
> + * then enable.
> + */
> + reg_value = __raw_readl(usbotg_base + PORTSC_OFFSET);
> + reg_value |= MXC_EHCI_UTMI_16BIT;
> + __raw_writel(reg_value, usbotg_base + PORTSC_OFFSET);
> +
> + /* need to reset the controller here so that the ID pin
> + * is correctly detected.
> + */
> + /* Stop then Reset */
> + reg_value = __raw_readl(usbotg_base + USBCMD_OFFSET);
> + reg_value &= ~UCMD_RUN_STOP;
> + __raw_writel(reg_value, usbotg_base + USBCMD_OFFSET);
> + while (__raw_readl(usbotg_base + USBCMD_OFFSET) & UCMD_RUN_STOP);
> +
> + reg_value = __raw_readl(usbotg_base + USBCMD_OFFSET);
> + reg_value |= UCMD_RESET;
> + __raw_writel(reg_value, usbotg_base + USBCMD_OFFSET);
> + while (__raw_readl(usbotg_base + USBCMD_OFFSET) & UCMD_RESET);
> +
> + iounmap(usb_base);
> + /* allow controller to reset, and leave time for
> + * the ULPI transceiver to reset too.
> + */
> + msleep(100);
> +}
> +
> +int usbotg_init(struct platform_device *pdev)
> +{
> + pr_debug("%s: pdev=0x%p\n", __func__, pdev);
> +
> + otg_set_utmi_xcvr();
> +
> + pr_debug("%s: success\n", __func__);
> + return 0;
> +}
> +EXPORT_SYMBOL(usbotg_init);
> +
> +int usbotg_uninit(struct platform_device *pdev)
> +{
> + pr_debug("%s\n", __func__);
> + return 0;
> +}
> +EXPORT_SYMBOL(usbotg_uninit);
The second half of the file is just a copy of the first, and it is just
there because things are not abstracted but hard-coded.
On Tue, Apr 13, 2010 at 11:10:27AM -0500, [email protected] wrote:
> This patch adds the device platform registration for enabling USB
> host functionality on the OTG port on Freescale MX51 Babbage HW. This
> file makes platform specific calls to initialize the USB HW.
>
> This patch applies to 2.6.34-rc4.
>
> Signed-off-by: Dinh Nguyen <[email protected]>
> ---
> arch/arm/mach-mx5/Makefile | 2 +-
> arch/arm/mach-mx5/board-mx51_babbage.c | 4 ++
> arch/arm/mach-mx5/usb_dr.c | 57 ++++++++++++++++++++++++++++++++
> 3 files changed, 62 insertions(+), 1 deletions(-)
> create mode 100644 arch/arm/mach-mx5/usb_dr.c
>
> diff --git a/arch/arm/mach-mx5/Makefile b/arch/arm/mach-mx5/Makefile
> index bf23f86..3fca1f1 100644
> --- a/arch/arm/mach-mx5/Makefile
> +++ b/arch/arm/mach-mx5/Makefile
> @@ -3,7 +3,7 @@
> #
>
> # Object file lists.
> -obj-y := cpu.o mm.o clock-mx51.o devices.o
> +obj-y := cpu.o mm.o clock-mx51.o devices.o usb_dr.o
>
> obj-$(CONFIG_MACH_MX51_BABBAGE) += board-mx51_babbage.o
>
> diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
> index afbe400..4e196d7 100644
> --- a/arch/arm/mach-mx5/board-mx51_babbage.c
> +++ b/arch/arm/mach-mx5/board-mx51_babbage.c
> @@ -27,6 +27,8 @@
>
> #include "devices.h"
>
> +extern void __init mx5_usb_dr_init(void);
> +
> static struct platform_device *devices[] __initdata = {
> &mxc_fec_device,
> };
> @@ -78,6 +80,8 @@ static void __init mxc_board_init(void)
> platform_add_devices(devices, ARRAY_SIZE(devices));
>
> mxc_register_gpios();
> +
> + mx5_usb_dr_init();
> }
>
> static void __init mx51_babbage_timer_init(void)
> diff --git a/arch/arm/mach-mx5/usb_dr.c b/arch/arm/mach-mx5/usb_dr.c
> new file mode 100644
> index 0000000..52273ea
> --- /dev/null
> +++ b/arch/arm/mach-mx5/usb_dr.c
> @@ -0,0 +1,57 @@
> +/*
> + * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
> + *
> + * 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.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, write to the Free Software
> + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
> + * MA 02110-1301, USA.
> + */
> +
> +#include <linux/platform_device.h>
> +#include <mach/mxc_ehci.h>
> +#include <mach/common.h>
> +#include "devices.h"
> +
> +extern int usbotg_init(struct platform_device *pdev);
> +extern int usbotg_uninit(struct platform_device *pdev);
> +
> +static int usbotg_init_ext(struct platform_device *pdev);
> +static int usbotg_uninit_ext(struct platform_device *pdev);
> +
> +/*
> + * platform data structs
> + * - Which one to use is determined by CONFIG options in usb.h
> + * - operating_mode plugged at run time
> + */
> +static struct mxc_usbh_platform_data dr_utmi_config = {
> + .init = usbotg_init_ext,
> + .exit = usbotg_uninit_ext,
> + .portsc = MXC_EHCI_UTMI_16BIT,
> + .flags = MXC_EHCI_INTERNAL_PHY,
> +};
This is also board specific, and nothing you should assume for all
boards. Other implementations may do this differntly, which is why
this belongs to board code.
> +/* Notes: configure USB clock*/
> +static int usbotg_init_ext(struct platform_device *pdev)
> +{
> + return usbotg_init(pdev);
> +}
> +
> +static int usbotg_uninit_ext(struct platform_device *pdev)
> +{
> + return usbotg_uninit(pdev);
> +}
> +
> +void __init mx5_usb_dr_init(void)
> +{
> + mxc_register_device(&mxc_usbdr_host_device, &dr_utmi_config);
> +}
What's the reason for having the _ext variants that are just wrapers?
On Tue, Apr 13, 2010 at 11:10:28AM -0500, [email protected] wrote:
> diff --git a/arch/arm/mach-mx5/usb_h1.c b/arch/arm/mach-mx5/usb_h1.c
> new file mode 100644
> index 0000000..23ae336
> --- /dev/null
> +++ b/arch/arm/mach-mx5/usb_h1.c
> @@ -0,0 +1,90 @@
> +/*
> + * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
> + *
> + * 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.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, write to the Free Software
> + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
> + * MA 02110-1301, USA.
> + */
> +
> +#include <linux/delay.h>
> +#include <linux/gpio.h>
> +#include <linux/platform_device.h>
> +#include <mach/iomux-mx51.h>
> +#include <mach/mxc_ehci.h>
> +#include <mach/common.h>
> +#include "devices.h"
> +
> +#define GPIO1_27 (0*32 +27)
I'm confident there is a better definition for this already ;)
> +
> +extern int fsl_usb_host_init(struct platform_device *pdev);
> +extern int fsl_usb_host_uninit(struct fsl_usb2_platform_data *pdata);
> +
> +static int fsl_usb_host_init_ext(struct platform_device *pdev);
> +static int fsl_usb_host_uninit_ext(struct platform_device *pdev);
> +
> +static struct mxc_usbh_platform_data usbh1_config = {
> + .init = fsl_usb_host_init_ext,
> + .exit = fsl_usb_host_uninit_ext,
> + .portsc = MXC_EHCI_MODE_ULPI,
> + .flags = MXC_EHCI_POWER_PINS_ENABLED,
> +};
This is actually the way to go. All driver code in lower layers should
use these flags eventually, and no assumptions should be hard-coded
anywhere.
> +/*
> + * USB Host1 HS port
> + */
> +static int gpio_usbh1_active(void)
> +{
> + struct pad_desc usbh1stp_gpio = MX51_PAD_GPIO_1_27__USBH1_STP_ERR;
> + int ret;
> +
> + /* Set USBH1_STP to GPIO and toggle it */
> + mxc_iomux_v3_setup_pad(&usbh1stp_gpio);
> + ret = gpio_request(GPIO1_27, "usbh1_stp");
> +
> + if (ret) {
> + pr_debug("failed to get USBH1_STP_GPIO1_27: %d\n", ret);
> + return ret;
> + }
> + gpio_direction_output(GPIO1_27, 0);
> + gpio_set_value(GPIO1_27, 1);
> +
> + msleep(100);
> + gpio_free(GPIO1_27);
> + return 0;
> +}
> +
> +static int fsl_usb_host_init_ext(struct platform_device *pdev)
> +{
> + int ret;
> + struct pad_desc usbh1stp = MX51_PAD_GPIO_1_27__USBH1_STP;
> +
> + gpio_usbh1_active();
> + ret = fsl_usb_host_init(pdev);
> + if (ret)
> + return ret;
> +
> + /* setback USBH1_STP to be function */
> + mxc_iomux_v3_setup_pad(&usbh1stp);
> + return 0;
> +}
> +
> +static int fsl_usb_host_uninit_ext(struct platform_device *pdev)
> +{
> + return fsl_usb_host_uninit(pdev);
> +}
> +void __init mx5_usbh1_init(void)
> +{
> + mxc_register_device(&mxc_usbh1_device, &usbh1_config);
> +}
> +
> --
> 1.6.0.4
>
>
> _______________________________________________
> linux-arm-kernel mailing list
> [email protected]
> http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
On Tue, Apr 13, 2010 at 11:10:29AM -0500, [email protected] wrote:
> This patch updates the clocks, gpios, iomuxing and device structures for
> enabling USB Host functionality on Freescale MX51 Babbage HW.
> This patch applies to 2.6.34-rc4.
>
> Signed-off-by: Dinh Nguyen <[email protected]>
> ---
> arch/arm/mach-mx5/board-mx51_babbage.c | 40 +++++++++++++++++++++++++-
> arch/arm/mach-mx5/clock-mx51.c | 8 +++++
> arch/arm/mach-mx5/devices.c | 49 ++++++++++++++++++++++++++++++++
> arch/arm/mach-mx5/devices.h | 2 +
> 4 files changed, 98 insertions(+), 1 deletions(-)
That should be split in two patches - one for common code and one for
the board definition.
>
> diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
> index 1338d6a..ddfa48b 100644
> --- a/arch/arm/mach-mx5/board-mx51_babbage.c
> +++ b/arch/arm/mach-mx5/board-mx51_babbage.c
> @@ -13,6 +13,7 @@
> #include <linux/init.h>
> #include <linux/platform_device.h>
> #include <linux/gpio.h>
> +#include <linux/delay.h>
>
> #include <mach/common.h>
> #include <mach/hardware.h>
> @@ -30,6 +31,8 @@
> extern void __init mx5_usb_dr_init(void);
> extern void __init mx5_usbh1_init(void);
>
> +#define GPIO_1_7 (0*32+7)
> +
> static struct platform_device *devices[] __initdata = {
> &mxc_fec_device,
> };
> @@ -50,6 +53,22 @@ static struct pad_desc mx51babbage_pads[] = {
> MX51_PAD_EIM_D26__UART3_TXD,
> MX51_PAD_EIM_D27__UART3_RTS,
> MX51_PAD_EIM_D24__UART3_CTS,
> +
> + /* USB HOST1 */
> + MX51_PAD_GPIO_1_25__USBH1_CLK,
> + MX51_PAD_GPIO_1_26__USBH1_DIR,
> + MX51_PAD_GPIO_1_28__USBH1_NXT,
> + MX51_PAD_GPIO_1_11__USBH1_DATA0,
> + MX51_PAD_GPIO_1_12__USBH1_DATA1,
> + MX51_PAD_GPIO_1_13__USBH1_DATA2,
> + MX51_PAD_GPIO_1_14__USBH1_DATA3,
> + MX51_PAD_GPIO_1_15__USBH1_DATA4,
> + MX51_PAD_GPIO_1_16__USBH1_DATA5,
> + MX51_PAD_GPIO_1_17__USBH1_DATA6,
> + MX51_PAD_GPIO_1_18__USBH1_DATA7,
> +
> + /* USB HUB reset line*/
> + MX51_PAD_GPIO_1_7__GPIO1_7,
> };
>
> /* Serial ports */
> @@ -64,12 +83,31 @@ static inline void mxc_init_imx_uart(void)
> mxc_register_device(&mxc_uart_device1, &uart_pdata);
> mxc_register_device(&mxc_uart_device2, &uart_pdata);
> }
> -#else /* !SERIAL_IMX */
> +#else /* SERIAL_IMX */
> static inline void mxc_init_imx_uart(void)
> {
> }
> #endif /* SERIAL_IMX */
>
> +static inline void mx5_babbage_usbhub_reset(void)
> +{
> + int ret;
> +
> + /* Bring USB hub out of reset */
> + ret = gpio_request(GPIO_1_7, "GPIO1_7");
> + if (ret) {
> + printk("failed to get GPIO_1_7: %d\n", ret);
> + return;
> + }
> + gpio_direction_output(GPIO_1_7, 0);
> +
> + /* USB HUB RESET - De-assert USB HUB RESET_N */
> + msleep(1);
> + gpio_set_value(GPIO_1_7, 0);
> + msleep(1);
> + gpio_set_value(GPIO_1_7, 1);
> +}
> +
> /*
> * Board specific initialization.
> */
> diff --git a/arch/arm/mach-mx5/clock-mx51.c b/arch/arm/mach-mx5/clock-mx51.c
> index 8f85f73..36684d0 100644
> --- a/arch/arm/mach-mx5/clock-mx51.c
> +++ b/arch/arm/mach-mx5/clock-mx51.c
> @@ -765,6 +765,10 @@ DEFINE_CLOCK(gpt_ipg_clk, 0, MXC_CCM_CCGR2, MXC_CCM_CCGRx_CG10_OFFSET,
> DEFINE_CLOCK(fec_clk, 0, MXC_CCM_CCGR2, MXC_CCM_CCGRx_CG12_OFFSET,
> NULL, NULL, &ipg_clk, NULL);
>
> +/* USB */
> +DEFINE_CLOCK(usboh3_clk, 0, MXC_CCM_CCGR2, MXC_CCM_CCGRx_CG14_OFFSET,
> + NULL, NULL, &pll3_sw_clk, NULL);
> +
> #define _REGISTER_CLOCK(d, n, c) \
> { \
> .dev_id = d, \
> @@ -778,6 +782,10 @@ static struct clk_lookup lookups[] = {
> _REGISTER_CLOCK("imx-uart.2", NULL, uart3_clk)
> _REGISTER_CLOCK(NULL, "gpt", gpt_clk)
> _REGISTER_CLOCK("fec.0", NULL, fec_clk)
> + _REGISTER_CLOCK("mxc-ehci.0", "usb", usboh3_clk)
> + _REGISTER_CLOCK("mxc-ehci.0", "usb_ahb", ahb_clk)
> + _REGISTER_CLOCK("mxc-ehci.1", "usb", usboh3_clk)
> + _REGISTER_CLOCK("mxc-ehci.1", "usb_ahb", ahb_clk)
> };
>
> static void clk_tree_init(void)
> diff --git a/arch/arm/mach-mx5/devices.c b/arch/arm/mach-mx5/devices.c
> index 73f2342..3d8f66a 100644
> --- a/arch/arm/mach-mx5/devices.c
> +++ b/arch/arm/mach-mx5/devices.c
> @@ -11,6 +11,7 @@
> */
>
> #include <linux/platform_device.h>
> +#include <linux/dma-mapping.h>
> #include <mach/hardware.h>
> #include <mach/gpio.h>
> #include <mach/imx-uart.h>
> @@ -92,6 +93,54 @@ struct platform_device mxc_fec_device = {
> .resource = mxc_fec_resources,
> };
>
> +static u64 usb_dma_mask = DMA_BIT_MASK(32);
> +
> +static struct resource usbotg_resources[] = {
> + {
> + .start = MX51_OTG_BASE_ADDR,
> + .end = MX51_OTG_BASE_ADDR + 0x1ff,
> + .flags = IORESOURCE_MEM,
> + },
> + {
> + .start = MX51_MXC_INT_USB_OTG,
> + .flags = IORESOURCE_IRQ,
> + },
> +};
> +
> +struct platform_device mxc_usbdr_host_device = {
> + .name = "mxc-ehci",
> + .id = 0,
> + .num_resources = ARRAY_SIZE(usbotg_resources),
> + .resource = usbotg_resources,
> + .dev = {
> + .dma_mask = &usb_dma_mask,
> + .coherent_dma_mask = DMA_BIT_MASK(32),
> + },
> +};
> +
> +static struct resource usbh1_resources[] = {
> + {
> + .start = MX51_OTG_BASE_ADDR + 0x200,
> + .end = MX51_OTG_BASE_ADDR + 0x200 + 0x1ff,
> + .flags = IORESOURCE_MEM,
> + },
> + {
> + .start = MX51_MXC_INT_USB_H1,
> + .flags = IORESOURCE_IRQ,
> + },
> +};
> +
> +struct platform_device mxc_usbh1_device = {
> + .name = "mxc-ehci",
> + .id = 1,
> + .num_resources = ARRAY_SIZE(usbh1_resources),
> + .resource = usbh1_resources,
> + .dev = {
> + .dma_mask = &usb_dma_mask,
> + .coherent_dma_mask = DMA_BIT_MASK(32),
> + },
> +};
> +
> struct mxc_gpio_port mxc_gpio_ports[] = {
> {
> .chip.label = "gpio-0",
> diff --git a/arch/arm/mach-mx5/devices.h b/arch/arm/mach-mx5/devices.h
> index f339ab8..95c45f9 100644
> --- a/arch/arm/mach-mx5/devices.h
> +++ b/arch/arm/mach-mx5/devices.h
> @@ -2,3 +2,5 @@ extern struct platform_device mxc_uart_device0;
> extern struct platform_device mxc_uart_device1;
> extern struct platform_device mxc_uart_device2;
> extern struct platform_device mxc_fec_device;
> +extern struct platform_device mxc_usbdr_host_device;
> +extern struct platform_device mxc_usbh1_device;
> --
> 1.6.0.4
>
>
> _______________________________________________
> linux-arm-kernel mailing list
> [email protected]
> http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
-----Original Message-----
From: Daniel Mack [mailto:[email protected]]
Sent: Tuesday, April 13, 2010 11:46 AM
To: Nguyen Dinh-R00091
Cc: [email protected]; [email protected];
[email protected]; [email protected];
[email protected]; Herring Robert-RA7055;
[email protected]; [email protected];
[email protected]
Subject: Re: [PATCH 2.6.34-rc4 1/8] mx5: Add registration of GPIOs for
MX51 Babbage board.
First, I'm glad to see Freescale sending patches for mainline code -
thanks for doing this :)
Other people might give more detailed feedback, but I'll still comment
on some things that caught my eye.
[Dinh-FSL] - Thanks Daniel!
On Tue, Apr 13, 2010 at 11:10:24AM -0500, [email protected]
wrote:
[...]
> index d6fd396..73f2342 100644
> --- a/arch/arm/mach-mx5/devices.c
> +++ b/arch/arm/mach-mx5/devices.c
> @@ -1,5 +1,6 @@
> /*
> * Copyright 2009 Amit Kucheria <[email protected]>
> + * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights
Reserved.
> *
> * The code contained herein is licensed under the GNU General Public
> * License. You may obtain a copy of the GNU General Public License
> @@ -11,7 +12,9 @@
>
> #include <linux/platform_device.h>
> #include <mach/hardware.h>
> +#include <mach/gpio.h>
> #include <mach/imx-uart.h>
> +#include <mach/irqs.h>
>
> static struct resource uart0[] = {
> {
> @@ -89,8 +92,34 @@ struct platform_device mxc_fec_device = {
> .resource = mxc_fec_resources,
> };
>
> -/* Dummy definition to allow compiling in AVIC and TZIC
> simultaneously */
> +struct mxc_gpio_port mxc_gpio_ports[] = {
> + {
> + .chip.label = "gpio-0",
> + .base = MX51_IO_ADDRESS(MX51_GPIO1_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO1_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START
> + },
> + {
> + .chip.label = "gpio-1",
> + .base = MX51_IO_ADDRESS(MX51_GPIO2_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO2_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 1
> + },
> + {
> + .chip.label = "gpio-2",
> + .base = MX51_IO_ADDRESS(MX51_GPIO3_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO3_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 2
> + },
> + {
> + .chip.label = "gpio-3",
> + .base = MX51_IO_ADDRESS(MX51_GPIO4_BASE_ADDR),
> + .irq = MX51_MXC_INT_GPIO4_LOW,
> + .virtual_irq_start = MXC_GPIO_IRQ_START + 32 * 3
> + },
> +};
> +
> int __init mxc_register_gpios(void)
> {
> - return 0;
> + return mxc_gpio_init(mxc_gpio_ports, 4);
Use ARRAY_SIZE() instead of the hard-coded constant.
[Dinh-FSL]: will be corrected
> diff --git a/arch/arm/plat-mxc/gpio.c b/arch/arm/plat-mxc/gpio.c index
> 70b2389..1df23b2 100644
> --- a/arch/arm/plat-mxc/gpio.c
> +++ b/arch/arm/plat-mxc/gpio.c
> @@ -3,7 +3,7 @@
> * Copyright 2008 Juergen Beisert, [email protected]
> *
> * Based on code from Freescale,
> - * Copyright 2004-2006 Freescale Semiconductor, Inc. All Rights
Reserved.
> + * Copyright (C) 2004-2010 Freescale Semiconductor, Inc. All Rights
Reserved.
> *
> * This program is free software; you can redistribute it and/or
> * modify it under the terms of the GNU General Public License @@
> -38,7 +38,6 @@ static int gpio_table_size;
> #define GPIO_ICR2 (cpu_is_mx1_mx2() ? 0x2C : 0x10)
> #define GPIO_IMR (cpu_is_mx1_mx2() ? 0x30 : 0x14)
> #define GPIO_ISR (cpu_is_mx1_mx2() ? 0x34 : 0x18)
> -#define GPIO_ISR (cpu_is_mx1_mx2() ? 0x34 : 0x18)
>
> #define GPIO_INT_LOW_LEV (cpu_is_mx1_mx2() ? 0x3 : 0x0)
> #define GPIO_INT_HIGH_LEV (cpu_is_mx1_mx2() ? 0x2 : 0x1)
> @@ -171,6 +170,25 @@ static void mxc_gpio_irq_handler(struct
mxc_gpio_port *port, u32 irq_stat)
> }
> }
>
> +/* one interrupt *per* gpio port */
> +static void mx5_gpio_irq_handler(u32 irq, struct irq_desc *desc) {
> + u32 irq_stat;
> + u32 mask = 0xFFFFFFFF;
> + struct mxc_gpio_port *port = (struct mxc_gpio_port
> +*)get_irq_data(irq);
> +
> +#ifdef MXC_GPIO_SPLIT_IRQ_2
Where is that macro defined?
[Dinh-FSL] - This macro is optional so that the interrupts can be broken
up into 2 sets.
> + if (irq == port->irq)
> + mask = 0x0000FFFF;
> + else
> + mask = 0xFFFF0000;
> +#endif
> +
> + irq_stat = __raw_readl(port->base + GPIO_ISR) &
> + (__raw_readl(port->base + GPIO_IMR) & mask);
> + mxc_gpio_irq_handler(port, irq_stat); }
> +
> /* MX1 and MX3 has one interrupt *per* gpio port */ static void
> mx3_gpio_irq_handler(u32 irq, struct irq_desc *desc) { @@ -289,11
> +307,13 @@ int __init mxc_gpio_init(struct mxc_gpio_port *port, int
cnt)
> /* its a serious configuration bug when it fails */
> BUG_ON( gpiochip_add(&port[i].chip) < 0 );
>
> - if (cpu_is_mx1() || cpu_is_mx3() || cpu_is_mx25()) {
> - /* setup one handler for each entry */
> + /* setup one handler for each entry */
> + if (cpu_is_mx1() || cpu_is_mx3() || cpu_is_mx25())
> set_irq_chained_handler(port[i].irq,
mx3_gpio_irq_handler);
> - set_irq_data(port[i].irq, &port[i]);
> - }
> + else if (cpu_is_mx51())
> + set_irq_chained_handler(port[i].irq,
mx5_gpio_irq_handler);
> +
> + set_irq_data(port[i].irq, &port[i]);
> }
>
> if (cpu_is_mx2()) {
> --
> 1.6.0.4
On Tue, Apr 13, 2010 at 11:10:24AM -0500, [email protected] wrote:
> diff --git a/arch/arm/mach-mx5/devices.c b/arch/arm/mach-mx5/devices.c
> index d6fd396..73f2342 100644
> --- a/arch/arm/mach-mx5/devices.c
> +++ b/arch/arm/mach-mx5/devices.c
> @@ -1,5 +1,6 @@
> /*
> * Copyright 2009 Amit Kucheria <[email protected]>
> + * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
> *
> * The code contained herein is licensed under the GNU General Public
> * License. You may obtain a copy of the GNU General Public License
> @@ -11,7 +12,9 @@
>
> #include <linux/platform_device.h>
> #include <mach/hardware.h>
> +#include <mach/gpio.h>
linux/gpio.h
On 04/13/2010 09:10 AM, [email protected] wrote:
> From: Dinh Nguyen<[email protected]>
>
> This patch updates the clocks, gpios, iomuxing and device structures for
> enabling USB Host functionality on Freescale MX51 Babbage HW.
> This patch applies to 2.6.34-rc4.
>
> Signed-off-by: Dinh Nguyen<[email protected]>
> ---
> arch/arm/mach-mx5/board-mx51_babbage.c | 40 +++++++++++++++++++++++++-
> arch/arm/mach-mx5/clock-mx51.c | 8 +++++
> arch/arm/mach-mx5/devices.c | 49 ++++++++++++++++++++++++++++++++
> arch/arm/mach-mx5/devices.h | 2 +
> 4 files changed, 98 insertions(+), 1 deletions(-)
>
> diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
> index 1338d6a..ddfa48b 100644
> --- a/arch/arm/mach-mx5/board-mx51_babbage.c
> +++ b/arch/arm/mach-mx5/board-mx51_babbage.c
> @@ -13,6 +13,7 @@
> #include<linux/init.h>
> #include<linux/platform_device.h>
> #include<linux/gpio.h>
> +#include<linux/delay.h>
>
> #include<mach/common.h>
> #include<mach/hardware.h>
> @@ -30,6 +31,8 @@
> extern void __init mx5_usb_dr_init(void);
> extern void __init mx5_usbh1_init(void);
>
> +#define GPIO_1_7 (0*32+7)
> +
As this GPIO used below, it is better to name it just as
#define GPIO_USB_RESET 7 /* GPIO_1_7 */
> static struct platform_device *devices[] __initdata = {
> &mxc_fec_device,
> };
> @@ -50,6 +53,22 @@ static struct pad_desc mx51babbage_pads[] = {
> MX51_PAD_EIM_D26__UART3_TXD,
> MX51_PAD_EIM_D27__UART3_RTS,
> MX51_PAD_EIM_D24__UART3_CTS,
> +
> + /* USB HOST1 */
> + MX51_PAD_GPIO_1_25__USBH1_CLK,
> + MX51_PAD_GPIO_1_26__USBH1_DIR,
> + MX51_PAD_GPIO_1_28__USBH1_NXT,
> + MX51_PAD_GPIO_1_11__USBH1_DATA0,
> + MX51_PAD_GPIO_1_12__USBH1_DATA1,
> + MX51_PAD_GPIO_1_13__USBH1_DATA2,
> + MX51_PAD_GPIO_1_14__USBH1_DATA3,
> + MX51_PAD_GPIO_1_15__USBH1_DATA4,
> + MX51_PAD_GPIO_1_16__USBH1_DATA5,
> + MX51_PAD_GPIO_1_17__USBH1_DATA6,
> + MX51_PAD_GPIO_1_18__USBH1_DATA7,
> +
> + /* USB HUB reset line*/
> + MX51_PAD_GPIO_1_7__GPIO1_7
How about "MX51_PAD_GPIO_1_7__GPIO_USB_RESET",
,
> };
>
> /* Serial ports */
> @@ -64,12 +83,31 @@ static inline void mxc_init_imx_uart(void)
> mxc_register_device(&mxc_uart_device1,&uart_pdata);
> mxc_register_device(&mxc_uart_device2,&uart_pdata);
> }
> -#else /* !SERIAL_IMX */
> +#else /* SERIAL_IMX */
> static inline void mxc_init_imx_uart(void)
> {
> }
> #endif /* SERIAL_IMX */
>
> +static inline void mx5_babbage_usbhub_reset(void)
> +{
> + int ret;
> +
> + /* Bring USB hub out of reset */
> + ret = gpio_request(GPIO_1_7, "GPIO1_7");
> + if (ret) {
> + printk("failed to get GPIO_1_7: %d\n", ret);
> + return;
> + }
> + gpio_direction_output(GPIO_1_7, 0);
> +
> + /* USB HUB RESET - De-assert USB HUB RESET_N */
> + msleep(1);
> + gpio_set_value(GPIO_1_7, 0);
> + msleep(1);
> + gpio_set_value(GPIO_1_7, 1);
> +}
> +
%s/GPIO_1_7/GPIO_USB_RESET/g
> /*
> * Board specific initialization.
> */
> diff --git a/arch/arm/mach-mx5/clock-mx51.c b/arch/arm/mach-mx5/clock-mx51.c
> index 8f85f73..36684d0 100644
> --- a/arch/arm/mach-mx5/clock-mx51.c
> +++ b/arch/arm/mach-mx5/clock-mx51.c
> @@ -765,6 +765,10 @@ DEFINE_CLOCK(gpt_ipg_clk, 0, MXC_CCM_CCGR2, MXC_CCM_CCGRx_CG10_OFFSET,
> DEFINE_CLOCK(fec_clk, 0, MXC_CCM_CCGR2, MXC_CCM_CCGRx_CG12_OFFSET,
> NULL, NULL,&ipg_clk, NULL);
>
> +/* USB */
> +DEFINE_CLOCK(usboh3_clk, 0, MXC_CCM_CCGR2, MXC_CCM_CCGRx_CG14_OFFSET,
> + NULL, NULL,&pll3_sw_clk, NULL);
> +
It should be
+ NULL, NULL, &pll3_sw_clk, NULL);
I'm a little bit picky here, but please use scripts/checkpatch.pl to fix this
coding style issue.
> #define _REGISTER_CLOCK(d, n, c) \
> { \
> .dev_id = d, \
> @@ -778,6 +782,10 @@ static struct clk_lookup lookups[] = {
> _REGISTER_CLOCK("imx-uart.2", NULL, uart3_clk)
> _REGISTER_CLOCK(NULL, "gpt", gpt_clk)
> _REGISTER_CLOCK("fec.0", NULL, fec_clk)
> + _REGISTER_CLOCK("mxc-ehci.0", "usb", usboh3_clk)
> + _REGISTER_CLOCK("mxc-ehci.0", "usb_ahb", ahb_clk)
> + _REGISTER_CLOCK("mxc-ehci.1", "usb", usboh3_clk)
> + _REGISTER_CLOCK("mxc-ehci.1", "usb_ahb", ahb_clk)
> };
>
> static void clk_tree_init(void)
> diff --git a/arch/arm/mach-mx5/devices.c b/arch/arm/mach-mx5/devices.c
> index 73f2342..3d8f66a 100644
> --- a/arch/arm/mach-mx5/devices.c
> +++ b/arch/arm/mach-mx5/devices.c
> @@ -11,6 +11,7 @@
> */
>
> #include<linux/platform_device.h>
> +#include<linux/dma-mapping.h>
> #include<mach/hardware.h>
> #include<mach/gpio.h>
> #include<mach/imx-uart.h>
> @@ -92,6 +93,54 @@ struct platform_device mxc_fec_device = {
> .resource = mxc_fec_resources,
> };
>
> +static u64 usb_dma_mask = DMA_BIT_MASK(32);
> +
> +static struct resource usbotg_resources[] = {
> + {
> + .start = MX51_OTG_BASE_ADDR,
> + .end = MX51_OTG_BASE_ADDR + 0x1ff,
> + .flags = IORESOURCE_MEM,
> + },
> + {
> + .start = MX51_MXC_INT_USB_OTG,
> + .flags = IORESOURCE_IRQ,
> + },
> +};
> +
> +struct platform_device mxc_usbdr_host_device = {
> + .name = "mxc-ehci",
> + .id = 0,
> + .num_resources = ARRAY_SIZE(usbotg_resources),
> + .resource = usbotg_resources,
> + .dev = {
> + .dma_mask =&usb_dma_mask,
> + .coherent_dma_mask = DMA_BIT_MASK(32),
> + },
> +};
> +
> +static struct resource usbh1_resources[] = {
> + {
> + .start = MX51_OTG_BASE_ADDR + 0x200,
> + .end = MX51_OTG_BASE_ADDR + 0x200 + 0x1ff,
> + .flags = IORESOURCE_MEM,
> + },
> + {
> + .start = MX51_MXC_INT_USB_H1,
> + .flags = IORESOURCE_IRQ,
> + },
> +};
> +
> +struct platform_device mxc_usbh1_device = {
> + .name = "mxc-ehci",
> + .id = 1,
> + .num_resources = ARRAY_SIZE(usbh1_resources),
> + .resource = usbh1_resources,
> + .dev = {
> + .dma_mask =&usb_dma_mask,
+ .dma_mask = &usb_dma_mask,
> + .coherent_dma_mask = DMA_BIT_MASK(32),
> + },
> +};
> +
> struct mxc_gpio_port mxc_gpio_ports[] = {
> {
> .chip.label = "gpio-0",
> diff --git a/arch/arm/mach-mx5/devices.h b/arch/arm/mach-mx5/devices.h
> index f339ab8..95c45f9 100644
> --- a/arch/arm/mach-mx5/devices.h
> +++ b/arch/arm/mach-mx5/devices.h
> @@ -2,3 +2,5 @@ extern struct platform_device mxc_uart_device0;
> extern struct platform_device mxc_uart_device1;
> extern struct platform_device mxc_uart_device2;
> extern struct platform_device mxc_fec_device;
> +extern struct platform_device mxc_usbdr_host_device;
> +extern struct platform_device mxc_usbh1_device;
--
Bryan Wu <[email protected]>
Kernel Developer +86.138-1617-6545 Mobile
Ubuntu Kernel Team | Hardware Enablement Team
Canonical Ltd. http://www.canonical.com
Ubuntu - Linux for human beings | http://www.ubuntu.com
This patch looks OK for me, but I failed to find the 8th patch of this patchset.
Did you forget to send it out?
-Bryan
On 04/13/2010 09:10 AM, [email protected] wrote:
> From: Dinh Nguyen<[email protected]>
>
> Updade mx51_defconfig to include USB host support.
> This patch applies to 2.6.34-rc4.
>
> Signed-off-by: Dinh Nguyen<[email protected]>
> ---
> arch/arm/configs/mx51_defconfig | 17 ++++++++++++++++-
> 1 files changed, 16 insertions(+), 1 deletions(-)
>
> diff --git a/arch/arm/configs/mx51_defconfig b/arch/arm/configs/mx51_defconfig
> index c88e952..a708fd6 100644
> --- a/arch/arm/configs/mx51_defconfig
> +++ b/arch/arm/configs/mx51_defconfig
> @@ -809,7 +809,22 @@ CONFIG_SSB_POSSIBLE=y
> CONFIG_DUMMY_CONSOLE=y
> # CONFIG_SOUND is not set
> # CONFIG_HID_SUPPORT is not set
> -# CONFIG_USB_SUPPORT is not set
> +CONFIG_USB_SUPPORT=y
> +CONFIG_USB_ARCH_HAS_HCD=y
> +# CONFIG_USB_ARCH_HAS_OHCI is not set
> +CONFIG_USB_ARCH_HAS_EHCI=y
> +CONFIG_USB=y
> +
> +#
> +# USB Host Controller Drivers
> +#
> +# CONFIG_USB_C67X00_HCD is not set
> +CONFIG_USB_EHCI_HCD=y
> +CONFIG_USB_EHCI_ROOT_HUB_TT=y
> +# CONFIG_USB_EHCI_TT_NEWSCHED is not set
> +CONFIG_USB_EHCI_MXC=y
> +
> +
> CONFIG_MMC=y
> # CONFIG_MMC_DEBUG is not set
> # CONFIG_MMC_UNSAFE_RESUME is not set
On Tue, Apr 13, 2010 at 11:10:25AM -0500, [email protected] wrote:
> From: Dinh Nguyen <[email protected]>
>
> This patch is part of enabling USB for Freescale MX51 Babbage HW. This
> patch updates the iomux pins for USB, and gpio line for reset the
> USB hub on the MX51 Babbage HW.
>
> This patch applies to 2.6.34-rc4.
>
> /*
> * The naming convention for the pad modes is MX51_PAD_<padname>__<padmode>
> @@ -208,18 +214,19 @@ typedef enum iomux_config {
> #define MX51_PAD_KEY_COL3__KEY_COL3 IOMUX_PAD(0x658, 0x268, 0, 0x0, 0, NO_PAD_CTRL)
> #define MX51_PAD_KEY_COL4__KEY_COL4 IOMUX_PAD(0x65C, 0x26C, 0, 0x0, 0, NO_PAD_CTRL)
> #define MX51_PAD_KEY_COL5__KEY_COL5 IOMUX_PAD(0x660, 0x270, 0, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_25__USBH1_CLK IOMUX_PAD(0x678, 0x278, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_26__USBH1_DIR IOMUX_PAD(0x67C, 0x27C, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_27__USBH1_STP IOMUX_PAD(0x680, 0x280, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_28__USBH1_NXT IOMUX_PAD(0x684, 0x284, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_11__USBH1_DATA0 IOMUX_PAD(0x688, 0x288, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_12__USBH1_DATA1 IOMUX_PAD(0x68C, 0x28C, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_13__USBH1_DATA2 IOMUX_PAD(0x690, 0x290, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_14__USBH1_DATA3 IOMUX_PAD(0x694, 0x294, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_15__USBH1_DATA4 IOMUX_PAD(0x698, 0x298, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_16__USBH1_DATA5 IOMUX_PAD(0x69C, 0x29C, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_17__USBH1_DATA6 IOMUX_PAD(0x6A0, 0x2A0, 2, 0x0, 0, NO_PAD_CTRL)
> -#define MX51_PAD_GPIO_1_18__USBH1_DATA7 IOMUX_PAD(0x6A4, 0x2A4, 2, 0x0, 0, NO_PAD_CTRL)
> +#define MX51_PAD_GPIO_1_25__USBH1_CLK IOMUX_PAD(0x678, 0x278, IOMUX_CONFIG_ALT0, 0x0, 0, MX51_USBH1_PAD_CTRL)
The naming convention is MX51_PAD_<padname>__<function> with padname
being the name in the datasheet, so this pad should be named
MX51_PAD_USBH1_CLK__USBH1_CLK, or if used as gpio
MX51_PAD_USBH1_CLK__GPIO_1_25. This is not your fault, it was wrong
before and I haven't recognized it. We should fix this before these
definitions actually get used.
Sascha
--
Pengutronix e.K. | |
Industrial Linux Solutions | http://www.pengutronix.de/ |
Peiner Str. 6-8, 31137 Hildesheim, Germany | Phone: +49-5121-206917-0 |
Amtsgericht Hildesheim, HRA 2686 | Fax: +49-5121-206917-5555 |
On Tue, Apr 13, 2010 at 12:36:07PM -0700, Nguyen Dinh-R00091 wrote:
> > +
> > +#ifdef MXC_GPIO_SPLIT_IRQ_2
>
> Where is that macro defined?
> [Dinh-FSL] - This macro is optional so that the interrupts can be broken
> up into 2 sets.
What's the purpose of doing so?
Such compile time depencies are not a good idea since the board may want
to decide whether to split the interrupts or not. Note that we support
kernels for more than one board.
Sascha
--
Pengutronix e.K. | |
Industrial Linux Solutions | http://www.pengutronix.de/ |
Peiner Str. 6-8, 31137 Hildesheim, Germany | Phone: +49-5121-206917-0 |
Amtsgericht Hildesheim, HRA 2686 | Fax: +49-5121-206917-5555 |
On 04/13/2010 09:10 AM, [email protected] wrote:
> From: Dinh Nguyen<[email protected]>
>
> This patch adds the device platform registration for enabling USB
> host functionality on the OTG port on Freescale MX51 Babbage HW. This
> file makes platform specific calls to initialize the USB HW.
>
> This patch applies to 2.6.34-rc4.
>
> Signed-off-by: Dinh Nguyen<[email protected]>
> ---
> arch/arm/mach-mx5/Makefile | 2 +-
> arch/arm/mach-mx5/board-mx51_babbage.c | 4 ++
Agree with Daniel here, this patch should be split into 2 parts, a) for usb_dr.c
and Makefile, b) for board-mx51_babbage.c change.
And one more suggestion is merge usb_dr.c and usb_h1.c as one file usb.c. It is
more simple to maintain and review.
-Bryan
> arch/arm/mach-mx5/usb_dr.c | 57 ++++++++++++++++++++++++++++++++
> 3 files changed, 62 insertions(+), 1 deletions(-)
> create mode 100644 arch/arm/mach-mx5/usb_dr.c
>
> diff --git a/arch/arm/mach-mx5/Makefile b/arch/arm/mach-mx5/Makefile
> index bf23f86..3fca1f1 100644
> --- a/arch/arm/mach-mx5/Makefile
> +++ b/arch/arm/mach-mx5/Makefile
> @@ -3,7 +3,7 @@
> #
>
> # Object file lists.
> -obj-y := cpu.o mm.o clock-mx51.o devices.o
> +obj-y := cpu.o mm.o clock-mx51.o devices.o usb_dr.o
>
> obj-$(CONFIG_MACH_MX51_BABBAGE) += board-mx51_babbage.o
>
> diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
> index afbe400..4e196d7 100644
> --- a/arch/arm/mach-mx5/board-mx51_babbage.c
> +++ b/arch/arm/mach-mx5/board-mx51_babbage.c
> @@ -27,6 +27,8 @@
>
> #include "devices.h"
>
> +extern void __init mx5_usb_dr_init(void);
> +
> static struct platform_device *devices[] __initdata = {
> &mxc_fec_device,
> };
> @@ -78,6 +80,8 @@ static void __init mxc_board_init(void)
> platform_add_devices(devices, ARRAY_SIZE(devices));
>
> mxc_register_gpios();
> +
> + mx5_usb_dr_init();
> }
>
> static void __init mx51_babbage_timer_init(void)
> diff --git a/arch/arm/mach-mx5/usb_dr.c b/arch/arm/mach-mx5/usb_dr.c
> new file mode 100644
> index 0000000..52273ea
> --- /dev/null
> +++ b/arch/arm/mach-mx5/usb_dr.c
> @@ -0,0 +1,57 @@
> +/*
> + * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
> + *
> + * 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.
> + *
> + * This program is distributed in the hope that it will be useful,
> + * but WITHOUT ANY WARRANTY; without even the implied warranty of
> + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
> + * GNU General Public License for more details.
> + *
> + * You should have received a copy of the GNU General Public License
> + * along with this program; if not, write to the Free Software
> + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
> + * MA 02110-1301, USA.
> + */
> +
> +#include<linux/platform_device.h>
> +#include<mach/mxc_ehci.h>
> +#include<mach/common.h>
> +#include "devices.h"
> +
> +extern int usbotg_init(struct platform_device *pdev);
> +extern int usbotg_uninit(struct platform_device *pdev);
> +
> +static int usbotg_init_ext(struct platform_device *pdev);
> +static int usbotg_uninit_ext(struct platform_device *pdev);
> +
> +/*
> + * platform data structs
> + * - Which one to use is determined by CONFIG options in usb.h
> + * - operating_mode plugged at run time
> + */
> +static struct mxc_usbh_platform_data dr_utmi_config = {
> + .init = usbotg_init_ext,
> + .exit = usbotg_uninit_ext,
> + .portsc = MXC_EHCI_UTMI_16BIT,
> + .flags = MXC_EHCI_INTERNAL_PHY,
> +};
> +
> +/* Notes: configure USB clock*/
> +static int usbotg_init_ext(struct platform_device *pdev)
> +{
> + return usbotg_init(pdev);
> +}
> +
> +static int usbotg_uninit_ext(struct platform_device *pdev)
> +{
> + return usbotg_uninit(pdev);
> +}
> +
> +void __init mx5_usb_dr_init(void)
> +{
> + mxc_register_device(&mxc_usbdr_host_device,&dr_utmi_config);
> +}
On Tue, Apr 13, 2010 at 11:58:04PM -0700, Bryan Wu wrote:
> On 04/13/2010 09:10 AM, [email protected] wrote:
> >From: Dinh Nguyen<[email protected]>
> >
> >This patch adds the device platform registration for enabling USB
> >host functionality on the OTG port on Freescale MX51 Babbage HW. This
> >file makes platform specific calls to initialize the USB HW.
> >
> >This patch applies to 2.6.34-rc4.
> >
> >Signed-off-by: Dinh Nguyen<[email protected]>
> >---
> > arch/arm/mach-mx5/Makefile | 2 +-
> > arch/arm/mach-mx5/board-mx51_babbage.c | 4 ++
>
> Agree with Daniel here, this patch should be split into 2 parts, a)
> for usb_dr.c and Makefile, b) for board-mx51_babbage.c change.
>
> And one more suggestion is merge usb_dr.c and usb_h1.c as one file
> usb.c. It is more simple to maintain and review.
I don't think usb_dr.c is needed at all, as its content is not anything
that should be shared between boards. Those definitions should be placed
in mx51_babbage.c alltogether.
But we're disussing at the wrong end of the patch set; once the
mx5-generic parts have been fixed, the interface to board support code
will also change.
Daniel
> > arch/arm/mach-mx5/usb_dr.c | 57 ++++++++++++++++++++++++++++++++
> > 3 files changed, 62 insertions(+), 1 deletions(-)
> > create mode 100644 arch/arm/mach-mx5/usb_dr.c
> >
> >diff --git a/arch/arm/mach-mx5/Makefile b/arch/arm/mach-mx5/Makefile
> >index bf23f86..3fca1f1 100644
> >--- a/arch/arm/mach-mx5/Makefile
> >+++ b/arch/arm/mach-mx5/Makefile
> >@@ -3,7 +3,7 @@
> > #
> >
> > # Object file lists.
> >-obj-y := cpu.o mm.o clock-mx51.o devices.o
> >+obj-y := cpu.o mm.o clock-mx51.o devices.o usb_dr.o
> >
> > obj-$(CONFIG_MACH_MX51_BABBAGE) += board-mx51_babbage.o
> >
> >diff --git a/arch/arm/mach-mx5/board-mx51_babbage.c b/arch/arm/mach-mx5/board-mx51_babbage.c
> >index afbe400..4e196d7 100644
> >--- a/arch/arm/mach-mx5/board-mx51_babbage.c
> >+++ b/arch/arm/mach-mx5/board-mx51_babbage.c
> >@@ -27,6 +27,8 @@
> >
> > #include "devices.h"
> >
> >+extern void __init mx5_usb_dr_init(void);
> >+
> > static struct platform_device *devices[] __initdata = {
> > &mxc_fec_device,
> > };
> >@@ -78,6 +80,8 @@ static void __init mxc_board_init(void)
> > platform_add_devices(devices, ARRAY_SIZE(devices));
> >
> > mxc_register_gpios();
> >+
> >+ mx5_usb_dr_init();
> > }
> >
> > static void __init mx51_babbage_timer_init(void)
> >diff --git a/arch/arm/mach-mx5/usb_dr.c b/arch/arm/mach-mx5/usb_dr.c
> >new file mode 100644
> >index 0000000..52273ea
> >--- /dev/null
> >+++ b/arch/arm/mach-mx5/usb_dr.c
> >@@ -0,0 +1,57 @@
> >+/*
> >+ * Copyright (C) 2010 Freescale Semiconductor, Inc. All Rights Reserved.
> >+ *
> >+ * 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.
> >+ *
> >+ * This program is distributed in the hope that it will be useful,
> >+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
> >+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
> >+ * GNU General Public License for more details.
> >+ *
> >+ * You should have received a copy of the GNU General Public License
> >+ * along with this program; if not, write to the Free Software
> >+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
> >+ * MA 02110-1301, USA.
> >+ */
> >+
> >+#include<linux/platform_device.h>
> >+#include<mach/mxc_ehci.h>
> >+#include<mach/common.h>
> >+#include "devices.h"
> >+
> >+extern int usbotg_init(struct platform_device *pdev);
> >+extern int usbotg_uninit(struct platform_device *pdev);
> >+
> >+static int usbotg_init_ext(struct platform_device *pdev);
> >+static int usbotg_uninit_ext(struct platform_device *pdev);
> >+
> >+/*
> >+ * platform data structs
> >+ * - Which one to use is determined by CONFIG options in usb.h
> >+ * - operating_mode plugged at run time
> >+ */
> >+static struct mxc_usbh_platform_data dr_utmi_config = {
> >+ .init = usbotg_init_ext,
> >+ .exit = usbotg_uninit_ext,
> >+ .portsc = MXC_EHCI_UTMI_16BIT,
> >+ .flags = MXC_EHCI_INTERNAL_PHY,
> >+};
> >+
> >+/* Notes: configure USB clock*/
> >+static int usbotg_init_ext(struct platform_device *pdev)
> >+{
> >+ return usbotg_init(pdev);
> >+}
> >+
> >+static int usbotg_uninit_ext(struct platform_device *pdev)
> >+{
> >+ return usbotg_uninit(pdev);
> >+}
> >+
> >+void __init mx5_usb_dr_init(void)
> >+{
> >+ mxc_register_device(&mxc_usbdr_host_device,&dr_utmi_config);
> >+}
>
On Wed, Apr 14, 2010 at 08:51:31AM +0200, Sascha Hauer wrote:
> On Tue, Apr 13, 2010 at 12:36:07PM -0700, Nguyen Dinh-R00091 wrote:
> > > +
> > > +#ifdef MXC_GPIO_SPLIT_IRQ_2
> >
> > Where is that macro defined?
> > [Dinh-FSL] - This macro is optional so that the interrupts can be broken
> > up into 2 sets.
>
> What's the purpose of doing so?
>
> Such compile time depencies are not a good idea since the board may want
> to decide whether to split the interrupts or not. Note that we support
> kernels for more than one board.
And I would have expected at least one active user. As it stands, it's
just dead code.
Daniel
On Wed, Apr 14, 2010 at 09:31:38AM +0200, Daniel Mack wrote:
> On Wed, Apr 14, 2010 at 08:51:31AM +0200, Sascha Hauer wrote:
> > On Tue, Apr 13, 2010 at 12:36:07PM -0700, Nguyen Dinh-R00091 wrote:
> > > > +
> > > > +#ifdef MXC_GPIO_SPLIT_IRQ_2
> > >
> > > Where is that macro defined?
> > > [Dinh-FSL] - This macro is optional so that the interrupts can be broken
> > > up into 2 sets.
> >
> > What's the purpose of doing so?
> >
> > Such compile time depencies are not a good idea since the board may want
> > to decide whether to split the interrupts or not. Note that we support
> > kernels for more than one board.
>
> And I would have expected at least one active user. As it stands, it's
> just dead code.
Ack, this should be removed. Anyone wanting this code will send a
seperate patch and can explain what and why he wants to do.
Sascha
--
Pengutronix e.K. | |
Industrial Linux Solutions | http://www.pengutronix.de/ |
Peiner Str. 6-8, 31137 Hildesheim, Germany | Phone: +49-5121-206917-0 |
Amtsgericht Hildesheim, HRA 2686 | Fax: +49-5121-206917-5555 |
The 8th patch was for a USB timeout change that was sent to the USB
maintainer. Thanks everyone for their comments, I am almost ready with
another set with review comments taken into consideration.
Dinh
-----Original Message-----
From: Bryan Wu [mailto:[email protected]]
Sent: Wednesday, April 14, 2010 1:33 AM
To: Nguyen Dinh-R00091
Cc: [email protected]; [email protected];
[email protected]; [email protected];
[email protected]; [email protected]; [email protected];
Herring Robert-RA7055; [email protected]
Subject: Re: [PATCH 2.6.34-rc4 7/8] mx5: Add USB to Freescale MX51
Babbage
This patch looks OK for me, but I failed to find the 8th patch of this
patchset.
Did you forget to send it out?
-Bryan
On 04/13/2010 09:10 AM, [email protected] wrote:
> From: Dinh Nguyen<[email protected]>
>
> Updade mx51_defconfig to include USB host support.
> This patch applies to 2.6.34-rc4.
>
> Signed-off-by: Dinh Nguyen<[email protected]>
> ---
> arch/arm/configs/mx51_defconfig | 17 ++++++++++++++++-
> 1 files changed, 16 insertions(+), 1 deletions(-)
>
> diff --git a/arch/arm/configs/mx51_defconfig
> b/arch/arm/configs/mx51_defconfig index c88e952..a708fd6 100644
> --- a/arch/arm/configs/mx51_defconfig
> +++ b/arch/arm/configs/mx51_defconfig
> @@ -809,7 +809,22 @@ CONFIG_SSB_POSSIBLE=y
> CONFIG_DUMMY_CONSOLE=y
> # CONFIG_SOUND is not set
> # CONFIG_HID_SUPPORT is not set
> -# CONFIG_USB_SUPPORT is not set
> +CONFIG_USB_SUPPORT=y
> +CONFIG_USB_ARCH_HAS_HCD=y
> +# CONFIG_USB_ARCH_HAS_OHCI is not set CONFIG_USB_ARCH_HAS_EHCI=y
> +CONFIG_USB=y
> +
> +#
> +# USB Host Controller Drivers
> +#
> +# CONFIG_USB_C67X00_HCD is not set
> +CONFIG_USB_EHCI_HCD=y
> +CONFIG_USB_EHCI_ROOT_HUB_TT=y
> +# CONFIG_USB_EHCI_TT_NEWSCHED is not set CONFIG_USB_EHCI_MXC=y
> +
> +
> CONFIG_MMC=y
> # CONFIG_MMC_DEBUG is not set
> # CONFIG_MMC_UNSAFE_RESUME is not set