📄 mifare.c
字号:
#include <reg52.h>
#include <string.h>
#include "main.h"
#include "mfrc500.h"
#include "mifare.h"
#define FSD 64 //RC500 FIFO BUFFER SIZE
/////////////////////////////////////////////////////////////////////
//功 能:寻卡
//参数说明: req_code[IN]:寻卡方式
// 0x52 = 寻感应区内所有符合14443A标准的卡
// 0x26 = 寻未进入休眠状态的卡
// pTagType[OUT]:卡片类型代码
// 0x4400 = Mifare_UltraLight
// 0x0400 = Mifare_One(S50)
// 0x0200 = Mifare_One(S70)
// 0x0800 = Mifare_Pro(X)
// 0x4403 = Mifare_DESFire
//返 回: 成功返回MI_OK
/////////////////////////////////////////////////////////////////////
char PcdRequest(unsigned char req_code,unsigned char *pTagType)
{
char status;
unsigned int unLen;
unsigned char idata ucComBuf[FSD];
WriteRawRC(RegChannelRedundancy,0x03);
ClearBitMask(RegControl,0x08);
WriteRawRC(RegBitFraming,0x07);
SetBitMask(RegTxControl,0x03);
PcdSetTmo(4);
ucComBuf[0] = req_code;
status = PcdComISO14443(PCD_TRANSCEIVE,ucComBuf,1,ucComBuf,&unLen);
if ((status == MI_OK) && (unLen == 0x10))
{
*pTagType = ucComBuf[0];
*(pTagType+1) = ucComBuf[1];
}
else
{ status = MI_ERR; }
return status;
}
/////////////////////////////////////////////////////////////////////
//功 能:防冲撞
//参数说明: pSnr[OUT]:卡片序列号,4字节
//返 回: 成功返回MI_OK
/////////////////////////////////////////////////////////////////////
char PcdAnticoll(unsigned char *pSnr)
{
char status ;
unsigned char i;
unsigned char ucBits;
unsigned char ucBytes;
unsigned char snr_check = 0;
unsigned char ucCollPosition = 0;
unsigned char ucLength=0;
unsigned char ucTemp;
unsigned int unLen;
unsigned char ucSNR[5] = {0, 0, 0, 0 ,0};
unsigned char idata ucComBuf[FSD];
WriteRawRC(RegDecoderControl,0x28);
ClearBitMask(RegControl,0x08);
WriteRawRC(RegChannelRedundancy,0x03);
PcdSetTmo(4);
do
{
ucBits = (ucCollPosition) % 8;
if (ucBits != 0)
{
ucBytes = ucCollPosition / 8 + 1;
WriteRawRC(RegBitFraming, (ucBits << 4) + ucBits);
}
else
{
ucBytes = ucCollPosition / 8;
}
ucComBuf[0] = PICC_ANTICOLL1;
ucComBuf[1] = 0x20 + ((ucCollPosition / 8) << 4) + (ucBits & 0x0F);
for (i=0; i<ucBytes; i++)
{
ucComBuf[i + 2] = ucSNR[i];
}
ucLength = ucBytes + 2;
status = PcdComISO14443(PCD_TRANSCEIVE,ucComBuf,ucLength,ucComBuf,&unLen);
ucTemp = ucSNR[(ucCollPosition / 8)];
if (status == MI_COLLERR)
{
for (i=0; i < 5 - (ucCollPosition / 8); i++)
{
ucSNR[i + (ucCollPosition / 8)] = ucComBuf[i+1];
}
ucSNR[(ucCollPosition / 8)] |= ucTemp;
ucCollPosition = ucComBuf[0];
}
else if (status == MI_OK)
{
for (i=0; i < (unLen / 8); i++)
{
ucSNR[4 - i] = ucComBuf[unLen/8 - i - 1];
}
ucSNR[(ucCollPosition / 8)] |= ucTemp;
}
} while (status == MI_COLLERR);
if (status == MI_OK)
{
for (i=0; i<4; i++)
{
*(pSnr+i) = ucSNR[i];
snr_check ^= ucSNR[i];
}
if (snr_check != ucSNR[i])
{ status = MI_ERR; }
}
ClearBitMask(RegDecoderControl,0x20);
return status;
}
////////////////////////////////////////////////////////////////////
//功 能:选定卡片
//参数说明: pSnr[IN]:卡片序列号,4字节
//返 回: 成功返回MI_OK
/////////////////////////////////////////////////////////////////////
char PcdSelect(unsigned char *pSnr)
{
char status ;
unsigned char i, snr_check = 0;
unsigned int unLen;
unsigned char idata ucComBuf[FSD];
WriteRawRC(RegChannelRedundancy,0x0F);
ClearBitMask(RegControl,0x08);
PcdSetTmo(4);
ucComBuf[0] = PICC_ANTICOLL1;
ucComBuf[1] = 0x70;
for (i=0; i<4; i++)
{
snr_check ^= *(pSnr+i);
ucComBuf[i+2] = *(pSnr+i);
}
ucComBuf[6] = snr_check;
status = PcdComISO14443(PCD_TRANSCEIVE,ucComBuf,7,ucComBuf,&unLen);
if ((status == MI_OK) && (unLen == 0x08))
{ status = MI_OK; }
else
{ status = MI_ERR; }
return status;
}
/////////////////////////////////////////////////////////////////////
//功 能:将Mifare_One卡密钥转换为RC500接收格式
//参数说明:uncoded[IN]:6字节未转换的密钥
// coded[OUT]:12字节转换后的密钥
//返 回: 成功返回MI_OK
/////////////////////////////////////////////////////////////////////
char ChangeCodeKey(unsigned char *uncoded,unsigned char *coded)
{
unsigned char cnt=0;
unsigned char ln=0;
unsigned char hn=0;
for (cnt=0; cnt<6; cnt++)
{
ln = uncoded[cnt] & 0x0F;
hn = uncoded[cnt] >> 4;
coded[cnt*2+1] = (~ln<<4) | ln;
coded[cnt*2] = (~hn<<4) | hn;
}
return MI_OK;
}
/*
/////////////////////////////////////////////////////////////////////
//功 能:将存在RC500的EEPROM中的密钥匙调入RC500的FIFO
//参数说明:addr[IN]:EEPROM地址
//返 回: 成功返回MI_OK
/////////////////////////////////////////////////////////////////////
char PcdLoadKeyE2(unsigned int addr)
{
char status ;
unsigned int unLen;
unsigned char idata ucComBuf[FSD];
ucComBuf[0] = addr & 0xFF;
ucComBuf[1] = (addr >> 8) & 0xFF;
status = PcdComISO14443(PCD_LOADKEYE2,ucComBuf,2,ucComBuf,&unLen);
return status;
}
*/
/////////////////////////////////////////////////////////////////////
//功 能:将已转换格式后的密钥送到RC500的FIFO中
//参数说明:pKey[IN]:密钥
//返 回: 成功返回MI_OK
/////////////////////////////////////////////////////////////////////
char PcdAuthKey(unsigned char *pKey)
{
char status;
unsigned int unLen;
unsigned char idata ucComBuf[FSD];
PcdSetTmo(4);
memcpy(ucComBuf, pKey, 12);
status = PcdComISO14443(PCD_LOADKEY,ucComBuf,12,ucComBuf,&unLen);
return status;
}
/////////////////////////////////////////////////////////////////////
//功 能:验证卡片密码
//参数说明: auth_mode[IN]: 密码验证模式
// 0x60 = 验证A密钥
// 0x61 = 验证B密钥
// addr[IN]:块地址
// pSnr[IN]:卡片序列号,4字节
//返 回: 成功返回MI_OK
/////////////////////////////////////////////////////////////////////
char PcdAuthState(unsigned char auth_mode,unsigned char addr,unsigned char *pSnr)
{
char status;
unsigned int unLen;
unsigned char idata ucComBuf[FSD];
PcdSetTmo(4);
ucComBuf[0] = auth_mode;
ucComBuf[1] = addr;
memcpy(&ucComBuf[2], pSnr, 4);
status = PcdComISO14443(PCD_AUTHENT1,ucComBuf,6,ucComBuf,&unLen);
if ((status == MI_OK) && !(ReadRawRC(RegSecondaryStatus) & 0x07))
{
status = PcdComISO14443(PCD_AUTHENT2,ucComBuf,0,ucComBuf,&unLen);
if ((status == MI_OK) && (ReadRawRC(RegControl) & 0x08))
{ status = MI_OK; }
else
{ status = MI_ERR; }
}
else
{ status = MI_ERR; }
return status;
}
/////////////////////////////////////////////////////////////////////
//功 能:读取M1卡一块数据
//参数说明: addr[IN]:块地址
// pData[OUT]:读出的数据,16字节
//返 回: 成功返回MI_OK
/////////////////////////////////////////////////////////////////////
char PcdRead(unsigned char addr,unsigned char *pData)
{
char status;
unsigned int unLen;
unsigned char idata ucComBuf[FSD];
PcdSetTmo(5);
WriteRawRC(RegChannelRedundancy,0x0F);
ucComBuf[0] = PICC_READ;
ucComBuf[1] = addr;
status = PcdComISO14443(PCD_TRANSCEIVE,ucComBuf,2,ucComBuf,&unLen);
if ((status == MI_OK) && (unLen == 0x80))
{ memcpy(pData, ucComBuf, 16); }
else
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -