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

📄 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 页
字号:
        RETAILMSG(1,(L"PRIME failed on EP0\r\n") );

        if ( INREG32(&pOtgReg->ENDPTSETUPSTAT) & 1 )
            {
            GetSetupPacket(pPdd, data);

            RETAILMSG(1,(L"New setup received when priming=%x, %x\r\n", data[0], data[1]));

            DEBUGCHK ( pPdd->ep[0]->bPagesLocked == 0 );

            pPdd->pfnNotify(pPdd->pMddContext, UFN_MSG_SETUP_PACKET, (DWORD)data);

            RETAILMSG(1,(L"Status for td0=%x, tb=%x\r\n", 
                pPdd->qhbuffer->qh[0].dtd.status,pPdd->qhbuffer->qh[0].dtd.tb));
            }
        retry = 1;
        goto again;
    }

    pPdd->qhbuffer->bPrimed[0] = TRUE;

    UNLOCK();
}

//-------------------------------------------------------------
// 
//  Function: PrimeQh0ForZeroTransfer
//
//  This is to prime the end point 0 and is used during the handshake status
//
//  Parameters: 
//      pPdd - Pointer to the USBFN_PDD
//      bIN  - TRUE : IN transfer
//             FALSE: OUT transfer
//
//  Return: NULL
//
//------------------------------------------------------------------
static void 
PrimeQh0ForZeroTransfer(USBFN_PDD *pPdd, BOOL bIN )
{
    volatile CSP_USB_REG * pOtgReg=&(pPdd->pUSBDRegs->OTG);
    int endp;
    USB_ENDPTSTAT_T stat;
    DWORD *pStat = (DWORD*)&stat;
    USB_ENDPTPRIME_T edptprime;
    DWORD *pPrime=(DWORD * )&edptprime;

    *pPrime = 0;

    if ( bIN )
    {
        edptprime.PETB = 1;
        endp = 1;
    }
    else
    {
        edptprime.PERB = 1;
        endp = 0;
    }

    CeLogMsg(_T("PrimeFZLT: %s"), bIN ? _T("IN") : _T("OUT"));

    *pStat = INREG32(&pOtgReg->ENDPTSTATUS);
    if ( (bIN && (stat.ETBR & 1)) || (!bIN && (stat.ERBR & 1)) )
    {
        RETAILMSG(1, (_T("Can not prime for ZLT (%s): busy\r\n"),
                bIN ? _T("IN") : _T("OUT")) );
        return;
    }

    memset(&(pPdd->qhbuffer->qh[endp]),0, sizeof(USBD_dQH_T)-2*sizeof(DWORD));
    pPdd->qhbuffer->bPrimed[endp] = FALSE;

    // Endpoint 0 
    pPdd->qhbuffer->qh[endp].ios= (endp == 0 ? 1 : 0);
    pPdd->qhbuffer->qh[endp].mpl=USB_FULL_HIGH_SPEED_CONTROL_MAX_PACKET_SIZE;    
    pPdd->qhbuffer->qh[endp].zlt=1;
    //overlayer  default
    {
        DWORD t;
        t=DescriptorPhy(pPdd, (DWORD)&(pPdd->qhbuffer->td[endp]));
        t>>=5;
        pPdd->qhbuffer->qh[endp].dtd.next_dtd=t;
        pPdd->qhbuffer->qh[endp].dtd.T=0;
    }

    // OUTREG32(&pOtgReg->ENDPTSETUPSTAT, 0xffff);

    memset (&(pPdd->qhbuffer->td[endp]), 0, sizeof(USBD_dTD_T));
    pPdd->qhbuffer->td[endp].T=1;
    pPdd->qhbuffer->td[endp].next_dtd=0xDEAD;
    pPdd->qhbuffer->td[endp].status=0x80;            // Active
    pPdd->qhbuffer->td[endp].ioc=1;
    pPdd->qhbuffer->td[endp].tb=0; 
    //  leave all bp null for a null transfer

    OUTREG32(&pOtgReg->ENDPTPRIME, *pPrime);  // prime Out transition
    while(INREG32(&pOtgReg->ENDPTPRIME) & *pPrime)
    {
        ;
    }

    *pStat = INREG32(&pOtgReg->ENDPTSTATUS);
    if ( (bIN && ((stat.ETBR & 1) == 0)) || (!bIN && ((stat.ERBR & 1) == 0)) )
    {
        USB_ENDPTCOMPLETE_T edptcomp;
        DWORD *pEpc;

        pEpc = (DWORD*)&edptcomp;
        *pEpc = INREG32(&pOtgReg->ENDPTCOMPLETE);
        if ( (bIN && ((edptcomp.ETCE & 1) == 0)) || (!bIN && ((edptcomp.ERCE & 1) == 0)) )
        {
            RETAILMSG(1,(_T("################ Failed to prime for ZLT %s\r\n"), bIN ? TEXT("IN") : TEXT("OUT")));
        }
    }

    pPdd->qhbuffer->bPrimed[endp] = TRUE;
}

//-------------------------------------------------------------
// 
//  Function: HandleUSBReset
//
//  This is to handle the USB Reset interrupt
//
//  Parameters: 
//      pPdd - Pointer to USBFN_PDD
//
//  Return: NULL
//
//------------------------------------------------------------------
static void 
HandleUSBReset(USBFN_PDD *pPdd)
{
    volatile CSP_USB_REG * pOtgReg=&(pPdd->pUSBDRegs->OTG);
    USB_PORTSC_T state;
    DWORD * tPortsc;

    LOCK();

    // clear all setup notification bits 
    OUTREG32(&pOtgReg->ENDPTSETUPSTAT, INREG32(&pOtgReg->ENDPTSETUPSTAT));
            
    // clear all complete bits
    OUTREG32(&pOtgReg->ENDPTCOMPLETE, INREG32(&pOtgReg->ENDPTCOMPLETE));

    // wait for all prime (if any in progress) to complete, then flush all
    while ( INREG32(&pOtgReg->ENDPTPRIME) )
    {
        ;
    }

    OUTREG32(&pOtgReg->ENDPTFLUSH, 0xFFFFFFFF);

    // and check that we're still in RESET
    tPortsc = (DWORD*)&state;
    *tPortsc = INREG32(&pOtgReg->PORTSC[USBD_PORT_NUM]);
    if ( state.PR == 0 )
    {
        DEBUGMSG(ZONE_WARNING,(_T("HandleUSBReset: Not still in reset condition. Possibly reset controller??\r\n")));
    }

    UNLOCK();

    // no need to free TDs since they are statically allocated.
}


