📄 mifare.c
字号:
/*************************************************************
Mifare serial reader communication sequence
Date : 28\08\2007
Ver :
COMMAND SEQUENCE
Host Reader
STX -------->
<-------- DLE WHen there is no response try again
INFO[0] -------->
INFO[1] -------->
:
:
INFO[N-1] -------->
DLE -------->
ETX -------->
<-------- DLE/NAK If NAK try again
RESPONSE SEQUENCE
Host Reader
<-------- STX
DLE --------> DLE If host does not respond comm fail
<-------- INFO[0]
<-------- INFO[1]
:
:
<-------- INFO[N-1]
<--------- DLE
<--------- ETX
DLE --------->
the time out for communicatiois 0.55 sec
if there is error in communication or BCC mismatch then receiver responds with NAK
Format of transmit block
--------------------------------------------------------------
| SEQ No | CMD | LEN |DATA[0]|DATA[1]|---------DATA[N]| BCC |
--------------------------------------------------------------
INFO[0] INFO[1] INFO[N-1]
BCC = INFO[0] ^ INFO[1]...................... INFO[N-1]
receive block
--------------------------------------------------------------
|SEQ NO | RES | LEN |DATA[0]|DATA[1]|---------DATA[N]| BCC |
--------------------------------------------------------------
*************************************************************/
#include "LPC23xx.H" /* LPC23xx/24xx definitions */
#include "type.h"
#include "uart.h"
#include "display.h"
/***************************************************/
// RFID Functions
/**************************************************/
unsigned char serial_rx_timeout(void);
unsigned char mif_send_block(unsigned char *, unsigned char *);
unsigned char mif_request(void);
unsigned char mif_anti_col(void);
unsigned char mif_select(void);
unsigned char mif_auth(unsigned char , unsigned char );
unsigned char mif_load_key(unsigned char , unsigned char , unsigned char *);
unsigned char mif_halt(void);
void rfid_init(void);
//void rfid_close();
unsigned char mif_write_card(unsigned char *, unsigned char );
unsigned char mif_read_card(unsigned char *, unsigned char );
unsigned char mif_seq_no;
unsigned char mif_ser_no[4];
//unsigned char const mif_req_seq[] = {0x03, 0x41, 0x01, 0x01};
unsigned char const mif_transport_key[] =
{
0xBD,0xDE,0x6F,0x37,0x83,0x83,0x14,0x8A,0xC5,0xE2,0x28,0x28,0x7D,0x3E,0x9F,0x4F,0x95,0x95,0xAD,0xD6,0x6B,0x35,0xC8,0xC8,
0xDF,0xEF,0x77,0xBB,0xE4,0xE4,0x09,0x84,0x42,0x21,0xBC,0xBC,0x5F,0xAF,0xD7,0xEB,0xA5,0xA5,0x29,0x14,0x8A,0xC5,0x9F,0x9F,
0xFA,0xFD,0xFE,0x7F,0xFF,0xFF,0x73,0x39,0x9C,0xCE,0xBE,0xBE,0xFC,0x7E,0xBF,0xDF,0xBF,0xBF,0xCF,0xE7,0x73,0x39,0x51,0x51,
0xF7,0xFB,0x7D,0x3E,0x5A,0x5A,0xF2,0x79,0x3C,0x1E,0x8D,0x8D,0xCF,0xE7,0x73,0x39,0x45,0x45,0xB7,0xDB,0x6D,0xB6,0x7D,0x7D
};
void rfid_init(void)
{
FIO4SET = 0x01 << 29;//B
FIO4CLR = 0x01 << 28;//A
FIO2SET = 0x01 << 12;//rfid power on
}
/***************************************************************
function waits for fixed timeout and returns stautus of
communications 0x00 indicates timeout
***************************************************************/
unsigned char serial_rx_timeout(void)
{
unsigned long mif_timeout;
unsigned char ret_val = 0x00;
mif_timeout = 1000000;
while(mif_timeout > 0)
{
if(U2LSR & 0X01)
{
ret_val = U2RBR;
break;
}
else
mif_timeout--;
}
return ret_val;
}
/****************************************************************
function to transmit given packet of data after calculating BCC
returns the status of communicaion and data if any
1 -------> successful communication
0 -------> no response
no bytes to be transmitted is passed in first byte of an array
****************************************************************/
unsigned char mif_send_block(unsigned char *mif_send_data, unsigned char *mif_cmd_res)
{
unsigned char mif_temp_cnt;
unsigned char mif_bcc, mif_com_status, mif_temp_buf = 0x00;
unsigned long mif_rx_timeout;
mif_com_status = 0x00;
mif_bcc = 0x00;
for(mif_temp_cnt=1; mif_temp_cnt <=mif_send_data[0]; mif_temp_cnt++)
mif_bcc ^= mif_send_data[mif_temp_cnt]; //calculate BCC include sequence number
mif_bcc ^= mif_seq_no;
for(mif_temp_cnt = 0; mif_temp_cnt < 3; mif_temp_cnt++)
{
serial_send(2,0x02);
if(serial_rx_timeout() == 0x10)
{
mif_com_status = 0x01;
break;
}
}
if(mif_com_status)
{
mif_com_status = 0x00;
serial_send(2,mif_seq_no); //send packet
if(mif_seq_no == 0x10)
serial_send(2,mif_seq_no);
for(mif_temp_cnt=1; mif_temp_cnt <= mif_send_data[0]; mif_temp_cnt++)
{
serial_send(2,mif_send_data[mif_temp_cnt]);
if(mif_send_data[mif_temp_cnt] == 0x10)
serial_send(2,mif_send_data[mif_temp_cnt]);
}
serial_send(2,mif_bcc);
if(mif_bcc == 0x10)
serial_send(2,0x10);
serial_send(2,0x10); // DLE and ETX
serial_send(2,0x03);
mif_temp_cnt = 0;
if(serial_rx_timeout() == 0x10) //if DLE and STX are received proceed further
{
if(serial_rx_timeout() == 0x02)
{
serial_send(2,0x10);
mif_rx_timeout = 1000000;
while(1)
{
if(U2LSR & 0X01)
{
mif_rx_timeout = 1000000;
if(mif_temp_buf == 0x10) //check if last character is 0x10
{
mif_temp_buf = U2RBR;
//RI = 0;
if(mif_temp_buf == 0X10) //if present char is 0x10 do nothing
{
mif_cmd_res[++mif_temp_cnt] = mif_temp_buf;
mif_temp_buf = 0x00;
}
else if(mif_temp_buf == 0x03) //if present char is 0x03 end of text mark as successful com
{
mif_com_status = 0x01;
serial_send(2,0x10);
break;
}
else
break; //if any other character is received after 0x10 error
}
else
{
mif_temp_buf = U2RBR;
//RI = 0;
if(mif_temp_buf!= 0X10)
{
mif_cmd_res[++mif_temp_cnt] = mif_temp_buf;
}
if(mif_temp_cnt > 25)
break;
}
}
else
{
mif_rx_timeout--;
if(!mif_rx_timeout)
break;
}
}
}
}
}
if((mif_com_status) && (mif_seq_no == mif_cmd_res[1])) // if communication and seq no are ok,check bcc
{
mif_bcc = 0x00;
mif_cmd_res[0] = mif_temp_cnt;
for(mif_temp_cnt = 1; mif_temp_cnt < mif_cmd_res[0]; mif_temp_cnt++)
mif_bcc ^= mif_cmd_res[mif_temp_cnt];
if(mif_bcc != mif_cmd_res[mif_temp_cnt])
mif_com_status = 0x00;
return
mif_com_status;
}
else
return 0x00;
}
/*mifare request function checks for the presence of the card in the
feild and returns satus of card the status of the card is returned
by the send_blk function*/
unsigned char mif_request(void)
{
unsigned char mif_req_data[10], mif_req_res[30];
unsigned char mif_req_status, mif_req_cnt;
mif_seq_no = 0x01;
mif_req_data[0] = 0x03;
mif_req_data[1] = 0x41;
mif_req_data[2] = 0x01;
mif_req_data[3] = 0x01;
for(mif_req_cnt = 0; mif_req_cnt<3; mif_req_cnt++)
{
mif_req_status = mif_send_block(mif_req_data, mif_req_res);
if(mif_req_status)
{
mif_req_status = 0x00;
mif_seq_no++;
if(mif_req_res[2] == 0x00)
{
mif_req_status = 0x01;
break;
}
}
}
return mif_req_status;
}
unsigned char mif_anti_col(void)
{
unsigned char mif_ant_data[10], mif_ant_res[30];
unsigned char mif_ant_sts;
mif_ant_data[0] = 0x07;
mif_ant_data[1] = 0x42;
mif_ant_data[2] = 0x05;
mif_ant_data[3] = 0x00;
mif_ant_data[4] = 0x00;
mif_ant_data[5] = 0x00;
mif_ant_data[6] = 0x00;
mif_ant_data[7] = 0x00;
mif_ant_sts = mif_send_block(mif_ant_data, mif_ant_res);
if(mif_ant_sts)
{
mif_seq_no++;
if((mif_ant_res[2] == 0x00)&&(mif_ant_res[3]==4))
{
mif_ser_no[0] = mif_ant_res[4];
mif_ser_no[1] = mif_ant_res[5];
mif_ser_no[2] = mif_ant_res[6];
mif_ser_no[3] = mif_ant_res[7];
}
else
mif_ant_sts = 0x00;
}
return mif_ant_sts;
}
unsigned char mif_select(void)
{
unsigned char mif_sel_data[10], mif_sel_res[30];
unsigned char mif_sel_sts;
mif_sel_data[0] = 0x06;
mif_sel_data[1] = 0x43;
mif_sel_data[2] = 0x04;
mif_sel_data[3] = mif_ser_no[0];
mif_sel_data[4] = mif_ser_no[1];
mif_sel_data[5] = mif_ser_no[2];
mif_sel_data[6] = mif_ser_no[3];
mif_sel_sts = mif_send_block(mif_sel_data, mif_sel_res);
if(mif_sel_sts)
{
mif_seq_no++;
if(mif_sel_res[2] != 0x00)
mif_sel_sts = 0x00;
}
return mif_sel_sts;
}
unsigned char mif_auth(unsigned char mif_auth_mode, unsigned char mif_auth_sec)
{
unsigned char mif_auth_data[10], mif_auth_res[30];
unsigned char mif_auth_sts;
mif_auth_data[0] = 0x04;
mif_auth_data[1] = 0x44;
mif_auth_data[2] = 0x02;
mif_auth_data[3] = mif_auth_mode;
mif_auth_data[4] = mif_auth_sec;
mif_auth_sts = mif_send_block(mif_auth_data, mif_auth_res);
if(mif_auth_sts)
{
mif_seq_no++;
if(mif_auth_res[2] != 0x00)
mif_auth_sts = 0x00;
}
return mif_auth_sts;
}
unsigned char mif_load_key(unsigned char mif_lk_mode, unsigned char mif_lk_sec, unsigned char *mif_lk_key)
{
unsigned char mif_lk_data[25],mif_lk_res[30];
unsigned char mif_lk_sts, mif_lk_cnt ;
mif_lk_data[0] = 0x14;
mif_lk_data[1] = 0x4c;
mif_lk_data[2] = 0x12;
mif_lk_data[3] = mif_lk_mode;
mif_lk_data[4] = mif_lk_sec;
for(mif_lk_cnt=0; mif_lk_cnt<6; mif_lk_cnt++)
mif_lk_data[mif_lk_cnt + 5] = mif_transport_key[(mif_lk_sec * 6) + mif_lk_cnt];
mif_lk_data[11] = 0x00;
mif_lk_data[12] = 0x00;
for(mif_lk_cnt=0; mif_lk_cnt<6; mif_lk_cnt++)
mif_lk_data[mif_lk_cnt + 13] = mif_lk_key[ mif_lk_cnt];
mif_lk_data[19] = 0x00;
mif_lk_data[20] = 0x00;
// clrscr();
// for(mif_lk_sts=0;mif_lk_sts<21;mif_lk_sts++)
// printf("%02x ",((unsigned int) mif_lk_data[mif_lk_sts])&0x00ff);
// get_key();
// mif_lk_sts = 0x00;
mif_lk_sts = mif_send_block(mif_lk_data, mif_lk_res);
if(mif_lk_sts)
{
mif_seq_no++;
if(mif_lk_res[2] != 0x00)
mif_lk_sts = 0x00;
}
return mif_lk_sts;
}
unsigned char mif_halt(void)
{
unsigned char mif_halt_data[10], mif_halt_res[30];
unsigned char mif_halt_status;
mif_halt_data[0] = 0x02;
mif_halt_data[1] = 0x45;
mif_halt_data[2] = 0x00;
mif_halt_status = mif_send_block(mif_halt_data, mif_halt_res);
if(mif_halt_status)
{
mif_seq_no++;
if(mif_halt_res[2] != 0x00)
mif_halt_status = 0x00;
}
return mif_halt_status;
}
//void rfid_init(void)
//{
// DATAOUT_C = DATAOUT_C | 0x08; //rfid power enable
//}
/*
void rfid_close()
{
DATAOUT_C = DATAOUT_C & 0xf7; //rfid power disable
}
*/
unsigned char mif_write_card(unsigned char *mif_write_data, unsigned char mif_write_add)
{
unsigned char mif_wrcd_data[25],mif_wrcd_res[30];
unsigned char mif_wrcd_sts, mif_wrcd_cnt ;
if((mif_write_add%4) == 3)
return 0x00;
//setport(0);
for(mif_wrcd_cnt = 0; mif_wrcd_cnt < 4; mif_wrcd_cnt++)
mif_ser_no[mif_wrcd_cnt] = 0x00;
//rfid_init();
mif_wrcd_sts = mif_request();
if(mif_wrcd_sts)
{
mif_wrcd_sts = mif_anti_col();
}
if( mif_wrcd_sts)
{
mif_wrcd_sts = mif_select();
}
if(mif_wrcd_sts)
{
mif_wrcd_sts = mif_auth(0x00, (mif_write_add/4));
}
if(mif_wrcd_sts)
{
mif_wrcd_data[0] = 0x13;
mif_wrcd_data[1] = 0x47;
mif_wrcd_data[2] = 0x11;
mif_wrcd_data[3] = mif_write_add;
for(mif_wrcd_cnt = 0; mif_wrcd_cnt < 16; mif_wrcd_cnt++)
mif_wrcd_data[mif_wrcd_cnt + 4] = mif_write_data[mif_wrcd_cnt];
mif_wrcd_sts = mif_send_block(mif_wrcd_data, mif_wrcd_res);
if(mif_wrcd_sts)
{
mif_seq_no++;
if(mif_wrcd_res[2] != 0x00)
mif_wrcd_sts = 0x00;
}
mif_halt();
}
//rfid_close();
return mif_wrcd_sts;
}
unsigned char mif_read_card(unsigned char *mif_read_data, unsigned char mif_read_add)
{
unsigned char mif_rd_data[10],mif_rd_res[30];
unsigned char mif_rd_sts, mif_rd_cnt ;
if((mif_read_add%4) == 3)
return 0x00;
//setport(0);
//rfid_init();
for(mif_rd_cnt = 0; mif_rd_cnt < 4; mif_rd_cnt++)
mif_ser_no[mif_rd_cnt] = 0x00;
mif_rd_sts = mif_request();
if(mif_rd_sts)
mif_rd_sts = mif_anti_col();
if( mif_rd_sts)
mif_rd_sts = mif_select();
if(mif_rd_sts)
mif_rd_sts = mif_auth(0x00, (mif_read_add/4));
if(mif_rd_sts)
{
mif_rd_data[0] = 0x03;
mif_rd_data[1] = 0x46;
mif_rd_data[2] = 0x01;
mif_rd_data[3] = mif_read_add;
mif_rd_sts = mif_send_block(mif_rd_data, mif_rd_res);
if(mif_rd_sts)
{
mif_seq_no++;
if(mif_rd_res[2] == 0x00)
{
for(mif_rd_cnt=0; mif_rd_cnt<16; mif_rd_cnt++)
mif_read_data[mif_rd_cnt] = mif_rd_res[mif_rd_cnt + 4];
mif_rd_sts = 0x01;
}
else
mif_rd_sts = 0x00;
}
mif_halt();
}
//rfid_close();
return mif_rd_sts;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -