1242 lines
35 KiB
C
1242 lines
35 KiB
C
/**
|
|
******************************************************************************
|
|
* @file otgd_fs_cal.c
|
|
* @author MCD Application Team
|
|
* @version V3.4.0
|
|
* @date 29-June-2012
|
|
* @brief OTG FS Device Core Access Layer interface.
|
|
******************************************************************************
|
|
* @attention
|
|
*
|
|
* <h2><center>© COPYRIGHT 2012 STMicroelectronics</center></h2>
|
|
*
|
|
* Licensed under MCD-ST Liberty SW License Agreement V2, (the "License");
|
|
* You may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at:
|
|
*
|
|
* http://www.st.com/software_license_agreement_liberty_v2
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*
|
|
******************************************************************************
|
|
*/
|
|
|
|
|
|
#ifdef STM32F10X_CL
|
|
|
|
/* Includes ------------------------------------------------------------------*/
|
|
#include "otgd_fs_cal.h"
|
|
#include "usb_conf.h"
|
|
#include "otgd_fs_regs.h"
|
|
|
|
/* Private typedef -----------------------------------------------------------*/
|
|
/* Private define ------------------------------------------------------------*/
|
|
/* Private macro -------------------------------------------------------------*/
|
|
/* Private variables ---------------------------------------------------------*/
|
|
|
|
USB_OTG_CORE_REGS USB_OTG_FS_regs;
|
|
|
|
/* Private function prototypes -----------------------------------------------*/
|
|
static USB_OTG_Status OTGD_FS_SetDeviceMode(void);
|
|
static USB_OTG_Status OTGD_FS_CoreReset(void);
|
|
|
|
extern uint32_t STM32_PCD_OTG_ISR_Handler (void);
|
|
|
|
/******************************************************************************/
|
|
/* Common Core Layer */
|
|
/******************************************************************************/
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_WritePacket
|
|
* Description : Writes a packet into the Tx FIFO associated with the EP
|
|
* Input : None
|
|
* Output : None
|
|
* Return : Status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_WritePacket(uint8_t *src, uint8_t ep_num, uint16_t bytes)
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
uint32_t dword_count = 0 , i = 0;
|
|
__IO uint32_t *fifo;
|
|
|
|
/* Find the DWORD length, padded by extra bytes as necessary if MPS
|
|
* is not a multiple of DWORD */
|
|
dword_count = (bytes + 3) / 4;
|
|
|
|
fifo = USB_OTG_FS_regs.FIFO[ep_num];
|
|
|
|
for (i = 0; i < dword_count; i++, src += 4)
|
|
{
|
|
USB_OTG_WRITE_REG32( fifo, *((__packed uint32_t *)src) );
|
|
}
|
|
|
|
return status;
|
|
}
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_ReadPacket
|
|
* Description : Reads a packet from the Rx FIFO
|
|
* Input : None
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
void* OTGD_FS_ReadPacket(uint8_t *dest, uint16_t bytes)
|
|
{
|
|
uint32_t i = 0;
|
|
uint32_t word_count = (bytes + 3) / 4;
|
|
|
|
__IO uint32_t *fifo = USB_OTG_FS_regs.FIFO[0];
|
|
uint32_t *data_buff = (uint32_t *)dest;
|
|
|
|
for (i = 0; i < word_count; i++, data_buff++)
|
|
{
|
|
*data_buff = USB_OTG_READ_REG32(fifo);
|
|
}
|
|
|
|
/* Return the buffer pointer because if the transfer is composed of several packets,
|
|
the data of the next packet must be stored following the previous packet's data */
|
|
return ((void *)data_buff);
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_SetAddress
|
|
* Description : Initialize core registers addresses.
|
|
* Input : BaseAddress
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_SetAddress(uint32_t BaseAddress)
|
|
{
|
|
uint32_t i = 0;
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_FS_regs.GREGS = (USB_OTG_GREGS *)(BaseAddress +\
|
|
USB_OTG_CORE_GLOBAL_REGS_OFFSET);
|
|
|
|
USB_OTG_FS_regs.DEV = (USB_OTG_DEV *) (BaseAddress +\
|
|
USB_OTG_DEV_GLOBAL_REG_OFFSET);
|
|
|
|
for (i = 0; i < NUM_TX_FIFOS; i++)
|
|
{
|
|
USB_OTG_FS_regs.DINEPS[i] = (USB_OTG_DINEPS *) (BaseAddress + \
|
|
USB_OTG_DEV_IN_EP_REG_OFFSET + (i * USB_OTG_EP_REG_OFFSET));
|
|
|
|
USB_OTG_FS_regs.DOUTEPS[i] = (USB_OTG_DOUTEPS *) (BaseAddress + \
|
|
USB_OTG_DEV_OUT_EP_REG_OFFSET + (i * USB_OTG_EP_REG_OFFSET));
|
|
}
|
|
|
|
for (i = 0; i < NUM_TX_FIFOS; i++)
|
|
{
|
|
USB_OTG_FS_regs.FIFO[i] = (uint32_t *)(BaseAddress + \
|
|
USB_OTG_DATA_FIFO_OFFSET + (i * USB_OTG_DATA_FIFO_SIZE));
|
|
}
|
|
|
|
USB_OTG_FS_regs.PCGCCTL = (uint32_t *)(BaseAddress + USB_OTG_PCGCCTL_OFFSET);
|
|
|
|
return status;
|
|
}
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_CoreInit
|
|
* Description : Initialize the USB_OTG controller registers and prepares the core
|
|
for device mode or host mode operation.
|
|
* Input : None
|
|
* Output : None
|
|
* Return : Status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_CoreInit(void)
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_GUSBCFG_TypeDef usbcfg;
|
|
USB_OTG_GCCFG_TypeDef gccfg;
|
|
|
|
usbcfg.d32 = 0;
|
|
gccfg.d32 = 0;
|
|
|
|
usbcfg.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.GREGS->GUSBCFG);
|
|
usbcfg.b.physel = 1;
|
|
USB_OTG_WRITE_REG32 (&USB_OTG_FS_regs.GREGS->GUSBCFG, usbcfg.d32);
|
|
|
|
/* init and configure the phy */
|
|
gccfg.d32 = 0;
|
|
gccfg.b.vbussensingB = 1;
|
|
gccfg.b.pwdn = 1;
|
|
USB_OTG_WRITE_REG32 (&USB_OTG_FS_regs.GREGS->GCCFG, gccfg.d32);
|
|
mDELAY(50);
|
|
|
|
/* Reset after a PHY select and set Host mode */
|
|
OTGD_FS_CoreReset();
|
|
|
|
/* Set Device Mode */
|
|
OTGD_FS_SetDeviceMode();
|
|
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_CoreReset
|
|
* Description : Soft reset of the core
|
|
* Input : None
|
|
* Output : None
|
|
* Return : Status
|
|
*******************************************************************************/
|
|
static USB_OTG_Status OTGD_FS_CoreReset(void)
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
__IO USB_OTG_GRSTCTL_TypeDef greset;
|
|
uint32_t timeout = 0;
|
|
|
|
greset.d32 = 0;
|
|
|
|
/* Wait for AHB master IDLE state. */
|
|
do
|
|
{
|
|
uDELAY(5);
|
|
greset.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.GREGS->GRSTCTL);
|
|
if (++timeout > USB_OTG_TIMEOUT)
|
|
{
|
|
return USB_OTG_OK;
|
|
}
|
|
}
|
|
while (greset.b.ahbidle == 0);
|
|
|
|
/* Core Soft Reset */
|
|
timeout = 0;
|
|
greset.b.csftrst = 1;
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.GREGS->GRSTCTL, greset.d32 );
|
|
|
|
do
|
|
{
|
|
greset.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.GREGS->GRSTCTL);
|
|
if (++timeout > USB_OTG_TIMEOUT)
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
while (greset.b.csftrst == 1);
|
|
|
|
/* Wait for 3 PHY Clocks*/
|
|
uDELAY(5);
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_EnableGlobalInt
|
|
* Description : Enables the controller's Global Int in the AHB Config reg
|
|
* Input : None
|
|
* Output : None
|
|
* Return : Status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_EnableGlobalInt(void)
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_GAHBCFG_TypeDef ahbcfg;
|
|
|
|
ahbcfg.d32 = 0;
|
|
|
|
ahbcfg.b.gintmsk = 1; /* Enable interrupts */
|
|
USB_OTG_MODIFY_REG32(&USB_OTG_FS_regs.GREGS->GAHBCFG, 0, ahbcfg.d32);
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_DisableGlobalInt
|
|
* Description : Disables the controller's Global Int in the AHB Config reg
|
|
* Input : None
|
|
* Output : None
|
|
* Return : Status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_DisableGlobalInt(void)
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_GAHBCFG_TypeDef ahbcfg;
|
|
|
|
ahbcfg.d32 = 0;
|
|
ahbcfg.b.gintmsk = 1; /* Enable interrupts */
|
|
USB_OTG_MODIFY_REG32(&USB_OTG_FS_regs.GREGS->GAHBCFG, ahbcfg.d32, 0);
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_FlushTxFifo
|
|
* Description : Flush a Tx FIFO
|
|
* Input : FIFO num
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_FlushTxFifo (uint32_t num )
|
|
{
|
|
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
__IO USB_OTG_GRSTCTL_TypeDef greset;
|
|
uint32_t timeout = 0;
|
|
|
|
greset.d32 = 0;
|
|
|
|
greset.b.txfflsh = 1;
|
|
greset.b.txfnum = num;
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.GREGS->GRSTCTL, greset.d32 );
|
|
|
|
do
|
|
{
|
|
greset.d32 = USB_OTG_READ_REG32( &USB_OTG_FS_regs.GREGS->GRSTCTL);
|
|
if (++timeout > USB_OTG_TIMEOUT)
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
while (greset.b.txfflsh == 1);
|
|
|
|
/* Wait for 3 PHY Clocks*/
|
|
uDELAY(5);
|
|
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_FlushRxFifo
|
|
* Description : Flush a Rx FIFO
|
|
* Input : None
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_FlushRxFifo( void )
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
__IO USB_OTG_GRSTCTL_TypeDef greset;
|
|
uint32_t timeout = 0;
|
|
|
|
greset.d32 = 0;
|
|
|
|
greset.b.rxfflsh = 1;
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.GREGS->GRSTCTL, greset.d32 );
|
|
|
|
do
|
|
{
|
|
greset.d32 = USB_OTG_READ_REG32( &USB_OTG_FS_regs.GREGS->GRSTCTL);
|
|
if (++timeout > USB_OTG_TIMEOUT)
|
|
{
|
|
break;
|
|
}
|
|
}
|
|
while (greset.b.rxfflsh == 1);
|
|
|
|
/* Wait for 3 PHY Clocks*/
|
|
uDELAY(5);
|
|
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_SetDeviceMode
|
|
* Description : Set device mode
|
|
* Input : None
|
|
* Output : None
|
|
* Return : Status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_SetDeviceMode(void)
|
|
{
|
|
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_GUSBCFG_TypeDef usbcfg ;
|
|
|
|
usbcfg.d32 = 0;
|
|
|
|
usbcfg.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.GREGS->GUSBCFG);
|
|
|
|
usbcfg.b.force_dev = 1;
|
|
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.GREGS->GUSBCFG, usbcfg.d32);
|
|
|
|
mDELAY(50);
|
|
|
|
return status;
|
|
}
|
|
/*******************************************************************************
|
|
* Function Name : IsDeviceMode
|
|
* Description : check device mode
|
|
* Input : None
|
|
* Output : None
|
|
* Return : current mode
|
|
*******************************************************************************/
|
|
uint32_t USBD_FS_IsDeviceMode(void)
|
|
{
|
|
return ((USB_OTG_READ_REG32(&USB_OTG_FS_regs.GREGS->GINTSTS ) & 0x1) == 0 );
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_ReadCoreItr
|
|
* Description : returns the Core Interrupt register
|
|
* Input : None
|
|
* Output : None
|
|
* Return : None
|
|
*******************************************************************************/
|
|
uint32_t OTGD_FS_ReadCoreItr(void)
|
|
{
|
|
uint32_t v = 0;
|
|
|
|
v = USB_OTG_READ_REG32(&USB_OTG_FS_regs.GREGS->GINTSTS);
|
|
v &= USB_OTG_READ_REG32(&USB_OTG_FS_regs.GREGS->GINTMSK);
|
|
|
|
return v;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_ReadOtgItr
|
|
* Description : returns the USB_OTG Interrupt register
|
|
* Input : None
|
|
* Output : None
|
|
* Return : None
|
|
*******************************************************************************/
|
|
uint32_t OTGD_FS_ReadOtgItr (void)
|
|
{
|
|
return (USB_OTG_READ_REG32 (&USB_OTG_FS_regs.GREGS->GOTGINT));
|
|
}
|
|
|
|
/******************************************************************************/
|
|
/* PCD Core Layer */
|
|
/******************************************************************************/
|
|
|
|
/*******************************************************************************
|
|
* Function Name : InitDevSpeed
|
|
* Description : Initializes the DevSpd field of the DCFG register depending
|
|
on the PHY type and the enumeration speed of the device.
|
|
* Input : None
|
|
* Output : None
|
|
* Return : None
|
|
*******************************************************************************/
|
|
static void InitDevSpeed(void)
|
|
{
|
|
USB_OTG_DCFG_TypeDef dcfg;
|
|
|
|
dcfg.d32 = 0;
|
|
|
|
dcfg.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DEV->DCFG);
|
|
dcfg.b.devspd = 0x3; /* Full speed PHY */
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.DEV->DCFG, dcfg.d32);
|
|
}
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_CoreInitDev
|
|
* Description : Initialize the USB_OTG controller registers for device mode
|
|
* Input : None
|
|
* Output : None
|
|
* Return : Status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_CoreInitDev (void)
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_DEPCTLx_TypeDef depctl;
|
|
USB_OTG_DCFG_TypeDef dcfg;
|
|
USB_OTG_FIFOSIZ_TypeDef txfifosize0;
|
|
USB_OTG_FIFOSIZ_TypeDef txfifosize;
|
|
uint32_t i = 0;
|
|
|
|
depctl.d32 = 0;
|
|
dcfg.d32 = 0;
|
|
txfifosize0.d32 = 0;
|
|
txfifosize.d32 = 0;
|
|
|
|
/* Set device speed */
|
|
InitDevSpeed ();
|
|
|
|
/* Restart the Phy Clock */
|
|
USB_OTG_WRITE_REG32(USB_OTG_FS_regs.PCGCCTL, 0);
|
|
|
|
/* Device configuration register */
|
|
dcfg.d32 = USB_OTG_READ_REG32( &USB_OTG_FS_regs.DEV->DCFG);
|
|
dcfg.b.perfrint = DCFG_FRAME_INTERVAL_80;
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DEV->DCFG, dcfg.d32 );
|
|
|
|
/* set Rx FIFO size */
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.GREGS->GRXFSIZ, RX_FIFO_SIZE);
|
|
|
|
/* EP0 TX*/
|
|
txfifosize0.b.depth = TX0_FIFO_SIZE;
|
|
txfifosize0.b.startaddr = RX_FIFO_SIZE;
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.GREGS->DIEPTXF0, txfifosize0.d32 );
|
|
|
|
|
|
/* EP1 TX*/
|
|
txfifosize.b.startaddr = txfifosize0.b.startaddr + txfifosize0.b.depth;
|
|
txfifosize.b.depth = TX1_FIFO_SIZE;
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.GREGS->DIEPTXFx[0], txfifosize.d32 );
|
|
|
|
|
|
/* EP2 TX*/
|
|
txfifosize.b.startaddr += txfifosize.b.depth;
|
|
txfifosize.b.depth = TX2_FIFO_SIZE;
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.GREGS->DIEPTXFx[1], txfifosize.d32 );
|
|
|
|
|
|
/* EP3 TX*/
|
|
txfifosize.b.startaddr += txfifosize.b.depth;
|
|
txfifosize.b.depth = TX3_FIFO_SIZE;
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.GREGS->DIEPTXFx[2], txfifosize.d32 );
|
|
|
|
|
|
/* Flush the FIFOs */
|
|
OTGD_FS_FlushTxFifo(0x10); /* all Tx FIFOs */
|
|
OTGD_FS_FlushRxFifo();
|
|
|
|
/* Clear all pending Device Interrupts */
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DEV->DIEPMSK, 0 );
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DEV->DOEPMSK, 0 );
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DEV->DAINT, 0xFFFFFFFF );
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DEV->DAINTMSK, 0 );
|
|
|
|
for (i = 0; i < NUM_TX_FIFOS; i++)
|
|
{
|
|
depctl.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DINEPS[i]->DIEPCTLx);
|
|
if (depctl.b.epena)
|
|
{
|
|
depctl.d32 = 0;
|
|
depctl.b.epdis = 1;
|
|
depctl.b.snak = 1;
|
|
}
|
|
else
|
|
{
|
|
depctl.d32 = 0;
|
|
}
|
|
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DINEPS[i]->DIEPCTLx, depctl.d32);
|
|
|
|
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DINEPS[i]->DIEPTSIZx, 0);
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DINEPS[i]->DIEPINTx, 0xFF);
|
|
}
|
|
|
|
for (i = 0; i < 1/* NUM_OUT_EPS*/; i++)
|
|
{
|
|
depctl.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DOUTEPS[i]->DOEPCTLx);
|
|
if (depctl.b.epena)
|
|
{
|
|
depctl.d32 = 0;
|
|
depctl.b.epdis = 1;
|
|
depctl.b.snak = 1;
|
|
}
|
|
else
|
|
{
|
|
depctl.d32 = 0;
|
|
}
|
|
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DOUTEPS[i]->DOEPCTLx, depctl.d32);
|
|
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DOUTEPS[i]->DOEPTSIZx, 0);
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.DOUTEPS[i]->DOEPINTx, 0xFF);
|
|
}
|
|
|
|
OTGD_FS_EnableDevInt();
|
|
|
|
return status;
|
|
}
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_EnableDevInt
|
|
* Description : Enables the Device mode interrupts
|
|
* Input : None
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_EnableDevInt(void)
|
|
{
|
|
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_GINTMSK_TypeDef intr_mask;
|
|
|
|
intr_mask.d32 = 0;
|
|
|
|
/* Disable all interrupts. */
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.GREGS->GINTMSK, 0);
|
|
|
|
/* Clear any pending interrupts */
|
|
USB_OTG_WRITE_REG32( &USB_OTG_FS_regs.GREGS->GINTSTS, 0xFFFFFFFF);
|
|
|
|
/* Enable the defined interrupts in Device mode */
|
|
#ifdef INTR_SOFINTR
|
|
intr_mask.b.sofintr = 1;
|
|
#endif /* INTR_SOFINTR */
|
|
#ifdef INTR_RXSTSQLVL
|
|
intr_mask.b.rxstsqlvl = 1;
|
|
#endif /* INTR_RXSTSQLVL */
|
|
#ifdef INTR_GINNAKEFF
|
|
intr_mask.b.ginnakeff = 1;
|
|
#endif /* INTR_GINNAKEFF */
|
|
#ifdef INTR_GOUTNAKEFF
|
|
intr_mask.b.goutnakeff = 1;
|
|
#endif /* INTR_GOUTNAKEFF */
|
|
#ifdef INTR_ERLYSUSPEND
|
|
intr_mask.b.erlysuspend = 1;
|
|
#endif /* INTR_ERLYSUSPEND */
|
|
#ifdef INTR_USBSUSPEND
|
|
intr_mask.b.usbsuspend = 1;
|
|
#endif /* INTR_USBSUSPEND */
|
|
#ifdef INTR_USBRESET
|
|
intr_mask.b.usbreset = 1;
|
|
#endif /* INTR_USBRESET */
|
|
#ifdef INTR_ENUMDONE
|
|
intr_mask.b.enumdone = 1;
|
|
#endif /* INTR_ENUMDONE */
|
|
#ifdef INTR_ISOOUTDROP
|
|
intr_mask.b.isooutdrop = 1;
|
|
#endif /* INTR_ISOOUTDROP */
|
|
#ifdef INTR_EOPFRAME
|
|
intr_mask.b.eopframe = 1;
|
|
#endif /* INTR_EOPFRAME */
|
|
#ifdef INTR_INEPINTR
|
|
intr_mask.b.inepintr = 1;
|
|
#endif /* INTR_INEPINTR */
|
|
#ifdef INTR_OUTEPINTR
|
|
intr_mask.b.outepintr = 1;
|
|
#endif /* INTR_OUTEPINTR */
|
|
#ifdef INTR_INCOMPLISOIN
|
|
intr_mask.b.incomplisoin = 1;
|
|
#endif /* INTR_INCOMPLISOIN */
|
|
#ifdef INTR_INCOMPLISOOUT
|
|
intr_mask.b.incomplisoout = 1;
|
|
#endif /* INTR_INCOMPLISOOUT */
|
|
#ifdef INTR_DISCONNECT
|
|
intr_mask.b.disconnect = 1;
|
|
#endif /* INTR_DISCONNECT */
|
|
#ifdef INTR_WKUPINTR
|
|
intr_mask.b.wkupintr = 1;
|
|
#endif /* INTR_WKUPINTR */
|
|
|
|
USB_OTG_MODIFY_REG32( &USB_OTG_FS_regs.GREGS->GINTMSK, intr_mask.d32, intr_mask.d32);
|
|
return status;
|
|
|
|
}
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_EP0Activate
|
|
* Description : enables EP0 OUT to receive SETUP packets and configures EP0
|
|
IN for transmitting packets
|
|
* Input : None
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_EP0Activate(void)
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_DEPCTLx_TypeDef diepctl;
|
|
USB_OTG_DCTL_TypeDef dctl;
|
|
|
|
diepctl.d32 = 0;
|
|
dctl.d32 = 0;
|
|
|
|
diepctl.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DINEPS[0]->DIEPCTLx);
|
|
diepctl.b.mps = DEP0CTL_MPS_64;
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.DINEPS[0]->DIEPCTLx, diepctl.d32);
|
|
|
|
dctl.b.cgnpinnak = 1;
|
|
USB_OTG_MODIFY_REG32(&USB_OTG_FS_regs.DEV->DCTL, dctl.d32, dctl.d32);
|
|
|
|
return status;
|
|
}
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_EPActivate
|
|
* Description : Activates an EP
|
|
* Input : ep
|
|
* Output : None
|
|
* Return : num_in_ep
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_EPActivate(USB_OTG_EP *ep)
|
|
{
|
|
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_DEPCTLx_TypeDef depctl;
|
|
USB_OTG_DAINT_TypeDef daintmsk;
|
|
__IO uint32_t *addr;
|
|
|
|
|
|
depctl.d32 = 0;
|
|
daintmsk.d32 = 0;
|
|
|
|
/* Read DEPCTLn register */
|
|
if (ep->is_in == 1)
|
|
{
|
|
addr = &USB_OTG_FS_regs.DINEPS[ep->num]->DIEPCTLx;
|
|
daintmsk.ep.in = 1 << ep->num;
|
|
}
|
|
else
|
|
{
|
|
addr = &USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPCTLx;
|
|
daintmsk.ep.out = 1 << ep->num;
|
|
}
|
|
|
|
/* If the EP is already active don't change the EP Control
|
|
* register. */
|
|
depctl.d32 = USB_OTG_READ_REG32(addr);
|
|
if (!depctl.b.usbactep)
|
|
{
|
|
depctl.b.mps = ep->maxpacket;
|
|
depctl.b.eptype = ep->type;
|
|
depctl.b.txfnum = ep->tx_fifo_num;
|
|
depctl.b.setd0pid = 1;
|
|
depctl.b.usbactep = 1;
|
|
USB_OTG_WRITE_REG32(addr, depctl.d32);
|
|
}
|
|
|
|
/* Enable the Interrupt for this EP */
|
|
USB_OTG_MODIFY_REG32(&USB_OTG_FS_regs.DEV->DAINTMSK, 0, daintmsk.d32);
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_EPDeactivate
|
|
* Description : Deactivates an EP
|
|
* Input : ep
|
|
* Output : None
|
|
* Return : num_in_ep
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_EPDeactivate(USB_OTG_EP *ep)
|
|
{
|
|
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_DEPCTLx_TypeDef depctl;
|
|
__IO uint32_t *addr;
|
|
USB_OTG_DAINT_TypeDef daintmsk;
|
|
|
|
depctl.d32 = 0;
|
|
daintmsk.d32 = 0;
|
|
|
|
/* Read DEPCTLn register */
|
|
if (ep->is_in == 1)
|
|
{
|
|
addr = &USB_OTG_FS_regs.DINEPS[ep->num]->DIEPCTLx;
|
|
daintmsk.ep.in = 1 << ep->num;
|
|
}
|
|
else
|
|
{
|
|
addr = &USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPCTLx;
|
|
daintmsk.ep.out = 1 << ep->num;
|
|
}
|
|
|
|
depctl.b.usbactep = 0;
|
|
USB_OTG_WRITE_REG32(addr, depctl.d32);
|
|
|
|
/* Disable the Interrupt for this EP */
|
|
USB_OTG_MODIFY_REG32(&USB_OTG_FS_regs.DEV->DAINTMSK, daintmsk.d32, 0);
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_EPStartXfer
|
|
* Description : Handle the setup for data xfer for an EP and starts the xfer
|
|
* Input : None
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_EPStartXfer(USB_OTG_EP *ep)
|
|
{
|
|
USB_OTG_DSTS_TypeDef dsts;
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
__IO USB_OTG_DEPCTLx_TypeDef depctl;
|
|
OTG_FS_DEPTSIZx_TypeDef deptsiz;
|
|
|
|
depctl.d32 = 0;
|
|
deptsiz.d32 = 0;
|
|
|
|
/* IN endpoint */
|
|
if (ep->is_in == 1)
|
|
{
|
|
|
|
depctl.d32 = USB_OTG_READ_REG32(&(USB_OTG_FS_regs.DINEPS[ep->num]->DIEPCTLx));
|
|
deptsiz.d32 = USB_OTG_READ_REG32(&(USB_OTG_FS_regs.DINEPS[ep->num]->DIEPTSIZx));
|
|
|
|
/* Zero Length Packet? */
|
|
if (ep->xfer_len == 0)
|
|
{
|
|
deptsiz.b.xfersize = 0;
|
|
deptsiz.b.pktcnt = 1;
|
|
|
|
}
|
|
else
|
|
{
|
|
/* Program the transfer size and packet count
|
|
* as follows: xfersize = N * maxpacket +
|
|
* short_packet pktcnt = N + (short_packet
|
|
* exist ? 1 : 0)
|
|
*/
|
|
deptsiz.b.xfersize = ep->xfer_len;
|
|
deptsiz.b.pktcnt = (ep->xfer_len - 1 + ep->maxpacket) / ep->maxpacket;
|
|
|
|
if (ep->type == EP_TYPE_ISOC)
|
|
{
|
|
deptsiz.b.mcount = 1;
|
|
}
|
|
}
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.DINEPS[ep->num]->DIEPTSIZx, deptsiz.d32);
|
|
|
|
if (ep->type != EP_TYPE_ISOC)
|
|
{
|
|
/* Enable the Tx FIFO Empty Interrupt for this EP */
|
|
uint32_t fifoemptymsk = 0;
|
|
fifoemptymsk = 1 << ep->num;
|
|
USB_OTG_MODIFY_REG32(&USB_OTG_FS_regs.DEV->DIEPEMPMSK, 0, fifoemptymsk);
|
|
}
|
|
|
|
/* EP enable, IN data in FIFO */
|
|
depctl.b.cnak = 1;
|
|
depctl.b.epena = 1;
|
|
|
|
if (ep->type == EP_TYPE_ISOC)
|
|
{
|
|
dsts.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DEV->DSTS);
|
|
|
|
if (((dsts.b.soffn)&0x1)==0)
|
|
{
|
|
depctl.b.setoddfrm=1;
|
|
}
|
|
else
|
|
{
|
|
depctl.b.setd0pid=1;
|
|
}
|
|
}
|
|
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.DINEPS[ep->num]->DIEPCTLx, depctl.d32);
|
|
|
|
if (ep->type == EP_TYPE_ISOC)
|
|
{
|
|
/*write buffer in TXFIFO*/
|
|
/* user should ensure that ep->xfer_len <= ep->maxpacket */
|
|
OTGD_FS_WritePacket(ep->xfer_buff, ep->num, ep->xfer_len);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
/* OUT endpoint */
|
|
depctl.d32 = USB_OTG_READ_REG32(&(USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPCTLx));
|
|
deptsiz.d32 = USB_OTG_READ_REG32(&(USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPTSIZx));
|
|
|
|
/* Program the transfer size and packet count as follows:
|
|
* pktcnt = N
|
|
* xfersize = N * maxpacket
|
|
*/
|
|
if (ep->xfer_len == 0)
|
|
{
|
|
deptsiz.b.xfersize = ep->maxpacket;
|
|
deptsiz.b.pktcnt = 1;
|
|
}
|
|
else
|
|
{
|
|
deptsiz.b.pktcnt = (ep->xfer_len + (ep->maxpacket - 1)) / ep->maxpacket;
|
|
deptsiz.b.xfersize = deptsiz.b.pktcnt * ep->maxpacket;
|
|
}
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPTSIZx, deptsiz.d32);
|
|
|
|
if (ep->type == EP_TYPE_ISOC)
|
|
{
|
|
|
|
if (ep->even_odd_frame)
|
|
{
|
|
depctl.b.setoddfrm = 1;
|
|
}
|
|
else
|
|
{
|
|
depctl.b.setd0pid = 1;
|
|
}
|
|
}
|
|
|
|
/* EP enable */
|
|
depctl.b.cnak = 1;
|
|
depctl.b.epena = 1;
|
|
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPCTLx, depctl.d32);
|
|
|
|
}
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_EP0StartXfer
|
|
* Description : Handle the setup for a data xfer for EP0 and starts the xfer
|
|
* Input : None
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_EP0StartXfer(USB_OTG_EP *ep)
|
|
{
|
|
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
uint32_t fifoemptymsk = 0;
|
|
USB_OTG_DEPCTLx_TypeDef depctl;
|
|
OTG_FS_DEPTSIZx_TypeDef deptsiz;
|
|
USB_OTG_DINEPS *in_regs ;
|
|
|
|
depctl.d32 = 0;
|
|
deptsiz.d32 = 0;
|
|
|
|
/* IN endpoint */
|
|
if (ep->is_in == 1)
|
|
{
|
|
in_regs = USB_OTG_FS_regs.DINEPS[0];
|
|
depctl.d32 = USB_OTG_READ_REG32(&in_regs->DIEPCTLx);
|
|
deptsiz.d32 = USB_OTG_READ_REG32(&in_regs->DIEPTSIZx);
|
|
|
|
/* Zero Length Packet? */
|
|
if (ep->xfer_len == 0)
|
|
{
|
|
deptsiz.b.xfersize = 0;
|
|
deptsiz.b.pktcnt = 1;
|
|
}
|
|
else
|
|
{
|
|
if (ep->xfer_len > ep->maxpacket)
|
|
{
|
|
ep->xfer_len = ep->maxpacket;
|
|
deptsiz.b.xfersize = ep->maxpacket;
|
|
}
|
|
else
|
|
{
|
|
deptsiz.b.xfersize = ep->xfer_len;
|
|
}
|
|
deptsiz.b.pktcnt = 1;
|
|
|
|
}
|
|
USB_OTG_WRITE_REG32(&in_regs->DIEPTSIZx, deptsiz.d32);
|
|
|
|
/* EP enable, IN data in FIFO */
|
|
depctl.b.cnak = 1;
|
|
depctl.b.epena = 1;
|
|
USB_OTG_WRITE_REG32(&in_regs->DIEPCTLx, depctl.d32);
|
|
|
|
/* Enable the Tx FIFO Empty Interrupt for this EP */
|
|
if (ep->xfer_len > 0)
|
|
{
|
|
fifoemptymsk |= 1 << ep->num;
|
|
USB_OTG_MODIFY_REG32(&USB_OTG_FS_regs.DEV->DIEPEMPMSK, 0, fifoemptymsk);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
/* OUT endpoint */
|
|
depctl.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DOUTEPS[0]->DOEPCTLx);
|
|
deptsiz.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DOUTEPS[0]->DOEPTSIZx);
|
|
|
|
/* Program the transfer size and packet count as follows:
|
|
* xfersize = N * (maxpacket + 4 - (maxpacket % 4))
|
|
* pktcnt = N */
|
|
if (ep->xfer_len == 0)
|
|
{
|
|
deptsiz.b.xfersize = ep->maxpacket;
|
|
deptsiz.b.pktcnt = 1;
|
|
}
|
|
else
|
|
{
|
|
deptsiz.b.pktcnt = (ep->xfer_len + (ep->maxpacket - 1)) / ep->maxpacket;
|
|
deptsiz.b.xfersize = deptsiz.b.pktcnt * ep->maxpacket;
|
|
}
|
|
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.DOUTEPS[0]->DOEPTSIZx, deptsiz.d32);
|
|
|
|
/* EP enable */
|
|
depctl.b.cnak = 1;
|
|
depctl.b.epena = 1;
|
|
USB_OTG_WRITE_REG32 (&(USB_OTG_FS_regs.DOUTEPS[0]->DOEPCTLx), depctl.d32);
|
|
}
|
|
return status;
|
|
}
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_EPSetStall
|
|
* Description : Set the EP STALL
|
|
* Input : None
|
|
* Output : None
|
|
* Return : Status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_EPSetStall(USB_OTG_EP *ep)
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_DEPCTLx_TypeDef depctl;
|
|
__IO uint32_t *depctl_addr;
|
|
|
|
depctl.d32 = 0;
|
|
|
|
|
|
if (ep->is_in == 1)
|
|
{
|
|
depctl_addr = &(USB_OTG_FS_regs.DINEPS[ep->num]->DIEPCTLx);
|
|
depctl.d32 = USB_OTG_READ_REG32(depctl_addr);
|
|
|
|
/* set the disable and stall bits */
|
|
if (depctl.b.epena)
|
|
{
|
|
depctl.b.epdis = 1;
|
|
}
|
|
depctl.b.stall = 1;
|
|
USB_OTG_WRITE_REG32(depctl_addr, depctl.d32);
|
|
}
|
|
else
|
|
{
|
|
depctl_addr = &(USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPCTLx);
|
|
depctl.d32 = USB_OTG_READ_REG32(depctl_addr);
|
|
|
|
/* set the stall bit */
|
|
depctl.b.stall = 1;
|
|
USB_OTG_WRITE_REG32(depctl_addr, depctl.d32);
|
|
}
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_EPClearStall
|
|
* Description : Clear the EP STALL
|
|
* Input : None
|
|
* Output : None
|
|
* Return : Status
|
|
*******************************************************************************/
|
|
USB_OTG_Status OTGD_FS_EPClearStall(USB_OTG_EP *ep)
|
|
{
|
|
USB_OTG_Status status = USB_OTG_OK;
|
|
USB_OTG_DEPCTLx_TypeDef depctl;
|
|
__IO uint32_t *depctl_addr;
|
|
|
|
|
|
depctl.d32 = 0;
|
|
|
|
if (ep->is_in == 1)
|
|
{
|
|
depctl_addr = &(USB_OTG_FS_regs.DINEPS[ep->num]->DIEPCTLx);
|
|
}
|
|
else
|
|
{
|
|
depctl_addr = &(USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPCTLx);
|
|
}
|
|
|
|
|
|
depctl.d32 = USB_OTG_READ_REG32(depctl_addr);
|
|
|
|
/* clear the stall bits */
|
|
depctl.b.stall = 0;
|
|
|
|
if (ep->type == EP_TYPE_INTR || ep->type == EP_TYPE_BULK)
|
|
{
|
|
depctl.b.setd0pid = 1; /* DATA0 */
|
|
}
|
|
|
|
USB_OTG_WRITE_REG32(depctl_addr, depctl.d32);
|
|
return status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_ReadDevAllOutEp_itr
|
|
* Description : returns the OUT endpoint interrupt bits
|
|
* Input : None
|
|
* Output : None
|
|
* Return : None
|
|
*******************************************************************************/
|
|
uint32_t OTGD_FS_ReadDevAllOutEp_itr(void)
|
|
{
|
|
uint32_t v = 0;
|
|
|
|
v = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DEV->DAINT);
|
|
v &= USB_OTG_READ_REG32(&USB_OTG_FS_regs.DEV->DAINTMSK);
|
|
return ((v & 0xffff0000) >> 16);
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_ReadDevOutEP_itr
|
|
* Description : returns the Device OUT EP Interrupt register
|
|
* Input : None
|
|
* Output : None
|
|
* Return : None
|
|
*******************************************************************************/
|
|
uint32_t OTGD_FS_ReadDevOutEP_itr(USB_OTG_EP *ep)
|
|
{
|
|
uint32_t v = 0;
|
|
|
|
v = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPINTx);
|
|
v &= USB_OTG_READ_REG32(&USB_OTG_FS_regs.DEV->DOEPMSK);
|
|
return v;
|
|
}
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_ReadDevAllInEPItr
|
|
* Description : Get int status register
|
|
* Input : None
|
|
* Output : None
|
|
* Return : None
|
|
*******************************************************************************/
|
|
uint32_t OTGD_FS_ReadDevAllInEPItr(void)
|
|
{
|
|
uint32_t v = 0;
|
|
|
|
v = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DEV->DAINT);
|
|
v &= USB_OTG_READ_REG32(&USB_OTG_FS_regs.DEV->DAINTMSK);
|
|
return (v & 0xffff);
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_GetEPStatus
|
|
* Description : returns the EP Status
|
|
* Input : - ep: pointer to the EP structure
|
|
* Output : None
|
|
* Return : status: DEV_EP_TX_STALL, DEV_EP_TX_VALID, DEV_EP_TX_NAK,
|
|
* DEV_EP_RX_STALL, DEV_EP_RX_VALID or DEV_EP_RX_NAK,
|
|
*******************************************************************************/
|
|
uint32_t OTGD_FS_GetEPStatus(USB_OTG_EP *ep)
|
|
{
|
|
USB_OTG_DEPCTLx_TypeDef depctl;
|
|
__IO uint32_t *depctl_addr;
|
|
uint32_t Status = 0;
|
|
|
|
depctl.d32 = 0;
|
|
|
|
if (ep->is_in == 1)
|
|
{
|
|
depctl_addr = &(USB_OTG_FS_regs.DINEPS[ep->num]->DIEPCTLx);
|
|
}
|
|
else
|
|
{
|
|
depctl_addr = &(USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPCTLx);
|
|
}
|
|
|
|
depctl.d32 = USB_OTG_READ_REG32(depctl_addr);
|
|
|
|
/* Process for IN endpoint */
|
|
if (ep->is_in == 1)
|
|
{
|
|
if (depctl.b.stall == 1)
|
|
Status = DEV_EP_TX_STALL;
|
|
else if (depctl.b.naksts == 1)
|
|
Status = DEV_EP_TX_NAK;
|
|
else
|
|
Status = DEV_EP_TX_VALID;
|
|
}
|
|
/* Process for OUT endpoint */
|
|
else
|
|
{
|
|
if (depctl.b.stall == 1)
|
|
Status = DEV_EP_RX_STALL;
|
|
else if (depctl.b.naksts == 1)
|
|
Status = DEV_EP_RX_NAK;
|
|
else
|
|
Status = DEV_EP_RX_VALID;
|
|
}
|
|
|
|
/* Return the current status */
|
|
return Status;
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_SetEPStatus
|
|
* Description : Sets the EP Status
|
|
* Input : - ep: pointer to the EP structure
|
|
* - Status: new status to be set
|
|
* Output : None
|
|
* Return : None
|
|
*******************************************************************************/
|
|
void OTGD_FS_SetEPStatus(USB_OTG_EP *ep, uint32_t Status)
|
|
{
|
|
USB_OTG_DEPCTLx_TypeDef depctl;
|
|
__IO uint32_t *depctl_addr;
|
|
|
|
depctl.d32 = 0;
|
|
|
|
|
|
if (ep->is_in == 1)
|
|
{
|
|
depctl_addr = &(USB_OTG_FS_regs.DINEPS[ep->num]->DIEPCTLx);
|
|
}
|
|
else
|
|
{
|
|
depctl_addr = &(USB_OTG_FS_regs.DOUTEPS[ep->num]->DOEPCTLx);
|
|
}
|
|
|
|
depctl.d32 = USB_OTG_READ_REG32(depctl_addr);
|
|
|
|
/* Process for IN endpoint */
|
|
if (ep->is_in == 1)
|
|
{
|
|
if (Status == DEV_EP_TX_STALL)
|
|
{
|
|
OTGD_FS_EPSetStall(ep); return;
|
|
}
|
|
else if (Status == DEV_EP_TX_NAK)
|
|
depctl.b.snak = 1;
|
|
else if (Status == DEV_EP_TX_VALID)
|
|
{
|
|
if (depctl.b.stall == 1)
|
|
{
|
|
ep->even_odd_frame = 0;
|
|
OTGD_FS_EPClearStall(ep);
|
|
return;
|
|
}
|
|
depctl.b.cnak = 1;
|
|
depctl.b.usbactep = 1;
|
|
depctl.b.epena = 1;
|
|
}
|
|
else if (Status == DEV_EP_TX_DIS)
|
|
depctl.b.usbactep = 0;
|
|
}
|
|
else /* Process for OUT endpoint */
|
|
{
|
|
if (Status == DEV_EP_RX_STALL) {
|
|
depctl.b.stall = 1;
|
|
}
|
|
else if (Status == DEV_EP_RX_NAK)
|
|
depctl.b.snak = 1;
|
|
else if (Status == DEV_EP_RX_VALID)
|
|
{
|
|
if (depctl.b.stall == 1)
|
|
{
|
|
ep->even_odd_frame = 0;
|
|
OTGD_FS_EPClearStall(ep);
|
|
return;
|
|
}
|
|
depctl.b.cnak = 1;
|
|
depctl.b.usbactep = 1;
|
|
depctl.b.epena = 1;
|
|
}
|
|
else if (Status == DEV_EP_RX_DIS)
|
|
{
|
|
depctl.b.usbactep = 0;
|
|
}
|
|
}
|
|
|
|
USB_OTG_WRITE_REG32(depctl_addr, depctl.d32);
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_SetRemoteWakeup
|
|
* Description : Enable Remote wakeup signaling
|
|
* Input : None
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
void OTGD_FS_SetRemoteWakeup()
|
|
{
|
|
USB_OTG_DCTL_TypeDef devctl;
|
|
|
|
devctl.d32 = 0;
|
|
|
|
devctl.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DEV->DCTL);
|
|
|
|
/* Enable the Remote Wakeup signal */
|
|
devctl.b.rmtwkupsig = 1;
|
|
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.DEV->DCTL, devctl.d32);
|
|
}
|
|
|
|
/*******************************************************************************
|
|
* Function Name : OTGD_FS_ResetRemoteWakeup
|
|
* Description : Disable Remote wakeup signaling
|
|
* Input : None
|
|
* Output : None
|
|
* Return : status
|
|
*******************************************************************************/
|
|
void OTGD_FS_ResetRemoteWakeup()
|
|
{
|
|
USB_OTG_DCTL_TypeDef devctl;
|
|
|
|
|
|
devctl.d32 = 0;
|
|
|
|
devctl.d32 = USB_OTG_READ_REG32(&USB_OTG_FS_regs.DEV->DCTL);
|
|
|
|
/* Disable the Remote Wakeup signal */
|
|
devctl.b.rmtwkupsig = 0;
|
|
|
|
USB_OTG_WRITE_REG32(&USB_OTG_FS_regs.DEV->DCTL, devctl.d32);
|
|
}
|
|
#endif /* STM32F10X_CL */
|
|
|
|
/************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
|