📄 m500auc.c
字号:
{
MpIsrIn[MpIsrInfo->nBytesReceived] = ReadIO(RegFIFOData);
MpIsrInfo->nBytesReceived++;
}
nbytes = ReadIO(RegFIFOLength);
// reset IRQ bit - idle irq will
}while (nbytes>0);
WriteIO(RegInterruptRq,0x0A & irqBits); // be deleted in a seperate section
}
//************** IdleIRQ Handling ***********
if (irqBits & 0x04) // Idle IRQ
{
WriteIO(RegInterruptEn,0x20); // disable Timer IRQ
WriteIO(RegInterruptRq,0x20); // disable Timer IRQ request
irqBits &= ~0x20; // clear Timer IRQ in local var
MpIsrInfo->irqSource &= ~0x20; // clear Timer IRQ in info var
// when idle received, then cancel
// timeout
WriteIO(RegInterruptRq,0x04); // reset IRQ bit
MpIsrInfo->irqSource |= 0x04; // set idle-flag in case of valid rx-irq
// status should still be MI_OK
// no error - only used for wake up
}
//************* TimerIRQ Handling ***********
if (irqBits & 0x20) // timer IRQ
{
WriteIO(RegInterruptRq,0x20); // reset IRQ bit
MpIsrInfo->status = MI_NOTAGERR; // timeout error
// otherwise ignore the interrupt
}
}
}
}
///////////////////////////////////////////////////////////////////////
// S e t T i m e o u t L E N G T H
///////////////////////////////////////////////////////////////////////
void M500PcdSetTmo(unsigned char tmoLength)
{
switch(tmoLength)
{ // timer clock frequency 13,56 MHz
case 1: // short timeout (1,0 ms)
WriteIO(RegTimerClock,0x07); // TAutoRestart=0,TPrescale=128
WriteIO(RegTimerReload,0x6a);// TReloadVal = 'h6a =106(dec)
break;
case 2: // medium timeout (1,5 ms)
WriteIO(RegTimerClock,0x07); // TAutoRestart=0,TPrescale=128
WriteIO(RegTimerReload,0xa0);// TReloadVal = 'ha0 =160(dec)
break;
case 3: // medium timeout (6 ms)
WriteIO(RegTimerClock,0x09); // TAutoRestart=0,TPrescale=4*128
WriteIO(RegTimerReload,0xa0);// TReloadVal = 'ha0 =160(dec)
break;
case 4: // long timeout (9.6 ms)
WriteIO(RegTimerClock,0x09); // TAutoRestart=0,TPrescale=4*128
WriteIO(RegTimerReload,0xff);// TReloadVal = 'hff =255(dec)
break;
case 5: // long timeout (38.5 ms)
WriteIO(RegTimerClock,0x0b); // TAutoRestart=0,TPrescale=16*128
WriteIO(RegTimerReload,0xff);// TReloadVal = 'hff =255(dec)
break;
case 6: // long timeout (154 ms)
WriteIO(RegTimerClock,0x0d); // TAutoRestart=0,TPrescale=64*128
WriteIO(RegTimerReload,0xff);// TReloadVal = 'hff =255(dec)
break;
case 7: // long timeout (616.2 ms)
WriteIO(RegTimerClock,0x0f); // TAutoRestart=0,TPrescale=256*128
WriteIO(RegTimerReload,0xff);// TReloadVal = 'hff =255(dec)
break;
default: //
WriteIO(RegTimerClock,0x07); // TAutoRestart=0,TPrescale=128
WriteIO(RegTimerReload,tmoLength);// TReloadVal = 'h6a =tmoLength(dec)
break;
}
}
//////////////////////////////////////////////////////////////////////
// W R I T E A P C D C O M M A N D
///////////////////////////////////////////////////////////////////////
char M500PcdCmd(unsigned char cmd,
unsigned char * send,
unsigned char * rcv,
MfCmdInfo *info)
{
char status = MI_OK;
char tmpStatus ;
unsigned char lastBits;
unsigned char irqEn = 0x00;
unsigned char waitFor = 0x00;
unsigned char timerCtl = 0x02;
unsigned char validErrorFlags = 0x1F;
unsigned char ii=0;
WriteIO(RegInterruptEn,0x7F); // disable all interrupts
WriteIO(RegInterruptRq,0x7F); // reset interrupt requests
FlushFIFO(); // flush FIFO buffer
// wait until e2 programming is finished
while (((ReadIO(RegSecondaryStatus) & 0x40) == 0)){};
WriteIO(RegCommand,PCD_IDLE); // terminate probably running command
// save info structures to module pointers
MpIsrInfo = info;
MpIsrOut = send;
MpIsrIn = rcv;
info->irqSource = 0x0; // reset interrupt flags
//enable INT1 interrupt // depending on the command code, appropriate interrupts are enabled (irqEn)
// and the commit interrupt is choosen (waitFor).
switch(cmd)
{
case PCD_IDLE: // nothing else required
irqEn = 0x00;
waitFor = 0x00;
break;
case PCD_WRITEE2: // LoAlert and TxIRq
timerCtl = 0x00; // start and stop timer manually
irqEn = 0x11;
waitFor = 0x14;
validErrorFlags &= ~0x08;
break;
case PCD_READE2: // HiAlert, LoAlert and IdleIRq
timerCtl = 0x00; // start and stop timer manually
irqEn = 0x07;
waitFor = 0x04;
validErrorFlags &= ~0x08;
break;
case PCD_LOADKEYE2: // IdleIRq and LoAlert
timerCtl = 0x00; // start and stop timer manually
irqEn = 0x05;
waitFor = 0x04;
validErrorFlags &= ~0x08;
break;
case PCD_LOADCONFIG: // IdleIRq and LoAlert
timerCtl = 0x00; // start and stop timer manually
irqEn = 0x05;
waitFor = 0x04;
break;
case PCD_AUTHENT1: // IdleIRq and LoAlert
irqEn = 0x05;
waitFor = 0x04;
break;
case PCD_CALCCRC: // LoAlert and TxIRq
timerCtl = 0x00; // start and stop timer manually
irqEn = 0x11;
waitFor = 0x10;
break;
case PCD_AUTHENT2: // IdleIRq
irqEn = 0x0C;
waitFor = 0x04;
break;
case PCD_RECEIVE: // HiAlert and IdleIRq
info->nBitsReceived = -(ReadIO(RegBitFraming) >> 4);
timerCtl = 0x04; // start timer manually and stop
// with first bit received
irqEn = 0x06;
waitFor = 0x04;
break;
case PCD_LOADKEY: // IdleIRq
timerCtl = 0x00; // start and stop timer manually
irqEn = 0x05;
waitFor = 0x04;
break;
case PCD_TRANSMIT: // LoAlert and IdleIRq
timerCtl = 0x00; // start and stop timer manually
irqEn = 0x05;
waitFor = 0x04;
break;
case PCD_TRANSCEIVE: // TxIrq, RxIrq, IdleIRq and LoAlert
info->nBitsReceived = -(ReadIO(RegBitFraming) >> 4);
//printf("orgenal BIts=%b02X",info->nBitsReceived);
irqEn = 0x1D;
waitFor = 0x04;
break;
default:
status = MI_UNKNOWN_COMMAND;
}
if (status == MI_OK)
{
irqEn |= 0x20; // always enable timout irq
waitFor |= 0x20; // always wait for timeout
start_timeout(8000); // initialise and start guard timer for reader
// 50us resolution, 200ms
WriteIO(RegTimerControl,timerCtl);
if (~timerCtl & 0x02) // if no start condition could be detected, then
// start timer manually
{
SetBitMask(RegControl,0x02);
}
WriteIO(RegCommand,cmd); //start command
WriteIO(RegInterruptEn,irqEn | 0x80); //necessary interrupts are enabled
// wait for commmand completion
// a command is completed, if the corresponding interrupt occurs
// or a timeout is signaled
while (!(MpIsrInfo->irqSource & waitFor
|| T2IR)) EX1=1; // wait for cmd completion or timeout
WriteIO(RegInterruptEn,0x7F); // disable all interrupts
WriteIO(RegInterruptRq,0x7F); // clear all interrupt requests
SetBitMask(RegControl,0x04); // stop timer now
stop_timeout(); // stop timeout for reader
WriteIO(RegCommand,PCD_IDLE); // reset command register
if (!(MpIsrInfo->irqSource & waitFor)) // reader has not terminated
{ // timer 2 expired
status = MI_ACCESSTIMEOUT;
}
else
status = MpIsrInfo->status; // set status
//printf("\nISR-status=%b02X",status);
if (status == MI_OK) // no timeout error occured
{
if (tmpStatus = (ReadIO(RegErrorFlag) & validErrorFlags)) // error occured
{
if (tmpStatus & 0x01) // collision detected
{
info->collPos = ReadIO(RegCollpos); // read collision position
status = MI_COLLERR;
}
else
{
info->collPos = 0;
if (tmpStatus & 0x02) // parity error
{
status = MI_PARITYERR;
}
}
if (tmpStatus & 0x04) // framing error
{
status = MI_FRAMINGERR;
}
if (tmpStatus & 0x10) // FIFO overflow
{
FlushFIFO();
status = MI_OVFLERR;
}
if (tmpStatus & 0x08) //CRC error
{
status = MI_CRCERR;
}
if (status == MI_OK)
status = MI_NY_IMPLEMENTED,printf("MI_NY_IMPLEMENTED");
// key error occures always, because of
// missing crypto 1 keys loaded
} //end if of tempstatus
// if the last command was TRANSCEIVE, the number of
// received bits must be calculated - even if an error occured
if (cmd == PCD_TRANSCEIVE)
{ // printf("\nCacula BitsReceived ");
// number of bits in the last byte
lastBits = ReadIO(RegSecondaryStatus) & 0x07;
if (lastBits)
ii += (info->nBytesReceived-1) * 8 + lastBits;
else
ii += info->nBytesReceived * 8;
ii+=info->nBitsReceived ;
info->nBitsReceived=ii;
// printf("\nACK Read Byte =%b02X",info->nBytesReceived);
//printf("\nACK Read BIT =%b02X",ii);
}
}
else
{
info->collPos = 0x00;
}
// if (!rxMultiple)
// ClearBitMask(RegDecoderControl,0x40);
}
EX1=0; // disable INT1
MpIsrInfo = 0; // reset interface variables for ISR
MpIsrOut = 0;
MpIsrIn = 0;
return status;
}
//////////////////////////////////////////////////////////////////////
// S E T A B I T M A S K
///////////////////////////////////////////////////////////////////////
char SetBitMask(unsigned char reg,unsigned char mask) //
{
char data tmp = 0x0;
tmp = ReadIO(reg);
WriteIO(reg,tmp | mask); // set bit mask
return 0x0;
}
//////////////////////////////////////////////////////////////////////
// C L E A R A B I T M A S K
///////////////////////////////////////////////////////////////////////
char ClearBitMask(unsigned char reg,unsigned char mask) //
{
char data tmp = 0x0;
tmp = ReadIO(reg);
WriteIO(reg,tmp & ~mask); // clear bit mask
return 0x0;
}
///////////////////////////////////////////////////////////////////////
// F L U S H F I F O
///////////////////////////////////////////////////////////////////////
void FlushFIFO(void)
{
SetBitMask(RegControl,0x01);
}
///////////////////////////////////////////////////////////////////////
// M I F A R E M O D U L E R E S E T
///////////////////////////////////////////////////////////////////////
char M500PcdReset(void)
{
char status = MI_OK;
RC500RST = 0; // clear reset pin
delay_1ms(50); // wait for 25ms
RC500RST = 1; // reset RC500
delay_50us(100); // wait for 2.5ms
RC500RST = 0; // clear reset pin
start_timeout(42000); // count down with a period of 50 us
// 42000 * 50 us = 2.1 s
// wait until reset command recognized
while (((ReadIO(RegCommand) & 0x3F) != 0x3F) && !T2IR);
// while reset sequence in progress
while ((ReadIO(RegCommand) & 0x3F) && !T2IR);
stop_timeout(); // stop timeout counter
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -