www.pudn.com > S3C2410_USB_Device.rar > usbout.c


/**************************************************************** 
 NAME: usbout.c 
 DESC: USB bulk-OUT operation related functions 
 HISTORY: 
 Mar.25.2002:purnnamu: ported for S3C2410X. 
 Mar.27.2002:purnnamu: DMA is enabled. 
 ****************************************************************/ 
#include "def.h" 
#include "config.h" 
#include "board.h" 
#include "2410addr.h" 
 
#include "2410usb.h" 
#include "usblib.h" 
#include "usbsetup.h" 
#include "usbout.h" 
#include "usbin.h" 
 
#ifdef	USB_DOWNLOAD_SUPPORT 
 
extern volatile U32 download_addr; 
extern volatile U8 *downPt; 
extern volatile U32 download_len; 
extern volatile U32 totalDmaCount; 
extern volatile U16 checkSum; 
 
static void RdPktEp3_CheckSum(U8 *buf,int num); 
 
// =================================================================== 
// All following commands will operate in case  
// - out_csr3 is valid. 
// =================================================================== 
 
#define CLR_EP3_OUT_PKT_READY() rOUT_CSR1_REG= ( out_csr3 &(~ EPO_WR_BITS)\ 
					&(~EPO_OUT_PKT_READY) )  
#define SET_EP3_SEND_STALL()	rOUT_CSR1_REG= ( out_csr3 & (~EPO_WR_BITS)\ 
					| EPO_SEND_STALL) ) 
#define CLR_EP3_SENT_STALL()	rOUT_CSR1_REG= ( out_csr3 & (~EPO_WR_BITS)\ 
					&(~EPO_SENT_STALL) ) 
#define FLUSH_EP3_FIFO() 	rOUT_CSR1_REG= ( out_csr3 & (~EPO_WR_BITS)\ 
					|EPO_FIFO_FLUSH) ) 
 
// *************************** 
// *** VERY IMPORTANT NOTE *** 
// *************************** 
// Prepare for the packit size constraint!!! 
 
// EP3 = OUT end point.  
 
extern U32 UsbFunction; 
extern U32 UsbState; 
extern U32 UsbInLength; 
extern U8 *UsbTxAddr; 
 
U8 ep3Buf[EP3_PKT_SIZE]; 
 
void Ep3Handler(void) 
{ 
    U8 out_csr3; 
    int fifoCnt;  
 
/*	static int led = 0xf; 
	led ^= 1; 
	Led_Display(led); 
*/	     
    rINDEX_REG = 3; 
    out_csr3 = rOUT_CSR1_REG; 
     
//	DbgOut("<3:%x]",out_csr3);		 
 
    if(out_csr3 & EPO_OUT_PKT_READY) 
    {    
		fifoCnt = rOUT_FIFO_CNT1_REG; 
		 
		if(UsbFunction) 
		{				 
			RdPktEp3(ep3Buf, fifoCnt);						 
			CLR_EP3_OUT_PKT_READY(); 
			if(*(U32 *)ep3Buf==0x01234567) 
			{ 
				UsbState    = 0x01234567; 
				UsbTxAddr   = (U8 *)0x31000000; 
				UsbInLength = *(U32 *)(ep3Buf+4); 
				PrepareEp1Fifo(); 
				putch('@'); 
			}									 
			return; 
		} 
 
		if(download_len==0) 
		{ 
			RdPktEp3((U8 *)downPt, 8); 
			 
			download_addr = *(U32 *)downPt; 
			download_len  = *(U32 *)(downPt+4); 
//			checkSum=0; 
			downPt=(U8 *)download_addr; 
			 
			RdPktEp3_CheckSum((U8 *)downPt, fifoCnt-8); //The first 8-bytes are deleted.	     
  	    	downPt+=fifoCnt-8;   
  	     
	  	#if USBDMA 
    	 	    //CLR_EP3_OUT_PKT_READY() is not executed.  
				//So, USBD may generate NAK until DMA2 is configured for USB_EP3; 
     	    DisableIrq(BIT_USBD);	 
      	    return;	 
	  	#endif	 
		} 
		else 
		{ 
		#if USBDMA    	 
			DbgOut(""); 
		#endif     
		    RdPktEp3_CheckSum((U8 *)downPt,fifoCnt); 
	    	downPt+=fifoCnt;  //fifoCnt=64 
		} 
	   	CLR_EP3_OUT_PKT_READY(); 
		return; 
    } 
    
    //I think that EPO_SENT_STALL will not be set to 1. 
    if(out_csr3 & EPO_SENT_STALL) 
    {    
		DbgOut("[STALL]"); 
	   	CLR_EP3_SENT_STALL(); 
   		return; 
    }	 
} 
 
void RdPktEp3_CheckSum(U8 *buf,int num) 
{ 
    int i; 
    	 
    for(i=0;i=download_len)// is last? 
    { 
    	totalDmaCount = download_len; 
			 
    	ConfigEp3IntMode(); 
			 
    	if(out_csr3& EPO_OUT_PKT_READY) 
    	{ 
   	    	CLR_EP3_OUT_PKT_READY(); 
		} 
        DisableIrq(BIT_DMA2);// 
//        	putch('*'); 
        EnableIrq(BIT_USBD);//rINTMSK&=~(BIT_USBD); 
//			putch('*');        	         
//        DbgOut("@"); 
    } 
    else 
    { 
	    ReConfigEp3Dma(download_addr+totalDmaCount-8, ((download_len-totalDmaCount)>0x80000)?0x80000:(download_len-totalDmaCount)); 
    	while(rEP3_DMA_TTC<0xfffff) 
   	    { 
   	        rEP3_DMA_TTC_L = 0xff; 
   	        rEP3_DMA_TTC_M = 0xff; 
   	        rEP3_DMA_TTC_H = 0xf;	    //0xfffff; 
   	    } 
    	 
    } 
    rINDEX_REG = saveIndexReg; 
} 
 
 
void ClearEp3OutPktReady(void) 
{ 
    U8 out_csr3; 
    rINDEX_REG=3; 
    out_csr3=rOUT_CSR1_REG; 
    CLR_EP3_OUT_PKT_READY(); 
} 
 
#endif