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

📄 trf7960.c

📁 TRF7960源代码
💻 C
📖 第 1 页 / 共 2 页
字号:


#include "TRF7960.h"
#include <avr/delay.h>
#include <avr/crc16.h>
#include <avr/signal.h>
#include <avr/interrupt.h>

volatile char IRQ_Status=0;
//volatile char *cFIFO_Data[30];
//volatile char cFIFO_Len;


/*
//计算CRC16
unsigned int calcrc(unsigned char *ptr, unsigned char count)
{
    unsigned int crc = 0;
    while (count--)
    {
        crc =_crc16_update(crc,*ptr++);
    }
    return crc;
}
*/

// get data from TRF7963
char Data_Input(void)
{
	char data=0;
	
	// data5-0 input, 上拉使能
	DDRC &= ~AD5_AD0;
	//PORTC |= (1<<AD0)|(1<<AD1)|(1<<AD2)|(1<<AD3);
	
	// data7-6 input, 上拉使能
	DDRB &= ~AD7_AD6;
	//PORTB |= (1<<AD4)|(1<<AD5)|(1<<AD6)|(1<<AD7);
	
	DelayUs(10);
	
	data |= (PINC & AD5_AD0);// bit5-0
	data |= ( (PINB & AD7_AD6)<<6 );// bit7-6
	
	return data;
}


// put data to TRF7963
char Data_Output(char data)
{
	// output data5-0
	DDRC |= AD5_AD0;
	PORTC = (PORTC & (~AD5_AD0)) | (data & AD5_AD0);
	
	// output data7-6
	DDRB |= AD7_AD6;
	PORTB = (PORTB & (~AD7_AD6)) | (data>>6);
	
	DelayUs(10);
	
	return data;
}


void CLK_Low(void)
{
	// DATA_CLK output low
	PORTB &= ~(1<<DATA_CLK);
	DelayUs(10);
}

void CLK_High(void)
{
	// DATA_CLK output high
	PORTB |= (1<<DATA_CLK);
	DelayUs(10);
}

void Start_Condition(void)
{
	// start condition
	CLK_High();
	Data_Output(0x00);
	Data_Output(0xFF);
	CLK_Low();
}

void Stop_Condition(void)
{
	// stop condition
	CLK_High();
	Data_Output(0xFF);	
	Data_Output(0x00);
	CLK_Low();
}


void Stop_Continue(void)
{
	// stop continue condition
	CLK_Low();
	Data_Output(0x00);
	Data_Output(0xFF);
	Data_Output(0x00);
}


// put cmd to TRF7963
void TRF7963_cmd(char cCmd)
{
	// start condition
	Start_Condition();

	// addr, data or cmd
	Data_Output(cCmd|TRF7963_CMD);
	CLK_High();
	CLK_Low();
	
	// stop condition
	Stop_Condition();
}



// get data from TRF7963
char TRF7963_getc(char cAddr)
{
	char cTmp;
	
	// start condition
	Start_Condition();
	
	// addr
	Data_Output(cAddr|TRF7963_READ);
	CLK_High();
	CLK_Low();
	
	// get data
	CLK_High();
	cTmp = Data_Input();
	CLK_Low();
	
	// stop condition
	Stop_Condition();
	
	return cTmp;
}


int TRF7963_gets(char cAddr, char *cData, int length)
{
	int i;

	// start continue condition
	Start_Condition();

	// addr
	Data_Output(cAddr | TRF7963_READ | TRF7963_CON_MODE);
	CLK_High();
	CLK_Low();

	// get data
	for (i=0; i<length; i++)
	{
		CLK_High();
		cData[i] = Data_Input();
		CLK_Low();
	}

	// stop continue condition
	Stop_Continue();

	return i;
}


// put cmd to TRF7963
void TRF7963_putc(char cAddr, char cData)
{
	// start condition
	Start_Condition();

	// addr
	Data_Output(cAddr);
	CLK_High();
	CLK_Low();

	// put data
	Data_Output(cData);
	CLK_High();
	CLK_Low();
	
	// stop condition
	Stop_Condition();
}



