From 4da04b77e2a330ad67b89f6c71cb3fb60575d20b Mon Sep 17 00:00:00 2001 From: Dave Chapman Date: Sun, 4 Feb 2007 21:46:01 +0000 Subject: [PATCH] Fix USB detection on ipods and other portalplayer targets - Rockbox now correctly distinguishes between a USB connection to a computer and a connection to a USB AC charger. Based on the experimental USB code in FS #6494 by Barry Wardell. Closes FS #4724. git-svn-id: svn://svn.rockbox.org/rockbox/trunk@12198 a1c6a512-1295-4272-9138-f99709370657 --- firmware/export/config-e200.h | 3 + firmware/export/config-h10.h | 3 + firmware/export/config-h10_5gb.h | 3 + firmware/export/config-ipod4g.h | 3 + firmware/export/config-ipodcolor.h | 3 + firmware/export/config-ipodmini.h | 3 + firmware/export/config-ipodmini2g.h | 3 + firmware/export/config-ipodnano.h | 3 + firmware/export/config-ipodvideo.h | 3 + firmware/export/config-tpj1022.h | 3 + firmware/export/config.h | 5 +- firmware/export/mx31.h | 372 ++++++++++++++++++++++++++++ firmware/target/arm/usb-pp.c | 111 ++++++++- firmware/target/arm/usb-target.h | 104 -------- 14 files changed, 504 insertions(+), 118 deletions(-) create mode 100644 firmware/export/mx31.h diff --git a/firmware/export/config-e200.h b/firmware/export/config-e200.h index 214d701055..aca0e1cdc8 100644 --- a/firmware/export/config-e200.h +++ b/firmware/export/config-e200.h @@ -119,6 +119,9 @@ /* #define USB_IPODSTYLE */ +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ #define HAVE_USB_POWER diff --git a/firmware/export/config-h10.h b/firmware/export/config-h10.h index ae2a150ae6..de1f517cf6 100644 --- a/firmware/export/config-h10.h +++ b/firmware/export/config-h10.h @@ -142,6 +142,9 @@ /* #define USB_IPODSTYLE */ +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ #define HAVE_USB_POWER diff --git a/firmware/export/config-h10_5gb.h b/firmware/export/config-h10_5gb.h index 42f774832a..1d79947acf 100644 --- a/firmware/export/config-h10_5gb.h +++ b/firmware/export/config-h10_5gb.h @@ -122,6 +122,9 @@ /* #define USB_IPODSTYLE */ +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ #define HAVE_USB_POWER diff --git a/firmware/export/config-ipod4g.h b/firmware/export/config-ipod4g.h index 65d0df1b87..d6958befbe 100644 --- a/firmware/export/config-ipod4g.h +++ b/firmware/export/config-ipod4g.h @@ -117,6 +117,9 @@ #define USB_IPODSTYLE +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ #define HAVE_USB_POWER diff --git a/firmware/export/config-ipodcolor.h b/firmware/export/config-ipodcolor.h index 36adcd22c2..3ccfb1a879 100644 --- a/firmware/export/config-ipodcolor.h +++ b/firmware/export/config-ipodcolor.h @@ -108,6 +108,9 @@ #define USB_IPODSTYLE +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ #define HAVE_USB_POWER diff --git a/firmware/export/config-ipodmini.h b/firmware/export/config-ipodmini.h index d51d97a073..423773dab7 100644 --- a/firmware/export/config-ipodmini.h +++ b/firmware/export/config-ipodmini.h @@ -111,6 +111,9 @@ #define USB_IPODSTYLE +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ #define HAVE_USB_POWER diff --git a/firmware/export/config-ipodmini2g.h b/firmware/export/config-ipodmini2g.h index edcf095c13..9a7bc98815 100644 --- a/firmware/export/config-ipodmini2g.h +++ b/firmware/export/config-ipodmini2g.h @@ -114,6 +114,9 @@ #define USB_IPODSTYLE +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ #define HAVE_USB_POWER diff --git a/firmware/export/config-ipodnano.h b/firmware/export/config-ipodnano.h index e1b856eed8..ce0309996e 100644 --- a/firmware/export/config-ipodnano.h +++ b/firmware/export/config-ipodnano.h @@ -113,6 +113,9 @@ #define USB_IPODSTYLE +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ #define HAVE_USB_POWER diff --git a/firmware/export/config-ipodvideo.h b/firmware/export/config-ipodvideo.h index 1ed7f93a69..f28d2d93ab 100644 --- a/firmware/export/config-ipodvideo.h +++ b/firmware/export/config-ipodvideo.h @@ -113,6 +113,9 @@ #define USB_IPODSTYLE +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ #define HAVE_USB_POWER diff --git a/firmware/export/config-tpj1022.h b/firmware/export/config-tpj1022.h index 03ab9445fb..c57c8cf5d1 100644 --- a/firmware/export/config-tpj1022.h +++ b/firmware/export/config-tpj1022.h @@ -108,6 +108,9 @@ /* #define USB_IPODSTYLE */ +/* USB On-the-go */ +#define CONFIG_USBOTG USBOTG_ARC + /* define this if the unit can be powered or charged via USB */ /*#define HAVE_USB_POWER*/ diff --git a/firmware/export/config.h b/firmware/export/config.h index ab1cfeafec..5e127b430d 100644 --- a/firmware/export/config.h +++ b/firmware/export/config.h @@ -154,8 +154,9 @@ #define RTC_AS3514 6 /* Sandisk Sansa e200 series */ /* USB On-the-go */ -#define USBOTG_ISP1362 1362 -#define USBOTG_M5636 5636 +#define USBOTG_ISP1362 1362 /* iriver H300 */ +#define USBOTG_M5636 5636 /* iAudio X5 */ +#define USBOTG_ARC 5020 /* PortalPlayer 502x */ /* Multiple cores */ #define CPU 0 diff --git a/firmware/export/mx31.h b/firmware/export/mx31.h new file mode 100644 index 0000000000..5af3bb052a --- /dev/null +++ b/firmware/export/mx31.h @@ -0,0 +1,372 @@ +/*************************************************************************** + * __________ __ ___. + * Open \______ \ ____ ____ | | _\_ |__ _______ ___ + * Source | _// _ \_/ ___\| |/ /| __ \ / _ \ \/ / + * Jukebox | | ( <_> ) \___| < | \_\ ( <_> > < < + * Firmware |____|_ /\____/ \___ >__|_ \|___ /\____/__/\_ \ + * \/ \/ \/ \/ \/ + * $Id: $ + * + * Copyright (C) 2007 by Barry Wardell + * + * i.MX31 driver based on code from the Linux Target Image Builder from + * Freescale - http://www.bitshrine.org/ and + * http://www.bitshrine.org/gpp/linux-2.6.16-mx31-usb-2.patch + * Adapted for Rockbox in January 2007 + * Original file: drivers/usb/gadget/arcotg_udc.h + * + * Copyright 2004-2006 Freescale Semiconductor, Inc. All Rights Reserved. + * + * Based on mpc-udc.h + * Author: Li Yang (leoli@freescale.com) + * Jiang Bo (Tanya.jiang@freescale.com) + * + * All files in this archive are subject to the GNU General Public License. + * See the file COPYING in the source tree root for full license agreement. + * + * This software is distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY + * KIND, either express or implied. + * + ****************************************************************************/ + +/* + * Freescale USB device/endpoint management registers + */ +#ifndef __MX31_H +#define __MX31_H + +/* Register addresses - from Freescale i.MX31 reference manual */ +/* The PortalPlayer USB controller usec base address 0xc5000000 */ +#define USB_BASE 0xc5000000 + +/* OTG */ +#define UOG_ID (*(volatile unsigned int *)(USB_BASE+0x000)) +#define UOG_HWGENERAL (*(volatile unsigned int *)(USB_BASE+0x004)) +#define UOG_HWHOST (*(volatile unsigned int *)(USB_BASE+0x008)) +#define UOG_HWTXBUF (*(volatile unsigned int *)(USB_BASE+0x010)) +#define UOG_HWRXBUF (*(volatile unsigned int *)(USB_BASE+0x014)) +#define UOG_CAPLENGTH (*(volatile unsigned char *)(USB_BASE+0x100)) +#define UOG_HCIVERSION (*(volatile unsigned short *)(USB_BASE+0x102)) +#define UOG_HCSPARAMS (*(volatile unsigned int *)(USB_BASE+0x104)) +#define UOG_HCCPARAMS (*(volatile unsigned int *)(USB_BASE+0x108)) +#define UOG_DCIVERSION (*(volatile unsigned short *)(USB_BASE+0x120)) +#define UOG_DCCPARAMS (*(volatile unsigned int *)(USB_BASE+0x124)) +#define UOG_USBCMD (*(volatile unsigned int *)(USB_BASE+0x140)) +#define UOG_USBSTS (*(volatile unsigned int *)(USB_BASE+0x144)) +#define UOG_USBINTR (*(volatile unsigned int *)(USB_BASE+0x148)) +#define UOG_FRINDEX (*(volatile unsigned int *)(USB_BASE+0x14c)) +#define UOG_PERIODICLISTBASE (*(volatile unsigned int *)(USB_BASE+0x154)) +#define UOG_ASYNCLISTADDR (*(volatile unsigned int *)(USB_BASE+0x158)) +#define UOG_BURSTSIZE (*(volatile unsigned int *)(USB_BASE+0x160)) +#define UOG_TXFILLTUNING (*(volatile unsigned int *)(USB_BASE+0x164)) +#define UOG_ULPIVIEW (*(volatile unsigned int *)(USB_BASE+0x170)) +#define UOG_CFGFLAG (*(volatile unsigned int *)(USB_BASE+0x180)) +#define UOG_PORTSC1 (*(volatile unsigned int *)(USB_BASE+0x184)) +/*#define UOG_PORTSC2 (*(volatile unsigned int *)(USB_BASE+0x188)) +#define UOG_PORTSC3 (*(volatile unsigned int *)(USB_BASE+0x18c)) +#define UOG_PORTSC4 (*(volatile unsigned int *)(USB_BASE+0x190)) +#define UOG_PORTSC5 (*(volatile unsigned int *)(USB_BASE+0x194)) +#define UOG_PORTSC6 (*(volatile unsigned int *)(USB_BASE+0x198)) +#define UOG_PORTSC7 (*(volatile unsigned int *)(USB_BASE+0x19c)) +#define UOG_PORTSC8 (*(volatile unsigned int *)(USB_BASE+0x1a0))*/ +#define UOG_OTGSC (*(volatile unsigned int *)(USB_BASE+0x1a4)) +#define UOG_USBMODE (*(volatile unsigned int *)(USB_BASE+0x1a8)) +#define UOG_ENDPTSETUPSTAT (*(volatile unsigned int *)(USB_BASE+0x1ac)) +#define UOG_ENDPTPRIME (*(volatile unsigned int *)(USB_BASE+0x1b0)) +#define UOG_ENDPTFLUSH (*(volatile unsigned int *)(USB_BASE+0x1b4)) +#define UOG_ENDPTSTAT (*(volatile unsigned int *)(USB_BASE+0x1b8)) +#define UOG_ENDPTCOMPLETE (*(volatile unsigned int *)(USB_BASE+0x1bc)) +#define ENDPTCRTL0 (*(volatile unsigned int *)(USB_BASE+0x1c0)) +#define ENDPTCRTL1 (*(volatile unsigned int *)(USB_BASE+0x1c4)) +#define ENDPTCRTL2 (*(volatile unsigned int *)(USB_BASE+0x1c8)) +#define ENDPTCRTL3 (*(volatile unsigned int *)(USB_BASE+0x1cc)) +#define ENDPTCRTL4 (*(volatile unsigned int *)(USB_BASE+0x1d0)) +#define ENDPTCRTL5 (*(volatile unsigned int *)(USB_BASE+0x1d4)) +#define ENDPTCRTL6 (*(volatile unsigned int *)(USB_BASE+0x1d8)) +#define ENDPTCRTL7 (*(volatile unsigned int *)(USB_BASE+0x1dc)) +/*#define ENDPTCRTL8 (*(volatile unsigned int *)(USB_BASE+0x1e0)) +#define ENDPTCRTL9 (*(volatile unsigned int *)(USB_BASE+0x1e4)) +#define ENDPTCRTL10 (*(volatile unsigned int *)(USB_BASE+0x1e8)) +#define ENDPTCRTL11 (*(volatile unsigned int *)(USB_BASE+0x1ec)) +#define ENDPTCRTL12 (*(volatile unsigned int *)(USB_BASE+0x1f0)) +#define ENDPTCRTL13 (*(volatile unsigned int *)(USB_BASE+0x1f4)) +#define ENDPTCRTL14 (*(volatile unsigned int *)(USB_BASE+0x1f8)) +#define ENDPTCRTL15 (*(volatile unsigned int *)(USB_BASE+0x1fc))*/ + +/* Host 1 */ +#define UH1_ID (*(volatile unsigned int *)(USB_BASE+0x200)) +#define UH1_HWGENERAL (*(volatile unsigned int *)(USB_BASE+0x204)) +#define UH1_HWHOST (*(volatile unsigned int *)(USB_BASE+0x208)) +#define UH1_HWTXBUF (*(volatile unsigned int *)(USB_BASE+0x210)) +#define UH1_HWRXBUF (*(volatile unsigned int *)(USB_BASE+0x214)) +#define UH1_CAPLENGTH (*(volatile unsigned int *)(USB_BASE+0x300)) +#define UH1_HCIVERSION (*(volatile unsigned int *)(USB_BASE+0x302)) +#define UH1_HCSPARAMS (*(volatile unsigned int *)(USB_BASE+0x304)) +#define UH1_HCCPARAMS (*(volatile unsigned int *)(USB_BASE+0x308)) +#define UH1_USBCMD (*(volatile unsigned int *)(USB_BASE+0x340)) +#define UH1_USBSTS (*(volatile unsigned int *)(USB_BASE+0x344)) +#define UH1_USBINTR (*(volatile unsigned int *)(USB_BASE+0x348)) +#define UH1_FRINDEX (*(volatile unsigned int *)(USB_BASE+0x34c)) +#define UH1_PERIODICLISTBASE (*(volatile unsigned int *)(USB_BASE+0x354)) +#define UH1_ASYNCLISTADDR (*(volatile unsigned int *)(USB_BASE+0x358)) +#define UH1_BURSTSIZE (*(volatile unsigned int *)(USB_BASE+0x360)) +#define UH1_TXFILLTUNING (*(volatile unsigned int *)(USB_BASE+0x364)) +#define UH1_PORTSC1 (*(volatile unsigned int *)(USB_BASE+0x384)) +#define UH1_USBMODE (*(volatile unsigned int *)(USB_BASE+0x3a8)) + +/* Host 2 */ +#define UH2_ID (*(volatile unsigned int *)(USB_BASE+0x400)) +#define UH2_HWGENERAL (*(volatile unsigned int *)(USB_BASE+0x404)) +#define UH2_HWHOST (*(volatile unsigned int *)(USB_BASE+0x408)) +#define UH2_HWTXBUF (*(volatile unsigned int *)(USB_BASE+0x410)) +#define UH2_HWRXBUF (*(volatile unsigned int *)(USB_BASE+0x414)) +#define UH2_CAPLENGTH (*(volatile unsigned int *)(USB_BASE+0x500)) +#define UH2_HCIVERSION (*(volatile unsigned int *)(USB_BASE+0x502)) +#define UH2_HCSPARAMS (*(volatile unsigned int *)(USB_BASE+0x504)) +#define UH2_HCCPARAMS (*(volatile unsigned int *)(USB_BASE+0x508)) +#define UH2_USBCMD (*(volatile unsigned int *)(USB_BASE+0x540)) +#define UH2_USBSTS (*(volatile unsigned int *)(USB_BASE+0x544)) +#define UH2_USBINTR (*(volatile unsigned int *)(USB_BASE+0x548)) +#define UH2_FRINDEX (*(volatile unsigned int *)(USB_BASE+0x54c)) +#define UH2_PERIODICLISTBASE (*(volatile unsigned int *)(USB_BASE+0x554)) +#define UH2_ASYNCLISTADDR (*(volatile unsigned int *)(USB_BASE+0x558)) +#define UH2_BURSTSIZE (*(volatile unsigned int *)(USB_BASE+0x560)) +#define UH2_TXFILLTUNING (*(volatile unsigned int *)(USB_BASE+0x564)) +#define UH2_ULPIVIEW (*(volatile unsigned int *)(USB_BASE+0x570)) +#define UH2_PORTSC1 (*(volatile unsigned int *)(USB_BASE+0x584)) +#define UH2_USBMODE (*(volatile unsigned int *)(USB_BASE+0x5a8)) + +/* General */ +#define USB_CTRL (*(volatile unsigned int *)(USB_BASE+0x600)) +#define USB_OTG_MIRROR (*(volatile unsigned int *)(USB_BASE+0x604)) + +/* Maximum values */ +#define USB_MAX_ENDPOINTS 8 +#define USB_MAX_PIPES (USB_MAX_ENDPOINTS*2) +#define USB_MAX_CTRL_PAYLOAD 64 + +/* ep0 transfer state */ +#define WAIT_FOR_SETUP 0 +#define DATA_STATE_XMIT 1 +#define DATA_STATE_NEED_ZLP 2 +#define WAIT_FOR_OUT_STATUS 3 +#define DATA_STATE_RECV 4 + +/* Frame Index Register Bit Masks */ +#define USB_FRINDEX_MASKS (0x3fff) + +/* USB CMD Register Bit Masks */ +#define USB_CMD_RUN_STOP (0x00000001) +#define USB_CMD_CTRL_RESET (0x00000002) +#define USB_CMD_PERIODIC_SCHEDULE_EN (0x00000010) +#define USB_CMD_ASYNC_SCHEDULE_EN (0x00000020) +#define USB_CMD_INT_AA_DOORBELL (0x00000040) +#define USB_CMD_ASP (0x00000300) +#define USB_CMD_ASYNC_SCH_PARK_EN (0x00000800) +#define USB_CMD_SUTW (0x00002000) +#define USB_CMD_ATDTW (0x00004000) +#define USB_CMD_ITC (0x00FF0000) + +/* bit 15,3,2 are frame list size */ +#define USB_CMD_FRAME_SIZE_1024 (0x00000000) +#define USB_CMD_FRAME_SIZE_512 (0x00000004) +#define USB_CMD_FRAME_SIZE_256 (0x00000008) +#define USB_CMD_FRAME_SIZE_128 (0x0000000C) +#define USB_CMD_FRAME_SIZE_64 (0x00008000) +#define USB_CMD_FRAME_SIZE_32 (0x00008004) +#define USB_CMD_FRAME_SIZE_16 (0x00008008) +#define USB_CMD_FRAME_SIZE_8 (0x0000800C) + +/* bit 9-8 are async schedule park mode count */ +#define USB_CMD_ASP_00 (0x00000000) +#define USB_CMD_ASP_01 (0x00000100) +#define USB_CMD_ASP_10 (0x00000200) +#define USB_CMD_ASP_11 (0x00000300) +#define USB_CMD_ASP_BIT_POS (8) + +/* bit 23-16 are interrupt threshold control */ +#define USB_CMD_ITC_NO_THRESHOLD (0x00000000) +#define USB_CMD_ITC_1_MICRO_FRM (0x00010000) +#define USB_CMD_ITC_2_MICRO_FRM (0x00020000) +#define USB_CMD_ITC_4_MICRO_FRM (0x00040000) +#define USB_CMD_ITC_8_MICRO_FRM (0x00080000) +#define USB_CMD_ITC_16_MICRO_FRM (0x00100000) +#define USB_CMD_ITC_32_MICRO_FRM (0x00200000) +#define USB_CMD_ITC_64_MICRO_FRM (0x00400000) +#define USB_CMD_ITC_BIT_POS (16) + +/* USB STS Register Bit Masks */ +#define USB_STS_INT (0x00000001) +#define USB_STS_ERR (0x00000002) +#define USB_STS_PORT_CHANGE (0x00000004) +#define USB_STS_FRM_LST_ROLL (0x00000008) +#define USB_STS_SYS_ERR (0x00000010) +#define USB_STS_IAA (0x00000020) +#define USB_STS_RESET (0x00000040) +#define USB_STS_SOF (0x00000080) +#define USB_STS_SUSPEND (0x00000100) +#define USB_STS_HC_HALTED (0x00001000) +#define USB_STS_RCL (0x00002000) +#define USB_STS_PERIODIC_SCHEDULE (0x00004000) +#define USB_STS_ASYNC_SCHEDULE (0x00008000) + +/* USB INTR Register Bit Masks */ +#define USB_INTR_INT_EN (0x00000001) +#define USB_INTR_ERR_INT_EN (0x00000002) +#define USB_INTR_PTC_DETECT_EN (0x00000004) +#define USB_INTR_FRM_LST_ROLL_EN (0x00000008) +#define USB_INTR_SYS_ERR_EN (0x00000010) +#define USB_INTR_ASYN_ADV_EN (0x00000020) +#define USB_INTR_RESET_EN (0x00000040) +#define USB_INTR_SOF_EN (0x00000080) +#define USB_INTR_DEVICE_SUSPEND (0x00000100) + +/* Device Address bit masks */ +#define USB_DEVICE_ADDRESS_MASK (0xFE000000) +#define USB_DEVICE_ADDRESS_BIT_POS (25) + +/* endpoint list address bit masks */ +#define USB_EP_LIST_ADDRESS_MASK (0xfffff800) + +/* PORTSCX Register Bit Masks */ +#define PORTSCX_CURRENT_CONNECT_STATUS (0x00000001) +#define PORTSCX_CONNECT_STATUS_CHANGE (0x00000002) +#define PORTSCX_PORT_ENABLE (0x00000004) +#define PORTSCX_PORT_EN_DIS_CHANGE (0x00000008) +#define PORTSCX_OVER_CURRENT_ACT (0x00000010) +#define PORTSCX_OVER_CURRENT_CHG (0x00000020) +#define PORTSCX_PORT_FORCE_RESUME (0x00000040) +#define PORTSCX_PORT_SUSPEND (0x00000080) +#define PORTSCX_PORT_RESET (0x00000100) +#define PORTSCX_LINE_STATUS_BITS (0x00000C00) +#define PORTSCX_PORT_POWER (0x00001000) +#define PORTSCX_PORT_INDICTOR_CTRL (0x0000C000) +#define PORTSCX_PORT_TEST_CTRL (0x000F0000) +#define PORTSCX_WAKE_ON_CONNECT_EN (0x00100000) +#define PORTSCX_WAKE_ON_CONNECT_DIS (0x00200000) +#define PORTSCX_WAKE_ON_OVER_CURRENT (0x00400000) +#define PORTSCX_PHY_LOW_POWER_SPD (0x00800000) +#define PORTSCX_PORT_FORCE_FULL_SPEED (0x01000000) +#define PORTSCX_PORT_SPEED_MASK (0x0C000000) +#define PORTSCX_PORT_WIDTH (0x10000000) +#define PORTSCX_PHY_TYPE_SEL (0xC0000000) + +/* bit 11-10 are line status */ +#define PORTSCX_LINE_STATUS_SE0 (0x00000000) +#define PORTSCX_LINE_STATUS_JSTATE (0x00000400) +#define PORTSCX_LINE_STATUS_KSTATE (0x00000800) +#define PORTSCX_LINE_STATUS_UNDEF (0x00000C00) +#define PORTSCX_LINE_STATUS_BIT_POS (10) + +/* bit 15-14 are port indicator control */ +#define PORTSCX_PIC_OFF (0x00000000) +#define PORTSCX_PIC_AMBER (0x00004000) +#define PORTSCX_PIC_GREEN (0x00008000) +#define PORTSCX_PIC_UNDEF (0x0000C000) +#define PORTSCX_PIC_BIT_POS (14) + +/* bit 19-16 are port test control */ +#define PORTSCX_PTC_DISABLE (0x00000000) +#define PORTSCX_PTC_JSTATE (0x00010000) +#define PORTSCX_PTC_KSTATE (0x00020000) +#define PORTSCX_PTC_SEQNAK (0x00030000) +#define PORTSCX_PTC_PACKET (0x00040000) +#define PORTSCX_PTC_FORCE_EN (0x00050000) +#define PORTSCX_PTC_BIT_POS (16) + +/* bit 27-26 are port speed */ +#define PORTSCX_PORT_SPEED_FULL (0x00000000) +#define PORTSCX_PORT_SPEED_LOW (0x04000000) +#define PORTSCX_PORT_SPEED_HIGH (0x08000000) +#define PORTSCX_PORT_SPEED_UNDEF (0x0C000000) +#define PORTSCX_SPEED_BIT_POS (26) + +/* bit 28 is parallel transceiver width for UTMI interface */ +#define PORTSCX_PTW (0x10000000) +#define PORTSCX_PTW_8BIT (0x00000000) +#define PORTSCX_PTW_16BIT (0x10000000) + +/* bit 31-30 are port transceiver select */ +#define PORTSCX_PTS_UTMI (0x00000000) +#define PORTSCX_PTS_ULPI (0x80000000) +#define PORTSCX_PTS_FSLS (0xC0000000) +#define PORTSCX_PTS_BIT_POS (30) + +/* USB MODE Register Bit Masks */ +#define USB_MODE_CTRL_MODE_IDLE (0x00000000) +#define USB_MODE_CTRL_MODE_DEVICE (0x00000002) +#define USB_MODE_CTRL_MODE_HOST (0x00000003) +#define USB_MODE_CTRL_MODE_RSV (0x00000001) +#define USB_MODE_SETUP_LOCK_OFF (0x00000008) +#define USB_MODE_STREAM_DISABLE (0x00000010) + +/* Endpoint Flush Register */ +#define EPFLUSH_TX_OFFSET (0x00010000) +#define EPFLUSH_RX_OFFSET (0x00000000) + +/* Endpoint Setup Status bit masks */ +#define EP_SETUP_STATUS_MASK (0x0000003F) +#define EP_SETUP_STATUS_EP0 (0x00000001) + +/* ENDPOINTCTRLx Register Bit Masks */ +#define EPCTRL_TX_ENABLE (0x00800000) +#define EPCTRL_TX_DATA_TOGGLE_RST (0x00400000) /* Not EP0 */ +#define EPCTRL_TX_DATA_TOGGLE_INH (0x00200000) /* Not EP0 */ +#define EPCTRL_TX_TYPE (0x000C0000) +#define EPCTRL_TX_DATA_SOURCE (0x00020000) /* Not EP0 */ +#define EPCTRL_TX_EP_STALL (0x00010000) +#define EPCTRL_RX_ENABLE (0x00000080) +#define EPCTRL_RX_DATA_TOGGLE_RST (0x00000040) /* Not EP0 */ +#define EPCTRL_RX_DATA_TOGGLE_INH (0x00000020) /* Not EP0 */ +#define EPCTRL_RX_TYPE (0x0000000C) +#define EPCTRL_RX_DATA_SINK (0x00000002) /* Not EP0 */ +#define EPCTRL_RX_EP_STALL (0x00000001) + +/* bit 19-18 and 3-2 are endpoint type */ +#define EPCTRL_EP_TYPE_CONTROL (0) +#define EPCTRL_EP_TYPE_ISO (1) +#define EPCTRL_EP_TYPE_BULK (2) +#define EPCTRL_EP_TYPE_INTERRUPT (3) +#define EPCTRL_TX_EP_TYPE_SHIFT (18) +#define EPCTRL_RX_EP_TYPE_SHIFT (2) + +/* SNOOPn Register Bit Masks */ +#define SNOOP_ADDRESS_MASK (0xFFFFF000) +#define SNOOP_SIZE_ZERO (0x00) /* snooping disable */ +#define SNOOP_SIZE_4KB (0x0B) /* 4KB snoop size */ +#define SNOOP_SIZE_8KB (0x0C) +#define SNOOP_SIZE_16KB (0x0D) +#define SNOOP_SIZE_32KB (0x0E) +#define SNOOP_SIZE_64KB (0x0F) +#define SNOOP_SIZE_128KB (0x10) +#define SNOOP_SIZE_256KB (0x11) +#define SNOOP_SIZE_512KB (0x12) +#define SNOOP_SIZE_1MB (0x13) +#define SNOOP_SIZE_2MB (0x14) +#define SNOOP_SIZE_4MB (0x15) +#define SNOOP_SIZE_8MB (0x16) +#define SNOOP_SIZE_16MB (0x17) +#define SNOOP_SIZE_32MB (0x18) +#define SNOOP_SIZE_64MB (0x19) +#define SNOOP_SIZE_128MB (0x1A) +#define SNOOP_SIZE_256MB (0x1B) +#define SNOOP_SIZE_512MB (0x1C) +#define SNOOP_SIZE_1GB (0x1D) +#define SNOOP_SIZE_2GB (0x1E) /* 2GB snoop size */ + +/* pri_ctrl Register Bit Masks */ +#define PRI_CTRL_PRI_LVL1 (0x0000000C) +#define PRI_CTRL_PRI_LVL0 (0x00000003) + +/* si_ctrl Register Bit Masks */ +#define SI_CTRL_ERR_DISABLE (0x00000010) +#define SI_CTRL_IDRC_DISABLE (0x00000008) +#define SI_CTRL_RD_SAFE_EN (0x00000004) +#define SI_CTRL_RD_PREFETCH_DISABLE (0x00000002) +#define SI_CTRL_RD_PREFEFETCH_VAL (0x00000001) + +/* control Register Bit Masks */ +#define USB_CTRL_IOENB (0x00000004) +#define USB_CTRL_ULPI_INT0EN (0x00000001) + +#endif /* __MX31_H */ diff --git a/firmware/target/arm/usb-pp.c b/firmware/target/arm/usb-pp.c index f8d0a836ad..983457b924 100644 --- a/firmware/target/arm/usb-pp.c +++ b/firmware/target/arm/usb-pp.c @@ -40,7 +40,8 @@ #include "hwcompat.h" #include "usb-target.h" - +#include "mx31.h" + void usb_init_device(void) { int r0; @@ -55,22 +56,25 @@ void usb_init_device(void) DEV_INIT |= INIT_USB; while ((inl(0x70000028) & 0x80) == 0); - UOG_PORTSC1 |= 0x100; - while ((UOG_PORTSC1 & 0x100) != 0); + UOG_PORTSC1 |= PORTSCX_PORT_RESET; + while ((UOG_PORTSC1 & PORTSCX_PORT_RESET) != 0); UOG_OTGSC |= 0x5F000000; if( (UOG_OTGSC & 0x100) == 0) { - UOG_USBMODE &=~ 0x3; - UOG_USBMODE |= 0x2; + UOG_USBMODE &=~ USB_MODE_CTRL_MODE_HOST; + UOG_USBMODE |= USB_MODE_CTRL_MODE_DEVICE; outl(inl(0x70000028) | 0x4000, 0x70000028); outl(inl(0x70000028) | 0x2, 0x70000028); } else { - UOG_USBMODE |= 0x2; + UOG_USBMODE |= USB_MODE_CTRL_MODE_DEVICE; outl(inl(0x70000028) &~0x4000, 0x70000028); outl(inl(0x70000028) | 0x2, 0x70000028); } - UOG_USBCMD |= 0x2; - while((UOG_USBCMD & 0x2) != 0); + + + UOG_USBCMD |= USB_CMD_CTRL_RESET; + while((UOG_USBCMD & USB_CMD_CTRL_RESET) != 0); + r0 = UOG_PORTSC1; /* Note from IPL source (referring to next 5 lines of code: @@ -116,9 +120,81 @@ void usb_enable(bool on) } } +/*------------------------------------------------------------------ + Internal Hardware related function + ------------------------------------------------------------------*/ + +/* @qh_addr is the aligned virt addr of ep QH addr + * it is used to set endpointlistaddr Reg */ +static int dr_controller_setup(void/* *qh_addr, struct device *dev*/) +{ + int timeout = 0; +/* struct arc_usb_config *config; + + config = udc_controller->config; +*/ + /* before here, make sure usb_slave_regs has been initialized */ +/* if (!qh_addr) + return -EINVAL; +*/ + /* Stop and reset the usb controller */ + UOG_USBCMD &= ~USB_CMD_RUN_STOP; + + UOG_USBCMD |= USB_CMD_CTRL_RESET; + + /* Wait for reset to complete */ + timeout = 10000000; + while ((UOG_USBCMD & USB_CMD_CTRL_RESET) && + --timeout) { + continue; + } + if (timeout == 0) { + //logf("%s: TIMEOUT", __FUNCTION__); + return 1; + } + + /* Set the controller as device mode and disable setup lockout */ + UOG_USBMODE |= (USB_MODE_CTRL_MODE_DEVICE | USB_MODE_SETUP_LOCK_OFF); + + /* Clear the setup status */ + UOG_USBSTS = 0; + +/* tmp = virt_to_phys(qh_addr); + tmp &= USB_EP_LIST_ADDRESS_MASK; + usb_slave_regs->endpointlistaddr = cpu_to_le32(tmp); +*/ + UOG_PORTSC1 = (UOG_PORTSC1 & ~PORTSCX_PHY_TYPE_SEL) | PORTSCX_PTS_UTMI; + +/* if (config->set_vbus_power) + config->set_vbus_power(0); +*/ + return 0; +} + +/* just Enable DR irq reg and Set Dr controller Run */ +static void dr_controller_run(void/*struct arcotg_udc *udc*/) +{ + /*Enable DR irq reg */ + UOG_USBINTR = USB_INTR_INT_EN | USB_INTR_ERR_INT_EN | + USB_INTR_PTC_DETECT_EN | USB_INTR_RESET_EN | + USB_INTR_DEVICE_SUSPEND | USB_INTR_SYS_ERR_EN; + + /* Clear stopped bit */ + /*udc->stopped = 0;*/ + + /* Set the controller as device mode */ + UOG_USBMODE |= USB_MODE_CTRL_MODE_DEVICE; + + /* Set controller to Run */ + UOG_USBCMD |= USB_CMD_RUN_STOP; + + return; +} + bool usb_detect(void) { - bool current_status; + static bool prev_usbstatus1 = false; + bool usbstatus1,usbstatus2; /* UOG_ID should have the bit format: [31:24] = 0x0 @@ -130,7 +206,18 @@ bool usb_detect(void) if (UOG_ID != 0x22FA05) { return false; } - current_status = (UOG_OTGSC & 0x800)?true:false; - - return current_status; + + usbstatus1 = (UOG_OTGSC & 0x800) ? true : false; + if ((usbstatus1 == true) && (prev_usbstatus1 == false)) { + dr_controller_setup(); + dr_controller_run(); + } + prev_usbstatus1 = usbstatus1; + usbstatus2 = (UOG_PORTSC1 & PORTSCX_CURRENT_CONNECT_STATUS) ? true : false; + + if (usbstatus1 && usbstatus2) { + return true; + } else { + return false; + } } diff --git a/firmware/target/arm/usb-target.h b/firmware/target/arm/usb-target.h index 2a5400be7e..ea6043d63e 100644 --- a/firmware/target/arm/usb-target.h +++ b/firmware/target/arm/usb-target.h @@ -19,110 +19,6 @@ #ifndef USB_TARGET_H #define USB_TARGET_H -/* The PortalPlayer USB controller is compatible with Freescale i.MX31 */ - -/* Register addresses */ -/* OTG */ -#define UOG_ID (*(volatile unsigned long *)(0xc5000000)) -#define UOG_HWGENERAL (*(volatile unsigned long *)(0xc5000004)) -#define UOG_HWHOST (*(volatile unsigned long *)(0xc5000008)) -#define UOG_HWTXBUF (*(volatile unsigned long *)(0xc5000010)) -#define UOG_HWRXBUF (*(volatile unsigned long *)(0xc5000014)) -#define UOG_CAPLENGTH (*(volatile unsigned char *)(0xc5000100)) -#define UOG_HCIVERSION (*(volatile unsigned short *)(0xc5000102)) -#define UOG_HCSPARAMS (*(volatile unsigned long *)(0xc5000104)) -#define UOG_HCCPARAMS (*(volatile unsigned long *)(0xc5000108)) -#define UOG_DCIVERSION (*(volatile unsigned short *)(0xc5000120)) -#define UOG_DCCPARAMS (*(volatile unsigned long *)(0xc5000124)) -#define UOG_USBCMD (*(volatile unsigned long *)(0xc5000140)) -#define UOG_USBSTS (*(volatile unsigned long *)(0xc5000144)) -#define UOG_USBINTR (*(volatile unsigned long *)(0xc5000148)) -#define UOG_FRINDEX (*(volatile unsigned long *)(0xc500014c)) -#define UOG_PERIODICLISTBASE (*(volatile unsigned long *)(0xc5000154)) -#define UOG_ASYNCLISTADDR (*(volatile unsigned long *)(0xc5000158)) -#define UOG_BURSTSIZE (*(volatile unsigned long *)(0xc5000160)) -#define UOG_TXFILLTUNING (*(volatile unsigned long *)(0xc5000164)) -#define UOG_ULPIVIEW (*(volatile unsigned long *)(0xc5000170)) -#define UOG_CFGFLAG (*(volatile unsigned long *)(0xc5000180)) -#define UOG_PORTSC1 (*(volatile unsigned long *)(0xc5000184)) -/*#define UOG_PORTSC2 (*(volatile unsigned long *)(0xc5000188)) -#define UOG_PORTSC3 (*(volatile unsigned long *)(0xc500018c)) -#define UOG_PORTSC4 (*(volatile unsigned long *)(0xc5000190)) -#define UOG_PORTSC5 (*(volatile unsigned long *)(0xc5000194)) -#define UOG_PORTSC6 (*(volatile unsigned long *)(0xc5000198)) -#define UOG_PORTSC7 (*(volatile unsigned long *)(0xc500019c)) -#define UOG_PORTSC8 (*(volatile unsigned long *)(0xc50001a0))*/ -#define UOG_OTGSC (*(volatile unsigned long *)(0xc50001a4)) -#define UOG_USBMODE (*(volatile unsigned long *)(0xc50001a8)) -#define UOG_ENDPTSETUPSTAT (*(volatile unsigned long *)(0xc50001ac)) -#define UOG_ENDPTPRIME (*(volatile unsigned long *)(0xc50001b0)) -#define UOG_ENDPTFLUSH (*(volatile unsigned long *)(0xc50001b4)) -#define UOG_ENDPTSTAT (*(volatile unsigned long *)(0xc50001b8)) -#define UOG_ENDPTCOMPLETE (*(volatile unsigned long *)(0xc50001bc)) -#define ENDPTCRTL0 (*(volatile unsigned long *)(0xc50001c0)) -#define ENDPTCRTL1 (*(volatile unsigned long *)(0xc50001c4)) -#define ENDPTCRTL2 (*(volatile unsigned long *)(0xc50001c8)) -#define ENDPTCRTL3 (*(volatile unsigned long *)(0xc50001cc)) -#define ENDPTCRTL4 (*(volatile unsigned long *)(0xc50001d0)) -#define ENDPTCRTL5 (*(volatile unsigned long *)(0xc50001d4)) -#define ENDPTCRTL6 (*(volatile unsigned long *)(0xc50001d8)) -#define ENDPTCRTL7 (*(volatile unsigned long *)(0xc50001dc)) -/*#define ENDPTCRTL8 (*(volatile unsigned long *)(0xc50001e0)) -#define ENDPTCRTL9 (*(volatile unsigned long *)(0xc50001e4)) -#define ENDPTCRTL10 (*(volatile unsigned long *)(0xc50001e8)) -#define ENDPTCRTL11 (*(volatile unsigned long *)(0xc50001ec)) -#define ENDPTCRTL12 (*(volatile unsigned long *)(0xc50001f0)) -#define ENDPTCRTL13 (*(volatile unsigned long *)(0xc50001f4)) -#define ENDPTCRTL14 (*(volatile unsigned long *)(0xc50001f8)) -#define ENDPTCRTL15 (*(volatile unsigned long *)(0xc50001fc))*/ - -/* Host 1 */ -#define UH1_ID (*(volatile unsigned long *)(0xc5000200)) -#define UH1_HWGENERAL (*(volatile unsigned long *)(0xc5000204)) -#define UH1_HWHOST (*(volatile unsigned long *)(0xc5000208)) -#define UH1_HWTXBUF (*(volatile unsigned long *)(0xc5000210)) -#define UH1_HWRXBUF (*(volatile unsigned long *)(0xc5000214)) -#define UH1_CAPLENGTH (*(volatile unsigned long *)(0xc5000300)) -#define UH1_HCIVERSION (*(volatile unsigned long *)(0xc5000302)) -#define UH1_HCSPARAMS (*(volatile unsigned long *)(0xc5000304)) -#define UH1_HCCPARAMS (*(volatile unsigned long *)(0xc5000308)) -#define UH1_USBCMD (*(volatile unsigned long *)(0xc5000340)) -#define UH1_USBSTS (*(volatile unsigned long *)(0xc5000344)) -#define UH1_USBINTR (*(volatile unsigned long *)(0xc5000348)) -#define UH1_FRINDEX (*(volatile unsigned long *)(0xc500034c)) -#define UH1_PERIODICLISTBASE (*(volatile unsigned long *)(0xc5000354)) -#define UH1_ASYNCLISTADDR (*(volatile unsigned long *)(0xc5000358)) -#define UH1_BURSTSIZE (*(volatile unsigned long *)(0xc5000360)) -#define UH1_TXFILLTUNING (*(volatile unsigned long *)(0xc5000364)) -#define UH1_PORTSC1 (*(volatile unsigned long *)(0xc5000384)) -#define UH1_USBMODE (*(volatile unsigned long *)(0xc50003a8)) - -/* Host 2 */ -#define UH2_ID (*(volatile unsigned long *)(0xc5000400)) -#define UH2_HWGENERAL (*(volatile unsigned long *)(0xc5000404)) -#define UH2_HWHOST (*(volatile unsigned long *)(0xc5000408)) -#define UH2_HWTXBUF (*(volatile unsigned long *)(0xc5000410)) -#define UH2_HWRXBUF (*(volatile unsigned long *)(0xc5000414)) -#define UH2_CAPLENGTH (*(volatile unsigned long *)(0xc5000500)) -#define UH2_HCIVERSION (*(volatile unsigned long *)(0xc5000502)) -#define UH2_HCSPARAMS (*(volatile unsigned long *)(0xc5000504)) -#define UH2_HCCPARAMS (*(volatile unsigned long *)(0xc5000508)) -#define UH2_USBCMD (*(volatile unsigned long *)(0xc5000540)) -#define UH2_USBSTS (*(volatile unsigned long *)(0xc5000544)) -#define UH2_USBINTR (*(volatile unsigned long *)(0xc5000548)) -#define UH2_FRINDEX (*(volatile unsigned long *)(0xc500054c)) -#define UH2_PERIODICLISTBASE (*(volatile unsigned long *)(0xc5000554)) -#define UH2_ASYNCLISTADDR (*(volatile unsigned long *)(0xc5000558)) -#define UH2_BURSTSIZE (*(volatile unsigned long *)(0xc5000560)) -#define UH2_TXFILLTUNING (*(volatile unsigned long *)(0xc5000564)) -#define UH2_ULPIVIEW (*(volatile unsigned long *)(0xc5000570)) -#define UH2_PORTSC1 (*(volatile unsigned long *)(0xc5000584)) -#define UH2_USBMODE (*(volatile unsigned long *)(0xc50005a8)) - -/* General */ -#define USB_CTRL (*(volatile unsigned long *)(0xc5000600)) -#define USB_OTG_MIRROR (*(volatile unsigned long *)(0xc5000604)) - void usb_init_device(void); #endif