📄 usb_ep1_pxa.c
字号:
/* * Generic xmit layer for the PXA USB client function * * This code was loosely inspired by the original version which was * Copyright (c) Compaq Computer Corporation, 1998-1999 * Copyright (c) 2001 by Nicolas Pitre * * 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. * * 02-May-2002 * Frank Becker (Intrinsyc) - derived from sa1100 usb_send.c * * TODO: Add support for DMA. * */#ifdef HAVE_CONFIG_H# include <blob/config.h>#endif#include <blob/arch.h>#include <linux/errno.h>#include "pxa_usb.h"#include "usb_ctl_pxa.h"#if DEBUGstatic unsigned int usb_debug = DEBUG;#else#define usb_debug 0 /* gcc will remove all the debug code for us */#endifstatic char *ep1_buf;static int ep1_len;static int ep1_remain;static usb_callback_t ep1_callback;static int tx_pktsize;/* device state is changing, async */voidep1_state_change_notify( int new_state ){}/* set feature stall executing, async */voidep1_stall( void ){ UDCCS1 |= UDCCS_BI_FST;}static voidep1_send_packet(void){ int i; char *buf = ep1_buf + ep1_len - ep1_remain; int out_size = tx_pktsize; //if( usb_debug) printk( "ep1_send_packet: UICR0=%x UDCCS1=%x\n", UICR0, UDCCS1); if( out_size > ep1_remain) { out_size = ep1_remain; } for( i=0; i<out_size; i++) { UDDR1 = *buf++; } UDCCS1 = UDCCS_BI_TPC; if( out_size < tx_pktsize) { /* short packet */ UDCCS1 = UDCCS_BI_TSP; } ep1_remain -= out_size; /* if( usb_debug) printk( "ep1_send_packet: " "UICR0=%x UDCCS1=%x send bytes=%d left=%d\n", UICR0, UDCCS1, out_size, ep1_remain); */}static voidep1_start(void){ if (!ep1_len) return; UICR0 &= ~UICR0_IM1; ep1_send_packet();}static voidep1_done(int flag){ int size = ep1_len - ep1_remain; if (ep1_len) { ep1_len = 0; if (ep1_callback) ep1_callback(flag, size); }}intep1_init(int chn){ /* int i; desc_t * pdesc = pxa_usb_get_descriptor_ptr(); for ( i = 0; i < pdesc->ep_num; i++ ) { if( BULK_IN1 == ( 0xF & pdesc->ep[i].bEndpointAddress) ) { tx_pktsize = __le16_to_cpu( pdesc->ep[i].wMaxPacketSize ); } } */ /* FIXME */ tx_pktsize = 64; ep1_done(-EAGAIN); return 0;}voidep1_reset(void){ /* int i; desc_t * pdesc = pxa_usb_get_descriptor_ptr(); for ( i = 0; i < pdesc->ep_num; i++ ) { if( BULK_IN1 == ( 0xF & pdesc->ep[i].bEndpointAddress) ) { tx_pktsize = __le16_to_cpu( pdesc->ep[i].wMaxPacketSize ); } } */ /* FIXME */ tx_pktsize = 64; UDCCS1 &= ~UDCCS_BI_FST; ep1_done(-EINTR);}voidep1_int_hndlr(int usir0){ int status = UDCCS1; if (ep1_remain != 0) { /* more data to go */ ep1_start(); } else { if( status & UDCCS_BI_TPC) { UDCCS1 = UDCCS_BI_TPC; } ep1_done(0); }}intep1_send(char *buf, int len, usb_callback_t callback){ int i=0; int flags; /* if( usb_debug) printk( "pxa_usb_send: " "data len=%d state=%d blen=%d\n", len, usbd_info.state, ep1_len); */ if (usbd_info.state != USB_STATE_CONFIGURED) return -ENODEV; if (ep1_len) { SerialOutputString("busy...\n"); return -EBUSY; } /* for ( i=0; i < len; i++) { SerialOutputHex(buf[i]); SerialOutputString(" "); } SerialOutputString("\n"); */ //local_irq_save(flags); ep1_buf = buf; ep1_len = len; ep1_callback = callback; ep1_remain = len; ep1_start(); //local_irq_restore(flags); return 0;}int ep1_xmitter_avail( void ){ if (usbd_info.state != USB_STATE_CONFIGURED) return -ENODEV; if (ep1_len) return -EBUSY; return 0;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -