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

📄 main.c

📁 使用Atmel Mega48开发的USB 接口的HID设备源码
💻 C
字号:
/* Name: main.c * Project: AVR USB driver for CDC interface on Low-Speed USB * Author: Osamu Tamura * Creation Date: 2006-05-12 * Tabsize: 4 * Copyright: (c) 2006 by Recursion Co., Ltd. * License: Proprietary, free under certain conditions. See Documentation. *
 * 2006-07-08   removed zero-sized receive block
 * 2006-07-08   adapted to higher baud rate by T.Kitazawa
 *
 */#include <avr/io.h>#include <avr/interrupt.h>#include <avr/pgmspace.h>#include <avr/wdt.h>#include <avr/iomx8.h>
#include <avr/signal.h>
#include "usbdrv.h"#include "oddebug.h"#include "uart.h"

//use PORTC and PORTB
#define SPORTC 	PORTC
#define SDDRC   DDRC
#define SPINC	PINC

#define SPORTB	PORTB
#define SDDRB	DDRB
#define SPINB	PINB


#define DO		0x02
#define	SS		0x01

#define DI		0x10
#define	SCK		0x20
#define STAT1 	0x02
#define STAT2	0x01
	

extern uchar Cmd;
extern uchar  m_tmpbuffer[64];
extern uchar *m_buffer;
extern uchar	flag1;
extern uchar	Dflag;

