usb:add usb host1.1 for 3G modem
authorhxy <hxy@rock-chips.com>
Thu, 26 Aug 2010 06:49:04 +0000 (14:49 +0800)
committerhxy <hxy@rock-chips.com>
Thu, 26 Aug 2010 06:51:22 +0000 (14:51 +0800)
14 files changed:
arch/arm/configs/rk2818_info_defconfig
arch/arm/mach-rk2818/clock.c
drivers/usb/core/hub.c
drivers/usb/dwc_otg/dwc_otg_attr.c
drivers/usb/dwc_otg/dwc_otg_cil.c
drivers/usb/dwc_otg/dwc_otg_cil_intr.c
drivers/usb/dwc_otg/dwc_otg_driver.c
drivers/usb/dwc_otg/dwc_otg_hcd.c
drivers/usb/dwc_otg/dwc_otg_hcd.h
drivers/usb/dwc_otg/dwc_otg_hcd_intr.c
drivers/usb/dwc_otg/dwc_otg_hcd_queue.c
drivers/usb/dwc_otg/dwc_otg_pcd.c
drivers/usb/dwc_otg/dwc_otg_pcd_intr.c
drivers/usb/serial/option.c

index ba48ece1099f60eef142694638130780311a014d..de4429d7447b057525eda4abc40a4ca596259624 100755 (executable)
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
 # Linux kernel version: 2.6.32.9
-# Sat Aug 21 11:03:43 2010
+# Thu Aug 26 13:15:43 2010
 #
 CONFIG_ARM=y
 CONFIG_SYS_SUPPORTS_APM_EMULATION=y
@@ -429,11 +429,15 @@ CONFIG_BT_HIDP=y
 #
 # Bluetooth device drivers
 #
+# CONFIG_BT_HCIBTUSB is not set
 # CONFIG_BT_HCIBTSDIO is not set
 CONFIG_BT_HCIUART=y
 CONFIG_BT_HCIUART_H4=y
 # CONFIG_BT_HCIUART_BCSP is not set
 # CONFIG_BT_HCIUART_LL is not set
+# CONFIG_BT_HCIBCM203X is not set
+# CONFIG_BT_HCIBPA10X is not set
+# CONFIG_BT_HCIBFUSB is not set
 # CONFIG_BT_HCIVHCI is not set
 # CONFIG_BT_MRVL is not set
 # CONFIG_BT_HCIBCM4325 is not set
@@ -548,6 +552,7 @@ CONFIG_MTD_NAND=y
 CONFIG_MTD_NAND_RK2818=y
 # CONFIG_MTD_NAND_NANDSIM is not set
 # CONFIG_MTD_NAND_PLATFORM is not set
+# CONFIG_MTD_ALAUDA is not set
 # CONFIG_MTD_ONENAND is not set
 
 #
@@ -565,6 +570,7 @@ CONFIG_BLK_DEV=y
 CONFIG_BLK_DEV_LOOP=y
 # CONFIG_BLK_DEV_CRYPTOLOOP is not set
 # CONFIG_BLK_DEV_NBD is not set
+# CONFIG_BLK_DEV_UB is not set
 # CONFIG_BLK_DEV_RAM is not set
 # CONFIG_CDROM_PKTCDVD is not set
 # CONFIG_ATA_OVER_ETH is not set
@@ -645,6 +651,15 @@ CONFIG_BCM4329_NVRAM_PATH="/etc/firmware/nvram_bcm4329_B23.txt"
 #
 # Enable WiMAX (Networking options) to see the WiMAX drivers
 #
+
+#
+# USB Network Adapters
+#
+# CONFIG_USB_CATC is not set
+# CONFIG_USB_KAWETH is not set
+# CONFIG_USB_PEGASUS is not set
+# CONFIG_USB_RTL8150 is not set
+# CONFIG_USB_USBNET is not set
 # CONFIG_WAN is not set
 CONFIG_PPP=y
 # CONFIG_PPP_MULTILINK is not set
@@ -709,6 +724,7 @@ CONFIG_TOUCHSCREEN_XPT2046_SPI=y
 # CONFIG_TOUCHSCREEN_XPT2046_CBN_SPI is not set
 # CONFIG_TOUCHSCREEN_XPT2046_320X480_SPI is not set
 # CONFIG_TOUCHSCREEN_XPT2046_320X480_CBN_SPI is not set
+# CONFIG_TOUCHSCREEN_IT7250 is not set
 # CONFIG_TOUCHSCREEN_AD7879_I2C is not set
 # CONFIG_TOUCHSCREEN_AD7879_SPI is not set
 # CONFIG_TOUCHSCREEN_AD7879 is not set
@@ -1043,6 +1059,9 @@ CONFIG_SND_JACK=y
 # CONFIG_SND_DRIVERS is not set
 # CONFIG_SND_ARM is not set
 # CONFIG_SND_SPI is not set
+CONFIG_SND_USB=y
+# CONFIG_SND_USB_AUDIO is not set
+# CONFIG_SND_USB_CAIAQ is not set
 CONFIG_SND_SOC=y
 CONFIG_SND_ROCKCHIP_SOC=y
 CONFIG_SND_ROCKCHIP_SOC_I2S=y
@@ -1060,15 +1079,135 @@ CONFIG_USB_SUPPORT=y
 CONFIG_USB_ARCH_HAS_HCD=y
 # CONFIG_USB_ARCH_HAS_OHCI is not set
 # CONFIG_USB_ARCH_HAS_EHCI is not set
-# CONFIG_USB is not set
+CONFIG_USB=y
+# CONFIG_USB_DEBUG is not set
+# CONFIG_USB_ANNOUNCE_NEW_DEVICES is not set
+
+#
+# Miscellaneous USB options
+#
+# CONFIG_USB_DEVICEFS is not set
+CONFIG_USB_DEVICE_CLASS=y
+# CONFIG_USB_DYNAMIC_MINORS is not set
+# CONFIG_USB_SUSPEND is not set
+# CONFIG_USB_OTG is not set
 # CONFIG_USB_OTG_WHITELIST is not set
 # CONFIG_USB_OTG_BLACKLIST_HUB is not set
+# CONFIG_USB_MON is not set
+# CONFIG_USB_WUSB is not set
+# CONFIG_USB_WUSB_CBAF is not set
+
+#
+# USB Host Controller Drivers
+#
+# CONFIG_USB_C67X00_HCD is not set
+# CONFIG_USB_OXU210HP_HCD is not set
+# CONFIG_USB_ISP116X_HCD is not set
+# CONFIG_USB_ISP1760_HCD is not set
+# CONFIG_USB_ISP1362_HCD is not set
+# CONFIG_USB_SL811_HCD is not set
+# CONFIG_USB_R8A66597_HCD is not set
+# CONFIG_USB_HWA_HCD is not set
 # CONFIG_USB_MUSB_HDRC is not set
 # CONFIG_USB_GADGET_MUSB_HDRC is not set
 
+#
+# USB Device Class drivers
+#
+CONFIG_USB_ACM=y
+# CONFIG_USB_PRINTER is not set
+# CONFIG_USB_WDM is not set
+# CONFIG_USB_TMC is not set
+
 #
 # NOTE: USB_STORAGE depends on SCSI but BLK_DEV_SD may
 #
+
+#
+# also be needed; see USB_STORAGE Help for more info
+#
+# CONFIG_USB_LIBUSUAL is not set
+
+#
+# USB Imaging devices
+#
+# CONFIG_USB_MDC800 is not set
+
+#
+# USB port drivers
+#
+CONFIG_USB_SERIAL=y
+# CONFIG_USB_SERIAL_CONSOLE is not set
+# CONFIG_USB_EZUSB is not set
+CONFIG_USB_SERIAL_GENERIC=y
+# CONFIG_USB_SERIAL_AIRCABLE is not set
+# CONFIG_USB_SERIAL_ARK3116 is not set
+# CONFIG_USB_SERIAL_BELKIN is not set
+# CONFIG_USB_SERIAL_CH341 is not set
+# CONFIG_USB_SERIAL_WHITEHEAT is not set
+# CONFIG_USB_SERIAL_DIGI_ACCELEPORT is not set
+# CONFIG_USB_SERIAL_CP210X is not set
+# CONFIG_USB_SERIAL_CYPRESS_M8 is not set
+# CONFIG_USB_SERIAL_EMPEG is not set
+# CONFIG_USB_SERIAL_FTDI_SIO is not set
+# CONFIG_USB_SERIAL_FUNSOFT is not set
+# CONFIG_USB_SERIAL_VISOR is not set
+# CONFIG_USB_SERIAL_IPAQ is not set
+# CONFIG_USB_SERIAL_IR is not set
+# CONFIG_USB_SERIAL_EDGEPORT is not set
+# CONFIG_USB_SERIAL_EDGEPORT_TI is not set
+# CONFIG_USB_SERIAL_GARMIN is not set
+# CONFIG_USB_SERIAL_IPW is not set
+# CONFIG_USB_SERIAL_IUU is not set
+# CONFIG_USB_SERIAL_KEYSPAN_PDA is not set
+# CONFIG_USB_SERIAL_KEYSPAN is not set
+# CONFIG_USB_SERIAL_KLSI is not set
+# CONFIG_USB_SERIAL_KOBIL_SCT is not set
+# CONFIG_USB_SERIAL_MCT_U232 is not set
+# CONFIG_USB_SERIAL_MOS7720 is not set
+# CONFIG_USB_SERIAL_MOS7840 is not set
+# CONFIG_USB_SERIAL_MOTOROLA is not set
+# CONFIG_USB_SERIAL_NAVMAN is not set
+# CONFIG_USB_SERIAL_PL2303 is not set
+# CONFIG_USB_SERIAL_OTI6858 is not set
+# CONFIG_USB_SERIAL_QUALCOMM is not set
+# CONFIG_USB_SERIAL_SPCP8X5 is not set
+# CONFIG_USB_SERIAL_HP4X is not set
+# CONFIG_USB_SERIAL_SAFE is not set
+# CONFIG_USB_SERIAL_SIEMENS_MPI is not set
+# CONFIG_USB_SERIAL_SIERRAWIRELESS is not set
+# CONFIG_USB_SERIAL_SYMBOL is not set
+# CONFIG_USB_SERIAL_TI is not set
+# CONFIG_USB_SERIAL_CYBERJACK is not set
+# CONFIG_USB_SERIAL_XIRCOM is not set
+CONFIG_USB_SERIAL_OPTION=y
+# CONFIG_USB_SERIAL_OMNINET is not set
+# CONFIG_USB_SERIAL_OPTICON is not set
+# CONFIG_USB_SERIAL_DEBUG is not set
+
+#
+# USB Miscellaneous drivers
+#
+# CONFIG_USB_EMI62 is not set
+# CONFIG_USB_EMI26 is not set
+# CONFIG_USB_ADUTUX is not set
+# CONFIG_USB_SEVSEG is not set
+# CONFIG_USB_RIO500 is not set
+# CONFIG_USB_LEGOTOWER is not set
+# CONFIG_USB_LCD is not set
+# CONFIG_USB_BERRY_CHARGE is not set
+# CONFIG_USB_LED is not set
+# CONFIG_USB_CYPRESS_CY7C63 is not set
+# CONFIG_USB_CYTHERM is not set
+# CONFIG_USB_IDMOUSE is not set
+# CONFIG_USB_FTDI_ELAN is not set
+# CONFIG_USB_APPLEDISPLAY is not set
+# CONFIG_USB_LD is not set
+# CONFIG_USB_TRANCEVIBRATOR is not set
+# CONFIG_USB_IOWARRIOR is not set
+# CONFIG_USB_TEST is not set
+# CONFIG_USB_ISIGHTFW is not set
+# CONFIG_USB_VST is not set
 CONFIG_USB_GADGET=y
 # CONFIG_USB_GADGET_DEBUG is not set
 # CONFIG_USB_GADGET_DEBUG_FILES is not set
@@ -1117,12 +1256,12 @@ CONFIG_USB_ANDROID_RNDIS_WCEIS=y
 #
 # CONFIG_USB_GPIO_VBUS is not set
 # CONFIG_NOP_USB_XCEIV is not set
-# CONFIG_RK2818_HOST11 is not set
+CONFIG_RK2818_HOST11=y
 CONFIG_DWC_OTG=y
 # CONFIG_DWC_OTG_DEBUG is not set
 # CONFIG_DWC_OTG_HOST_ONLY is not set
-CONFIG_DWC_OTG_DEVICE_ONLY=y
-# CONFIG_DWC_OTG_BOTH_HOST_SLAVE is not set
+# CONFIG_DWC_OTG_DEVICE_ONLY is not set
+CONFIG_DWC_OTG_BOTH_HOST_SLAVE=y
 # CONFIG_DWC_OTG_NORMAL_PREFERENCE is not set
 # CONFIG_DWC_OTG_HOST_PREFERENCE is not set
 CONFIG_DWC_OTG_DEVICE_PREFERENCE=y
@@ -1235,7 +1374,13 @@ CONFIG_RTC_HYM8563=y
 #
 CONFIG_STAGING=y
 # CONFIG_STAGING_EXCLUDE_BUILD is not set
+# CONFIG_USB_IP_COMMON is not set
+# CONFIG_PRISM2_USB is not set
 # CONFIG_ECHO is not set
+# CONFIG_COMEDI is not set
+# CONFIG_ASUS_OLED is not set
+# CONFIG_INPUT_MIMIO is not set
+# CONFIG_TRANZPORT is not set
 
 #
 # Android
@@ -1265,6 +1410,11 @@ CONFIG_ANDROID_LOW_MEMORY_KILLER=y
 # CONFIG_DST is not set
 # CONFIG_POHMELFS is not set
 # CONFIG_PLAN9AUTH is not set
+# CONFIG_LINE6_USB is not set
+# CONFIG_USB_SERIAL_QUATECH2 is not set
+# CONFIG_USB_SERIAL_QUATECH_USB2 is not set
+# CONFIG_VT6656 is not set
+# CONFIG_FB_UDL is not set
 
 #
 # RAR Register Driver
@@ -1291,6 +1441,7 @@ CONFIG_RK2818_POWER=y
 # CMMB
 #
 # CONFIG_CMMB is not set
+
 #
 # File systems
 #
index 2696864f8b86f878ceaa7f90a589c7f6ddd398b3..62b30881d54d75722403e6949c3c5cde1dbdfc03 100644 (file)
@@ -1301,8 +1301,11 @@ static struct rk2818_freq_info rk2818_freqs[] = {
 //X    OP(768, 350, 768, 24, 1, 16,  41,  41),
 //     OP(720, 350, 720, 24, 1, 15,  41,  21),
 //     OP(672, 350, 672, 24, 1, 14,  41,  21),
-//     OP(624, 350, 624, 24, 1, 13,  41,  21),
+#if defined(CONFIG_MACH_INFO)
+       OP(624, 350, 624, 24, 1, 13,  31,  21),
+#else
        OP(600, 350, 600, 24, 1, 12,  41,  21),
+#endif
 //     OP(576, 350, 576, 24, 1, 12,  41,  21),
 //     OP(528, 350, 528, 24, 1, 11,  41,  21),
 //     OP(480, 350, 480, 24, 1, 10,  41,  21),
index 1f747c68b545b378842bf7c2e3e9cff0e9703d2a..c6341922eac1a312b4faf0a6b7be0c8bb8a8e7e4 100644 (file)
@@ -1170,7 +1170,8 @@ static void hub_disconnect(struct usb_interface *intf)
 
        kref_put(&hub->kref, hub_release);
 }
-
+struct usb_hub *g_root_hub20 = NULL;
+struct usb_hub *g_root_hub11 = NULL;
 static int hub_probe(struct usb_interface *intf, const struct usb_device_id *id)
 {
        struct usb_host_interface *desc;
@@ -1221,7 +1222,13 @@ descriptor_error:
                dev_dbg (&intf->dev, "couldn't kmalloc hub struct\n");
                return -ENOMEM;
        }
-
+       if(hdev->parent == NULL)
+       {
+               if(!g_root_hub20)
+                       g_root_hub20 = hub;
+               else if(!g_root_hub11)
+                       g_root_hub11 = hub;
+       }
        kref_init(&hub->kref);
        INIT_LIST_HEAD(&hub->event_list);
        hub->intfdev = &intf->dev;
@@ -3381,15 +3388,13 @@ loop:
 
         } /* end while (1) */
 }
-// cmy@091222: µ±¿ªHost¶Ë¿ÚËùÁ¬½ÓµÄÉ豸£¬¹©host/slaveÇл»ÓÃ
-void hub_disconnect_device()
+
+/* yk@rk 20100730 
+ * disconnect all devices on root hub
+ */
+void hub_disconnect_device(struct usb_hub *hub)
 {
-    if(g_usb_device)
-    {
-        struct usb_hub *hub = hdev_to_hub(g_usb_device->parent);
-        // cmy: ¶Ï¿ªÉ豸Á¬½Ó
        hub_port_connect_change(hub, 1, 0, 0x2);
-    }
 }
 
 static int hub_thread(void *__unused)
index 17fa55c7ba7f607d526f05114401ee26294b442f..ef77142600e4a759ac045f5739aad200aab095aa 100755 (executable)
  * MACROs for defining sysfs attribute
  */
 #define DWC_OTG_DEVICE_ATTR_BITFIELD_SHOW(_otg_attr_name_,_addr_,_mask_,_shift_,_string_) \
-static ssize_t _otg_attr_name_##_show (struct device *_dev, char *buf) \
+static ssize_t _otg_attr_name_##_show (struct device *_dev, struct device_attribute *attr, char *buf) \
 { \
         dwc_otg_device_t *otg_dev = _dev->platform_data;\
        uint32_t val; \
@@ -277,7 +277,7 @@ static ssize_t _otg_attr_name_##_show (struct device *_dev, char *buf) \
        return sprintf (buf, "%s = 0x%x\n", _string_, val); \
 }
 #define DWC_OTG_DEVICE_ATTR_BITFIELD_STORE(_otg_attr_name_,_addr_,_mask_,_shift_,_string_) \
-static ssize_t _otg_attr_name_##_store (struct device *_dev, const char *buf, size_t count) \
+static ssize_t _otg_attr_name_##_store (struct device *_dev, struct device_attribute *attr, const char *buf, size_t count) \
 { \
         dwc_otg_device_t *otg_dev = _dev->platform_data;\
        uint32_t set = simple_strtoul(buf, NULL, 16); \
@@ -302,7 +302,7 @@ DEVICE_ATTR(_otg_attr_name_,0444,_otg_attr_name_##_show,NULL);
  * MACROs for defining sysfs attribute for 32-bit registers
  */
 #define DWC_OTG_DEVICE_ATTR_REG_SHOW(_otg_attr_name_,_addr_,_string_) \
-static ssize_t _otg_attr_name_##_show (struct device *_dev, char *buf) \
+static ssize_t _otg_attr_name_##_show (struct device *_dev, struct device_attribute *attr, char *buf) \
 { \
         dwc_otg_device_t *otg_dev = _dev->platform_data;\
        uint32_t val; \
@@ -310,7 +310,7 @@ static ssize_t _otg_attr_name_##_show (struct device *_dev, char *buf) \
        return sprintf (buf, "%s = 0x%08x\n", _string_, val); \
 }
 #define DWC_OTG_DEVICE_ATTR_REG_STORE(_otg_attr_name_,_addr_,_string_) \
-static ssize_t _otg_attr_name_##_store (struct device *_dev, const char *buf, size_t count) \
+static ssize_t _otg_attr_name_##_store (struct device *_dev, struct device_attribute *attr, const char *buf, size_t count) \
 { \
         dwc_otg_device_t *otg_dev = _dev->platform_data;\
        uint32_t val = simple_strtoul(buf, NULL, 16); \
@@ -335,17 +335,19 @@ DEVICE_ATTR(_otg_attr_name_,0444,_otg_attr_name_##_show,NULL);
 /**
  * Show the register offset of the Register Access.
  */
-static ssize_t regoffset_show( struct device *_dev, char *buf) 
+static ssize_t regoffset_show( struct device *_dev,
+                                                       struct device_attribute *attr, char *buf) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
+        
        return snprintf(buf, sizeof("0xFFFFFFFF\n")+1,"0x%08x\n", otg_dev->reg_offset);
 }
 
 /**
  * Set the register offset for the next Register Access        Read/Write
  */
-static ssize_t regoffset_store( struct device *_dev, const char *buf, 
-                                size_t count ) 
+static ssize_t regoffset_store( struct device *_dev, struct device_attribute *attr,
+                                                       const char *buf, size_t count ) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
        uint32_t offset = simple_strtoul(buf, NULL, 16);
@@ -366,7 +368,8 @@ DEVICE_ATTR(regoffset, S_IRUGO|S_IWUSR, regoffset_show, regoffset_store);
  * Show the value of the register at the offset in the reg_offset
  * attribute.
  */
-static ssize_t regvalue_show( struct device *_dev, char *buf) 
+static ssize_t regvalue_show( struct device *_dev,
+                                                               struct device_attribute *attr, char *buf) 
 {
        dwc_otg_device_t *otg_dev = _dev->platform_data;
        uint32_t val;
@@ -395,8 +398,9 @@ static ssize_t regvalue_show( struct device *_dev, char *buf)
  * attribute.
  * 
  */
-static ssize_t regvalue_store( struct device *_dev, const char *buf, 
-                               size_t count ) 
+static ssize_t regvalue_store( struct device *_dev,
+                                                               struct device_attribute *attr, 
+                                                               const char *buf,  size_t count ) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
        volatile uint32_t * addr;
@@ -449,7 +453,8 @@ DWC_OTG_DEVICE_ATTR_REG32_RW(hprt0,otg_dev->core_if->host_if->hprt0,"HPRT0");
 /**
  * Show the HNP status bit
  */
-static ssize_t hnp_show( struct device *_dev, char *buf) 
+static ssize_t hnp_show( struct device *_dev,
+                                                               struct device_attribute *attr,  char *buf) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
        gotgctl_data_t val;
@@ -460,8 +465,9 @@ static ssize_t hnp_show( struct device *_dev, char *buf)
 /**
  * Set the HNP Request bit
  */
-static ssize_t hnp_store( struct device *_dev, const char *buf, 
-                         size_t count ) 
+static ssize_t hnp_store( struct device *_dev,
+                                                               struct device_attribute *attr, 
+                                                               const char *buf, size_t count ) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
        uint32_t in = simple_strtoul(buf, NULL, 16);
@@ -481,7 +487,8 @@ DEVICE_ATTR(hnp, 0644, hnp_show, hnp_store);
 /**
  * Show the SRP status bit
  */
-static ssize_t srp_show( struct device *_dev, char *buf) 
+static ssize_t srp_show( struct device *_dev,
+                                                               struct device_attribute *attr,  char *buf) 
 {
 #ifndef DWC_HOST_ONLY
         dwc_otg_device_t *otg_dev = _dev->platform_data;
@@ -498,8 +505,9 @@ static ssize_t srp_show( struct device *_dev, char *buf)
 /**
  * Set the SRP Request bit
  */
-static ssize_t srp_store( struct device *_dev, const char *buf, 
-                         size_t count ) 
+static ssize_t srp_store( struct device *_dev,
+                                                               struct device_attribute *attr, 
+                                                               const char *buf, size_t count ) 
 {
 #ifndef DWC_HOST_ONLY
         dwc_otg_device_t *otg_dev = _dev->platform_data;
@@ -515,7 +523,8 @@ DEVICE_ATTR(srp, 0644, srp_show, srp_store);
 /**
  * Show the Bus Power status
  */
-static ssize_t buspower_show( struct device *_dev, char *buf) 
+static ssize_t buspower_show( struct device *_dev,
+                                                               struct device_attribute *attr,  char *buf) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
        hprt0_data_t val;
@@ -527,8 +536,9 @@ static ssize_t buspower_show( struct device *_dev, char *buf)
 /**
  * Set the Bus Power status
  */
-static ssize_t buspower_store( struct device *_dev, const char *buf, 
-                               size_t count ) 
+static ssize_t buspower_store( struct device *_dev,
+                                                               struct device_attribute *attr, 
+                                                               const char *buf, size_t count ) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
        uint32_t on = simple_strtoul(buf, NULL, 16);
@@ -551,7 +561,8 @@ DEVICE_ATTR(buspower, 0644, buspower_show, buspower_store);
 /**
  * Show the Bus Suspend status
  */
-static ssize_t bussuspend_show( struct device *_dev, char *buf) 
+static ssize_t bussuspend_show( struct device *_dev,
+                                                               struct device_attribute *attr,  char *buf) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
        hprt0_data_t val;
@@ -562,8 +573,9 @@ static ssize_t bussuspend_show( struct device *_dev, char *buf)
 /**
  * Set the Bus Suspend status
  */
-static ssize_t bussuspend_store( struct device *_dev, const char *buf, 
-                                 size_t count ) 
+static ssize_t bussuspend_store( struct device *_dev,
+                                                               struct device_attribute *attr, 
+                                                               const char *buf, size_t count ) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
        uint32_t in = simple_strtoul(buf, NULL, 16);
@@ -580,7 +592,8 @@ DEVICE_ATTR(bussuspend, 0644, bussuspend_show, bussuspend_store);
 /**
  * Show the status of Remote Wakeup.
  */
-static ssize_t remote_wakeup_show( struct device *_dev, char *buf) 
+static ssize_t remote_wakeup_show( struct device *_dev, 
+                                                                               struct device_attribute *attr,char *buf) 
 {
 #ifndef DWC_HOST_ONLY
         dwc_otg_device_t *otg_dev = _dev->platform_data;
@@ -599,8 +612,9 @@ static ssize_t remote_wakeup_show( struct device *_dev, char *buf)
  * flag is set.
  * 
  */
-static ssize_t remote_wakeup_store( struct device *_dev, const char *buf, 
-                                    size_t count ) 
+static ssize_t remote_wakeup_store( struct device *_dev, 
+                                               struct device_attribute *attr,
+                                               const char *buf,  size_t count ) 
 {
 #ifndef DWC_HOST_ONLY
         uint32_t val = simple_strtoul(buf, NULL, 16);        
@@ -614,14 +628,15 @@ static ssize_t remote_wakeup_store( struct device *_dev, const char *buf,
 #endif
        return count;
 }
-DEVICE_ATTR(remote_wakeup,  S_IRUGO|S_IWUSR, remote_wakeup_show, 
+static DEVICE_ATTR(remote_wakeup,  S_IRUGO|S_IWUSR, remote_wakeup_show, 
             remote_wakeup_store);
 
 /**
  * Dump global registers and either host or device registers (depending on the
  * current mode of the core).
  */
-static ssize_t regdump_show( struct device *_dev, char *buf) 
+static ssize_t regdump_show( struct device *_dev, 
+                                                               struct device_attribute *attr, char *buf) 
 {
         dwc_otg_device_t *otg_dev = _dev->platform_data;
         dwc_otg_dump_global_registers( otg_dev->core_if);
@@ -638,7 +653,8 @@ DEVICE_ATTR(regdump, S_IRUGO|S_IWUSR, regdump_show, 0);
 /**
  * Dump the current hcd state.
  */
-static ssize_t hcddump_show( struct device *_dev, char *buf) 
+static ssize_t hcddump_show( struct device *_dev, 
+                                                               struct device_attribute *attr, char *buf) 
 {
 #ifndef DWC_DEVICE_ONLY
         dwc_otg_device_t *otg_dev = _dev->platform_data;
@@ -654,7 +670,8 @@ DEVICE_ATTR(hcddump, S_IRUGO|S_IWUSR, hcddump_show, 0);
  * determine average interrupt latency. Frame remaining is also shown for
  * start transfer and two additional sample points.
  */
-static ssize_t hcd_frrem_show( struct device *_dev, char *buf) 
+static ssize_t hcd_frrem_show( struct device *_dev,
+                                                               struct device_attribute *attr,  char *buf) 
 {
 #ifndef DWC_DEVICE_ONLY
         dwc_otg_device_t *otg_dev = _dev->platform_data;
@@ -671,7 +688,8 @@ DEVICE_ATTR(hcd_frrem, S_IRUGO|S_IWUSR, hcd_frrem_show, 0);
  */
 #define RW_REG_COUNT 10000000
 #define MSEC_PER_JIFFIE 1000/HZ        
-static ssize_t rd_reg_test_show( struct device *_dev, char *buf) 
+static ssize_t rd_reg_test_show( struct device *_dev, 
+                                                               struct device_attribute *attr, char *buf) 
 {
        int i;
        int time;
@@ -695,7 +713,8 @@ DEVICE_ATTR(rd_reg_test, S_IRUGO|S_IWUSR, rd_reg_test_show, 0);
  * Displays the time required to write the GNPTXFSIZ register many times (the
  * output shows the number of times the register is written).
  */
-static ssize_t wr_reg_test_show( struct device *_dev, char *buf) 
+static ssize_t wr_reg_test_show( struct device *_dev, 
+                                                               struct device_attribute *attr, char *buf) 
 {
        int i;
        int time;
index 9baa41691706089a30d716438630a81ea40dfa3e..273357b71091555f25af2d7a0c80a4426e5497c5 100755 (executable)
@@ -67,7 +67,7 @@
 #include "dwc_otg_driver.h"
 #include "dwc_otg_cil.h"
 #define SCU_BASE_ADDR_VA RK2818_SCU_BASE
-static dwc_otg_core_if_t * dwc_core_if;
+static dwc_otg_core_if_t * dwc_core_if = NULL;
 /** 
  * This function is called to initialize the DWC_otg CSR data
  * structures. The register addresses in the device and host
@@ -212,6 +212,7 @@ dwc_otg_core_if_t *dwc_otg_cil_init(const uint32_t *_reg_base_addr,
        core_if->srp_timer_started = 0;
 
        core_if->usb_wakeup = 0;
+       if(dwc_core_if  ==  NULL)
              dwc_core_if = core_if;
        return core_if;
 }
@@ -383,7 +384,7 @@ static uint32_t calc_num_in_eps(dwc_otg_core_if_t *_core_if)
        
        for(i = 0; i < num_eps; ++i)
        {
-               if(!(hwcfg1 & 0x1))
+               if((hwcfg1 & 0x3) == 0x01)
                        num_in_eps++;
                
                hwcfg1 >>= 2;
@@ -413,7 +414,7 @@ static uint32_t calc_num_out_eps(dwc_otg_core_if_t *_core_if)
        
        for(i = 0; i < num_eps; ++i)
        {
-               if(!(hwcfg1 & 0x2))
+               if((hwcfg1 & 0x3) == 0x02)
                        num_out_eps++;
                
                hwcfg1 >>= 2;
@@ -1051,6 +1052,16 @@ void dwc_otg_hc_init(dwc_otg_core_if_t *_core_if, dwc_hc_t *_hc)
                                }
                        }
                }
+#if 1
+               //yk@rk 20100714
+               if((_core_if->core_params->host_channels <= 2)&&
+                       _hc->ep_is_in && 
+                       _hc->ep_type == DWC_OTG_EP_TYPE_BULK)
+               {
+                       //DWC_PRINT("%s bulk in\n",__func__);
+                       hc_intr_mask.b.nak = 1;
+               }
+#endif
        } 
        else 
        {
@@ -1223,8 +1234,6 @@ void dwc_otg_hc_halt(dwc_otg_core_if_t *_core_if,
                         dwc_hc_t *_hc,
                         dwc_otg_halt_status_e _halt_status)
 {
-       gnptxsts_data_t                 nptxsts;
-       hptxsts_data_t                  hptxsts;
        hcchar_data_t                   hcchar;
        dwc_otg_hc_regs_t               *hc_regs;
        dwc_otg_core_global_regs_t      *global_regs;
@@ -1289,56 +1298,38 @@ void dwc_otg_hc_halt(dwc_otg_core_if_t *_core_if,
                 * happen when a transfer is aborted by a higher level in
                 * the stack.
                 */
-#ifdef DEBUG
+               
                DWC_PRINT("*** %s: Channel %d, _hc->halt_pending already set ***\n",
                          __func__, _hc->hc_num);
+#ifdef DEBUG
 
 /*             dwc_otg_dump_global_registers(_core_if); */
 /*             dwc_otg_dump_host_registers(_core_if); */
 #endif         
                return;
        }
+    
 
        hcchar.d32 = dwc_read_reg32(&hc_regs->hcchar);
-       hcchar.b.chen = 1;
-       hcchar.b.chdis = 1;
-
-       if (!_core_if->dma_enable) 
-       {
-               /* Check for space in the request queue to issue the halt. */
-               if (_hc->ep_type == DWC_OTG_EP_TYPE_CONTROL ||
-                       _hc->ep_type == DWC_OTG_EP_TYPE_BULK) 
-               {
-                       nptxsts.d32 = dwc_read_reg32(&global_regs->gnptxsts);
-                       if (nptxsts.b.nptxqspcavail == 0) 
-                       {
-                               hcchar.b.chen = 0;
-                       }
-               } 
-               else 
-               {
-                       hptxsts.d32 = dwc_read_reg32(&host_global_regs->hptxsts);
-                       if ((hptxsts.b.ptxqspcavail == 0) || (_core_if->queuing_high_bandwidth)) 
-                       {
-                               hcchar.b.chen = 0;
-                       }
-               }
-       }
-
-       dwc_write_reg32(&hc_regs->hcchar, hcchar.d32);
-
-       _hc->halt_status = _halt_status;
-
-       if (hcchar.b.chen) 
+       //hcchar.b.chen = 1;
+       //hcchar.b.chdis = 1;
+       if(hcchar.b.chen)
        {
+               hcchar.b.chen = 0;
+               hcchar.b.chdis = 1;
+               //hcchar.b.epdir = 0;
+               dwc_write_reg32(&hc_regs->hcchar, hcchar.d32);
+               
                _hc->halt_pending = 1;
                _hc->halt_on_queue = 0;
-       } 
-       else 
+               _hc->halt_status = _halt_status;
+       }
+       else
        {
+               DWC_PRINT("%s channel already halt!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n", __func__);
                _hc->halt_on_queue = 1;
        }
-
+       
        DWC_DEBUGPL(DBG_HCDV, "%s: Channel %d\n", __func__, _hc->hc_num);
        DWC_DEBUGPL(DBG_HCDV, "  hcchar: 0x%08x\n", hcchar.d32);
        DWC_DEBUGPL(DBG_HCDV, "  halt_pending: %d\n", _hc->halt_pending);
@@ -2898,7 +2889,8 @@ void dwc_otg_core_reset(dwc_otg_core_if_t *_core_if)
 {
        dwc_otg_core_global_regs_t *global_regs = _core_if->core_global_regs;
        volatile grstctl_t greset = { .d32 = 0};
-       gusbcfg_data_t usbcfg = { .d32 = 0 };
+       volatile gusbcfg_data_t usbcfg = { .d32 = 0 };
+       volatile gintsts_data_t gintsts =  { .d32 = 0 };
        int count = 0;
        DWC_DEBUGPL(DBG_CILV, "%s\n", __func__);
        /* Wait for AHB master IDLE state. */
@@ -2950,7 +2942,21 @@ void dwc_otg_core_reset(dwc_otg_core_if_t *_core_if)
     dwc_write_reg32( &global_regs->gusbcfg, usbcfg.d32 );
        /* Wait for 3 PHY Clocks*/
        //DWC_PRINT("100ms\n");
-       MDELAY(100);
+       mdelay(10);
+       count = 0;
+       if(usbcfg.b.force_hst_mode)
+       do 
+       {
+               gintsts.d32 = dwc_read_reg32( &global_regs->gintsts);
+               if (++count > 100)
+               {
+                       DWC_WARN("%s() ERROR! Force host mode GINTSTS=%0x\n", __func__, 
+                               gintsts.d32);
+                       break;
+               }
+               mdelay(5);
+       } 
+       while (gintsts.b.curmode != DWC_HOST_MODE);
 }
 
 
@@ -2987,22 +2993,20 @@ extern void dwc_otg_cil_register_pcd_callbacks( dwc_otg_core_if_t *_core_if,
        _cb->p = _p;
 }
 
-void rk28_usb_force_disconnect( void )
+void rk28_usb_force_disconnect( dwc_otg_core_if_t *core_if )
 {
         gotgctl_data_t    gctrl;
         dctl_data_t dctl = {.d32=0};
-        if( dwc_core_if == NULL )
-                return ;
 
-        gctrl.d32 = dwc_read_reg32( &dwc_core_if->core_global_regs->gotgctl );
+        gctrl.d32 = dwc_read_reg32( &core_if->core_global_regs->gotgctl );
         if( !gctrl.b.bsesvld )
                 return ;
 
         printk("%s\n" , __func__);
         /* soft disconnect */
-        dctl.d32 = dwc_read_reg32( &dwc_core_if->dev_if->dev_global_regs->dctl );
+        dctl.d32 = dwc_read_reg32( &core_if->dev_if->dev_global_regs->dctl );
         dctl.b.sftdiscon = 1;
-        dwc_write_reg32( &dwc_core_if->dev_if->dev_global_regs->dctl, dctl.d32 );
+        dwc_write_reg32( &core_if->dev_if->dev_global_regs->dctl, dctl.d32 );
 }
 
 /**
index 481c1b04de7efd2acd37ec46479ee2c7316731ea..783a48a1e323da6668ef9fe3858169fbd6968385 100755 (executable)
@@ -407,9 +407,9 @@ int32_t dwc_otg_handle_conn_id_status_change_intr(dwc_otg_core_if_t *_core_if)
                         MDELAY(100);
                         if (++count > 10000) *(uint32_t*)NULL=0;
                 }
-        _core_if->op_state = B_PERIPHERAL;
 
         hcd_stop(_core_if);
+        _core_if->op_state = B_PERIPHERAL;
         pcd->phy_suspend = 1;
         pcd->vbus_status = 0;
        dwc_otg_pcd_start_vbus_timer( pcd );
index 1893f6b36102d41a0d817ae36b7e1e1c3beacb12..8ab58fa8f00cc3281dd06b76beccf26a40065b73 100755 (executable)
@@ -75,7 +75,7 @@
 
 static const char dwc_driver_name[] = "dwc_otg";
 
-struct dwc_otg_device_t* g_otgdev = NULL;
+dwc_otg_device_t* g_otgdev = NULL;
 
 /*-------------------------------------------------------------------------*/
 /* Encapsulate the module parameter settings */
@@ -151,7 +151,7 @@ static dwc_otg_core_params_t dwc_otg_module_params = {
 
 #ifdef CONFIG_RK2818_HOST11
 
-struct dwc_otg_device_t* g_host11 = NULL;
+dwc_otg_device_t* g_host11 = NULL;
 
 static dwc_otg_core_params_t rk28_host11_module_params = {
        .opt = -1,
@@ -255,12 +255,14 @@ static ssize_t dbg_level_store(struct device_driver *_drv, const char *_buf,
 }
 static DRIVER_ATTR(debuglevel, S_IRUGO|S_IWUSR, dbg_level_show, dbg_level_store);
 
+extern struct usb_hub *g_root_hub20;
+extern struct usb_hub *g_root_hub11;
 #ifdef DWC_BOTH_HOST_SLAVE
 extern void hcd_start( dwc_otg_core_if_t *_core_if );
 
 extern int rk28_usb_suspend( int exitsuspend );
-extern void hub_disconnect_device();
-extern void rk28_usb_force_disconnect( void );
+extern void hub_disconnect_device(struct usb_hub *hub);
+extern void rk28_usb_force_disconnect( dwc_otg_core_if_t *core_if );
 
 static ssize_t force_usb_mode_show(struct device_driver *_drv, char *_buf)
 {
@@ -298,13 +300,13 @@ void dwc_otg_force_host(dwc_otg_core_if_t *core_if)
        {
                rk28_usb_suspend( 1 );
        }
+    del_timer(&otg_dev->pcd->check_vbus_timer);
+    rk28_usb_force_disconnect(core_if);
     if (core_if->pcd_cb && core_if->pcd_cb->stop ) {
             core_if->pcd_cb->stop( core_if->pcd_cb->p );
     }
-    del_timer(&otg_dev->pcd->check_vbus_timer);
-    rk28_usb_force_disconnect();
     
-    core_if->op_state = A_HOST;
+    //core_if->op_state = A_HOST;
     /*
      * Initialize the Core for Host mode.
      */
@@ -316,16 +318,16 @@ void dwc_otg_force_host(dwc_otg_core_if_t *core_if)
 void dwc_otg_force_device(dwc_otg_core_if_t *core_if)
 {
     dwc_otg_device_t *otg_dev = g_otgdev;
+    dwc_otg_disable_global_interrupts( core_if );
+       hub_disconnect_device(g_root_hub20);
+    if (core_if->hcd_cb && core_if->hcd_cb->stop) {
+       core_if->hcd_cb->stop( core_if->hcd_cb->p );
+    }
     if(core_if->op_state == B_PERIPHERAL)
     {
        printk("dwc_otg_force_device,already in B_PERIPHERAL,everest\n");
        return;
     }
-    dwc_otg_disable_global_interrupts( core_if );
-       hub_disconnect_device();
-    if (core_if->hcd_cb && core_if->hcd_cb->stop) {
-       core_if->hcd_cb->stop( core_if->hcd_cb->p );
-    }
     otg_dev->core_if->op_state = B_PERIPHERAL;
        /* Reset the Controller */
        dwc_otg_core_reset( core_if );
@@ -360,11 +362,10 @@ static void dwc_otg_set_gusbcfg(dwc_otg_core_if_t *core_if, int mode)
 static ssize_t force_usb_mode_store(struct device_driver *_drv, const char *_buf, 
                          size_t _count ) 
 {
-    int new_mode = simple_strtoul(_buf, NULL, 10);
+    int new_mode = simple_strtoul(_buf, NULL, 16);
     dwc_otg_device_t *otg_dev = g_otgdev;
     dwc_otg_core_if_t *core_if = otg_dev->core_if;
-    dwc_otg_core_global_regs_t *global_regs = core_if->core_global_regs;
-    
+    DWC_PRINT("%s %d->%d\n",__func__, core_if->usb_mode, new_mode);
     if(core_if->usb_mode == new_mode)
     {
        return _count;
@@ -458,7 +459,7 @@ static ssize_t force_usb_mode_store(struct device_driver *_drv, const char *_buf
                default:
                        break;
        }       
-       return 0;       
+       return _count;  
 }
 int otg_debug( int action )
 {
@@ -772,10 +773,11 @@ static int check_parameters(dwc_otg_core_if_t *core_if)
                                        (core_params->max_packet_count < (1 << (core_if->hwcfg3.b.packet_size_cntr_width + 4))),
                                        ((1 << (core_if->hwcfg3.b.packet_size_cntr_width + 4)) - 1));
 
+// yk@rk use 1 channel in host 1.1
        retval += DWC_OTG_PARAM_CHECK_VALID(host_channels,
                                        "host_channels",
                                        (core_params->host_channels <= (core_if->hwcfg2.b.num_host_chan + 1)),
-                                       (core_if->hwcfg2.b.num_host_chan + 1));
+                                       (core_if->hwcfg2.b.num_host_chan));// + 1
 
        retval += DWC_OTG_PARAM_CHECK_VALID(dev_endpoints,
                                        "dev_endpoints",
@@ -919,7 +921,7 @@ static int check_parameters(dwc_otg_core_if_t *core_if)
  * This function is the top level interrupt handler for the Common
  * (Device and host modes) interrupts.
  */
-static irqreturn_t dwc_otg_common_irq(int _irq, void *_dev, struct pt_regs *_r)
+static irqreturn_t dwc_otg_common_irq(int _irq, void *_dev)
 {
        dwc_otg_device_t *otg_dev = _dev;
        int32_t retval = IRQ_NONE;
@@ -937,7 +939,7 @@ static irqreturn_t dwc_otg_common_irq(int _irq, void *_dev, struct pt_regs *_r)
  *
  * @param[in] pdev
  */
-static void dwc_otg_driver_remove(struct platform_device *pdev)
+static int dwc_otg_driver_remove(struct platform_device *pdev)
 {
        struct device *dev = &pdev->dev;
        dwc_otg_device_t *otg_dev = dev->platform_data;
@@ -946,7 +948,7 @@ static void dwc_otg_driver_remove(struct platform_device *pdev)
        if (otg_dev == NULL) 
        {
                /* Memory allocation for the dwc_otg_device failed. */
-               return;
+               return 0;
        }
 
        /*
@@ -1000,6 +1002,7 @@ static void dwc_otg_driver_remove(struct platform_device *pdev)
        dwc_otg_module_params.host_nperio_tx_fifo_size = -1;
        dwc_otg_module_params.dev_rx_fifo_size = -1;
 #endif 
+       return 0;
 }
 
 /**
@@ -1215,6 +1218,11 @@ static int dwc_otg_driver_suspend(struct platform_device *_dev , pm_message_t st
        struct device *dev = &_dev->dev;
        dwc_otg_device_t *otg_dev = dev->platform_data;
     dwc_otg_core_if_t *core_if = otg_dev->core_if;
+    if(core_if->op_state == A_HOST)
+    {
+       printk("%s,A_HOST mode\n", __func__);
+       return 0;
+    }
     //gotgctl_data_t    gctrl;
 #if 0
     if( __rkusb_debug_mod() ) 
@@ -1235,6 +1243,11 @@ static int dwc_otg_driver_resume(struct platform_device *_dev )
 
     dwc_otg_core_global_regs_t *global_regs = 
        core_if->core_global_regs;
+    if(core_if->op_state == A_HOST)
+    {
+       printk("%s,A_HOST mode\n", __func__);
+       return 0;
+    }
 #if 0        
     if( __rkusb_debug_mod() ) 
             goto sendwakeup;
@@ -1304,7 +1317,117 @@ static struct platform_driver dwc_otg_driver = {
 };
 
 #ifdef CONFIG_RK2818_HOST11
-static void rk28_host11_driver_remove(struct platform_device *pdev)
+
+void rk28_host11_driver_enable(dwc_otg_core_if_t *core_if)
+{
+    unsigned int * otg_phy_con1 = (unsigned int*)(RK2818_REGFILE_BASE+0x3c);
+    unsigned int * scu_clkgate1_con = (unsigned int*)(RK2818_SCU_BASE+0x20);
+       /*
+        * enable usb phy & clockgate host controller
+        */
+    core_if->usb_mode == USB_MODE_FORCE_HOST;
+    core_if->op_state = A_HOST;
+    dwc_modify_reg32(scu_clkgate1_con,0x80000000,0); //clock gate enable
+    udelay(10);
+    dwc_modify_reg32(otg_phy_con1,0x80000000,0);// exit suspend.
+    mdelay(10);
+
+    /*
+     * Initialize the Core for Host mode.
+     */
+    dwc_otg_core_init(core_if);
+    dwc_otg_enable_global_interrupts(core_if);
+    hcd_start( core_if );
+}
+
+void rk28_host11_driver_disable(dwc_otg_core_if_t *core_if)
+{
+    unsigned int * otg_phy_con1 = (unsigned int*)(RK2818_REGFILE_BASE+0x3c);
+    unsigned int * scu_clkgate1_con = (unsigned int*)(RK2818_SCU_BASE+0x20);
+    dwc_otg_disable_global_interrupts( core_if );
+    hub_disconnect_device(g_root_hub11);
+    if (core_if->hcd_cb && core_if->hcd_cb->stop) {
+       core_if->hcd_cb->stop( core_if->hcd_cb->p );
+    }
+       /*
+        *disable usb phy & clockgate host controller
+        */
+    dwc_modify_reg32(otg_phy_con1,0x80000000,0x80000000);// exit suspend.
+    mdelay(10);
+    dwc_modify_reg32(scu_clkgate1_con,0x80000000,0x80000000); //clock gate enable
+}
+extern void dwc_otg_hcd_remove(struct device *_dev);
+extern int __devinit rk28_host11_hcd_init(struct device *_dev);
+
+static int s_host11_enable = 0;
+
+static ssize_t enable_usb11_show(struct device_driver *_drv, char *_buf)
+{
+    return sprintf(_buf, "%d\n", s_host11_enable);
+}
+
+static ssize_t enable_usb11_store(struct device_driver *_drv, const char *_buf, 
+                         size_t _count ) 
+{
+    int enabled = simple_strtoul(_buf, NULL, 16);
+    dwc_otg_device_t *otg_dev = g_host11;
+    dwc_otg_core_if_t *core_if = otg_dev->core_if;
+    printk("enable usb11: %d\n", enabled);
+    
+    if(enabled)
+    {// enable usb1.1
+        printk("BEGIN enable\n");
+        if(s_host11_enable){
+            printk("HOST1.1 already enable\n");
+            return _count;
+        }
+        rk28_host11_driver_enable(core_if);
+#if 0          
+        GPIOSetPinDirection(GPIOPortG_Pin1, GPIO_OUT);
+        GPIOSetPinLevel(GPIOPortG_Pin1, GPIO_LOW);
+        msleep(10);
+        
+        GPIOSetPinDirection(GPIOPortB_Pin0, GPIO_OUT);
+        GPIOSetPinLevel(GPIOPortB_Pin0, GPIO_HIGH);
+        msleep(10);
+
+        GPIOSetPinDirection(GPIOPortG_Pin0, GPIO_OUT);
+        GPIOSetPinLevel(GPIOPortG_Pin0, GPIO_HIGH);
+        msleep(10);
+        
+        GPIOSetPinDirection(GPIOPortG_Pin1, GPIO_OUT);
+        GPIOSetPinLevel(GPIOPortG_Pin1, GPIO_HIGH);
+#endif
+        s_host11_enable = 1;
+        printk("END\n");
+    }
+    else
+    {// disable usb1.1
+// cmy: 
+        printk("BEGIN disable\n");
+        rk28_host11_driver_disable(core_if);
+#if 0  
+      GPIOSetPinDirection(GPIOPortB_Pin0, GPIO_OUT);
+        GPIOSetPinLevel(GPIOPortB_Pin0, GPIO_LOW);
+        msleep(10);
+
+        GPIOSetPinDirection(GPIOPortG_Pin0, GPIO_OUT);
+        GPIOSetPinLevel(GPIOPortG_Pin0, GPIO_LOW);
+        msleep(10);
+        
+        GPIOSetPinDirection(GPIOPortG_Pin1, GPIO_OUT);
+        GPIOSetPinLevel(GPIOPortG_Pin1, GPIO_LOW);
+#endif
+        s_host11_enable = 0;
+        printk("END\n");
+    }
+
+    return _count;
+}
+
+static DRIVER_ATTR(enable_usb11, 0666/*S_IRUGO|S_IWUSR*/, enable_usb11_show, enable_usb11_store);
+
+static int rk28_host11_driver_remove(struct platform_device *pdev)
 {
        struct device *dev = &pdev->dev;
        dwc_otg_device_t *otg_dev = dev->platform_data;
@@ -1313,7 +1436,7 @@ static void rk28_host11_driver_remove(struct platform_device *pdev)
        if (otg_dev == NULL) 
        {
                /* Memory allocation for the dwc_otg_device failed. */
-               return;
+               return 0;
        }
 
        /*
@@ -1353,6 +1476,7 @@ static void rk28_host11_driver_remove(struct platform_device *pdev)
         */
        dev->platform_data = 0;
 
+       return 0;
 }
 
 /**
@@ -1524,17 +1648,17 @@ static __devinit int rk28_host11_driver_probe(struct platform_device *pdev)
 
 static int rk28_host11_driver_suspend(struct platform_device *_dev , pm_message_t state )
 {
-       struct device *dev = &_dev->dev;
-       dwc_otg_device_t *otg_dev = dev->platform_data;
-    dwc_otg_core_if_t *core_if = otg_dev->core_if;
+       //struct device *dev = &_dev->dev;
+       //dwc_otg_device_t *otg_dev = dev->platform_data;
+    //dwc_otg_core_if_t *core_if = otg_dev->core_if;
     return 0;
 }
 
 static int rk28_host11_driver_resume(struct platform_device *_dev )
 {
-       struct device *dev = &_dev->dev;
-       dwc_otg_device_t *otg_dev = dev->platform_data;
-    dwc_otg_core_if_t *core_if = otg_dev->core_if;
+       //struct device *dev = &_dev->dev;
+       //dwc_otg_device_t *otg_dev = dev->platform_data;
+    //dwc_otg_core_if_t *core_if = otg_dev->core_if;
     return 0;
 }
 
@@ -1571,9 +1695,11 @@ static int __init dwc_otg_driver_init(void)
        }
        if (driver_create_file(&dwc_otg_driver.driver, &driver_attr_version))
                pr_warning("DWC_OTG: Failed to create driver version file\n");
+       if (driver_create_file(&dwc_otg_driver.driver, &driver_attr_debuglevel))
+               pr_warning("DWC_OTG: Failed to create driver debug level file\n");
                
 #ifdef DWC_BOTH_HOST_SLAVE
-       driver_create_file(&dwc_otg_driver.driver, &driver_attr_force_usb_mode);
+       retval = driver_create_file(&dwc_otg_driver.driver, &driver_attr_force_usb_mode);
 #endif
     
 #ifdef CONFIG_RK2818_HOST11
@@ -1583,8 +1709,7 @@ static int __init dwc_otg_driver_init(void)
                printk(KERN_ERR "%s retval=%d\n", __func__, retval);
                return retval;
        }
-       if (driver_create_file(&rk28_host11_driver.driver, &driver_attr_version))
-               pr_warning("DWC_OTG: Failed to create driver version file\n");
+       retval = driver_create_file(&rk28_host11_driver.driver, &driver_attr_enable_usb11);
 #endif
        return retval;
 }
@@ -1601,6 +1726,7 @@ static void __exit dwc_otg_driver_cleanup(void)
        printk(KERN_DEBUG "dwc_otg_driver_cleanup()\n");
 
        driver_remove_file(&dwc_otg_driver.driver, &driver_attr_version);
+       driver_remove_file(&dwc_otg_driver.driver, &driver_attr_debuglevel);
 #ifdef DWC_BOTH_HOST_SLAVE     
        driver_remove_file(&dwc_otg_driver.driver, &driver_attr_force_usb_mode);
 #endif
index ac94ca2a27b717878e95efcc888aabee09c21463..79502141b6f194e84284ff460f7b38340f5bf890 100755 (executable)
 
 static int dwc_otg_hcd_suspend(struct usb_hcd *hcd)
 {
-       return 0;
+#if 1
+    dwc_otg_hcd_t *dwc_otg_hcd = hcd_to_dwc_otg_hcd (hcd);
+    dwc_otg_core_if_t *core_if = dwc_otg_hcd->core_if;
+    hprt0_data_t hprt0;
+    pcgcctl_data_t pcgcctl;
+    //dwc_debug(1);
+    
+    if(core_if->op_state == B_PERIPHERAL)
+    {
+       printk("%s, usb device mode\n", __func__);
+       return 0;
+    }
+    hprt0.d32 = dwc_read_reg32(core_if->host_if->hprt0);
+    DWC_PRINT("%s, HPRT0:0x%x\n",__func__,hprt0.d32);
+    //partial power-down
+    if(!hprt0.b.prtsusp)
+    {
+        //hprt0.d32 = 0;
+        hprt0.b.prtsusp = 1;
+        hprt0.b.prtena = 0;
+        dwc_write_reg32(core_if->host_if->hprt0, hprt0.d32);
+    }
+    udelay(10);
+    hprt0.d32 = dwc_read_reg32(core_if->host_if->hprt0);
+    DWC_PRINT("%s, HPRT0:0x%x\n",__func__,hprt0.d32);
+    if(!hprt0.b.prtsusp)
+    {
+        //hprt0.d32 = 0;
+        hprt0.b.prtsusp = 1;
+        hprt0.b.prtena = 0;
+        dwc_write_reg32(core_if->host_if->hprt0, hprt0.d32);
+    }
+    mdelay(5);
+#if 1
+    pcgcctl.d32 = dwc_read_reg32(core_if->pcgcctl);
+    pcgcctl.b.pwrclmp = 1;//power clamp
+    dwc_write_reg32(core_if->pcgcctl, pcgcctl.d32);
+    udelay(1);
+    //pcgcctl.b.rstpdwnmodule = 1;//reset PDM
+    pcgcctl.b.stoppclk = 1;//stop phy clk
+    dwc_write_reg32(core_if->pcgcctl, pcgcctl.d32);
+#endif
+#endif
+    //power off
+    return 0;
 }
 
 static int dwc_otg_hcd_resume(struct usb_hcd *hcd)
 {
+#if 1
+    dwc_otg_hcd_t *dwc_otg_hcd = hcd_to_dwc_otg_hcd (hcd);
+    dwc_otg_core_if_t *core_if = dwc_otg_hcd->core_if;
+    hprt0_data_t hprt0;
+    pcgcctl_data_t pcgcctl;
+    gintmsk_data_t gintmsk;
+       
+    if(core_if->op_state == B_PERIPHERAL)
+    {
+       printk("%s, usb device mode\n", __func__);
+       return 0;
+    }
+#if 1
+    //partial power-down
+    //power on
+    pcgcctl.d32 = dwc_read_reg32(core_if->pcgcctl);;
+    pcgcctl.b.stoppclk = 0;//stop phy clk
+    dwc_write_reg32(core_if->pcgcctl, pcgcctl.d32);
+    udelay(1);
+    pcgcctl.b.pwrclmp = 0;//power clamp
+    dwc_write_reg32(core_if->pcgcctl, pcgcctl.d32);
+    udelay(2);
+#endif
+    //dwc_debug(3);
+    //dwc_debug(1);
+    gintmsk.d32 = dwc_read_reg32(&core_if->core_global_regs->gintmsk);
+    gintmsk.b.portintr = 0;
+    dwc_write_reg32(&core_if->core_global_regs->gintmsk, gintmsk.d32);
+
+    hprt0.d32 = dwc_read_reg32(core_if->host_if->hprt0);
+    DWC_PRINT("%s, HPRT0:0x%x\n",__func__,hprt0.d32);
+    hprt0.b.prtpwr = 1;    
+    hprt0.b.prtres = 1;
+    hprt0.b.prtena = 0;
+    dwc_write_reg32(core_if->host_if->hprt0, hprt0.d32);
+    mdelay(20);
+    hprt0.d32 = dwc_read_reg32(core_if->host_if->hprt0);       
+    DWC_PRINT("%s, HPRT0:0x%x\n",__func__,hprt0.d32);
+    //hprt0.d32 = 0;
+    hprt0.b.prtpwr = 1;    
+    hprt0.b.prtres = 0;
+    hprt0.b.prtena = 0;
+    dwc_write_reg32(core_if->host_if->hprt0, hprt0.d32);
+    hprt0.d32 = 0;
+    hprt0.b.prtpwr = 1;
+    hprt0.b.prtena = 0;
+    hprt0.b.prtconndet = 1;
+    dwc_write_reg32(core_if->host_if->hprt0, hprt0.d32);
+
+    hprt0.d32 = dwc_read_reg32(core_if->host_if->hprt0);       
+    DWC_PRINT("%s, HPRT0:0x%x\n",__func__,hprt0.d32);
+       
+    gintmsk.b.portintr = 1;
+    dwc_write_reg32(&core_if->core_global_regs->gintmsk, gintmsk.d32);
+    mdelay(10);
+#endif
        return 0;
 }
 
@@ -468,10 +568,6 @@ int __devinit dwc_otg_hcd_init(struct device *dev)
        dwc_hc_t        *channel;
 
        int retval = 0;
-       printk("dwc_otg_hcd_init everest\n");
-//     g_dbg_lvl = 0xff;
-       
-       DWC_DEBUGPL(DBG_HCD, "DWC OTG HCD INIT\n");
 #if 1  //kaiker .these code must execute before usb_create_hcd
        /* Set device flags indicating whether the HCD supports DMA. */
        static u64 usb_dmamask = 0xffffffffUL;
@@ -485,6 +581,10 @@ int __devinit dwc_otg_hcd_init(struct device *dev)
                dev->coherent_dma_mask = 0;
        }
 #endif
+       printk("dwc_otg_hcd_init everest\n");
+//     g_dbg_lvl = 0xff;
+       
+       DWC_DEBUGPL(DBG_HCD, "DWC OTG HCD INIT\n");
 
        /*
         * Allocate memory for the base HCD plus the DWC OTG HCD.
@@ -500,6 +600,9 @@ int __devinit dwc_otg_hcd_init(struct device *dev)
 
        /* Initialize the DWC OTG HCD. */
        dwc_otg_hcd = hcd_to_dwc_otg_hcd(hcd);
+
+       spin_lock_init(&dwc_otg_hcd->global_lock);
+
        dwc_otg_hcd->core_if = otg_dev->core_if;
        otg_dev->hcd = dwc_otg_hcd;
 
@@ -625,10 +728,6 @@ int __devinit rk28_host11_hcd_init(struct device *dev)
        dwc_hc_t        *channel;
 
        int retval = 0;
-       printk("%s everest\n",__func__);
-//     g_dbg_lvl = 0xff;
-       
-       DWC_DEBUGPL(DBG_HCD, "DWC OTG HCD INIT\n");
 #if 1  //kaiker .these code must execute before usb_create_hcd
        /* Set device flags indicating whether the HCD supports DMA. */
        static u64 usb_dmamask = 0xffffffffUL;
@@ -642,6 +741,10 @@ int __devinit rk28_host11_hcd_init(struct device *dev)
                dev->coherent_dma_mask = 0;
        }
 #endif
+       printk("%s everest\n",__func__);
+//     g_dbg_lvl = 0xff;
+       
+       DWC_DEBUGPL(DBG_HCD, "DWC OTG HCD INIT\n");
 
        /*
         * Allocate memory for the base HCD plus the DWC OTG HCD.
@@ -660,6 +763,9 @@ int __devinit rk28_host11_hcd_init(struct device *dev)
        dwc_otg_hcd->core_if = otg_dev->core_if;
        otg_dev->hcd = dwc_otg_hcd;
 
+       spin_lock_init(&dwc_otg_hcd->global_lock);
+
+
         /* Register the HCD CIL Callbacks */
         dwc_otg_cil_register_hcd_callbacks(otg_dev->core_if, 
                                           &rk28_host11_cil_callbacks, hcd);
@@ -826,11 +932,13 @@ int dwc_otg_hcd_start(struct usb_hcd *_hcd)
 {
     dwc_otg_hcd_t *dwc_otg_hcd = hcd_to_dwc_otg_hcd (_hcd);
     dwc_otg_core_if_t *core_if = dwc_otg_hcd->core_if;
+       unsigned long flags;
        
        struct usb_device *udev;
        struct usb_bus *bus;
 
        DWC_DEBUGPL(DBG_HCD, "DWC OTG HCD START\n");
+       spin_lock_irqsave(&dwc_otg_hcd->global_lock, flags);
 #if 0
        unsigned int regvalue;
        printk("__________________________________________________________________\n");
@@ -886,6 +994,7 @@ int dwc_otg_hcd_start(struct usb_hcd *_hcd)
        }
        hcd_reinit(dwc_otg_hcd);
 out:
+       spin_unlock_irqrestore(&dwc_otg_hcd->global_lock, flags);
 
        return 0;
 }
@@ -1109,8 +1218,11 @@ int dwc_otg_hcd_urb_enqueue(struct usb_hcd *_hcd,
 
        retval = usb_hcd_link_urb_to_ep(_hcd, _urb);
        if (retval)
+       {
+               printk("%s, usb_hcd_link_urb_to_ep error\n", __func__);
                return retval;
-       local_irq_save(flags);
+       }
+       spin_lock_irqsave(&dwc_otg_hcd->global_lock, flags);
 #if 1
        /*
         * Make sure the start of frame interrupt is enabled now that
@@ -1145,7 +1257,8 @@ int dwc_otg_hcd_urb_enqueue(struct usb_hcd *_hcd,
                dwc_otg_hcd_qtd_free(qtd);
        }
 out:
-       local_irq_restore(flags);
+       spin_unlock_irqrestore(&dwc_otg_hcd->global_lock, flags);
+
        return retval;
 }
 
@@ -1169,10 +1282,10 @@ int dwc_otg_hcd_urb_dequeue(struct usb_hcd *_hcd, struct urb *_urb, int _status)
                return -1;
        }
        qh = (dwc_otg_qh_t *) _ep->hcpriv;
-       local_irq_save(flags);
+       spin_lock_irqsave(&dwc_otg_hcd->global_lock, flags);
        retval = usb_hcd_check_unlink_urb(_hcd, _urb, _status);
        if (retval) {
-               local_irq_restore(flags);
+               spin_unlock_irqrestore(&dwc_otg_hcd->global_lock, flags);
                return retval;
        }
 
@@ -1217,7 +1330,7 @@ int dwc_otg_hcd_urb_dequeue(struct usb_hcd *_hcd, struct urb *_urb, int _status)
                dwc_otg_hcd_qh_remove(dwc_otg_hcd, qh);
        }
 #endif
-       local_irq_restore(flags);
+       spin_unlock_irqrestore(&dwc_otg_hcd->global_lock, flags);
        _urb->hcpriv = NULL;
        usb_hcd_unlink_urb_from_ep(_hcd, _urb);
     /* Higher layer software sets URB status. */
@@ -1237,9 +1350,12 @@ void dwc_otg_hcd_endpoint_disable(struct usb_hcd *_hcd,
                                  struct usb_host_endpoint *_ep)
                                  
 {
+       unsigned long flags;
        dwc_otg_qh_t *qh;
        dwc_otg_hcd_t *dwc_otg_hcd = hcd_to_dwc_otg_hcd(_hcd);
 
+       spin_lock_irqsave(&dwc_otg_hcd->global_lock, flags);
+
        DWC_DEBUGPL(DBG_HCD, "DWC OTG HCD EP DISABLE: _bEndpointAddress=0x%02x, "
                    "endpoint=%d\n", _ep->desc.bEndpointAddress,
                    dwc_ep_addr_to_endpoint(_ep->desc.bEndpointAddress));
@@ -1258,6 +1374,8 @@ void dwc_otg_hcd_endpoint_disable(struct usb_hcd *_hcd,
                _ep->hcpriv = NULL;
        }
 
+       spin_unlock_irqrestore(&dwc_otg_hcd->global_lock, flags);
+
        return;
 }
 
@@ -1266,11 +1384,19 @@ void dwc_otg_hcd_endpoint_disable(struct usb_hcd *_hcd,
  * interrupt.
  *
  * This function is called by the USB core when an interrupt occurs */
-irqreturn_t dwc_otg_hcd_irq(struct usb_hcd *_hcd, 
-                            struct pt_regs *_regs)
+irqreturn_t dwc_otg_hcd_irq(struct usb_hcd *_hcd)
 {
+       irqreturn_t result;
+       unsigned long flags;
        dwc_otg_hcd_t *dwc_otg_hcd = hcd_to_dwc_otg_hcd (_hcd);
-       return IRQ_RETVAL(dwc_otg_hcd_handle_intr(dwc_otg_hcd));
+
+       spin_lock_irqsave(&dwc_otg_hcd->global_lock, flags);
+
+       result = IRQ_RETVAL(dwc_otg_hcd_handle_intr(dwc_otg_hcd));
+
+       spin_unlock_irqrestore(&dwc_otg_hcd->global_lock, flags);
+
+       return result;
 }
 
 /** Creates Status Change bitmap for the root hub and root port. The bitmap is
@@ -1829,6 +1955,7 @@ int dwc_otg_hcd_hub_control(struct usb_hcd *_hcd,
                            u16 _wLength)
 {
        int retval = 0;
+       unsigned long flags;
 
         dwc_otg_hcd_t *dwc_otg_hcd = hcd_to_dwc_otg_hcd (_hcd);
         dwc_otg_core_if_t *core_if = hcd_to_dwc_otg_hcd (_hcd)->core_if;
@@ -1836,6 +1963,7 @@ int dwc_otg_hcd_hub_control(struct usb_hcd *_hcd,
        hprt0_data_t hprt0 = {.d32 = 0};
 
        uint32_t port_status;
+       spin_lock_irqsave(&dwc_otg_hcd->global_lock, flags);
 
        switch (_typeReq) {
        case ClearHubFeature:
@@ -2221,6 +2349,7 @@ int dwc_otg_hcd_hub_control(struct usb_hcd *_hcd,
                break;
        }
 
+       spin_unlock_irqrestore(&dwc_otg_hcd->global_lock, flags);
        return retval;
 }
 
@@ -2440,9 +2569,15 @@ dwc_otg_transaction_type_e dwc_otg_hcd_select_transactions(dwc_otg_hcd_t *_hcd)
        qh_ptr = _hcd->non_periodic_sched_inactive.next;
        num_channels = _hcd->core_if->core_params->host_channels;
        while (qh_ptr != &_hcd->non_periodic_sched_inactive &&
+               /*yk@rk 20100714
               (_hcd->non_periodic_channels <
                num_channels - _hcd->periodic_channels) &&
+               */
               !list_empty(&_hcd->free_hc_list)) {
+              
+           if((num_channels > 2)&&(_hcd->non_periodic_channels >=
+               num_channels - _hcd->periodic_channels))
+                       break;
 
                qh = list_entry(qh_ptr, dwc_otg_qh_t, qh_list_entry);
                assign_and_init_hc(_hcd, qh);
index 92e55a58847e8bec3502c8f68d455f63fe1ca0b8..18ddb3ea19238c62ac74d4709b487278a1f810aa 100755 (executable)
@@ -361,6 +361,8 @@ typedef struct dwc_otg_hcd {
        /* Tasket to do a reset */
        struct tasklet_struct   *reset_tasklet;
 
+       spinlock_t global_lock;
+
 #ifdef DEBUG
        uint32_t                frrem_samples;
        uint64_t                frrem_accum;
@@ -416,8 +418,7 @@ extern int dwc_otg_hcd_urb_dequeue(struct usb_hcd *hcd,
                                   int status);
 extern void dwc_otg_hcd_endpoint_disable(struct usb_hcd *hcd,
                                         struct usb_host_endpoint *ep);
-extern irqreturn_t dwc_otg_hcd_irq(struct usb_hcd *hcd, 
-                                  struct pt_regs *regs);
+extern irqreturn_t dwc_otg_hcd_irq(struct usb_hcd *hcd);
 extern int dwc_otg_hcd_hub_status_data(struct usb_hcd *hcd, 
                                       char *buf);
 extern int dwc_otg_hcd_hub_control(struct usb_hcd *hcd, 
index 7a646272b9f216a599f0fe07638d19c654438bb6..8e24b6173e055a4172664c371b96452dcb3d2ea5 100755 (executable)
@@ -55,6 +55,7 @@ int32_t dwc_otg_hcd_handle_intr (dwc_otg_hcd_t *_dwc_otg_hcd)
         if (dwc_otg_is_host_mode(core_if)) {
                gintsts.d32 = dwc_otg_read_core_intr(core_if);
                if (!gintsts.d32) {
+                       DWC_PRINT("%s,GINTSTS = 0\n",__func__);
                        return 0;
                }
 
@@ -467,17 +468,23 @@ int32_t dwc_otg_hcd_handle_port_intr (dwc_otg_hcd_t *_dwc_otg_hcd)
  * host channel interrupt and handles them appropriately. */
 int32_t dwc_otg_hcd_handle_hc_intr (dwc_otg_hcd_t *_dwc_otg_hcd)
 {
-       int hcnum;
+       int i;
        int retval = 0;
-       struct list_head        *qh_entry;
-       dwc_otg_qh_t            *qh;
        haint_data_t haint;
 
        /* Clear appropriate bits in HCINTn to clear the interrupt bit in
         * GINTSTS */
 
        haint.d32 = dwc_otg_read_host_all_channels_intr(_dwc_otg_hcd->core_if);
-
+#if 1
+       for (i = 0; i < _dwc_otg_hcd->core_if->core_params->host_channels; i++) {
+               if (haint.b2.chint & (1 << i))
+                       retval |= dwc_otg_hcd_handle_hc_n_intr(_dwc_otg_hcd, i);
+       }
+#else
+       int hcnum;
+       struct list_head        *qh_entry;
+       dwc_otg_qh_t            *qh;
        /* yk@rk 20100511
         * USB Spec2.0 11.18.4
         * for all periodic endpoints that have split transactions scheduled within 
@@ -505,6 +512,7 @@ int32_t dwc_otg_hcd_handle_hc_intr (dwc_otg_hcd_t *_dwc_otg_hcd)
                        retval |= dwc_otg_hcd_handle_hc_n_intr (_dwc_otg_hcd, hcnum);
                }
        }
+#endif
        return retval;
 }
 
@@ -784,9 +792,19 @@ static void release_channel(dwc_otg_hcd_t *_hcd,
        dwc_otg_transaction_type_e tr_type;
        int free_qtd;
 
+       int continue_trans = 0;
+
        DWC_DEBUGPL(DBG_HCDV, "  %s: channel %d, halt_status %d\n",
                    __func__, _hc->hc_num, _halt_status);
-
+       if((!_hc->halt_pending)||
+//             (!list_empty(&_hcd->non_periodic_sched_inactive))
+               (_hcd->core_if->core_params->host_channels > 2)||
+               (!_hc->ep_is_in)||
+               (_hc->ep_type != DWC_OTG_EP_TYPE_BULK)
+               )
+       {
+               continue_trans = 1;
+       }
        switch (_halt_status) {
        case DWC_OTG_HC_XFER_URB_COMPLETE:
                free_qtd = 1;
@@ -848,12 +866,23 @@ static void release_channel(dwc_otg_hcd_t *_hcd,
                 */
                break;
        }
-
-       /* Try to queue more transfers now that there's a free channel. */
-       tr_type = dwc_otg_hcd_select_transactions(_hcd);
-       if (tr_type != DWC_OTG_TRANSACTION_NONE) {
-               dwc_otg_hcd_queue_transactions(_hcd, tr_type);
+       if(continue_trans)
+       {
+               /* Try to queue more transfers now that there's a free channel. */
+               tr_type = dwc_otg_hcd_select_transactions(_hcd);
+               if (tr_type != DWC_OTG_TRANSACTION_NONE) {
+                       dwc_otg_hcd_queue_transactions(_hcd, tr_type);
+               }
        }
+       /*
+        * Make sure the start of frame interrupt is enabled now that
+        * we know we should have queued data. The SOF interrupt
+        * handler automatically disables itself when idle to reduce
+        * the number of interrupts. See dwc_otg_hcd_handle_sof_intr()
+        * for the disable
+        */
+       dwc_modify_reg32(&_hcd->core_if->core_global_regs->gintmsk, 0,
+                        DWC_SOF_INTR_MASK);
 }
 
 /**
@@ -1201,6 +1230,12 @@ static int32_t handle_hc_nak_intr(dwc_otg_hcd_t *_hcd,
                         * occurs. The core will continue transferring data.
                         */
                        _qtd->error_count = 0;
+                       //yk@rk 20100714
+                       #if 1
+                       if((_hcd->core_if->core_params->host_channels <= 2)
+                               &&(!_hc->halt_pending))
+                       dwc_otg_hc_halt(_hcd->core_if, _hc, DWC_OTG_HC_XFER_NAK);
+                       #endif
                        goto handle_nak_done;
                }
 
@@ -1238,6 +1273,8 @@ static int32_t handle_hc_nak_intr(dwc_otg_hcd_t *_hcd,
        }
 
  handle_nak_done:
+       clear_hc_int(_hc_regs,nak);
+       if(_hcd->core_if->core_params->host_channels > 2)
        disable_hc_int(_hc_regs,nak);
 
        return 1;
@@ -1697,6 +1734,23 @@ static void handle_hc_chhltd_intr_dma(dwc_otg_hcd_t *_hcd,
        hcint.d32 = dwc_read_reg32(&_hc_regs->hcint);
        hcintmsk.d32 = dwc_read_reg32(&_hc_regs->hcintmsk);
 
+       if((!hcint.b.xfercomp)&&
+               (_hcd->core_if->core_params->host_channels <= 2)&&
+               (_hc->halt_pending)&&
+               (_hc->ep_is_in)&&
+               (_hc->ep_type == DWC_OTG_EP_TYPE_BULK))
+       {
+               if(hcint.b.ack && !hcintmsk.b.ack)
+               {
+                       //DWC_PRINT("Halt pending, ack!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\n");
+                       handle_hc_xfercomp_intr(_hcd, _hc, _hc_regs, _qtd);
+                       return;
+               }
+               release_channel(_hcd, _hc, _qtd, DWC_OTG_HC_XFER_NAK);
+               clear_hc_int(_hc_regs,chhltd);  
+               return;
+       }
+       
        if (hcint.b.xfercomp) {
                /** @todo This is here because of a possible hardware bug.  Spec
                 * says that on SPLIT-ISOC OUT transfers in DMA mode that a HALT
@@ -1745,6 +1799,10 @@ static void handle_hc_chhltd_intr_dma(dwc_otg_hcd_t *_hcd,
                 * split transfers. Start splits halt on ACK.
                 */
                handle_hc_ack_intr(_hcd, _hc, _hc_regs, _qtd);
+       } else if(hcint.b.datatglerr){
+            DWC_PRINT("%s, DATA toggle error\n");
+            dwc_debug(1);
+                               clear_hc_int(_hc_regs,chhltd);
        } else {
                if (_hc->ep_type == DWC_OTG_EP_TYPE_INTR ||
                    _hc->ep_type == DWC_OTG_EP_TYPE_ISOC) {
@@ -1764,6 +1822,7 @@ static void handle_hc_chhltd_intr_dma(dwc_otg_hcd_t *_hcd,
                                  "for halting is unknown, hcint 0x%08x, intsts 0x%08x\n",
                                  __func__, _hc->hc_num, hcint.d32,
                                  dwc_read_reg32(&_hcd->core_if->core_global_regs->gintsts));
+                               clear_hc_int(_hc_regs,chhltd);
                }
        }
 }
index 76326dd69a3488d3fa7b414ca2e942f0ef0330b2..120080356f653d6f95972020352fbd5a8b748dff 100755 (executable)
@@ -86,10 +86,8 @@ void dwc_otg_hcd_qh_free (dwc_otg_qh_t *_qh)
 {
        dwc_otg_qtd_t *qtd;
        struct list_head *pos;
-       unsigned long flags;
 
        /* Free each QTD in the QTD list */
-       local_irq_save (flags);
        for (pos = _qh->qtd_list.next;
             pos != &_qh->qtd_list;
             pos = _qh->qtd_list.next)
@@ -98,7 +96,6 @@ void dwc_otg_hcd_qh_free (dwc_otg_qh_t *_qh)
                qtd = dwc_list_to_qtd (pos);
                dwc_otg_hcd_qtd_free (qtd);
        }
-       local_irq_restore (flags);
 
        kfree (_qh);
        return;
@@ -145,6 +142,8 @@ void dwc_otg_hcd_qh_init(dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh, struct urb *_ur
        /* yk@rk 20100625
         * _urb->dev->tt->hub may be null
         */
+       if((_urb->dev->tt)&&(!_urb->dev->tt->hub))
+               printk("%s tt->hub null!\n",__func__);
        if (((_urb->dev->speed == USB_SPEED_LOW) || 
             (_urb->dev->speed == USB_SPEED_FULL)) &&
            (_urb->dev->tt) && (_urb->dev->tt->hub)&&
@@ -163,10 +162,15 @@ void dwc_otg_hcd_qh_init(dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh, struct urb *_ur
 
                /** @todo Account for split transfers in the bus time. */
                int bytecount = dwc_hb_mult(_qh->maxp) * dwc_max_packet(_qh->maxp);
+               /*
+                * The results from usb_calc_bus_time are in nanosecs,
+                * so divide the result by 1000 to convert to
+                * microsecs expected by this driver
+                */
                _qh->usecs = usb_calc_bus_time(_urb->dev->speed,
                                               usb_pipein(_urb->pipe),
                                               (_qh->ep_type == USB_ENDPOINT_XFER_ISOC),
-                                              bytecount);
+                                              bytecount) / 1000;
 
                /* Start in a slightly future (micro)frame. */
                _qh->sched_frame = dwc_frame_num_inc(_hcd->frame_number,
@@ -237,8 +241,9 @@ static int periodic_channel_available(dwc_otg_hcd_t *_hcd)
         * non-periodic transactions.
         */
        int status;
+/*yk@rk modified for usb host 1.1*/
+#if 0
        int num_channels;
-
        num_channels = _hcd->core_if->core_params->host_channels;
        if ((_hcd->periodic_channels + _hcd->non_periodic_channels < num_channels) &&
            (_hcd->periodic_channels < num_channels - 1)) {
@@ -250,7 +255,9 @@ static int periodic_channel_available(dwc_otg_hcd_t *_hcd)
                           _hcd->non_periodic_channels);
                status = -ENOSPC;
        }
-
+#else
+       status = 0;
+#endif
        return status;
 }
 
@@ -392,10 +399,12 @@ static int schedule_periodic(dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh)
  */
 int dwc_otg_hcd_qh_add (dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh)
 {
-       //unsigned long flags;
        int status = 0;
 
-       //local_irq_save(flags);
+       if (!spin_is_locked(&_hcd->global_lock))        {
+               //pr_err("%s don't have hcd->global_lock\n", __func__);
+               //BUG();
+       }
 
        if (!list_empty(&_qh->qh_list_entry)) {
                /* QH already in a schedule. */
@@ -454,9 +463,10 @@ static void deschedule_periodic(dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh)
  * @param[in] _qh QH to remove from schedule. */
 void dwc_otg_hcd_qh_remove (dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh)
 {
-       unsigned long flags;
-
-       local_irq_save(flags);
+       if (!spin_is_locked(&_hcd->global_lock))        {
+               //pr_err("%s don't have hcd->global_lock\n", __func__);
+               //BUG();
+       }
 
        if (list_empty(&_qh->qh_list_entry)) {
                /* QH is not in a schedule. */
@@ -473,7 +483,7 @@ void dwc_otg_hcd_qh_remove (dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh)
        }
 
  done:
-       local_irq_restore(flags);
+       ;
 }
 
 /**
@@ -491,14 +501,16 @@ void dwc_otg_hcd_qh_remove (dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh)
  */
 void dwc_otg_hcd_qh_deactivate(dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh, int sched_next_periodic_split)
 {
-       unsigned long flags;
-       local_irq_save(flags);
-
+       if (!spin_is_locked(&_hcd->global_lock))        {
+               //pr_err("%s don't have hcd->global_lock\n", __func__);
+               //BUG();
+       }
        if (dwc_qh_is_non_per(_qh)) {
                dwc_otg_hcd_qh_remove(_hcd, _qh);
                if (!list_empty(&_qh->qtd_list)) {
                        /* Add back to inactive non-periodic schedule. */
                        dwc_otg_hcd_qh_add(_hcd, _qh);
+               return;
                }
        } else {
                uint16_t frame_number = dwc_otg_hcd_get_frame_number(dwc_otg_hcd_to_hcd(_hcd));
@@ -554,7 +566,7 @@ void dwc_otg_hcd_qh_deactivate(dwc_otg_hcd_t *_hcd, dwc_otg_qh_t *_qh, int sched
                }
        }
 
-       local_irq_restore(flags);
+
 }
 
 /** 
index bee5e0783cfc4ae03a526e677a8a61f9374f8ab9..4394e6ca420fb2ba511b00f909a132093a9cb595 100755 (executable)
@@ -330,7 +330,16 @@ static int dwc_otg_pcd_ep_enable(struct usb_ep *_ep,
                        ep->dwc_ep.tx_fifo_num = assign_tx_fifo(pcd->otg_dev->core_if);
                }
                         #endif 
-                         ep->dwc_ep.tx_fifo_num = ep->dwc_ep.num ; /* 1,3,5 */
+        /* yk@rk
+         * ep0 -- tx fifo 0
+         * ep1 -- tx fifo 1
+         * ep3 -- tx fifo 2
+         * ep5 -- tx fifo 3
+         */
+        if(ep->dwc_ep.num == 0)
+               ep->dwc_ep.tx_fifo_num = 0;
+        else
+           ep->dwc_ep.tx_fifo_num = (ep->dwc_ep.num>>1)+1 ; /* 1,3,5 */
        }                
        /* Set initial data PID. */
        if ((_desc->bmAttributes & USB_ENDPOINT_XFERTYPE_MASK) == 
@@ -398,7 +407,7 @@ static int dwc_otg_pcd_ep_disable(struct usb_ep *_ep)
  * @param _gfp_flags the GFP_* flags to use.
  */
 static struct usb_request *dwc_otg_pcd_alloc_request(struct usb_ep *_ep,
-                                                                                                        int _gfp_flags)
+                                                                                                        gfp_t _gfp_flags)
 {
        dwc_otg_pcd_request_t *req;
        DWC_DEBUGPL(DBG_PCDV,"%s(%p,%d)\n", __func__, _ep, _gfp_flags);
@@ -536,7 +545,7 @@ static void dwc_otg_pcd_free_buffer(struct usb_ep *_ep, void *_buf,
  *       flag.
  */
 static int dwc_otg_pcd_ep_queue(struct usb_ep *_ep, 
-                                                               struct usb_request *_req, int _gfp_flags)
+                                                               struct usb_request *_req, gfp_t _gfp_flags)
 {
        int prevented = 0;
        dwc_otg_pcd_request_t *req;
@@ -557,13 +566,12 @@ static int dwc_otg_pcd_ep_queue(struct usb_ep *_ep,
        /* 20091226,HSL@RK */
        if ( !list_empty(&req->queue) ) 
        {
-                       return -EINVAL;
-                       printk("%s::req not empty,done it error!\n" , __func__ );
-                       while(!list_empty(&req->queue) ) {
-                               ep = container_of(_ep, dwc_otg_pcd_ep_t, ep);
-                               request_done(ep, req, -ECONNABORTED);
-                       }
-               
+        printk("%s::ep %s req not empty,done it error!\n" , __func__, _ep->name);
+               return -EINVAL;
+        while(!list_empty(&req->queue) ) {
+                ep = container_of(_ep, dwc_otg_pcd_ep_t, ep);
+                request_done(ep, req, -ECONNABORTED);
+        }
        }
        
        ep = container_of(_ep, dwc_otg_pcd_ep_t, ep);
@@ -1026,7 +1034,7 @@ void dwc_otg_pcd_update_otg( dwc_otg_pcd_t *_pcd, const unsigned _reset )
  * This function is the top level PCD interrupt handler.
  */
 static irqreturn_t 
-dwc_otg_pcd_irq(int _irq, void *_dev, struct pt_regs *_r)
+dwc_otg_pcd_irq(int _irq, void *_dev)
 {
        dwc_otg_pcd_t *pcd = _dev;
        int32_t retval = IRQ_NONE;
@@ -1599,11 +1607,13 @@ void dwc_otg_msc_unlock(void)
 
 static void dwc_phy_reconnect(struct work_struct *work)
 {
-        dwc_otg_pcd_t *pcd = container_of(work, dwc_otg_pcd_t, reconnect.work);;
-        dwc_otg_core_if_t *core_if = GET_CORE_IF(pcd);
+        dwc_otg_pcd_t *pcd;
+        dwc_otg_core_if_t *core_if;
         gotgctl_data_t    gctrl;
         dctl_data_t dctl = {.d32=0};
 
+        pcd = container_of(work, dwc_otg_pcd_t, reconnect.work);
+        core_if = GET_CORE_IF(pcd); 
         gctrl.d32 = dwc_read_reg32( &core_if->core_global_regs->gotgctl );
         if( gctrl.b.bsesvld  ) {
             dwc_otg_msc_lock();
@@ -1978,6 +1988,10 @@ int rk28_msc_switch(int action)
        return 0;
 }
 #else
+int dwc_otg_set_vbus_status(int status)
+{
+    return 0;
+}
 int rk28_usb_suspend( int exitsuspend )
 {
        return 0;
index 9b7c83d9c11624ea38d7d6f37f09b624098eade2..bfa4850bf507fb646df34cd9ba5dd1ed7e8fa753 100755 (executable)
@@ -37,7 +37,7 @@
 #include "dwc_otg_pcd.h"
 
 
-#define DEBUG_EP0
+//#define DEBUG_EP0
 
 /* request functions defined in "dwc_otg_pcd.c" */
 extern void request_done( dwc_otg_pcd_ep_t *_ep, dwc_otg_pcd_request_t *_req, 
@@ -875,6 +875,7 @@ int32_t dwc_otg_pcd_handle_enum_done_intr(dwc_otg_pcd_t *_pcd)
        gusbcfg.d32 = dwc_read_reg32(&global_regs->gusbcfg);
        if (_pcd->gadget.speed == USB_SPEED_HIGH) 
        {
+       depctl.b.mps = 0x200;
                if (GET_CORE_IF(_pcd)->hwcfg2.b.hs_phy_type == DWC_HWCFG2_HS_PHY_TYPE_ULPI) 
                {
                        /* ULPI interface */
@@ -925,6 +926,7 @@ int32_t dwc_otg_pcd_handle_enum_done_intr(dwc_otg_pcd_t *_pcd)
        } 
        else 
        {
+       depctl.b.mps = 0x40;
                /* Full or low speed */
                gusbcfg.b.usbtrdtim = 9;
        }
@@ -936,14 +938,12 @@ int32_t dwc_otg_pcd_handle_enum_done_intr(dwc_otg_pcd_t *_pcd)
        dwc_write_reg32( &GET_CORE_IF(_pcd)->core_global_regs->gintsts, 
                                                 gintsts.d32 );
        /* enable ep2out */
-       depctl.d32 = 0;
        depctl.b.setd0pid = 1;
     dwc_write_reg32( &GET_CORE_IF(_pcd)->dev_if->in_ep_regs[1]->diepctl, depctl.d32);
        depctl.b.snak = 1;
        depctl.b.txfnum = 2;
        depctl.b.eptype = 2;
     depctl.b.usbactep = 1;
-    depctl.b.mps = 0x200;
     dwc_write_reg32( &GET_CORE_IF(_pcd)->dev_if->out_ep_regs[2]->doepctl, depctl.d32 );
        return 1;
 }
@@ -2536,7 +2536,6 @@ int32_t dwc_otg_pcd_handle_out_nak_effective( dwc_otg_pcd_t *_pcd )
  * All interrupt registers are processed from LSB to MSB.
  * 
  */
- extern void dwc_otg_dump_global_registers(dwc_otg_core_if_t *_core_if);
 int32_t dwc_otg_pcd_handle_intr( dwc_otg_pcd_t *_pcd )
 {
        dwc_otg_core_if_t *core_if = GET_CORE_IF(_pcd);
index be3dff16d7c4d284fc67d84af47d33eb462d3a72..1f84257851a52d27714ee9d9fac541d450626cd5 100644 (file)
@@ -344,8 +344,13 @@ static int  option_resume(struct usb_serial *serial);
 #define HAIER_VENDOR_ID                                0x201e
 #define HAIER_PRODUCT_CE100                    0x2009
 
+/* Thinkwill products */
+#define THINKWILL_VENDOR_ID    0x19f5
+#define THINKWILL_PRODUCT_ID   0x9909
+
 static struct usb_device_id option_ids[] = {
        { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_COLT) },
+       { USB_DEVICE(THINKWILL_VENDOR_ID,THINKWILL_PRODUCT_ID)},
        { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_RICOLA) },
        { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_RICOLA_LIGHT) },
        { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_RICOLA_QUAD) },