s5pc110: Add S5PC110 S3C UDC OTG driver and enable CDC Ethernet networking (tftp)
authorKyungmin Park <kyungmin.park@samsung.com>
Thu, 18 Feb 2010 07:59:35 +0000 (16:59 +0900)
committerKyungmin Park <kyungmin.park@samsung.com>
Thu, 18 Feb 2010 07:59:35 +0000 (16:59 +0900)
Signed-off-by: Kyungmin Park <kyungmin.park@samsung.com>
13 files changed:
board/samsung/universal/universal.c
common/cmd_misc.c
cpu/arm_cortexa8/cpu.c
cpu/arm_cortexa8/s5pc1xx/timer.c
drivers/usb/gadget/Makefile
drivers/usb/gadget/ether.c
drivers/usb/gadget/gadget_chips.h
drivers/usb/gadget/s3c_udc.h
drivers/usb/gadget/s3c_udc_otg.c
drivers/usb/gadget/s3c_udc_otg_xfer_dma.c
include/asm-arm/arch-s5pc1xx/hs_otg.h [new file with mode: 0644]
include/asm-arm/arch-s5pc1xx/regs-otg.h [new file with mode: 0644]
include/configs/s5pc1xx_universal.h

index 4e79660..d9795d1 100644 (file)
@@ -33,6 +33,8 @@
 #include <asm/arch/mmc.h>
 #include <asm/arch/power.h>
 #include <asm/arch/mem.h>
+#include <asm/arch/hs_otg.h>
+#include <asm/arch/regs-otg.h>
 #include <asm/errno.h>
 #include <fbutils.h>
 #include <lcd.h>
@@ -2043,6 +2045,63 @@ void board_sleep_resume(void)
        check_micro_usb(1);
 }
 
