⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 pdd.c

📁 Microsoft WinCE 6.0 BSP FINAL release source code for use with the i.MX27ADS TO2 WCE600_FINAL_MX27_S
💻 C
📖 第 1 页 / 共 5 页
字号:
    }

    // Come here if the Data is not over in the first page itself, or did not go in to the above condition

    BPCount = 1;  // First page has been taken care of , so start from second page

    while (len > 0)
    {
        // Flow through the user buffer till the end and then check for the alignment of the length
        if ( len > MAX_SIZE_PER_BP )
        {
            len -= MAX_SIZE_PER_BP;
            BPCount++;
        }
        else
        {
            if ((len % 32) != 0)
            {
                memcpy((pPdd->ep[EpNum]->pMappedBufPtr + ((BPCount * MAX_SIZE_PER_BP) - dwOffset)), 
                        Buffer_Td2, len );
            }
            len = 0;
        }
    }

    DEBUGMSG(1,(_T("-CopyFromUncachedBuffer\r\n")));
}

//------------------------------------------------------------------------------
//
//  Function:  DumpInterruptSource
//
//  This function dump the value on the interrupt register USBSTS
//
//  
//  Parameters:
//
//      source - pointer to USBSTS
//
//  Return:
//      
//      NULL
//
//-------------------------------------------------------------------------------
void DumpInterruptSource(USB_USBSTS_T * source)
{
    if (source->UI)
        RETAILMSG(1, (L"\tUSB Interrupt (USBINT)\r\n"));
    if (source->UEI)
        RETAILMSG(1, (L"\tUSB Error Interrupt (USBERRINT)\r\n"));
    if (source->PCI)
        RETAILMSG(1, (L"\tPort Change Detect\r\n"));
    if (source->FRI)
        RETAILMSG(1, (L"\tFrame List Rollover\r\n"));
    if (source->SEI)
        RETAILMSG(1, (L"\tSystem Error\r\n"));
    if (source->AAI)
        RETAILMSG(1, (L"\tInterrupt on Async Advance\r\n"));
    if (source->URI)
        RETAILMSG(1, (L"\tUSB Reset Received \r\n"));
    if (source->SRI)
        RETAILMSG(1, (L"\tSOF Received \r\n"));
    if (source->SLI)
        RETAILMSG(1, (L"\tDCSuspend \r\n"));
    if (source->ULPII)
        RETAILMSG(1, (L"\tULPI Interrupt\r\n"));
    if (source->HCH)
        RETAILMSG(1, (L"\tHCHaIted \r\n"));
    if (source->RCL)
        RETAILMSG(1, (L"\tReclamation,Only used by the host controller. \r\n"));
    if (source->PS)
        RETAILMSG(1, (L"\tPeriodic Schedule Status. \r\n"));
    if (source->AS)
        RETAILMSG(1, (L"\tAsynchronous Schedule Status. \r\n"));
}