// put addr, data or cmd to TRF7963
// cFIFO_start means the address of cData, or else 0
int TRF7963_puts(char *cData, int length, char cFIFO_start, char bDelay)
{
	int i, j;

	// start continue condition
	Start_Condition();
	
	// no FIFO data, or FIFO bytes <=12
	if( (length-cFIFO_start)<13 )
	{
		for (i=0; i<length; i++)
		{
			Data_Output(cData[i]);
			CLK_High();
			CLK_Low();
		}
	}
	else
	{
		// first 12 bytes to FIFO
		for (i=0; i<cFIFO_start+12; i++)
		{
			Data_Output(cData[i]);
			CLK_High();
			CLK_Low();
		}
		//DelayMs(500);		
		Stop_Continue();

		// wait for FIFO data sending out
		j = 0;
		while (1)
		{
			WaitforSignal(0x20, 100);		
			if (TRF7963_getc(0x1C) & 0x20)
			{
				break;
			}
			j++;
			//DelayMs(10);
			if (j == 5)
			{
				return -1;// delay 500ms, exit
			}			
		}
		
		Start_Condition();
		// addr
		Data_Output(0x3F);
		CLK_High();
		CLK_Low();		
		for (; i<length; i++)
		{		
			Data_Output(cData[i]);
			CLK_High();
			CLK_Low();		
		}
	}

	// stop continue condition
	if(bDelay)
	{
		DelayMs(10);
	}
	Stop_Continue();
	
	return i;
}


int TRF7963_Init(void)
{
	char i;

	// EN high
	DDRD |= (1<<DDD7);
	PORTD |= (1<<PD7);
	
	// ASK/OOK , 0-ASK, 1-OOK
	//DDRD |= (1<<DDD4);
	//PORTD |= (1<<PD4);
	
	// EN2 high
	DDRB |= (1<<DDD6);
	PORTB |= (1<<PD6);
	
	// DATA_CLK output
	DDRB |= (1<<DATA_CLK);

	DelayMs(10);
	
	// 
	Data_Input();
	
	TRF7963_cmd(0x03);// TRF7963 soft init
	TRF7963_putc(0, 0x21);	// TX Enbale
	DelayMs(10);
	if (TRF7963_getc(0) != 0x21)
	{
		return -1;
	}
	return 0;
	
	//TRF7963_putc(1, 0x08);	// ISO14443A
	
	// No response interrupt
	//cTmp = TRF7963_getc(0x0D);
	//cTmp |= 0x01;
	//TRF7963_putc(0x0D, cTmp);	

//	memset(cFIFO_Data, 0x00, sizeof(cFIFO_Data));
//	cFIFO_Len = 0;
}



// 0 for OK
// 0xFF for time out
char WaitforSignal(char cMask, int ms)
{
	int i=0;
	char cTmp;

	while (1)
	{
		if (IRQ_Status)
		{			
			if (IRQ_Status&cMask)
			{	
				IRQ_Status = 0;
				return 0;
			}			
			cTmp = IRQ_Status;
			IRQ_Status = 0;
			return cTmp;
		}
		else if (i++ >= ms)
		{
			break;
		}

		DelayMs(1);		
	}

	return 0xFF;
}
/*int WaitforInt(char cValue, int ms)
{
	int i=0;

	while (1)
	{
		if ((PIND&(1<<PIND3)))
		{	
			if(TRF7963_getc(0x0C) & cValue)
			{
				return 0;
			}
		}
		else if (i++ == ms)
		{
			break;
		}
		DelayMs(1);
	}

	return -1;
}*/



int GetFIFOData(char *cBuf, int nlength)
{
	char cTmp;
	int length;
		
	length = 0;


	while(1)
	{
		// Read FIFO status register to determine number of bytes in FIFO
		cTmp = TRF7963_getc(0x1C) ;
		
		if(cTmp & 0x10)
		{
			UART_puts("Over flow!\r\n");
			return 0xFF;
		}
		
		cTmp &= 0x0F;

		// Read data from FIFO
		if (cTmp)
		{
			TRF7963_gets(0x1F, cBuf+length, cTmp+1);
			length += cTmp+1;
			if (length > 256)
			{
				break;
			}
		}

		if (WaitforSignal(0x20, 300))
		{
			break;
		}

	}


//	cTmp = TRF7963_getc(0x1C)&0x0F;	
	if (length == 0)
	{
		cBuf[0] = TRF7963_getc(0x1F);
		length = 1;
	}


	// reset FIFO
	TRF7963_cmd(0x0F);
	
	return length;
}






// first call the function , must be mask_length=0, mask_value[0..8]=0, cpreSLOT_Pointer=16
// such as GetTagUID(mask_value, 0, cTagNO);
// mask_length= 4, 8, 12, 16 ...
// mask_value[0..8] half byte is: [0x0..0x0F]

// if the mask value is 25A3D, then 
// mask_value[0] = 0x3D,
// mask_value[1] = 0x5A,
// mask_value[2] = 0x02, 

