usb.c

来自「SAMSUNG S3C6410 CPU BSP for winmobile6」· C语言 代码 · 共 1,937 行 · 第 1/5 页

C
1,937
字号
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, ENDPOINT_DESC_SIZE);
			Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
			OTGDEV_WrPktEp0((UINT8 *)&oOtgDev.m_oDesc.oDescEndpt2+0, ENDPOINT_DESC_SIZE);
			oOtgDev.m_uEp0State = EP0_STATE_INIT;
			break;

				// === GET_DESCRIPTOR:STRING ===
		case EP0_STATE_GD_STR_I0:
			DBGUSB(("[GDS0_0]"));
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, 4);
			Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
			OTGDEV_WrPktEp0((UINT8 *)aDescStr0, 4);
			oOtgDev.m_uEp0State = EP0_STATE_INIT;
			break;

		case EP0_STATE_GD_STR_I1:
			DBGUSB(("[GDS1_%d]", oOtgDev.m_uEp0SubState));
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, sizeof(aDescStr1));
			if ((oOtgDev.m_uEp0SubState*oOtgDev.m_uControlEPMaxPktSize+oOtgDev.m_uControlEPMaxPktSize)<sizeof(aDescStr1))
			{
				if (oOtgDev.m_eSpeed == USB_HIGH)
					Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(0<<0));	//ep0 enable, clear nak, next ep0, 64byte
				else
					Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
				OTGDEV_WrPktEp0((UINT8 *)aDescStr1+(oOtgDev.m_uEp0SubState*oOtgDev.m_uControlEPMaxPktSize), oOtgDev.m_uControlEPMaxPktSize);
				oOtgDev.m_uEp0State = EP0_STATE_GD_STR_I1;
				oOtgDev.m_uEp0SubState++;
			}
			else
			{
				if (oOtgDev.m_eSpeed == USB_HIGH)
					Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(0<<0));	//ep0 enable, clear nak, next ep0, 64byte
				else
					Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
				OTGDEV_WrPktEp0((UINT8 *)aDescStr1+(oOtgDev.m_uEp0SubState*oOtgDev.m_uControlEPMaxPktSize), sizeof(aDescStr1)-(oOtgDev.m_uEp0SubState*oOtgDev.m_uControlEPMaxPktSize));
				oOtgDev.m_uEp0State = EP0_STATE_INIT;
				oOtgDev.m_uEp0SubState = 0;
			}
			break;

		case EP0_STATE_GD_STR_I2:
			DBGUSB(("[GDS2_%d]", oOtgDev.m_uEp0SubState));
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, sizeof(aDescStr2));
			if ((oOtgDev.m_uEp0SubState*oOtgDev.m_uControlEPMaxPktSize+oOtgDev.m_uControlEPMaxPktSize)<sizeof(aDescStr2))
			{
				if (oOtgDev.m_eSpeed == USB_HIGH)
					Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(0<<0));	//ep0 enable, clear nak, next ep0, 64byte
				else
					Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
				OTGDEV_WrPktEp0((UINT8 *)aDescStr2+(oOtgDev.m_uEp0SubState*oOtgDev.m_uControlEPMaxPktSize), oOtgDev.m_uControlEPMaxPktSize);
				oOtgDev.m_uEp0State = EP0_STATE_GD_STR_I2;
				oOtgDev.m_uEp0SubState++;
			}
			else
			{
				if (oOtgDev.m_eSpeed == USB_HIGH)
					Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(0<<0));	//ep0 enable, clear nak, next ep0, 64byte
				else
					Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
				DBGUSB(("[E]"));
				OTGDEV_WrPktEp0((UINT8 *)aDescStr2+(oOtgDev.m_uEp0SubState*oOtgDev.m_uControlEPMaxPktSize), sizeof(aDescStr2)-(oOtgDev.m_uEp0SubState*oOtgDev.m_uControlEPMaxPktSize));
				oOtgDev.m_uEp0State = EP0_STATE_INIT;
				oOtgDev.m_uEp0SubState = 0;
			}
			break;

		case EP0_STATE_GD_DEV_QUALIFIER:
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, 10);
			Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(0<<0));	//ep0 enable, clear nak, next ep0, 8byte
			OTGDEV_WrPktEp0((UINT8 *)aDeviceQualifierDescriptor+0, 10);
			oOtgDev.m_uEp0State = EP0_STATE_INIT;
			break;

		case EP0_STATE_INTERFACE_GET:
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, 1);
			Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
			OTGDEV_WrPktEp0((UINT8 *)&oInterfaceGet+0, 1);
			oOtgDev.m_uEp0State = EP0_STATE_INIT;
			break;


		case EP0_STATE_GET_STATUS0:
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, 1);
			Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
			OTGDEV_WrPktEp0((UINT8 *)&oStatusGet+0, 1);
			oOtgDev.m_uEp0State = EP0_STATE_INIT;
			break;

		case EP0_STATE_GET_STATUS1:
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, 1);
			Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
			OTGDEV_WrPktEp0((UINT8 *)&oStatusGet+1, 1);
			oOtgDev.m_uEp0State = EP0_STATE_INIT;
			break;

		case EP0_STATE_GET_STATUS2:
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, 1);
			Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
			OTGDEV_WrPktEp0((UINT8 *)&oStatusGet+2, 1);
			oOtgDev.m_uEp0State = EP0_STATE_INIT;
			break;

		case EP0_STATE_GET_STATUS3:
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, 1);
			Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
			OTGDEV_WrPktEp0((UINT8 *)&oStatusGet+3, 1);
			oOtgDev.m_uEp0State = EP0_STATE_INIT;
			break;

		case EP0_STATE_GET_STATUS4:
			OTGDEV_SetInEpXferSize(EP_TYPE_CONTROL, 1, 1);
			Outp32(DIEPCTL0, (1u<<31)|(1<<26)|(BULK_IN_EP<<11)|(3<<0));	//ep0 enable, clear nak, next ep0, 8byte
			OTGDEV_WrPktEp0((UINT8 *)&oStatusGet+4, 1);
			oOtgDev.m_uEp0State = EP0_STATE_INIT;
			break;

		default:
			break;
	}
}


//////////
// Function Name : OTGDEV_HandleEvent_BulkIn
// Function Desctiption : This function handles bulk in transfer in CPU mode.
// Input : NONE
// Output : NONE
// Version :
void OTGDEV_HandleEvent_BulkIn(void)
{
	UINT8* BulkInBuf;
	UINT32 uRemainCnt;

	DBGUSB(("CPU_MODE Bulk In Function\n"));

	BulkInBuf = (UINT8*)oOtgDev.m_pUpPt;

	uRemainCnt = oOtgDev.m_uUploadSize- ((UINT32)oOtgDev.m_pUpPt - oOtgDev.m_uUploadAddr);

	if (uRemainCnt > oOtgDev.m_uBulkInEPMaxPktSize)
	{
		OTGDEV_SetInEpXferSize(EP_TYPE_BULK, 1, oOtgDev.m_uBulkInEPMaxPktSize);
		Outp32(bulkIn_DIEPCTL, 1u<<31|1<<26|2<<18|1<<15|oOtgDev.m_uBulkInEPMaxPktSize<<0);		//ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64
		OTGDEV_WrPktBulkInEp(BulkInBuf, oOtgDev.m_uBulkInEPMaxPktSize);

		oOtgDev.m_pUpPt += oOtgDev.m_uBulkInEPMaxPktSize;
	}
	else if(uRemainCnt > 0)
	{
		OTGDEV_SetInEpXferSize(EP_TYPE_BULK, 1, uRemainCnt);
		Outp32(bulkIn_DIEPCTL, 1u<<31|1<<26|2<<18|1<<15|oOtgDev.m_uBulkInEPMaxPktSize<<0);		//ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64
		OTGDEV_WrPktBulkInEp(BulkInBuf, uRemainCnt);

		oOtgDev.m_pUpPt += uRemainCnt;
	}
	else	//uRemainCnt = 0
	{
		Outp32(bulkIn_DIEPCTL, (DEPCTL_SNAK|DEPCTL_BULK_TYPE));
	}
}

//////////
// Function Name : OTGDEV_HandleEvent_BulkOut
// Function Desctiption : This function handles bulk out transfer.
// Input : NONE
// Output : NONE
// Version :
#if 1

void OTGDEV_HandleEvent_BulkOut(UINT32 fifoCntByte)
{
	if (oOtgDev.m_eOpMode == USB_CPU)
	{
//		EdbgOutputDebugString("fifoCntByte : %x\n", fifoCntByte);g_pDownPt
		OTGDEV_RdPktBulkOutEp((UINT8 *)g_pDownPt, fifoCntByte);

		OTGDEV_SetOutEpXferSize(EP_TYPE_BULK, 1, fifoCntByte);

		Outp32(bulkOut_DOEPCTL, 1<<31|1<<26|2<<18|1<<15|oOtgDev.m_uBulkOutEPMaxPktSize<<0);		//ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64
	}
}


#else
void OTGDEV_HandleEvent_BulkOut(UINT32 fifoCntByte)
{
	UINT8 TempBuf[16];
	UINT32 uCheck;

	if (oOtgDev.m_uDownloadFileSize==0)
	{
		if (fifoCntByte == 10)
		{
			OTGDEV_RdPktBulkOutEp((UINT8 *)TempBuf, 10);
			uCheck = *((UINT8 *)(TempBuf+8)) + (*((UINT8 *)(TempBuf+9))<<8);

			if (uCheck==0x1)
			{
				oOtgDev.m_uUploadAddr =
					*((UINT8 *)(TempBuf+0))+
					(*((UINT8 *)(TempBuf+1))<<8)+
					(*((UINT8 *)(TempBuf+2))<<16)+
					(*((UINT8 *)(TempBuf+3))<<24);

				oOtgDev.m_uUploadSize =
					*((UINT8 *)(TempBuf+4))+
					(*((UINT8 *)(TempBuf+5))<<8)+
					(*((UINT8 *)(TempBuf+6))<<16)+
					(*((UINT8 *)(TempBuf+7))<<24);
				oOtgDev.m_pUpPt=(UINT8 *)oOtgDev.m_uUploadAddr;
				DBGUSB(("UploadAddress : 0x%x, UploadSize: %d\n", oOtgDev.m_uUploadAddr, oOtgDev.m_uUploadSize));

				if (oOtgDev.m_eOpMode == USB_DMA)
				{
					if (oOtgDev.m_uUploadSize>0)
					{
						UINT32 uPktCnt, uRemainder;

						DBGUSB(("Dma Start for IN PKT \n"));

						Outp32(GAHBCFG, MODE_DMA|BURST_INCR4|GBL_INT_UNMASK);
						Outp32(GINTMSK, INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|INT_RESET|INT_SUSPEND); //gint unmask

						Outp32(bulkIn_DIEPDMA, (UINT32)oOtgDev.m_pUpPt);

						uPktCnt = (UINT32)(oOtgDev.m_uUploadSize/oOtgDev.m_uBulkInEPMaxPktSize);
						uRemainder = (UINT32)(oOtgDev.m_uUploadSize%oOtgDev.m_uBulkInEPMaxPktSize);
						if(uRemainder != 0)
						{
							uPktCnt += 1;
						}
						if (uPktCnt > 1023)
						{
							OTGDEV_SetInEpXferSize(EP_TYPE_BULK, 1023, (oOtgDev.m_uBulkInEPMaxPktSize*1023));
						}
						else
						{
							OTGDEV_SetInEpXferSize(EP_TYPE_BULK, uPktCnt, oOtgDev.m_uUploadSize);
						}

						Outp32(bulkIn_DIEPCTL, 1u<<31|1<<26|2<<18|1<<15|BULK_IN_EP<<11|oOtgDev.m_uBulkInEPMaxPktSize<<0);		//ep1 enable, clear nak, bulk, usb active, next ep1, max pkt
					}
				}
				else
				{
					if (oOtgDev.m_uUploadSize > oOtgDev.m_uBulkInEPMaxPktSize)
					{
						OTGDEV_SetInEpXferSize(EP_TYPE_BULK, 1, oOtgDev.m_uBulkInEPMaxPktSize);
					}
					else
					{
						OTGDEV_SetInEpXferSize(EP_TYPE_BULK, 1, oOtgDev.m_uUploadSize);
					}
					Outp32(bulkIn_DIEPCTL, 1u<<31|1<<26|2<<18|1<<15|oOtgDev.m_uBulkInEPMaxPktSize<<0);		//ep1 enable, clear nak, bulk, usb active, max pkt 64
				}
			}
			oOtgDev.m_uDownloadFileSize=0;
			return;
		}
		else
		{
			OTGDEV_RdPktBulkOutEp((UINT8 *)TempBuf, 8);
			DBGUSB(("downloadFileSize==0, 1'st BYTE_READ_CNT_REG : %x\n", fifoCntByte));
			oOtgDev.m_uDownloadAddress=
				*((UINT8 *)(TempBuf+0))+
				(*((UINT8 *)(TempBuf+1))<<8)+
				(*((UINT8 *)(TempBuf+2))<<16)+
				(*((UINT8 *)(TempBuf+3))<<24);

			oOtgDev.m_uDownloadFileSize=
				*((UINT8 *)(TempBuf+4))+
				(*((UINT8 *)(TempBuf+5))<<8)+
				(*((UINT8 *)(TempBuf+6))<<16)+
				(*((UINT8 *)(TempBuf+7))<<24);

			oOtgDev.m_pDownPt=(UINT8 *)oOtgDev.m_uDownloadAddress;
			DBGUSB(("downloadAddress : 0x%x, downloadFileSize: %d\n", oOtgDev.m_uDownloadAddress, oOtgDev.m_uDownloadFileSize));

			OTGDEV_RdPktBulkOutEp((UINT8 *)oOtgDev.m_pDownPt, fifoCntByte-8); // The first 8-bytes are deleted.
			oOtgDev.m_pDownPt += fifoCntByte-8;

			if (oOtgDev.m_eOpMode == USB_CPU)
			{
				OTGDEV_SetOutEpXferSize(EP_TYPE_BULK, 1, oOtgDev.m_uBulkOutEPMaxPktSize);
				Outp32(bulkOut_DOEPCTL, 1u<<31|1<<26|2<<18|1<<15|oOtgDev.m_uBulkOutEPMaxPktSize<<0);		//ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64
			}
			else
			{
				if (oOtgDev.m_uDownloadFileSize>oOtgDev.m_uBulkOutEPMaxPktSize)
				{
					UINT32 uPktCnt, uRemainder;

					DBGUSB(("downloadFileSize!=0, Dma Start for 2nd OUT PKT \n"));
					Outp32(GINTMSK, INT_RESUME|INT_OUT_EP|INT_IN_EP|INT_ENUMDONE|INT_RESET|INT_SUSPEND); //gint unmask
					Outp32(GAHBCFG, MODE_DMA|BURST_INCR4|GBL_INT_UNMASK);
					Outp32(bulkOut_DOEPDMA, (UINT32)oOtgDev.m_pDownPt);
					uPktCnt = (UINT32)(oOtgDev.m_uDownloadFileSize-oOtgDev.m_uBulkOutEPMaxPktSize)/oOtgDev.m_uBulkOutEPMaxPktSize;
					uRemainder = (UINT32)((oOtgDev.m_uDownloadFileSize-oOtgDev.m_uBulkOutEPMaxPktSize)%oOtgDev.m_uBulkOutEPMaxPktSize);
					if(uRemainder != 0)
					{
						uPktCnt += 1;
					}
					if (uPktCnt > 1023)
					{
						OTGDEV_SetOutEpXferSize(EP_TYPE_BULK, 1023, (oOtgDev.m_uBulkOutEPMaxPktSize*1023));
					}
					else
					{
						OTGDEV_SetOutEpXferSize(EP_TYPE_BULK, uPktCnt, (oOtgDev.m_uDownloadFileSize-oOtgDev.m_uBulkOutEPMaxPktSize));
					}
					Outp32(bulkOut_DOEPCTL, 1u<<31|1<<26|2<<18|1<<15|oOtgDev.m_uBulkOutEPMaxPktSize<<0);		//ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64
				}
			}
		}
	}

	else
	{
		if (oOtgDev.m_eOpMode == USB_CPU)
		{
			DBGUSB(("downloadFileSize!=0, 2nd BYTE_READ_CNT_REG : %x\n", fifoCntByte));
			OTGDEV_RdPktBulkOutEp((UINT8 *)oOtgDev.m_pDownPt, fifoCntByte);
			oOtgDev.m_pDownPt += fifoCntByte;

			OTGDEV_SetOutEpXferSize(EP_TYPE_BULK, 1, oOtgDev.m_uBulkOutEPMaxPktSize);
			Outp32(bulkOut_DOEPCTL, 1u<<31|1<<26|2<<18|1<<15|oOtgDev.m_uBulkOutEPMaxPktSize<<0);		//ep3 enable, clear nak, bulk, usb active, next ep3, max pkt 64
		}
	}
}

#endif
//#pragma optimize ("",off)

//////////
// Function Name : OTGDEV_InitPhyCon
// Function Desctiption : This function initializes OTG Phy.
// Input : NONE
// Output : NONE
// Version :
void OTGDEV_InitPhyCon(void)
{
	Outp32(PHYPWR, 0x0);
	Outp32(PHYCTRL, 0x20);
	Outp32(RSTCON, 0x1);
	delayLoop(100);
	Outp32(RSTCON, 0x0);
	delayLoop(100);
}

//#pragma optimize ("",on)


//////////
// Function Name : OTGDEV_SoftResetCore
// Function Desctiption : This function soft-resets OTG Core and then unresets again.
// Input : NONE
// Output : NONE
// Version :
void OTGDEV_SoftResetCore(void)
{
	volatile UINT32 uTemp;

	Outp32(GRSTCTL, CORE_SOFT_RESET);

	do
	{
		Inp32(GRSTCTL, uTemp);
	}while(!(uTemp & AHB_MASTER_IDLE));

}

//////////
// Function Name : OTGDEV_WaitCableInsertion
// Function Desctiption : This function checks if the cable is inserted.
// Input : NONE
// Output : NONE
// Version :
void OTGDEV_WaitCableInsertion(void)
{
	volatile UINT32 uTemp;
	bool ucFirst=1;

	do
	{
		//uTemp = Inp32(GOTGCTL);
		Inp32(GOTGCTL, uTemp);

		if (uTemp & (B_SESSION_VALID|A_SESSION_VALID))

⌨️ 快捷键说明

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