if (status != MI_NOTAGERR) //识别应答
{
if (MInfo.nBitsReceived != 4)
{
status = MI_BITCOUNTERR;
}
else
{
SerBuffer[0] &= 0x0f;
switch(SerBuffer[0])
{
case 0x00:
status = MI_NOTAUTHERR;
break;
case 0x0a:
status = MI_OK;
break;
case 0x01:
status = MI_VALERR;
break;
default:
status = MI_CODEERR;
break;
}
}
}
if ( status == MI_OK)
{
M500PcdSetTmo(3);
ResetInfo(MInfo);
memcpy(SerBuffer,value,4);
MInfo.nBytesToSend = 4;
status = M500PcdCmd(PCD_TRANSCEIVE,
SerBuffer,
&MInfo);//发送数据(第2次发送)
if (status == MI_OK) //识别应答
{
if (MInfo.nBitsReceived != 4)
{
status = MI_BITCOUNTERR;
}
else
{
SerBuffer[0] &= 0x0f;
switch(SerBuffer[0])
{
case 0x00:
status = MI_NOTAUTHERR;
break;
case 0x01:
status = MI_VALERR;
break;
default:
status = MI_CODEERR;
break;
}
}
}
else
{
if (status == MI_NOTAGERR )
status = MI_OK;
}
}
/******************以下代码起什么作用************************/
if (status == MI_OK)
{
ResetInfo(MInfo);
SerBuffer[0] = PICC_TRANSFER;
SerBuffer[1] = trans_addr; //再次传送块号???
MInfo.nBytesToSend = 2;
status = M500PcdCmd(PCD_TRANSCEIVE,
SerBuffer,
&MInfo);//(第3次发送)
if (status != MI_NOTAGERR)
{
if (MInfo.nBitsReceived != 4)
{
status = MI_BITCOUNTERR;
}
else
{
SerBuffer[0] &= 0x0f;
switch(SerBuffer[0])
{
case 0x00:
status = MI_NOTAUTHERR;
break;
case 0x0a:
status = MI_OK;
break;
case 0x01:
status = MI_VALERR;
break;
default:
status = MI_CODEERR;
break;
}
}
}
}
return status;
}
// Value format operations for Mifare Standard card ICs(调试OK)
///////////////////////////////////////////////////////////////////////
//说明:上层函数调用该函数时对addr和trans_addr 传递的值是一样的 1~63
// 加或减值命令 块地址 4byte 数据 块地址
char M500PiccValue(unsigned char dd_mode,unsigned char addr,unsigned char *value,unsigned char trans_addr)
{
char status = MI_OK;
M500PcdSetTmo(1); //设置时间
ResetInfo(MInfo); //控制块
SerBuffer[0] = dd_mode;
SerBuffer[1] = addr;
MInfo.nBytesToSend = 2;
status = M500PcdCmd(PCD_TRANSCEIVE,
SerBuffer,
&MInfo); //发送命令和块号(第1次发送)
if (status != MI_NOTAGERR) //识别应答
{
if (MInfo.nBitsReceived != 4)
{
status = MI_BITCOUNTERR;
}
else
{
SerBuffer[0] &= 0x0f;
switch(SerBuffer[0])
{
case 0x00:
status = MI_NOTAUTHERR;
break;
case 0x0a:
status = MI_OK;
break;
case 0x01:
status = MI_VALERR;
break;
default:
status = MI_CODEERR;
break;
}
}
}
if ( status == MI_OK)
{
M500PcdSetTmo(3);
ResetInfo(MInfo);
memcpy(SerBuffer,value,4);
MInfo.nBytesToSend = 4;
status = M500PcdCmd(PCD_TRANSCEIVE,
SerBuffer,
&MInfo);//发送数据(第2次发送)
if (status == MI_OK) //识别应答
{
if (MInfo.nBitsReceived != 4)
{
status = MI_BITCOUNTERR;
}
else
{
SerBuffer[0] &= 0x0f;
switch(SerBuffer[0])
{
case 0x00:
status = MI_NOTAUTHERR;
break;
case 0x01:
status = MI_VALERR;
break;
default:
status = MI_CODEERR;
break;
}
}
}
else
{
if (status == MI_NOTAGERR )
status = MI_OK;
}
}
/******************以下代码起什么作用************************/
if (status == MI_OK)
{
ResetInfo(MInfo);
SerBuffer[0] = PICC_TRANSFER;
SerBuffer[1] = trans_addr; //再次传送块号???
MInfo.nBytesToSend = 2;
status = M500PcdCmd(PCD_TRANSCEIVE,
SerBuffer,
&MInfo);//(第3次发送)
if (status != MI_NOTAGERR)
{
if (MInfo.nBitsReceived != 4)
{
status = MI_BITCOUNTERR;
}
else
{
SerBuffer[0] &= 0x0f;
switch(SerBuffer[0])
{
case 0x00:
status = MI_NOTAUTHERR;
break;
case 0x0a:
status = MI_OK;
break;
case 0x01:
status = MI_VALERR;
break;
default:
status = MI_CODEERR;
break;
}
}
}
}
return status;
}
///////////////////////////////////////////////////////////////////////
写指令分两帧写命令,发送两个字节的写指令,“A0H,ADDR”,ADDR为BLOCK地址,CMD为1EH,CRC校验方式,如果权限校验通过,卡返回1010(即0x0A),若权限校验不通过,返回0000,若发生通讯错误,返回0001;如果权限校验通过,则进行第二帧写数据,CMD为1EH,CRC校验方式,发送4个字节的数据,即写数据,CRC校验方式,操作正常,卡会再返回1010,错误则返回错误信息。
前面两次已经把命令和数据都已经发送出去了,为什么还来个第3次发送?如你所说不是也只要发送两次就可以了嘛,
干嘛来个第3次发送???
首先PICC中应该存在3种存储单元, 1.接收数据缓冲单元2.内部数据寄存器 3.EEPROM
卡接收到的数据保存在数据缓冲单元,再依据命令做响应.
当我们写数据时,卡接收到完整的命令和数据后,直接将其写入EEPROM就是我们指定的操作块.写入之前这个块的值是多少
我们不关心.
当我们要加减值时,卡收到完整的命令后->把命令中指定的块号对应的数据读取到内部数据寄存器(因为在寄存器里面才能
执行运算)然后等待数据的到来.->接收到数据后,将数据和寄存器里面的值加/减后,并保存在寄存器里面.然后等待下一个命令
指定操作块->接收到命令后将寄存器里面的值写入操作块.
在上例中addr为源块,trans_addr为目的块(源块 目的块可以不同).简单来说就是把某个源块的数据加减后再写入某目的块,这样做就可以实现任意块的
加减和存入.为什么要这样做?那是为了PICC的高级操作的强大备份功能.
再来看以上的代码就清楚了,第一次发送是告诉PICC我是要对哪个块的数据进行加减,第2次发送是要加减的值,第3次发送告诉
PICC.(把结果存到这个块吧!)
总算把RC500玩转了,谢谢zhangf1021 提供的资料.谢谢楼上的回复.
一周热门 更多>