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

📄 d12.c

📁 USB文本阅读器
💻 C
字号:
#include "d12.h"
#include "alt_types.h"
#include <io.h>

/**************************************/
#define	D12_DELAY	Delay(20)
//#define	USB_DEBUG
/*******************************************/
alt_u8 mDevice_Descriptor[] = {
					0x12,		//设备描述符长度
					0x01,		//设备描述符类型
					0x10, 0x01,		//USB协议版本
					0xDC,		//测试设备类型
					0x00,		//设备子类
					0x00,		//设备协议
					EP0_PK_LEN,			//端点0最大数据包大小
					0x71, 0x04,		//厂商ID
					0x8a, 0x88,		//产品ID
					0x00, 0x01,		//设备系列号
					0x00,		//索引
					0x00,	
					0x00,
					0x01  };	//可能配置数

alt_u8 mAll_Descriptor[] = {
				/********配置描述符*************/
					0x09,		//配置描述符长度
					0x02,		//配置描述符类型
					0x2e, 0x00,		//描述符总长度
					0x01,		//仅支持一个接口
					0x01,		//配置值
					0x00,		//无字符串描述符指针
					0xa0,		//总线供电,支持远程唤醒
					0x00,		//最大消耗200mA电流
				/********接口描述符*************/
					0x09,		//接口描述符长度
					0x04,		//接口描述符类型
					0x00,		//只有一个接口
					0x00,		//可选配置只有一个
					0x04,		//端点数目(除端点0外)
					0xdc,		//测试设备类型
					0xa0,		//子类代码
					0xb0,		//协议代码
					0x00,		//字符串描述符索引
				/*********端点描述符************/
				/*********端点1:IN*************/
					0x07,		//端点描述符长度
					0x05,		//端点描述符类型
					0x81,		//端点1:IN
					0x03,		//中断传输
					16,	0,	//最大数据包大小
					0x0a,		//传输间隔时间
				/*********端点1:OUT*************/
					0x07,		//端点描述符长度
					0x05,		//端点描述符类型
					0x01,		//端点1:OUT
					0x03,		//中断传输
					16,	0,	//最大数据包大小
					0x0a,		//传输间隔时间
				/*********端点2:IN*************/
					0x07,		//端点描述符长度
					0x05,		//端点描述符类型
					0x82,		//端点1:IN
					0x02,		//批量传输
					64,	0,	//最大数据包大小
					0x01,		//传输间隔时间
				/*********端点2:OUT*************/
					0x07,		//端点描述符长度
					0x05,		//端点描述符类型
					0x02,		//端点2:OUT
					0x02,		//批量传输
					64,	0,	//最大数据包大小
					0x01
					};


void Delay(alt_u32 delay)
{
  while(delay--);
}
/***********D12初始化********************/
void USB_Port_Init(void)
{
 	if(D12RdChipId() != 0x1210)
	{
		printf("\nUSB Error: Not Found D12 Chip!");
		return;
	}
	USB_SetDMA_Mode(0x00);		//设置USB DMA
	USB_Connect(0x02,0x4b);		//断开USB
	Delay(100000);
	USB_Connect(0x12,0x45);		//重新连接USB
	USB_Read_INT_Flag();   
}

/**********D12操作程序*****************/
alt_u16 D12RdChipId(void)			//读取D12 ID
{
	alt_u16 tmp;
	
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0xfd);
	D12_DELAY;
	tmp = IORD_8DIRECT(D12_BASE, USB_DAT);
	D12_DELAY;
	tmp = (tmp<<8) | IORD_8DIRECT(D12_BASE, USB_DAT);
	return tmp;	
}

void USB_Connect(alt_u8 mMode,alt_u8 mClk)
{
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0xf3);
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_DAT, mMode);
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_DAT, mClk);
}

void USB_SetAddr_Enable(alt_u8 mAddr,alt_u8 mEnable)	//设置地址
{
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0xd0);
	D12_DELAY;
	if(mEnable)
    IOWR_8DIRECT(D12_BASE, USB_DAT, mAddr | 0x80);
	else
    IOWR_8DIRECT(D12_BASE, USB_DAT, mAddr);
}

void USB_SetEndPoint_Enable(alt_u8 mEnable)		//设置端点使能
{
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0xd8);
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_DAT, mEnable & 0x01);
}

void USB_SetDMA_Mode(alt_u8 mMode)
{
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0xfb);
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_DAT, mMode);
}

alt_u16 USB_Read_INT_Flag(void)		//读中断标志
{
	alt_u16 Temp1,Temp2;
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0xf4);
	D12_DELAY;
	Temp2 = IORD_8DIRECT(D12_BASE, USB_DAT);
	D12_DELAY;
	Temp1 = IORD_8DIRECT(D12_BASE, USB_DAT);
	D12_DELAY;
	Temp1 <<= 8;
	return Temp1 + Temp2;
}

alt_u8 USB_Read_LastStatus(alt_u8 mEndPoint)	//读最后处理状态寄存器
{
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0x40 | mEndPoint);
	D12_DELAY;
	return IORD_8DIRECT(D12_BASE, USB_DAT);;
}

alt_u8 USB_Select_EndPoint(alt_u8 mEndPoint)	//选择端点
{
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, mEndPoint);
	D12_DELAY;
	return IORD_8DIRECT(D12_BASE, USB_DAT);;
}

alt_u8 USB_Read_EndPoint_Buff(alt_u8 mEndPoint,alt_u8 mLen,alt_u8 *mBuff)	//读缓冲区
{
	alt_u8 len,i,Temp;
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, mEndPoint);
	D12_DELAY;
	if((IORD_8DIRECT(D12_BASE, USB_DAT) & 0x01) == 0)		//如果缓冲区为空,则返回
		return 0;
	else
	{
		D12_DELAY;
    IOWR_8DIRECT(D12_BASE, USB_CMD, 0xf0);
		D12_DELAY;
		Temp = IORD_8DIRECT(D12_BASE, USB_DAT);
		D12_DELAY;
		len = IORD_8DIRECT(D12_BASE, USB_DAT);
		D12_DELAY;
		if(len > mLen)
			len = mLen;
		for(i=0;i<len;i++)
		{
			D12_DELAY;
			mBuff[i] = IORD_8DIRECT(D12_BASE, USB_DAT);
		}
		D12_DELAY;
    IOWR_8DIRECT(D12_BASE, USB_CMD, 0xf2);
		return len;      
	}
}

void USB_Write_EndPoint_Buff(alt_u8 mEndPoint,alt_u8 mLen,alt_u8 *mBuff)	//写缓冲区
{
	alt_u8 i;
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, mEndPoint);
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0xf0);
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_DAT, 0);
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_DAT, mLen);
	D12_DELAY;
	for(i=0; i<mLen; i++)
	{
		D12_DELAY;
    IOWR_8DIRECT(D12_BASE, USB_DAT, mBuff[i]);
	}
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0xfa);
}

void USB_EndPoint_Setup_Ack(alt_u8 mEndPoint)		//SetUp包应答
{
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, mEndPoint);
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0xf1);
	D12_DELAY;
	if(!mEndPoint)
    IOWR_8DIRECT(D12_BASE, USB_CMD, 0xf2);
}

void USB_SetEndPoint_Status(alt_u8 mEndPoint,alt_u8 mStall)		//设置端点状态
{
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0x40 | mEndPoint);
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_DAT, mStall);
}

alt_u8 USB_GetEndPoint_Status(alt_u8 mEndPoint)		//获取端点状态
{
	D12_DELAY;
  IOWR_8DIRECT(D12_BASE, USB_CMD, 0x40 | mEndPoint);
	D12_DELAY;
	return IORD_8DIRECT(D12_BASE, USB_DAT);
}

void USB_Stall(void)		//设备停止
{
	USB_SetEndPoint_Status(ENDPOINT0_OUT,1);
	USB_SetEndPoint_Status(ENDPOINT0_IN,1);
}

/********************标准设备请求*********************************/
DEVICE_REQUEST mDevice_Request;
alt_u8 RemoteWakeupState;
alt_u8 Config;
alt_u8 UsbSendDescFlag;
alt_u8 *pUSBSendDisc;
alt_u8 DiscSendRemainLen;
alt_u8 UsbGetStatus(alt_u8 *SetupPkt)
{	
	alt_u8 temp;
	if(SetupPkt[2] | SetupPkt[3] | SetupPkt[5] | SetupPkt[7])
		return STATUS_ERR;
	if(SetupPkt[6] != 2)
		return STATUS_ERR;
	if(SetupPkt[0] == 0x80)
	{
		if(SetupPkt[4])
			return STATUS_ERR;
		SetupPkt[0] = RemoteWakeupState ? 1 : 0;
		SetupPkt[1] = 0;
	}
	else
	if(SetupPkt[0] == 0x81)
	{
		if(SetupPkt[4])
			return STATUS_ERR;
		SetupPkt[0] = 0;
		SetupPkt[1] = 0;		
	}
	else
	if(SetupPkt[0] == 0x82)
	{
		temp = USB_Select_EndPoint((SetupPkt[4] << 1) | (SetupPkt[4] >> 7));
		SetupPkt[1] = (temp & 2) ? 1 : 0;
		SetupPkt[0] = 0;
	}
	else
		return STATUS_ERR;

	USB_Write_EndPoint_Buff(ENDPOINT0_IN, 2, SetupPkt);
	return STATUS_OK;		
}

alt_u8 UsbClrFeature(alt_u8 *SetupPkt)
{

	if(SetupPkt[0] & 0x80)
		return STATUS_ERR;
	if(SetupPkt[3] | SetupPkt[5] | SetupPkt[6] | SetupPkt[7])	
		return STATUS_ERR;
		
	if(SetupPkt[0] & 0x1f)
	{
		if((SetupPkt[0]&0x1f) != 2)
			return STATUS_ERR;
		USB_SetEndPoint_Status((SetupPkt[4] << 1) | (SetupPkt[4] >> 7), 0);		//设置端点状态
	}
	else
	{
		if(SetupPkt[4])
			return STATUS_ERR;
		RemoteWakeupState = 0;
	}
	
	USB_Write_EndPoint_Buff(ENDPOINT0_IN, 0, SetupPkt);
	return STATUS_OK;
}

alt_u8 UsbSetFeature(alt_u8 *SetupPkt)
{
	if(!(SetupPkt[0] & 0x80))
		return STATUS_ERR;
	if(SetupPkt[3] | SetupPkt[5] | SetupPkt[6] | SetupPkt[7])
		return STATUS_ERR;
		
	if(SetupPkt[0] & 0x1f)
	{
		if((SetupPkt[0] & 0x1f) != 2)
			return STATUS_ERR;
		
		USB_SetEndPoint_Status((SetupPkt[4] << 1) | (SetupPkt[4] >> 7), 1);
	}
	else
	{
		if(SetupPkt[4])
			return STATUS_ERR;
		
		RemoteWakeupState = 1;
	}
	
	USB_Write_EndPoint_Buff(ENDPOINT0_IN, 0, SetupPkt);
	return STATUS_OK;
}

alt_u8 UsbSetAddress(alt_u8 *SetupPkt)
{

	if(SetupPkt[0] | SetupPkt[3] | SetupPkt[4] | SetupPkt[5] | SetupPkt[6] | SetupPkt[7])
		return STATUS_ERR;
		
	USB_SetAddr_Enable(SetupPkt[2], 1);
	USB_Write_EndPoint_Buff(ENDPOINT0_IN, 0, SetupPkt);
	return STATUS_OK;	
}

void UsbSendDesc()
{
	alt_u8 len;
#ifdef USB_DEBUG
	alt_u8 i;
#endif

	UsbSendDescFlag = DiscSendRemainLen >= EP0_PK_LEN;	
	len = UsbSendDescFlag ? EP0_PK_LEN : DiscSendRemainLen;
	USB_Write_EndPoint_Buff(ENDPOINT0_IN, len, pUSBSendDisc);

#ifdef USB_DEBUG
	printf("@");
	for(i=0; i<len; i++)
		printf("%x,", pUSBSendDisc[i]);	
  printf("\n");
#endif
		
	DiscSendRemainLen -= len;
	pUSBSendDisc += len;
}

alt_u8 UsbGetDescriptor(alt_u8 *SetupPkt)
{
	if(SetupPkt[0] != 0x80)
		return STATUS_ERR;
		
	switch(SetupPkt[3])
	{
		case 0x01:		//获取设备描述符
			pUSBSendDisc = mDevice_Descriptor;
			DiscSendRemainLen = mDevice_Descriptor[0];
			break;
		case 0x02:		//获取接口描述符
			pUSBSendDisc = mAll_Descriptor;
			DiscSendRemainLen = mAll_Descriptor[2];
			break;
		default:
			return STATUS_ERR;	
	}

	if(mDevice_Request.wLength < DiscSendRemainLen)
		DiscSendRemainLen = mDevice_Request.wLength;
	
	UsbSendDesc();
	return STATUS_OK;	
}

alt_u8 UsbGetConfiguration(alt_u8 *SetupPkt)
{
	if(SetupPkt[0] != 0x80)
		return STATUS_ERR;
	if(SetupPkt[2] | SetupPkt[3] | SetupPkt[4] | SetupPkt[5] | SetupPkt[7])
		return STATUS_ERR;
	if(SetupPkt[6]!=1)
		return STATUS_ERR;
		
	SetupPkt[0] = Config ? 1 : 0;
	USB_Write_EndPoint_Buff(ENDPOINT0_IN, 1, SetupPkt);
	return STATUS_OK;	
}

alt_u8 UsbSetConfiguration(alt_u8 *SetupPkt)
{
	if(SetupPkt[0] | SetupPkt[3] | SetupPkt[4] | SetupPkt[5] | SetupPkt[6] | SetupPkt[7])
		return STATUS_ERR;
	if(SetupPkt[2]&0xfe)
		return STATUS_ERR;
		
	Config = SetupPkt[2] & 0x01;
	USB_SetEndPoint_Enable(Config);
	USB_SetEndPoint_Status(ENDPOINT1_OUT, Config^1);
	USB_SetEndPoint_Status(ENDPOINT1_IN, Config^1);
	USB_SetEndPoint_Status(ENDPOINT2_OUT, Config^1);
	USB_SetEndPoint_Status(ENDPOINT2_IN, Config^1);
	USB_Write_EndPoint_Buff(ENDPOINT0_IN, 0, SetupPkt);
	return STATUS_OK;	
}

alt_u8 UsbGetInterface(alt_u8 *SetupPkt)
{
	if(SetupPkt[0]!=0x81)
		return STATUS_ERR;
	if(SetupPkt[2]|SetupPkt[3]|SetupPkt[4]|SetupPkt[5]|SetupPkt[7])
		return STATUS_ERR;
	if(SetupPkt[6]!=1)
		return STATUS_ERR;
		
	SetupPkt[0] = 0;
	USB_Write_EndPoint_Buff(ENDPOINT0_IN, 1, SetupPkt);
	return STATUS_OK;
}

alt_u8 UsbSetInterface(alt_u8 *SetupPkt)
{
	return STATUS_ERR;
}

alt_u8 UsbReserved(alt_u8 *SetupPkt)
{
	return STATUS_ERR;	
}

alt_u8 (*StdUSBDevReq[])(alt_u8 *SetupPkt) = {
	UsbGetStatus,
	UsbClrFeature,
	UsbReserved,
	UsbSetFeature,
	UsbReserved,
	UsbSetAddress,
	UsbGetDescriptor,
	UsbReserved,
	UsbGetConfiguration,
	UsbSetConfiguration,
	UsbGetInterface,
	UsbSetInterface,
	UsbReserved,
	UsbReserved,
	UsbReserved,
	UsbReserved
}; 

/*****************************************************************/
void USB_EndPoint0_IN(void)		//端点0 IN 中断服务子程序
{
	alt_u8 m_Status;
	m_Status=USB_Read_LastStatus(ENDPOINT0_IN);
	if(UsbSendDescFlag)
		UsbSendDesc();
}

void USB_EndPoint0_OUT(void)	//端点0 OUT中断服务子程序
{
	alt_u8 mStatus;
#ifdef USB_DEBUG
	alt_u8 i;
	alt_u8 *PakeData = (alt_u8 *)&mDevice_Request;
#endif
	UsbSendDescFlag = FALSE;
	mStatus = USB_Read_LastStatus(ENDPOINT0_OUT);
	if(mStatus == USB_SETUPPACKET)		//接收到正确的setup包
	{
		if(USB_Read_EndPoint_Buff(ENDPOINT0_OUT, 16, (alt_u8 *)&mDevice_Request) == 8)   //读取数据到USB_Buff
		{
			USB_EndPoint_Setup_Ack(0);		//应答Setup包
			USB_EndPoint_Setup_Ack(1);
		#ifdef USB_DEBUG
			printf("$");
			for(i=0; i<8; i++)
				printf("0x%x,", PakeData[i]);
      printf("\n");
		#endif		
			if(!StdUSBDevReq[mDevice_Request.bRequest & 0xf]((alt_u8 *)&mDevice_Request));
				return;
		}
	}
	USB_Stall();	
}

//端点1 IN中断服务子程序
void USB_EndPoint1_IN(void)		
{
	alt_u16 m_Status;
	m_Status=USB_Read_LastStatus(ENDPOINT1_IN);
}

//端点1 OUT中断服务子程序
void USB_EndPoint1_OUT(void)	
{ 
	alt_u16 m_Status;
	m_Status=USB_Read_LastStatus(ENDPOINT1_OUT);
}

//端点02 IN中断服务子程序
void USB_EndPoint2_IN(void)		
{
	alt_u16 m_Status;
	m_Status=USB_Read_LastStatus(ENDPOINT2_IN);
}


⌨️ 快捷键说明

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