richjhart
richjhart

Reputation: 356

Cannot wakeup MIFARE 1k card

What we need to do

We need to detect both the presence and absence of an RFID chip. We intend to do this by continually checking for a card. If one is there, we read it and confirm which it is. If there isn't one there after there previously was, then that is noted. It doesn't have to be super fast.

What we're using

Arduino UNO + RC522 FRID reader, with MIFARE 1k cards. Using the library at: https://github.com/miguelbalboa/rfid

The problems

Cannot read multiple cards

Contrary to what seems to be stated in example code found elsewhere, I am never able to read more than one card without resetting the RC522. As soon as it reads a card, and it's HALTed, no more cards can be read until the processor is reset. Other examples suggest this shouldn't be the case and a new card should immediately be readable on the next loop. Using:

void loop() {
    // Look for new cards
    if ( ! mfrc522.PICC_IsNewCardPresent()) {
        return;
    }

    // Select one of the cards
    if ( ! mfrc522.PICC_ReadCardSerial()) {
        return;
    }

    // Dump debug info about the card; PICC_HaltA() is automatically called
    mfrc522.PICC_DumpDetailsToSerial(&(mfrc522.uid));
    mfrc522.PICC_HaltA();
}

Successfully gives:

Card UID: B6 35 9F 46 
Card SAK: 08 
PICC type: MIFARE 1KB

But I cannot read any more cards until I reset the RF522 (either using software or just restarting the device).

Cannot authenticate card

void loop() {
    // Look for new cards
    if ( ! mfrc522.PICC_IsNewCardPresent()) {
        return;
    }

    // Select one of the cards
    if ( ! mfrc522.PICC_ReadCardSerial()) {
        return;
    }

    // Dump debug info about the card; PICC_HaltA() is automatically called
    mfrc522.PICC_DumpToSerial(&(mfrc522.uid));
}

Gives the following output

Card UID: B6 35 9F 46
Card SAK: 08
PICC type: MIFARE 1KB
Sector Block   0  1  2  3   4  5  6  7   8  9 10 11  12 13 14 15  AccessBits
  15     63  PCD_Authenticate() failed: Timeout in communication.
  14     59  PCD_Authenticate() failed: Timeout in communication.
  13     55  PCD_Authenticate() failed: Timeout in communication.
...

Cannot read card when starting

I cannot read a card if it's present when starting the RC522, the communication times out. It does, however, take longer when a card is present. Using the following code:

// this is triggered by a serial command input
void resetAndRead() {
    Serial.println("Init and check for any card");
    mfrc522[0].PCD_Reset();
    Serial.print("Reset complete (antenna off): ");
    Serial.println(millis() - time_last_action);
    delay(2000);
    time_last_action = millis();
    initialise();
    Serial.print("Init complete: ");
    Serial.println(millis() - time_last_action);
    delay(10);
    time_last_action = millis();
    PICC_IsAnyCardPresent();
    Serial.print("Check for card complete: ");
    Serial.println(millis() - time_last_action);
}

void initialise() {
    mfrc522[0].PCD_Init(ssPins[0], RST_PIN); // Init each MFRC522 card
    mfrc522[0].PCD_DumpVersionToSerial();
}

bool PICC_IsAnyCardPresent() {
    byte bufferATQA[2];
    byte bufferSize = sizeof(bufferATQA);
    MFRC522::StatusCode result = mfrc522[0].PICC_WakeupA(bufferATQA, &bufferSize);
    Serial.print("Status Code: ");
    Serial.print(mfrc522[0].GetStatusCodeName(result));
    Serial.println();
    return (result == MFRC522::STATUS_OK || result == MFRC522::STATUS_COLLISION);
}

I get the following output with no card present

Init and check for any card
Reset complete (antenna off): 50
Firmware Version: 0x92 = v2.0
Init complete: 51
Status Code: Timeout in communication.
Check for card complete: 41

And with a card present

Init and check for any card
Reset complete (antenna off): 52
Firmware Version: 0x92 = v2.0
Init complete: 53
Status Code: Timeout in communication.
Check for card complete: 294

The Questions

Particularly given the first issue - does this sound like a hardware issue? No one else seems to have problems reading multiple cards without requiring a reset.

Should it be possible to solve the third issue? i.e. should an RFID reader be able to communicate with an RFID chip when the antenna is first switched on.

Upvotes: 2

Views: 4081

Answers (2)

RazVan
RazVan

Reputation: 46

Bit late, but perhaps someone will find these usefull..

https://github.com/miguelbalboa/rfid/issues/269#issuecomment-292783655 https://github.com/miguelbalboa/rfid/issues/269#issuecomment-472342583

// Function requires an integer assigned to specific reader
// If not multi-reader, just drop the [...]

void mfrc522_fast_Reset(int reader) {
  digitalWrite(RST_PIN, HIGH);

  mfrc522[reader].PCD_Reset();
  mfrc522[reader].PCD_WriteRegister(mfrc522[reader].TModeReg, 0x80); // TAuto=1; 

  // Timer starts automatically at the end of the transmission 
  // in all communication modes at all speeds

  mfrc522[reader].PCD_WriteRegister(mfrc522[reader].TPrescalerReg, 0x43); // 10μs.
  //  mfrc522.PCD_WriteRegister(mfrc522.TPrescalerReg, 0x20);   // test

  mfrc522[reader].PCD_WriteRegister(mfrc522[reader].TReloadRegH, 0x00);   
  // Reload timer with 0x064 = 30, ie 0.3ms before timeout.

  mfrc522[reader].PCD_WriteRegister(mfrc522[reader].TReloadRegL, 0x1E);
  //mfrc522.PCD_WriteRegister(mfrc522.TReloadRegL, 0x1E);

  mfrc522[reader].PCD_WriteRegister(mfrc522[reader].TxASKReg, 0x40);    
  // Default 0x00. Force a 100 % ASK modulation independent 
  //of the ModGsPReg register setting

  mfrc522[reader].PCD_WriteRegister(mfrc522[reader].ModeReg, 0x3D);   
  // Default 0x3F. Set the preset value for the CRC coprocessor 
  // for the CalcCRC command to 0x6363 (ISO 14443-3 part 6.2.4)

  mfrc522[reader].PCD_AntennaOn(); // Enable the antenna driver pins TX1 and TX2 
  // (they were disabled by the reset)
}

Upvotes: 2

Fruchtzwerg
Fruchtzwerg

Reputation: 11389

You forgot exit an authentificated PICC. Try to use the MFRC522::PCD_StopCrypto1() function.

Used to exit the PCD from its authenticated state. Remember to call this function after communicating with an authenticated PICC - otherwise no new communications can start.

You can use the method after dumping the information:

mfrc522.PICC_DumpToSerial(&(mfrc522.uid));

or directly before checking a new card (multiple calls are no problem):

mfrc522.PICC_IsNewCardPresent()

Upvotes: 2

Related Questions