diff --git a/include/controller.h b/include/controller.h index 48d25b2..c961c77 100644 --- a/include/controller.h +++ b/include/controller.h @@ -17,6 +17,8 @@ private: void _check_buttons(); bool _debounce_button(uint8_t index); uint32_t _get_rfid_card_uid(); + String _read_rfid_data(); + bool _rfid_present = false; uint32_t _last_rfid_card_uid = 0; uint8_t _no_rfid_card_count = 0; Player* _player; diff --git a/src/controller.cpp b/src/controller.cpp index 84bcad4..747ed8f 100644 --- a/src/controller.cpp +++ b/src/controller.cpp @@ -59,11 +59,28 @@ uint32_t Controller::_get_rfid_card_uid() { } void Controller::_check_rfid() { - uint32_t uid = _get_rfid_card_uid(); - if (uid != _last_rfid_card_uid) { + MFRC522::StatusCode status; + if (_rfid_present) { + byte buffer[2]; + byte buffer_size = 2; + _spi->select_rc522(); + status = _rfid->PICC_WakeupA(buffer, &buffer_size); + if (status == MFRC522::STATUS_OK) { + // Card is still present. + _rfid->PICC_HaltA(); + _spi->select_rc522(false); + return; + } + _spi->select_rc522(false); + // Card is now gone + _rfid_present = false; + INFO("No more RFID card.\n"); + _player->stop(); + } else { + uint32_t uid = _get_rfid_card_uid(); if (uid > 0) { _mqtt_client->publish_rfid_uid(uid); - _no_rfid_card_count = 0; + //_no_rfid_card_count = 0; String temp = String(uid, HEX); String s_uid = ""; for (int i=0; i<(8-temp.length()); i++) { @@ -71,65 +88,67 @@ void Controller::_check_rfid() { } s_uid.concat(temp); INFO("New RFID card uid: %s\n", s_uid.c_str()); + _rfid_present = true; + + String data = _read_rfid_data(); + _player->play_id(s_uid); - - - DEBUG("Trying to read RFID data..."); - _spi->select_rc522(); - String data = ""; - MFRC522::MIFARE_Key key; - for (int i=0; i<6; i++) key.keyByte[i]=0xFF; - MFRC522::PICC_Type type = _rfid->PICC_GetType(_rfid->uid.sak); - MFRC522::StatusCode status; - uint8_t sectors = 0; - switch(type) { - case MFRC522::PICC_TYPE_MIFARE_MINI: sectors = 5; break; - case MFRC522::PICC_TYPE_MIFARE_1K: sectors = 16; break; - case MFRC522::PICC_TYPE_MIFARE_4K: sectors = 40; break; - default: INFO("Unknown PICC type %s\n", String(MFRC522::PICC_GetTypeName(type)).c_str()); + } + } +} + +String Controller::_read_rfid_data() { + _spi->select_rc522(); + DEBUG("Trying to read RFID data...\n"); + + String data = ""; + MFRC522::MIFARE_Key key; + key.keyByte[0] = 0xD3; + key.keyByte[1] = 0xF7; + key.keyByte[2] = 0xD3; + key.keyByte[3] = 0xF7; + key.keyByte[4] = 0xD3; + key.keyByte[5] = 0xF7; + MFRC522::PICC_Type type = _rfid->PICC_GetType(_rfid->uid.sak); + + uint8_t sectors = 0; + switch(type) { + case MFRC522::PICC_TYPE_MIFARE_MINI: sectors = 5; break; + case MFRC522::PICC_TYPE_MIFARE_1K: sectors = 16; break; + case MFRC522::PICC_TYPE_MIFARE_4K: sectors = 40; break; + default: INFO("Unknown PICC type %s\n", String(MFRC522::PICC_GetTypeName(type)).c_str()); + } + + for (uint8_t sector=1; sectorPCD_Authenticate(MFRC522::PICC_CMD_MF_AUTH_KEY_A, block_offset, &key, &_rfid->uid); + if (status != MFRC522::STATUS_OK) { + DEBUG("PCD_Authenticate() for sector %d failed: %s\n", sector, String(_rfid->GetStatusCodeName(status)).c_str()); + continue; + } + + for (uint8_t block=0; blockMIFARE_Read(block_offset + block, buffer, &byte_count); + if (status != MFRC522::STATUS_OK) { + DEBUG("MIFARE_Read() failed: %s\n", String(_rfid->GetStatusCodeName(status)).c_str()); + continue; } - - for (uint8_t sector=0; sectorPCD_Authenticate(MFRC522::PICC_CMD_MF_AUTH_KEY_A, block_offset, &key, &_rfid->uid); - if (status != MFRC522::STATUS_OK) { - DEBUG("PCD_Authenticate() failed: %s\n", String(_rfid->GetStatusCodeName(status)).c_str()); - continue; - } - - for (uint8_t block=0; blockMIFARE_Read(block_offset + block, buffer, &byte_count); - if (status != MFRC522::STATUS_OK) { - DEBUG("MIFARE_Read() failed: %s\n", String(_rfid->GetStatusCodeName(status)).c_str()); - continue; - } - for (int i=0; i<16; i++) { - if (buffer[i]!=0x00) data.concat(buffer[i]); - } - } - } - - _rfid->PICC_HaltA(); - _rfid->PCD_StopCrypto1(); - _spi->select_rc522(false); - - DEBUG("Data from RFID: %s", data.c_str()); - - } else { - if (_no_rfid_card_count >= 1) { - INFO("No more RFID card.\n"); - _player->stop(); - } else { - _no_rfid_card_count++; - return; + for (int i=0; i<16; i++) { + if (buffer[i]>=0x20 && buffer[i]<0x7F) data.concat((char)buffer[i]); } } - _last_rfid_card_uid = uid; } + + _rfid->PICC_HaltA(); + _rfid->PCD_StopCrypto1(); + DEBUG("Data from RFID: %s", data.c_str()); + _spi->select_rc522(false); + return data; } void Controller::_check_serial() {