uchar	DI_status;
uchar spidat;
uchar Tflag;
uchar	lenth=0;
uchar	j=0;
uchar	k=0;enum {    SEND_ENCAPSULATED_COMMAND = 0,    GET_ENCAPSULATED_RESPONSE,    SET_COMM_FEATURE,    GET_COMM_FEATURE,    CLEAR_COMM_FEATURE,    SET_LINE_CODING = 0x20,    GET_LINE_CODING,    SET_CONTROL_LINE_STATE,    SEND_BREAK};char usbDescrConfig[] PROGMEM = {    /* USB configuration descriptor */    9,          /* sizeof(usbDescrConfig): length of descriptor in bytes */    USBDESCR_CONFIG,    /* descriptor type */    USB_CFG_EXTERNAL_CONFIG_DESCRIPTOR_LENGH,    0,          /* total length of data returned (including inlined descriptors) */    2,          /* number of interfaces in this configuration */    1,          /* index of this configuration */    0,          /* configuration name string index */#if USB_CFG_IS_SELF_POWERED    USBATTR_SELFPOWER,  /* attributes */#else    USBATTR_BUSPOWER,   /* attributes */#endif    USB_CFG_MAX_BUS_POWER/2,            /* max USB current in 2mA units */    /* interface descriptor follows inline: */    9,          /* sizeof(usbDescrInterface): length of descriptor in bytes */    USBDESCR_INTERFACE, /* descriptor type */    0,          /* index of this interface */    0,          /* alternate setting for this interface */    USB_CFG_HAVE_INTRIN_ENDPOINT,   /* endpoints excl 0: number of endpoint descriptors to follow */    USB_CFG_INTERFACE_CLASS,    USB_CFG_INTERFACE_SUBCLASS,    USB_CFG_INTERFACE_PROTOCOL,    0,          /* string index for interface */    /* CDC Class-Specific descriptor */    5,           /* sizeof(usbDescrCDC_HeaderFn): length of descriptor in bytes */    0x24,        /* descriptor type */    0,           /* header functional descriptor */    0x10, 0x01,    4,           /* sizeof(usbDescrCDC_AcmFn): length of descriptor in bytes */    0x24,        /* descriptor type */    2,           /* abstract control management functional descriptor */    0x02,        /* SET_LINE_CODING,    GET_LINE_CODING, SET_CONTROL_LINE_STATE    */    5,           /* sizeof(usbDescrCDC_UnionFn): length of descriptor in bytes */    0x24,        /* descriptor type */    6,           /* union functional descriptor */    0,           /* CDC_COMM_INTF_ID */    1,           /* CDC_DATA_INTF_ID */    5,           /* sizeof(usbDescrCDC_CallMgtFn): length of descriptor in bytes */    0x24,        /* descriptor type */    1,           /* call management functional descriptor */    3,           /* allow management on data interface, handles call management by itself */    1,           /* CDC_DATA_INTF_ID */    /* Endpoint Descriptor */    7,           /* sizeof(usbDescrEndpoint) */    USBDESCR_ENDPOINT,  /* descriptor type = endpoint */    0x83,        /* IN endpoint number 3 */    0x03,        /* attrib: Interrupt endpoint */    8, 0,        /* maximum packet size */    100,         /* in ms */    /* Interface Descriptor  */    9,           /* sizeof(usbDescrInterface): length of descriptor in bytes */    4,           /* descriptor type */    1,           /* index of this interface */    0,           /* alternate setting for this interface */    2,           /* endpoints excl 0: number of endpoint descriptors to follow */    0x0A,        /* Data Interface Class Codes */    0,    0,           /* Data Interface Class Protocol Codes */    0,           /* string index for interface */    /* Endpoint Descriptor */    7,           /* sizeof(usbDescrEndpoint) */    USBDESCR_ENDPOINT,  /* descriptor type = endpoint */    0x01,        /* OUT endpoint number 1 */    0x02,        /* attrib: Bulk endpoint */    8, 0,        /* maximum packet size */    0,           /* in ms */    /* Endpoint Descriptor */    7,           /* sizeof(usbDescrEndpoint) */    USBDESCR_ENDPOINT,  /* descriptor type = endpoint */    0x81,        /* IN endpoint number 1 */    0x02,        /* attrib: Bulk endpoint */    8, 0,        /* maximum packet size */    0,           /* in ms */};static uchar        intr3Status;    /* used to control interrupt endpoint transmissions *//* ------------------------------------------------------------------------- *//* ----------------------------- USB interface ----------------------------- *//* ------------------------------------------------------------------------- */uchar usbFunctionSetup(uchar data[8]){usbRequest_t    *rq = (void *)data;    if((rq->bmRequestType & USBRQ_TYPE_MASK) == USBRQ_TYPE_CLASS){    /* class request type */        if( rq->bRequest==GET_LINE_CODING || rq->bRequest==SET_LINE_CODING ){            return 0xff;        /*    GET_LINE_CODING -> usbFunctionRead()    */        /*    SET_LINE_CODING -> usbFunctionWrite()    */        }        if(rq->bRequest == SET_CONTROL_LINE_STATE){            /* Report serial state (carrier detect). On several Unix platforms,             * tty devices can only be opened when carrier detect is set.             */            intr3Status = 2;        }    }    return 0;}/*---------------------------------------------------------------------------*//* usbFunctionRead                                                          *//*---------------------------------------------------------------------------*/uchar usbFunctionRead( uchar *data, uchar len ){//    data[0] = baud.bytes[0];//    data[1] = baud.bytes[1];//    data[2] = baud.bytes[2];
//    data[3] = baud.bytes[3];
//    data[4] = stopbit;//    data[5] = parity;//    data[6] = databit;    return 7;}/*---------------------------------------------------------------------------*//* usbFunctionWrite                                                          *//*---------------------------------------------------------------------------*/uchar usbFunctionWrite( uchar *data, uchar len ){    /*    SET_LINE_CODING    *///    baud.bytes[0] = data[0];//    baud.bytes[1] = data[1];//    baud.bytes[2] = data[2];
//    baud.bytes[3] = data[3];
//#if USB_CFG_HAVE_USART//    stopbit    = data[4];//    parity     = data[5];//    databit    = data[6];//    if( parity>2 )//        parity    = 0;//    if( stopbit==1 )//        stopbit    = 0;//#endif//    resetUart();    return 1;}void usbFunctionWriteOut( uchar *data, uchar len ){    /*    usb -> rs232c:  transmit char    */    //usbDisableAllRequests();//    for( ; len; len-- ) {//       uartTxBufAppend(*data++);//    }}static void hardwareInit(void){uchar    i, j;    /* activate pull-ups except on USB lines */    USB_CFG_IOPORT   = (uchar)~((1<<USB_CFG_DMINUS_BIT)|(1<<USB_CFG_DPLUS_BIT)|1<<2);	//PORTD2=INT0    /* all pins input except USB (-> USB reset) */#ifdef USB_CFG_PULLUP_IOPORT    /* use usbDeviceConnect()/usbDeviceDisconnect() if available */    USBDDR    = 0;    /* we do RESET by deactivating pullup */    usbDeviceDisconnect();#else    USBDDR    = (1<<USB_CFG_DMINUS_BIT)|(1<<USB_CFG_DPLUS_BIT);#endif    j = 0;    while(--j){          /* USB Reset by device only required on Watchdog Reset */        i = 0;        while(--i);      /* delay >10ms for USB reset */    }#ifdef USB_CFG_PULLUP_IOPORT    usbDeviceConnect();#else    USBDDR    = 0;      /*  remove USB reset condition */#endif
    /*    USART configuration    */}
#define  DO_H			SPORTC|=DO			// MOSI out 1

#define  DO_L		    SPORTC&=~DO			//MOSI out 0

#define  SS_H			SPORTC|=SS			//SS out 1

#define  SS_L      		SPORTC&=~SS      		//SS out 0

#define  SCK_H     		SPORTB|=SCK			//SCK out 1

#define  SCK_L			SPORTB&=~SCK			//SCK out 0

void delay (void)
{

	uchar k;
	for(k=0;k<20;k++)
	{

	}

}


uchar DI_IN()					//DI status
{
	uchar tmp=0;
	SCK_H;
	//delay();
	if((SPINB&DI)==0x10)
		tmp=0x01;
	else
	    tmp=0;
	SCK_L;
	//delay();
	return tmp;		

}


// send a byte
void send_spi(uchar dat)
{
	uchar i,dat1;
	for(i=0;i<8;i++)
		{
		dat1=dat;
		if((dat1&0x80)==0x80)
			{
			DO_H;
			SCK_H;
			delay();
			SCK_L;
			delay();
			}
		else
			{
			DO_L;
			SCK_H;
			delay();
			SCK_L;
			delay();
			}
		dat=dat<<1;
	}
}

rev_spi()         //recive 1 byte
{
	uchar i,rev;
	spidat=0;
	for(i=0;i<7;i++)
	{
		rev=DI_IN();
		if(rev) spidat|=0x01;
		spidat=spidat<<1;
	}
	rev=DI_IN();
	if(rev) spidat|=0x01;

}

//#pragma interrupt_handler timer1_isr:0x0D


 SIGNAL(SIG_OVERFLOW1)
{

	TCCR1B=0;				//close timer1
	Tflag=0;
	
}

void init_timer1(void)
{

	TCNT1H=0xFE;
	TCNT1L=0xC2;			//27ms
	TIMSK1=0x01;
	SREG|=0x80;


}
/*
void init_timer2(void)
{

	TCNT1H=0xFF;
	TCNT1L=0x87;			//10ms
	TIMSK1=0x01;
	SREG|=0x80;


}
*/
int main(void){	//uchar bytesRead, *data;
	uchar temp,temp1,temp2;
	unsigned long tm1;
	Cmd=0;
	DI_status=DI_IN();
	Dflag=0;
	temp=DI_status;
	temp2=DI_status;
	

	SDDRC|=(SS+DO);				//SS/DO= out
	SDDRB|=SCK;					//SCK=out
	 
	SDDRB&=~(DI+STAT1+STAT2);					//DI/STAT1/STAT2=in


	//mode 0
	SPORTC|=SS;					//ss out=1
	SPORTB&=~SCK;				//SCK out=0

	SPORTB|=(DI+STAT1+STAT2);					//DI pull_up

	
	wdt_enable(WDTO_1S);    hardwareInit();
    usbInit();
    sei();    usbSetInterrupt(0, 0);  /* the host eats the first packet -- don't know why... */

   for(;;){    /* main event loop */        wdt_reset();        usbPoll();

//-------------CHECK DI----
		temp2=DI_IN();
		temp=DI_status;
		if(temp2!=temp)
		{
			tm1=0x000fffff;
			//Tflag=1;
			//init_timer1();			//init timer1
			//TCCR1B=0x05;  		//open tiner1 delay 10ms
			//temp=Tflag;
			/*
			while(1)
			{
			if(temp==0) break;
			//temp=Tflag;
			
			}*/
			do
			{
				tm1--;
			}while(tm1!=0);
			//TCCR1B=0;
			temp=DI_IN();		//delay DI is chang
			if(temp2==temp) DI_status=DI_IN();



		}
//--------------------------

//send SPI data
	if(Cmd==1)								//has CMD SEND SPI data
		{
			Cmd=0;								//clear CMD_flg
			lenth=0;
			temp=0;
			//STATUT is High redeay recive
			temp=SPINB&STAT1;
			if(temp==0x02)					//STAT1=H,send data to RF_Model
			{
		
				for(j=0;j<6;j++)
				{
				   if(m_tmpbuffer[j]!=0xb3) break;
				}
					
					temp=m_tmpbuffer[j];			//length
					temp1=~(m_tmpbuffer[j+1]);		//~Length
					if(temp==temp1)
					{

//----------------------
						if(m_tmpbuffer[j+2]==0x05)
						{
							Dflag=1;					//get DI_Statuts
							m_buffer=m_tmpbuffer;
							*(m_buffer+6)=DI_status;
							
						
						}

						else
//-----------------------------------
						{
						lenth=temp+5;
						SS_L;					//SS ready	
						delay();	
						m_buffer=m_tmpbuffer;
						for(j=0;j<lenth;j++)
							{
					
						  		temp=*m_buffer++ ;
						  		send_spi(temp);
						  						
							}
						}
										
					 }	
				}	
				
			if(Dflag!=1)		
			
			//wait recive RF_Model data    STAT=L recive SPI_DATA
			{
		
				flag1=0;				//when recevie RF data USB return 0 pack
				init_timer1();			//init timer1
				Tflag=1;
				TCCR1B=0x05;           //open timer1

				while(Tflag==1)
				{

					if((SPINB&STAT1)==0x0) 
					{
					 	TCCR1B=0;				//close timer1
						Tflag=0;	
					
						m_buffer=m_tmpbuffer;
						while((SPINB&STAT1)==0)
						{
						rev_spi();
						*m_buffer++=spidat;
						}
						
						flag1=1;

					}
				
				}

				SS_H;
				
			}
		


			
		} 


//--------------------------

    }    return 0;}

⌨️ 快捷键说明

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