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

📄 usb_loop.c

📁 USB固件开发源程序,以单片机为核心,转贴的
💻 C
字号:
#include "reg52.h"
#include "usb.h"
#include "study.h"
/*
//*************************************************************************
// USB protocol function pointer arrays
//*************************************************************************
*/
code void (*StandardDeviceRequest[])(void) =
{
	get_status,
	clear_feature,
	reserved,
	set_feature,
	reserved,
	set_address,
	get_descriptor,
	reserved,
	get_configuration,
	set_configuration,
	get_interface,
	set_interface,
	reserved,
	reserved,
	reserved,
	reserved
};

code void (*VendorDeviceRequest[])(void) =
{
	reserved,
	reserved,
	reserved,
	reserved,
	reserved,
	reserved,
	reserved,
	reserved,
	reserved,
	reserved,
	reserved,
	reserved,
	read_write_register,
	reserved,
	reserved,
	reserved
};


//extern xdata EPPFLAGS bEPPflags;
//extern xdata CONTROL_XFER ControlData;
//extern void D12_SetMode(uchar bConfig, uchar bClkDiv);
//extern void D12_SetDMA(uchar bMode);
//extern void D12_SetEndpointStatus(uchar bEndp, uchar bStalled);
//extern uchar D12_WriteEndpoint(uchar endp, uchar len, uchar * buf);
//extern void D12_SetEndpointEnable(uchar bEnable);




void disconnect_USB(void)
{
	// Initialize D12 configuration
//	D12_SetMode(D12_NOLAZYCLOCK, );//0x02,0x40|0x03
	D12_SetMode(0,D12_SETTOONE | D12_CLOCK_12M);
	
}

void connect_USB(void)
{
	// reset event flags

	DISABLE;
	bEPPflags.value = 0;
	ENABLE;
	D12_SetDMA(D12_ENDP4INTENABLE | D12_ENDP5INTENABLE);
	D12_SetMode(D12_NOLAZYCLOCK | D12_SOFTCONNECT,D12_SETTOONE | D12_CLOCK_12M );
   				//0x02|0x10,0x40|0x30
}


void reconnect_USB(void)
{
	unsigned long clk_cnt;

	MCU_LED1 = 0;
	MCU_LED2 = 0;
	MCU_LED3 = 0;
	MCU_LED4 = 0;
	disconnect_USB();
    for(clk_cnt=0;clk_cnt<20000;clk_cnt++);//延时
	connect_USB();

	P3=0xff;
	MCU_LED1 = 1;
	MCU_LED2 = 1;
	MCU_LED3 = 0;
	MCU_LED4 = 0;

}
//------------------------------
void stall_ep0(void)
{
	D12_SetEndpointStatus(0, 1);
	D12_SetEndpointStatus(1, 1);
}

//---------------
//void on_exit(void)
//{
//}


//中断传输调用函数
//
void usb_interrupt_transmit(void)
{
	uchar xdata key_ad[4];
/*	if(usbDemo.usb_state==USB_UNOPEN)
	{
		beep(1);
		return;
	}
*/
	
//发数据****************************

	key_ad[0] = HEAD_KEY;					//0字头的中断传输数据代表是键盘AD值
	key_ad[1] = getkey_usb(1000);	//键值
	key_ad[2] = get_ad(1);			//当前亮度

	if ( key_ad[1] != 0)             //如果按键没变化,就代表没有按下
		usbDemo.key=key_ad[1];
	if ( usbDemo.key=='C')
		usbDemo.usb_state=USB_UNOPEN;

	key_ad[1] = usbDemo.key;			//发送的是最上次的按键值		
	D12_WriteEndpoint(3, 4, key_ad);		//写端点索引3,4个字节
	
//收数据********************************
	if(bEPPflags.bits.ep1_rxdone) {    //如果端点1OUT有请求
		DISABLE;                       //
		bEPPflags.bits.ep1_rxdone = 0; //设置状态位 
		
		//判断PC包头
		switch(GenEpBuf[0])
		{
			case HEAD_KEY:				//PC的按键
				show_pc_key(GenEpBuf[1]);break;

			case READ_FLASH_FROM:		//读FLASH,起始包
				if(GenEpBuf[4]!=READ_FLASH_FROM2)
					break;					//这里其实需要判断2个字节才确定是读FLASH请求
				usbDemo.read_flash_begin=(ulong)GenEpBuf[1] + (((ulong)GenEpBuf[2])<<8) + (((ulong)GenEpBuf[3])<<16);
				usbDemo.read_flash_end  =(ulong)GenEpBuf[5] + (((ulong)GenEpBuf[6])<<8) + (((ulong)GenEpBuf[7])<<16);
				if(usbDemo.read_flash_end<MAX_FLASH_SIZE)
					bEPPflags.bits.read_flash=1;			//置开始读FLASH标志
				break;

			case READ_FLASH_STOP:			//终止读FLASH
				bEPPflags.bits.read_flash=0;	
				break;

			case HEAD_END:				//关闭USB功能,并关闭连接
				if( GenEpBuf[1]==0x55 && GenEpBuf[2]==0xaa  && GenEpBuf[3]==0x10)//自定义的数据包,收到后用于关闭USB
				usbDemo.usb_state=USB_UNOPEN;
				break;

			default:
				break;
				
		}	
		ENABLE;

	}
		
}
//--------------------------
void init_unconfig(void)
{
	//uchar i;

	D12_SetEndpointEnable(0);	/* Disable all endpoints but EPP0. */
}

void init_config(void)
{
	D12_SetEndpointEnable(1);	/* Enable  generic/iso endpoints. */
}
//--------------------------

void single_transmit(uchar * buf, uchar len)
{
	if( len <= EP0_PACKET_SIZE) {
		D12_WriteEndpoint(1, len, buf);
	}
}

void code_transmit(uchar code * pRomData, unsigned short len)
{
	ControlData.wCount = 0;
	if(ControlData.wLength > len)
		ControlData.wLength = len;

	ControlData.pData = pRomData;
	if( ControlData.wLength >= EP0_PACKET_SIZE) {	// 如果发送代码大于包长度
		D12_WriteEndpoint(1, EP0_PACKET_SIZE, ControlData.pData);
		ControlData.wCount += EP0_PACKET_SIZE;

		DISABLE;
		bEPPflags.bits.control_state = USB_TRANSMIT;
		ENABLE;
	}
	else {						//发送代码小于包长度
		D12_WriteEndpoint(1, ControlData.wLength, pRomData);
		ControlData.wCount += ControlData.wLength;
		DISABLE;
		bEPPflags.bits.control_state = USB_IDLE;
		ENABLE;
	}
}

//---------------------------
/*
void setup_dma()
{
	ioSize = ioRequest.uSize;
	ioCount = 0;

	DISABLE;
	bEPPflags.bits.dma_state = DMA_RUNNING;
	ENABLE;

	single_transmit(0, 0);

	if(ioRequest.bCommand & 0x1) {
		if(ioSize > 64 || ioSize == 0) {
			//if(bNoRAM)
				D12_WriteEndpoint(5, 64, EpBuf);
			//else
			//	D12_WriteEndpoint(5, 64, MainEpBuf);
			ioCount += 64;
		}
		else {
			//if(bNoRAM)
				D12_WriteEndpoint(5, ioSize, EpBuf);
			//else
			//	D12_WriteEndpoint(5, ioSize, MainEpBuf);
			ioCount += ioSize;
		}
	}
}
*/
//------------------------------
void control_handler()
{
	uchar type, req;

	type = ControlData.DeviceRequest.bmRequestType & USB_REQUEST_TYPE_MASK;	//0x60
	req = ControlData.DeviceRequest.bRequest & USB_REQUEST_MASK;		//0x0F

	//help_devreq(type, req); // print out device request

	if (type == USB_STANDARD_REQUEST)
		(*StandardDeviceRequest[req])();
	else if (type == USB_VENDOR_REQUEST)
		(*VendorDeviceRequest[req])();
	else
		stall_ep0();

}

⌨️ 快捷键说明

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