//----------------------------------------------------------------
//
//  Function:  UfnPdd_PowerDown
//
//  This is power down function for USB PDD function driver
//
//  Parameters: 
//      pPddContext - PDD Context
//       
//  Return:
//      NULL
//
//----------------------------------------------------------------
VOID WINAPI UfnPdd_PowerDown(VOID *pPddContext)
{
    int i = 0;
    USBFN_PDD *pPdd = (USBFN_PDD *)(pPddContext);
    RETAILMSG(1, (L"UfnPdd_PowerDown+\r\n"));
    if (pPdd->bInUSBFN)
    {
        USB_CTRL_T ctrl;
        USB_PORTSC_T portsc;
        USB_USBCMD_T usbcmd;                
        DWORD *temp3;
        DWORD *temp2;
        DWORD *temp;

        if (pPdd->bUSBCoreClk == FALSE)
        {
            // We know it is suspend already ...why bother to
            // further processing anything.
            // We use bUSBCoreClk as checking since this is the last thing to 
            // do b4 we go to suspend.
            DEBUGMSG(ZONE_POWER, (TEXT("UfnPdd_PowerDown no action required\r\n")));
            return;
        }

        // Stop USB Run/Stop CMD
        temp2 = (DWORD *)&usbcmd;
        *temp2 = INREG32(&pPdd->pUSBDRegs->OTG.USBCMD);
        usbcmd.RS = 0;
        OUTREG32(&pPdd->pUSBDRegs->OTG.USBCMD, *temp2);
        DEBUGMSG(ZONE_POWER, (TEXT("PowerDown USBCMD = 0x%x\r\n"), INREG32(&pPdd->pUSBDRegs->OTG.USBCMD)));

        // Clear USB Interrupt      
        pPdd->dwUSBIntrValue = INREG32(&pPdd->pUSBDRegs->OTG.USBINTR);
        OUTREG32(&pPdd->pUSBDRegs->OTG.USBINTR, 0x00);
        DEBUGMSG(ZONE_POWER, (TEXT("PowerDown USBINTR = 0x%x\r\n"), INREG32(&pPdd->pUSBDRegs->OTG.USBINTR)));

        // Clear USBSTS
        OUTREG32(&pPdd->pUSBDRegs->OTG.USBSTS, INREG32(&pPdd->pUSBDRegs->OTG.USBSTS));


        temp = (DWORD *)&portsc;
        *temp = INREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0]);
        portsc.WKOC = 1;
        portsc.WKDC = 1;
        portsc.WKCN = 1;
        OUTREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0], *temp);       
        DEBUGMSG(ZONE_POWER, (TEXT("PowerDown PORTSC= 0x%x\r\n"), INREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0])));        
    
        // Switch ULPI to suspend mode
        //SetPHYPowerMgmt(pPdd->pUSBDRegs, TRUE);

        // Disable wakeup condition
        temp3 = (DWORD *)&ctrl;
        *temp3 = INREG32(&pPdd->pUSBDRegs->USB_CTRL);

        // We have to disable the wakeup, or it will fail in following condition:
        // - Unplug the USB device cable and plug in a DOK
        // - Unplug the DOK and wake it up by pressing the power on button
        //ctrl.OWIE = 1;
        //ctrl.OUIE = 1;
        ctrl.OWIE = 0;
        ctrl.OUIE = 0;

        OUTREG32(&pPdd->pUSBDRegs->USB_CTRL, *temp3);
        DEBUGMSG(ZONE_POWER, (TEXT("PowerDown USBCTRL=0x%x\r\n"), INREG32(&pPdd->pUSBDRegs->USB_CTRL)));

        
        // Set PORTSC PHCD to 1
        temp = (DWORD *)&portsc;
        *temp = INREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0]);
        portsc.PHCD = 1;
        OUTREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0], *temp);
        DEBUGMSG(ZONE_POWER, (TEXT("PowerDown PORTSC= 0x%x\r\n"), INREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0])));      

        // We need to wait for SUSPEND bit set
        //while((INREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0]) & 0x80) == 0x00)
        //  Sleep(0);
        if (pPdd->bUSBPanicMode)
        {
            DEBUGMSG(ZONE_POWER, (TEXT("Panic Mode off\r\n")));
            pPdd->bUSBPanicMode = FALSE;
#if 1 /*ERIC0907, need implemented?*/
            DEBUGMSG(0, (TEXT("DDKClockDisablePanicMode : 5\r\n")));
#else
            DDKClockDisablePanicMode();
#endif            
        }

        // Stop USB Clock now
        if (pPdd->bUSBCoreClk)
        {
            DEBUGMSG(ZONE_POWER, (TEXT("USB Clock stop\r\n")));
            pPdd->bUSBCoreClk = FALSE;
            USBClockDisable(TRUE);
        }       
    }
    RETAILMSG(1, (TEXT("UfnPdd_PowerDown-\r\n")));
}
//------------------------------------------------------------------------------
//
//  Function:  UfnPdd_PowerUp
//
//  This function is called during Power Up
//
//  Parameters: 
//     pPddContext - Pointer to USBFN_PDD 
//
//  Return:
//     NULL
//
//------------------------------------------------------------------------------
VOID WINAPI UfnPdd_PowerUp(VOID *pPddContext)
{
    USBFN_PDD *pPdd = (USBFN_PDD *)(pPddContext);

    DEBUGMSG(ZONE_POWER, (_T("UsbPdd_PowerUp with bInUSBFN %d\r\n"), pPdd->bInUSBFN) ); 
    RETAILMSG(1, (_T("UsbPdd_PowerUp+ (bInUSBFN %d\r\n)"), pPdd->bInUSBFN) ); 

    if (pPdd->bInUSBFN)
    {

        USB_CTRL_T ctrl;
        USB_USBCMD_T usbcmd;
        DWORD *temp3;
        DWORD *temp2;

        // Start USB Clock now
        if (pPdd->bUSBCoreClk == FALSE)
        {
            DEBUGMSG(ZONE_POWER, (TEXT("USB Clock start\r\n")));
            pPdd->bUSBCoreClk = TRUE;
            USBClockDisable(FALSE);
        }       

        if (pPdd->bUSBPanicMode == FALSE)
        {
            DEBUGMSG(ZONE_POWER, (TEXT("Panic Mode On\r\n")));
            pPdd->bUSBPanicMode = TRUE;
#if 1 /*ERIC0907 need implemented?*/            
            DEBUGMSG(0, (TEXT("DDKClockEnablePanicMode : 6\r\n")));
#else            
            DDKClockEnablePanicMode();
#endif            
        }


        RETAILMSG(1, (TEXT("PowerUp:USBSTS(0x%x) PORTSC(0x%x)\r\n"), 
            INREG32(&pPdd->pUSBDRegs->OTG.USBSTS), INREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0]) ));

        // Force resume first
        if (INREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0]) & 0x800000)
        {
            // Clear the PHCD
            OUTREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0], (INREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0]) & ~0x800000));

            StallExecution(500);

            // Force Resume bit
            OUTREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0], INREG32(&pPdd->pUSBDRegs->OTG.PORTSC[0])|0x40); 

            RETAILMSG(1, (TEXT("Force resume\r\n")));
        }

        //Disable wakeup condition
        temp3 = (DWORD *)&ctrl;
        *temp3 = INREG32(&pPdd->pUSBDRegs->USB_CTRL);

        DEBUGMSG(ZONE_POWER, (TEXT("PowerUp wakeup = 0x%x\r\n"), *temp3));
        if (ctrl.OWIR == 1)
        {
            *temp3 = 0;
            ctrl.OWIE = 1;
            CLRREG32(&pPdd->pUSBDRegs->USB_CTRL, *temp3);
        }

        // Switch ULPI to resume mode
        //SetPHYPowerMgmt(pPdd->pUSBDRegs, FALSE);

        // Enable back all interrupt
        OUTREG32(&pPdd->pUSBDRegs->OTG.USBINTR, pPdd->dwUSBIntrValue);
        DEBUGMSG(ZONE_POWER, (TEXT("Wakeup Interrupt Setting 0x%x\r\n"), 
                    pPdd->dwUSBIntrValue));

        // Start USB Run/Stop CMD
        temp2 = (DWORD *)&usbcmd;
        *temp2 = INREG32(&pPdd->pUSBDRegs->OTG.USBCMD);
        usbcmd.RS = 1;
        OUTREG32(&pPdd->pUSBDRegs->OTG.USBCMD, *temp2);
        DEBUGMSG(ZONE_POWER, (TEXT("PowerUp USBCMD = 0x%x\r\n"), INREG32(&pPdd->pUSBDRegs->OTG.USBCMD)));

        pPdd->bResume = TRUE;
        SetInterruptEvent(pPdd->sysIntr);        
    }

    RETAILMSG(1,(TEXT("UsbPdd_PowerUp-\r\n")));
}
//------------------------------------------------------------------------------
//
// Function: UpdateDevicePower
//
// UpdateDevice according to self power state and PM power state.
//
// Parameter:
//    pPdd - Pointer to USBFN_PDD
//
// Return:
//    Current Power state

⌨️ 快捷键说明

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