// return <0, err
// return 0, no tag it
// return >0, tag NO
int GetTagUID(char *mask_value, char mask_length, char *cTagNO)
{

	char cStr[50];
	char TRF7963_FIFO[50];
	char cTmp, cTmp1;
	char cBuf[30], i, length;
	char size;
	int iTagitNUM = 0;

	IRQ_Status = 0;
	size = (mask_length+4)/8;
	memset(cBuf, 0x00, sizeof(cBuf));
	//memset(mask_value, 0x00, sizeof(mask_value));
	
	// mask depth is overlay
	if (size > 15)
	{
		return 0;
	}

	// No response interrupt
	cTmp = TRF7963_getc(0x0D);
	cTmp |= 0x01;
	TRF7963_putc(0x0D, cTmp);

	cBuf[0] = 0x8f;	// Reset FIFO command
	cBuf[1] = 0x91;	// send with CRC
	cBuf[2] = 0x3d;	// write continuous from register 1D
	cBuf[3] = (char)( (3+size)>>8 );
	cBuf[4] = (char)( (3+size)<<4 );
	cBuf[5] = 0x06;	// ISO15693 flag with 16 slots bit set
	cBuf[6] = 0x01;	// ISO15693 anti collision command code



	cBuf[7] = mask_length;		// mask length
	
	if (size > 0)
	{		
		memcpy(cBuf+8, mask_value, size);
	}



	length = 8+size;
	TRF7963_puts(cBuf, length, 5, 0);
		



	// waitfor End of transmit interrupt
	if(WaitforSignal(0x80, 100) == 0xFF)
	{	
		return -1;
	}
		
	for(i=0; i<16; i++)
	{			
		memset(cStr, 0x00, sizeof(cStr));
		
		// waitfor End of RX interrupt
		cTmp = WaitforSignal(0x40,100);
		
		if ( cTmp == 0 )
		{			
			memset(TRF7963_FIFO, 0x00, sizeof(TRF7963_FIFO));
			cTmp = GetFIFOData(TRF7963_FIFO, 0);

			if (cTmp >= 9)
			{
				cTmp = iTagitNUM;
//				for (cTmp1=2; cTmp1<10; cTmp1++)
//				{
//					cTagNO[cTmp1-2+cTmp*8] = TRF7963_FIFO[cTmp1];
//				}
				memcpy(cTagNO+iTagitNUM*8, TRF7963_FIFO+2, 8);
				iTagitNUM++;				
			}
		}
		else if (cTmp & 0x02 && i)
		{			
			cTmp = (mask_length+4)>>3;
			if (mask_length & 0x04)
			{
				mask_value[cTmp] |=  i<<4;// high 4 bits
			}
			else
			{
				mask_value[cTmp] |=  i;//low 4 bits
			}
			
			iTagitNUM += GetTagUID(mask_value, mask_length+4, cTagNO+iTagitNUM*8);

			if (mask_length & 0x04)
			{
				mask_value[cTmp] &=  0x0F;// high 4 bits
			}
			else
			{
				mask_value[cTmp] =  0;//low 4 bits
			}
		}
	
		// Reset FIFO
		TRF7963_cmd(0x0F);	
		DelayUs(50);	

		// send EOF
		TRF7963_cmd(0x16);	// Send Block RX command
		DelayUs(50);
		TRF7963_cmd(0x17); // Send Enable RX command	
		DelayUs(50);
		TRF7963_cmd(0x14); // Send Transmit Next Slot (EOF) command
	}


	// disable No response interrupt
	cTmp = TRF7963_getc(0x0D);
	cTmp &= 0xFE;
	TRF7963_putc(0x0D, cTmp);	
	
	return iTagitNUM;

}

int GetTagUID1Slot(char *cTagNO)
{

	char TRF7963_FIFO[50];
	char cTmp;
	char cBuf[30], length;
	int iTagitNUM = 0;

	IRQ_Status = 0;
	memset(cBuf, 0x00, sizeof(cBuf));

	cBuf[0] = 0x8f;	// Reset FIFO command
	cBuf[1] = 0x91;	// send with CRC
	cBuf[2] = 0x3d;	// write continuous from register 1D
	cBuf[3] = (char)( 3>>8 );
	cBuf[4] = (char)( 3<<4 );
	cBuf[5] = 0x26;	// ISO15693 flag with 16 slots bit set
	cBuf[6] = 0x01;	// ISO15693 anti collision command code



	cBuf[7] = 0;//mask_length;		// mask length
	
//	if (size > 0)
//	{		
//		memcpy(cBuf+8, mask_value, size);
//	}



	length = 8;
	TRF7963_puts(cBuf, length, 5, 0);
		


	// waitfor End of transmit interrupt
	if(WaitforSignal(0x80, 500) == 0xFF)
	{
		return -1;
	}

	// waitfor End of RX interrupt
	if(WaitforSignal(0x40, 500) == 0xFF)
	{

⌨️ 快捷键说明

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