+#if defined(CONFIG_USB_GADGET_S3C_UDC_OTG)
+
+static int s5pc1xx_phy_control(int on)
+{
+       static int status;
+
+       if (on && !status) {
+//             printf("turning USB power on\n");
+#ifdef CONFIG_CMD_PMIC
+               run_command("pmic ldo 3 on", 0);
+#endif
+               /* S5PC110 */
+               if (board_is_limo_universal() ||
+                       board_is_limo_real() ||
+                       board_is_media()) {
+                       /* check usb path */
+                       if (board_is_limo_real() && !hwrevision(6))
+                               check_mhl();
+               }
+
+               if (machine_is_tickertape())
+                       /* USB_SEL: XM0ADDR_0: MP04[0] output mode */
+                       gpio_direction_output(&s5pc110_gpio->gpio_mp0_4, 0, 0);
+
+               /* USB Path to AP */
+               micro_usb_switch(0);
+               status = 1;
+       } else if (!on && status) {
+//             printf("turning USB power off\n");
+#ifdef CONFIG_CMD_PMIC
+               run_command("pmic ldo 3 off", 0);
+#endif
+               status = 0;
+       }
+       udelay(10000);
+}
+
+struct s3c_plat_otg_data s5pc110_otg_data = {
+       .phy_control = s5pc1xx_phy_control,
+       .regs_phy = S5PC110_PHY_BASE,
+       .regs_otg = S5PC110_OTG_BASE,
+};
+
+int board_eth_init(bd_t *bis)
+{
+       int res = -1;
+
+       if (cpu_is_s5pc100())
+               return -1;
+
+       s3c_udc_probe(&s5pc110_otg_data);
+       if (usb_eth_initialize(bis) >= 0)
+               res = 0;
+       return res;
+}
+#endif
+
 #ifdef CONFIG_CMD_USBDOWN
 int usb_board_init(void)
 {
index b0ced2f..d5b759d 100644 (file)
@@ -27,7 +27,7 @@
 #include <common.h>
 #include <command.h>
 
-int do_sleep (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+int do_sleep1 (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
 {
        ulong start = get_timer(0);
        ulong delay;
@@ -50,7 +50,7 @@ int do_sleep (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
 }
 
 U_BOOT_CMD(
-       sleep ,    2,    1,     do_sleep,
+       wait ,    2,    1,     do_sleep1,
        "delay execution for some time",
        "N\n"
        "    - delay execution for N seconds (N is _decimal_ !!!)"
index a01e0d6..3b6f86b 100644 (file)
@@ -39,7 +39,7 @@
 #include <asm/arch/sys_proto.h>
 #endif
 
-static void cache_flush(void);
+void cache_flush(void);
 
 int cleanup_before_linux(void)
 {
@@ -77,7 +77,7 @@ int cleanup_before_linux(void)
        return 0;
 }
 
-static void cache_flush(void)
+void cache_flush(void)
 {
        asm ("mcr p15, 0, %0, c7, c5, 0": :"r" (0));
 }
index 297e69a..d9ca7c1 100644 (file)
@@ -112,7 +112,7 @@ void reset_timer(void)
 
 unsigned long get_timer(unsigned long base)
 {
-       return get_timer_masked() - base;
+       return (get_timer_masked()/2000 - base);
 }
 
 void set_timer(unsigned long t)
index 27e7f40..ebfdd07 100644 (file)
@@ -38,6 +38,7 @@ endif
 # new USB gadget layer dependencies
 COBJS-$(CONFIG_USB_ETHER) += ether.o epautoconf.o config.o usbstring.o
 COBJS-$(CONFIG_USB_GADGET_AT91) += at91_udc.o
+COBJS-$(CONFIG_USB_GADGET_S3C_UDC_OTG) += s3c_udc_otg.o
 
 COBJS  := $(COBJS-y)
 SRCS   := $(COBJS:.o=.c)
index f290883..3793e1d 100644 (file)
@@ -30,7 +30,7 @@
 
 #include "gadget_chips.h"
 
-#define USB_NET_NAME "usb0"
+#define USB_NET_NAME "CDC Ethernet"
 #define dprintf(x, ...)
 #undef INFO
 #define INFO(x, s...)  printf(s)
@@ -108,7 +108,7 @@ static const char driver_desc [] = DRIVER_DESC;
                        |USB_CDC_PACKET_TYPE_PROMISCUOUS \
                        |USB_CDC_PACKET_TYPE_DIRECTED)
 
-#define USB_CONNECT_TIMEOUT (3 * CONFIG_SYS_HZ)
+#define USB_CONNECT_TIMEOUT (10 * CONFIG_SYS_HZ)
 
 /*-------------------------------------------------------------------------*/
 static struct eth_dev l_ethdev;
@@ -134,6 +134,14 @@ static inline int is_cdc(struct eth_dev *dev)
 
 #define DEFAULT_QLEN   2       /* double buffering by default */
 
+#ifdef CONFIG_USB_GADGET_DUALSPEED
+
+static unsigned qmult = 5;
+
+#else  /* full speed (low speed doesn't do bulk) */
+#define qmult          1
+#endif
+
 /* peak bulk transfer bits-per-second */
 #define        HS_BPS          (13 * 512 * 8 * 1000 * 8)
 #define        FS_BPS          (19 *  64 * 1 * 1000 * 8)
@@ -920,10 +928,14 @@ static void eth_status_complete (struct usb_ep *ep, struct usb_request *req)
        int                             value = req->status;
        struct eth_dev                  *dev = ep->driver_data;
 
+       dprintf("eth_status_complete\n");
+
        /* issue the second notification if host reads the first */
        if (event->bNotificationType == USB_CDC_NOTIFY_NETWORK_CONNECTION
                        && value == 0) {
-               __le32  *data = req->buf + sizeof *event;
+               char *src, *dst = req->buf + sizeof *event;
+               __le32 data;
+               int i;
 
                event->bmRequestType = 0xA1;
                event->bNotificationType = USB_CDC_NOTIFY_SPEED_CHANGE;
@@ -932,8 +944,16 @@ static void eth_status_complete (struct usb_ep *ep, struct usb_request *req)
                event->wLength = __constant_cpu_to_le16 (8);
 
                /* SPEED_CHANGE data is up/down speeds in bits/sec */
-               data [0] = data [1] = cpu_to_le32 (BITRATE (dev->gadget));
 
+               data = cpu_to_le32 (BITRATE (dev->gadget));
+
+               src = &data;
+               for (i=0; i<4; i++)
+                       *dst++ = *src++;
+               src = &data;
+               for (i=0; i<4; i++)
+                       *dst++ = *src++;
+       
                req->length = STATUS_BYTECOUNT;
                value = usb_ep_queue (ep, req, GFP_ATOMIC);
                dprintf ("send SPEED_CHANGE --> %d\n", value);
@@ -950,6 +970,7 @@ static void eth_status_complete (struct usb_ep *ep, struct usb_request *req)
                }
        }
        req->context = NULL;
+       dprintf("done\n");
 }
 
 static void issue_start_status (struct eth_dev *dev)
@@ -1422,7 +1443,7 @@ static void eth_unbind (struct usb_gadget *gadget)
 {
        struct eth_dev *dev = get_gadget_data (gadget);
 
-       printf("eth_unbind:...\n");
+       dprintf("eth_unbind:...\n");
 
        if (dev->stat_req) {
                usb_ep_free_request (dev->status_ep, dev->stat_req);
@@ -1759,6 +1780,7 @@ static int usb_eth_init(struct eth_device* netdev, bd_t* bd)
 {
        struct eth_dev *dev=&l_ethdev;
        struct usb_gadget *gadget;
+       int status = 0;
        unsigned long ts;
        unsigned long timeout = USB_CONNECT_TIMEOUT;
 
@@ -1767,12 +1789,18 @@ static int usb_eth_init(struct eth_device* netdev, bd_t* bd)
                goto fail;
        }
 
+       status = usb_gadget_register_driver(&eth_driver);
+       if (status < 0)
+               goto fail;
+
+       usb_gadget_handle_interrupts();
+
        dev->network_started = 0;
        dev->tx_req = NULL;
        dev->rx_req = NULL;
 
        packet_received = 0;
-       packet_sent = 0;
+       packet_sent = 1;
 
        gadget = dev->gadget;
        usb_gadget_connect(gadget);
@@ -1783,12 +1811,17 @@ static int usb_eth_init(struct eth_device* netdev, bd_t* bd)
        ts = get_timer(0);
        while (!l_ethdev.network_started)
        {
+               int irq_res;
                /* Handle control-c and timeouts */
                if (ctrlc() || (get_timer(ts) > timeout)) {
                        printf("The remote end did not respond in time.\n");
                        goto fail;
                }
-               usb_gadget_handle_interrupts();
+               irq_res = usb_gadget_handle_interrupts();
+
+               /* hack nice progress display */
+               if (irq_res && !l_ethdev.network_started)
+                       printf(".");    
        }
 
        rx_submit (dev, dev->rx_req, 0);
@@ -1805,6 +1838,13 @@ static int usb_eth_send(struct eth_device* netdev, volatile void* packet, int le
        struct eth_dev *dev = &l_ethdev;
        dprintf("%s:...\n",__func__);
 
+       while(!packet_sent)
+       {
+               packet_sent=0;
+               usb_gadget_handle_interrupts();
+               dprintf("^");
+       }
+
        req = dev->tx_req;
 
        req->buf = (void *)packet;
@@ -1820,7 +1860,7 @@ static int usb_eth_send(struct eth_device* netdev, volatile void* packet, int le
                length++;
 
        req->length = length;
-#if 0
+#if 1
        /* throttle highspeed IRQ rate back slightly */
        if (gadget_is_dualspeed(dev->gadget))
                req->no_interrupt = (dev->gadget->speed == USB_SPEED_HIGH)
@@ -1832,10 +1872,6 @@ static int usb_eth_send(struct eth_device* netdev, volatile void* packet, int le
 
        if (!retval)
                dprintf("%s: packet queued\n",__func__);
-       while(!packet_sent)
-       {
-               packet_sent=0;
-       }
 
        return 0;
 }
@@ -1844,6 +1880,8 @@ static int usb_eth_recv(struct eth_device* netdev)
 {
        struct eth_dev *dev = &l_ethdev;
 
+       dprintf("%s:...\n",__func__);
+
        usb_gadget_handle_interrupts();
 
        if (packet_received)
@@ -1856,9 +1894,11 @@ static int usb_eth_recv(struct eth_device* netdev)
 
                        if (dev->rx_req)
                                rx_submit (dev, dev->rx_req, 0);
+                       dprintf("-");
                }
                else printf("dev->rx_req invalid\n");
        }
+       dprintf("done\n");
        return 0;
 }
 
@@ -1872,7 +1912,8 @@ void usb_eth_halt(struct eth_device* netdev)
                return;
        }
 
-       usb_gadget_disconnect(dev->gadget);
+       usb_gadget_unregister_driver(&eth_driver);
+       usb_gadget_handle_interrupts();
 }
 
 static struct usb_gadget_driver eth_driver = {
@@ -1893,7 +1934,7 @@ int usb_eth_initialize(bd_t *bi)
        int status = 0;
        struct eth_device *netdev=&l_netdev;
 
-       sprintf(netdev->name,"usb_ether");
+       sprintf(netdev->name, "USB CDC Ethernet");
 
        netdev->init = usb_eth_init;
        netdev->send = usb_eth_send;
@@ -1934,10 +1975,6 @@ int usb_eth_initialize(bd_t *bi)
        if (status)
                goto fail;
 
-       status = usb_gadget_register_driver(&eth_driver);
-       if (status < 0)
-               goto fail;
-
        eth_register(netdev);
        return 0;
 
index 480bc87..e66c8fb 100644 (file)
 #define        gadget_is_m66592(g)     0
 #endif
 
+#ifdef CONFIG_USB_GADGET_S3C_UDC_OTG
+#define        gadget_is_s3c_udc_otg(g)        !strcmp("s3c-udc", (g)->name)
+#else
+#define        gadget_is_s3c_udc_otg(g)        0
+#endif
 
 // CONFIG_USB_GADGET_SX2
 // CONFIG_USB_GADGET_AU1X00
@@ -215,5 +220,7 @@ static inline int usb_gadget_controller_number(struct usb_gadget *gadget)
                return 0x20;
        else if (gadget_is_m66592(gadget))
                return 0x21;
+       else if (gadget_is_s3c_udc_otg(gadget))
+               return 0x22;
        return -ENOENT;
 }
index 40cc18a..b2ac008 100644 (file)
 #ifndef __S3C_USB_GADGET
 #define __S3C_USB_GADGET
 
-#include <linux/module.h>
-#include <linux/kernel.h>
-#include <linux/ioport.h>
-#include <linux/types.h>
-#include <linux/version.h>
-#include <linux/errno.h>
-#include <linux/delay.h>
-#include <linux/sched.h>
-#include <linux/slab.h>
-#include <linux/init.h>
-#include <linux/timer.h>
-#include <linux/list.h>
-#include <linux/interrupt.h>
-#include <linux/proc_fs.h>
-#include <linux/mm.h>
-#include <linux/device.h>
-#include <linux/dma-mapping.h>
-#include <linux/regulator/consumer.h>
-
-#include <asm/byteorder.h>
-#include <asm/dma.h>
-#include <asm/io.h>
-#include <asm/irq.h>
-#include <asm/system.h>
-#include <asm/unaligned.h>
-//#include <asm/hardware.h>
 
 #include <linux/usb/ch9.h>
 #include <linux/usb/gadget.h>
+#include <linux/list.h>
+
+
+#define __iomem
+
+/*-------------------------------------------------------------------------*/
 
 #define DMA_BUFFER_SIZE                (4096*4)        /* DMA bounce buffer size, 16K is enough even for mass storage */
 
 // Max packet size
+/*
 #if defined(CONFIG_USB_GADGET_S3C_FS)
 #define EP0_FIFO_SIZE          8
 #define EP_FIFO_SIZE           64
 #define S3C_MAX_ENDPOINTS      5
 #elif defined(CONFIG_USB_GADGET_S3C_HS) || defined(CONFIG_PLAT_S5P64XX) || defined(CONFIG_PLAT_S5PC1XX) \
        || defined(CONFIG_CPU_S5P6442)
+*/
 #define EP0_FIFO_SIZE          64
 #define EP_FIFO_SIZE           512
 #define EP_FIFO_SIZE2          1024
 #define S3C_MAX_ENDPOINTS      16
+/*
 #else
 #define EP0_FIFO_SIZE          64
 #define EP_FIFO_SIZE           512
 #define EP_FIFO_SIZE2          1024
 #define S3C_MAX_ENDPOINTS      16
 #endif
-
+*/
 #define WAIT_FOR_SETUP          0
 #define DATA_STATE_XMIT         1
 #define DATA_STATE_NEED_ZLP     2
@@ -126,7 +109,8 @@ struct s3c_udc {
        struct usb_gadget gadget;
        struct usb_gadget_driver *driver;
        //struct device *dev;
-       struct platform_device *dev;
+//     struct platform_device *dev;
+       struct s3c_plat_otg_data *pdata;
        spinlock_t lock;
        void *dma_buf[S3C_MAX_ENDPOINTS+1];
 
@@ -135,8 +119,8 @@ struct s3c_udc {
 
        unsigned char usb_address;
 
-       struct regulator *regulator_a;
-       struct regulator *regulator_d;
+//     struct regulator *regulator_a;
+//     struct regulator *regulator_d;
 
        unsigned req_pending:1, req_std:1, req_config:1;
 };
@@ -147,4 +131,32 @@ extern struct s3c_udc *the_controller;
 #define ep_index(EP)           ((EP)->bEndpointAddress&0xF)
 #define ep_maxpacket(EP)       ((EP)->ep.maxpacket)
 
+
+
+/*-------------------------------------------------------------------------*/
+
+#ifdef DEBUG
+#define DBG(stuff...)          printf("udc: " stuff)
+#else
+#define DBG(stuff...)          do{}while(0)
+#endif
+
+#ifdef VERBOSE
+#define VDBG(x...)     printf(x)
+//VDBG(x...) printf(__FUNCTION__ , x)
+#else
+#define VDBG(stuff...) do{}while(0)
+#endif
+
+#ifdef PACKET_TRACE
+#    define PACKET             VDBG
+#else
+#    define PACKET(stuff...)   do{}while(0)
+#endif
+
+#define ERR(stuff...)          printf("ERR udc: " stuff)
+#define WARN(stuff...)         printf("WARNING udc: " stuff)
+#define INFO(stuff...)         printf("INFO udc: " stuff)
+
+
 #endif
index 0353027..f728fa7 100644 (file)
  *
  */
 
-#include "s3c_udc.h"
-#include <linux/platform_device.h>
-#include <linux/clk.h>
-#include <mach/map.h>
-#include "s3c_udc-regs-otg.h"
-#include <plat/regs-sys.h>
-#include <plat/regs-clock.h>
 
+#include <common.h>
+#include <asm/errno.h>
+#include <linux/list.h>
+#include <malloc.h>
 
-void __iomem           *regs_otg;
-void __iomem           *regs_phy;
-struct resource                *res_otg;
-struct resource                *res_phy;
+#include <linux/usb/ch9.h>
+#include <linux/usb/gadget.h>
 
-/* Initializes OTG Phy. */
-void otg_phy_init(void)
-{
-       printk("otg phy init: regs %08x, phy %08x\n", (u32)regs_otg, (u32)regs_phy);
 
-       /*USB PHY0 Enable */
-//     writel(readl(S5P_USB_PHY_CONTROL)|(0x1<<0), S5P_USB_PHY_CONTROL);
-       writel(readl(S5PC110_USB_PHY_CON)|(0x1<<0), S5PC110_USB_PHY_CON);
-       writel((readl(S3C_USBOTG_PHYPWR)&~(0x3<<3)&~(0x1<<0))|(0x1<<5),
-                       S3C_USBOTG_PHYPWR);
-       writel((readl(S3C_USBOTG_PHYCLK)&~(0x5<<2))|(0x3<<0),
-                       S3C_USBOTG_PHYCLK);
-       writel((readl(S3C_USBOTG_RSTCON)&~(0x3<<1))|(0x1<<0),
-                       S3C_USBOTG_RSTCON);
-       udelay(10);
-       writel(readl(S3C_USBOTG_RSTCON)&~(0x7<<0), S3C_USBOTG_RSTCON);
-       udelay(10);
+/* common */
+typedef int    spinlock_t;
+typedef int    wait_queue_head_t;
+typedef int    irqreturn_t;
+#define spin_lock_init(...)
+#define spin_lock(...)
+#define spin_lock_irqsave(lock, flags) flags=1
+#define spin_unlock(...)
+#define spin_unlock_irqrestore(lock, flags) flags=0
+#define disable_irq(...)
+#define enable_irq(...)
 
-       printk("otg phy init done\n");
+#define mutex_init(...)
+#define mutex_lock(...)
+#define mutex_unlock(...)
 
-}
-EXPORT_SYMBOL(otg_phy_init);
+#define WARN_ON(x) if (x) { printf("WARNING in %s line %d\n", __FILE__, __LINE__); }
 
-/* OTG PHY Power Off */
-void otg_phy_off(void)
-{
-       printk("otg phy off\n");
-       writel(readl(S3C_USBOTG_PHYPWR)|(0x3<<3), S3C_USBOTG_PHYPWR);
-       writel(readl(S5PC110_USB_PHY_CON)&~(1<<0), S5PC110_USB_PHY_CON);
-//     writel(readl(S5P_USB_PHY_CONTROL)&~(1<<0), S5P_USB_PHY_CONTROL);
-       printk("otg phy off done\n");
-}
-EXPORT_SYMBOL(otg_phy_off);
+#define printk printf
 
+#define KERN_WARNING
+#define KERN_ERR
+#define KERN_NOTICE
+#define KERN_DEBUG
 
-#if    defined(CONFIG_USB_GADGET_S3C_OTGD_DMA_MODE) /* DMA mode */
-#define OTG_DMA_MODE           1
+#define GFP_KERNEL                     0
 
-#elif  defined(CONFIG_USB_GADGET_S3C_OTGD_SLAVE_MODE) /* Slave mode */
-#define OTG_DMA_MODE           0
-#error " Slave Mode is not implemented to do later"
-#else
-#error " Unknown S3C OTG operation mode, Select a correct operation mode"
-#endif
+#define IRQ_HANDLED    1
+
+#define ENOTSUPP       524     /* Operation is not supported */
+
+#define EXPORT_SYMBOL(x)
+
+#define dma_cache_maint(addr, size, mode) cache_flush()
+
+#define kmalloc(size, type) malloc(size)
+#define kfree(addr) free(addr)
+#define mdelay(n) ({unsigned long msec = (n); while (msec--) udelay(1000); })
+
+#include <asm/byteorder.h>
+#include <asm/io.h>
+#include <asm-arm/proc-armv/system.h>
+#include <asm/mach-types.h>
+
+#include <asm/arch/gpio.h>
+
+#define __iomem
+
+#include "s3c_udc.h"
+#include <asm/arch/regs-otg.h>
+#include <asm/arch/hs_otg.h>
+#include <asm/arch/power.h>
+
+
+/***********************************************************/
+
+#define OTG_DMA_MODE           1
 
 #undef DEBUG_S3C_UDC_SETUP
 #undef DEBUG_S3C_UDC_EP0
@@ -87,12 +96,12 @@ EXPORT_SYMBOL(otg_phy_off);
 #undef DEBUG_S3C_UDC_IN_EP
 #undef DEBUG_S3C_UDC
 
-#define DEBUG_S3C_UDC_SETUP
-#define DEBUG_S3C_UDC_EP0
+//#define DEBUG_S3C_UDC_SETUP
+//#define DEBUG_S3C_UDC_EP0 *
 //#define DEBUG_S3C_UDC_ISR
 //#define DEBUG_S3C_UDC_OUT_EP
 //#define DEBUG_S3C_UDC_IN_EP
-#define DEBUG_S3C_UDC
+//#define DEBUG_S3C_UDC
 
 #define EP0_CON                0
 #define EP_MASK                0xF
@@ -146,7 +155,6 @@ static char *state_names[] = {
 #define DEBUG_IN_EP(fmt,args...) do {} while(0)
 #endif
 
-
 #define        DRIVER_DESC             "S3C HS USB OTG Device Driver, (c) 2008-2009 Samsung Electronics"
 #define        DRIVER_VERSION          "15 March 2009"
 
@@ -207,61 +215,55 @@ static struct usb_ep_ops s3c_ep_ops = {
        .fifo_flush = s3c_fifo_flush,
 };
 
-#ifdef CONFIG_USB_GADGET_DEBUG_FILES
+#define create_proc_files() do {} while (0)
+#define remove_proc_files() do {} while (0)
 
-static const char proc_node_name[] = "driver/udc";
+/***********************************************************/
 
-static int
-udc_proc_read(char *page, char **start, off_t off, int count,
-             int *eof, void *_dev)
+void __iomem           *regs_otg;
+void __iomem           *regs_phy;
+
+
+void otg_phy_init(void)
 {
-       char *buf = page;
-       struct s3c_udc *dev = _dev;
-       char *next = buf;
-       unsigned size = count;
-       unsigned long flags;
-       int t;
+       the_controller->pdata->phy_control(1);
 
-       if (off != 0)
-               return 0;
+       /*USB PHY0 Enable */
+//     printf("USB PHY0 Enable\n");
+//     writel(readl(S5P_USB_PHY_CONTROL)|(0x1<<0), S5P_USB_PHY_CONTROL);
+       writel(readl(S5PC110_USB_PHY_CON)|(0x1<<0), S5PC110_USB_PHY_CON);
+
+       writel((readl(S3C_USBOTG_PHYPWR)&~(0x3<<3)&~(0x1<<0))|(0x1<<5),
+                       S3C_USBOTG_PHYPWR);
+       writel((readl(S3C_USBOTG_PHYCLK)&~(0x5<<2))|(0x3<<0),
+                       S3C_USBOTG_PHYCLK);
+       writel((readl(S3C_USBOTG_RSTCON)&~(0x3<<1))|(0x1<<0),
+                       S3C_USBOTG_RSTCON);
 
-       local_irq_save(flags);
-
-       /* basic device status */
-       t = scnprintf(next, size,
-                     DRIVER_DESC "\n"
-                     "%s version: %s\n"
-                     "Gadget driver: %s\n"
-                     "\n",
-                     driver_name, DRIVER_VERSION,
-                     dev->driver ? dev->driver->driver.name : "(none)");
-       size -= t;
-       next += t;
-
-       local_irq_restore(flags);
-       *eof = 1;
-       return count - size;
+       writel(0x1, S3C_USBOTG_RSTCON);
+       udelay(20);
+       writel(0x0, S3C_USBOTG_RSTCON);
+       udelay(20);
 }
 
-#define create_proc_files() \
-       create_proc_read_entry(proc_node_name, 0, NULL, udc_proc_read, dev)
-#define remove_proc_files() \
-       remove_proc_entry(proc_node_name, NULL)
+void otg_phy_off(void)
+{
+       writel(readl(S3C_USBOTG_PHYPWR)|(0x3<<3), S3C_USBOTG_PHYPWR);
+       writel(readl(S5PC110_USB_PHY_CON)&~(1<<0), S5PC110_USB_PHY_CON);
+//     writel(readl(S5P_USB_PHY_CONTROL)&~(1<<0), S5P_USB_PHY_CONTROL);
+
+       writel((readl(S3C_USBOTG_PHYPWR)&~(0x3<<3)&~(0x1<<0)),S3C_USBOTG_PHYPWR);
+       writel((readl(S3C_USBOTG_PHYCLK)&~(0x5<<2)),S3C_USBOTG_PHYCLK);
 
-#else  /* !CONFIG_USB_GADGET_DEBUG_FILES */
+       udelay(10000);
 
-#define create_proc_files() do {} while (0)
-#define remove_proc_files() do {} while (0)
+       the_controller->pdata->phy_control(0);
+}
 
-#endif /* CONFIG_USB_GADGET_DEBUG_FILES */
+/***********************************************************/
 
-#if    OTG_DMA_MODE /* DMA Mode */
 #include "s3c_udc_otg_xfer_dma.c"
 
-#else  /* Slave Mode */
-#include "s3c_udc_otg_xfer_slave.c"
-#endif
-
 /*
  *     udc_disable - disable USB device controller
  */
@@ -335,10 +337,10 @@ static int udc_enable(struct s3c_udc *dev)
 int usb_gadget_register_driver(struct usb_gadget_driver *driver)
 {
        struct s3c_udc *dev = the_controller;
-       int retval;
+       int retval = 0;
        unsigned long flags;
 
-       DEBUG_SETUP("%s: %s\n", __FUNCTION__, driver->driver.name);
+       DEBUG_SETUP("%s: %s\n", __FUNCTION__, "no name");
 
         if (!driver
             || (driver->speed != USB_SPEED_FULL && driver->speed != USB_SPEED_HIGH)
@@ -370,9 +372,9 @@ int usb_gadget_register_driver(struct usb_gadget_driver *driver)
 */
        /* first hook up the driver ... */
        dev->driver = driver;
-       dev->gadget.dev.driver = &driver->driver;
+//     dev->gadget.dev.driver = &driver->driver;
        spin_unlock_irqrestore(&dev->lock, flags);
-       retval = device_add(&dev->gadget.dev);
+//     retval = device_add(&dev->gadget.dev);
 
        if(retval) { /* TODO */
                printk("target device_add failed, error %d\n", retval);
@@ -381,18 +383,18 @@ int usb_gadget_register_driver(struct usb_gadget_driver *driver)
 
        retval = driver->bind(&dev->gadget);
        if (retval) {
-               printk("%s: bind to driver %s --> error %d\n", dev->gadget.name,
-                      driver->driver.name, retval);
-               device_del(&dev->gadget.dev);
+//             printk("%s: bind to driver %s --> error %d\n", dev->gadget.name,
+//                    driver->driver.name, retval);
+//             device_del(&dev->gadget.dev);
 
                dev->driver = 0;
-               dev->gadget.dev.driver = 0;
+//             dev->gadget.dev.driver = 0;
                return retval;
        }
 
        enable_irq(IRQ_OTG);
 
-       printk("Registered gadget driver '%s'\n", driver->driver.name);
+//     printk("Registered gadget driver %s\n", dev->gadget.name);
        udc_enable(dev);
 
        return 0;
@@ -419,14 +421,14 @@ int usb_gadget_unregister_driver(struct usb_gadget_driver *driver)
        spin_unlock_irqrestore(&dev->lock, flags);
 
        driver->unbind(&dev->gadget);
-       device_del(&dev->gadget.dev);
+//     device_del(&dev->gadget.dev);
 
        disable_irq(IRQ_OTG);
 
-       printk("Unregistered gadget driver '%s'\n", driver->driver.name);
+//     printk("Unregistered gadget driver '%s'\n", driver->driver.name);
 
        udc_disable(dev);
-
+/*
        if (!IS_ERR(dev->regulator_a)) {
                regulator_disable(dev->regulator_a);
                regulator_put(dev->regulator_a);
@@ -437,7 +439,7 @@ int usb_gadget_unregister_driver(struct usb_gadget_driver *driver)
                regulator_put(dev->regulator_d);
                dev->regulator_d = NULL;
        }
-
+*/
        return 0;
 }
 
@@ -470,10 +472,28 @@ static void done(struct s3c_ep *ep, struct s3c_request *req, int status)
        /* don't modify queue heads during completion callback */
        ep->stopped = 1;
 
+#ifdef DEBUG_S3C_UDC
+       printf("calling complete callback\n");
+       {
+               int i, len = req->req.length;
+
+               printf("pkt[%d] = ", req->req.length);
+               if (len > 64)
+                       len = 64;
+               for (i=0; i<len; i++) {
+                       printf("%02x", ((u8*)req->req.buf)[i]);
+                       if ((i & 7) == 7)
+                               printf(" ");
+               }
+               printf("\n");
+       }
+#endif
        spin_unlock(&ep->dev->lock);
        req->req.complete(&ep->ep, &req->req);
        spin_lock(&ep->dev->lock);
 
+       DEBUG("callback completed\n");
+
        ep->stopped = stopped;
 }
 
@@ -527,6 +547,8 @@ static void reconfig_usbd(void)
        int i;
        unsigned int uTemp = writel(CORE_SOFT_RESET, S3C_UDC_OTG_GRSTCTL);
 
+       DEBUG(2, "Reseting OTG controller\n");
+
        writel( 0<<15           /* PHY Low Power Clock sel*/
                |1<<14          /* Non-Periodic TxFIFO Rewind Enable*/
                |0x5<<10        /* Turnaround time*/
@@ -590,12 +612,14 @@ static void reconfig_usbd(void)
 
         /* Flush the RX FIFO */
         writel(0x10, S3C_UDC_OTG_GRSTCTL);
-        while(readl(S3C_UDC_OTG_GRSTCTL) & 0x10);
+        while(readl(S3C_UDC_OTG_GRSTCTL) & 0x10)
+               DEBUG("%s: waiting for S3C_UDC_OTG_GRSTCTL\n", __FUNCTION__);
 
         /* Flush all the Tx FIFO's */
         writel(0x10<<6, S3C_UDC_OTG_GRSTCTL);
         writel((0x10<<6)|0x20, S3C_UDC_OTG_GRSTCTL);
-        while(readl(S3C_UDC_OTG_GRSTCTL) & 0x20);
+        while(readl(S3C_UDC_OTG_GRSTCTL) & 0x20)
+               DEBUG("%s: waiting for S3C_UDC_OTG_GRSTCTL\n", __FUNCTION__);
 
        /* 13. Clear NAK bit of EP0, EP1, EP2*/
        /* For Slave mode*/
@@ -860,10 +884,11 @@ static struct s3c_udc memory = {
                   .ops = &s3c_udc_ops,
                   .ep0 = &memory.ep[0].ep,
                   .name = driver_name,
-                  .dev = {
+/*                .dev = {
                           .init_name = "gadget",
                           .release = nop_release,
                           },
+*/
                   },
 
        /* control endpoint */
@@ -1099,21 +1124,18 @@ static struct s3c_udc memory = {
 /*
  *     probe - binds to the platform device
  */
-static struct clk      *otg_clock = NULL;
 
-static int s3c_udc_probe(struct platform_device *pdev)
+int s3c_udc_probe(struct s3c_plat_otg_data *pdata)
 {
-       struct resource *res;
        struct s3c_udc *dev = &memory;
-       int retval, i;
+       int retval=0, i;
 
-       DEBUG("%s: %p\n", __FUNCTION__, pdev);
+       DEBUG("%s: %p\n", __FUNCTION__, pdata);
 
-       spin_lock_init(&dev->lock);
-       dev->dev = pdev;
+       dev->pdata = pdata;
 
-       device_initialize(&dev->gadget.dev);
-       dev->gadget.dev.parent = &pdev->dev;
+       regs_phy = (void *)pdata->regs_phy;
+       regs_otg = (void*)pdata->regs_otg;
 
        dev->gadget.is_dualspeed = 1;   /* Hack only*/
        dev->gadget.is_otg = 0;
@@ -1123,241 +1145,28 @@ static int s3c_udc_probe(struct platform_device *pdev)
        dev->gadget.a_alt_hnp_support = 0;
 
        the_controller = dev;
-       platform_set_drvdata(pdev, dev);
-
-       otg_clock = clk_get(&pdev->dev, "otg");
-       if (otg_clock == NULL) {
-               printk(KERN_INFO "failed to find otg clock source\n");
-               return -ENOENT;
-       }
-       clk_enable(otg_clock);
 
-       /* basic endpoint records init */
        for (i = 0; i < S3C_MAX_ENDPOINTS+1; i++)
                dev->dma_buf[i] = kmalloc(DMA_BUFFER_SIZE, GFP_KERNEL);
        usb_ctrl = dev->dma_buf[0];
-       
-       printk(KERN_INFO "allocating resources\n");
-       res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
-       if (!res) {
-               printk(KERN_INFO "cannot find register resource 0\n");
-               return -EINVAL;
-       }
-
-       res_otg = request_mem_region(res->start, resource_size(res),
-                                       dev_name(&pdev->dev));
-       if (!res_otg) {
-               printk(KERN_INFO "cannot reserve registers\n");
-               return -ENOENT;
-       }
-
-       regs_otg = ioremap(res->start, resource_size(res));
-       if (!regs_otg) {
-               printk(KERN_INFO "cannot map registers\n");
-               retval = -ENXIO;
-       }
-
-       res = platform_get_resource(pdev, IORESOURCE_MEM, 1);
-       if (!res) {
-               printk(KERN_INFO "cannot find register resource 1\n");
-               return -EINVAL;
-       }
-
-       res_phy = request_mem_region(res->start, resource_size(res),
-                                       dev_name(&pdev->dev));
-       if (!res_phy) {
-               printk(KERN_INFO "cannot reserve registers\n");
-               return -ENOENT;
-       }
-
-       regs_phy = ioremap(res->start, resource_size(res));
-       if (!regs_phy) {
-               printk(KERN_INFO "cannot map registers\n");
-               retval = -ENXIO;
-       }
 
        udc_reinit(dev);
 
-       local_irq_disable();
-
-       /* irq setup after old hardware state is cleaned up */
-       retval =
-           request_irq(IRQ_OTG, s3c_udc_irq, 0, driver_name, dev);
-
-       if (retval != 0) {
-               DEBUG(KERN_ERR "%s: can't get irq %i, err %d\n", driver_name,
-                     IRQ_OTG, retval);
-               return -EBUSY;
-       }
-
-       disable_irq(IRQ_OTG);
-       local_irq_enable();
-       create_proc_files();
-
        return retval;
 }
 
 static int s3c_udc_remove(struct platform_device *pdev)
 {
-       struct s3c_udc *dev = platform_get_drvdata(pdev);
-
-       DEBUG("%s: %p\n", __FUNCTION__, pdev);
-
-       regulator_disable(dev->regulator_a);
-       regulator_disable(dev->regulator_d);
-       regulator_put(dev->regulator_a);
-       regulator_put(dev->regulator_d);
-
-       if (otg_clock != NULL) {
-               clk_disable(otg_clock);
-               clk_put(otg_clock);
-               otg_clock = NULL;
-       }
-
-       remove_proc_files();
-       usb_gadget_unregister_driver(dev->driver);
-
-       free_irq(IRQ_OTG, dev);
-
-       platform_set_drvdata(pdev, 0);
-
-       iounmap(regs_otg);
-       iounmap(regs_phy);
-
-       release_mem_region(res_phy->start, resource_size(res_phy));
-       release_mem_region(res_otg->start, resource_size(res_otg));
-
        the_controller = 0;
-
        return 0;
 }
 
-#ifdef CONFIG_PM
-static int s3c_udc_suspend(struct platform_device *pdev, pm_message_t state)
-{
-        struct s3c_udc *dev = platform_get_drvdata(pdev);
-        int i;
-
-        if (dev->driver) {
-                if (dev->driver->suspend)
-                        dev->driver->suspend(&dev->gadget);
-
-                /* Terminate any outstanding requests  */
-                for (i = 0; i < S3C_MAX_ENDPOINTS; i++) {
-                        struct s3c_ep *ep = &dev->ep[i];
-                        if ( ep->dev != NULL )
-                                spin_lock(&ep->dev->lock);
-                        ep->stopped = 1;
-                        nuke(ep, -ESHUTDOWN);
-                        if ( ep->dev != NULL )
-                                spin_unlock(&ep->dev->lock);
-                }
-
-                disable_irq(IRQ_OTG);
-                udc_disable(dev);
-                clk_disable(otg_clock);
-
-               /* Workaround: can't find a regulator at probe time */
-               if (!dev->regulator_a) {
-                       dev->regulator_a = regulator_get(&pdev->dev, "vusb_a");
-                       if (IS_ERR(dev->regulator_a))
-                               dev->regulator_a = NULL;
-                       else
-                               regulator_enable(dev->regulator_a);
-               }
-
-               if (!dev->regulator_d) {
-                       dev->regulator_d = regulator_get(&pdev->dev, "vusb_d");
-                       if (IS_ERR(dev->regulator_d))
-                               dev->regulator_d = NULL;
-                       else
-                               regulator_enable(dev->regulator_d);
-               }
-
-               if (dev->regulator_a && regulator_is_enabled(dev->regulator_a)) {
-                       int ret = regulator_disable(dev->regulator_a);
-                       if (ret)
-                               return ret;
-               }
-
-               if (dev->regulator_d && regulator_is_enabled(dev->regulator_d)) {
-                       int ret = regulator_disable(dev->regulator_d);
-                       if (ret)
-                               return ret;
-               }
-        }
-
-        return 0;
-}
-
-static int s3c_udc_resume(struct platform_device *pdev)
-{
-        struct s3c_udc *dev = platform_get_drvdata(pdev);
-
-        if (dev->driver) {
-               if (dev->regulator_d) {
-                       int ret = regulator_enable(dev->regulator_d);
-                       if (ret)
-                               return ret;
-               }
-
-               if (dev->regulator_a) {
-                       int ret = regulator_enable(dev->regulator_a);
-                       if (ret)
-                               return ret;
-               }
-
-                clk_enable(otg_clock);
-                udc_reinit(dev);
-                enable_irq(IRQ_OTG);
-                udc_enable(dev);
-
-                if (dev->driver->resume)
-                        dev->driver->resume(&dev->gadget);
-        }
-
-        return 0;
-}
-#else
-#define s3c_udc_suspend NULL
-#define s3c_udc_resume  NULL
-#endif /* CONFIG_PM */
-
-/*-------------------------------------------------------------------------*/
-static struct platform_driver s3c_udc_driver = {
-       .probe          = s3c_udc_probe,
-       .remove         = s3c_udc_remove,
-       .suspend        = s3c_udc_suspend,
-       .resume         = s3c_udc_resume,
-       .driver         = {
-               .owner  = THIS_MODULE,
-               .name   = "s3c-otg",
-       },
-};
-
-static int __init udc_init(void)
+int usb_gadget_handle_interrupts()
 {
-       int ret;
-
-       ret = platform_driver_register(&s3c_udc_driver);
-       if(!ret)
-          printk("%s : %s\n"
-                 "%s : version %s %s \n",
-                 driver_name, DRIVER_DESC,
-                 driver_name, DRIVER_VERSION, OTG_DMA_MODE? "(DMA Mode)" : "(Slave Mode)");
-
-       return ret;
-}
+       u32 intr_status = readl(S3C_UDC_OTG_GINTSTS);
+       u32 gintmsk = readl(S3C_UDC_OTG_GINTMSK);
 
-static void __exit udc_exit(void)
-{
-       platform_driver_unregister(&s3c_udc_driver);
-       printk("Unloaded %s version %s\n", driver_name, DRIVER_VERSION);
+       if (intr_status & gintmsk)
+               return s3c_udc_irq(1, (void*)the_controller);
+       return 0;
 }
-
-module_init(udc_init);
-module_exit(udc_exit);
-
-MODULE_DESCRIPTION(DRIVER_DESC);
-MODULE_AUTHOR("Samsung");
-MODULE_LICENSE("GPL");
index eaca2bd..95c6015 100644 (file)
@@ -77,6 +77,15 @@ static inline void s3c_udc_pre_setup(void)
 
        ep_ctrl = readl(S3C_UDC_OTG_DOEPCTL(EP0_CON));
        writel(ep_ctrl|DEPCTL_EPENA|DEPCTL_CNAK, S3C_UDC_OTG_DOEPCTL(EP0_CON));
+
+       DEBUG_OUT_EP("%s: EP%d RX DMA start : DOEPDMA = 0x%x, DOEPTSIZ = 0x%x, DOEPCTL = 0x%x\n"
+                       "\tbuf = 0x%p, pktcnt = %d, xfersize = %d\n",
+                       __func__, 0,
+                       readl(S3C_UDC_OTG_DOEPDMA(0)),
+                       readl(S3C_UDC_OTG_DOEPTSIZ(0)),
+                       readl(S3C_UDC_OTG_DOEPCTL(0)),
+                       usb_ctrl, 1, sizeof(*usb_ctrl));
+
 }
 
 static int setdma_rx(struct s3c_ep *ep, struct s3c_request *req)
@@ -511,7 +520,7 @@ static int s3c_queue(struct usb_ep *_ep, struct usb_request *_req,
 
        if (unlikely(!_ep || (!ep->desc && ep->ep.name != ep0name))) {
 
-               DEBUG("%s: bad ep\n", __func__);
+               DEBUG("%s: bad ep: %s, %d, %x\n", __func__, ep->ep.name, !ep->desc, _ep);
                return -EINVAL;
        }
 
@@ -535,6 +544,22 @@ static int s3c_queue(struct usb_ep *_ep, struct usb_request *_req,
                _req, _req->length,_req->buf,
                list_empty(&ep->queue), ep->stopped);
 
+#ifdef DEBUG_S3C_UDC
+       {
+               int i, len = _req->length;
+
+               printf("pkt = ");
+               if (len > 64)
+                       len = 64;
+               for (i=0; i<len; i++) {
+                       printf("%02x", ((u8*)_req->buf)[i]);
+                       if ((i & 7) == 7)
+                               printf(" ");
+               }
+               printf("\n");
+       }
+#endif
+
        if (list_empty(&ep->queue) && !ep->stopped) {
 
                if (ep_num == 0) {
diff --git a/include/asm-arm/arch-s5pc1xx/hs_otg.h b/include/asm-arm/arch-s5pc1xx/hs_otg.h
new file mode 100644 (file)
index 0000000..d68db04
--- /dev/null
@@ -0,0 +1,32 @@
+/*
+ * (C) Copyright 2009 SAMSUNG Electronics
+ * Minkyu Kang <mk7.kang@samsung.com>
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * 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., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ *
+ */
+
+#ifndef __ASM_ARCH_HSOTG_H_
+#define __ASM_ARCH_HSOTG_H_
+
+#ifndef __ASSEMBLY__
+struct s3c_plat_otg_data {
+       int             (*phy_control)(int on);
+       unsigned int    regs_phy;
+       unsigned int    regs_otg;
+};
+
+#endif /* __ASSEMBLY__ */
+#endif
diff --git a/include/asm-arm/arch-s5pc1xx/regs-otg.h b/include/asm-arm/arch-s5pc1xx/regs-otg.h
new file mode 100644 (file)
index 0000000..72769c4
--- /dev/null
@@ -0,0 +1,264 @@
+/* linux/arch/arm/plat-s3c/include/plat/regs-otg.h
+ *
+ * Copyright (C) 2004 Herbert Poetzl <herbert@13thfloor.at>
+ *
+ * This include file is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+*/
+
+#ifndef __ASM_ARCH_REGS_USB_OTG_HS_H
+#define __ASM_ARCH_REGS_USB_OTG_HS_H
+
+/*
+ * USB2.0 HS OTG
+ */
+#define S5PC100_OTG_BASE       0xED200000
+#define S5PC100_PHY_BASE       0xED300000
+
+#define S5PC110_OTG_BASE       0xEC000000
+#define S5PC110_PHY_BASE       0xEC100000
+
+/* USB2.0 OTG Controller register */
+#define S3C_USBOTG_PHYREG(x)           (((u32)regs_phy) + (x))
+#define S3C_USBOTG_PHYPWR              S3C_USBOTG_PHYREG(0x0)
+#define S3C_USBOTG_PHYCLK              S3C_USBOTG_PHYREG(0x4)
+#define S3C_USBOTG_RSTCON              S3C_USBOTG_PHYREG(0x8)
+
+
+/* USB2.0 OTG Controller register */
+#define S3C_USBOTGREG(x)               (((u32)regs_otg) + (x))
+/*============================================================================================== */
+       /* Core Global Registers */
+#define S3C_UDC_OTG_GOTGCTL            S3C_USBOTGREG(0x000)            /* OTG Control & Status */
+#define S3C_UDC_OTG_GOTGINT            S3C_USBOTGREG(0x004)            /* OTG Interrupt */
+#define S3C_UDC_OTG_GAHBCFG            S3C_USBOTGREG(0x008)            /* Core AHB Configuration */
+#define S3C_UDC_OTG_GUSBCFG            S3C_USBOTGREG(0x00C)            /* Core USB Configuration */
+#define S3C_UDC_OTG_GRSTCTL            S3C_USBOTGREG(0x010)            /* Core Reset */
+#define S3C_UDC_OTG_GINTSTS            S3C_USBOTGREG(0x014)            /* Core Interrupt */
+#define S3C_UDC_OTG_GINTMSK            S3C_USBOTGREG(0x018)            /* Core Interrupt Mask */
+#define S3C_UDC_OTG_GRXSTSR            S3C_USBOTGREG(0x01C)            /* Receive Status Debug Read/Status Read */
+#define S3C_UDC_OTG_GRXSTSP            S3C_USBOTGREG(0x020)            /* Receive Status Debug Pop/Status Pop */
+#define S3C_UDC_OTG_GRXFSIZ            S3C_USBOTGREG(0x024)            /* Receive FIFO Size */
+#define S3C_UDC_OTG_GNPTXFSIZ          S3C_USBOTGREG(0x028)            /* Non-Periodic Transmit FIFO Size */
+#define S3C_UDC_OTG_GNPTXSTS           S3C_USBOTGREG(0x02C)            /* Non-Periodic Transmit FIFO/Queue Status */
+
+#define S3C_UDC_OTG_HPTXFSIZ           S3C_USBOTGREG(0x100)            /* Host Periodic Transmit FIFO Size */
+#define S3C_UDC_OTG_DIEPTXF(n)         S3C_USBOTGREG(0x104 + ((n)-1)*0x4)/* Device IN EP Transmit FIFO Size Register */
+
+/*============================================================================================== */
+/* Host Mode Registers */
+/*------------------------------------------------ */
+/* Host Global Registers */
+#define S3C_UDC_OTG_HCFG               S3C_USBOTGREG(0x400)            /* Host Configuration */
+#define S3C_UDC_OTG_HFIR               S3C_USBOTGREG(0x404)            /* Host Frame Interval */
+#define S3C_UDC_OTG_HFNUM              S3C_USBOTGREG(0x408)            /* Host Frame Number/Frame Time Remaining */
+#define S3C_UDC_OTG_HPTXSTS            S3C_USBOTGREG(0x410)            /* Host Periodic Transmit FIFO/Queue Status */
+#define S3C_UDC_OTG_HAINT              S3C_USBOTGREG(0x414)            /* Host All Channels Interrupt */
+#define S3C_UDC_OTG_HAINTMSK           S3C_USBOTGREG(0x418)            /* Host All Channels Interrupt Mask */
+
+/*------------------------------------------------ */
+/* Host Port Control & Status Registers */
+#define S3C_UDC_OTG_HPRT               S3C_USBOTGREG(0x440)            /* Host Port Control & Status */
+
+/*------------------------------------------------ */
+/* Host Channel-Specific Registers */
+#define S3C_UDC_OTG_HCCHAR0            S3C_USBOTGREG(0x500)            /* Host Channel-0 Characteristics */
+#define S3C_UDC_OTG_HCSPLT0            S3C_USBOTGREG(0x504)            /* Host Channel-0 Split Control */
+#define S3C_UDC_OTG_HCINT0             S3C_USBOTGREG(0x508)            /* Host Channel-0 Interrupt */
+#define S3C_UDC_OTG_HCINTMSK0          S3C_USBOTGREG(0x50C)            /* Host Channel-0 Interrupt Mask */
+#define S3C_UDC_OTG_HCTSIZ0            S3C_USBOTGREG(0x510)            /* Host Channel-0 Transfer Size */
+#define S3C_UDC_OTG_HCDMA0             S3C_USBOTGREG(0x514)            /* Host Channel-0 DMA Address */
+
+
+/*============================================================================================== */
+/* Device Mode Registers */
+/*------------------------------------------------ */
+/* Device Global Registers */
+#define S3C_UDC_OTG_DCFG               S3C_USBOTGREG(0x800)            /* Device Configuration */
+#define S3C_UDC_OTG_DCTL               S3C_USBOTGREG(0x804)            /* Device Control */
+#define S3C_UDC_OTG_DSTS               S3C_USBOTGREG(0x808)            /* Device Status */
+#define S3C_UDC_OTG_DIEPMSK            S3C_USBOTGREG(0x810)            /* Device IN Endpoint Common Interrupt Mask */
+#define S3C_UDC_OTG_DOEPMSK            S3C_USBOTGREG(0x814)            /* Device OUT Endpoint Common Interrupt Mask */
+#define S3C_UDC_OTG_DAINT              S3C_USBOTGREG(0x818)            /* Device All Endpoints Interrupt */
+#define S3C_UDC_OTG_DAINTMSK           S3C_USBOTGREG(0x81C)            /* Device All Endpoints Interrupt Mask */
+#define S3C_UDC_OTG_DTKNQR1            S3C_USBOTGREG(0x820)            /* Device IN Token Sequence Learning Queue Read 1 */
+#define S3C_UDC_OTG_DTKNQR2            S3C_USBOTGREG(0x824)            /* Device IN Token Sequence Learning Queue Read 2 */
+#define S3C_UDC_OTG_DVBUSDIS           S3C_USBOTGREG(0x828)            /* Device VBUS Discharge Time */
+#define S3C_UDC_OTG_DVBUSPULSE         S3C_USBOTGREG(0x82C)            /* Device VBUS Pulsing Time */
+#define S3C_UDC_OTG_DTKNQR3            S3C_USBOTGREG(0x830)            /* Device IN Token Sequence Learning Queue Read 3 */
+#define S3C_UDC_OTG_DTKNQR4            S3C_USBOTGREG(0x834)            /* Device IN Token Sequence Learning Queue Read 4 */
+
+/*------------------------------------------------ */
+/* Device Logical IN Endpoint-Specific Registers */
+#define S3C_UDC_OTG_DIEPCTL(n)         S3C_USBOTGREG(0x900 + n*0x20)   /* Device IN Endpoint n Control */
+#define S3C_UDC_OTG_DIEPINT(n)         S3C_USBOTGREG(0x908 + n*0x20)   /* Device IN Endpoint n Interrupt */
+#define S3C_UDC_OTG_DIEPTSIZ(n)                S3C_USBOTGREG(0x910 + n*0x20)   /* Device IN Endpoint n Transfer Size */
+#define S3C_UDC_OTG_DIEPDMA(n)         S3C_USBOTGREG(0x914 + n*0x20)   /* Device IN Endpoint n DMA Address */
+
+/*------------------------------------------------ */
+/* Device Logical OUT Endpoint-Specific Registers */
+#define S3C_UDC_OTG_DOEPCTL(n)         S3C_USBOTGREG(0xB00 + n*0x20)   /* Device OUT Endpoint n Control */
+#define S3C_UDC_OTG_DOEPINT(n)         S3C_USBOTGREG(0xB08 + n*0x20)   /* Device OUT Endpoint n Interrupt */
+#define S3C_UDC_OTG_DOEPTSIZ(n)                S3C_USBOTGREG(0xB10 + n*0x20)   /* Device OUT Endpoint n Transfer Size */
+#define S3C_UDC_OTG_DOEPDMA(n)         S3C_USBOTGREG(0xB14 + n*0x20)   /* Device OUT Endpoint n DMA Address */
+
+/*------------------------------------------------ */
+/* Endpoint FIFO address */
+#define S3C_UDC_OTG_EP0_FIFO           S3C_USBOTGREG(0x1000)
+#define S3C_UDC_OTG_EP1_FIFO           S3C_USBOTGREG(0x2000)
+#define S3C_UDC_OTG_EP2_FIFO           S3C_USBOTGREG(0x3000)
+#define S3C_UDC_OTG_EP3_FIFO           S3C_USBOTGREG(0x4000)
+#define S3C_UDC_OTG_EP4_FIFO           S3C_USBOTGREG(0x5000)
+#define S3C_UDC_OTG_EP5_FIFO           S3C_USBOTGREG(0x6000)
+#define S3C_UDC_OTG_EP6_FIFO           S3C_USBOTGREG(0x7000)
+#define S3C_UDC_OTG_EP7_FIFO           S3C_USBOTGREG(0x8000)
+#define S3C_UDC_OTG_EP8_FIFO           S3C_USBOTGREG(0x9000)
+#define S3C_UDC_OTG_EP9_FIFO           S3C_USBOTGREG(0xA000)
+#define S3C_UDC_OTG_EP10_FIFO          S3C_USBOTGREG(0xB000)
+#define S3C_UDC_OTG_EP11_FIFO          S3C_USBOTGREG(0xC000)
+#define S3C_UDC_OTG_EP12_FIFO          S3C_USBOTGREG(0xD000)
+#define S3C_UDC_OTG_EP13_FIFO          S3C_USBOTGREG(0xE000)
+#define S3C_UDC_OTG_EP14_FIFO          S3C_USBOTGREG(0xF000)
+#define S3C_UDC_OTG_EP15_FIFO          S3C_USBOTGREG(0x10000)
+
+/*===================================================================== */
+/*definitions related to CSR setting */
+
+/* S3C_UDC_OTG_GOTGCTL */
+#define B_SESSION_VALID                        (0x1<<19)
+#define A_SESSION_VALID                        (0x1<<18)
+
+/* S3C_UDC_OTG_GAHBCFG */
+#define PTXFE_HALF                     (0<<8)
+#define PTXFE_ZERO                     (1<<8)
+#define NPTXFE_HALF                    (0<<7)
+#define NPTXFE_ZERO                    (1<<7)
+#define MODE_SLAVE                     (0<<5)
+#define MODE_DMA                       (1<<5)
+#define BURST_SINGLE                   (0<<1)
+#define BURST_INCR                     (1<<1)
+#define BURST_INCR4                    (3<<1)
+#define BURST_INCR8                    (5<<1)
+#define BURST_INCR16                   (7<<1)
+#define GBL_INT_UNMASK                 (1<<0)
+#define GBL_INT_MASK                   (0<<0)
+
+/* S3C_UDC_OTG_GRSTCTL */
+#define AHB_MASTER_IDLE                        (1u<<31)
+#define CORE_SOFT_RESET                        (0x1<<0)
+
+/* S3C_UDC_OTG_GINTSTS/S3C_UDC_OTG_GINTMSK core interrupt register */
+#define INT_RESUME                     (1u<<31)
+#define INT_DISCONN                    (0x1<<29)
+#define INT_CONN_ID_STS_CNG            (0x1<<28)
+#define INT_OUT_EP                     (0x1<<19)
+#define INT_IN_EP                      (0x1<<18)
+#define INT_ENUMDONE                   (0x1<<13)
+#define INT_RESET                      (0x1<<12)
+#define INT_SUSPEND                    (0x1<<11)
+#define INT_EARLY_SUSPEND              (0x1<<10)
+#define INT_NP_TX_FIFO_EMPTY           (0x1<<5)
+#define INT_RX_FIFO_NOT_EMPTY          (0x1<<4)
+#define INT_SOF                                (0x1<<3)
+#define INT_DEV_MODE                   (0x0<<0)
+#define INT_HOST_MODE                  (0x1<<1)
+#define        INT_GOUTNakEff                  (0x01<<7)
+#define        INT_GINNakEff                   (0x01<<6)
+
+#define FULL_SPEED_CONTROL_PKT_SIZE    8
+#define FULL_SPEED_BULK_PKT_SIZE       64
+
+#define HIGH_SPEED_CONTROL_PKT_SIZE    64
+#define HIGH_SPEED_BULK_PKT_SIZE       512
+
+#define RX_FIFO_SIZE                   (1024*4)
+#define NPTX_FIFO_SIZE                 (1024*4)
+#define PTX_FIFO_SIZE                  (1536*1)
+
+#define DEPCTL_TXFNUM_0                        (0x0<<22)
+#define DEPCTL_TXFNUM_1                        (0x1<<22)
+#define DEPCTL_TXFNUM_2                        (0x2<<22)
+#define DEPCTL_TXFNUM_3                        (0x3<<22)
+#define DEPCTL_TXFNUM_4                        (0x4<<22)
+
+/* Enumeration speed */
+#define USB_HIGH_30_60MHZ              (0x0<<1)
+#define USB_FULL_30_60MHZ              (0x1<<1)
+#define USB_LOW_6MHZ                   (0x2<<1)
+#define USB_FULL_48MHZ                 (0x3<<1)
+
+/* S3C_UDC_OTG_GRXSTSP STATUS */
+#define OUT_PKT_RECEIVED               (0x2<<17)
+#define OUT_TRANSFER_COMPLELTED                (0x3<<17)
+#define SETUP_TRANSACTION_COMPLETED    (0x4<<17)
+#define SETUP_PKT_RECEIVED             (0x6<<17)
+#define GLOBAL_OUT_NAK                 (0x1<<17)
+
+/* S3C_UDC_OTG_DCTL device control register */
+#define NORMAL_OPERATION               (0x1<<0)
+#define SOFT_DISCONNECT                        (0x1<<1)
+#define TEST_CONTROL_MASK              (0x7<<4)
+#define TEST_J_MODE                    (0x1<<4)
+#define TEST_K_MODE                    (0x2<<4)
+#define TEST_SE0_NAK_MODE              (0x3<<4)
+#define TEST_PACKET_MODE               (0x4<<4)
+#define TEST_FORCE_ENABLE_MODE         (0x5<<4)
+
+/* S3C_UDC_OTG_DAINT device all endpoint interrupt register */
+#define DAINT_OUT_BIT                  (16)
+#define DAINT_MASK                     (0xFFFF)
+
+/* S3C_UDC_OTG_DIEPCTL0/DOEPCTL0 device control IN/OUT endpoint 0 control register */
+#define DEPCTL_EPENA                   (0x1<<31)
+#define DEPCTL_EPDIS                   (0x1<<30)
+#define DEPCTL_SETD1PID                        (0x1<<29)
+#define DEPCTL_SETD0PID                        (0x1<<28)
+#define DEPCTL_SNAK                    (0x1<<27)
+#define DEPCTL_CNAK                    (0x1<<26)
+#define DEPCTL_STALL                   (0x1<<21)
+#define DEPCTL_TYPE_BIT                        (18)
+#define DEPCTL_TYPE_MASK               (0x3<<18)
+#define DEPCTL_CTRL_TYPE               (0x0<<18)
+#define DEPCTL_ISO_TYPE                        (0x1<<18)
+#define DEPCTL_BULK_TYPE               (0x2<<18)
+#define DEPCTL_INTR_TYPE               (0x3<<18)
+#define DEPCTL_USBACTEP                        (0x1<<15)
+#define DEPCTL_NEXT_EP_BIT             (11)
+#define DEPCTL_MPS_BIT                 (0)
+#define DEPCTL_MPS_MASK                        (0x7FF)
+
+#define DEPCTL0_MPS_64                 (0x0<<0)
+#define DEPCTL0_MPS_32                 (0x1<<0)
+#define DEPCTL0_MPS_16                 (0x2<<0)
+#define DEPCTL0_MPS_8                  (0x3<<0)
+#define DEPCTL_MPS_BULK_512            (512<<0)
+#define DEPCTL_MPS_INT_MPS_16          (16<<0)
+
+#define DIEPCTL0_NEXT_EP_BIT           (11)
+
+/* S3C_UDC_OTG_DIEPCTLn/DOEPCTLn device control IN/OUT endpoint n control register */
+
+/* S3C_UDC_OTG_DIEPMSK/DOEPMSK device IN/OUT endpoint common interrupt mask register */
+/* S3C_UDC_OTG_DIEPINTn/DOEPINTn device IN/OUT endpoint interrupt register */
+#define BACK2BACK_SETUP_RECEIVED       (0x1<<6)
+#define INTKNEPMIS                     (0x1<<5)
+#define INTKN_TXFEMP                   (0x1<<4)
+#define NON_ISO_IN_EP_TIMEOUT          (0x1<<3)
+#define CTRL_OUT_EP_SETUP_PHASE_DONE   (0x1<<3)
+#define AHB_ERROR                      (0x1<<2)
+#define EPDISBLD                       (0x1<<1)
+#define TRANSFER_DONE                  (0x1<<0)
+
+/*DIEPTSIZ0 / DOEPTSIZ0 */
+
+/* DEPTSIZ common bit */
+#define DEPTSIZ_PKT_CNT_BIT            (19)
+#define DEPTSIZ_XFER_SIZE_BIT          (0)
+
+#define        DEPTSIZ_SETUP_PKCNT_1           (1<<29)
+#define        DEPTSIZ_SETUP_PKCNT_2           (2<<29)
+#define        DEPTSIZ_SETUP_PKCNT_3           (3<<29)
+
+#endif
index 0c693a1..453d7da 100644 (file)
 #undef CONFIG_CMD_IMLS
 #undef CONFIG_CMD_FLASH
 #undef CONFIG_CMD_IMLS
-#undef CONFIG_CMD_NET
 #define CONFIG_CMD_CACHE
 #define CONFIG_CMD_REGINFO
 #define CONFIG_CMD_ONENAND
 
 #define CONFIG_SYS_64BIT_VSPRINTF      1
 
-#define CONFIG_BOOTDELAY       1
+#define CONFIG_BOOTDELAY       10
 
 #define CONFIG_ZERO_BOOTDELAY_CHECK
 
+/* Ethernet */
+#define CONFIG_NET_MULTI               1
+#define CONFIG_NET_RETRY_COUNT         2
+#define CONFIG_NET_DO_NOT_TRY_ANOTHER  1
+
+/* Configure Ethernet over USB */
+/*#define CONFIG_USB_ETH_RNDIS         1*/
+#define CONFIG_USB_GADGET              1
+#define CONFIG_USB_GADGET_S3C_UDC_OTG          1
+#define CONFIG_USB_GADGET_DUALSPEED    1
+#define CONFIG_USB_ETHER               1
+#define CONFIG_USBNET_MANUFACTURER      "S5PC1xx U-Boot"
+/* ethaddr settings can be overruled via environment settings */
+#define CONFIG_USBNET_DEV_ADDR         "8e:28:0f:fa:3c:39"
+#define CONFIG_USBNET_HOST_ADDR                "0a:fa:63:8b:e8:0a"
+#define CONFIG_USB_CDC_VENDOR_ID        0x0525
+#define CONFIG_USB_CDC_PRODUCT_ID       0xa4a1
+#define CONFIG_USB_RNDIS_VENDOR_ID      0x0525
+#define CONFIG_USB_RNDIS_PRODUCT_ID     0xa4a2
+
 #define CONFIG_NETMASK         255.255.255.0
 #define CONFIG_IPADDR          192.168.129.3
 #define CONFIG_SERVERIP                192.168.129.1
 #define CONFIG_GATEWAYIP       192.168.129.1
-#define CONFIG_ETHADDR         00:0E:99:34:10:00
+#define CONFIG_ETHADDR         8e:28:0f:fa:3c:39
 
 #define CONFIG_MTD_DEVICE
 #define CONFIG_MTD_PARTITIONS
        "ubifsboot=set bootargs root=ubi0!rootfs rootfstype=ubifs " \
         CONFIG_UBIFS_OPTION CONFIG_UBI_MTD " ${opts} ${lcdinfo} " \
         CONFIG_COMMON_BOOT "; run bootk\0" \
+       "tftpboot=set bootargs root=ubi0!rootfs rootfstype=ubifs " \
+        CONFIG_UBIFS_OPTION CONFIG_UBI_MTD " ${opts} ${lcdinfo} " \
+        CONFIG_COMMON_BOOT "; tftp 0x30007FC0 uImage; bootm 0x30007FC0\0" \
        "boottrace=setenv opts initcall_debug; run bootcmd\0" \
        "android=set bootargs root=ubi0!ramdisk " CONFIG_UBI_MTD \
         " rootfstype=ubifs init=/init.sh " CONFIG_COMMON_BOOT "; run bootk\0" \