参考http://www.arm9home.net/read.php?tid-80476.html
http://www.arm9home.net/read.php?tid-25944.html
https://github.com/kangear/tiny210v2-uboot
4412的u-boot:
https://github.com/friendlyarm/uboot_tiny4412
cmd_usbd.c :
-
/*
-
* common/cmd_usbd.c
-
*
-
* $Id: cmd_usbd.c,v 1.2 2009/01/28 00:11:42 dark0351 Exp $
-
*
-
* (C) Copyright 2007
-
* Byungjae Lee, Samsung Erectronics, bjlee@samsung.com.
-
* - support for S3C2412, S3C2443 and S3C6400
-
*
-
* (C) Copyright SAMSUNG Electronics
-
* SW.LEE <hitchcar@samsung.com>
-
* - add USB device fo S3C2440A, S3C24A0A
-
*
-
* (C) Copyright 2000
-
* Wolfgang Denk, DENX Software Engineering, wd@denx.de.
-
*
-
* See file CREDITS for list of people who contributed to this
-
* project.
-
*
-
* This program is free software; you can redistribute it and/or
-
* modify it under the terms of the GNU General Public License as
-
* published by the Free Software Foundation; either version 2 of
-
* the License, or (at your option) any later version.
-
*/
-
-
/*
-
* Memory Functions
-
*
-
* Copied from FADS ROM, Dan Malek (dmalek@jlc.net)
-
*/
-
-
#include <common.h>
-
#include <command.h>
-
-
#ifdef CONFIG_S3C_USBD
-
-
#include <regs.h>
-
-
#if defined(CONFIG_S3C2412) || defined(CONFIG_S3C2442)
-
#include "../cpu/s3c24xx/usbd-fs.h"
-
#elif defined(CONFIG_S3C2443) || defined(CONFIG_S3C2450) || defined(CONFIG_S3C2416)
-
#include "../cpu/s3c24xx/usbd-hs.h"
-
#elif defined(CONFIG_S3C6400) || defined(CONFIG_S3C6410) || defined(CONFIG_S3C6430)
-
#include "../cpu/s3c64xx/usbd-otg-hs.h"
-
#elif defined(CONFIG_S5PC100)
-
#include "../cpu/s5pc1xx/usbd-otg-hs.h"
-
#elif defined(CONFIG_S5PC110)
-
#include "../cpu/s5pc11x/usbd-otg-hs.h"
-
#elif defined(CONFIG_S5P6440)
-
#include "../cpu/s5p64xx/usbd-otg-hs.h"
-
#elif defined(CONFIG_S5P6442)
-
#include "../cpu/s5p644x/usbd-otg-hs.h"
-
#else
-
#error "* CFG_ERROR : you have to setup right Samsung CPU configuration"
-
#endif
-
-
#undef CMD_USBD_DEBUG
-
#ifdef CMD_USBD_DEBUG
-
#define PRINTF(fmt,args...) printf (fmt ,##args)
-
#else
-
#define PRINTF(fmt,args...)
-
#endif
-
-
static const char pszMe[] = "usbd: ";
-
-
int do_usbd_dnw ( cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
-
{
-
-
if (argv[0][0] == 'u') {
-
DNW = 0;
-
}
-
else {
-
DNW = 1;
-
s3c_got_header = 0;
-
}
-
-
switch (argc) {
-
case 1 :
-
s3c_usbd_dn_addr = USBD_DOWN_ADDR; /* Default Address */
-
break;
-
case 2 :
-
s3c_usbd_dn_addr = simple_strtoul(argv[1], NULL, 16);
-
break;
-
default:
-
printf ("Usage:\n%s\n", cmdtp->usage);
-
return 1;
-
}
-
-
s3c_receive_done = 0;
-
-
s3c_usbctl_init(0);
-
s3c_usbc_activate();
-
-
PRINTF("Download address 0x%08x\n", s3c_usbd_dn_addr);
-
printf("Now, Waiting for DNW to transmit data\n");
-
-
while (1) {
-
if (S3C_USBD_DETECT_IRQ()) {
-
s3c_udc_int_hndlr();
-
S3C_USBD_CLEAR_IRQ();
-
}
-
-
if (s3c_receive_done)
-
break;
-
-
if (serial_tstc()) {
-
serial_getc();
-
break;
-
}
-
}
-
-
/* when operation is done, usbd must be stopped */
-
s3c_usb_stop();
-
-
return 0;
-
}
-
-
#if 0 /* ud command not support yet */
-
U_BOOT_CMD(
-
ud, 3, 0, do_usbd_dnw,
-
"ud - initialize USB device and ready to receive for LINUX server (specific)\n",
-
"[download address]\n"
-
);
-
#endif
-
-
U_BOOT_CMD(
-
dnw, 3, 0, do_usbd_dnw,
-
"dnw - initialize USB device and ready to receive for Windows server (specific)\n",
-
"[download address]\n"
-
);
-
-
#endif /* CONFIG_S3C_USBD */
Usbd-otg-hs.c (cpu\s5pc11x)
-
/*
-
* cpu/s5pc1xx/usbd-otg-hs.c
-
*
-
* (C) Copyright 2007
-
* Byungjae Lee, Samsung Erectronics, bjlee@samsung.com.
-
* - only support for S5PC100
-
*
-
* This program is free software; you can redistribute it and/or
-
* modify it under the terms of the GNU General Public License as
-
* published by the Free Software Foundation; either version 2 of
-
* the License, or (at your option) any later version.
-
*
-
* This program is distributed in the hope that it will be useful,
-
* but WITHOUT ANY WARRANTY; without even the implied warranty of
-
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-
* GNU General Public License for more details.
-
*
-
* You should have received a copy of the GNU General Public License
-
* along with this program; if not, write to the Free Software
-
* Foundation, Inc., 59 Temple Place, Suite 330, Boston,
-
* MA 02111-1307 USA
-
*/
-
-
#include <common.h>
-
-
#if defined(CONFIG_S5PC110)
-
#include <command.h>
-
#include <asm/errno.h>
-
#include <asm/io.h>
-
#include <regs.h>
-
#include "usbd-otg-hs.h"
-
-
#undef USB_OTG_DEBUG_SETUP
-
#ifdef USB_OTG_DEBUG_SETUP
-
#define DBG_SETUP0(fmt, args...) printf("[%s:%d] " fmt, __FUNCTION__, __LINE__, ##args)
-
#define DBG_SETUP1(fmt, args...) printf("\t" fmt, ##args)
-
#define DBG_SETUP2(fmt, args...) printf(fmt, ##args)
-
#else
-
#define DBG_SETUP0(fmt, args...) do { } while (0)
-
#define DBG_SETUP1(fmt, args...) do { } while (0)
-
#define DBG_SETUP2(fmt, args...) do { } while (0)
-
#endif
-
-
#undef USB_OTG_DEBUG_BULK
-
#ifdef USB_OTG_DEBUG_BULK
-
#define DBG_BULK0(fmt, args...) printf("[%s:%d] " fmt, __FUNCTION__, __LINE__, ##args)
-
#define DBG_BULK1(fmt, args...) printf("\t" fmt, ##args)
-
#else
-
#define DBG_BULK0(fmt, args...) do { } while (0)
-
#define DBG_BULK1(fmt, args...) do { } while (0)
-
#endif
-
-
#define USB_CHECKSUM_EN
-
-
#define TRUE 1
-
#define FALSE 0
-
#define SUSPEND_RESUME_ON FALSE
-
-
u32 s3c_usbd_dn_addr = 0;
-
u32 s3c_usbd_dn_cnt = 0;
-
u32 remode_wakeup;
-
u16 config_value;
-
-
int DNW;
-
int s3c_receive_done = 0;
-
int s3c_got_header = 0;
-
int s3c_usb_phy_inited=0;
-
int s3c_usb_connected_status= 0;/*0,none,1,usb connected,2,power connected,3,bad usb connected*/
-
USB_OPMODE op_mode = USB_CPU;
-
USB_SPEED speed = USB_HIGH;
-
-
otg_dev_t otg;
-
get_status_t get_status;
-
get_intf_t get_intf;
-
-
enum EP_INDEX
-
{
-
EP0, EP1, EP2, EP3, EP4
-
};
-
-
/*------------------------------------------------*/
-
/* EP0 state */
-
enum EP0_STATE
-
{
-
EP0_STATE_INIT = 0,
-
EP0_STATE_GD_DEV_0 = 11,
-
EP0_STATE_GD_DEV_1 = 12,
-
EP0_STATE_GD_DEV_2 = 13,
-
EP0_STATE_GD_CFG_0 = 21,
-
EP0_STATE_GD_CFG_1 = 22,
-
EP0_STATE_GD_CFG_2 = 23,
-
EP0_STATE_GD_CFG_3 = 24,
-
EP0_STATE_GD_CFG_4 = 25,
-
EP0_STATE_GD_STR_I0 = 30,
-
EP0_STATE_GD_STR_I1 = 31,
-
EP0_STATE_GD_STR_I2 = 32,
-
EP0_STATE_GD_DEV_QUALIFIER = 33,
-
EP0_STATE_INTERFACE_GET = 34,
-
EP0_STATE_GET_STATUS0 = 35,
-
EP0_STATE_GET_STATUS1 = 36,
-
EP0_STATE_GET_STATUS2 = 37,
-
EP0_STATE_GET_STATUS3 = 38,
-
EP0_STATE_GET_STATUS4 = 39,
-
EP0_STATE_GD_OTHER_SPEED = 40,
-
EP0_STATE_GD_CFG_ONLY_0 = 41,
-
EP0_STATE_GD_CFG_ONLY_1 = 42,
-
EP0_STATE_GD_IF_ONLY_0 = 44,
-
EP0_STATE_GD_IF_ONLY_1 = 45,
-
EP0_STATE_GD_EP0_ONLY_0 = 46,
-
EP0_STATE_GD_EP1_ONLY_0 = 47,
-
EP0_STATE_GD_EP2_ONLY_0 = 48,
-
EP0_STATE_GD_EP3_ONLY_0 = 49,
-
EP0_STATE_GD_OTHER_SPEED_HIGH_1 = 51,
-
EP0_STATE_GD_OTHER_SPEED_HIGH_2 = 52,
-
EP0_STATE_GD_OTHER_SPEED_HIGH_3 = 53
-
};
-
-
/*definitions related to CSR setting */
-
-
/* S5P_OTG_GOTGCTL*/
-
#define B_SESSION_VALID (0x1<<19)
-
#define A_SESSION_VALID (0x1<<18)
-
-
/* S5P_OTG_GAHBCFG*/
-
#define PTXFE_HALF (0<<8)
-
#define PTXFE_ZERO (1<<8)
-
#define NPTXFE_HALF (0<<7)
-
#define NPTXFE_ZERO (1<<7)
-
#define MODE_SLAVE (0<<5)
-
#define MODE_DMA (1<<5)
-
#define BURST_SINGLE (0<<1)
-
#define BURST_INCR (1<<1)
-
#define BURST_INCR4 (3<<1)
-
#define BURST_INCR8 (5<<1)
-
#define BURST_INCR16 (7<<1)
-
#define GBL_INT_UNMASK (1<<0)
-
#define GBL_INT_MASK (0<<0)
-
-
/* S5P_OTG_GRSTCTL*/
-
#define AHB_MASTER_IDLE (1u<<31)
-
#define CORE_SOFT_RESET (0x1<<0)
-
-
/* S5P_OTG_GINTSTS/S5P_OTG_GINTMSK core interrupt register */
-
#define INT_RESUME (1u<<31)
-
#define INT_DISCONN (0x1<<29)
-
#define INT_CONN_ID_STS_CNG (0x1<<28)
-
#define INT_OUT_EP (0x1<<19)
-
#define INT_IN_EP (0x1<<18)
-
#define INT_ENUMDONE (0x1<<13)
-
#define INT_RESET (0x1<<12)
-
#define INT_SUSPEND (0x1<<11)
-
#define INT_TX_FIFO_EMPTY (0x1<<5)
-
#define INT_RX_FIFO_NOT_EMPTY (0x1<<4)
-
#define INT_SOF (0x1<<3)
-
#define INT_DEV_MODE (0x0<<0)
-
#define INT_HOST_MODE (0x1<<1)
-
-
/* S5P_OTG_GRXSTSP STATUS*/
-
#define GLOBAL_OUT_NAK (0x1<<17)
-
#define OUT_PKT_RECEIVED (0x2<<17)
-
#define OUT_TRNASFER_COMPLETED (0x3<<17)
-
#define SETUP_TRANSACTION_COMPLETED (0x4<<17)
-
#define SETUP_PKT_RECEIVED (0x6<<17)
-
-
/* S5P_OTG_DCTL device control register */
-
#define NORMAL_OPERATION (0x1<<0)
-
#define SOFT_DISCONNECT (0x1<<1)
-
#define TEST_J_MODE (TEST_J<<4)
-
#define TEST_K_MODE (TEST_K<<4)
-
#define TEST_SE0_NAK_MODE (TEST_SE0_NAK<<4)
-
#define TEST_PACKET_MODE (TEST_PACKET<<4)
-
#define TEST_FORCE_ENABLE_MODE (TEST_FORCE_ENABLE<<4)
-
#define TEST_CONTROL_FIELD (0x7<<4)
-
-
/* S5P_OTG_DAINT device all endpoint interrupt register */
-
#define INT_IN_EP0 (0x1<<0)
-
#define INT_IN_EP1 (0x1<<1)
-
#define INT_IN_EP3 (0x1<<3)
-
#define INT_OUT_EP0 (0x1<<16)
-
#define INT_OUT_EP2 (0x1<<18)
-
#define INT_OUT_EP4 (0x1<<20)
-
-
/* S5P_OTG_DIEPCTL0/S5P_OTG_DOEPCTL0 */
-
#define DEPCTL_EPENA (0x1<<31)
-
#define DEPCTL_EPDIS (0x1<<30)
-
#define DEPCTL_SNAK (0x1<<27)
-
#define DEPCTL_CNAK (0x1<<26)
-
#define DEPCTL_CTRL_TYPE (EP_TYPE_CONTROL<<18)
-
#define DEPCTL_ISO_TYPE (EP_TYPE_ISOCHRONOUS<<18)
-
#define DEPCTL_BULK_TYPE (EP_TYPE_BULK<<18)
-
#define DEPCTL_INTR_TYPE (EP_TYPE_INTERRUPT<<18)
-
#define DEPCTL_USBACTEP (0x1<<15)
-
-
/*ep0 enable, clear nak, next ep0, max 64byte */
-
#define EPEN_CNAK_EP0_64 (DEPCTL_EPENA|DEPCTL_CNAK|(CONTROL_EP<<11)|(0<<0))
-
-
/*ep0 enable, clear nak, next ep0, 8byte */
-
#define EPEN_CNAK_EP0_8 (DEPCTL_EPENA|DEPCTL_CNAK|(CONTROL_EP<<11)|(3<<0))
-
-
/* DIEPCTLn/DOEPCTLn */
-
#define BACK2BACK_SETUP_RECEIVED (0x1<<6)
-
#define INTKN_TXFEMP (0x1<<4)
-
#define NON_ISO_IN_EP_TIMEOUT (0x1<<3)
-
#define CTRL_OUT_EP_SETUP_PHASE_DONE (0x1<<3)
-
#define AHB_ERROR (0x1<<2)
-
#define TRANSFER_DONE (0x1<<0)
-
-
-
/* codes representing languages */
-
const u8 string_desc0[] =
-
{
-
4, STRING_DESCRIPTOR, LANGID_US_L, LANGID_US_H,
-
};
-
-
const u8 string_desc1[] = /* Manufacturer */
-
{
-
(0x14+2), STRING_DESCRIPTOR,
-
'S', 0x0, 'y', 0x0, 's', 0x0, 't', 0x0, 'e', 0x0,
-
'm', 0x0, ' ', 0x0, 'M', 0x0, 'C', 0x0, 'U', 0x0,
-
};
-
-
const u8 string_desc2[] = /* Product */
-
{
-
(0x2a+2), STRING_DESCRIPTOR,
-
'S', 0x0, 'E', 0x0, 'C', 0x0, ' ', 0x0, 'S', 0x0,
-
'3', 0x0, 'C', 0x0, '6', 0x0, '4', 0x0, '0', 0x0,
-
'0', 0x0, 'X', 0x0, ' ', 0x0, 'T', 0x0, 'e', 0x0,
-
's', 0x0, 't', 0x0, ' ', 0x0, 'B', 0x0, '/', 0x0,
-
'D', 0x0
-
};
-
-
/* setting the device qualifier descriptor and a string descriptor */
-
const u8 qualifier_desc[] =
-
{
-
0x0a, /* 0 desc size */
-
0x06, /* 1 desc type (DEVICE_QUALIFIER)*/
-
0x00, /* 2 USB release */
-
0x02, /* 3 => 2.00*/
-
0xFF, /* 4 class */
-
0x00, /* 5 subclass */
-
0x00, /* 6 protocol */
-
64, /* 7 max pack size */
-
0x01, /* 8 number of other-speed configuration */
-
0x00, /* 9 reserved */
-
};
-
-
const u8 config_full[] =
-
{
-
0x09, /* 0 desc size */
-
0x07, /* 1 desc type (other speed)*/
-
0x20, /* 2 Total length of data returned */
-
0x00, /* 3 */
-
0x01, /* 4 Number of interfaces supported by this speed configuration */
-
0x01, /* 5 value to use to select configuration */
-
0x00, /* 6 index of string desc */
-
/* 7 same as configuration desc */
-
CONF_ATTR_DEFAULT|CONF_ATTR_SELFPOWERED,
-
0x19, /* 8 same as configuration desc */
-
-
};
-
-
const u8 config_full_total[] =
-
{
-
0x09, 0x07 ,0x20 ,0x00 ,0x01 ,0x01 ,0x00 ,0xC0 ,0x19,
-
0x09 ,0x04 ,0x00 ,0x00 ,0x02 ,0xff ,0x00 ,0x00 ,0x00,
-
0x07 ,0x05 ,0x83 ,0x02 ,0x40 ,0x00 ,0x00,
-
0x07 ,0x05 ,0x04 ,0x02 ,0x40 ,0x00 ,0x00
-
};
-
-
const u8 config_high[] =
-
{
-
0x09, /* 0 desc size */
-
0x07, /* 1 desc type (other speed)*/
-
0x20, /* 2 Total length of data returned */
-
0x00, /* 3 */
-
0x01, /* 4 Number of interfaces supported by this speed configuration */
-
0x01, /* 5 value to use to select configuration */
-
0x00, /* 6 index of string desc */
-
/* 7 same as configuration desc */
-
CONF_ATTR_DEFAULT|CONF_ATTR_SELFPOWERED,
-
0x19, /* 8 same as configuration desc */
-
-
};
-
-
const u8 config_high_total[] =
-
{
-
0x09, 0x07 ,0x20 ,0x00 ,0x01 ,0x01 ,0x00 ,0xC0 ,0x19,
-
0x09 ,0x04 ,0x00 ,0x00 ,0x02 ,0xff ,0x00 ,0x00 ,0x00,
-
0x07 ,0x05 ,0x81 ,0x02 ,0x00 ,0x02 ,0x00,
-
0x07 ,0x05 ,0x02 ,0x02 ,0x00 ,0x02 ,0x00
-
};
-
-
/* Descriptor size */
-
enum DESCRIPTOR_SIZE
-
{
-
DEVICE_DESC_SIZE = sizeof(device_desc_t),
-
STRING_DESC0_SIZE = sizeof(string_desc0),
-
STRING_DESC1_SIZE = sizeof(string_desc1),
-
STRING_DESC2_SIZE = sizeof(string_desc2),
-
CONFIG_DESC_SIZE = sizeof(config_desc_t),
-
INTERFACE_DESC_SIZE = sizeof(intf_desc_t),
-
ENDPOINT_DESC_SIZE = sizeof(ep_desc_t),
-
DEVICE_QUALIFIER_SIZE = sizeof(qualifier_desc),
-
OTHER_SPEED_CFG_SIZE = 9
-
-
};
-
-
/*32 <cfg desc>+<if desc>+<endp0 desc>+<endp1 desc>*/
-
#define CONFIG_DESC_TOTAL_SIZE \
-
(CONFIG_DESC_SIZE+INTERFACE_DESC_SIZE+ENDPOINT_DESC_SIZE*2)
-
#define TEST_PKT_SIZE 53
-
-
u8 test_pkt [TEST_PKT_SIZE] = {
-
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, /*JKJKJKJK x 9*/
-
0xAA,0xAA,0xAA,0xAA,0xAA,0xAA,0xAA,0xAA, /*JJKKJJKK x 8*/
-
0xEE,0xEE,0xEE,0xEE,0xEE,0xEE,0xEE,0xEE, /*JJJJKKKK x 8*/
-
0xFE,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF, /*JJJJJJJKKKKKKK x8 - '1'*/
-
0x7F,0xBF,0xDF,0xEF,0xF7,0xFB,0xFD, /*'1' + JJJJJJJK x 8*/
-
0xFC,0x7E,0xBF,0xDF,0xEF,0xF7,0xFB,0xFD,0x7E /*{JKKKKKKK x 10},JK*/
-
};
-
-
void s3c_usb_init_phy(void)
-
{
-
writel(readl(USB_PHY_CONTROL)|(1<<0), USB_PHY_CONTROL); /*USB PHY0 Enable */
-
-
writel(0xa0, S5P_OTG_PHYPWR);
-
writel(0x3, S5P_OTG_PHYCLK);
-
writel(0x1, S5P_OTG_RSTCON);
-
udelay(10);
-
writel(0x0, S5P_OTG_RSTCON);
-
udelay(10);
-
-
}
-
-
/* OTG PHY Power Off */
-
void s3c_usb_phy_off(void) {
-
writel(readl(S5P_OTG_PHYPWR)|(0x18), S5P_OTG_PHYPWR);
-
writel(readl(USB_PHY_CONTROL)&~(1<<0), USB_PHY_CONTROL);
-
s3c_usb_phy_inited=0;
-
}
-
-
void s3c_usb_core_soft_reset(void)
-
{
-
u32 tmp;
-
-
writel(CORE_SOFT_RESET, S5P_OTG_GRSTCTL);
-
-
do
-
{
-
tmp = readl(S5P_OTG_GRSTCTL);
-
}while(!(tmp & AHB_MASTER_IDLE));
-
-
}
-
-
void s3c_usb_wait_cable_insert(void)
-
{
-
u32 tmp;
-
int ucFirst=1;
-
-
do {
-
udelay(50);
-
-
tmp = readl(S5P_OTG_GOTGCTL);
-
-
if (tmp & (B_SESSION_VALID|A_SESSION_VALID)) {
-
printf("OTG cable Connected!\n");
-
break;
-
} else if(ucFirst == 1) {
-
printf("Insert a OTG cable into the connector!\n");
-
ucFirst = 0;
-
}
-
} while(1);
-
}
-
-
void s3c_usb_init_core(void)
-
{
-
writel(PTXFE_HALF|NPTXFE_HALF|MODE_SLAVE|BURST_SINGLE|GBL_INT_UNMASK,
-
S5P_OTG_GAHBCFG);
-
-
writel( 0<<15 /* PHY Low Power Clock sel */
-
|1<<14 /* Non-Periodic TxFIFO Rewind Enable */
-
|0x5<<10 /* Turnaround time */
-
|0<<9 /* 0:HNP disable, 1:HNP enable */
-
|0<<8 /* 0:SRP disable, 1:SRP enable */
-
|0<<7 /* ULPI DDR sel */
-
|0<<6 /* 0: high speed utmi+, 1: full speed serial */
-
|0<<4 /* 0: utmi+, 1:ulpi */
-
|1<<3 /* phy i/f 0:8bit, 1:16bit */
-
|0x7<<0, /* HS/FS Timeout**/
-
S5P_OTG_GUSBCFG );
-
}
-
-
void s3c_usb_check_current_mode(u8 *pucMode)
-
{
-
u32 tmp;
-
-
tmp = readl(S5P_OTG_GINTSTS);
-
*pucMode = tmp & 0x1;
-
}
-
-
void s3c_usb_set_soft_disconnect(void)
-
{
-
u32 tmp;
-
-
tmp = readl(S5P_OTG_DCTL);
-
tmp |= SOFT_DISCONNECT;
-
writel(tmp, S5P_OTG_DCTL);
-
}
-
-
void s3c_usb_clear_soft_disconnect(void)
-
{
-
u32 tmp;
-
-
tmp = readl(S5P_OTG_DCTL);
-
tmp &= ~SOFT_DISCONNECT;
-
writel(tmp, S5P_OTG_DCTL);
-
}
-
-
void s3c_usb_init_device(void)
-
{
-
writel(1<<18|otg.speed<<0, S5P_OTG_DCFG); /* [][1: full speed(30Mhz) 0:high speed]*/
-
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|
-
INT_RESET|INT_SUSPEND|INT_RX_FIFO_NOT_EMPTY,
-
S5P_OTG_GINTMSK); /*gint unmask */
-
s3c_usb_phy_inited=1;
-
}
-
-
int s3c_usbctl_init(int ischeckstatus)/*diog, if not for check status, donot need wait cable insert*/
-
{
-
u8 ucMode;
-
-
DBG_SETUP0("USB Control Init\n");
-
-
otg.speed = speed;
-
otg.set_config = 0;
-
otg.ep0_state = EP0_STATE_INIT;
-
otg.ep0_substate = 0;
-
s3c_usb_init_phy();
-
s3c_usb_core_soft_reset();
-
if(!ischeckstatus)
-
s3c_usb_wait_cable_insert();
-
s3c_usb_init_core();
-
s3c_usb_check_current_mode(&ucMode);
-
-
if (ucMode == INT_DEV_MODE) {
-
s3c_usb_set_soft_disconnect();
-
udelay(10);
-
s3c_usb_clear_soft_disconnect();
-
s3c_usb_init_device();
-
return 0;
-
} else {
-
printf("Error : Current Mode is Host\n");
-
return 0;
-
}
-
}
-
-
int s3c_usbc_activate (void)
-
{
-
/* dont used in usb high speed, but used in common file cmd_usbd.c */
-
return 0;
-
}
-
-
int s3c_usb_stop (void)
-
{
-
/* dont used in usb high speed, but used in common file cmd_usbd.c */
-
s3c_usb_core_soft_reset();
-
s3c_usb_phy_off();
-
return 0;
-
}
-
-
void s3c_usb_print_pkt(u8 *pt, u8 count)
-
{
-
int i;
-
printf("[s3c_usb_print_pkt:");
-
-
for(i=0;i<count;i++)
-
printf("%x,", pt[i]);
-
-
printf("]\n");
-
}
-
-
void s3c_usb_verify_checksum(void)
-
{
-
u8 *cs_start, *cs_end;
-
u16 dnCS;
-
u16 checkSum;
-
-
printf("Checksum is being calculated.");
-
-
/* checksum calculation */
-
cs_start = (u8*)otg.dn_addr;
-
cs_end = (u8*)(otg.dn_addr+otg.dn_filesize-10);
-
checkSum = 0;
-
while(cs_start < cs_end) {
-
checkSum += *cs_start++;
-
if(((u32)cs_start&0xfffff)==0) printf(".");
-
}
-
-
/* fixed alignment fault in case when cs_end is odd. */
-
dnCS = (u16)((cs_end[1]<<8) + cs_end[0]);
-
//dnCS = *(u16 *)cs_end;
-
-
if (checkSum == dnCS)
-
{
-
printf("\nChecksum O.K.\n");
-
}
-
else
-
{
-
printf("\nChecksum Value => MEM:%x DNW:%x\n",checkSum,dnCS);
-
printf("Checksum failed.\n\n");
-
}
-
-
}
-
-
void s3c_usb_set_inep_xfersize(EP_TYPE type, u32 pktcnt, u32 xfersize)
-
{
-
if(type == EP_TYPE_CONTROL)
-
{
-
writel((pktcnt<<19)|(xfersize<<0), S5P_OTG_DIEPTSIZ0);
-
}
-
else if(type == EP_TYPE_BULK)
-
{
-
writel((1<<29)|(pktcnt<<19)|(xfersize<<0), S5P_OTG_DIEPTSIZ_IN);
-
}
-
}
-
-
void s3c_usb_set_outep_xfersize(EP_TYPE type, u32 pktcnt, u32 xfersize)
-
{
-
if(type == EP_TYPE_CONTROL)
-
{
-
writel((1<<29)|(pktcnt<<19)|(xfersize<<0), S5P_OTG_DOEPTSIZ0);
-
}
-
else if(type == EP_TYPE_BULK)
-
{
-
writel((pktcnt<<19)|(xfersize<<0), S5P_OTG_DOEPTSIZ_OUT);
-
}
-
}
-
-
void s3c_usb_write_ep0_fifo(u8 *buf, int num)
-
{
-
int i;
-
u32 Wr_Data=0;
-
-
DBG_SETUP1("[s3c_usb_write_ep0_fifo:");
-
-
for(i=0;i<num;i+=4)
-
{
-
Wr_Data = ((*(buf+3))<<24)|((*(buf+2))<<16)|((*(buf+1))<<8)|*buf;
-
DBG_SETUP2(" 0x%08x,", Wr_Data);
-
writel(Wr_Data, S5P_OTG_EP0_FIFO);
-
buf += 4;
-
}
-
-
DBG_SETUP2("]\n");
-
}
-
-
-
void s3c_usb_write_in_fifo(u8 *buf, int num)
-
{
-
int i;
-
u32 data=0;
-
-
for(i=0;i<num;i+=4)
-
{
-
data=((*(buf+3))<<24)|((*(buf+2))<<16)|((*(buf+1))<<8)|*buf;
-
writel(data, S5P_OTG_IN_FIFO);
-
buf += 4;
-
}
-
}
-
-
void s3c_usb_read_out_fifo(u8 *buf, int num)
-
{
-
int i;
-
u32 data;
-
-
for (i=0;i<num;i+=4)
-
{
-
data = readl(S5P_OTG_OUT_FIFO);
-
-
buf[i] = (u8)data;
-
buf[i+1] = (u8)(data>>8);
-
buf[i+2] = (u8)(data>>16);
-
buf[i+3] = (u8)(data>>24);
-
}
-
}
-
-
void s3c_usb_get_desc(void)
-
{
-
switch (otg.dev_req.wValue_H) {
-
case DEVICE_DESCRIPTOR:
-
otg.req_length = (u32)((otg.dev_req.wLength_H << 8) |
-
otg.dev_req.wLength_L);
-
DBG_SETUP1("DEVICE_DESCRIPTOR = 0x%x \n",otg.req_length);
-
otg.ep0_state = EP0_STATE_GD_DEV_0;
-
break;
-
-
case CONFIGURATION_DESCRIPTOR:
-
otg.req_length = (u32)((otg.dev_req.wLength_H << 8) |
-
otg.dev_req.wLength_L);
-
DBG_SETUP1("CONFIGURATION_DESCRIPTOR = 0x%x \n",otg.req_length);
-
-
/* GET_DESCRIPTOR:CONFIGURATION+INTERFACE+ENDPOINT0+ENDPOINT1 */
-
if (otg.req_length > CONFIG_DESC_SIZE){
-
otg.ep0_state = EP0_STATE_GD_CFG_0;
-
} else
-
otg.ep0_state = EP0_STATE_GD_CFG_ONLY_0;
-
break;
-
-
case STRING_DESCRIPTOR :
-
DBG_SETUP1("STRING_DESCRIPTOR \n");
-
-
switch(otg.dev_req.wValue_L) {
-
case 0:
-
otg.ep0_state = EP0_STATE_GD_STR_I0;
-
break;
-
case 1:
-
otg.ep0_state = EP0_STATE_GD_STR_I1;
-
break;
-
case 2:
-
otg.ep0_state = EP0_STATE_GD_STR_I2;
-
break;
-
default:
-
break;
-
}
-
break;
-
-
case ENDPOINT_DESCRIPTOR:
-
DBG_SETUP1("ENDPOINT_DESCRIPTOR \n");
-
switch(otg.dev_req.wValue_L&0xf) {
-
case 0:
-
otg.ep0_state=EP0_STATE_GD_EP0_ONLY_0;
-
break;
-
case 1:
-
otg.ep0_state=EP0_STATE_GD_EP1_ONLY_0;
-
break;
-
default:
-
break;
-
}
-
break;
-
-
case DEVICE_QUALIFIER:
-
otg.req_length = (u32)((otg.dev_req.wLength_H << 8) |
-
otg.dev_req.wLength_L);
-
DBG_SETUP1("DEVICE_QUALIFIER = 0x%x \n",otg.req_length);
-
otg.ep0_state = EP0_STATE_GD_DEV_QUALIFIER;
-
break;
-
-
case OTHER_SPEED_CONFIGURATION :
-
DBG_SETUP1("OTHER_SPEED_CONFIGURATION \n");
-
otg.req_length = (u32)((otg.dev_req.wLength_H << 8) |
-
otg.dev_req.wLength_L);
-
otg.ep0_state = EP0_STATE_GD_OTHER_SPEED;
-
break;
-
-
}
-
}
-
-
void s3c_usb_clear_feature(void)
-
{
-
switch (otg.dev_req.bmRequestType) {
-
case DEVICE_RECIPIENT:
-
DBG_SETUP1("DEVICE_RECIPIENT \n");
-
if (otg.dev_req.wValue_L == 1)
-
remode_wakeup = FALSE;
-
break;
-
-
case ENDPOINT_RECIPIENT:
-
DBG_SETUP1("ENDPOINT_RECIPIENT \n");
-
if (otg.dev_req.wValue_L == 0) {
-
if ((otg.dev_req.wIndex_L & 0x7f) == CONTROL_EP)
-
get_status.ep_ctrl= 0;
-
-
/* IN Endpoint */
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_IN_EP)
-
get_status.ep_in= 0;
-
-
/* OUT Endpoint */
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_OUT_EP)
-
get_status.ep_out= 0;
-
}
-
break;
-
-
default:
-
DBG_SETUP1("\n");
-
break;
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
-
}
-
-
void s3c_usb_set_feature(void)
-
{
-
u32 tmp;
-
-
switch (otg.dev_req.bmRequestType) {
-
case DEVICE_RECIPIENT:
-
DBG_SETUP1("DEVICE_RECIPIENT \n");
-
if (otg.dev_req.wValue_L == 1)
-
remode_wakeup = TRUE;
-
break;
-
-
case ENDPOINT_RECIPIENT:
-
DBG_SETUP1("ENDPOINT_RECIPIENT \n");
-
if (otg.dev_req.wValue_L == 0) {
-
if ((otg.dev_req.wIndex_L & 0x7f) == CONTROL_EP)
-
get_status.ep_ctrl= 1;
-
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_IN_EP)
-
get_status.ep_in= 1;
-
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_OUT_EP)
-
get_status.ep_out= 1;
-
}
-
break;
-
-
default:
-
DBG_SETUP1("\n");
-
break;
-
}
-
-
switch (otg.dev_req.wValue_L) {
-
case EP_STALL:
-
/* TBD: additional processing if required */
-
break;
-
-
case TEST_MODE:
-
if ((0 != otg.dev_req.wIndex_L ) ||(0 != otg.dev_req.bmRequestType))
-
break;
-
-
/* Set TEST MODE*/
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_FORCE_ENABLE_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
-
switch(otg.dev_req.wIndex_H) {
-
case TEST_J:
-
/*Set Test J*/
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_J_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
break;
-
-
case TEST_K:
-
/*Set Test K*/
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_K_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
break;
-
-
case TEST_SE0_NAK:
-
/*Set Test SE0NAK*/
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_SE0_NAK_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
break;
-
-
case TEST_PACKET:
-
DBG_SETUP1 ("Test_packet\n");
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, TEST_PKT_SIZE);
-
s3c_usb_write_ep0_fifo(test_pkt, TEST_PKT_SIZE);
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_PACKET_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
DBG_SETUP1 ("S5P_OTG_DCTL=0x%08x\n", tmp);
-
break;
-
}
-
break;
-
-
default:
-
break;
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
-
}
-
-
void s3c_usb_get_status(void)
-
{
-
switch(otg.dev_req.bmRequestType) {
-
case (0x80): /*device */
-
DBG_SETUP1("DEVICE\n");
-
get_status.Device=((u8)remode_wakeup<<1)|0x1; /* SelfPowered */
-
otg.ep0_state = EP0_STATE_GET_STATUS0;
-
break;
-
-
case (0x81): /*interface */
-
DBG_SETUP1("INTERFACE\n");
-
get_status.Interface=0;
-
otg.ep0_state = EP0_STATE_GET_STATUS1;
-
break;
-
-
case (0x82): /*endpoint */
-
DBG_SETUP1("ENDPOINT\n");
-
if ((otg.dev_req.wIndex_L & 0x7f) == CONTROL_EP)
-
otg.ep0_state = EP0_STATE_GET_STATUS2;
-
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_IN_EP)
-
otg.ep0_state = EP0_STATE_GET_STATUS3;
-
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_OUT_EP)
-
otg.ep0_state = EP0_STATE_GET_STATUS4;
-
break;
-
-
default:
-
DBG_SETUP1("\n");
-
break;
-
}
-
-
}
-
-
void s3c_usb_ep0_int_hndlr(void)
-
{
-
u16 i;
-
u32 buf[2]={0x0000, };
-
u16 addr;
-
-
DBG_SETUP0("Event EP0\n");
-
-
if (otg.ep0_state == EP0_STATE_INIT) {
-
-
for(i=0;i<2;i++)
-
buf[i] = readl(S5P_OTG_EP0_FIFO);
-
-
otg.dev_req.bmRequestType = buf[0];
-
otg.dev_req.bRequest = buf[0]>>8;
-
otg.dev_req.wValue_L = buf[0]>>16;
-
otg.dev_req.wValue_H = buf[0]>>24;
-
otg.dev_req.wIndex_L = buf[1];
-
otg.dev_req.wIndex_H = buf[1]>>8;
-
otg.dev_req.wLength_L = buf[1]>>16;
-
otg.dev_req.wLength_H = buf[1]>>24;
-
-
#ifdef USB_OTG_DEBUG_SETUP
-
s3c_usb_print_pkt((u8 *)&otg.dev_req, 8);
-
#endif
-
-
switch (otg.dev_req.bRequest) {
-
case STANDARD_SET_ADDRESS:
-
/* Set Address Update bit */
-
addr = (otg.dev_req.wValue_L);
-
writel(1<<18|addr<<4|otg.speed<<0, S5P_OTG_DCFG);
-
DBG_SETUP1("S5P_OTG_DCFG : %x, STANDARD_SET_ADDRESS : %d\n",
-
readl(S5P_OTG_DCFG), addr);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case STANDARD_SET_DESCRIPTOR:
-
DBG_SETUP1("STANDARD_SET_DESCRIPTOR \n");
-
break;
-
-
case STANDARD_SET_CONFIGURATION:
-
DBG_SETUP1("STANDARD_SET_CONFIGURATION \n");
-
/* Configuration value in configuration descriptor */
-
config_value = otg.dev_req.wValue_L;
-
otg.set_config = 1;
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case STANDARD_GET_CONFIGURATION:
-
DBG_SETUP1("STANDARD_GET_CONFIGURATION \n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
-
/*ep0 enable, clear nak, next ep0, 8byte */
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
writel(config_value, S5P_OTG_EP0_FIFO);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case STANDARD_GET_DESCRIPTOR:
-
DBG_SETUP1("STANDARD_GET_DESCRIPTOR :");
-
s3c_usb_get_desc();
-
break;
-
-
case STANDARD_CLEAR_FEATURE:
-
DBG_SETUP1("STANDARD_CLEAR_FEATURE :");
-
s3c_usb_clear_feature();
-
break;
-
-
case STANDARD_SET_FEATURE:
-
DBG_SETUP1("STANDARD_SET_FEATURE :");
-
s3c_usb_set_feature();
-
break;
-
-
case STANDARD_GET_STATUS:
-
DBG_SETUP1("STANDARD_GET_STATUS :");
-
s3c_usb_get_status();
-
break;
-
-
case STANDARD_GET_INTERFACE:
-
DBG_SETUP1("STANDARD_GET_INTERFACE \n");
-
otg.ep0_state = EP0_STATE_INTERFACE_GET;
-
break;
-
-
case STANDARD_SET_INTERFACE:
-
DBG_SETUP1("STANDARD_SET_INTERFACE \n");
-
get_intf.AlternateSetting= otg.dev_req.wValue_L;
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case STANDARD_SYNCH_FRAME:
-
DBG_SETUP1("STANDARD_SYNCH_FRAME \n");
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
default:
-
break;
-
}
-
}
-
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.ctrl_max_pktsize);
-
-
if(otg.speed == USB_HIGH) {
-
/*clear nak, next ep0, 64byte */
-
writel(((1<<26)|(CONTROL_EP<<11)|(0<<0)), S5P_OTG_DIEPCTL0);
-
}
-
else {
-
/*clear nak, next ep0, 8byte */
-
writel(((1<<26)|(CONTROL_EP<<11)|(3<<0)), S5P_OTG_DIEPCTL0);
-
}
-
-
}
-
-
void s3c_usb_set_otherspeed_conf_desc(u32 length)
-
{
-
/* Standard device descriptor */
-
if (otg.speed == USB_HIGH)
-
{
-
if (length ==9)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 9);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_full)+0, 9);
-
}
-
else if(length ==32)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 32);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_full_total)+0, 32);
-
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
if (length ==9)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+0, 8);
-
}
-
else if(length ==32)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high_total)+0, 8);
-
}
-
otg.ep0_state = EP0_STATE_GD_OTHER_SPEED_HIGH_1;
-
}
-
}
-
-
void s3c_usb_transfer_ep0(void)
-
{
-
-
DBG_SETUP0("otg.ep0_state = %d\n", otg.ep0_state);
-
-
switch (otg.ep0_state) {
-
case EP0_STATE_INIT:
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 0);
-
-
/*ep0 enable, clear nak, next ep0, 8byte */
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
DBG_SETUP1("EP0_STATE_INIT\n");
-
break;
-
-
/* GET_DESCRIPTOR:DEVICE */
-
case EP0_STATE_GD_DEV_0:
-
DBG_SETUP1("EP0_STATE_GD_DEV_0 :");
-
if (otg.speed == USB_HIGH) {
-
DBG_SETUP1("High Speed\n");
-
-
/*ep0 enable, clear nak, next ep0, max 64byte */
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
if (otg.req_length < DEVICE_DESC_SIZE) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+0, otg.req_length);
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, DEVICE_DESC_SIZE);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+0, DEVICE_DESC_SIZE);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
} else {
-
DBG_SETUP1("Full Speed\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<DEVICE_DESC_SIZE) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, DEVICE_DESC_SIZE);
-
}
-
-
if(otg.req_length<FS_CTRL_PKT_SIZE) {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+0, otg.req_length);
-
otg.ep0_state = EP0_STATE_INIT;
-
} else {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+0, FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_DEV_1;
-
}
-
}
-
break;
-
-
case EP0_STATE_GD_DEV_1:
-
DBG_SETUP1("EP0_STATE_GD_DEV_1\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<(2*FS_CTRL_PKT_SIZE)) {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+FS_CTRL_PKT_SIZE,
-
(otg.req_length-FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
} else {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+FS_CTRL_PKT_SIZE,
-
FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_DEV_2;
-
}
-
break;
-
-
case EP0_STATE_GD_DEV_2:
-
DBG_SETUP1("EP0_STATE_GD_DEV_2\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<DEVICE_DESC_SIZE) {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+(2*FS_CTRL_PKT_SIZE),
-
(otg.req_length-2*FS_CTRL_PKT_SIZE));
-
} else {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+(2*FS_CTRL_PKT_SIZE),
-
(DEVICE_DESC_SIZE-2*FS_CTRL_PKT_SIZE));
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:CONFIGURATION+INTERFACE+ENDPOINT0+ENDPOINT1 */
-
case EP0_STATE_GD_CFG_0:
-
DBG_SETUP1("EP0_STATE_GD_CFG_0 :");
-
if (otg.speed == USB_HIGH)
-
{
-
DBG_SETUP1("High Speed\n");
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<CONFIG_DESC_TOTAL_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, CONFIG_DESC_TOTAL_SIZE);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, CONFIG_DESC_TOTAL_SIZE);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
DBG_SETUP1("Full Speed\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<CONFIG_DESC_TOTAL_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, CONFIG_DESC_TOTAL_SIZE);
-
}
-
if(otg.req_length<FS_CTRL_PKT_SIZE)
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, otg.req_length);
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_1;
-
}
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_1:
-
DBG_SETUP1("EP0_STATE_GD_CFG_1\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<(2*FS_CTRL_PKT_SIZE))
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+FS_CTRL_PKT_SIZE,
-
(otg.req_length-FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+FS_CTRL_PKT_SIZE,
-
FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_2;
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_2:
-
DBG_SETUP1("EP0_STATE_GD_CFG_2\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<(3*FS_CTRL_PKT_SIZE))
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+(2*FS_CTRL_PKT_SIZE),
-
(otg.req_length-2*FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+(2*FS_CTRL_PKT_SIZE),
-
FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_3;
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_3:
-
DBG_SETUP1("EP0_STATE_GD_CFG_3\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<(4*FS_CTRL_PKT_SIZE))
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+(3*FS_CTRL_PKT_SIZE),
-
(otg.req_length-3*FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+(3*FS_CTRL_PKT_SIZE),
-
FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_4;
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_4:
-
DBG_SETUP1("EP0_STATE_GD_CFG_4\n");
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GD_DEV_QUALIFIER: /*only supported in USB 2.0*/
-
DBG_SETUP1("EP0_STATE_GD_DEV_QUALIFIER\n");
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<10)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
s3c_usb_write_ep0_fifo((u8 *)qualifier_desc+0, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 10);
-
s3c_usb_write_ep0_fifo((u8 *)qualifier_desc+0, 10);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GD_OTHER_SPEED:
-
DBG_SETUP1("EP0_STATE_GD_OTHER_SPEED\n");
-
s3c_usb_set_otherspeed_conf_desc(otg.req_length);
-
break;
-
-
case EP0_STATE_GD_OTHER_SPEED_HIGH_1:
-
DBG_SETUP1("EP0_STATE_GD_OTHER_SPEED_HIGH_1\n");
-
if(otg.req_length==9)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+8, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+8, 8);
-
otg.ep0_state = EP0_STATE_GD_OTHER_SPEED_HIGH_2;
-
}
-
break;
-
-
case EP0_STATE_GD_OTHER_SPEED_HIGH_2:
-
DBG_SETUP1("EP0_STATE_GD_OTHER_SPEED_HIGH_2\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+16, 8);
-
otg.ep0_state = EP0_STATE_GD_OTHER_SPEED_HIGH_3;
-
break;
-
-
case EP0_STATE_GD_OTHER_SPEED_HIGH_3:
-
DBG_SETUP1("EP0_STATE_GD_OTHER_SPEED_HIGH_3\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+24, 8);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:CONFIGURATION ONLY*/
-
case EP0_STATE_GD_CFG_ONLY_0:
-
DBG_SETUP1("EP0_STATE_GD_CFG_ONLY_0:");
-
if (otg.speed == USB_HIGH)
-
{
-
DBG_SETUP1("High Speed\n");
-
if(otg.req_length<CONFIG_DESC_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, CONFIG_DESC_SIZE);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0,
-
CONFIG_DESC_SIZE);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
DBG_SETUP1("Full Speed\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<CONFIG_DESC_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, CONFIG_DESC_SIZE);
-
}
-
if(otg.req_length<FS_CTRL_PKT_SIZE)
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, otg.req_length);
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_ONLY_1;
-
}
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_ONLY_1:
-
DBG_SETUP1("EP0_STATE_GD_CFG_ONLY_1\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+FS_CTRL_PKT_SIZE,
-
(CONFIG_DESC_SIZE-FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:INTERFACE ONLY */
-
-
case EP0_STATE_GD_IF_ONLY_0:
-
DBG_SETUP1("EP0_STATE_GD_IF_ONLY_0 :");
-
if (otg.speed == USB_HIGH)
-
{
-
DBG_SETUP1("High Speed\n");
-
if(otg.req_length<INTERFACE_DESC_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+0, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, INTERFACE_DESC_SIZE);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+0, INTERFACE_DESC_SIZE);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
DBG_SETUP1("Full Speed\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<INTERFACE_DESC_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, INTERFACE_DESC_SIZE);
-
}
-
if(otg.req_length<FS_CTRL_PKT_SIZE)
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+0, otg.req_length);
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+0, FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_IF_ONLY_1;
-
}
-
}
-
break;
-
-
case EP0_STATE_GD_IF_ONLY_1:
-
DBG_SETUP1("EP0_STATE_GD_IF_ONLY_1\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+FS_CTRL_PKT_SIZE,
-
(INTERFACE_DESC_SIZE-FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
-
/* GET_DESCRIPTOR:ENDPOINT 1 ONLY */
-
case EP0_STATE_GD_EP0_ONLY_0:
-
DBG_SETUP1("EP0_STATE_GD_EP0_ONLY_0\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, ENDPOINT_DESC_SIZE);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.ep1))+0, ENDPOINT_DESC_SIZE);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:ENDPOINT 2 ONLY */
-
case EP0_STATE_GD_EP1_ONLY_0:
-
DBG_SETUP1("EP0_STATE_GD_EP1_ONLY_0\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, ENDPOINT_DESC_SIZE);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.ep2))+0, ENDPOINT_DESC_SIZE);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:STRING */
-
case EP0_STATE_GD_STR_I0:
-
DBG_SETUP1("EP0_STATE_GD_STR_I0\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, STRING_DESC0_SIZE);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc0, STRING_DESC0_SIZE);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GD_STR_I1:
-
DBG_SETUP1("EP0_STATE_GD_STR_I1 %d\n", otg.ep0_substate);
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, sizeof(string_desc1));
-
if ((otg.ep0_substate*otg.ctrl_max_pktsize+otg.ctrl_max_pktsize)
-
< sizeof(string_desc1)) {
-
-
if (otg.speed == USB_HIGH)
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
else
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc1+(otg.ep0_substate*otg.ctrl_max_pktsize),
-
otg.ctrl_max_pktsize);
-
otg.ep0_state = EP0_STATE_GD_STR_I1;
-
otg.ep0_substate++;
-
} else {
-
if (otg.speed == USB_HIGH)
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
else
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc1+(otg.ep0_substate*otg.ctrl_max_pktsize),
-
sizeof(string_desc1)-(otg.ep0_substate*otg.ctrl_max_pktsize));
-
otg.ep0_state = EP0_STATE_INIT;
-
otg.ep0_substate = 0;
-
}
-
break;
-
-
case EP0_STATE_GD_STR_I2:
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, sizeof(string_desc2));
-
if ((otg.ep0_substate*otg.ctrl_max_pktsize+otg.ctrl_max_pktsize)
-
< sizeof(string_desc2)) {
-
-
if (otg.speed == USB_HIGH)
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
else
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc2+(otg.ep0_substate*otg.ctrl_max_pktsize),
-
otg.ctrl_max_pktsize);
-
otg.ep0_state = EP0_STATE_GD_STR_I2;
-
otg.ep0_substate++;
-
} else {
-
if (otg.speed == USB_HIGH)
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
else
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc2+(otg.ep0_substate*otg.ctrl_max_pktsize),
-
sizeof(string_desc2)-(otg.ep0_substate*otg.ctrl_max_pktsize));
-
otg.ep0_state = EP0_STATE_INIT;
-
otg.ep0_substate = 0;
-
}
-
DBG_SETUP1("EP0_STATE_GD_STR_I2 %d", otg.ep0_substate);
-
break;
-
-
case EP0_STATE_INTERFACE_GET:
-
DBG_SETUP1("EP0_STATE_INTERFACE_GET\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_intf+0, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
-
case EP0_STATE_GET_STATUS0:
-
DBG_SETUP1("EP0_STATE_GET_STATUS0\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+0, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GET_STATUS1:
-
DBG_SETUP1("EP0_STATE_GET_STATUS1\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+1, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GET_STATUS2:
-
DBG_SETUP1("EP0_STATE_GET_STATUS2\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+2, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GET_STATUS3:
-
DBG_SETUP1("EP0_STATE_GET_STATUS3\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+3, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GET_STATUS4:
-
DBG_SETUP1("EP0_STATE_GET_STATUS4\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+4, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
default:
-
break;
-
}
-
}
-
-
-
void s3c_usb_int_bulkin(void)
-
{
-
u8* bulkin_buf;
-
u32 remain_cnt;
-
-
DBG_BULK0("Bulk In Function\n");
-
-
bulkin_buf = (u8*)otg.up_ptr;
-
remain_cnt = otg.up_size- ((u32)otg.up_ptr - otg.up_addr);
-
DBG_BULK1("bulkin_buf = 0x%x,remain_cnt = 0x%x \n", bulkin_buf, remain_cnt);
-
-
if (remain_cnt > otg.bulkin_max_pktsize) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1, otg.bulkin_max_pktsize);
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
-
s3c_usb_write_in_fifo(bulkin_buf, otg.bulkin_max_pktsize);
-
-
otg.up_ptr += otg.bulkin_max_pktsize;
-
-
} else if(remain_cnt > 0) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1, remain_cnt);
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
-
s3c_usb_write_in_fifo(bulkin_buf, remain_cnt);
-
-
otg.up_ptr += remain_cnt;
-
-
} else { /*remain_cnt = 0*/
-
writel((DEPCTL_SNAK|DEPCTL_BULK_TYPE), S5P_OTG_DIEPCTL_IN);
-
}
-
}
-
-
void s3c_usb_upload_start(void)
-
{
-
u8 tmp_buf[12];
-
u32 check;
-
-
s3c_usb_read_out_fifo((u8 *)tmp_buf, 10);
-
check = *((u8 *)(tmp_buf+8)) + (*((u8 *)(tmp_buf+9))<<8);
-
-
if (check==0x1) {
-
otg.up_addr =
-
*((u8 *)(tmp_buf+0))+
-
(*((u8 *)(tmp_buf+1))<<8)+
-
(*((u8 *)(tmp_buf+2))<<16)+
-
(*((u8 *)(tmp_buf+3))<<24);
-
-
otg.up_size =
-
*((u8 *)(tmp_buf+4))+
-
(*((u8 *)(tmp_buf+5))<<8)+
-
(*((u8 *)(tmp_buf+6))<<16)+
-
(*((u8 *)(tmp_buf+7))<<24);
-
-
otg.up_ptr=(u8 *)otg.up_addr;
-
DBG_BULK1("UploadAddress : 0x%x, UploadSize: %d\n",
-
otg.up_addr, otg.up_size);
-
-
if (otg.op_mode == USB_CPU) {
-
if (otg.up_size > otg.bulkin_max_pktsize) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1,
-
otg.bulkin_max_pktsize);
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1,
-
otg.up_size);
-
}
-
-
/*ep1 enable, clear nak, bulk, usb active, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
} else if ((otg.op_mode == USB_DMA) && (otg.up_size > 0)) {
-
u32 pktcnt, remainder;
-
-
DBG_BULK1("Dma Start for IN PKT \n");
-
-
writel(MODE_DMA|BURST_INCR4|GBL_INT_UNMASK,
-
S5P_OTG_GAHBCFG);
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP| INT_ENUMDONE|
-
INT_RESET|INT_SUSPEND, S5P_OTG_GINTMSK);
-
-
writel((u32)otg.up_ptr, S5P_OTG_DIEPDMA_IN);
-
-
pktcnt = (u32)(otg.up_size/otg.bulkin_max_pktsize);
-
remainder = (u32)(otg.up_size%otg.bulkin_max_pktsize);
-
if(remainder != 0) {
-
pktcnt += 1;
-
}
-
-
if (pktcnt > 1023) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1023,
-
(otg.bulkin_max_pktsize*1023));
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, pktcnt,
-
otg.up_size);
-
}
-
-
/*ep1 enable, clear nak, bulk, usb active, next ep1, max pkt */
-
writel(1u<<31|1<<26|2<<18|1<<15|BULK_IN_EP<<11|
-
otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
}
-
}
-
otg.dn_filesize=0;
-
}
-
-
void s3c_usb_download_start(u32 fifo_cnt_byte)
-
{
-
u8 tmp_buf[8];
-
-
s3c_usb_read_out_fifo((u8 *)tmp_buf, 8);
-
DBG_BULK1("downloadFileSize==0, 1'st BYTE_READ_CNT_REG : %x\n",
-
fifo_cnt_byte);
-
-
otg.dn_addr=s3c_usbd_dn_addr;
-
otg.dn_filesize=
-
*((u8 *)(tmp_buf+4))+
-
(*((u8 *)(tmp_buf+5))<<8)+
-
(*((u8 *)(tmp_buf+6))<<16)+
-
(*((u8 *)(tmp_buf+7))<<24);
-
-
otg.dn_ptr=(u8 *)otg.dn_addr;
-
DBG_BULK1("downloadAddress : 0x%x, downloadFileSize: %x\n",
-
otg.dn_addr, otg.dn_filesize);
-
-
/* The first 8-bytes are deleted.*/
-
s3c_usb_read_out_fifo((u8 *)otg.dn_ptr, fifo_cnt_byte-8);
-
otg.dn_ptr += fifo_cnt_byte-8;
-
-
if (otg.op_mode == USB_CPU) {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1,
-
otg.bulkout_max_pktsize);
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
} else if (otg.dn_filesize>otg.bulkout_max_pktsize) {
-
u32 pkt_cnt, remain_cnt;
-
-
DBG_BULK1("downloadFileSize!=0, Dma Start for 2nd OUT PKT \n");
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|
-
INT_RESET|INT_SUSPEND, S5P_OTG_GINTMSK); /*gint unmask */
-
writel(MODE_DMA|BURST_INCR4|GBL_INT_UNMASK,
-
S5P_OTG_GAHBCFG);
-
writel((u32)otg.dn_ptr, S5P_OTG_DOEPDMA_OUT);
-
pkt_cnt = (u32)(otg.dn_filesize-otg.bulkout_max_pktsize)/otg.bulkout_max_pktsize;
-
remain_cnt = (u32)((otg.dn_filesize-otg.bulkout_max_pktsize)%otg.bulkout_max_pktsize);
-
if(remain_cnt != 0) {
-
pkt_cnt += 1;
-
}
-
-
if (pkt_cnt > 1023) {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1023,
-
(otg.bulkout_max_pktsize*1023));
-
} else {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, pkt_cnt,
-
(otg.dn_filesize-otg.bulkout_max_pktsize));
-
}
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
}
-
}
-
-
void s3c_usb_download_continue(u32 fifo_cnt_byte)
-
{
-
if (otg.op_mode == USB_CPU) {
-
s3c_usb_read_out_fifo((u8 *)otg.dn_ptr, fifo_cnt_byte);
-
otg.dn_ptr += fifo_cnt_byte;
-
DBG_BULK1("downloadFileSize!=0, 2nd BYTE_READ_CNT_REG = 0x%x, m_pDownPt = 0x%x\n",
-
fifo_cnt_byte, otg.dn_ptr);
-
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1, otg.bulkout_max_pktsize);
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
-
/* USB format : addr(4)+size(4)+data(n)+cs(2) */
-
if (((u32)otg.dn_ptr - otg.dn_addr) >= (otg.dn_filesize - 8)) {
-
printf("Download Done!! Download Address: 0x%x, Download Filesize:0x%x\n",
-
otg.dn_addr, (otg.dn_filesize-10));
-
-
s3c_usbd_dn_cnt = otg.dn_filesize-10;
-
s3c_usbd_dn_addr = otg.dn_addr;
-
-
#ifdef USB_CHECKSUM_EN
-
s3c_usb_verify_checksum();
-
#endif
-
s3c_receive_done = 1;
-
}
-
-
}\
-
}
-
-
void s3c_usb_int_bulkout(u32 fifo_cnt_byte)
-
{
-
DBG_BULK0("Bulk Out Function : otg.dn_filesize=0x%x\n", otg.dn_filesize);
-
if (otg.dn_filesize==0) {
-
if (fifo_cnt_byte == 10) {
-
s3c_usb_upload_start();
-
} else {
-
s3c_usb_download_start(fifo_cnt_byte);
-
}
-
} else {
-
s3c_usb_download_continue(fifo_cnt_byte);
-
}
-
}
-
-
void s3c_usb_dma_in_done(void)
-
{
-
s32 remain_cnt;
-
-
DBG_BULK0("DMA IN : Transfer Done\n");
-
-
otg.up_ptr = (u8 *)readl(S5P_OTG_DIEPDMA_IN);
-
remain_cnt = otg.up_size- ((u32)otg.up_ptr - otg.up_addr);
-
-
if (remain_cnt>0) {
-
u32 pktcnt, remainder;
-
pktcnt = (u32)(remain_cnt/otg.bulkin_max_pktsize);
-
remainder = (u32)(remain_cnt%otg.bulkin_max_pktsize);
-
if(remainder != 0) {
-
pktcnt += 1;
-
}
-
DBG_SETUP1("remain_cnt : %d \n", remain_cnt);
-
if (pktcnt> 1023) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1023,
-
(otg.bulkin_max_pktsize*1023));
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, pktcnt,
-
remain_cnt);
-
}
-
-
/*ep1 enable, clear nak, bulk, usb active, next ep1, max pkt */
-
writel(1u<<31|1<<26|2<<18|1<<15|BULK_IN_EP<<11|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
} else
-
DBG_SETUP1("DMA IN : Transfer Complete\n");
-
}
-
-
void s3c_usb_dma_out_done(void)
-
{
-
s32 remain_cnt;
-
-
DBG_BULK1("DMA OUT : Transfer Done\n");
-
otg.dn_ptr = (u8 *)readl(S5P_OTG_DOEPDMA_OUT);
-
-
remain_cnt = otg.dn_filesize - ((u32)otg.dn_ptr - otg.dn_addr + 8);
-
-
if (remain_cnt>0) {
-
u32 pktcnt, remainder;
-
pktcnt = (u32)(remain_cnt/otg.bulkout_max_pktsize);
-
remainder = (u32)(remain_cnt%otg.bulkout_max_pktsize);
-
if(remainder != 0) {
-
pktcnt += 1;
-
}
-
DBG_BULK1("remain_cnt : %d \n", remain_cnt);
-
if (pktcnt> 1023) {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1023,
-
(otg.bulkout_max_pktsize*1023));
-
} else {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, pktcnt,
-
remain_cnt);
-
}
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
} else {
-
DBG_BULK1("DMA OUT : Transfer Complete\n");
-
udelay(500); /*for FPGA ???*/
-
}
-
}
-
-
void s3c_usb_set_all_outep_nak(void)
-
{
-
u8 i;
-
u32 tmp;
-
-
for(i=0;i<16;i++)
-
{
-
tmp = readl(S5P_OTG_DOEPCTL0+0x20*i);
-
tmp |= DEPCTL_SNAK;
-
writel(tmp, S5P_OTG_DOEPCTL0+0x20*i);
-
}
-
}
-
-
void s3c_usb_clear_all_outep_nak(void)
-
{
-
u8 i;
-
u32 tmp;
-
-
for(i=0;i<16;i++)
-
{
-
tmp = readl(S5P_OTG_DOEPCTL0+0x20*i);
-
tmp |= (DEPCTL_EPENA|DEPCTL_CNAK);
-
writel(tmp, S5P_OTG_DOEPCTL0+0x20*i);
-
}
-
}
-
-
void s3c_usb_set_max_pktsize(USB_SPEED speed)
-
{
-
if (speed == USB_HIGH)
-
{
-
otg.speed = USB_HIGH;
-
otg.ctrl_max_pktsize = HS_CTRL_PKT_SIZE;
-
otg.bulkin_max_pktsize = HS_BULK_PKT_SIZE;
-
otg.bulkout_max_pktsize = HS_BULK_PKT_SIZE;
-
}
-
else
-
{
-
otg.speed = USB_FULL;
-
otg.ctrl_max_pktsize = FS_CTRL_PKT_SIZE;
-
otg.bulkin_max_pktsize = FS_BULK_PKT_SIZE;
-
otg.bulkout_max_pktsize = FS_BULK_PKT_SIZE;
-
}
-
}
-
-
void s3c_usb_set_endpoint(void)
-
{
-
/* Unmask S5P_OTG_DAINT source */
-
writel(0xff, S5P_OTG_DIEPINT0);
-
writel(0xff, S5P_OTG_DOEPINT0);
-
writel(0xff, S5P_OTG_DIEPINT_IN);
-
writel(0xff, S5P_OTG_DOEPINT_OUT);
-
-
/* Init For Ep0*/
-
if(otg.speed == USB_HIGH)
-
{
-
/*MPS:64bytes */
-
writel(((1<<26)|(CONTROL_EP<<11)|(0<<0)), S5P_OTG_DIEPCTL0);
-
/*ep0 enable, clear nak */
-
writel((1u<<31)|(1<<26)|(0<<0), S5P_OTG_DOEPCTL0);
-
}
-
else
-
{
-
/*MPS:8bytes */
-
writel(((1<<26)|(CONTROL_EP<<11)|(3<<0)), S5P_OTG_DIEPCTL0);
-
/*ep0 enable, clear nak */
-
writel((1u<<31)|(1<<26)|(3<<0), S5P_OTG_DOEPCTL0);
-
}
-
}
-
-
void s3c_usb_set_descriptors(void)
-
{
-
/* Standard device descriptor */
-
otg.desc.dev.bLength=DEVICE_DESC_SIZE; /*0x12*/
-
otg.desc.dev.bDescriptorType=DEVICE_DESCRIPTOR;
-
otg.desc.dev.bDeviceClass=0xFF; /* 0x0*/
-
otg.desc.dev.bDeviceSubClass=0x0;
-
otg.desc.dev.bDeviceProtocol=0x0;
-
otg.desc.dev.bMaxPacketSize0=otg.ctrl_max_pktsize;
-
otg.desc.dev.idVendorL=0xE8; /*0x45;*/
-
otg.desc.dev.idVendorH=0x04; /*0x53;*/
-
otg.desc.dev.idProductL=0x34; /*0x00*/
-
otg.desc.dev.idProductH=0x12; /*0x64*/
-
otg.desc.dev.bcdDeviceL=0x00;
-
otg.desc.dev.bcdDeviceH=0x01;
-
otg.desc.dev.iManufacturer=0x1; /* index of string descriptor */
-
otg.desc.dev.iProduct=0x2; /* index of string descriptor */
-
otg.desc.dev.iSerialNumber=0x0;
-
otg.desc.dev.bNumConfigurations=0x1;
-
if (otg.speed == USB_FULL) {
-
otg.desc.dev.bcdUSBL=0x10;
-
otg.desc.dev.bcdUSBH=0x01; /* Ver 1.10*/
-
}
-
else {
-
otg.desc.dev.bcdUSBL=0x00;
-
otg.desc.dev.bcdUSBH=0x02; /* Ver 2.0*/
-
}
-
-
/* Standard configuration descriptor */
-
otg.desc.config.bLength=CONFIG_DESC_SIZE; /* 0x9 bytes */
-
otg.desc.config.bDescriptorType=CONFIGURATION_DESCRIPTOR;
-
otg.desc.config.wTotalLengthL=CONFIG_DESC_TOTAL_SIZE;
-
otg.desc.config.wTotalLengthH=0;
-
otg.desc.config.bNumInterfaces=1;
-
/* dbg descConf.bConfigurationValue=2; // why 2? There's no reason.*/
-
otg.desc.config.bConfigurationValue=1;
-
otg.desc.config.iConfiguration=0;
-
otg.desc.config.bmAttributes=CONF_ATTR_DEFAULT|CONF_ATTR_SELFPOWERED; /* bus powered only.*/
-
otg.desc.config.maxPower=25; /* draws 50mA current from the USB bus.*/
-
-
/* Standard interface descriptor */
-
otg.desc.intf.bLength=INTERFACE_DESC_SIZE; /* 9*/
-
otg.desc.intf.bDescriptorType=INTERFACE_DESCRIPTOR;
-
otg.desc.intf.bInterfaceNumber=0x0;
-
otg.desc.intf.bAlternateSetting=0x0; /* ?*/
-
otg.desc.intf.bNumEndpoints = 2; /* # of endpoints except EP0*/
-
otg.desc.intf.bInterfaceClass=0xff; /* 0x0 ?*/
-
otg.desc.intf.bInterfaceSubClass=0x0;
-
otg.desc.intf.bInterfaceProtocol=0x0;
-
otg.desc.intf.iInterface=0x0;
-
-
/* Standard endpoint0 descriptor */
-
otg.desc.ep1.bLength=ENDPOINT_DESC_SIZE;
-
otg.desc.ep1.bDescriptorType=ENDPOINT_DESCRIPTOR;
-
otg.desc.ep1.bEndpointAddress=BULK_IN_EP|EP_ADDR_IN;
-
otg.desc.ep1.bmAttributes=EP_ATTR_BULK;
-
otg.desc.ep1.wMaxPacketSizeL=(u8)otg.bulkin_max_pktsize; /* 64*/
-
otg.desc.ep1.wMaxPacketSizeH=(u8)(otg.bulkin_max_pktsize>>8);
-
otg.desc.ep1.bInterval=0x0; /* not used */
-
-
/* Standard endpoint1 descriptor */
-
otg.desc.ep2.bLength=ENDPOINT_DESC_SIZE;
-
otg.desc.ep2.bDescriptorType=ENDPOINT_DESCRIPTOR;
-
otg.desc.ep2.bEndpointAddress=BULK_OUT_EP|EP_ADDR_OUT;
-
otg.desc.ep2.bmAttributes=EP_ATTR_BULK;
-
otg.desc.ep2.wMaxPacketSizeL=(u8)otg.bulkout_max_pktsize; /* 64*/
-
otg.desc.ep2.wMaxPacketSizeH=(u8)(otg.bulkout_max_pktsize>>8);
-
otg.desc.ep2.bInterval=0x0; /* not used */
-
}
-
-
void s3c_usb_check_speed(USB_SPEED *speed)
-
{
-
u32 status;
-
-
status = readl(S5P_OTG_DSTS); /* System status read */
-
-
*speed = (USB_SPEED)((status&0x6) >>1);
-
}
-
-
void s3c_usb_clear_dnfile_info(void)
-
{
-
otg.dn_addr = 0;
-
otg.dn_filesize = 0;
-
otg.dn_ptr = 0;
-
}
-
-
void s3c_usb_clear_upfile_info(void)
-
{
-
otg.up_addr= 0;
-
otg.up_size= 0;
-
otg.up_ptr = 0;
-
}
-
-
-
int s3c_usb_check_setconf(void)
-
{
-
if (otg.set_config == 0)
-
return FALSE;
-
else
-
return TRUE;
-
}
-
-
void s3c_usb_set_opmode(USB_OPMODE mode)
-
{
-
otg.op_mode = mode;
-
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|
-
INT_RESET|INT_SUSPEND|INT_RX_FIFO_NOT_EMPTY,
-
S5P_OTG_GINTMSK); /*gint unmask */
-
-
writel(MODE_SLAVE|BURST_SINGLE|GBL_INT_UNMASK, S5P_OTG_GAHBCFG);
-
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1, otg.bulkout_max_pktsize);
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1, 0);
-
-
/*bulk out ep enable, clear nak, bulk, usb active, next ep3, max pkt */
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
-
/*bulk in ep enable, clear nak, bulk, usb active, next ep1, max pkt */
-
writel(0u<<31|1<<26|2<<18|1<<15|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
}
-
-
void s3c_usb_reset(void)
-
{
-
s3c_usb_set_all_outep_nak();
-
-
otg.ep0_state = EP0_STATE_INIT;
-
writel(((1<<BULK_OUT_EP)|(1<<CONTROL_EP))<<16|((1<<BULK_IN_EP)|(1<<CONTROL_EP)),
-
S5P_OTG_DAINTMSK);
-
writel(CTRL_OUT_EP_SETUP_PHASE_DONE|AHB_ERROR|TRANSFER_DONE,
-
S5P_OTG_DOEPMSK);
-
writel(INTKN_TXFEMP|NON_ISO_IN_EP_TIMEOUT|AHB_ERROR|TRANSFER_DONE,
-
S5P_OTG_DIEPMSK);
-
-
/* Rx FIFO Size */
-
writel(RX_FIFO_SIZE, S5P_OTG_GRXFSIZ);
-
-
/* Non Periodic Tx FIFO Size */
-
writel(NPTX_FIFO_SIZE<<16| NPTX_FIFO_START_ADDR<<0, S5P_OTG_GNPTXFSIZ);
-
-
s3c_usb_clear_all_outep_nak();
-
-
/*clear device address */
-
writel(readl(S5P_OTG_DCFG)&~(0x7f<<4), S5P_OTG_DCFG);
-
-
if(SUSPEND_RESUME_ON) {
-
writel(readl(S5P_OTG_PCGCCTL)&~(1<<0), S5P_OTG_PCGCCTL);
-
}
-
}
-
int s3c_usb_set_init(void)
-
{
-
u32 status;
-
-
status = readl(S5P_OTG_DSTS); /* System status read */
-
-
/* Set if Device is High speed or Full speed */
-
if (((status&0x6) >>1) == USB_HIGH) {
-
DBG_SETUP1("High Speed Detection\n");
-
s3c_usb_set_max_pktsize(USB_HIGH);
-
}
-
else if(((status&0x6) >>1) == USB_FULL) {
-
DBG_SETUP1("Full Speed Detec tion\n");
-
s3c_usb_set_max_pktsize(USB_FULL);
-
}
-
else {
-
printf("**** Error:Neither High_Speed nor Full_Speed\n");
-
return FALSE;
-
}
-
-
s3c_usb_set_endpoint();
-
s3c_usb_set_descriptors();
-
s3c_usb_clear_dnfile_info();
-
s3c_usb_set_opmode(op_mode);
-
-
return TRUE;
-
}
-
-
void s3c_usb_pkt_receive(void)
-
{
-
u32 rx_status;
-
u32 fifo_cnt_byte;
-
-
rx_status = readl(S5P_OTG_GRXSTSP);
-
DBG_SETUP0("S5P_OTG_GRXSTSP = 0x%x\n", rx_status);
-
-
if ((rx_status & (0xf<<17)) == SETUP_PKT_RECEIVED) {
-
DBG_SETUP1("SETUP_PKT_RECEIVED\n");
-
s3c_usb_ep0_int_hndlr();
-
-
} else if ((rx_status & (0xf<<17)) == OUT_PKT_RECEIVED) {
-
fifo_cnt_byte = (rx_status & 0x7ff0)>>4;
-
DBG_SETUP1("OUT_PKT_RECEIVED\n");
-
-
if((rx_status & BULK_OUT_EP)&&(fifo_cnt_byte)) {
-
s3c_usb_int_bulkout(fifo_cnt_byte);
-
if( otg.op_mode == USB_CPU )
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|
-
INT_ENUMDONE|INT_RESET|INT_SUSPEND|
-
INT_RX_FIFO_NOT_EMPTY,
-
S5P_OTG_GINTMSK);
-
return;
-
}
-
-
} else if ((rx_status & (0xf<<17)) == GLOBAL_OUT_NAK) {
-
DBG_SETUP1("GLOBAL_OUT_NAK\n");
-
-
} else if ((rx_status & (0xf<<17)) == OUT_TRNASFER_COMPLETED) {
-
DBG_SETUP1("OUT_TRNASFER_COMPLETED\n");
-
-
} else if ((rx_status & (0xf<<17)) == SETUP_TRANSACTION_COMPLETED) {
-
DBG_SETUP1("SETUP_TRANSACTION_COMPLETED\n");
-
-
} else {
-
DBG_SETUP1("Reserved\n");
-
}
-
}
-
-
void s3c_usb_transfer(void)
-
{
-
u32 ep_int;
-
u32 check_dma;
-
u32 ep_int_status;
-
-
ep_int = readl(S5P_OTG_DAINT);
-
DBG_SETUP0("S5P_OTG_DAINT = 0x%x", ep_int);
-
-
if (ep_int & (1<<CONTROL_EP)) {
-
ep_int_status = readl(S5P_OTG_DIEPINT0);
-
DBG_SETUP1("S5P_OTG_DIEPINT0 : %x \n", ep_int_status);
-
-
if (ep_int_status & INTKN_TXFEMP) {
-
u32 uNTxFifoSpace;
-
do {
-
uNTxFifoSpace=readl(S5P_OTG_GNPTXSTS)&0xffff;
-
}while(uNTxFifoSpace<otg.ctrl_max_pktsize);
-
-
s3c_usb_transfer_ep0();
-
}
-
-
writel(ep_int_status, S5P_OTG_DIEPINT0); /* Interrupt Clear */
-
}
-
-
if (ep_int & ((1<<CONTROL_EP)<<16)) {
-
ep_int_status = readl(S5P_OTG_DOEPINT0);
-
DBG_SETUP1("S5P_OTG_DOEPINT0 : %x \n", ep_int_status);
-
-
s3c_usb_set_outep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(1u<<31|1<<26, S5P_OTG_DOEPCTL0); /*ep0 enable, clear nak */
-
-
writel(ep_int_status, S5P_OTG_DOEPINT0); /* Interrupt Clear */
-
}
-
-
if(ep_int & (1<<BULK_IN_EP)) {
-
ep_int_status = readl(S5P_OTG_DIEPINT_IN);
-
DBG_BULK1("S5P_OTG_DIEPINT_IN : %x \n", ep_int_status);
-
writel(ep_int_status, S5P_OTG_DIEPINT_IN); /* Interrupt Clear */
-
-
if ( (ep_int_status&INTKN_TXFEMP) && otg.op_mode == USB_CPU)
-
s3c_usb_int_bulkin();
-
-
check_dma = readl(S5P_OTG_GAHBCFG);
-
if ((check_dma&MODE_DMA)&&(ep_int_status&TRANSFER_DONE))
-
s3c_usb_dma_in_done();
-
}
-
-
if (ep_int & ((1<<BULK_OUT_EP)<<16)) {
-
ep_int_status = readl(S5P_OTG_DOEPINT_OUT);
-
DBG_BULK1("S5P_OTG_DOEPINT_OUT : 0x%x\n", ep_int_status);
-
writel(ep_int_status, S5P_OTG_DOEPINT_OUT); /* Interrupt Clear */
-
-
check_dma = readl(S5P_OTG_GAHBCFG);
-
if ((check_dma&MODE_DMA)&&(ep_int_status&TRANSFER_DONE)) {
-
s3c_usb_dma_out_done();
-
}
-
}
-
}
-
-
void s3c_udc_int_hndlr(void)
-
{
-
u32 int_status;
-
int tmp;
-
-
int_status = readl(S5P_OTG_GINTSTS); /* Core Interrupt Register */
-
writel(int_status, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
DBG_SETUP0("*** USB OTG Interrupt(S5P_OTG_GINTSTS: 0x%08x) ****\n",
-
int_status);
-
-
if (int_status & INT_RESET) {
-
DBG_SETUP1("INT_RESET\n");
-
writel(INT_RESET, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
-
s3c_usb_reset();
-
}
-
-
if (int_status & INT_ENUMDONE) {
-
DBG_SETUP1("INT_ENUMDONE :");
-
writel(INT_ENUMDONE, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
s3c_usb_connected_status=3;
-
tmp = s3c_usb_set_init();
-
if (tmp == FALSE)
-
return;
-
-
}
-
-
if (int_status & INT_RESUME) {
-
DBG_SETUP1("INT_RESUME\n");
-
writel(INT_RESUME, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
-
if(SUSPEND_RESUME_ON) {
-
writel(readl(S5P_OTG_PCGCCTL)&~(1<<0), S5P_OTG_PCGCCTL);
-
DBG_SETUP1("INT_RESUME\n");
-
}
-
}
-
-
if (int_status & INT_SUSPEND) {
-
DBG_SETUP1("INT_SUSPEND\n");
-
writel(INT_SUSPEND, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
-
if(SUSPEND_RESUME_ON) {
-
writel(readl(S5P_OTG_PCGCCTL)|(1<<0), S5P_OTG_PCGCCTL);
-
}
-
}
-
-
if(int_status & INT_RX_FIFO_NOT_EMPTY) {
-
DBG_SETUP1("INT_RX_FIFO_NOT_EMPTY\n");
-
/* Read only register field */
-
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|
-
INT_ENUMDONE|INT_RESET|INT_SUSPEND,
-
S5P_OTG_GINTMSK);
-
s3c_usb_pkt_receive();
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|
-
INT_RESET |INT_SUSPEND|INT_RX_FIFO_NOT_EMPTY,
-
S5P_OTG_GINTMSK); /*gint unmask */
-
s3c_usb_connected_status=1;
-
}
-
-
if ((int_status & INT_IN_EP) || (int_status & INT_OUT_EP)) {
-
DBG_SETUP1("INT_IN or OUT_EP\n");
-
/* Read only register field */
-
-
s3c_usb_transfer();
-
}
-
}
-
-
int s3c_udc_is_adc_cable()
-
{
-
int count = 0;
-
while(count<10)
-
{
-
if((readl(S5P_OTG_HPRT)&0xc00)==0xc00)
-
count ++;
-
else
-
{
-
count =0;
-
return 0;
-
}
-
}
-
return 1;
-
}
-
/*the following is for u-boot battery charge*/
-
int s3c_check_usb_connect_status()
-
{
-
if(!s3c_usb_phy_inited)/*initalized at first*/
-
{
-
s3c_usbctl_init(1);
-
}
-
/*then check current usb status*/
-
unsigned long usec = (1000*1000*10);
-
ulong tmo, tmp;
-
-
if (usec >= 1000) { /* if "big" number, spread normalization to seconds */
-
tmo = usec / 1000; /* start to normalize for usec to ticks per sec */
-
tmo *= CFG_HZ; /* find number of "ticks" to wait to achieve target */
-
tmo /= 1000; /* finish normalize. */
-
}
-
else { /* else small number, don't kill it prior to HZ multiply */
-
tmo = usec * CFG_HZ;
-
tmo /= (1000 * 1000);
-
}
-
tmp = get_timer(0); /* get current timestamp */
-
if ((tmo + tmp + 1) < tmp) /* if setting this fordward will roll time stamp */
-
{
-
reset_timer_masked(); /* reset "advancing" timestamp to 0, set lastdec value */
-
}
-
else
-
tmo += tmp; /* else, set advancing stamp wake up time */
-
-
while (get_timer_masked()<tmo)
-
{
-
if (S3C_USBD_DETECT_IRQ()) {
-
s3c_udc_int_hndlr();
-
S3C_USBD_CLEAR_IRQ();
-
}
-
if(s3c_udc_is_adc_cable())
-
s3c_usb_connected_status=2;
-
if(s3c_usb_connected_status==2||s3c_usb_connected_status==1)
-
break;
-
}
-
-
if(s3c_usb_phy_inited)
-
{
-
s3c_usb_stop();
-
}
-
return s3c_usb_connected_status;
-
-
}
-
#endif
-
/*
-
* cpu/s5pc1xx/usbd-otg-hs.c
-
*
-
* (C) Copyright 2007
-
* Byungjae Lee, Samsung Erectronics, bjlee@samsung.com.
-
* - only support for S5PC100
-
*
-
* This program is free software; you can redistribute it and/or
-
* modify it under the terms of the GNU General Public License as
-
* published by the Free Software Foundation; either version 2 of
-
* the License, or (at your option) any later version.
-
*
-
* This program is distributed in the hope that it will be useful,
-
* but WITHOUT ANY WARRANTY; without even the implied warranty of
-
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-
* GNU General Public License for more details.
-
*
-
* You should have received a copy of the GNU General Public License
-
* along with this program; if not, write to the Free Software
-
* Foundation, Inc., 59 Temple Place, Suite 330, Boston,
-
* MA 02111-1307 USA
-
*/
-
-
#include <common.h>
-
-
#if defined(CONFIG_S5PC110)
-
#include <command.h>
-
#include <asm/errno.h>
-
#include <asm/io.h>
-
#include <regs.h>
-
#include "usbd-otg-hs.h"
-
-
#undef USB_OTG_DEBUG_SETUP
-
#ifdef USB_OTG_DEBUG_SETUP
-
#define DBG_SETUP0(fmt, args...) printf("[%s:%d] " fmt, __FUNCTION__, __LINE__, ##args)
-
#define DBG_SETUP1(fmt, args...) printf("\t" fmt, ##args)
-
#define DBG_SETUP2(fmt, args...) printf(fmt, ##args)
-
#else
-
#define DBG_SETUP0(fmt, args...) do { } while (0)
-
#define DBG_SETUP1(fmt, args...) do { } while (0)
-
#define DBG_SETUP2(fmt, args...) do { } while (0)
-
#endif
-
-
#undef USB_OTG_DEBUG_BULK
-
#ifdef USB_OTG_DEBUG_BULK
-
#define DBG_BULK0(fmt, args...) printf("[%s:%d] " fmt, __FUNCTION__, __LINE__, ##args)
-
#define DBG_BULK1(fmt, args...) printf("\t" fmt, ##args)
-
#else
-
#define DBG_BULK0(fmt, args...) do { } while (0)
-
#define DBG_BULK1(fmt, args...) do { } while (0)
-
#endif
-
-
#define USB_CHECKSUM_EN
-
-
#define TRUE 1
-
#define FALSE 0
-
#define SUSPEND_RESUME_ON FALSE
-
-
u32 s3c_usbd_dn_addr = 0;
-
u32 s3c_usbd_dn_cnt = 0;
-
u32 remode_wakeup;
-
u16 config_value;
-
-
int DNW;
-
int s3c_receive_done = 0;
-
int s3c_got_header = 0;
-
int s3c_usb_phy_inited=0;
-
int s3c_usb_connected_status= 0;/*0,none,1,usb connected,2,power connected,3,bad usb connected*/
-
USB_OPMODE op_mode = USB_CPU;
-
USB_SPEED speed = USB_HIGH;
-
-
otg_dev_t otg;
-
get_status_t get_status;
-
get_intf_t get_intf;
-
-
enum EP_INDEX
-
{
-
EP0, EP1, EP2, EP3, EP4
-
};
-
-
/*------------------------------------------------*/
-
/* EP0 state */
-
enum EP0_STATE
-
{
-
EP0_STATE_INIT = 0,
-
EP0_STATE_GD_DEV_0 = 11,
-
EP0_STATE_GD_DEV_1 = 12,
-
EP0_STATE_GD_DEV_2 = 13,
-
EP0_STATE_GD_CFG_0 = 21,
-
EP0_STATE_GD_CFG_1 = 22,
-
EP0_STATE_GD_CFG_2 = 23,
-
EP0_STATE_GD_CFG_3 = 24,
-
EP0_STATE_GD_CFG_4 = 25,
-
EP0_STATE_GD_STR_I0 = 30,
-
EP0_STATE_GD_STR_I1 = 31,
-
EP0_STATE_GD_STR_I2 = 32,
-
EP0_STATE_GD_DEV_QUALIFIER = 33,
-
EP0_STATE_INTERFACE_GET = 34,
-
EP0_STATE_GET_STATUS0 = 35,
-
EP0_STATE_GET_STATUS1 = 36,
-
EP0_STATE_GET_STATUS2 = 37,
-
EP0_STATE_GET_STATUS3 = 38,
-
EP0_STATE_GET_STATUS4 = 39,
-
EP0_STATE_GD_OTHER_SPEED = 40,
-
EP0_STATE_GD_CFG_ONLY_0 = 41,
-
EP0_STATE_GD_CFG_ONLY_1 = 42,
-
EP0_STATE_GD_IF_ONLY_0 = 44,
-
EP0_STATE_GD_IF_ONLY_1 = 45,
-
EP0_STATE_GD_EP0_ONLY_0 = 46,
-
EP0_STATE_GD_EP1_ONLY_0 = 47,
-
EP0_STATE_GD_EP2_ONLY_0 = 48,
-
EP0_STATE_GD_EP3_ONLY_0 = 49,
-
EP0_STATE_GD_OTHER_SPEED_HIGH_1 = 51,
-
EP0_STATE_GD_OTHER_SPEED_HIGH_2 = 52,
-
EP0_STATE_GD_OTHER_SPEED_HIGH_3 = 53
-
};
-
-
/*definitions related to CSR setting */
-
-
/* S5P_OTG_GOTGCTL*/
-
#define B_SESSION_VALID (0x1<<19)
-
#define A_SESSION_VALID (0x1<<18)
-
-
/* S5P_OTG_GAHBCFG*/
-
#define PTXFE_HALF (0<<8)
-
#define PTXFE_ZERO (1<<8)
-
#define NPTXFE_HALF (0<<7)
-
#define NPTXFE_ZERO (1<<7)
-
#define MODE_SLAVE (0<<5)
-
#define MODE_DMA (1<<5)
-
#define BURST_SINGLE (0<<1)
-
#define BURST_INCR (1<<1)
-
#define BURST_INCR4 (3<<1)
-
#define BURST_INCR8 (5<<1)
-
#define BURST_INCR16 (7<<1)
-
#define GBL_INT_UNMASK (1<<0)
-
#define GBL_INT_MASK (0<<0)
-
-
/* S5P_OTG_GRSTCTL*/
-
#define AHB_MASTER_IDLE (1u<<31)
-
#define CORE_SOFT_RESET (0x1<<0)
-
-
/* S5P_OTG_GINTSTS/S5P_OTG_GINTMSK core interrupt register */
-
#define INT_RESUME (1u<<31)
-
#define INT_DISCONN (0x1<<29)
-
#define INT_CONN_ID_STS_CNG (0x1<<28)
-
#define INT_OUT_EP (0x1<<19)
-
#define INT_IN_EP (0x1<<18)
-
#define INT_ENUMDONE (0x1<<13)
-
#define INT_RESET (0x1<<12)
-
#define INT_SUSPEND (0x1<<11)
-
#define INT_TX_FIFO_EMPTY (0x1<<5)
-
#define INT_RX_FIFO_NOT_EMPTY (0x1<<4)
-
#define INT_SOF (0x1<<3)
-
#define INT_DEV_MODE (0x0<<0)
-
#define INT_HOST_MODE (0x1<<1)
-
-
/* S5P_OTG_GRXSTSP STATUS*/
-
#define GLOBAL_OUT_NAK (0x1<<17)
-
#define OUT_PKT_RECEIVED (0x2<<17)
-
#define OUT_TRNASFER_COMPLETED (0x3<<17)
-
#define SETUP_TRANSACTION_COMPLETED (0x4<<17)
-
#define SETUP_PKT_RECEIVED (0x6<<17)
-
-
/* S5P_OTG_DCTL device control register */
-
#define NORMAL_OPERATION (0x1<<0)
-
#define SOFT_DISCONNECT (0x1<<1)
-
#define TEST_J_MODE (TEST_J<<4)
-
#define TEST_K_MODE (TEST_K<<4)
-
#define TEST_SE0_NAK_MODE (TEST_SE0_NAK<<4)
-
#define TEST_PACKET_MODE (TEST_PACKET<<4)
-
#define TEST_FORCE_ENABLE_MODE (TEST_FORCE_ENABLE<<4)
-
#define TEST_CONTROL_FIELD (0x7<<4)
-
-
/* S5P_OTG_DAINT device all endpoint interrupt register */
-
#define INT_IN_EP0 (0x1<<0)
-
#define INT_IN_EP1 (0x1<<1)
-
#define INT_IN_EP3 (0x1<<3)
-
#define INT_OUT_EP0 (0x1<<16)
-
#define INT_OUT_EP2 (0x1<<18)
-
#define INT_OUT_EP4 (0x1<<20)
-
-
/* S5P_OTG_DIEPCTL0/S5P_OTG_DOEPCTL0 */
-
#define DEPCTL_EPENA (0x1<<31)
-
#define DEPCTL_EPDIS (0x1<<30)
-
#define DEPCTL_SNAK (0x1<<27)
-
#define DEPCTL_CNAK (0x1<<26)
-
#define DEPCTL_CTRL_TYPE (EP_TYPE_CONTROL<<18)
-
#define DEPCTL_ISO_TYPE (EP_TYPE_ISOCHRONOUS<<18)
-
#define DEPCTL_BULK_TYPE (EP_TYPE_BULK<<18)
-
#define DEPCTL_INTR_TYPE (EP_TYPE_INTERRUPT<<18)
-
#define DEPCTL_USBACTEP (0x1<<15)
-
-
/*ep0 enable, clear nak, next ep0, max 64byte */
-
#define EPEN_CNAK_EP0_64 (DEPCTL_EPENA|DEPCTL_CNAK|(CONTROL_EP<<11)|(0<<0))
-
-
/*ep0 enable, clear nak, next ep0, 8byte */
-
#define EPEN_CNAK_EP0_8 (DEPCTL_EPENA|DEPCTL_CNAK|(CONTROL_EP<<11)|(3<<0))
-
-
/* DIEPCTLn/DOEPCTLn */
-
#define BACK2BACK_SETUP_RECEIVED (0x1<<6)
-
#define INTKN_TXFEMP (0x1<<4)
-
#define NON_ISO_IN_EP_TIMEOUT (0x1<<3)
-
#define CTRL_OUT_EP_SETUP_PHASE_DONE (0x1<<3)
-
#define AHB_ERROR (0x1<<2)
-
#define TRANSFER_DONE (0x1<<0)
-
-
-
/* codes representing languages */
-
const u8 string_desc0[] =
-
{
-
4, STRING_DESCRIPTOR, LANGID_US_L, LANGID_US_H,
-
};
-
-
const u8 string_desc1[] = /* Manufacturer */
-
{
-
(0x14+2), STRING_DESCRIPTOR,
-
'S', 0x0, 'y', 0x0, 's', 0x0, 't', 0x0, 'e', 0x0,
-
'm', 0x0, ' ', 0x0, 'M', 0x0, 'C', 0x0, 'U', 0x0,
-
};
-
-
const u8 string_desc2[] = /* Product */
-
{
-
(0x2a+2), STRING_DESCRIPTOR,
-
'S', 0x0, 'E', 0x0, 'C', 0x0, ' ', 0x0, 'S', 0x0,
-
'3', 0x0, 'C', 0x0, '6', 0x0, '4', 0x0, '0', 0x0,
-
'0', 0x0, 'X', 0x0, ' ', 0x0, 'T', 0x0, 'e', 0x0,
-
's', 0x0, 't', 0x0, ' ', 0x0, 'B', 0x0, '/', 0x0,
-
'D', 0x0
-
};
-
-
/* setting the device qualifier descriptor and a string descriptor */
-
const u8 qualifier_desc[] =
-
{
-
0x0a, /* 0 desc size */
-
0x06, /* 1 desc type (DEVICE_QUALIFIER)*/
-
0x00, /* 2 USB release */
-
0x02, /* 3 => 2.00*/
-
0xFF, /* 4 class */
-
0x00, /* 5 subclass */
-
0x00, /* 6 protocol */
-
64, /* 7 max pack size */
-
0x01, /* 8 number of other-speed configuration */
-
0x00, /* 9 reserved */
-
};
-
-
const u8 config_full[] =
-
{
-
0x09, /* 0 desc size */
-
0x07, /* 1 desc type (other speed)*/
-
0x20, /* 2 Total length of data returned */
-
0x00, /* 3 */
-
0x01, /* 4 Number of interfaces supported by this speed configuration */
-
0x01, /* 5 value to use to select configuration */
-
0x00, /* 6 index of string desc */
-
/* 7 same as configuration desc */
-
CONF_ATTR_DEFAULT|CONF_ATTR_SELFPOWERED,
-
0x19, /* 8 same as configuration desc */
-
-
};
-
-
const u8 config_full_total[] =
-
{
-
0x09, 0x07 ,0x20 ,0x00 ,0x01 ,0x01 ,0x00 ,0xC0 ,0x19,
-
0x09 ,0x04 ,0x00 ,0x00 ,0x02 ,0xff ,0x00 ,0x00 ,0x00,
-
0x07 ,0x05 ,0x83 ,0x02 ,0x40 ,0x00 ,0x00,
-
0x07 ,0x05 ,0x04 ,0x02 ,0x40 ,0x00 ,0x00
-
};
-
-
const u8 config_high[] =
-
{
-
0x09, /* 0 desc size */
-
0x07, /* 1 desc type (other speed)*/
-
0x20, /* 2 Total length of data returned */
-
0x00, /* 3 */
-
0x01, /* 4 Number of interfaces supported by this speed configuration */
-
0x01, /* 5 value to use to select configuration */
-
0x00, /* 6 index of string desc */
-
/* 7 same as configuration desc */
-
CONF_ATTR_DEFAULT|CONF_ATTR_SELFPOWERED,
-
0x19, /* 8 same as configuration desc */
-
-
};
-
-
const u8 config_high_total[] =
-
{
-
0x09, 0x07 ,0x20 ,0x00 ,0x01 ,0x01 ,0x00 ,0xC0 ,0x19,
-
0x09 ,0x04 ,0x00 ,0x00 ,0x02 ,0xff ,0x00 ,0x00 ,0x00,
-
0x07 ,0x05 ,0x81 ,0x02 ,0x00 ,0x02 ,0x00,
-
0x07 ,0x05 ,0x02 ,0x02 ,0x00 ,0x02 ,0x00
-
};
-
-
/* Descriptor size */
-
enum DESCRIPTOR_SIZE
-
{
-
DEVICE_DESC_SIZE = sizeof(device_desc_t),
-
STRING_DESC0_SIZE = sizeof(string_desc0),
-
STRING_DESC1_SIZE = sizeof(string_desc1),
-
STRING_DESC2_SIZE = sizeof(string_desc2),
-
CONFIG_DESC_SIZE = sizeof(config_desc_t),
-
INTERFACE_DESC_SIZE = sizeof(intf_desc_t),
-
ENDPOINT_DESC_SIZE = sizeof(ep_desc_t),
-
DEVICE_QUALIFIER_SIZE = sizeof(qualifier_desc),
-
OTHER_SPEED_CFG_SIZE = 9
-
-
};
-
-
/*32 <cfg desc>+<if desc>+<endp0 desc>+<endp1 desc>*/
-
#define CONFIG_DESC_TOTAL_SIZE \
-
(CONFIG_DESC_SIZE+INTERFACE_DESC_SIZE+ENDPOINT_DESC_SIZE*2)
-
#define TEST_PKT_SIZE 53
-
-
u8 test_pkt [TEST_PKT_SIZE] = {
-
0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, /*JKJKJKJK x 9*/
-
0xAA,0xAA,0xAA,0xAA,0xAA,0xAA,0xAA,0xAA, /*JJKKJJKK x 8*/
-
0xEE,0xEE,0xEE,0xEE,0xEE,0xEE,0xEE,0xEE, /*JJJJKKKK x 8*/
-
0xFE,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF, /*JJJJJJJKKKKKKK x8 - '1'*/
-
0x7F,0xBF,0xDF,0xEF,0xF7,0xFB,0xFD, /*'1' + JJJJJJJK x 8*/
-
0xFC,0x7E,0xBF,0xDF,0xEF,0xF7,0xFB,0xFD,0x7E /*{JKKKKKKK x 10},JK*/
-
};
-
-
void s3c_usb_init_phy(void)
-
{
-
writel(readl(USB_PHY_CONTROL)|(1<<0), USB_PHY_CONTROL); /*USB PHY0 Enable */
-
-
writel(0xa0, S5P_OTG_PHYPWR);
-
writel(0x3, S5P_OTG_PHYCLK);
-
writel(0x1, S5P_OTG_RSTCON);
-
udelay(10);
-
writel(0x0, S5P_OTG_RSTCON);
-
udelay(10);
-
-
}
-
-
/* OTG PHY Power Off */
-
void s3c_usb_phy_off(void) {
-
writel(readl(S5P_OTG_PHYPWR)|(0x18), S5P_OTG_PHYPWR);
-
writel(readl(USB_PHY_CONTROL)&~(1<<0), USB_PHY_CONTROL);
-
s3c_usb_phy_inited=0;
-
}
-
-
void s3c_usb_core_soft_reset(void)
-
{
-
u32 tmp;
-
-
writel(CORE_SOFT_RESET, S5P_OTG_GRSTCTL);
-
-
do
-
{
-
tmp = readl(S5P_OTG_GRSTCTL);
-
}while(!(tmp & AHB_MASTER_IDLE));
-
-
}
-
-
void s3c_usb_wait_cable_insert(void)
-
{
-
u32 tmp;
-
int ucFirst=1;
-
-
do {
-
udelay(50);
-
-
tmp = readl(S5P_OTG_GOTGCTL);
-
-
if (tmp & (B_SESSION_VALID|A_SESSION_VALID)) {
-
printf("OTG cable Connected!\n");
-
break;
-
} else if(ucFirst == 1) {
-
printf("Insert a OTG cable into the connector!\n");
-
ucFirst = 0;
-
}
-
} while(1);
-
}
-
-
void s3c_usb_init_core(void)
-
{
-
writel(PTXFE_HALF|NPTXFE_HALF|MODE_SLAVE|BURST_SINGLE|GBL_INT_UNMASK,
-
S5P_OTG_GAHBCFG);
-
-
writel( 0<<15 /* PHY Low Power Clock sel */
-
|1<<14 /* Non-Periodic TxFIFO Rewind Enable */
-
|0x5<<10 /* Turnaround time */
-
|0<<9 /* 0:HNP disable, 1:HNP enable */
-
|0<<8 /* 0:SRP disable, 1:SRP enable */
-
|0<<7 /* ULPI DDR sel */
-
|0<<6 /* 0: high speed utmi+, 1: full speed serial */
-
|0<<4 /* 0: utmi+, 1:ulpi */
-
|1<<3 /* phy i/f 0:8bit, 1:16bit */
-
|0x7<<0, /* HS/FS Timeout**/
-
S5P_OTG_GUSBCFG );
-
}
-
-
void s3c_usb_check_current_mode(u8 *pucMode)
-
{
-
u32 tmp;
-
-
tmp = readl(S5P_OTG_GINTSTS);
-
*pucMode = tmp & 0x1;
-
}
-
-
void s3c_usb_set_soft_disconnect(void)
-
{
-
u32 tmp;
-
-
tmp = readl(S5P_OTG_DCTL);
-
tmp |= SOFT_DISCONNECT;
-
writel(tmp, S5P_OTG_DCTL);
-
}
-
-
void s3c_usb_clear_soft_disconnect(void)
-
{
-
u32 tmp;
-
-
tmp = readl(S5P_OTG_DCTL);
-
tmp &= ~SOFT_DISCONNECT;
-
writel(tmp, S5P_OTG_DCTL);
-
}
-
-
void s3c_usb_init_device(void)
-
{
-
writel(1<<18|otg.speed<<0, S5P_OTG_DCFG); /* [][1: full speed(30Mhz) 0:high speed]*/
-
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|
-
INT_RESET|INT_SUSPEND|INT_RX_FIFO_NOT_EMPTY,
-
S5P_OTG_GINTMSK); /*gint unmask */
-
s3c_usb_phy_inited=1;
-
}
-
-
int s3c_usbctl_init(int ischeckstatus)/*diog, if not for check status, donot need wait cable insert*/
-
{
-
u8 ucMode;
-
-
DBG_SETUP0("USB Control Init\n");
-
-
otg.speed = speed;
-
otg.set_config = 0;
-
otg.ep0_state = EP0_STATE_INIT;
-
otg.ep0_substate = 0;
-
s3c_usb_init_phy();
-
s3c_usb_core_soft_reset();
-
if(!ischeckstatus)
-
s3c_usb_wait_cable_insert();
-
s3c_usb_init_core();
-
s3c_usb_check_current_mode(&ucMode);
-
-
if (ucMode == INT_DEV_MODE) {
-
s3c_usb_set_soft_disconnect();
-
udelay(10);
-
s3c_usb_clear_soft_disconnect();
-
s3c_usb_init_device();
-
return 0;
-
} else {
-
printf("Error : Current Mode is Host\n");
-
return 0;
-
}
-
}
-
-
int s3c_usbc_activate (void)
-
{
-
/* dont used in usb high speed, but used in common file cmd_usbd.c */
-
return 0;
-
}
-
-
int s3c_usb_stop (void)
-
{
-
/* dont used in usb high speed, but used in common file cmd_usbd.c */
-
s3c_usb_core_soft_reset();
-
s3c_usb_phy_off();
-
return 0;
-
}
-
-
void s3c_usb_print_pkt(u8 *pt, u8 count)
-
{
-
int i;
-
printf("[s3c_usb_print_pkt:");
-
-
for(i=0;i<count;i++)
-
printf("%x,", pt[i]);
-
-
printf("]\n");
-
}
-
-
void s3c_usb_verify_checksum(void)
-
{
-
u8 *cs_start, *cs_end;
-
u16 dnCS;
-
u16 checkSum;
-
-
printf("Checksum is being calculated.");
-
-
/* checksum calculation */
-
cs_start = (u8*)otg.dn_addr;
-
cs_end = (u8*)(otg.dn_addr+otg.dn_filesize-10);
-
checkSum = 0;
-
while(cs_start < cs_end) {
-
checkSum += *cs_start++;
-
if(((u32)cs_start&0xfffff)==0) printf(".");
-
}
-
-
/* fixed alignment fault in case when cs_end is odd. */
-
dnCS = (u16)((cs_end[1]<<8) + cs_end[0]);
-
//dnCS = *(u16 *)cs_end;
-
-
if (checkSum == dnCS)
-
{
-
printf("\nChecksum O.K.\n");
-
}
-
else
-
{
-
printf("\nChecksum Value => MEM:%x DNW:%x\n",checkSum,dnCS);
-
printf("Checksum failed.\n\n");
-
}
-
-
}
-
-
void s3c_usb_set_inep_xfersize(EP_TYPE type, u32 pktcnt, u32 xfersize)
-
{
-
if(type == EP_TYPE_CONTROL)
-
{
-
writel((pktcnt<<19)|(xfersize<<0), S5P_OTG_DIEPTSIZ0);
-
}
-
else if(type == EP_TYPE_BULK)
-
{
-
writel((1<<29)|(pktcnt<<19)|(xfersize<<0), S5P_OTG_DIEPTSIZ_IN);
-
}
-
}
-
-
void s3c_usb_set_outep_xfersize(EP_TYPE type, u32 pktcnt, u32 xfersize)
-
{
-
if(type == EP_TYPE_CONTROL)
-
{
-
writel((1<<29)|(pktcnt<<19)|(xfersize<<0), S5P_OTG_DOEPTSIZ0);
-
}
-
else if(type == EP_TYPE_BULK)
-
{
-
writel((pktcnt<<19)|(xfersize<<0), S5P_OTG_DOEPTSIZ_OUT);
-
}
-
}
-
-
void s3c_usb_write_ep0_fifo(u8 *buf, int num)
-
{
-
int i;
-
u32 Wr_Data=0;
-
-
DBG_SETUP1("[s3c_usb_write_ep0_fifo:");
-
-
for(i=0;i<num;i+=4)
-
{
-
Wr_Data = ((*(buf+3))<<24)|((*(buf+2))<<16)|((*(buf+1))<<8)|*buf;
-
DBG_SETUP2(" 0x%08x,", Wr_Data);
-
writel(Wr_Data, S5P_OTG_EP0_FIFO);
-
buf += 4;
-
}
-
-
DBG_SETUP2("]\n");
-
}
-
-
-
void s3c_usb_write_in_fifo(u8 *buf, int num)
-
{
-
int i;
-
u32 data=0;
-
-
for(i=0;i<num;i+=4)
-
{
-
data=((*(buf+3))<<24)|((*(buf+2))<<16)|((*(buf+1))<<8)|*buf;
-
writel(data, S5P_OTG_IN_FIFO);
-
buf += 4;
-
}
-
}
-
-
void s3c_usb_read_out_fifo(u8 *buf, int num)
-
{
-
int i;
-
u32 data;
-
-
for (i=0;i<num;i+=4)
-
{
-
data = readl(S5P_OTG_OUT_FIFO);
-
-
buf[i] = (u8)data;
-
buf[i+1] = (u8)(data>>8);
-
buf[i+2] = (u8)(data>>16);
-
buf[i+3] = (u8)(data>>24);
-
}
-
}
-
-
void s3c_usb_get_desc(void)
-
{
-
switch (otg.dev_req.wValue_H) {
-
case DEVICE_DESCRIPTOR:
-
otg.req_length = (u32)((otg.dev_req.wLength_H << 8) |
-
otg.dev_req.wLength_L);
-
DBG_SETUP1("DEVICE_DESCRIPTOR = 0x%x \n",otg.req_length);
-
otg.ep0_state = EP0_STATE_GD_DEV_0;
-
break;
-
-
case CONFIGURATION_DESCRIPTOR:
-
otg.req_length = (u32)((otg.dev_req.wLength_H << 8) |
-
otg.dev_req.wLength_L);
-
DBG_SETUP1("CONFIGURATION_DESCRIPTOR = 0x%x \n",otg.req_length);
-
-
/* GET_DESCRIPTOR:CONFIGURATION+INTERFACE+ENDPOINT0+ENDPOINT1 */
-
if (otg.req_length > CONFIG_DESC_SIZE){
-
otg.ep0_state = EP0_STATE_GD_CFG_0;
-
} else
-
otg.ep0_state = EP0_STATE_GD_CFG_ONLY_0;
-
break;
-
-
case STRING_DESCRIPTOR :
-
DBG_SETUP1("STRING_DESCRIPTOR \n");
-
-
switch(otg.dev_req.wValue_L) {
-
case 0:
-
otg.ep0_state = EP0_STATE_GD_STR_I0;
-
break;
-
case 1:
-
otg.ep0_state = EP0_STATE_GD_STR_I1;
-
break;
-
case 2:
-
otg.ep0_state = EP0_STATE_GD_STR_I2;
-
break;
-
default:
-
break;
-
}
-
break;
-
-
case ENDPOINT_DESCRIPTOR:
-
DBG_SETUP1("ENDPOINT_DESCRIPTOR \n");
-
switch(otg.dev_req.wValue_L&0xf) {
-
case 0:
-
otg.ep0_state=EP0_STATE_GD_EP0_ONLY_0;
-
break;
-
case 1:
-
otg.ep0_state=EP0_STATE_GD_EP1_ONLY_0;
-
break;
-
default:
-
break;
-
}
-
break;
-
-
case DEVICE_QUALIFIER:
-
otg.req_length = (u32)((otg.dev_req.wLength_H << 8) |
-
otg.dev_req.wLength_L);
-
DBG_SETUP1("DEVICE_QUALIFIER = 0x%x \n",otg.req_length);
-
otg.ep0_state = EP0_STATE_GD_DEV_QUALIFIER;
-
break;
-
-
case OTHER_SPEED_CONFIGURATION :
-
DBG_SETUP1("OTHER_SPEED_CONFIGURATION \n");
-
otg.req_length = (u32)((otg.dev_req.wLength_H << 8) |
-
otg.dev_req.wLength_L);
-
otg.ep0_state = EP0_STATE_GD_OTHER_SPEED;
-
break;
-
-
}
-
}
-
-
void s3c_usb_clear_feature(void)
-
{
-
switch (otg.dev_req.bmRequestType) {
-
case DEVICE_RECIPIENT:
-
DBG_SETUP1("DEVICE_RECIPIENT \n");
-
if (otg.dev_req.wValue_L == 1)
-
remode_wakeup = FALSE;
-
break;
-
-
case ENDPOINT_RECIPIENT:
-
DBG_SETUP1("ENDPOINT_RECIPIENT \n");
-
if (otg.dev_req.wValue_L == 0) {
-
if ((otg.dev_req.wIndex_L & 0x7f) == CONTROL_EP)
-
get_status.ep_ctrl= 0;
-
-
/* IN Endpoint */
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_IN_EP)
-
get_status.ep_in= 0;
-
-
/* OUT Endpoint */
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_OUT_EP)
-
get_status.ep_out= 0;
-
}
-
break;
-
-
default:
-
DBG_SETUP1("\n");
-
break;
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
-
}
-
-
void s3c_usb_set_feature(void)
-
{
-
u32 tmp;
-
-
switch (otg.dev_req.bmRequestType) {
-
case DEVICE_RECIPIENT:
-
DBG_SETUP1("DEVICE_RECIPIENT \n");
-
if (otg.dev_req.wValue_L == 1)
-
remode_wakeup = TRUE;
-
break;
-
-
case ENDPOINT_RECIPIENT:
-
DBG_SETUP1("ENDPOINT_RECIPIENT \n");
-
if (otg.dev_req.wValue_L == 0) {
-
if ((otg.dev_req.wIndex_L & 0x7f) == CONTROL_EP)
-
get_status.ep_ctrl= 1;
-
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_IN_EP)
-
get_status.ep_in= 1;
-
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_OUT_EP)
-
get_status.ep_out= 1;
-
}
-
break;
-
-
default:
-
DBG_SETUP1("\n");
-
break;
-
}
-
-
switch (otg.dev_req.wValue_L) {
-
case EP_STALL:
-
/* TBD: additional processing if required */
-
break;
-
-
case TEST_MODE:
-
if ((0 != otg.dev_req.wIndex_L ) ||(0 != otg.dev_req.bmRequestType))
-
break;
-
-
/* Set TEST MODE*/
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_FORCE_ENABLE_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
-
switch(otg.dev_req.wIndex_H) {
-
case TEST_J:
-
/*Set Test J*/
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_J_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
break;
-
-
case TEST_K:
-
/*Set Test K*/
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_K_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
break;
-
-
case TEST_SE0_NAK:
-
/*Set Test SE0NAK*/
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_SE0_NAK_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
break;
-
-
case TEST_PACKET:
-
DBG_SETUP1 ("Test_packet\n");
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, TEST_PKT_SIZE);
-
s3c_usb_write_ep0_fifo(test_pkt, TEST_PKT_SIZE);
-
tmp = readl(S5P_OTG_DCTL);
-
tmp = (tmp & ~(TEST_CONTROL_FIELD)) | (TEST_PACKET_MODE);
-
writel(tmp, S5P_OTG_DCTL);
-
DBG_SETUP1 ("S5P_OTG_DCTL=0x%08x\n", tmp);
-
break;
-
}
-
break;
-
-
default:
-
break;
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
-
}
-
-
void s3c_usb_get_status(void)
-
{
-
switch(otg.dev_req.bmRequestType) {
-
case (0x80): /*device */
-
DBG_SETUP1("DEVICE\n");
-
get_status.Device=((u8)remode_wakeup<<1)|0x1; /* SelfPowered */
-
otg.ep0_state = EP0_STATE_GET_STATUS0;
-
break;
-
-
case (0x81): /*interface */
-
DBG_SETUP1("INTERFACE\n");
-
get_status.Interface=0;
-
otg.ep0_state = EP0_STATE_GET_STATUS1;
-
break;
-
-
case (0x82): /*endpoint */
-
DBG_SETUP1("ENDPOINT\n");
-
if ((otg.dev_req.wIndex_L & 0x7f) == CONTROL_EP)
-
otg.ep0_state = EP0_STATE_GET_STATUS2;
-
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_IN_EP)
-
otg.ep0_state = EP0_STATE_GET_STATUS3;
-
-
if ((otg.dev_req.wIndex_L & 0x7f) == BULK_OUT_EP)
-
otg.ep0_state = EP0_STATE_GET_STATUS4;
-
break;
-
-
default:
-
DBG_SETUP1("\n");
-
break;
-
}
-
-
}
-
-
void s3c_usb_ep0_int_hndlr(void)
-
{
-
u16 i;
-
u32 buf[2]={0x0000, };
-
u16 addr;
-
-
DBG_SETUP0("Event EP0\n");
-
-
if (otg.ep0_state == EP0_STATE_INIT) {
-
-
for(i=0;i<2;i++)
-
buf[i] = readl(S5P_OTG_EP0_FIFO);
-
-
otg.dev_req.bmRequestType = buf[0];
-
otg.dev_req.bRequest = buf[0]>>8;
-
otg.dev_req.wValue_L = buf[0]>>16;
-
otg.dev_req.wValue_H = buf[0]>>24;
-
otg.dev_req.wIndex_L = buf[1];
-
otg.dev_req.wIndex_H = buf[1]>>8;
-
otg.dev_req.wLength_L = buf[1]>>16;
-
otg.dev_req.wLength_H = buf[1]>>24;
-
-
#ifdef USB_OTG_DEBUG_SETUP
-
s3c_usb_print_pkt((u8 *)&otg.dev_req, 8);
-
#endif
-
-
switch (otg.dev_req.bRequest) {
-
case STANDARD_SET_ADDRESS:
-
/* Set Address Update bit */
-
addr = (otg.dev_req.wValue_L);
-
writel(1<<18|addr<<4|otg.speed<<0, S5P_OTG_DCFG);
-
DBG_SETUP1("S5P_OTG_DCFG : %x, STANDARD_SET_ADDRESS : %d\n",
-
readl(S5P_OTG_DCFG), addr);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case STANDARD_SET_DESCRIPTOR:
-
DBG_SETUP1("STANDARD_SET_DESCRIPTOR \n");
-
break;
-
-
case STANDARD_SET_CONFIGURATION:
-
DBG_SETUP1("STANDARD_SET_CONFIGURATION \n");
-
/* Configuration value in configuration descriptor */
-
config_value = otg.dev_req.wValue_L;
-
otg.set_config = 1;
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case STANDARD_GET_CONFIGURATION:
-
DBG_SETUP1("STANDARD_GET_CONFIGURATION \n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
-
/*ep0 enable, clear nak, next ep0, 8byte */
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
writel(config_value, S5P_OTG_EP0_FIFO);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case STANDARD_GET_DESCRIPTOR:
-
DBG_SETUP1("STANDARD_GET_DESCRIPTOR :");
-
s3c_usb_get_desc();
-
break;
-
-
case STANDARD_CLEAR_FEATURE:
-
DBG_SETUP1("STANDARD_CLEAR_FEATURE :");
-
s3c_usb_clear_feature();
-
break;
-
-
case STANDARD_SET_FEATURE:
-
DBG_SETUP1("STANDARD_SET_FEATURE :");
-
s3c_usb_set_feature();
-
break;
-
-
case STANDARD_GET_STATUS:
-
DBG_SETUP1("STANDARD_GET_STATUS :");
-
s3c_usb_get_status();
-
break;
-
-
case STANDARD_GET_INTERFACE:
-
DBG_SETUP1("STANDARD_GET_INTERFACE \n");
-
otg.ep0_state = EP0_STATE_INTERFACE_GET;
-
break;
-
-
case STANDARD_SET_INTERFACE:
-
DBG_SETUP1("STANDARD_SET_INTERFACE \n");
-
get_intf.AlternateSetting= otg.dev_req.wValue_L;
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case STANDARD_SYNCH_FRAME:
-
DBG_SETUP1("STANDARD_SYNCH_FRAME \n");
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
default:
-
break;
-
}
-
}
-
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.ctrl_max_pktsize);
-
-
if(otg.speed == USB_HIGH) {
-
/*clear nak, next ep0, 64byte */
-
writel(((1<<26)|(CONTROL_EP<<11)|(0<<0)), S5P_OTG_DIEPCTL0);
-
}
-
else {
-
/*clear nak, next ep0, 8byte */
-
writel(((1<<26)|(CONTROL_EP<<11)|(3<<0)), S5P_OTG_DIEPCTL0);
-
}
-
-
}
-
-
void s3c_usb_set_otherspeed_conf_desc(u32 length)
-
{
-
/* Standard device descriptor */
-
if (otg.speed == USB_HIGH)
-
{
-
if (length ==9)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 9);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_full)+0, 9);
-
}
-
else if(length ==32)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 32);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_full_total)+0, 32);
-
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
if (length ==9)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+0, 8);
-
}
-
else if(length ==32)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high_total)+0, 8);
-
}
-
otg.ep0_state = EP0_STATE_GD_OTHER_SPEED_HIGH_1;
-
}
-
}
-
-
void s3c_usb_transfer_ep0(void)
-
{
-
-
DBG_SETUP0("otg.ep0_state = %d\n", otg.ep0_state);
-
-
switch (otg.ep0_state) {
-
case EP0_STATE_INIT:
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 0);
-
-
/*ep0 enable, clear nak, next ep0, 8byte */
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
DBG_SETUP1("EP0_STATE_INIT\n");
-
break;
-
-
/* GET_DESCRIPTOR:DEVICE */
-
case EP0_STATE_GD_DEV_0:
-
DBG_SETUP1("EP0_STATE_GD_DEV_0 :");
-
if (otg.speed == USB_HIGH) {
-
DBG_SETUP1("High Speed\n");
-
-
/*ep0 enable, clear nak, next ep0, max 64byte */
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
if (otg.req_length < DEVICE_DESC_SIZE) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+0, otg.req_length);
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, DEVICE_DESC_SIZE);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+0, DEVICE_DESC_SIZE);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
} else {
-
DBG_SETUP1("Full Speed\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<DEVICE_DESC_SIZE) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, DEVICE_DESC_SIZE);
-
}
-
-
if(otg.req_length<FS_CTRL_PKT_SIZE) {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+0, otg.req_length);
-
otg.ep0_state = EP0_STATE_INIT;
-
} else {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+0, FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_DEV_1;
-
}
-
}
-
break;
-
-
case EP0_STATE_GD_DEV_1:
-
DBG_SETUP1("EP0_STATE_GD_DEV_1\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<(2*FS_CTRL_PKT_SIZE)) {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+FS_CTRL_PKT_SIZE,
-
(otg.req_length-FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
} else {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+FS_CTRL_PKT_SIZE,
-
FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_DEV_2;
-
}
-
break;
-
-
case EP0_STATE_GD_DEV_2:
-
DBG_SETUP1("EP0_STATE_GD_DEV_2\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<DEVICE_DESC_SIZE) {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+(2*FS_CTRL_PKT_SIZE),
-
(otg.req_length-2*FS_CTRL_PKT_SIZE));
-
} else {
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.dev))+(2*FS_CTRL_PKT_SIZE),
-
(DEVICE_DESC_SIZE-2*FS_CTRL_PKT_SIZE));
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:CONFIGURATION+INTERFACE+ENDPOINT0+ENDPOINT1 */
-
case EP0_STATE_GD_CFG_0:
-
DBG_SETUP1("EP0_STATE_GD_CFG_0 :");
-
if (otg.speed == USB_HIGH)
-
{
-
DBG_SETUP1("High Speed\n");
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<CONFIG_DESC_TOTAL_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, CONFIG_DESC_TOTAL_SIZE);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, CONFIG_DESC_TOTAL_SIZE);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
DBG_SETUP1("Full Speed\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<CONFIG_DESC_TOTAL_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, CONFIG_DESC_TOTAL_SIZE);
-
}
-
if(otg.req_length<FS_CTRL_PKT_SIZE)
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, otg.req_length);
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_1;
-
}
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_1:
-
DBG_SETUP1("EP0_STATE_GD_CFG_1\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<(2*FS_CTRL_PKT_SIZE))
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+FS_CTRL_PKT_SIZE,
-
(otg.req_length-FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+FS_CTRL_PKT_SIZE,
-
FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_2;
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_2:
-
DBG_SETUP1("EP0_STATE_GD_CFG_2\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<(3*FS_CTRL_PKT_SIZE))
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+(2*FS_CTRL_PKT_SIZE),
-
(otg.req_length-2*FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+(2*FS_CTRL_PKT_SIZE),
-
FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_3;
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_3:
-
DBG_SETUP1("EP0_STATE_GD_CFG_3\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<(4*FS_CTRL_PKT_SIZE))
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+(3*FS_CTRL_PKT_SIZE),
-
(otg.req_length-3*FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+(3*FS_CTRL_PKT_SIZE),
-
FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_4;
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_4:
-
DBG_SETUP1("EP0_STATE_GD_CFG_4\n");
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GD_DEV_QUALIFIER: /*only supported in USB 2.0*/
-
DBG_SETUP1("EP0_STATE_GD_DEV_QUALIFIER\n");
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<10)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
s3c_usb_write_ep0_fifo((u8 *)qualifier_desc+0, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 10);
-
s3c_usb_write_ep0_fifo((u8 *)qualifier_desc+0, 10);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GD_OTHER_SPEED:
-
DBG_SETUP1("EP0_STATE_GD_OTHER_SPEED\n");
-
s3c_usb_set_otherspeed_conf_desc(otg.req_length);
-
break;
-
-
case EP0_STATE_GD_OTHER_SPEED_HIGH_1:
-
DBG_SETUP1("EP0_STATE_GD_OTHER_SPEED_HIGH_1\n");
-
if(otg.req_length==9)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+8, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+8, 8);
-
otg.ep0_state = EP0_STATE_GD_OTHER_SPEED_HIGH_2;
-
}
-
break;
-
-
case EP0_STATE_GD_OTHER_SPEED_HIGH_2:
-
DBG_SETUP1("EP0_STATE_GD_OTHER_SPEED_HIGH_2\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+16, 8);
-
otg.ep0_state = EP0_STATE_GD_OTHER_SPEED_HIGH_3;
-
break;
-
-
case EP0_STATE_GD_OTHER_SPEED_HIGH_3:
-
DBG_SETUP1("EP0_STATE_GD_OTHER_SPEED_HIGH_3\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&config_high)+24, 8);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:CONFIGURATION ONLY*/
-
case EP0_STATE_GD_CFG_ONLY_0:
-
DBG_SETUP1("EP0_STATE_GD_CFG_ONLY_0:");
-
if (otg.speed == USB_HIGH)
-
{
-
DBG_SETUP1("High Speed\n");
-
if(otg.req_length<CONFIG_DESC_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, CONFIG_DESC_SIZE);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0,
-
CONFIG_DESC_SIZE);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
DBG_SETUP1("Full Speed\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<CONFIG_DESC_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, CONFIG_DESC_SIZE);
-
}
-
if(otg.req_length<FS_CTRL_PKT_SIZE)
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, otg.req_length);
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+0, FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_CFG_ONLY_1;
-
}
-
}
-
break;
-
-
case EP0_STATE_GD_CFG_ONLY_1:
-
DBG_SETUP1("EP0_STATE_GD_CFG_ONLY_1\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.config))+FS_CTRL_PKT_SIZE,
-
(CONFIG_DESC_SIZE-FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:INTERFACE ONLY */
-
-
case EP0_STATE_GD_IF_ONLY_0:
-
DBG_SETUP1("EP0_STATE_GD_IF_ONLY_0 :");
-
if (otg.speed == USB_HIGH)
-
{
-
DBG_SETUP1("High Speed\n");
-
if(otg.req_length<INTERFACE_DESC_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+0, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, INTERFACE_DESC_SIZE);
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+0, INTERFACE_DESC_SIZE);
-
}
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
DBG_SETUP1("Full Speed\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
if(otg.req_length<INTERFACE_DESC_SIZE)
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, otg.req_length);
-
}
-
else
-
{
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, INTERFACE_DESC_SIZE);
-
}
-
if(otg.req_length<FS_CTRL_PKT_SIZE)
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+0, otg.req_length);
-
otg.ep0_state = EP0_STATE_INIT;
-
}
-
else
-
{
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+0, FS_CTRL_PKT_SIZE);
-
otg.ep0_state = EP0_STATE_GD_IF_ONLY_1;
-
}
-
}
-
break;
-
-
case EP0_STATE_GD_IF_ONLY_1:
-
DBG_SETUP1("EP0_STATE_GD_IF_ONLY_1\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.intf))+FS_CTRL_PKT_SIZE,
-
(INTERFACE_DESC_SIZE-FS_CTRL_PKT_SIZE));
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
-
/* GET_DESCRIPTOR:ENDPOINT 1 ONLY */
-
case EP0_STATE_GD_EP0_ONLY_0:
-
DBG_SETUP1("EP0_STATE_GD_EP0_ONLY_0\n");
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, ENDPOINT_DESC_SIZE);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.ep1))+0, ENDPOINT_DESC_SIZE);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:ENDPOINT 2 ONLY */
-
case EP0_STATE_GD_EP1_ONLY_0:
-
DBG_SETUP1("EP0_STATE_GD_EP1_ONLY_0\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, ENDPOINT_DESC_SIZE);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo(((u8 *)&(otg.desc.ep2))+0, ENDPOINT_DESC_SIZE);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
/* GET_DESCRIPTOR:STRING */
-
case EP0_STATE_GD_STR_I0:
-
DBG_SETUP1("EP0_STATE_GD_STR_I0\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, STRING_DESC0_SIZE);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc0, STRING_DESC0_SIZE);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GD_STR_I1:
-
DBG_SETUP1("EP0_STATE_GD_STR_I1 %d\n", otg.ep0_substate);
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, sizeof(string_desc1));
-
if ((otg.ep0_substate*otg.ctrl_max_pktsize+otg.ctrl_max_pktsize)
-
< sizeof(string_desc1)) {
-
-
if (otg.speed == USB_HIGH)
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
else
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc1+(otg.ep0_substate*otg.ctrl_max_pktsize),
-
otg.ctrl_max_pktsize);
-
otg.ep0_state = EP0_STATE_GD_STR_I1;
-
otg.ep0_substate++;
-
} else {
-
if (otg.speed == USB_HIGH)
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
else
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc1+(otg.ep0_substate*otg.ctrl_max_pktsize),
-
sizeof(string_desc1)-(otg.ep0_substate*otg.ctrl_max_pktsize));
-
otg.ep0_state = EP0_STATE_INIT;
-
otg.ep0_substate = 0;
-
}
-
break;
-
-
case EP0_STATE_GD_STR_I2:
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, sizeof(string_desc2));
-
if ((otg.ep0_substate*otg.ctrl_max_pktsize+otg.ctrl_max_pktsize)
-
< sizeof(string_desc2)) {
-
-
if (otg.speed == USB_HIGH)
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
else
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc2+(otg.ep0_substate*otg.ctrl_max_pktsize),
-
otg.ctrl_max_pktsize);
-
otg.ep0_state = EP0_STATE_GD_STR_I2;
-
otg.ep0_substate++;
-
} else {
-
if (otg.speed == USB_HIGH)
-
writel(EPEN_CNAK_EP0_64, S5P_OTG_DIEPCTL0);
-
else
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)string_desc2+(otg.ep0_substate*otg.ctrl_max_pktsize),
-
sizeof(string_desc2)-(otg.ep0_substate*otg.ctrl_max_pktsize));
-
otg.ep0_state = EP0_STATE_INIT;
-
otg.ep0_substate = 0;
-
}
-
DBG_SETUP1("EP0_STATE_GD_STR_I2 %d", otg.ep0_substate);
-
break;
-
-
case EP0_STATE_INTERFACE_GET:
-
DBG_SETUP1("EP0_STATE_INTERFACE_GET\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_intf+0, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
-
case EP0_STATE_GET_STATUS0:
-
DBG_SETUP1("EP0_STATE_GET_STATUS0\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+0, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GET_STATUS1:
-
DBG_SETUP1("EP0_STATE_GET_STATUS1\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+1, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GET_STATUS2:
-
DBG_SETUP1("EP0_STATE_GET_STATUS2\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+2, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GET_STATUS3:
-
DBG_SETUP1("EP0_STATE_GET_STATUS3\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+3, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
case EP0_STATE_GET_STATUS4:
-
DBG_SETUP1("EP0_STATE_GET_STATUS4\n");
-
s3c_usb_set_inep_xfersize(EP_TYPE_CONTROL, 1, 1);
-
writel(EPEN_CNAK_EP0_8, S5P_OTG_DIEPCTL0);
-
s3c_usb_write_ep0_fifo((u8 *)&get_status+4, 1);
-
otg.ep0_state = EP0_STATE_INIT;
-
break;
-
-
default:
-
break;
-
}
-
}
-
-
-
void s3c_usb_int_bulkin(void)
-
{
-
u8* bulkin_buf;
-
u32 remain_cnt;
-
-
DBG_BULK0("Bulk In Function\n");
-
-
bulkin_buf = (u8*)otg.up_ptr;
-
remain_cnt = otg.up_size- ((u32)otg.up_ptr - otg.up_addr);
-
DBG_BULK1("bulkin_buf = 0x%x,remain_cnt = 0x%x \n", bulkin_buf, remain_cnt);
-
-
if (remain_cnt > otg.bulkin_max_pktsize) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1, otg.bulkin_max_pktsize);
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
-
s3c_usb_write_in_fifo(bulkin_buf, otg.bulkin_max_pktsize);
-
-
otg.up_ptr += otg.bulkin_max_pktsize;
-
-
} else if(remain_cnt > 0) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1, remain_cnt);
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
-
s3c_usb_write_in_fifo(bulkin_buf, remain_cnt);
-
-
otg.up_ptr += remain_cnt;
-
-
} else { /*remain_cnt = 0*/
-
writel((DEPCTL_SNAK|DEPCTL_BULK_TYPE), S5P_OTG_DIEPCTL_IN);
-
}
-
}
-
-
void s3c_usb_upload_start(void)
-
{
-
u8 tmp_buf[12];
-
u32 check;
-
-
s3c_usb_read_out_fifo((u8 *)tmp_buf, 10);
-
check = *((u8 *)(tmp_buf+8)) + (*((u8 *)(tmp_buf+9))<<8);
-
-
if (check==0x1) {
-
otg.up_addr =
-
*((u8 *)(tmp_buf+0))+
-
(*((u8 *)(tmp_buf+1))<<8)+
-
(*((u8 *)(tmp_buf+2))<<16)+
-
(*((u8 *)(tmp_buf+3))<<24);
-
-
otg.up_size =
-
*((u8 *)(tmp_buf+4))+
-
(*((u8 *)(tmp_buf+5))<<8)+
-
(*((u8 *)(tmp_buf+6))<<16)+
-
(*((u8 *)(tmp_buf+7))<<24);
-
-
otg.up_ptr=(u8 *)otg.up_addr;
-
DBG_BULK1("UploadAddress : 0x%x, UploadSize: %d\n",
-
otg.up_addr, otg.up_size);
-
-
if (otg.op_mode == USB_CPU) {
-
if (otg.up_size > otg.bulkin_max_pktsize) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1,
-
otg.bulkin_max_pktsize);
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1,
-
otg.up_size);
-
}
-
-
/*ep1 enable, clear nak, bulk, usb active, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
} else if ((otg.op_mode == USB_DMA) && (otg.up_size > 0)) {
-
u32 pktcnt, remainder;
-
-
DBG_BULK1("Dma Start for IN PKT \n");
-
-
writel(MODE_DMA|BURST_INCR4|GBL_INT_UNMASK,
-
S5P_OTG_GAHBCFG);
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP| INT_ENUMDONE|
-
INT_RESET|INT_SUSPEND, S5P_OTG_GINTMSK);
-
-
writel((u32)otg.up_ptr, S5P_OTG_DIEPDMA_IN);
-
-
pktcnt = (u32)(otg.up_size/otg.bulkin_max_pktsize);
-
remainder = (u32)(otg.up_size%otg.bulkin_max_pktsize);
-
if(remainder != 0) {
-
pktcnt += 1;
-
}
-
-
if (pktcnt > 1023) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1023,
-
(otg.bulkin_max_pktsize*1023));
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, pktcnt,
-
otg.up_size);
-
}
-
-
/*ep1 enable, clear nak, bulk, usb active, next ep1, max pkt */
-
writel(1u<<31|1<<26|2<<18|1<<15|BULK_IN_EP<<11|
-
otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
}
-
}
-
otg.dn_filesize=0;
-
}
-
-
void s3c_usb_download_start(u32 fifo_cnt_byte)
-
{
-
u8 tmp_buf[8];
-
-
s3c_usb_read_out_fifo((u8 *)tmp_buf, 8);
-
DBG_BULK1("downloadFileSize==0, 1'st BYTE_READ_CNT_REG : %x\n",
-
fifo_cnt_byte);
-
-
otg.dn_addr=s3c_usbd_dn_addr;
-
otg.dn_filesize=
-
*((u8 *)(tmp_buf+4))+
-
(*((u8 *)(tmp_buf+5))<<8)+
-
(*((u8 *)(tmp_buf+6))<<16)+
-
(*((u8 *)(tmp_buf+7))<<24);
-
-
otg.dn_ptr=(u8 *)otg.dn_addr;
-
DBG_BULK1("downloadAddress : 0x%x, downloadFileSize: %x\n",
-
otg.dn_addr, otg.dn_filesize);
-
-
/* The first 8-bytes are deleted.*/
-
s3c_usb_read_out_fifo((u8 *)otg.dn_ptr, fifo_cnt_byte-8);
-
otg.dn_ptr += fifo_cnt_byte-8;
-
-
if (otg.op_mode == USB_CPU) {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1,
-
otg.bulkout_max_pktsize);
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
} else if (otg.dn_filesize>otg.bulkout_max_pktsize) {
-
u32 pkt_cnt, remain_cnt;
-
-
DBG_BULK1("downloadFileSize!=0, Dma Start for 2nd OUT PKT \n");
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|
-
INT_RESET|INT_SUSPEND, S5P_OTG_GINTMSK); /*gint unmask */
-
writel(MODE_DMA|BURST_INCR4|GBL_INT_UNMASK,
-
S5P_OTG_GAHBCFG);
-
writel((u32)otg.dn_ptr, S5P_OTG_DOEPDMA_OUT);
-
pkt_cnt = (u32)(otg.dn_filesize-otg.bulkout_max_pktsize)/otg.bulkout_max_pktsize;
-
remain_cnt = (u32)((otg.dn_filesize-otg.bulkout_max_pktsize)%otg.bulkout_max_pktsize);
-
if(remain_cnt != 0) {
-
pkt_cnt += 1;
-
}
-
-
if (pkt_cnt > 1023) {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1023,
-
(otg.bulkout_max_pktsize*1023));
-
} else {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, pkt_cnt,
-
(otg.dn_filesize-otg.bulkout_max_pktsize));
-
}
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
}
-
}
-
-
void s3c_usb_download_continue(u32 fifo_cnt_byte)
-
{
-
if (otg.op_mode == USB_CPU) {
-
s3c_usb_read_out_fifo((u8 *)otg.dn_ptr, fifo_cnt_byte);
-
otg.dn_ptr += fifo_cnt_byte;
-
DBG_BULK1("downloadFileSize!=0, 2nd BYTE_READ_CNT_REG = 0x%x, m_pDownPt = 0x%x\n",
-
fifo_cnt_byte, otg.dn_ptr);
-
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1, otg.bulkout_max_pktsize);
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
-
/* USB format : addr(4)+size(4)+data(n)+cs(2) */
-
if (((u32)otg.dn_ptr - otg.dn_addr) >= (otg.dn_filesize - 8)) {
-
printf("Download Done!! Download Address: 0x%x, Download Filesize:0x%x\n",
-
otg.dn_addr, (otg.dn_filesize-10));
-
-
s3c_usbd_dn_cnt = otg.dn_filesize-10;
-
s3c_usbd_dn_addr = otg.dn_addr;
-
-
#ifdef USB_CHECKSUM_EN
-
s3c_usb_verify_checksum();
-
#endif
-
s3c_receive_done = 1;
-
}
-
-
}\
-
}
-
-
void s3c_usb_int_bulkout(u32 fifo_cnt_byte)
-
{
-
DBG_BULK0("Bulk Out Function : otg.dn_filesize=0x%x\n", otg.dn_filesize);
-
if (otg.dn_filesize==0) {
-
if (fifo_cnt_byte == 10) {
-
s3c_usb_upload_start();
-
} else {
-
s3c_usb_download_start(fifo_cnt_byte);
-
}
-
} else {
-
s3c_usb_download_continue(fifo_cnt_byte);
-
}
-
}
-
-
void s3c_usb_dma_in_done(void)
-
{
-
s32 remain_cnt;
-
-
DBG_BULK0("DMA IN : Transfer Done\n");
-
-
otg.up_ptr = (u8 *)readl(S5P_OTG_DIEPDMA_IN);
-
remain_cnt = otg.up_size- ((u32)otg.up_ptr - otg.up_addr);
-
-
if (remain_cnt>0) {
-
u32 pktcnt, remainder;
-
pktcnt = (u32)(remain_cnt/otg.bulkin_max_pktsize);
-
remainder = (u32)(remain_cnt%otg.bulkin_max_pktsize);
-
if(remainder != 0) {
-
pktcnt += 1;
-
}
-
DBG_SETUP1("remain_cnt : %d \n", remain_cnt);
-
if (pktcnt> 1023) {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1023,
-
(otg.bulkin_max_pktsize*1023));
-
} else {
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, pktcnt,
-
remain_cnt);
-
}
-
-
/*ep1 enable, clear nak, bulk, usb active, next ep1, max pkt */
-
writel(1u<<31|1<<26|2<<18|1<<15|BULK_IN_EP<<11|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
} else
-
DBG_SETUP1("DMA IN : Transfer Complete\n");
-
}
-
-
void s3c_usb_dma_out_done(void)
-
{
-
s32 remain_cnt;
-
-
DBG_BULK1("DMA OUT : Transfer Done\n");
-
otg.dn_ptr = (u8 *)readl(S5P_OTG_DOEPDMA_OUT);
-
-
remain_cnt = otg.dn_filesize - ((u32)otg.dn_ptr - otg.dn_addr + 8);
-
-
if (remain_cnt>0) {
-
u32 pktcnt, remainder;
-
pktcnt = (u32)(remain_cnt/otg.bulkout_max_pktsize);
-
remainder = (u32)(remain_cnt%otg.bulkout_max_pktsize);
-
if(remainder != 0) {
-
pktcnt += 1;
-
}
-
DBG_BULK1("remain_cnt : %d \n", remain_cnt);
-
if (pktcnt> 1023) {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1023,
-
(otg.bulkout_max_pktsize*1023));
-
} else {
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, pktcnt,
-
remain_cnt);
-
}
-
-
/*ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64*/
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
} else {
-
DBG_BULK1("DMA OUT : Transfer Complete\n");
-
udelay(500); /*for FPGA ???*/
-
}
-
}
-
-
void s3c_usb_set_all_outep_nak(void)
-
{
-
u8 i;
-
u32 tmp;
-
-
for(i=0;i<16;i++)
-
{
-
tmp = readl(S5P_OTG_DOEPCTL0+0x20*i);
-
tmp |= DEPCTL_SNAK;
-
writel(tmp, S5P_OTG_DOEPCTL0+0x20*i);
-
}
-
}
-
-
void s3c_usb_clear_all_outep_nak(void)
-
{
-
u8 i;
-
u32 tmp;
-
-
for(i=0;i<16;i++)
-
{
-
tmp = readl(S5P_OTG_DOEPCTL0+0x20*i);
-
tmp |= (DEPCTL_EPENA|DEPCTL_CNAK);
-
writel(tmp, S5P_OTG_DOEPCTL0+0x20*i);
-
}
-
}
-
-
void s3c_usb_set_max_pktsize(USB_SPEED speed)
-
{
-
if (speed == USB_HIGH)
-
{
-
otg.speed = USB_HIGH;
-
otg.ctrl_max_pktsize = HS_CTRL_PKT_SIZE;
-
otg.bulkin_max_pktsize = HS_BULK_PKT_SIZE;
-
otg.bulkout_max_pktsize = HS_BULK_PKT_SIZE;
-
}
-
else
-
{
-
otg.speed = USB_FULL;
-
otg.ctrl_max_pktsize = FS_CTRL_PKT_SIZE;
-
otg.bulkin_max_pktsize = FS_BULK_PKT_SIZE;
-
otg.bulkout_max_pktsize = FS_BULK_PKT_SIZE;
-
}
-
}
-
-
void s3c_usb_set_endpoint(void)
-
{
-
/* Unmask S5P_OTG_DAINT source */
-
writel(0xff, S5P_OTG_DIEPINT0);
-
writel(0xff, S5P_OTG_DOEPINT0);
-
writel(0xff, S5P_OTG_DIEPINT_IN);
-
writel(0xff, S5P_OTG_DOEPINT_OUT);
-
-
/* Init For Ep0*/
-
if(otg.speed == USB_HIGH)
-
{
-
/*MPS:64bytes */
-
writel(((1<<26)|(CONTROL_EP<<11)|(0<<0)), S5P_OTG_DIEPCTL0);
-
/*ep0 enable, clear nak */
-
writel((1u<<31)|(1<<26)|(0<<0), S5P_OTG_DOEPCTL0);
-
}
-
else
-
{
-
/*MPS:8bytes */
-
writel(((1<<26)|(CONTROL_EP<<11)|(3<<0)), S5P_OTG_DIEPCTL0);
-
/*ep0 enable, clear nak */
-
writel((1u<<31)|(1<<26)|(3<<0), S5P_OTG_DOEPCTL0);
-
}
-
}
-
-
void s3c_usb_set_descriptors(void)
-
{
-
/* Standard device descriptor */
-
otg.desc.dev.bLength=DEVICE_DESC_SIZE; /*0x12*/
-
otg.desc.dev.bDescriptorType=DEVICE_DESCRIPTOR;
-
otg.desc.dev.bDeviceClass=0xFF; /* 0x0*/
-
otg.desc.dev.bDeviceSubClass=0x0;
-
otg.desc.dev.bDeviceProtocol=0x0;
-
otg.desc.dev.bMaxPacketSize0=otg.ctrl_max_pktsize;
-
otg.desc.dev.idVendorL=0xE8; /*0x45;*/
-
otg.desc.dev.idVendorH=0x04; /*0x53;*/
-
otg.desc.dev.idProductL=0x34; /*0x00*/
-
otg.desc.dev.idProductH=0x12; /*0x64*/
-
otg.desc.dev.bcdDeviceL=0x00;
-
otg.desc.dev.bcdDeviceH=0x01;
-
otg.desc.dev.iManufacturer=0x1; /* index of string descriptor */
-
otg.desc.dev.iProduct=0x2; /* index of string descriptor */
-
otg.desc.dev.iSerialNumber=0x0;
-
otg.desc.dev.bNumConfigurations=0x1;
-
if (otg.speed == USB_FULL) {
-
otg.desc.dev.bcdUSBL=0x10;
-
otg.desc.dev.bcdUSBH=0x01; /* Ver 1.10*/
-
}
-
else {
-
otg.desc.dev.bcdUSBL=0x00;
-
otg.desc.dev.bcdUSBH=0x02; /* Ver 2.0*/
-
}
-
-
/* Standard configuration descriptor */
-
otg.desc.config.bLength=CONFIG_DESC_SIZE; /* 0x9 bytes */
-
otg.desc.config.bDescriptorType=CONFIGURATION_DESCRIPTOR;
-
otg.desc.config.wTotalLengthL=CONFIG_DESC_TOTAL_SIZE;
-
otg.desc.config.wTotalLengthH=0;
-
otg.desc.config.bNumInterfaces=1;
-
/* dbg descConf.bConfigurationValue=2; // why 2? There's no reason.*/
-
otg.desc.config.bConfigurationValue=1;
-
otg.desc.config.iConfiguration=0;
-
otg.desc.config.bmAttributes=CONF_ATTR_DEFAULT|CONF_ATTR_SELFPOWERED; /* bus powered only.*/
-
otg.desc.config.maxPower=25; /* draws 50mA current from the USB bus.*/
-
-
/* Standard interface descriptor */
-
otg.desc.intf.bLength=INTERFACE_DESC_SIZE; /* 9*/
-
otg.desc.intf.bDescriptorType=INTERFACE_DESCRIPTOR;
-
otg.desc.intf.bInterfaceNumber=0x0;
-
otg.desc.intf.bAlternateSetting=0x0; /* ?*/
-
otg.desc.intf.bNumEndpoints = 2; /* # of endpoints except EP0*/
-
otg.desc.intf.bInterfaceClass=0xff; /* 0x0 ?*/
-
otg.desc.intf.bInterfaceSubClass=0x0;
-
otg.desc.intf.bInterfaceProtocol=0x0;
-
otg.desc.intf.iInterface=0x0;
-
-
/* Standard endpoint0 descriptor */
-
otg.desc.ep1.bLength=ENDPOINT_DESC_SIZE;
-
otg.desc.ep1.bDescriptorType=ENDPOINT_DESCRIPTOR;
-
otg.desc.ep1.bEndpointAddress=BULK_IN_EP|EP_ADDR_IN;
-
otg.desc.ep1.bmAttributes=EP_ATTR_BULK;
-
otg.desc.ep1.wMaxPacketSizeL=(u8)otg.bulkin_max_pktsize; /* 64*/
-
otg.desc.ep1.wMaxPacketSizeH=(u8)(otg.bulkin_max_pktsize>>8);
-
otg.desc.ep1.bInterval=0x0; /* not used */
-
-
/* Standard endpoint1 descriptor */
-
otg.desc.ep2.bLength=ENDPOINT_DESC_SIZE;
-
otg.desc.ep2.bDescriptorType=ENDPOINT_DESCRIPTOR;
-
otg.desc.ep2.bEndpointAddress=BULK_OUT_EP|EP_ADDR_OUT;
-
otg.desc.ep2.bmAttributes=EP_ATTR_BULK;
-
otg.desc.ep2.wMaxPacketSizeL=(u8)otg.bulkout_max_pktsize; /* 64*/
-
otg.desc.ep2.wMaxPacketSizeH=(u8)(otg.bulkout_max_pktsize>>8);
-
otg.desc.ep2.bInterval=0x0; /* not used */
-
}
-
-
void s3c_usb_check_speed(USB_SPEED *speed)
-
{
-
u32 status;
-
-
status = readl(S5P_OTG_DSTS); /* System status read */
-
-
*speed = (USB_SPEED)((status&0x6) >>1);
-
}
-
-
void s3c_usb_clear_dnfile_info(void)
-
{
-
otg.dn_addr = 0;
-
otg.dn_filesize = 0;
-
otg.dn_ptr = 0;
-
}
-
-
void s3c_usb_clear_upfile_info(void)
-
{
-
otg.up_addr= 0;
-
otg.up_size= 0;
-
otg.up_ptr = 0;
-
}
-
-
-
int s3c_usb_check_setconf(void)
-
{
-
if (otg.set_config == 0)
-
return FALSE;
-
else
-
return TRUE;
-
}
-
-
void s3c_usb_set_opmode(USB_OPMODE mode)
-
{
-
otg.op_mode = mode;
-
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|
-
INT_RESET|INT_SUSPEND|INT_RX_FIFO_NOT_EMPTY,
-
S5P_OTG_GINTMSK); /*gint unmask */
-
-
writel(MODE_SLAVE|BURST_SINGLE|GBL_INT_UNMASK, S5P_OTG_GAHBCFG);
-
-
s3c_usb_set_outep_xfersize(EP_TYPE_BULK, 1, otg.bulkout_max_pktsize);
-
s3c_usb_set_inep_xfersize(EP_TYPE_BULK, 1, 0);
-
-
/*bulk out ep enable, clear nak, bulk, usb active, next ep3, max pkt */
-
writel(1u<<31|1<<26|2<<18|1<<15|otg.bulkout_max_pktsize<<0,
-
S5P_OTG_DOEPCTL_OUT);
-
-
/*bulk in ep enable, clear nak, bulk, usb active, next ep1, max pkt */
-
writel(0u<<31|1<<26|2<<18|1<<15|otg.bulkin_max_pktsize<<0,
-
S5P_OTG_DIEPCTL_IN);
-
}
-
-
void s3c_usb_reset(void)
-
{
-
s3c_usb_set_all_outep_nak();
-
-
otg.ep0_state = EP0_STATE_INIT;
-
writel(((1<<BULK_OUT_EP)|(1<<CONTROL_EP))<<16|((1<<BULK_IN_EP)|(1<<CONTROL_EP)),
-
S5P_OTG_DAINTMSK);
-
writel(CTRL_OUT_EP_SETUP_PHASE_DONE|AHB_ERROR|TRANSFER_DONE,
-
S5P_OTG_DOEPMSK);
-
writel(INTKN_TXFEMP|NON_ISO_IN_EP_TIMEOUT|AHB_ERROR|TRANSFER_DONE,
-
S5P_OTG_DIEPMSK);
-
-
/* Rx FIFO Size */
-
writel(RX_FIFO_SIZE, S5P_OTG_GRXFSIZ);
-
-
/* Non Periodic Tx FIFO Size */
-
writel(NPTX_FIFO_SIZE<<16| NPTX_FIFO_START_ADDR<<0, S5P_OTG_GNPTXFSIZ);
-
-
s3c_usb_clear_all_outep_nak();
-
-
/*clear device address */
-
writel(readl(S5P_OTG_DCFG)&~(0x7f<<4), S5P_OTG_DCFG);
-
-
if(SUSPEND_RESUME_ON) {
-
writel(readl(S5P_OTG_PCGCCTL)&~(1<<0), S5P_OTG_PCGCCTL);
-
}
-
}
-
int s3c_usb_set_init(void)
-
{
-
u32 status;
-
-
status = readl(S5P_OTG_DSTS); /* System status read */
-
-
/* Set if Device is High speed or Full speed */
-
if (((status&0x6) >>1) == USB_HIGH) {
-
DBG_SETUP1("High Speed Detection\n");
-
s3c_usb_set_max_pktsize(USB_HIGH);
-
}
-
else if(((status&0x6) >>1) == USB_FULL) {
-
DBG_SETUP1("Full Speed Detec tion\n");
-
s3c_usb_set_max_pktsize(USB_FULL);
-
}
-
else {
-
printf("**** Error:Neither High_Speed nor Full_Speed\n");
-
return FALSE;
-
}
-
-
s3c_usb_set_endpoint();
-
s3c_usb_set_descriptors();
-
s3c_usb_clear_dnfile_info();
-
s3c_usb_set_opmode(op_mode);
-
-
return TRUE;
-
}
-
-
void s3c_usb_pkt_receive(void)
-
{
-
u32 rx_status;
-
u32 fifo_cnt_byte;
-
-
rx_status = readl(S5P_OTG_GRXSTSP);
-
DBG_SETUP0("S5P_OTG_GRXSTSP = 0x%x\n", rx_status);
-
-
if ((rx_status & (0xf<<17)) == SETUP_PKT_RECEIVED) {
-
DBG_SETUP1("SETUP_PKT_RECEIVED\n");
-
s3c_usb_ep0_int_hndlr();
-
-
} else if ((rx_status & (0xf<<17)) == OUT_PKT_RECEIVED) {
-
fifo_cnt_byte = (rx_status & 0x7ff0)>>4;
-
DBG_SETUP1("OUT_PKT_RECEIVED\n");
-
-
if((rx_status & BULK_OUT_EP)&&(fifo_cnt_byte)) {
-
s3c_usb_int_bulkout(fifo_cnt_byte);
-
if( otg.op_mode == USB_CPU )
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|
-
INT_ENUMDONE|INT_RESET|INT_SUSPEND|
-
INT_RX_FIFO_NOT_EMPTY,
-
S5P_OTG_GINTMSK);
-
return;
-
}
-
-
} else if ((rx_status & (0xf<<17)) == GLOBAL_OUT_NAK) {
-
DBG_SETUP1("GLOBAL_OUT_NAK\n");
-
-
} else if ((rx_status & (0xf<<17)) == OUT_TRNASFER_COMPLETED) {
-
DBG_SETUP1("OUT_TRNASFER_COMPLETED\n");
-
-
} else if ((rx_status & (0xf<<17)) == SETUP_TRANSACTION_COMPLETED) {
-
DBG_SETUP1("SETUP_TRANSACTION_COMPLETED\n");
-
-
} else {
-
DBG_SETUP1("Reserved\n");
-
}
-
}
-
-
void s3c_usb_transfer(void)
-
{
-
u32 ep_int;
-
u32 check_dma;
-
u32 ep_int_status;
-
-
ep_int = readl(S5P_OTG_DAINT);
-
DBG_SETUP0("S5P_OTG_DAINT = 0x%x", ep_int);
-
-
if (ep_int & (1<<CONTROL_EP)) {
-
ep_int_status = readl(S5P_OTG_DIEPINT0);
-
DBG_SETUP1("S5P_OTG_DIEPINT0 : %x \n", ep_int_status);
-
-
if (ep_int_status & INTKN_TXFEMP) {
-
u32 uNTxFifoSpace;
-
do {
-
uNTxFifoSpace=readl(S5P_OTG_GNPTXSTS)&0xffff;
-
}while(uNTxFifoSpace<otg.ctrl_max_pktsize);
-
-
s3c_usb_transfer_ep0();
-
}
-
-
writel(ep_int_status, S5P_OTG_DIEPINT0); /* Interrupt Clear */
-
}
-
-
if (ep_int & ((1<<CONTROL_EP)<<16)) {
-
ep_int_status = readl(S5P_OTG_DOEPINT0);
-
DBG_SETUP1("S5P_OTG_DOEPINT0 : %x \n", ep_int_status);
-
-
s3c_usb_set_outep_xfersize(EP_TYPE_CONTROL, 1, 8);
-
writel(1u<<31|1<<26, S5P_OTG_DOEPCTL0); /*ep0 enable, clear nak */
-
-
writel(ep_int_status, S5P_OTG_DOEPINT0); /* Interrupt Clear */
-
}
-
-
if(ep_int & (1<<BULK_IN_EP)) {
-
ep_int_status = readl(S5P_OTG_DIEPINT_IN);
-
DBG_BULK1("S5P_OTG_DIEPINT_IN : %x \n", ep_int_status);
-
writel(ep_int_status, S5P_OTG_DIEPINT_IN); /* Interrupt Clear */
-
-
if ( (ep_int_status&INTKN_TXFEMP) && otg.op_mode == USB_CPU)
-
s3c_usb_int_bulkin();
-
-
check_dma = readl(S5P_OTG_GAHBCFG);
-
if ((check_dma&MODE_DMA)&&(ep_int_status&TRANSFER_DONE))
-
s3c_usb_dma_in_done();
-
}
-
-
if (ep_int & ((1<<BULK_OUT_EP)<<16)) {
-
ep_int_status = readl(S5P_OTG_DOEPINT_OUT);
-
DBG_BULK1("S5P_OTG_DOEPINT_OUT : 0x%x\n", ep_int_status);
-
writel(ep_int_status, S5P_OTG_DOEPINT_OUT); /* Interrupt Clear */
-
-
check_dma = readl(S5P_OTG_GAHBCFG);
-
if ((check_dma&MODE_DMA)&&(ep_int_status&TRANSFER_DONE)) {
-
s3c_usb_dma_out_done();
-
}
-
}
-
}
-
-
void s3c_udc_int_hndlr(void)
-
{
-
u32 int_status;
-
int tmp;
-
-
int_status = readl(S5P_OTG_GINTSTS); /* Core Interrupt Register */
-
writel(int_status, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
DBG_SETUP0("*** USB OTG Interrupt(S5P_OTG_GINTSTS: 0x%08x) ****\n",
-
int_status);
-
-
if (int_status & INT_RESET) {
-
DBG_SETUP1("INT_RESET\n");
-
writel(INT_RESET, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
-
s3c_usb_reset();
-
}
-
-
if (int_status & INT_ENUMDONE) {
-
DBG_SETUP1("INT_ENUMDONE :");
-
writel(INT_ENUMDONE, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
s3c_usb_connected_status=3;
-
tmp = s3c_usb_set_init();
-
if (tmp == FALSE)
-
return;
-
-
}
-
-
if (int_status & INT_RESUME) {
-
DBG_SETUP1("INT_RESUME\n");
-
writel(INT_RESUME, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
-
if(SUSPEND_RESUME_ON) {
-
writel(readl(S5P_OTG_PCGCCTL)&~(1<<0), S5P_OTG_PCGCCTL);
-
DBG_SETUP1("INT_RESUME\n");
-
}
-
}
-
-
if (int_status & INT_SUSPEND) {
-
DBG_SETUP1("INT_SUSPEND\n");
-
writel(INT_SUSPEND, S5P_OTG_GINTSTS); /* Interrupt Clear */
-
-
if(SUSPEND_RESUME_ON) {
-
writel(readl(S5P_OTG_PCGCCTL)|(1<<0), S5P_OTG_PCGCCTL);
-
}
-
}
-
-
if(int_status & INT_RX_FIFO_NOT_EMPTY) {
-
DBG_SETUP1("INT_RX_FIFO_NOT_EMPTY\n");
-
/* Read only register field */
-
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|
-
INT_ENUMDONE|INT_RESET|INT_SUSPEND,
-
S5P_OTG_GINTMSK);
-
s3c_usb_pkt_receive();
-
writel(INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|
-
INT_RESET |INT_SUSPEND|INT_RX_FIFO_NOT_EMPTY,
-
S5P_OTG_GINTMSK); /*gint unmask */
-
s3c_usb_connected_status=1;
-
}
-
-
if ((int_status & INT_IN_EP) || (int_status & INT_OUT_EP)) {
-
DBG_SETUP1("INT_IN or OUT_EP\n");
-
/* Read only register field */
-
-
s3c_usb_transfer();
-
}
-
}
-
-
int s3c_udc_is_adc_cable()
-
{
-
int count = 0;
-
while(count<10)
-
{
-
if((readl(S5P_OTG_HPRT)&0xc00)==0xc00)
-
count ++;
-
else
-
{
-
count =0;
-
return 0;
-
}
-
}
-
return 1;
-
}
-
/*the following is for u-boot battery charge*/
-
int s3c_check_usb_connect_status()
-
{
-
if(!s3c_usb_phy_inited)/*initalized at first*/
-
{
-
s3c_usbctl_init(1);
-
}
-
/*then check current usb status*/
-
unsigned long usec = (1000*1000*10);
-
ulong tmo, tmp;
-
-
if (usec >= 1000) { /* if "big" number, spread normalization to seconds */
-
tmo = usec / 1000; /* start to normalize for usec to ticks per sec */
-
tmo *= CFG_HZ; /* find number of "ticks" to wait to achieve target */
-
tmo /= 1000; /* finish normalize. */
-
}
-
else { /* else small number, don't kill it prior to HZ multiply */
-
tmo = usec * CFG_HZ;
-
tmo /= (1000 * 1000);
-
}
-
tmp = get_timer(0); /* get current timestamp */
-
if ((tmo + tmp + 1) < tmp) /* if setting this fordward will roll time stamp */
-
{
-
reset_timer_masked(); /* reset "advancing" timestamp to 0, set lastdec value */
-
}
-
else
-
tmo += tmp; /* else, set advancing stamp wake up time */
-
-
while (get_timer_masked()<tmo)
-
{
-
if (S3C_USBD_DETECT_IRQ()) {
-
s3c_udc_int_hndlr();
-
S3C_USBD_CLEAR_IRQ();
-
}
-
if(s3c_udc_is_adc_cable())
-
s3c_usb_connected_status=2;
-
if(s3c_usb_connected_status==2||s3c_usb_connected_status==1)
-
break;
-
}
-
-
if(s3c_usb_phy_inited)
-
{
-
s3c_usb_stop();
-
}
-
return s3c_usb_connected_status;
-
-
}
-
#endif
usbd-otg-hs.h
-
/*
-
* cpu/s5pc1xx/usbd-otg-hs.h
-
*
-
* (C) Copyright 2009
-
* Byungjae Lee, Samsung Erectronics, bjlee@samsung.com.
-
* - only support for S5PC100
-
*
-
* This program is free software; you can redistribute it and/or
-
* modify it under the terms of the GNU General Public License as
-
* published by the Free Software Foundation; either version 2 of
-
* the License, or (at your option) any later version.
-
*
-
* This program is distributed in the hope that it will be useful,
-
* but WITHOUT ANY WARRANTY; without even the implied warranty of
-
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-
* GNU General Public License for more details.
-
*
-
* You should have received a copy of the GNU General Public License
-
* along with this program; if not, write to the Free Software
-
* Foundation, Inc., 59 Temple Place, Suite 330, Boston,
-
* MA 02111-1307 USA
-
*/
-
-
#ifndef __S3C_OTG_HS_H__
-
#define __S3C_OTG_HS_H__
-
-
#include <asm/byteorder.h>
-
#include <asm/arch/hardware.h>
-
#include <asm/io.h>
-
-
#define S3C_USBD_DETECT_IRQ() (readl(S5P_OTG_GINTSTS) & \
-
(GINTSTS_WkUpInt|GINTSTS_OEPInt|GINTSTS_IEPInt| \
-
GINTSTS_EnumDone|GINTSTS_USBRst|GINTSTS_USBSusp|GINTSTS_RXFLvl))
-
#define S3C_USBD_CLEAR_IRQ() do { \
-
writel(BIT_ALLMSK, (S5P_OTG_GINTSTS)); \
-
} while (0)
-
-
#define CONTROL_EP 0
-
#define BULK_IN_EP 1
-
#define BULK_OUT_EP 2
-
-
#define FS_CTRL_PKT_SIZE 8
-
#define FS_BULK_PKT_SIZE 64
-
-
#define HS_CTRL_PKT_SIZE 64
-
#define HS_BULK_PKT_SIZE 512
-
-
#define RX_FIFO_SIZE 512
-
#define NPTX_FIFO_START_ADDR RX_FIFO_SIZE
-
#define NPTX_FIFO_SIZE 512
-
#define PTX_FIFO_SIZE 512
-
-
// string descriptor
-
#define LANGID_US_L (0x09)
-
#define LANGID_US_H (0x04)
-
-
// Feature Selectors
-
#define EP_STALL 0
-
#define DEVICE_REMOTE_WAKEUP 1
-
#define TEST_MODE 2
-
-
/* Test Mode Selector*/
-
#define TEST_J 1
-
#define TEST_K 2
-
#define TEST_SE0_NAK 3
-
#define TEST_PACKET 4
-
#define TEST_FORCE_ENABLE 5
-
-
#define S5P_OTG_DIEPCTL_IN (S5P_OTG_DIEPCTL0 + 0x20*BULK_IN_EP)
-
#define S5P_OTG_DIEPINT_IN (S5P_OTG_DIEPINT0 + 0x20*BULK_IN_EP)
-
#define S5P_OTG_DIEPTSIZ_IN (S5P_OTG_DIEPTSIZ0 + 0x20*BULK_IN_EP)
-
#define S5P_OTG_DIEPDMA_IN (S5P_OTG_DIEPDMA0 + 0x20*BULK_IN_EP)
-
#define S5P_OTG_DOEPCTL_OUT (S5P_OTG_DOEPCTL0 + 0x20*BULK_OUT_EP)
-
#define S5P_OTG_DOEPINT_OUT (S5P_OTG_DOEPINT0 + 0x20*BULK_OUT_EP)
-
#define S5P_OTG_DOEPTSIZ_OUT (S5P_OTG_DOEPTSIZ0 + 0x20*BULK_OUT_EP)
-
#define S5P_OTG_DOEPDMA_OUT (S5P_OTG_DOEPDMA0 + 0x20*BULK_OUT_EP)
-
#define S5P_OTG_IN_FIFO (S5P_OTG_EP0_FIFO + 0x1000*BULK_IN_EP)
-
#define S5P_OTG_OUT_FIFO (S5P_OTG_EP0_FIFO + 0x1000*BULK_OUT_EP)
-
-
-
typedef struct
-
{
-
u8 bLength;
-
u8 bDescriptorType;
-
u8 bcdUSBL;
-
u8 bcdUSBH;
-
u8 bDeviceClass;
-
u8 bDeviceSubClass;
-
u8 bDeviceProtocol;
-
u8 bMaxPacketSize0;
-
u8 idVendorL;
-
u8 idVendorH;
-
u8 idProductL;
-
u8 idProductH;
-
u8 bcdDeviceL;
-
u8 bcdDeviceH;
-
u8 iManufacturer;
-
u8 iProduct;
-
u8 iSerialNumber;
-
u8 bNumConfigurations;
-
} __attribute__ ((packed)) device_desc_t;
-
-
typedef struct
-
{
-
u8 bLength;
-
u8 bDescriptorType;
-
u8 wTotalLengthL;
-
u8 wTotalLengthH;
-
u8 bNumInterfaces;
-
u8 bConfigurationValue;
-
u8 iConfiguration;
-
u8 bmAttributes;
-
u8 maxPower;
-
} __attribute__ ((packed)) config_desc_t;
-
-
typedef struct
-
{
-
u8 bLength;
-
u8 bDescriptorType;
-
u8 bInterfaceNumber;
-
u8 bAlternateSetting;
-
u8 bNumEndpoints;
-
u8 bInterfaceClass;
-
u8 bInterfaceSubClass;
-
u8 bInterfaceProtocol;
-
u8 iInterface;
-
} __attribute__ ((packed)) intf_desc_t;
-
-
typedef struct
-
{
-
u8 bLength;
-
u8 bDescriptorType;
-
u8 bEndpointAddress;
-
u8 bmAttributes;
-
u8 wMaxPacketSizeL;
-
u8 wMaxPacketSizeH;
-
u8 bInterval;
-
} __attribute__ ((packed)) ep_desc_t;
-
-
typedef struct
-
{
-
u8 bmRequestType;
-
u8 bRequest;
-
u8 wValue_L;
-
u8 wValue_H;
-
u8 wIndex_L;
-
u8 wIndex_H;
-
u8 wLength_L;
-
u8 wLength_H;
-
} __attribute__ ((packed)) device_req_t;
-
-
typedef struct
-
{
-
device_desc_t dev;
-
config_desc_t config;
-
intf_desc_t intf;
-
ep_desc_t ep1;
-
ep_desc_t ep2;
-
ep_desc_t ep3;
-
ep_desc_t ep4;
-
} __attribute__ ((packed)) descriptors_t;
-
-
typedef struct
-
{
-
u8 Device;
-
u8 Interface;
-
u8 ep_ctrl;
-
u8 ep_in;
-
u8 ep_out;
-
} __attribute__ ((packed)) get_status_t;
-
-
typedef struct
-
{
-
u8 AlternateSetting;
-
} __attribute__ ((packed)) get_intf_t;
-
-
-
typedef enum
-
{
-
USB_CPU, USB_DMA
-
} USB_OPMODE;
-
-
typedef enum
-
{
-
USB_HIGH, USB_FULL, USB_LOW
-
} USB_SPEED;
-
-
typedef enum
-
{
-
EP_TYPE_CONTROL, EP_TYPE_ISOCHRONOUS, EP_TYPE_BULK, EP_TYPE_INTERRUPT
-
} EP_TYPE;
-
-
-
typedef struct
-
{
-
descriptors_t desc;
-
device_req_t dev_req;
-
-
u32 ep0_state;
-
u32 ep0_substate;
-
USB_OPMODE op_mode;
-
USB_SPEED speed;
-
u32 ctrl_max_pktsize;
-
u32 bulkin_max_pktsize;
-
u32 bulkout_max_pktsize;
-
u32 dn_addr;
-
u32 dn_filesize;
-
u32 up_addr;
-
u32 up_size;
-
u8* dn_ptr;
-
u8* up_ptr;
-
u32 set_config;
-
u32 req_length;
-
} __attribute__ ((packed)) otg_dev_t;
-
-
// SPEC1.1
-
-
// Standard bmRequestType (direction)
-
enum DEV_REQUEST_DIRECTION
-
{
-
HOST_TO_DEVICE = 0x00,
-
DEVICE_TO_HOST = 0x80
-
};
-
-
// Standard bmRequestType (Type)
-
enum DEV_REQUEST_TYPE
-
{
-
STANDARD_TYPE = 0x00,
-
CLASS_TYPE = 0x20,
-
VENDOR_TYPE = 0x40,
-
RESERVED_TYPE = 0x60
-
};
-
-
// Standard bmRequestType (Recipient)
-
enum DEV_REQUEST_RECIPIENT
-
{
-
DEVICE_RECIPIENT = 0,
-
INTERFACE_RECIPIENT = 1,
-
ENDPOINT_RECIPIENT = 2,
-
OTHER_RECIPIENT = 3
-
};
-
-
// Descriptor types
-
enum DESCRIPTOR_TYPE
-
{
-
DEVICE_DESCRIPTOR = 1,
-
CONFIGURATION_DESCRIPTOR = 2,
-
STRING_DESCRIPTOR = 3,
-
INTERFACE_DESCRIPTOR = 4,
-
ENDPOINT_DESCRIPTOR = 5,
-
DEVICE_QUALIFIER = 6,
-
OTHER_SPEED_CONFIGURATION = 7,
-
INTERFACE_POWER = 8
-
};
-
-
// configuration descriptor: bmAttributes
-
enum CONFIG_ATTRIBUTES
-
{
-
CONF_ATTR_DEFAULT = 0x80,
-
CONF_ATTR_REMOTE_WAKEUP = 0x20,
-
CONF_ATTR_SELFPOWERED = 0x40
-
};
-
-
// endpoint descriptor
-
enum ENDPOINT_ATTRIBUTES
-
{
-
EP_ADDR_IN = 0x80,
-
EP_ADDR_OUT = 0x00,
-
-
EP_ATTR_CONTROL = 0x0,
-
EP_ATTR_ISOCHRONOUS = 0x1,
-
EP_ATTR_BULK = 0x2,
-
EP_ATTR_INTERRUPT = 0x3
-
};
-
-
// Standard bRequest codes
-
enum STANDARD_REQUEST_CODE
-
{
-
STANDARD_GET_STATUS = 0,
-
STANDARD_CLEAR_FEATURE = 1,
-
STANDARD_RESERVED_1 = 2,
-
STANDARD_SET_FEATURE = 3,
-
STANDARD_RESERVED_2 = 4,
-
STANDARD_SET_ADDRESS = 5,
-
STANDARD_GET_DESCRIPTOR = 6,
-
STANDARD_SET_DESCRIPTOR = 7,
-
STANDARD_GET_CONFIGURATION = 8,
-
STANDARD_SET_CONFIGURATION = 9,
-
STANDARD_GET_INTERFACE = 10,
-
STANDARD_SET_INTERFACE = 11,
-
STANDARD_SYNCH_FRAME = 12
-
};
-
-
int s3c_usbctl_init(int ischeckstatus);
-
int s3c_usbc_activate (void);
-
int s3c_usb_stop( void );
-
void s3c_udc_int_hndlr(void);
-
-
/* in usbd-otg-hs.c */
-
extern unsigned int s3c_usbd_dn_addr;
-
extern unsigned int s3c_usbd_dn_cnt;
-
extern int DNW;
-
extern int s3c_got_header;
-
extern int s3c_receive_done;
-
-
#endif
阅读(3395) | 评论(0) | 转发(0) |