📄 mifarepro.txt
字号:
unsigned char *atq,
unsigned char *sak,
unsigned char *uid,
unsigned char *uid_len);
char M500PiccActivateAll(unsigned char br,
unsigned char *atq,
unsigned char *sak,
unsigned char *uid,
unsigned char *uid_len);
{
return M500PiccActivateIdle(br,atq,sak,uid,uid_len);
}
char PcdSetTmo(unsigned long tmoLength)
{
unsigned char prescale = 7;
unsigned long reload = tmoLength;
while (reload > 255)
{
prescale++;
reload = reload >> 1; // division by 2
}
// if one of the higher bits are set, the prescaler is set
// to the largest value
if (prescale > 0x15)
{
prescale = 0x15;
reload = 0xFF;
}
// fcnt = 13560000 / (2^prescale)
// T = (reload - counter) / fcnt
WriteIO(RegTimerClock,prescale); // TAutoRestart=0,TPrescale=prescale
WriteIO(RegTimerReload,reload);// TReloadVal = reload
return MI_OK;
}
char PcdWriteE2( unsigned short startaddr,
unsigned char length,
unsigned char* data)
{
char status = MI_OK;
PcdSetTmo(6800);
// ************* Cmd Sequence **********************************
ResetInfo(MInfo);
MSndBuffer[0] = startaddr & 0xFF;
MSndBuffer[1] = (startaddr >> 8) & 0xFF;
memcpy(MSndBuffer + 2,data,length);
MInfo.nBytesToSend = length + 2;
status = M500PcdCmd(PCD_WRITEE2,
MSndBuffer,
MRcvBuffer,
&MInfo); // write e2
return status;
}
char M500PcdLoadKeyE2(unsigned char key_type,
unsigned char sector,
unsigned char *uncoded_keys)
{
// eeprom address calculation
// 0x80 ... offset
// key_sector ... sector
// 0x18 ... 2 * 12 = 24 = 0x18
signed char status = MI_OK;
unsigned short e2addr = 0x80 + sector * 0x18;
unsigned char coded_keys[12];
if (key_type == PICC_AUTHENT1B)
e2addr += 12; // key B offset
if ((status = M500HostCodeKey(uncoded_keys,coded_keys)) == MI_OK) //M500HostCodekey() function in the main head files.
status = PcdWriteE2( e2addr,12,coded_keys); //PcdWriteE2() function in the main head files.
return status;
}
char ExchangeByteStream(unsigned char Cmd,
unsigned char *send_data,
unsigned short send_bytelen,
unsigned char *rec_data,
unsigned short *rec_bytelen)
{
signed char status = MI_OK;
FlushFIFO(); // empty FIFO
ResetInfo(MInfo); // initialise ISR Info structure
if (send_bytelen > 0)
{
memcpy(MSndBuffer,send_data,send_bytelen); // write n bytes
MInfo.nBytesToSend = send_bytelen;
// write load command
status = M500PcdCmd(Cmd,
MSndBuffer,
MRcvBuffer,
&MInfo);
*rec_bytelen = MInfo.nBytesReceived;
// copy data to output, even in case of an error
if (*rec_bytelen)
{
memcpy(rec_data,MRcvBuffer,*rec_bytelen);
}
}
else
{
status = MI_WRONG_PARAMETER_VALUE;
}
return status;
}
char M500PiccExchangeBlock(unsigned char *send_data,
unsigned short send_bytelen,
unsigned char *rec_data,
unsigned short *rec_bytelen,
unsigned char append_crc,
unsigned long timeout )
{
char status = MI_OK;
if (append_crc)
{
// RxCRC and TxCRC enable, parity enable
WriteIO(RegChannelRedundancy,0x0F);
send_bytelen -= 2;
}
else
{
// RxCRC and TxCRC disable, parity enable
WriteIO(RegChannelRedundancy,0x03);
}
PcdSetTmo(timeout);
status = ExchangeByteStream(PCD_TRANSCEIVE,
send_data,
send_bytelen,
rec_data,
rec_bytelen);
// even if an error occured, the data should be
// returned - for debugging reasons
if (append_crc)
{
*rec_bytelen += 2; // for two CRC bytes
rec_data[*rec_bytelen - 2] = 0x00;
rec_data[*rec_bytelen - 1] = 0x00;
}
return status;
}
char M500PiccAuthE2( unsigned char auth_mode, // PICC_AUTHENT1A or PICC_AUTHENT1B
unsigned char *snr, // 4 bytes card serial number
unsigned char key_sector, // 0 <= key_sector <= 15
unsigned char block) // 0 <= block <= 256
{
char status = MI_OK;
// eeprom address calculation
// 0x80 ... offset
// key_sector ... sector
// 0x18 ... 2 * 12 = 24 = 0x18
unsigned short e2addr = 0x80 + key_sector * 0x18;
unsigned char *e2addrbuf = (unsigned char*)&e2addr;
PcdSetTmo(106);
if (auth_mode == PICC_AUTHENT1B)
e2addr += 12; // key B offset
FlushFIFO(); // empty FIFO
ResetInfo(MInfo);
memcpy(MSndBuffer,e2addrbuf,2); // write low and high byte of address
MInfo.nBytesToSend = 2;
// write load command
if ((status=M500PcdCmd(PCD_LOADKEYE2,MSndBuffer,MRcvBuffer,&MInfo)) == MI_OK)
{
// execute authentication
status = M500PiccAuthState(auth_mode,snr,block);
}
return status;
}
/**********************************************************************
函数名: MProCommand
输入参数: 读取命令,读取命令长度,返回数据,
返回数据长度,CRC检验码,时间设置-超时设置
(按照函数参数顺序)
输出: 读卡状态值,status
核心处理: M500PiccExchangeBlock,Block数据交换,返回读取状态.
**********************************************************************/
char MProCommand(unsgined char *ReadBuf,
unsigned int ReadBuf_len,
unsigned char *PReadBuf,
unsigned int *PReadBuf_len,
unsigned char append_crc,
unsigned int timeout)
{
unsigned char nkey[6]={0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xA5};
unsigned char idata i,atq[2],snr[10],sak,snr_len,TA; //得到的snr必须发送出去!
unsigned char FWI=5,SFCI; // TCL protocol's setting variables
unsigned char ConfigReadBuf[128];
char idata status,temp;
status = M500PcdConfig(); // Initialise the RC500
for(i=0; i<16; i++)
{
M500PcdLoadKeyE2(PICC_AUTHENT1A,i,nkey); // LOADING KEYS and load EEPROM
}
// IS014443A
if((status=M500PiccActivateAll(0,atq,&sak,snr,&snr_len))==MI_OK)
{
if((sak&0x24) == 0x20) /* ISO1443A commands, T=CL */
{
ConfigReadBuf[0]=0xE0; // RATS commands
ConfigReadBuf[1]=0x50; // FSD=128, CID=0
if(M500PiccExchangeBlock(ConfigReadBuf,4,ConfigReadBuf,&temp,1,4)==MI_OK) // length incl CRC
{
/* ATS received in ReadBuf START EXCHANGING TRANSPARENT DATA */
i = 2;
if(ConfigReadBuf[1]&0x40)
TA=ConfigReadBuf[i++];
else
TA=0;
if(ConfigReadBuf[1]&0x20)
FWI=ConfigReadBuf[i]>>4;
SFCI=ConfigReadBuf[1]&0x0f; //max PICC receive lenght
if(TA) //request PPSS
{
ConfigReadBuf[0]=0xd0; // PPSS commands
ConfigReadBuf[1]=0x11; // PPS0
ConfigReadBuf[2]=0x33; // PPS1, DRI=8, DSI=8
if(M500PiccExchangeBlock(ConfigReadBuf,5,ConfigReadBuf,&temp,1,FWI)==MI_OK) // length incl CRC
{
//M500PcdWriteRegister(0x14,0x01); // ISO14443A, 848KBaud
//M500PcdWriteRegister(0x19,0x13); // Rcv 848KBaud
}
}
// Demo with Mifare ProX Eval OS
//BLK = 0; // initialise the 1st block
status = M500PiccExchangeBlock(ReadBuf,ReadBuf_len,PoReadBuf,PReadBuf_len,append_crc,timeout);
}
else // Mifare Classic commands
{
if((status=M500PiccAuthE2(PICC_AUTHENT1A,snr,0,62))!=MI_OK) continue;
PrepareValue(100,ConfigReadBuf);
if(M500PiccWrite(62,ConfigReadBuf)!=MI_OK) continue;
if(M500PiccRead(62,ConfigReadBuf)!=MI_OK) continue;
PrepareValue(1,ConfigReadBuf);
if(M500PiccValue(PICC_DECREMENT,62,ConfigReadBuf,62)!=MI_OK) continue;
if(M500PiccValue(PICC_RESTORE,62,ConfigReadBuf,61)!=MI_OK) continue;
if(M500PiccRead(61,ConfigReadBuf)!=MI_OK) continue;
//status = M500PiccHalt(); //It is not need the M500PiccHalt() function here.
}
}
return status;
}
}
/**********************************************************************
函数名: PrepareValue
输入参数: 初值value,命令缓冲数组buf
输出: 命令值设置
核心处理:命令数据准备
时间: 11-03-09
**********************************************************************/
void PrepareValue (unsigned long value, unsigned char *buf)
{
unsigned char i;
for (i=0; i<4; i++)
{
buf[i] = buf[8+i] = (unsigned char)(value>>(8*i));
buf[4+i] = ~buf[i];
}
buf[12] = 0;
buf[13] = 255;
buf[14] = 0;
buf[15] = 255;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -