Merge branch 'master' of master.kernel.org:/pub/scm/linux/kernel/git/torvalds/linux-2.6

This commit is contained in:
David S. Miller
2009-01-08 11:05:59 -08:00
2400 changed files with 559700 additions and 49298 deletions

View File

@@ -297,13 +297,34 @@ config USB_S3C2410_DEBUG
# musb builds in ../musb along with host support
config USB_GADGET_MUSB_HDRC
boolean "Inventra HDRC USB Peripheral (TI, ...)"
boolean "Inventra HDRC USB Peripheral (TI, ADI, ...)"
depends on USB_MUSB_HDRC && (USB_MUSB_PERIPHERAL || USB_MUSB_OTG)
select USB_GADGET_DUALSPEED
select USB_GADGET_SELECTED
help
This OTG-capable silicon IP is used in dual designs including
the TI DaVinci, OMAP 243x, OMAP 343x, and TUSB 6010.
the TI DaVinci, OMAP 243x, OMAP 343x, TUSB 6010, and ADI Blackfin
config USB_GADGET_IMX
boolean "Freescale IMX USB Peripheral Controller"
depends on ARCH_MX1
help
Freescale's IMX series include an integrated full speed
USB 1.1 device controller. The controller in the IMX series
is register-compatible.
It has Six fixed-function endpoints, as well as endpoint
zero (for control transfers).
Say "y" to link the driver statically, or "m" to build a
dynamically linked module called "imx_udc" and force all
gadget drivers to also be dynamically linked.
config USB_IMX
tristate
depends on USB_GADGET_IMX
default USB_GADGET
select USB_GADGET_SELECTED
config USB_GADGET_M66592
boolean "Renesas M66592 USB Peripheral Controller"
@@ -377,6 +398,24 @@ config USB_FSL_QE
default USB_GADGET
select USB_GADGET_SELECTED
config USB_GADGET_CI13XXX
boolean "MIPS USB CI13xxx"
depends on PCI
select USB_GADGET_DUALSPEED
help
MIPS USB IP core family device controller
Currently it only supports IP part number CI13412
Say "y" to link the driver statically, or "m" to build a
dynamically linked module called "ci13xxx_udc" and force all
gadget drivers to also be dynamically linked.
config USB_CI13XXX
tristate
depends on USB_GADGET_CI13XXX
default USB_GADGET
select USB_GADGET_SELECTED
config USB_GADGET_NET2280
boolean "NetChip 228x"
depends on PCI

View File

@@ -10,6 +10,7 @@ obj-$(CONFIG_USB_NET2280) += net2280.o
obj-$(CONFIG_USB_AMD5536UDC) += amd5536udc.o
obj-$(CONFIG_USB_PXA25X) += pxa25x_udc.o
obj-$(CONFIG_USB_PXA27X) += pxa27x_udc.o
obj-$(CONFIG_USB_IMX) += imx_udc.o
obj-$(CONFIG_USB_GOKU) += goku_udc.o
obj-$(CONFIG_USB_OMAP) += omap_udc.o
obj-$(CONFIG_USB_LH7A40X) += lh7a40x_udc.o
@@ -19,6 +20,7 @@ obj-$(CONFIG_USB_ATMEL_USBA) += atmel_usba_udc.o
obj-$(CONFIG_USB_FSL_USB2) += fsl_usb2_udc.o
obj-$(CONFIG_USB_M66592) += m66592-udc.o
obj-$(CONFIG_USB_FSL_QE) += fsl_qe_udc.o
obj-$(CONFIG_USB_CI13XXX) += ci13xxx_udc.o
#
# USB gadget drivers

View File

@@ -1474,7 +1474,7 @@ static struct at91_udc controller = {
.ep0 = &controller.ep[0].ep,
.name = driver_name,
.dev = {
.bus_id = "gadget",
.init_name = "gadget",
.release = nop_release,
}
},

View File

@@ -1034,7 +1034,7 @@ static struct usba_udc the_udc = {
.is_dualspeed = 1,
.name = "atmel_usba_udc",
.dev = {
.bus_id = "gadget",
.init_name = "gadget",
.release = nop_release,
},
},

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,195 @@
/*
* ci13xxx_udc.h - structures, registers, and macros MIPS USB IP core
*
* Copyright (C) 2008 Chipidea - MIPS Technologies, Inc. All rights reserved.
*
* Author: David Lopo
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* Description: MIPS USB IP core family device controller
* Structures, registers and logging macros
*/
#ifndef _CI13XXX_h_
#define _CI13XXX_h_
/******************************************************************************
* DEFINE
*****************************************************************************/
#define ENDPT_MAX (16)
#define CTRL_PAYLOAD_MAX (64)
#define RX (0) /* similar to USB_DIR_OUT but can be used as an index */
#define TX (1) /* similar to USB_DIR_IN but can be used as an index */
/******************************************************************************
* STRUCTURES
*****************************************************************************/
/* DMA layout of transfer descriptors */
struct ci13xxx_td {
/* 0 */
u32 next;
#define TD_TERMINATE BIT(0)
/* 1 */
u32 token;
#define TD_STATUS (0x00FFUL << 0)
#define TD_STATUS_TR_ERR BIT(3)
#define TD_STATUS_DT_ERR BIT(5)
#define TD_STATUS_HALTED BIT(6)
#define TD_STATUS_ACTIVE BIT(7)
#define TD_MULTO (0x0003UL << 10)
#define TD_IOC BIT(15)
#define TD_TOTAL_BYTES (0x7FFFUL << 16)
/* 2 */
u32 page[5];
#define TD_CURR_OFFSET (0x0FFFUL << 0)
#define TD_FRAME_NUM (0x07FFUL << 0)
#define TD_RESERVED_MASK (0x0FFFUL << 0)
} __attribute__ ((packed));
/* DMA layout of queue heads */
struct ci13xxx_qh {
/* 0 */
u32 cap;
#define QH_IOS BIT(15)
#define QH_MAX_PKT (0x07FFUL << 16)
#define QH_ZLT BIT(29)
#define QH_MULT (0x0003UL << 30)
/* 1 */
u32 curr;
/* 2 - 8 */
struct ci13xxx_td td;
/* 9 */
u32 RESERVED;
struct usb_ctrlrequest setup;
} __attribute__ ((packed));
/* Extension of usb_request */
struct ci13xxx_req {
struct usb_request req;
unsigned map;
struct list_head queue;
struct ci13xxx_td *ptr;
dma_addr_t dma;
};
/* Extension of usb_ep */
struct ci13xxx_ep {
struct usb_ep ep;
const struct usb_endpoint_descriptor *desc;
u8 dir;
u8 num;
u8 type;
char name[16];
struct {
struct list_head queue;
struct ci13xxx_qh *ptr;
dma_addr_t dma;
} qh[2];
struct usb_request *status;
int wedge;
/* global resources */
spinlock_t *lock;
struct device *device;
struct dma_pool *td_pool;
};
/* CI13XXX UDC descriptor & global resources */
struct ci13xxx {
spinlock_t *lock; /* ctrl register bank access */
struct dma_pool *qh_pool; /* DMA pool for queue heads */
struct dma_pool *td_pool; /* DMA pool for transfer descs */
struct usb_gadget gadget; /* USB slave device */
struct ci13xxx_ep ci13xxx_ep[ENDPT_MAX]; /* extended endpts */
struct usb_gadget_driver *driver; /* 3rd party gadget driver */
};
/******************************************************************************
* REGISTERS
*****************************************************************************/
/* register size */
#define REG_BITS (32)
/* HCCPARAMS */
#define HCCPARAMS_LEN BIT(17)
/* DCCPARAMS */
#define DCCPARAMS_DEN (0x1F << 0)
#define DCCPARAMS_DC BIT(7)
/* TESTMODE */
#define TESTMODE_FORCE BIT(0)
/* USBCMD */
#define USBCMD_RS BIT(0)
#define USBCMD_RST BIT(1)
#define USBCMD_SUTW BIT(13)
/* USBSTS & USBINTR */
#define USBi_UI BIT(0)
#define USBi_UEI BIT(1)
#define USBi_PCI BIT(2)
#define USBi_URI BIT(6)
#define USBi_SLI BIT(8)
/* DEVICEADDR */
#define DEVICEADDR_USBADRA BIT(24)
#define DEVICEADDR_USBADR (0x7FUL << 25)
/* PORTSC */
#define PORTSC_SUSP BIT(7)
#define PORTSC_HSP BIT(9)
#define PORTSC_PTC (0x0FUL << 16)
/* DEVLC */
#define DEVLC_PSPD (0x03UL << 25)
#define DEVLC_PSPD_HS (0x02UL << 25)
/* USBMODE */
#define USBMODE_CM (0x03UL << 0)
#define USBMODE_CM_IDLE (0x00UL << 0)
#define USBMODE_CM_DEVICE (0x02UL << 0)
#define USBMODE_CM_HOST (0x03UL << 0)
#define USBMODE_SLOM BIT(3)
/* ENDPTCTRL */
#define ENDPTCTRL_RXS BIT(0)
#define ENDPTCTRL_RXT (0x03UL << 2)
#define ENDPTCTRL_RXR BIT(6) /* reserved for port 0 */
#define ENDPTCTRL_RXE BIT(7)
#define ENDPTCTRL_TXS BIT(16)
#define ENDPTCTRL_TXT (0x03UL << 18)
#define ENDPTCTRL_TXR BIT(22) /* reserved for port 0 */
#define ENDPTCTRL_TXE BIT(23)
/******************************************************************************
* LOGGING
*****************************************************************************/
#define ci13xxx_printk(level, format, args...) \
do { \
if (_udc == NULL) \
printk(level "[%s] " format "\n", __func__, ## args); \
else \
dev_printk(level, _udc->gadget.dev.parent, \
"[%s] " format "\n", __func__, ## args); \
} while (0)
#define err(format, args...) ci13xxx_printk(KERN_ERR, format, ## args)
#define warn(format, args...) ci13xxx_printk(KERN_WARNING, format, ## args)
#define info(format, args...) ci13xxx_printk(KERN_INFO, format, ## args)
#ifdef TRACE
#define trace(format, args...) ci13xxx_printk(KERN_DEBUG, format, ## args)
#define dbg_trace(format, args...) dev_dbg(dev, format, ##args)
#else
#define trace(format, args...) do {} while (0)
#define dbg_trace(format, args...) do {} while (0)
#endif
#endif /* _CI13XXX_h_ */

View File

@@ -161,7 +161,7 @@ ep_matches (
/* report address */
desc->bEndpointAddress &= USB_DIR_IN;
if (isdigit (ep->name [2])) {
u8 num = simple_strtol (&ep->name [2], NULL, 10);
u8 num = simple_strtoul (&ep->name [2], NULL, 10);
desc->bEndpointAddress |= num;
#ifdef MANY_ENDPOINTS
} else if (desc->bEndpointAddress & USB_DIR_IN) {

View File

@@ -1,7 +1,7 @@
/*
* file_storage.c -- File-backed USB Storage Gadget, for USB development
*
* Copyright (C) 2003-2007 Alan Stern
* Copyright (C) 2003-2008 Alan Stern
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
@@ -38,16 +38,17 @@
/*
* The File-backed Storage Gadget acts as a USB Mass Storage device,
* appearing to the host as a disk drive. In addition to providing an
* example of a genuinely useful gadget driver for a USB device, it also
* illustrates a technique of double-buffering for increased throughput.
* Last but not least, it gives an easy way to probe the behavior of the
* Mass Storage drivers in a USB host.
* appearing to the host as a disk drive or as a CD-ROM drive. In addition
* to providing an example of a genuinely useful gadget driver for a USB
* device, it also illustrates a technique of double-buffering for increased
* throughput. Last but not least, it gives an easy way to probe the
* behavior of the Mass Storage drivers in a USB host.
*
* Backing storage is provided by a regular file or a block device, specified
* by the "file" module parameter. Access can be limited to read-only by
* setting the optional "ro" module parameter. The gadget will indicate that
* it has removable media if the optional "removable" module parameter is set.
* setting the optional "ro" module parameter. (For CD-ROM emulation,
* access is always read-only.) The gadget will indicate that it has
* removable media if the optional "removable" module parameter is set.
*
* The gadget supports the Control-Bulk (CB), Control-Bulk-Interrupt (CBI),
* and Bulk-Only (also known as Bulk-Bulk-Bulk or BBB) transports, selected
@@ -64,7 +65,12 @@
* The default number of LUNs is taken from the number of "file" elements;
* it is 1 if "file" is not given. If "removable" is not set then a backing
* file must be specified for each LUN. If it is set, then an unspecified
* or empty backing filename means the LUN's medium is not loaded.
* or empty backing filename means the LUN's medium is not loaded. Ideally
* each LUN would be settable independently as a disk drive or a CD-ROM
* drive, but currently all LUNs have to be the same type. The CD-ROM
* emulation includes a single data track and no audio tracks; hence there
* need be only one backing file per LUN. Note also that the CD-ROM block
* length is set to 512 rather than the more common value 2048.
*
* Requirements are modest; only a bulk-in and a bulk-out endpoint are
* needed (an interrupt-out endpoint is also needed for CBI). The memory
@@ -91,6 +97,8 @@
* USB device controller (usually true),
* boolean to permit the driver to halt
* bulk endpoints
* cdrom Default false, boolean for whether to emulate
* a CD-ROM drive
* transport=XXX Default BBB, transport name (CB, CBI, or BBB)
* protocol=YYY Default SCSI, protocol name (RBC, 8020 or
* ATAPI, QIC, UFI, 8070, or SCSI;
@@ -103,15 +111,16 @@
* PAGE_CACHE_SIZE)
*
* If CONFIG_USB_FILE_STORAGE_TEST is not set, only the "file", "ro",
* "removable", "luns", and "stall" options are available; default values
* are used for everything else.
* "removable", "luns", "stall", and "cdrom" options are available; default
* values are used for everything else.
*
* The pathnames of the backing files and the ro settings are available in
* the attribute files "file" and "ro" in the lun<n> subdirectory of the
* gadget's sysfs directory. If the "removable" option is set, writing to
* these files will simulate ejecting/loading the medium (writing an empty
* line means eject) and adjusting a write-enable tab. Changes to the ro
* setting are not allowed when the medium is loaded.
* setting are not allowed when the medium is loaded or if CD-ROM emulation
* is being used.
*
* This gadget driver is heavily based on "Gadget Zero" by David Brownell.
* The driver's SCSI command interface was based on the "Information
@@ -261,7 +270,7 @@
#define DRIVER_DESC "File-backed Storage Gadget"
#define DRIVER_NAME "g_file_storage"
#define DRIVER_VERSION "7 August 2007"
#define DRIVER_VERSION "20 November 2008"
static const char longname[] = DRIVER_DESC;
static const char shortname[] = DRIVER_NAME;
@@ -341,6 +350,7 @@ static struct {
int removable;
int can_stall;
int cdrom;
char *transport_parm;
char *protocol_parm;
@@ -359,6 +369,7 @@ static struct {
.protocol_parm = "SCSI",
.removable = 0,
.can_stall = 1,
.cdrom = 0,
.vendor = DRIVER_VENDOR_ID,
.product = DRIVER_PRODUCT_ID,
.release = 0xffff, // Use controller chip type
@@ -382,6 +393,9 @@ MODULE_PARM_DESC(removable, "true to simulate removable media");
module_param_named(stall, mod_data.can_stall, bool, S_IRUGO);
MODULE_PARM_DESC(stall, "false to prevent bulk stalls");
module_param_named(cdrom, mod_data.cdrom, bool, S_IRUGO);
MODULE_PARM_DESC(cdrom, "true to emulate cdrom instead of disk");
/* In the non-TEST version, only the module parameters listed above
* are available. */
@@ -411,6 +425,10 @@ MODULE_PARM_DESC(buflen, "I/O buffer size");
/*-------------------------------------------------------------------------*/
/* SCSI device types */
#define TYPE_DISK 0x00
#define TYPE_CDROM 0x05
/* USB protocol value = the transport method */
#define USB_PR_CBI 0x00 // Control/Bulk/Interrupt
#define USB_PR_CB 0x01 // Control/Bulk w/o interrupt
@@ -487,6 +505,8 @@ struct interrupt_data {
#define SC_READ_12 0xa8
#define SC_READ_CAPACITY 0x25
#define SC_READ_FORMAT_CAPACITIES 0x23
#define SC_READ_HEADER 0x44
#define SC_READ_TOC 0x43
#define SC_RELEASE 0x17
#define SC_REQUEST_SENSE 0x03
#define SC_RESERVE 0x16
@@ -2006,23 +2026,28 @@ static int do_inquiry(struct fsg_dev *fsg, struct fsg_buffhd *bh)
u8 *buf = (u8 *) bh->buf;
static char vendor_id[] = "Linux ";
static char product_id[] = "File-Stor Gadget";
static char product_disk_id[] = "File-Stor Gadget";
static char product_cdrom_id[] = "File-CD Gadget ";
if (!fsg->curlun) { // Unsupported LUNs are okay
fsg->bad_lun_okay = 1;
memset(buf, 0, 36);
buf[0] = 0x7f; // Unsupported, no device-type
buf[4] = 31; // Additional length
return 36;
}
memset(buf, 0, 8); // Non-removable, direct-access device
memset(buf, 0, 8);
buf[0] = (mod_data.cdrom ? TYPE_CDROM : TYPE_DISK);
if (mod_data.removable)
buf[1] = 0x80;
buf[2] = 2; // ANSI SCSI level 2
buf[3] = 2; // SCSI-2 INQUIRY data format
buf[4] = 31; // Additional length
// No special options
sprintf(buf + 8, "%-8s%-16s%04x", vendor_id, product_id,
sprintf(buf + 8, "%-8s%-16s%04x", vendor_id,
(mod_data.cdrom ? product_cdrom_id :
product_disk_id),
mod_data.release);
return 36;
}
@@ -2101,6 +2126,75 @@ static int do_read_capacity(struct fsg_dev *fsg, struct fsg_buffhd *bh)
}
static void store_cdrom_address(u8 *dest, int msf, u32 addr)
{
if (msf) {
/* Convert to Minutes-Seconds-Frames */
addr >>= 2; /* Convert to 2048-byte frames */
addr += 2*75; /* Lead-in occupies 2 seconds */
dest[3] = addr % 75; /* Frames */
addr /= 75;
dest[2] = addr % 60; /* Seconds */
addr /= 60;
dest[1] = addr; /* Minutes */
dest[0] = 0; /* Reserved */
} else {
/* Absolute sector */
put_be32(dest, addr);
}
}
static int do_read_header(struct fsg_dev *fsg, struct fsg_buffhd *bh)
{
struct lun *curlun = fsg->curlun;
int msf = fsg->cmnd[1] & 0x02;
u32 lba = get_be32(&fsg->cmnd[2]);
u8 *buf = (u8 *) bh->buf;
if ((fsg->cmnd[1] & ~0x02) != 0) { /* Mask away MSF */
curlun->sense_data = SS_INVALID_FIELD_IN_CDB;
return -EINVAL;
}
if (lba >= curlun->num_sectors) {
curlun->sense_data = SS_LOGICAL_BLOCK_ADDRESS_OUT_OF_RANGE;
return -EINVAL;
}
memset(buf, 0, 8);
buf[0] = 0x01; /* 2048 bytes of user data, rest is EC */
store_cdrom_address(&buf[4], msf, lba);
return 8;
}
static int do_read_toc(struct fsg_dev *fsg, struct fsg_buffhd *bh)
{
struct lun *curlun = fsg->curlun;
int msf = fsg->cmnd[1] & 0x02;
int start_track = fsg->cmnd[6];
u8 *buf = (u8 *) bh->buf;
if ((fsg->cmnd[1] & ~0x02) != 0 || /* Mask away MSF */
start_track > 1) {
curlun->sense_data = SS_INVALID_FIELD_IN_CDB;
return -EINVAL;
}
memset(buf, 0, 20);
buf[1] = (20-2); /* TOC data length */
buf[2] = 1; /* First track number */
buf[3] = 1; /* Last track number */
buf[5] = 0x16; /* Data track, copying allowed */
buf[6] = 0x01; /* Only track is number 1 */
store_cdrom_address(&buf[8], msf, 0);
buf[13] = 0x16; /* Lead-out track is data */
buf[14] = 0xAA; /* Lead-out track number */
store_cdrom_address(&buf[16], msf, curlun->num_sectors);
return 20;
}
static int do_mode_sense(struct fsg_dev *fsg, struct fsg_buffhd *bh)
{
struct lun *curlun = fsg->curlun;
@@ -2848,6 +2942,26 @@ static int do_scsi_command(struct fsg_dev *fsg)
reply = do_read_capacity(fsg, bh);
break;
case SC_READ_HEADER:
if (!mod_data.cdrom)
goto unknown_cmnd;
fsg->data_size_from_cmnd = get_be16(&fsg->cmnd[7]);
if ((reply = check_command(fsg, 10, DATA_DIR_TO_HOST,
(3<<7) | (0x1f<<1), 1,
"READ HEADER")) == 0)
reply = do_read_header(fsg, bh);
break;
case SC_READ_TOC:
if (!mod_data.cdrom)
goto unknown_cmnd;
fsg->data_size_from_cmnd = get_be16(&fsg->cmnd[7]);
if ((reply = check_command(fsg, 10, DATA_DIR_TO_HOST,
(7<<6) | (1<<1), 1,
"READ TOC")) == 0)
reply = do_read_toc(fsg, bh);
break;
case SC_READ_FORMAT_CAPACITIES:
fsg->data_size_from_cmnd = get_be16(&fsg->cmnd[7]);
if ((reply = check_command(fsg, 10, DATA_DIR_TO_HOST,
@@ -2933,6 +3047,7 @@ static int do_scsi_command(struct fsg_dev *fsg)
// Fall through
default:
unknown_cmnd:
fsg->data_size_from_cmnd = 0;
sprintf(unknown, "Unknown x%02x", fsg->cmnd[0]);
if ((reply = check_command(fsg, fsg->cmnd_size,
@@ -3498,6 +3613,7 @@ static int open_backing_file(struct lun *curlun, const char *filename)
struct inode *inode = NULL;
loff_t size;
loff_t num_sectors;
loff_t min_sectors;
/* R/W if we can, R/O if we must */
ro = curlun->ro;
@@ -3541,8 +3657,19 @@ static int open_backing_file(struct lun *curlun, const char *filename)
rc = (int) size;
goto out;
}
num_sectors = size >> 9; // File size in 512-byte sectors
if (num_sectors == 0) {
num_sectors = size >> 9; // File size in 512-byte blocks
min_sectors = 1;
if (mod_data.cdrom) {
num_sectors &= ~3; // Reduce to a multiple of 2048
min_sectors = 300*4; // Smallest track is 300 frames
if (num_sectors >= 256*60*75*4) {
num_sectors = (256*60*75 - 1) * 4;
LINFO(curlun, "file too big: %s\n", filename);
LINFO(curlun, "using only first %d blocks\n",
(int) num_sectors);
}
}
if (num_sectors < min_sectors) {
LINFO(curlun, "file too small: %s\n", filename);
rc = -ETOOSMALL;
goto out;
@@ -3845,9 +3972,12 @@ static int __init fsg_bind(struct usb_gadget *gadget)
goto out;
if (mod_data.removable) { // Enable the store_xxx attributes
dev_attr_ro.attr.mode = dev_attr_file.attr.mode = 0644;
dev_attr_ro.store = store_ro;
dev_attr_file.attr.mode = 0644;
dev_attr_file.store = store_file;
if (!mod_data.cdrom) {
dev_attr_ro.attr.mode = 0644;
dev_attr_ro.store = store_ro;
}
}
/* Find out how many LUNs there should be */
@@ -3872,6 +4002,8 @@ static int __init fsg_bind(struct usb_gadget *gadget)
for (i = 0; i < fsg->nluns; ++i) {
curlun = &fsg->luns[i];
curlun->ro = mod_data.ro[i];
if (mod_data.cdrom)
curlun->ro = 1;
curlun->dev.release = lun_release;
curlun->dev.parent = &gadget->dev;
curlun->dev.driver = &fsg_driver.driver;
@@ -4031,9 +4163,9 @@ static int __init fsg_bind(struct usb_gadget *gadget)
mod_data.protocol_name, mod_data.protocol_type);
DBG(fsg, "VendorID=x%04x, ProductID=x%04x, Release=x%04x\n",
mod_data.vendor, mod_data.product, mod_data.release);
DBG(fsg, "removable=%d, stall=%d, buflen=%u\n",
DBG(fsg, "removable=%d, stall=%d, cdrom=%d, buflen=%u\n",
mod_data.removable, mod_data.can_stall,
mod_data.buflen);
mod_data.cdrom, mod_data.buflen);
DBG(fsg, "I/O thread pid: %d\n", task_pid_nr(fsg->thread_task));
set_bit(REGISTERED, &fsg->atomic_bitflags);
@@ -4050,6 +4182,7 @@ out:
fsg->state = FSG_STATE_TERMINATED; // The thread is dead
fsg_unbind(gadget);
close_all_backing_files(fsg);
complete(&fsg->thread_notifier);
return rc;
}

View File

@@ -26,6 +26,7 @@
#include <linux/ioport.h>
#include <linux/types.h>
#include <linux/errno.h>
#include <linux/err.h>
#include <linux/slab.h>
#include <linux/list.h>
#include <linux/interrupt.h>
@@ -370,6 +371,9 @@ static int qe_ep_bd_init(struct qe_udc *udc, unsigned char pipe_num)
/* alloc multi-ram for BD rings and set the ep parameters */
tmp_addr = cpm_muram_alloc(sizeof(struct qe_bd) * (bdring_len +
USB_BDRING_LEN_TX), QE_ALIGNMENT_OF_BD);
if (IS_ERR_VALUE(tmp_addr))
return -ENOMEM;
out_be16(&epparam->rbase, (u16)tmp_addr);
out_be16(&epparam->tbase, (u16)(tmp_addr +
(sizeof(struct qe_bd) * bdring_len)));
@@ -689,7 +693,7 @@ en_done2:
en_done1:
spin_unlock_irqrestore(&udc->lock, flags);
en_done:
dev_dbg(udc->dev, "failed to initialize %s\n", ep->ep.name);
dev_err(udc->dev, "failed to initialize %s\n", ep->ep.name);
return -ENODEV;
}
@@ -2408,6 +2412,8 @@ static struct qe_udc __devinit *qe_udc_config(struct of_device *ofdev)
tmp_addr = cpm_muram_alloc((USB_MAX_ENDPOINTS *
sizeof(struct usb_ep_para)),
USB_EP_PARA_ALIGNMENT);
if (IS_ERR_VALUE(tmp_addr))
goto cleanup;
for (i = 0; i < USB_MAX_ENDPOINTS; i++) {
out_be16(&usbpram->epptr[i], (u16)tmp_addr);
@@ -2513,7 +2519,7 @@ static int __devinit qe_udc_probe(struct of_device *ofdev,
/* Initialize the udc structure including QH member and other member */
udc_controller = qe_udc_config(ofdev);
if (!udc_controller) {
dev_dbg(&ofdev->dev, "udc_controll is NULL\n");
dev_err(&ofdev->dev, "failed to initialize\n");
return -ENOMEM;
}
@@ -2545,7 +2551,7 @@ static int __devinit qe_udc_probe(struct of_device *ofdev,
device_initialize(&udc_controller->gadget.dev);
strcpy(udc_controller->gadget.dev.bus_id, "gadget");
dev_set_name(&udc_controller->gadget.dev, "gadget");
udc_controller->gadget.dev.release = qe_udc_release;
udc_controller->gadget.dev.parent = &ofdev->dev;
@@ -2568,7 +2574,7 @@ static int __devinit qe_udc_probe(struct of_device *ofdev,
/* create a buf for ZLP send, need to remain zeroed */
udc_controller->nullbuf = kzalloc(256, GFP_KERNEL);
if (udc_controller->nullbuf == NULL) {
dev_dbg(udc_controller->dev, "cannot alloc nullbuf\n");
dev_err(udc_controller->dev, "cannot alloc nullbuf\n");
ret = -ENOMEM;
goto err3;
}

View File

@@ -110,7 +110,6 @@
#define gadget_is_at91(g) 0
#endif
/* status unclear */
#ifdef CONFIG_USB_GADGET_IMX
#define gadget_is_imx(g) !strcmp("imx_udc", (g)->name)
#else
@@ -158,6 +157,11 @@
#define gadget_is_fsl_qe(g) 0
#endif
#ifdef CONFIG_USB_GADGET_CI13XXX
#define gadget_is_ci13xxx(g) (!strcmp("ci13xxx_udc", (g)->name))
#else
#define gadget_is_ci13xxx(g) 0
#endif
// CONFIG_USB_GADGET_SX2
// CONFIG_USB_GADGET_AU1X00
@@ -225,6 +229,8 @@ static inline int usb_gadget_controller_number(struct usb_gadget *gadget)
return 0x21;
else if (gadget_is_fsl_qe(gadget))
return 0x22;
else if (gadget_is_ci13xxx(gadget))
return 0x23;
return -ENOENT;
}

View File

@@ -1349,7 +1349,7 @@ int usb_gadget_register_driver(struct usb_gadget_driver *driver)
int retval;
if (!driver
|| driver->speed != USB_SPEED_FULL
|| driver->speed < USB_SPEED_FULL
|| !driver->bind
|| !driver->disconnect
|| !driver->setup)

1516
drivers/usb/gadget/imx_udc.c Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,344 @@
/*
* Copyright (C) 2005 Mike Lee(eemike@gmail.com)
*
* This udc driver is now under testing and code is based on pxa2xx_udc.h
* Please use it with your own risk!
*
* 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.
*/
#ifndef __LINUX_USB_GADGET_IMX_H
#define __LINUX_USB_GADGET_IMX_H
#include <linux/types.h>
/* Helper macros */
#define EP_NO(ep) ((ep->bEndpointAddress) & ~USB_DIR_IN) /* IN:1, OUT:0 */
#define EP_DIR(ep) ((ep->bEndpointAddress) & USB_DIR_IN ? 1 : 0)
#define irq_to_ep(irq) (((irq) >= USBD_INT0) || ((irq) <= USBD_INT6) ? ((irq) - USBD_INT0) : (USBD_INT6)) /*should not happen*/
#define ep_to_irq(ep) (EP_NO((ep)) + USBD_INT0)
#define IMX_USB_NB_EP 6
/* Driver structures */
struct imx_request {
struct usb_request req;
struct list_head queue;
unsigned int in_use;
};
enum ep0_state {
EP0_IDLE,
EP0_IN_DATA_PHASE,
EP0_OUT_DATA_PHASE,
EP0_CONFIG,
EP0_STALL,
};
struct imx_ep_struct {
struct usb_ep ep;
struct imx_udc_struct *imx_usb;
struct list_head queue;
unsigned char stopped;
unsigned char fifosize;
unsigned char bEndpointAddress;
unsigned char bmAttributes;
};
struct imx_udc_struct {
struct usb_gadget gadget;
struct usb_gadget_driver *driver;
struct device *dev;
struct imx_ep_struct imx_ep[IMX_USB_NB_EP];
struct clk *clk;
enum ep0_state ep0state;
struct resource *res;
void __iomem *base;
unsigned char set_config;
int cfg,
intf,
alt,
usbd_int[7];
};
/* USB registers */
#define USB_FRAME (0x00) /* USB frame */
#define USB_SPEC (0x04) /* USB Spec */
#define USB_STAT (0x08) /* USB Status */
#define USB_CTRL (0x0C) /* USB Control */
#define USB_DADR (0x10) /* USB Desc RAM addr */
#define USB_DDAT (0x14) /* USB Desc RAM/EP buffer data */
#define USB_INTR (0x18) /* USB interrupt */
#define USB_MASK (0x1C) /* USB Mask */
#define USB_ENAB (0x24) /* USB Enable */
#define USB_EP_STAT(x) (0x30 + (x*0x30)) /* USB status/control */
#define USB_EP_INTR(x) (0x34 + (x*0x30)) /* USB interrupt */
#define USB_EP_MASK(x) (0x38 + (x*0x30)) /* USB mask */
#define USB_EP_FDAT(x) (0x3C + (x*0x30)) /* USB FIFO data */
#define USB_EP_FDAT0(x) (0x3C + (x*0x30)) /* USB FIFO data */
#define USB_EP_FDAT1(x) (0x3D + (x*0x30)) /* USB FIFO data */
#define USB_EP_FDAT2(x) (0x3E + (x*0x30)) /* USB FIFO data */
#define USB_EP_FDAT3(x) (0x3F + (x*0x30)) /* USB FIFO data */
#define USB_EP_FSTAT(x) (0x40 + (x*0x30)) /* USB FIFO status */
#define USB_EP_FCTRL(x) (0x44 + (x*0x30)) /* USB FIFO control */
#define USB_EP_LRFP(x) (0x48 + (x*0x30)) /* USB last read frame pointer */
#define USB_EP_LWFP(x) (0x4C + (x*0x30)) /* USB last write frame pointer */
#define USB_EP_FALRM(x) (0x50 + (x*0x30)) /* USB FIFO alarm */
#define USB_EP_FRDP(x) (0x54 + (x*0x30)) /* USB FIFO read pointer */
#define USB_EP_FWRP(x) (0x58 + (x*0x30)) /* USB FIFO write pointer */
/* USB Control Register Bit Fields.*/
#define CTRL_CMDOVER (1<<6) /* UDC status */
#define CTRL_CMDERROR (1<<5) /* UDC status */
#define CTRL_FE_ENA (1<<3) /* Enable Font End logic */
#define CTRL_UDC_RST (1<<2) /* UDC reset */
#define CTRL_AFE_ENA (1<<1) /* Analog Font end enable */
#define CTRL_RESUME (1<<0) /* UDC resume */
/* USB Status Register Bit Fields.*/
#define STAT_RST (1<<8)
#define STAT_SUSP (1<<7)
#define STAT_CFG (3<<5)
#define STAT_INTF (3<<3)
#define STAT_ALTSET (7<<0)
/* USB Interrupt Status/Mask Registers Bit fields */
#define INTR_WAKEUP (1<<31) /* Wake up Interrupt */
#define INTR_MSOF (1<<7) /* Missed Start of Frame */
#define INTR_SOF (1<<6) /* Start of Frame */
#define INTR_RESET_STOP (1<<5) /* Reset Signaling stop */
#define INTR_RESET_START (1<<4) /* Reset Signaling start */
#define INTR_RESUME (1<<3) /* Suspend to resume */
#define INTR_SUSPEND (1<<2) /* Active to suspend */
#define INTR_FRAME_MATCH (1<<1) /* Frame matched */
#define INTR_CFG_CHG (1<<0) /* Configuration change occurred */
/* USB Enable Register Bit Fields.*/
#define ENAB_RST (1<<31) /* Reset USB modules */
#define ENAB_ENAB (1<<30) /* Enable USB modules*/
#define ENAB_SUSPEND (1<<29) /* Suspend USB modules */
#define ENAB_ENDIAN (1<<28) /* Endian of USB modules */
#define ENAB_PWRMD (1<<0) /* Power mode of USB modules */
/* USB Descriptor Ram Address Register bit fields */
#define DADR_CFG (1<<31) /* Configuration */
#define DADR_BSY (1<<30) /* Busy status */
#define DADR_DADR (0x1FF) /* Descriptor Ram Address */
/* USB Descriptor RAM/Endpoint Buffer Data Register bit fields */
#define DDAT_DDAT (0xFF) /* Descriptor Endpoint Buffer */
/* USB Endpoint Status Register bit fields */
#define EPSTAT_BCOUNT (0x7F<<16) /* Endpoint FIFO byte count */
#define EPSTAT_SIP (1<<8) /* Endpoint setup in progress */
#define EPSTAT_DIR (1<<7) /* Endpoint transfer direction */
#define EPSTAT_MAX (3<<5) /* Endpoint Max packet size */
#define EPSTAT_TYP (3<<3) /* Endpoint type */
#define EPSTAT_ZLPS (1<<2) /* Send zero length packet */
#define EPSTAT_FLUSH (1<<1) /* Endpoint FIFO Flush */
#define EPSTAT_STALL (1<<0) /* Force stall */
/* USB Endpoint FIFO Status Register bit fields */
#define FSTAT_FRAME_STAT (0xF<<24) /* Frame status bit [0-3] */
#define FSTAT_ERR (1<<22) /* FIFO error */
#define FSTAT_UF (1<<21) /* FIFO underflow */
#define FSTAT_OF (1<<20) /* FIFO overflow */
#define FSTAT_FR (1<<19) /* FIFO frame ready */
#define FSTAT_FULL (1<<18) /* FIFO full */
#define FSTAT_ALRM (1<<17) /* FIFO alarm */
#define FSTAT_EMPTY (1<<16) /* FIFO empty */
/* USB Endpoint FIFO Control Register bit fields */
#define FCTRL_WFR (1<<29) /* Write frame end */
/* USB Endpoint Interrupt Status Regsiter bit fields */
#define EPINTR_FIFO_FULL (1<<8) /* fifo full */
#define EPINTR_FIFO_EMPTY (1<<7) /* fifo empty */
#define EPINTR_FIFO_ERROR (1<<6) /* fifo error */
#define EPINTR_FIFO_HIGH (1<<5) /* fifo high */
#define EPINTR_FIFO_LOW (1<<4) /* fifo low */
#define EPINTR_MDEVREQ (1<<3) /* multi Device request */
#define EPINTR_EOT (1<<2) /* fifo end of transfer */
#define EPINTR_DEVREQ (1<<1) /* Device request */
#define EPINTR_EOF (1<<0) /* fifo end of frame */
/* Debug macros */
#ifdef DEBUG
/* #define DEBUG_REQ */
/* #define DEBUG_TRX */
/* #define DEBUG_INIT */
/* #define DEBUG_EP0 */
/* #define DEBUG_EPX */
/* #define DEBUG_IRQ */
/* #define DEBUG_EPIRQ */
/* #define DEBUG_DUMP */
#define DEBUG_ERR
#ifdef DEBUG_REQ
#define D_REQ(dev, args...) dev_dbg(dev, ## args)
#else
#define D_REQ(dev, args...) do {} while (0)
#endif /* DEBUG_REQ */
#ifdef DEBUG_TRX
#define D_TRX(dev, args...) dev_dbg(dev, ## args)
#else
#define D_TRX(dev, args...) do {} while (0)
#endif /* DEBUG_TRX */
#ifdef DEBUG_INIT
#define D_INI(dev, args...) dev_dbg(dev, ## args)
#else
#define D_INI(dev, args...) do {} while (0)
#endif /* DEBUG_INIT */
#ifdef DEBUG_EP0
static const char *state_name[] = {
"EP0_IDLE",
"EP0_IN_DATA_PHASE",
"EP0_OUT_DATA_PHASE",
"EP0_CONFIG",
"EP0_STALL"
};
#define D_EP0(dev, args...) dev_dbg(dev, ## args)
#else
#define D_EP0(dev, args...) do {} while (0)
#endif /* DEBUG_EP0 */
#ifdef DEBUG_EPX
#define D_EPX(dev, args...) dev_dbg(dev, ## args)
#else
#define D_EPX(dev, args...) do {} while (0)
#endif /* DEBUG_EP0 */
#ifdef DEBUG_IRQ
static void dump_intr(const char *label, int irqreg, struct device *dev)
{
dev_dbg(dev, "<%s> USB_INTR=[%s%s%s%s%s%s%s%s%s]\n", label,
(irqreg & INTR_WAKEUP) ? " wake" : "",
(irqreg & INTR_MSOF) ? " msof" : "",
(irqreg & INTR_SOF) ? " sof" : "",
(irqreg & INTR_RESUME) ? " resume" : "",
(irqreg & INTR_SUSPEND) ? " suspend" : "",
(irqreg & INTR_RESET_STOP) ? " noreset" : "",
(irqreg & INTR_RESET_START) ? " reset" : "",
(irqreg & INTR_FRAME_MATCH) ? " fmatch" : "",
(irqreg & INTR_CFG_CHG) ? " config" : "");
}
#else
#define dump_intr(x, y, z) do {} while (0)
#endif /* DEBUG_IRQ */
#ifdef DEBUG_EPIRQ
static void dump_ep_intr(const char *label, int nr, int irqreg, struct device *dev)
{
dev_dbg(dev, "<%s> EP%d_INTR=[%s%s%s%s%s%s%s%s%s]\n", label, nr,
(irqreg & EPINTR_FIFO_FULL) ? " full" : "",
(irqreg & EPINTR_FIFO_EMPTY) ? " fempty" : "",
(irqreg & EPINTR_FIFO_ERROR) ? " ferr" : "",
(irqreg & EPINTR_FIFO_HIGH) ? " fhigh" : "",
(irqreg & EPINTR_FIFO_LOW) ? " flow" : "",
(irqreg & EPINTR_MDEVREQ) ? " mreq" : "",
(irqreg & EPINTR_EOF) ? " eof" : "",
(irqreg & EPINTR_DEVREQ) ? " devreq" : "",
(irqreg & EPINTR_EOT) ? " eot" : "");
}
#else
#define dump_ep_intr(x, y, z, i) do {} while (0)
#endif /* DEBUG_IRQ */
#ifdef DEBUG_DUMP
static void dump_usb_stat(const char *label, struct imx_udc_struct *imx_usb)
{
int temp = __raw_readl(imx_usb->base + USB_STAT);
dev_dbg(imx_usb->dev,
"<%s> USB_STAT=[%s%s CFG=%d, INTF=%d, ALTR=%d]\n", label,
(temp & STAT_RST) ? " reset" : "",
(temp & STAT_SUSP) ? " suspend" : "",
(temp & STAT_CFG) >> 5,
(temp & STAT_INTF) >> 3,
(temp & STAT_ALTSET));
}
static void dump_ep_stat(const char *label, struct imx_ep_struct *imx_ep)
{
int temp = __raw_readl(imx_ep->imx_usb->base + USB_EP_INTR(EP_NO(imx_ep)));
dev_dbg(imx_ep->imx_usb->dev,
"<%s> EP%d_INTR=[%s%s%s%s%s%s%s%s%s]\n", label, EP_NO(imx_ep),
(temp & EPINTR_FIFO_FULL) ? " full" : "",
(temp & EPINTR_FIFO_EMPTY) ? " fempty" : "",
(temp & EPINTR_FIFO_ERROR) ? " ferr" : "",
(temp & EPINTR_FIFO_HIGH) ? " fhigh" : "",
(temp & EPINTR_FIFO_LOW) ? " flow" : "",
(temp & EPINTR_MDEVREQ) ? " mreq" : "",
(temp & EPINTR_EOF) ? " eof" : "",
(temp & EPINTR_DEVREQ) ? " devreq" : "",
(temp & EPINTR_EOT) ? " eot" : "");
temp = __raw_readl(imx_ep->imx_usb->base + USB_EP_STAT(EP_NO(imx_ep)));
dev_dbg(imx_ep->imx_usb->dev,
"<%s> EP%d_STAT=[%s%s bcount=%d]\n", label, EP_NO(imx_ep),
(temp & EPSTAT_SIP) ? " sip" : "",
(temp & EPSTAT_STALL) ? " stall" : "",
(temp & EPSTAT_BCOUNT) >> 16);
temp = __raw_readl(imx_ep->imx_usb->base + USB_EP_FSTAT(EP_NO(imx_ep)));
dev_dbg(imx_ep->imx_usb->dev,
"<%s> EP%d_FSTAT=[%s%s%s%s%s%s%s]\n", label, EP_NO(imx_ep),
(temp & FSTAT_ERR) ? " ferr" : "",
(temp & FSTAT_UF) ? " funder" : "",
(temp & FSTAT_OF) ? " fover" : "",
(temp & FSTAT_FR) ? " fready" : "",
(temp & FSTAT_FULL) ? " ffull" : "",
(temp & FSTAT_ALRM) ? " falarm" : "",
(temp & FSTAT_EMPTY) ? " fempty" : "");
}
static void dump_req(const char *label, struct imx_ep_struct *imx_ep, struct usb_request *req)
{
int i;
if (!req || !req->buf) {
dev_dbg(imx_ep->imx_usb->dev, "<%s> req or req buf is free\n", label);
return;
}
if ((!EP_NO(imx_ep) && imx_ep->imx_usb->ep0state == EP0_IN_DATA_PHASE)
|| (EP_NO(imx_ep) && EP_DIR(imx_ep))) {
dev_dbg(imx_ep->imx_usb->dev, "<%s> request dump <", label);
for (i = 0; i < req->length; i++)
printk("%02x-", *((u8 *)req->buf + i));
printk(">\n");
}
}
#else
#define dump_ep_stat(x, y) do {} while (0)
#define dump_usb_stat(x, y) do {} while (0)
#define dump_req(x, y, z) do {} while (0)
#endif /* DEBUG_DUMP */
#ifdef DEBUG_ERR
#define D_ERR(dev, args...) dev_dbg(dev, ## args)
#else
#define D_ERR(dev, args...) do {} while (0)
#endif
#else
#define D_REQ(dev, args...) do {} while (0)
#define D_TRX(dev, args...) do {} while (0)
#define D_INI(dev, args...) do {} while (0)
#define D_EP0(dev, args...) do {} while (0)
#define D_EPX(dev, args...) do {} while (0)
#define dump_ep_intr(x, y, z, i) do {} while (0)
#define dump_intr(x, y, z) do {} while (0)
#define dump_ep_stat(x, y) do {} while (0)
#define dump_usb_stat(x, y) do {} while (0)
#define dump_req(x, y, z) do {} while (0)
#define D_ERR(dev, args...) do {} while (0)
#endif /* DEBUG */
#endif /* __LINUX_USB_GADGET_IMX_H */

View File

@@ -1981,7 +1981,7 @@ static struct lh7a40x_udc memory = {
.ep0 = &memory.ep[0].ep,
.name = driver_name,
.dev = {
.bus_id = "gadget",
.init_name = "gadget",
.release = nop_release,
},
},

View File

@@ -1546,8 +1546,6 @@ static void nop_completion(struct usb_ep *ep, struct usb_request *r)
{
}
#define resource_len(r) (((r)->end - (r)->start) + 1)
static int __init m66592_probe(struct platform_device *pdev)
{
struct resource *res;
@@ -1560,11 +1558,10 @@ static int __init m66592_probe(struct platform_device *pdev)
int ret = 0;
int i;
res = platform_get_resource_byname(pdev, IORESOURCE_MEM,
(char *)udc_name);
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
if (!res) {
ret = -ENODEV;
pr_err("platform_get_resource_byname error.\n");
pr_err("platform_get_resource error.\n");
goto clean_up;
}
@@ -1575,7 +1572,7 @@ static int __init m66592_probe(struct platform_device *pdev)
goto clean_up;
}
reg = ioremap(res->start, resource_len(res));
reg = ioremap(res->start, resource_size(res));
if (reg == NULL) {
ret = -ENOMEM;
pr_err("ioremap error.\n");

View File

@@ -669,7 +669,7 @@ fill_dma_desc (struct net2280_ep *ep, struct net2280_request *req, int valid)
/* 2280 may be polling VALID_BIT through ep->dma->dmadesc */
wmb ();
td->dmacount = cpu_to_le32p (&dmacount);
td->dmacount = cpu_to_le32(dmacount);
}
static const u32 dmactl_default =

View File

@@ -3006,7 +3006,7 @@ cleanup1:
cleanup0:
if (xceiv)
put_device(xceiv->dev);
otg_put_transceiver(xceiv);
if (cpu_is_omap16xx() || cpu_is_omap24xx()) {
clk_disable(hhc_clk);
@@ -3034,7 +3034,7 @@ static int __exit omap_udc_remove(struct platform_device *pdev)
pullup_disable(udc);
if (udc->transceiver) {
put_device(udc->transceiver->dev);
otg_put_transceiver(udc->transceiver);
udc->transceiver = NULL;
}
omap_writew(0, UDC_SYSCON1);

View File

@@ -1833,7 +1833,7 @@ static struct pxa25x_udc memory = {
.ep0 = &memory.ep[0].ep,
.name = driver_name,
.dev = {
.bus_id = "gadget",
.init_name = "gadget",
.release = nop_release,
},
},
@@ -2198,7 +2198,7 @@ static int __init pxa25x_udc_probe(struct platform_device *pdev)
udc_disable(dev);
udc_reinit(dev);
dev->vbus = is_vbus_present();
dev->vbus = !!is_vbus_present();
/* irq setup after old hardware state is cleaned up */
retval = request_irq(irq, pxa25x_udc_irq,

View File

@@ -430,7 +430,6 @@ static void pio_irq_enable(struct pxa_ep *ep)
/**
* pio_irq_disable - Disables irq generation for one endpoint
* @ep: udc endpoint
* @index: endpoint number
*/
static void pio_irq_disable(struct pxa_ep *ep)
{
@@ -586,7 +585,6 @@ static void inc_ep_stats_reqs(struct pxa_ep *ep, int is_in)
* inc_ep_stats_bytes - Update ep stats counts
* @ep: physical endpoint
* @count: bytes transfered on endpoint
* @req: usb request
* @is_in: ep direction (USB_DIR_IN or 0)
*/
static void inc_ep_stats_bytes(struct pxa_ep *ep, int count, int is_in)
@@ -2162,7 +2160,7 @@ static struct pxa_udc memory = {
.ep0 = &memory.udc_usb_ep[0].usb_ep,
.name = driver_name,
.dev = {
.bus_id = "gadget",
.init_name = "gadget",
},
},

View File

@@ -36,6 +36,7 @@
#include <linux/interrupt.h>
#include <linux/platform_device.h>
#include <linux/clk.h>
#include <linux/gpio.h>
#include <linux/debugfs.h>
#include <linux/seq_file.h>
@@ -51,7 +52,6 @@
#include <mach/irqs.h>
#include <mach/hardware.h>
#include <mach/regs-gpio.h>
#include <plat/regs-udc.h>
#include <plat/udc.h>
@@ -1510,11 +1510,7 @@ static irqreturn_t s3c2410_udc_vbus_irq(int irq, void *_dev)
dprintk(DEBUG_NORMAL, "%s()\n", __func__);
/* some cpus cannot read from an line configured to IRQ! */
s3c2410_gpio_cfgpin(udc_info->vbus_pin, S3C2410_GPIO_INPUT);
value = s3c2410_gpio_getpin(udc_info->vbus_pin);
s3c2410_gpio_cfgpin(udc_info->vbus_pin, S3C2410_GPIO_SFN2);
value = gpio_get_value(udc_info->vbus_pin) ? 1 : 0;
if (udc_info->vbus_pin_inverted)
value = !value;
@@ -1727,7 +1723,7 @@ static struct s3c2410_udc memory = {
.ep0 = &memory.ep[0].ep,
.name = gadget_name,
.dev = {
.bus_id = "gadget",
.init_name = "gadget",
},
},
@@ -1802,7 +1798,7 @@ static int s3c2410_udc_probe(struct platform_device *pdev)
struct s3c2410_udc *udc = &memory;
struct device *dev = &pdev->dev;
int retval;
unsigned int irq;
int irq;
dev_dbg(dev, "%s()\n", __func__);
@@ -1861,7 +1857,7 @@ static int s3c2410_udc_probe(struct platform_device *pdev)
/* irq setup after old hardware state is cleaned up */
retval = request_irq(IRQ_USBD, s3c2410_udc_irq,
IRQF_DISABLED, gadget_name, udc);
IRQF_DISABLED, gadget_name, udc);
if (retval != 0) {
dev_err(dev, "cannot get irq %i, err %d\n", IRQ_USBD, retval);
@@ -1872,17 +1868,28 @@ static int s3c2410_udc_probe(struct platform_device *pdev)
dev_dbg(dev, "got irq %i\n", IRQ_USBD);
if (udc_info && udc_info->vbus_pin > 0) {
irq = s3c2410_gpio_getirq(udc_info->vbus_pin);
retval = gpio_request(udc_info->vbus_pin, "udc vbus");
if (retval < 0) {
dev_err(dev, "cannot claim vbus pin\n");
goto err_int;
}
irq = gpio_to_irq(udc_info->vbus_pin);
if (irq < 0) {
dev_err(dev, "no irq for gpio vbus pin\n");
goto err_gpio_claim;
}
retval = request_irq(irq, s3c2410_udc_vbus_irq,
IRQF_DISABLED | IRQF_TRIGGER_RISING
| IRQF_TRIGGER_FALLING | IRQF_SHARED,
gadget_name, udc);
if (retval != 0) {
dev_err(dev, "can't get vbus irq %i, err %d\n",
dev_err(dev, "can't get vbus irq %d, err %d\n",
irq, retval);
retval = -EBUSY;
goto err_int;
goto err_gpio_claim;
}
dev_dbg(dev, "got irq %i\n", irq);
@@ -1902,6 +1909,9 @@ static int s3c2410_udc_probe(struct platform_device *pdev)
return 0;
err_gpio_claim:
if (udc_info && udc_info->vbus_pin > 0)
gpio_free(udc_info->vbus_pin);
err_int:
free_irq(IRQ_USBD, udc);
err_map:
@@ -1927,7 +1937,7 @@ static int s3c2410_udc_remove(struct platform_device *pdev)
debugfs_remove(udc->regs_info);
if (udc_info && udc_info->vbus_pin > 0) {
irq = s3c2410_gpio_getirq(udc_info->vbus_pin);
irq = gpio_to_irq(udc_info->vbus_pin);
free_irq(irq, udc);
}