UDC_EP_NUM_REG = udc->ep0_in ? 0 : UDC_EP_DIR; 
UDC_EP_NUM_REG = UDC_EP_DIR; 
omap_ep_queue(struct usb_ep *_ep, struct usb_request *_req, int gfp_flags){	struct omap_ep	*ep = container_of(_ep, struct omap_ep, ep);	struct omap_req	*req = container_of(_req, struct omap_req, req);	struct omap_udc	*udc;	unsigned long	flags;	int		is_iso = 0;	/* catch various bogus parameters */	if (!_req || !req->req.complete || !req->req.buf			|| !list_empty(&req->queue)) {		DBG("%s, bad params\n", __FUNCTION__);		return -EINVAL;	}	if (!_ep || (!ep->desc && ep->bEndpointAddress)) {		DBG("%s, bad ep\n", __FUNCTION__);		return -EINVAL;	}	if (ep->bmAttributes == USB_ENDPOINT_XFER_ISOC) {		if (req->req.length > ep->ep.maxpacket)			return -EMSGSIZE;		is_iso = 1;	}	/* this isn't bogus, but OMAP DMA isn't the only hardware to	 * have a hard time with partial packet reads...  reject it.	 */	if (use_dma			&& ep->has_dma			&& ep->bEndpointAddress != 0			&& (ep->bEndpointAddress & USB_DIR_IN) == 0			&& (req->req.length % ep->ep.maxpacket) != 0) {		DBG("%s, no partial packet OUT reads\n", __FUNCTION__);		return -EMSGSIZE;	}	udc = ep->udc;	if (!udc->driver || udc->gadget.speed == USB_SPEED_UNKNOWN)		return -ESHUTDOWN;	if (use_dma && ep->has_dma) {		if (req->req.dma == DMA_ADDR_INVALID) {			req->req.dma = dma_map_single(				ep->udc->gadget.dev.parent,				req->req.buf,				req->req.length,				(ep->bEndpointAddress & USB_DIR_IN)					? DMA_TO_DEVICE					: DMA_FROM_DEVICE);			req->mapped = 1;		} else {			dma_sync_single_for_device(				ep->udc->gadget.dev.parent,				req->req.dma, req->req.length,				(ep->bEndpointAddress & USB_DIR_IN)					? DMA_TO_DEVICE					: DMA_FROM_DEVICE);			req->mapped = 0;		}	}	VDBG("%s queue req %p, len %d buf %p\n",		ep->ep.name, _req, _req->length, _req->buf);	spin_lock_irqsave(&udc->lock, flags);	req->req.status = -EINPROGRESS;	req->req.actual = 0;	/* maybe kickstart non-iso i/o queues */	if (is_iso)		UDC_IRQ_EN_REG |= UDC_SOF_IE;	else if (list_empty(&ep->queue) && !ep->stopped && !ep->ackwait) {		int	is_in;		if (ep->bEndpointAddress == 0) {			if (!udc->ep0_pending || !list_empty (&ep->queue)) {				spin_unlock_irqrestore(&udc->lock, flags);				return -EL2HLT;			}			/* empty DATA stage? */			is_in = udc->ep0_in;			if (!req->req.length) {				/* chip became CONFIGURED or ADDRESSED				 * earlier; drivers may already have queued				 * requests to non-control endpoints				 */				if (udc->ep0_set_config) {					u16	irq_en = UDC_IRQ_EN_REG;					irq_en |= UDC_DS_CHG_IE | UDC_EP0_IE;					if (!udc->ep0_reset_config)						irq_en |= UDC_EPN_RX_IE							| UDC_EPN_TX_IE;					UDC_IRQ_EN_REG = irq_en;				}				/* STATUS is reverse direction */				UDC_EP_NUM_REG = is_in						? UDC_EP_SEL						: (UDC_EP_SEL|UDC_EP_DIR);				UDC_CTRL_REG = UDC_CLR_EP;				UDC_CTRL_REG = UDC_SET_FIFO_EN;				UDC_EP_NUM_REG = udc->ep0_in ? 0 : UDC_EP_DIR;				/* cleanup */				udc->ep0_pending = 0;				done(ep, req, 0);				req = 0;			/* non-empty DATA stage */			} else if (is_in) {				UDC_EP_NUM_REG = UDC_EP_SEL|UDC_EP_DIR;			} else {				if (udc->ep0_setup)					goto irq_wait;				UDC_EP_NUM_REG = UDC_EP_SEL;			}		} else {			is_in = ep->bEndpointAddress & USB_DIR_IN;			if (!ep->has_dma)				use_ep(ep, UDC_EP_SEL);			/* if ISO: SOF IRQs must be enabled/disabled! */		}		if (ep->has_dma)			(is_in ? next_in_dma : next_out_dma)(ep, req);		else if (req) {			if ((is_in ? write_fifo : read_fifo)(ep, req) == 1)				req = 0;			deselect_ep();			if (!is_in) {				UDC_CTRL_REG = UDC_SET_FIFO_EN;				ep->ackwait = 1 + ep->double_buf;			}			/* IN: 6 wait states before it'll tx */		}	}irq_wait:	/* irq handler advances the queue */	if (req != 0)		list_add_tail(&req->queue, &ep->queue);	spin_unlock_irqrestore(&udc->lock, flags);	return 0;}
10457	/local/tlutelli/issta_data/temp/c/2005_temp/2005/10457/313980c92724cf42877a7bdafdef439ee9d68ccb/omap_udc.c/clean/drivers/usb/gadget/omap_udc.c