//------------------------------------------------------------------------------
//
//  Function:  CheckEndpoint
//
//  This function handles the interrupt due to  endpoint complete 
//
//  
//  Parameters:
//
//      pPdd - Pointer to USBFN_PDD structure
//
//      i - endpoint to be examined
//
//  Return:
//      
//      NULL
//
//-------------------------------------------------------------------------------
static void CheckEndpoint(USBFN_PDD *pPdd, int i )
{
    CSP_USB_REGS* pUSBDRegs = pPdd->pUSBDRegs;
    STransfer * pTransfer;
    USB_ENDPTCOMPLETE_T edptcomp;
    DWORD *pEpc;

    pEpc = (DWORD*)&edptcomp;
    
    LOCK();
    // OUT endpoint
    *pEpc = INREG32(&pUSBDRegs->OTG.ENDPTCOMPLETE);

    if (edptcomp.ERCE&(1<<i))
    {
        pTransfer=pPdd->ep[i]->pTransfer;
        if (i)
        {
            PUSBD_dTD_R_T pTd;    
            PUSBD_dQH_T pQh;    
            
            pQh=&(pPdd->qhbuffer->qh[i*2]);
            pTd=TDVirtual(pQh->curr_dTD);
            if (pPdd->qhbuffer->qh[i*2].dtd.status)
                RETAILMSG(1,(L"Status is not 0 on recv %x =%x",i,pPdd->qhbuffer->qh[i*2].dtd.status));
            
            if (pTransfer&&pPdd->qhbuffer->qh[i*2].dtd.status!=0x80)
            {
                // calculate how much we were trying to tranfer in this TD
                DWORD len=pTransfer->cbBuffer-pTransfer->cbTransferred;
                
                if (len>MAX_SIZE_PER_TD)
                    len=MAX_SIZE_PER_TD;
                
                len-=pPdd->qhbuffer->qh[i*2].dtd.tb;  // reduce by any bytes outstanding
                
                // len is how much was actually transferred
                
                
                pTransfer->cbTransferred+=len;
                
                DEBUGMSG(0, (TEXT("ENDPTCOMPLETE %x\r\n"),(1<<i)));
                OUTREG32(&(pUSBDRegs->OTG.ENDPTCOMPLETE), (1<<i));    
                
                if (pPdd->qhbuffer->qh[i*2].dtd.status && pPdd->qhbuffer->qh[i*2].dtd.status!=0x80)
                {
                    RETAILMSG(1,(_T("CheckEndpoint(ep=%d): BUFFER_ERROR\r\n"),i) );
                    
                    DEBUGMSG(ZONE_ERROR,(_T("CheckEndpoint(ep=%d): BUFFER_ERROR\r\n"), i) );
                    
                    pTransfer->dwUsbError=UFN_CLIENT_BUFFER_ERROR;
                }
                else if ( (len == MAX_SIZE_PER_TD) &&
                          (pTransfer->cbTransferred < pTransfer->cbBuffer) )
                {
                    
                    /* RETAILMSG(1, (_T("More data need to send (0x%x) ep(%d)\r\n"), 
                                pTransfer->cbBuffer-pTransfer->cbTransferred, i)); */

                    pTransfer->dwUsbError=UFN_MORE_DATA;  
                    
                    UNLOCK();
                    UfnPdd_IssueTransfer(pPdd, i,pTransfer);
                    LOCK();
                }
                else
                {
                        pTransfer->dwUsbError=UFN_NO_ERROR;
                }
                
                pPdd->qhbuffer->bPrimed[i] = FALSE;
                                
                if (pTransfer->dwUsbError != UFN_MORE_DATA )
                {
                    CacheSync(CACHE_SYNC_DISCARD);
                    
                    //CacheRangeFlush(pTransfer->pvBuffer, pTransfer->cbBuffer, CACHE_SYNC_DISCARD);
                    // For copying from Uncached memory to user buffers
                    if ( pTransfer->cbBuffer > 0 )
                    {
                        CopyFromUncachedBuffer(pPdd,i,pTransfer->cbBuffer);
                    }
                    
                    
                    if ( pPdd->ep[i]->bPagesLocked )
                    {
                        DEBUGCHK( pPdd->ep[i]->pMappedBufPtr != NULL );
                        UnlockPages(pPdd->ep[i]->pMappedBufPtr, pTransfer->cbBuffer);
                        if (pPdd->ep[i]->pMappedBufPtr)
                        {
                            if(FAILED(CeCloseCallerBuffer(pPdd->ep[i]->pMappedBufPtr,
                                                                    (LPVOID)pTransfer->pvBuffer,
                                                                    pTransfer->cbBuffer,
                                                                    ARG_IO_PTR)))
                                    RETAILMSG(1, (TEXT("Failed to CloseCallerBuffer\r\n")));                
                            pPdd->ep[i]->pMappedBufPtr = NULL;
                        }

                        pPdd->ep[i]->bPagesLocked = 0;
                    }
                    
                    pPdd->ep[i]->pTransfer=NULL;

                    UNLOCK();
                    pPdd->pfnNotify(pPdd->pMddContext, UFN_MSG_TRANSFER_COMPLETE, (DWORD)pTransfer);

                    
                    DEBUGMSG(0, (TEXT("OUT %s Completed for endpoint %d\r\n"), 
                                pTransfer->dwUsbError == UFN_NO_ERROR ? TEXT("Normal") : TEXT("Cancel"),
                                i));  
                    LOCK();
                }
            }
            else //(pTransfer&&pPdd->qhbuffer->qh[i*2].dtd.status!=0x80)
            {
                RETAILMSG(1, (TEXT("############# ENDPTCOMPLETE %x NULL pTransfer or bad status (0x%x)!\r\n"),
                            (1<<i), 
                            pPdd->qhbuffer->qh[i*2].dtd.status
                            ));
                OUTREG32(&(pUSBDRegs->OTG.ENDPTCOMPLETE), (1<<i));  
            }
            
        }
    else // Endpoint 0 OUT Transaction if (i)
    {
            DWORD len;
            
            // OUT transcation of endpoint 0
            //   pTransfer=pPdd->ep[USBD_EP_COUNT-1]->pTransfer;
            
            pTransfer=pPdd->ep[0]->pTransfer;
            if (pTransfer)
            {
                len=pTransfer->cbBuffer-pPdd->qhbuffer->td[0].tb;
                if (len)
                {
                    pTransfer->cbTransferred+=len;
                    
                    pPdd->qhbuffer->bPrimed[0] = FALSE;
                    if (pTransfer->cbTransferred < pTransfer->cbBuffer)
                    {
                         RETAILMSG(1,(L"##### more data to receive on EP0 (status=0x%x)",
                         pPdd->qhbuffer->td[0].status));
                         
                        
                        OUTREG32(&(pUSBDRegs->OTG.ENDPTCOMPLETE), 1);    

                        UNLOCK();
                        UfnPdd_IssueTransfer(pPdd, 0,pTransfer);
                        LOCK();
                        
                        // EP0 is treated just like any other EP at this point (no setup phase ready)
                    }
                    else
                    {
                            pTransfer->dwUsbError=UFN_NO_ERROR;
                        
                        OUTREG32(&(pUSBDRegs->OTG.ENDPTCOMPLETE), 1);    
                        
                        // For copying from Uncached memory buffers to user buffers
                        if ( pTransfer->cbBuffer > 0 )
                        {
                            CopyFromUncachedBuffer(pPdd,0,pTransfer->cbBuffer);
                        }
                        CacheSync(CACHE_SYNC_DISCARD);
                        
                        if ( pPdd->ep[0]->bPagesLocked && pTransfer->pvBuffer )
                        {
                            DEBUGCHK( pPdd->ep[0]->pMappedBufPtr != NULL );
                            UnlockPages(pPdd->ep[0]->pMappedBufPtr, pTransfer->cbBuffer);
                            if (pPdd->ep[0]->pMappedBufPtr)
                            {
                                if(FAILED(CeCloseCallerBuffer(pPdd->ep[0]->pMappedBufPtr,
                                                                        (LPVOID)pTransfer->pvBuffer,
                                                                        pTransfer->cbBuffer,
                                                                        ARG_IO_PTR)))

                                    RETAILMSG(1, (TEXT("Failed to CloseCallerBuffer\r\n")));                
                            }
                            pPdd->ep[0]->pMappedBufPtr = NULL;
                            pPdd->ep[0]->bPagesLocked = 0;
                        }
                        
                        pPdd->ep[0]->pTransfer=NULL;
                        
                         DEBUGMSG(1, (TEXT("CheckEndpoint:EP0 OUT %d bytes notify (%s)\r\n"), 
                                    pTransfer->cbTransferred,
                                    (pTransfer->dwUsbError == UFN_NO_ERROR) ? TEXT("Normal") : TEXT("Cancel")
                                    ) ); 
                        
                        UNLOCK();
                        pPdd->pfnNotify(pPdd->pMddContext, UFN_MSG_TRANSFER_COMPLETE, (DWORD)pTransfer);
                        LOCK();
                    }
                }
                else
                {
                    OUTREG32(&(pUSBDRegs->OTG.ENDPTCOMPLETE), 1);    
                }
                
                DEBUGMSG(1, (_T("CheckEndpoint:EP0 OUT %d bytes completed\r\n"), pTransfer->cbTransferred) );
            }
            else // if (pTransfer)
            {
                OUTREG32(&(pUSBDRegs->OTG.ENDPTCOMPLETE), 1);    
                 DEBUGMSG(1, (_T("CheckEndpoint:EP0 OUT NULL transfer complete\r\n")) );
            }
            
        } // if (pTransfer&&pPdd->qhbuffer->qh[i*2].dtd.status!=0x80)
    } //  if (edptcomp.ERCE&(1<<i))  
    
    
    // IN packet transcation
    if (edptcomp.ETCE&(1<<i))
    {
        DWORD mapped_epNum = i;
        
        if (i == 0) 
        {
        /*
        * If this is the completion of a SetAddress (the status handshake part is an "IN") then
        * we should set the address now.  We only set the address after the command.
        * Address is & 0x80 as a flag to tell us to set the address.
            */
            if (pPdd->addr & 0x80)
            {
                DWORD addr;
                pPdd->addr&=0x7f;
                addr=pPdd->addr;
                addr<<=25;    
                
                OUTREG32(&pPdd->pUSBDRegs->OTG.T_154H.USBADR, addr);
                
                DEBUGMSG(1, (L"CheckEndpoint:Set Address: %x(%x), USBADR(%x)=%x \r\n", 
                addr, pPdd->addr, offset(CSP_USB_REG, T_154H.USBADR) , 
                INREG32(&pPdd->pUSBDRegs->OTG.T_154H.USBADR))); 
            }
            
            mapped_epNum = USBD_EP_COUNT-1;
        }
        
        pTransfer=pPdd->ep[mapped_epNum]->pTransfer;
        
        if (pPdd->qhbuffer->qh[i*2+1].dtd.status)
            RETAILMSG(1,(L"Status is not 0 on sent %x =%x\r\n",i,pPdd->qhbuffer->qh[i*2+1].dtd.status));
        
        if (pTransfer && pPdd->qhbuffer->qh[i*2+1].dtd.status!=0x80)
        {
            // calculate how much we were trying to transfer
            int len=pTransfer->cbBuffer-pTransfer->cbTransferred;
            if (len>MAX_SIZE_PER_TD)
                len=MAX_SIZE_PER_TD;
            
            len -= pPdd->qhbuffer->qh[i*2+1].dtd.tb; // reduce by what's still to go in the TD
            
            pTransfer->cbTransferred += len;  
            
            pPdd->qhbuffer->bPrimed[mapped_epNum] = FALSE;
            if (pPdd->qhbuffer->qh[i*2+1].dtd.tb)
            {
                RETAILMSG(1,(L"Send error?? len=%x, status=%x, tb=%x\r\n",
                    pTransfer->cbBuffer, pPdd->qhbuffer->qh[i*2+1].dtd.status, pPdd->qhbuffer->qh[i*2+1].dtd.tb));
                pTransfer->cbTransferred=pTransfer->cbBuffer;
            }
            
            if (pTransfer->cbTransferred<pTransfer->cbBuffer)
            {
                pTransfer->dwUsbError=UFN_MORE_DATA;  
                OUTREG32(&(pUSBDRegs->OTG.ENDPTCOMPLETE), (0x10000UL<<i));   

                UNLOCK();
                UfnPdd_IssueTransfer(pPdd, i, pTransfer); 
                LOCK();
            }
            else
            {
                    pTransfer->dwUsbError=UFN_NO_ERROR;
                
                OUTREG32(&(pUSBDRegs->OTG.ENDPTCOMPLETE), (0x10000UL<<i));    
                
                if ( pPdd->ep[mapped_epNum]->bPagesLocked )
                {
                    DEBUGCHK( pPdd->ep[mapped_epNum]->pMappedBufPtr != NULL );
                    UnlockPages(pPdd->ep[mapped_epNum]->pMappedBufPtr, pTransfer->cbBuffer);
                    if (pPdd->ep[mapped_epNum]->pMappedBufPtr)
                    {
                        if(FAILED(CeCloseCallerBuffer(pPdd->ep[mapped_epNum]->pMappedBufPtr,
                                                                (LPVOID)pTransfer->pvBuffer,
                                                                pTransfer->cbBuffer,
                                                                ARG_IO_PTR)))

                            RETAILMSG(1, (TEXT("Failed to CloseCallerBuffer\r\n")));                
                    }
                    pPdd->ep[mapped_epNum]->pMappedBufPtr = NULL;
                    pPdd->ep[mapped_epNum]->bPagesLocked = 0;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -