📄 fm1702.c
字号:
#include <msp430x41x.h>
static unsigned char DataBuffer[16]; //接收和发送数据缓冲区
static union NewUser
{ unsigned long Long;
unsigned char Byte[4];
}NewUser;
static union OldUser
{ unsigned long Long;
unsigned char Byte[4];
}OldUser;
static unsigned char Table[4]; //地址分配表
static unsigned char CardSnr[5]; //卡片序列号
static unsigned char Random[4]; //0扇区 块2下的随机数
static unsigned char CardKey[6] = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}; //默认卡片密码
/*********************FM1702通讯时返回的错误代码*********************/
#define MI_OK 0
#define MI_NOTHERE 1
#define MI_ERR 2
/************************FM1702 FIFO长度定义*************************/
#define DEF_FIFO_LENGTH 64 //FIFO size=64byte
#define MAXRLEN 18 //数据长度18字节
/****************************端口定义*******************************/
#define RST_1 P1OUT |= BIT0
#define RST_0 P1OUT &=~ BIT0
#define SCK_1 P1OUT |= BIT1
#define SCK_0 P1OUT &=~ BIT1
#define SO ((P1IN >> 2) & 0x01)
#define SI_1 P1OUT |= BIT3
#define SI_0 P1OUT &=~ BIT3
#define NSS_1 P1OUT |= BIT4
#define NSS_0 P1OUT &=~ BIT4
/****************************FM1702命令字***************************/
#define Idle 0x00 //取消当前命令
#define Transmit 0x1A //发送命令
#define Receive 0x16 //接收数据
#define Transceive 0x1E //发送并接收数据
#define WriteE2 0x01 //写FM1702EEPROM
#define ReadE2 0x03 //读FM1702EEPROM
#define LoadKeyE2 0x0B //将密钥从EEPROM复制到KEY缓存
#define LoadKey 0x19 //将密钥从FIFO复制到KEY缓存
#define Authent1 0x0C //认证过程1
#define Authent2 0x14 //认证过程2
/*************************Mifare_One卡片命令字**********************/
#define REQIDL 0x26 //寻天线区内未进入休眠状态
#define REQALL 0x52 //寻天线区内全部卡
#define ANTICOLL 0x93 //防冲撞
#define SELECT 0x93 //选择卡片
#define AUTHENTA 0x60 //验证A密钥
#define AUTHENTB 0x61 //验证B密钥
#define READ 0x30 //读块
#define WRITE 0xA0 //写块
#define DECREMENT 0xC0 //扣款
#define INCREMENT 0xC1 //充值
#define PRESTORE 0xC2 //调块数据到缓冲区
#define TRANSFER 0xB0 //保存缓冲区中数据
#define HALT 0x50 //休眠
/*************************FM1702寄存器定义**********************/
#define Page 0x00 //选择寄存器组
#define Command 0x01 //指令寄存器
#define FIFOData 0x02 //64byte FIFO 的输入输出寄存器
#define PrimaryStatus 0x03 //发射器接收器及FIFO 的标识位寄存器
#define FIFOLength 0x04 //当前FIFO 内byte数
#define SecondaryStatus 0x05 //各种状态标识寄存器
#define InterruptEn 0x06 //中断使能/禁止控制寄存器
#define InterruptRq 0x07 //中断请求标识寄存器
#define Control 0x09 //各种控制标识寄存器
#define ErrorFlag 0x0A //上一条指令结束后错误标识
#define CollPos 0x0B //侦测到的第一个冲突位的位置
#define TimerValue 0x0C //当前Timer值
#define CRCResultLSB 0x0D //协处理器低8位
#define CRCResultMSB 0x0E //协处理器高8位
#define BitFraming 0x0F //调整面向bit的帧格式
#define TxControl 0x11 //发射器控制寄存器
#define CWConductance 0x12 //选择发射脚TX1和TX2发射天线的阻抗
#define ModConductance 0x13 //预设寄存器不要改变内容
#define PreSet14 0x14 //预设寄存器不要改变内容
#define ModWidth 0x15 //选择载波调制宽度
#define PreSet16 0x16 //预设寄存器不要改变内容
#define PreSet17 0x17 //预设寄存器不要改变内容
#define RXControl1 0x19 //接收器控制寄存器
#define DecoderControl 0x1A //解码控制寄存器
#define BitPhase 0x1B //调整发射器和接收器时钟相差
#define Rxthreshold 0x1C //选择bit解码的阈值
#define PreSet1D 0x1D //预设寄存器不要改变内容
#define RxControl2 0x1E //解码控制及选择接收源
#define ClockQControl 0x1F //时钟产生控制寄存器
#define RxWait 0x21 //选择发射和接收之间的时间间隔
#define ChannelRedundancy 0x22 //选择数据校验种类和模式
#define CRCPresetLSB 0x23 //预置寄存器低8位
#define CRCPresetMSB 0x24 //预置寄存器高8位
#define PreSet25 0x25 //预设寄存器不要改变内容
#define MFOUTSelect 0x26 //选择MFOUT 信号源
#define PreSet27 0x27 //预设寄存器不要改变内容
#define FIFOLevel 0x29 //定义FIFO 溢出级别
#define TimerClock 0x2A //选择Timer时钟的分频
#define TimerControl 0x2B //选择Timer启动/停止条件
#define TimerReload 0x2C //Timer预置值
#define IRQPinConfig 0x2D //IRQ 输
#define TypeSH 0x31 //上海标准选择寄存器
#define TestDigiSelect 0x3D //测试管脚配置寄存器
/****************************************************************/
/*名称: Send_1_Char */
/*功能: 向FM1702发送1个字节 */
/*输入: Data-发送的值 */
/*输出: N/A */
/****************************************************************/
void Send_1_Char(unsigned char Data)
{
unsigned char i,Temp;
for (i=0;i<8;i++)
{
delay(10);
Temp=Data&0x80;
if (Temp==0x80)
SI_1;
else SI_0;
delay(10);
SCK_1;
Data<<=1;
delay(10);
SCK_0;
}
}
/****************************************************************/
/*名称: Rec_1_Char */
/*功能: 接收FM1702发送的1个字节 */
/*输入: N/A */
/*输出: 读出的值 */
/****************************************************************/
unsigned char Rec_1_Char(void)
{
unsigned char i,Temp=0;
for (i = 0; i < 8; i++)
{//接收FM1702发送1个字节
Temp <<= 1;
Temp |=SO;
SCK_1;
delay(10);
SCK_0;
}
return Temp;
}
/****************************************************************/
/*名称: ReadReg */
/*功能: 读FM1702寄存器 */
/*输入: Address-寄存器地址 */
/*输出: 读出的值 */
/****************************************************************/
unsigned char ReadReg(unsigned char Address)
{
unsigned char Temp;
Address=(Address<<1)|0x80;
NSS_0;
Send_1_Char(Address);
Temp=Rec_1_Char();
NSS_1;
return Temp;
}
/****************************************************************/
/*名称: WriteReg */
/*功能: 写FM1702寄存器 */
/*输入: Address - 寄存器地址; value - 写入的值 */
/*输出: N/A */
/****************************************************************/
void WriteReg(unsigned char Address, unsigned char Data)
{
Address = ((Address<<1)&0x7E);
NSS_0;
Send_1_Char(Address);
Send_1_Char(Data);
NSS_1;
}
/****************************************************************/
/*名称: Clear_FIFO */
/*功能: 清除FIFO数据 */
/*输入: N/A */
/*输出: N/A */
/****************************************************************/
void Clear_FIFO(void)
{
unsigned char i=0,Temp;
Temp =ReadReg(Control); //清空FIFO
Temp = (Temp | 0x01);
WriteReg(Control, Temp);
do{
if(ReadReg(FIFOLength)==0)
break;
}while(i++<200);
}
/****************************************************************/
/*名称: Write_FIFO */
/*功能: 写FIFO数据 */
/*输入: N/A */
/*输出: N/A */
/****************************************************************/
void Write_FIFO(unsigned char Number)
{
unsigned char i;
if(Number>0)
{
for (i=0; i<Number; i++)
WriteReg(FIFOData, DataBuffer[i]);
}
}
/****************************************************************/
/*名称: Read_FIFO */
/*功能: 读FIFO数据 */
/*输入: N/A */
/*输出: N/A */
/****************************************************************/
void Read_FIFO(void)
{
unsigned char i,Temp;
Temp=ReadReg(FIFOLength);
if(Temp>18)
Temp=18;
for (i=0; i<Temp; i++)
DataBuffer[i]=ReadReg(FIFOData);
}
/****************************************************************/
/*名称: Command_Send */
/*功能: 通过FM1702和ISO14443卡通讯 */
/*输入: Comm_Code-命令码;Number-数据个数 */
/*输出: N/A */
/****************************************************************/
void Command_Send(unsigned char Number,unsigned char Comm_Code)
{
unsigned char i=0,RetChar;
WriteReg(Command,Idle); //结束当前指令
Clear_FIFO(); //清除FIFO
Write_FIFO(Number);
ReadReg(FIFOLength);
WriteReg(Command, Comm_Code); //发送命令码
do
{
delay(10);
RetChar=ReadReg(Command);
if(RetChar==0)
break;
}while(i++<10);
}
/****************************************************************/
/*名称: FM1702Reset */
/*功能: 复位FM1702 */
/*输入: N/A */
/*输出: N/A */
/****************************************************************/
void FM1702Reset(void)
{
unsigned char Temp;
RST_1;
delay(10);
RST_0;
delay(10);
Temp=ReadReg(0x01);
while(Temp!=0x00) Temp=ReadReg(0x01);
WriteReg(Page,0x80);//总线选择
Temp=ReadReg(0x01);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -