RFID? NFC? Wat is dat eigenlijk?
In dit artikel laten we je zien hoe je ID-tags kunt lezen. De focus van het artikel is de PN532 NFC RFID module.
De module is gebaseerd op de NXP PN532 chip. Deze chipset wordt veel gebruikt op het gebied van NFC (Near Field Communication). Een voorwerp dat NFC ondersteunt, vaak een chequekaart met een NFC-chip, wordt tegen een NFC-lezer gehouden. Hierdoor kan in een fractie van een seconde informatie worden uitgewisseld.
Klinkt dat abstract? Als je een nieuwere EC-kaart hebt en die gebruikt voor contactloos betalen, dan ken je NFC zelfs uit het dagelijks leven. Door de kaart op de betaalterminal te leggen, wordt de transactie gestart - snel en eenvoudig.
We willen graag wat dieper ingaan op de technische processen hierachter. De PN532 module is hiervoor bij uitstek geschikt, omdat hij zowel I2C als SPI ondersteunt. Het gewenste communicatietype kan direct op het PN532 bord worden geselecteerd door de schakelaars om te zetten. De stand van de schakelaars die nodig zijn voor de respectieve interfaces vind je rechts van het schakelschema, dat iets verderop op de pagina staat.
Het schakelschema:
Tip: Je kunt hier een hoge resolutie versie van deze afbeelding vinden. Daar kun je de pintoewijzing wat beter zien.
De programmacode (I2C versie)
//*******************************************************************************************************
//** Voorbeeldschets voor het lezen van ID-tags. Als de ID overeenkomt, wordt PIN 13 gedurende 2 seconden ingeschakeld **
//** ingeschakeld (LED). Als de ID fout is, wordt er een toon gegenereerd op pin 12. (PASSIEVE zoemer / piezzo) **
//** gebruik. In plaats van een LED kan ook een deurslot worden geschakeld (via TIP120 schakelversterker **
//*******************************************************************************************************
#include <Wire.h> // Bibliotheek voor het I2C-protocol
#include <Adafruit_PN532.h> // Bibliotheek voor de NFC/RFID module!!! Gelieve te laden via Arduino IDE !!!
#define PN532_IRQ (2) // Definieer de IRQ connector
#define PN532_RESET (3) // Definieer de reset-aansluiting
const int AlarmPin = 12; // Pin 12 uitgang voor piëzoluidspreker
const int OutputPin = 13; // Pin 13 uitgang voor LED of via TIP120 naar een magnetisch slot
unsigned long cardid; // Variabele voor het gelezen TAG-ID
unsigned long TAGid1 = 1702536620; // Hier kunnen ID's worden ingevoerd die geaccepteerdmoeten worden
unsigned long TAGid2 = 4070796058; // Anders leeg laten. De ID van individuele TAGs kunnen worden ingevoerd met
unsigned long TAGid3 ; // de seriële monitor (stel 115200 baud in)
Adafruit_PN532 nfc(PN532_IRQ, PN532_RESET); // instantie met I2C-protocol aanmaken
void setup() // start setup-functie
pinMode(AlarmPin, OUTPUT); // Pin definiëren als uitgang
pinMode(OutputPin, OUTPUT); // Definieer PINals uitgang
Serial.begin(115200); // Open seriële transmissie met 115200 baud (ser monitor dezelfde baud-instelling!)
Serial.println("Hello!"); // Stuur tekst "Hello!" naar seriële monitor
nfc.begin(); // Start communicatie met RFID lezer
unsigned long versiondata = nfc.getFirmwareVersion(); // Versienummer van firmware lezen
als (! versiondata) { // Wenn keine Antwort kommt
Serial.print("Kann kein Board finden !"); // Sende Text "Kann kein..." an seriellen Monitor
while (1); // so lange Stopp
}
Serial.print("Chip PN5 gevonden"); Serial.println((versiondata >> 24) & 0xFF, HEX); // Stuur tekst en versie-info naar seriëlepoort van RFID-lezer
Serial.print("Firmware ver. "); Serial.print((versiondata >> 16) & 0xFF, DEC); // Controleer wanneer er antwoord komt van de printplaat
Serial.print('.'); Serial.println((versiondata >> 8) & 0xFF, DEC); //
nfc.SAMConfig(); // Configureer het bord om RFID-tags te lezen
Serial.println("Wachten op een ISO14443A chip ..."); // Stuur tekst die wacht naar seriële monitor
}
void loop() { // Lusfunctie starten
uint8_t succes; // Variabele aanmaken
uint8_t uid[] = { 0, 0, 0, 0, 0, 0, 0 }; // Buffer om de UID op te slaan
uint8_t uidLength; // Lengte van de UID (4 of 7 bytes afhankelijk van ISO14443A Card/Chip Type)
// Wacht op een ISO14443A chip. Als er een wordt gedetecteerd, wordt de variabele // gevuld met de UID
// gevuld met de UID. Afhankelijk van de // lengte (4 bytes (Mifare Classic) of
7 bytes (Mifare Ultralight) wordt het // kaarttype herkend.
succes = nfc.readPassiveTargetID(PN532_MIFARE_ISO14443A, uid, &uidLength);
if (succes) { // Indien gedetecteerd, proces....
Serial.println("ISO14443A kaart gevonden");
Serial.print(" UID Lengte: "); Serial.print(uidLength, DEC); Serial.println(" bytes");
Serial.print(" UID Waarde: ");
nfc.PrintHex(uid, uidLength); // informatie uitvoeren naar seriële monitor
als (uidLength == 4) { // Hat die Karte/der Chip 4 byte Länge...
// Mifare Classic Karte
cardid = uid[0]; //
cardid <<= 8; // Setze die 4 byte Blöcke
cardid |= uid[1]; //
cardid <<= 8; // zu einem einzigen Block
cardid |= uid[2]; //
cardid <<= 8; // zusammen
cardid |= uid[3]; //
Serial.print("Scheint eine Mifare Classic zu sein #"); //
Serial.println(cardid); // Gib die Informationen aus
Serial.println(""); //
Serial.println(""); //
}
als ((cardid) == (TAGid1)||(cardid) == (TAGid2)||(cardid) == (TAGid3)) // vraag of de TAGs 1..2..3 verbonden zijn met de respectievelijke
{digitalWrite(OutputPin,HIGH); // überein stimmt. Dann schalte je nach dem
delay(2000);
digitalWrite(OutputPin,LOW);} // aan of uit
anders
{tone(AlarmPin, 1000); // Und gib ggf. einen Ton/Frequenz aus
delay(4000);
noTone(AlarmPin);}
// Einde IF query/lus
// Einde van de lus
De programmacode (SPI-versie)
//*******************************************************************************************************
//** Voorbeeldschets voor het lezen van ID-tags. Als de ID geschikt is, wordt PIN 13 ** gedurende 2 seconden
//** ingeschakeld (LED). Als de ID fout is, wordt er een toon gegenereerd op pin 12. (PASSIEVE zoemer / piezzo) **
//** gebruik. In plaats van een LED kan ook een deurslot worden geschakeld (via TIP120 schakelversterker **
//*******************************************************************************************************
#include <Wire.h> // Bibliotheek voor het I2C-protocol
#include <SPI.h> // Bibliotheek voor het SPI-protocol
#include <Adafruit_PN532.h> // Bibliotheek voor de NFC/RFID module !!! Gelieve te laden via Arduino IDE !!!
const byte PN532_SCK = 2; //
const byte PN532_MOSI =3; // Definieer de aansluitingen voor
const byte PN532_SS = 4; // de SPI-verbinding naar de RFID
const byte PN532_MISO =5; // Board
const int AlarmPin = 12; // Definieer de aansluitingen voor
const int OutputPin = 13; // de (schakelende) uitgangen
unsigned long cardid; // Variabele voor de gelezen TAG-ID
unsigned long TAGid1 = 1702536620; // Hier kunnen ID's worden ingevoerd die geaccepteerdmoeten worden
unsigned long TAGid2 = 4070796058; // Anders leeg laten. De ID van individuele TAGs kunnen worden ingevoerd met
unsigned long TAGid3 ; // de seriële monitor (stel 115200 baud in)
Adafruit_PN532 nfc(PN532_SCK, PN532_MISO, PN532_MOSI, PN532_SS); // instantie aanmaken met SPI-protocol
void setup() // Start setup-functie
pinMode(AlarmPin, OUTPUT); // Pin definiëren als uitgang
pinMode(OutputPin, OUTPUT); // DefinieerPIN als uitgang
Serial.begin(115200); // Open seriële transmissie met 115200 baud (ser monitor dezelfde baud-instelling!)
Serial.println("Hello!"); // Stuur tekst "Hello!" naar seriële monitor
nfc.begin(); // Start communicatie met RFID lezer
unsigned long versiondata = nfc.getFirmwareVersion(); // Versienummer van firmware lezen
als (! versiondata) { // Wenn keine Antwort kommt
Serial.print("Kann kein Board finden !"); // Sende Text "Kann kein..." an seriellen Monitor
while (1); // so lange Stopp
}
Serial.print("Chip PN5 gevonden"); Serial.println((versiondata >> 24) & 0xFF, HEX); // Stuur tekst en versie-informatie naarde seriëlepoort van RFID-lezer
Serial.print("Firmware ver. "); Serial.print((versiondata >> 16) & 0xFF, DEC); // Controleer wanneer er antwoord komt van de printplaat
Serial.print('.'); Serial.println((versiondata >> 8) & 0xFF, DEC); //
nfc.SAMConfig(); // Configureer het bord om RFID-tags te lezen
Serial.println("Wachten op een ISO14443A chip ..."); // Stuur tekst die wacht naar seriële monitor
}
void loop() { // Lusfunctie starten
uint8_t succes; // Variabele aanmaken
uint8_t uid[] = { 0, 0, 0, 0, 0, 0, 0 }; // Buffer om de UID op te slaan
uint8_t uidLength; // Lengte van de UID (4 of 7 bytes afhankelijk van ISO14443A Card/Chip Type)
// Wacht op een ISO14443A chip. Als er een wordt gedetecteerd, wordt de variabele // gevuld met de UID
// gevuld met de UID. Afhankelijk van de // lengte (4 bytes (Mifare Classic) of
7 bytes (Mifare Ultralight) wordt het // kaarttype herkend.
succes = nfc.readPassiveTargetID(PN532_MIFARE_ISO14443A, uid, &uidLength);
if (succes) { // Indien gedetecteerd, proces....
Serial.println("ISO14443A kaart gevonden");
Serial.print(" UID Lengte: "); Serial.print(uidLength, DEC); Serial.println(" bytes");
Serial.print(" UID Waarde: ");
nfc.PrintHex(uid, uidLength); // informatie uitvoeren naar seriële monitor
als (uidLength == 4) { // Hat die Karte/der Chip 4 byte Länge...
// Mifare Classic Karte
cardid = uid[0]; //
cardid <<= 8; // Setze die 4 byte Blöcke
cardid |= uid[1]; //
cardid <<= 8; // zu einem einzigen Block
cardid |= uid[2]; //
cardid <<= 8; // zusammen
cardid |= uid[3]; //
Serial.print("Scheint eine Mifare Classic zu sein #"); //
Serial.println(cardid); // Gib die Informationen aus
Serial.println(""); //
Serial.println(""); //
}
als ((cardid) == (TAGid1)||(cardid) == (TAGid2)||(cardid) == (TAGid3)) // vraag of de TAGs 1..2..3 verbonden zijn met de respectievelijke
{digitalWrite(OutputPin,HIGH); // überein stimmt. Dann schalte je nach dem
delay(2000);
digitalWrite(OutputPin,LOW);} // aan of uit
anders
{tone(AlarmPin, 1000); // Und gib ggf. einen Ton/Frequenz aus
delay(4000);
noTone(AlarmPin);}
// Einde IF query/lus
// Einde van de lus
Feedback 2 zum Sketch
Funktioniert. Man muss die Baud-Rate bei serial Monitor richtig einstellen, hier 115200