안녕하세요. 애드라이프입니다.
정말 오랜만에 아두이노 포스팅을 하는것 같네요.
이번에 제가 준비한 녀석?은 RFID-RC522모듈입니다.
우선 실물부터 보시겠습니다.
제가 구입한 모듈은 납땜이 안되어있는 상태의
모듈입니다. 단가차이가 좀 나거든요.
그래도 납땜하기가 어려우신 분들은 땜된걸로
구입하시기 바랍니다.
짜잔!! 저는 납땜하는데 아무런 문제가 없기때문에
바로 납땜해버렸죠!! 후훗!!
자! 이제 모듈도 사용할 준비가 되었습니다.
실제로 TEST하기 전에 간단하게 해당 모듈의
스팩을 살펴보도록 하겠습니다.
RFID
Radio-Frequency IDentification
전파를 이용해 먼 거리에서 정보를 인식하는 기술.
그 예와 기술에 대한 자세한 정보는 나무위키 참고!!
우리가 사용하고자하는 RFID-RC522모듈은
동작전압 : +3.3V
소비전류 : 13~26mA
동작 주파수 : 13.56Mhz
지원하는 카드(tag) : Mifarel S50, Mifarel S70,
Mifare UltraLight, Mifare Pro, Mifare DESfire
오늘 TEST할 Tag는 아래보이는 하얀색 RFID CARD입니다.
이 카드는 1Kbyte의 데이터를 저장할 수 있습니다.
이번시간에는 RFID-RC522모듈을 통해서
위 카드의 정보를 읽어오는 방법을 설명하겠습니다.
[ 하드웨어 구성 ]
RFID-RC522 | 아두이노(Arduino) UNO |
RST | 9 |
SPI SDA | 10 |
SPI MOSI | 11 |
SPI MISO | 12 |
SPI SCK | 13 |
VCC | +3.3V |
GND | GND |
위 배선도와 아래 표를 함께 보시면
이해하는데 어렵지 않을 것입니다.
회로구성은 마무리되었습니다.
우리가 읽고자 하는 RFID TAG는
총 64개의 블럭이 존재합니다.
그리고 블럭 4개씩 묶어 하나의 Sector를 구성하죠
그리고 Sector의 마지막 블럭은 키데이터를
지니고 있습니다.
좀 더 자세한 설명은 다음 포스팅에서 하도록하고
이번 포스팅에는 바로 프로그램으로 넘어가겠습니다.
아래 두가지 셈플코드를 다운받아 주세요.
< RFID 라이브러리 파일 >
< RFID Master 라이브러리 파일 >
라이브러리 추가방법은 아래 링크를 참고해주세요.
라이브러리 추가가 끝나면
추가한 라이브러리중 rfid-master폴더 안의
examples폴더에 DumpInfo.ino파일을
실행시켜서 아두이노에 업로드 합니다.
/*
* --------------------------------------------------------------------------------------------------------------------
* Example sketch/program showing how to read data from a PICC to serial.
* --------------------------------------------------------------------------------------------------------------------
* This is a MFRC522 library example; for further details and other examples see: https://github.com/miguelbalboa/rfid
*
* Example sketch/program showing how to read data from a PICC (that is: a RFID Tag or Card) using a MFRC522 based RFID
* Reader on the Arduino SPI interface.
*
* When the Arduino and the MFRC522 module are connected (see the pin layout below), load this sketch into Arduino IDE
* then verify/compile and upload it. To see the output: use Tools, Serial Monitor of the IDE (hit Ctrl+Shft+M). When
* you present a PICC (that is: a RFID Tag or Card) at reading distance of the MFRC522 Reader/PCD, the serial output
* will show the ID/UID, type and any data blocks it can read. Note: you may see "Timeout in communication" messages
* when removing the PICC from reading distance too early.
*
* If your reader supports it, this sketch/program will read all the PICCs presented (that is: multiple tag reading).
* So if you stack two or more PICCs on top of each other and present them to the reader, it will first output all
* details of the first and then the next PICC. Note that this may take some time as all data blocks are dumped, so
* keep the PICCs at reading distance until complete.
*
* @license Released into the public domain.
*
* Typical pin layout used:
* -----------------------------------------------------------------------------------------
* MFRC522 Arduino Arduino Arduino Arduino Arduino
* Reader/PCD Uno Mega Nano v3 Leonardo/Micro Pro Micro
* Signal Pin Pin Pin Pin Pin Pin
* -----------------------------------------------------------------------------------------
* RST/Reset RST 9 5 D9 RESET/ICSP-5 RST
* SPI SS SDA(SS) 10 53 D10 10 10
* SPI MOSI MOSI 11 / ICSP-4 51 D11 ICSP-4 16
* SPI MISO MISO 12 / ICSP-1 50 D12 ICSP-1 14
* SPI SCK SCK 13 / ICSP-3 52 D13 ICSP-3 15
*/
#include <SPI.h>
#include <MFRC522.h>
#define RST_PIN 9 // Configurable, see typical pin layout above
#define SS_PIN 10 // Configurable, see typical pin layout above
MFRC522 mfrc522(SS_PIN, RST_PIN); // Create MFRC522 instance
void setup() {
Serial.begin(9600); // Initialize serial communications with the PC
while (!Serial); // Do nothing if no serial port is opened (added for Arduinos based on ATMEGA32U4)
SPI.begin(); // Init SPI bus
mfrc522.PCD_Init(); // Init MFRC522
mfrc522.PCD_DumpVersionToSerial(); // Show details of PCD - MFRC522 Card Reader details
Serial.println(F("Scan PICC to see UID, SAK, type, and data blocks..."));
}
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));
}
이렇게 되어있는 소스코드입니다.
업로드가 완료되고 시리얼 모니터를 실행시켜
결과가 아래와 같으면 성공적으로 정보를 읽어온것입니다.
이 수많은 데이터 중에서
정작쓰이는 데이터는 그렇게 많지 않습니다.
잘 생각해보면 우리가 이런 RFID기술을 쓰는 이유는
사용자를 구분하기 위해서가 아닐까요?
회사의 사원증이나 도서관의 출입증, 학생증 등등
그럼 카드마다 고유의 정보를 가지고 있고
해당 정보를 리더기에서 기억하고 있다가
허가를 해줄것인지 거부를 할것인지
정해주기만하면 우리도 얼마든지 RFID 기술을
응용 할 수 있다는 이야기다 됩니다.
여기서 간단하게 소량의 데이터를 가지고
위에서 말한 사용자 구분을 할 수있는 방법을 알려드립니다.
여기까지만 할 줄 알아도 졸업작품들에 응용하는데
어려움이 없을것이라 생각합니다!!
위에서 rfid-master에서 샘플코드를 가져왔다면
이번에는 AddicoreRFID폴더 안에서 Sample폴더의
Addicore_RFID_Example.ino를 실행시켜 업로드합니다.
// Example sketch to read the ID from an Addicore 13.56MHz RFID tag
// as found in the RFID AddiKit found at:
// http://www.addicore.com/RFID-AddiKit-with-RC522-MIFARE-Module-RFID-Cards-p/126.htm
#include <AddicoreRFID.h>
#include <SPI.h>
#define uchar unsigned char
#define uint unsigned int
//4 bytes tag serial number, the first 5 bytes for the checksum byte
uchar serNumA[5];
uchar fifobytes;
uchar fifoValue;
AddicoreRFID myRFID; // create AddicoreRFID object to control the RFID module
/////////////////////////////////////////////////////////////////////
//set the pins
/////////////////////////////////////////////////////////////////////
const int chipSelectPin = 10;
const int NRSTPD = 5;
//Maximum length of the array
#define MAX_LEN 16
void setup() {
Serial.begin(9600); // RFID reader SOUT pin connected to Serial RX pin at 9600bps
// start the SPI library:
SPI.begin();
pinMode(chipSelectPin,OUTPUT); // Set digital pin 10 as OUTPUT to connect it to the RFID /ENABLE pin
digitalWrite(chipSelectPin, LOW); // Activate the RFID reader
pinMode(NRSTPD,OUTPUT); // Set digital pin 10 , Not Reset and Power-down
digitalWrite(NRSTPD, HIGH);
myRFID.AddicoreRFID_Init();
}
void loop()
{
uchar i, tmp, checksum1;
uchar status;
uchar str[MAX_LEN];
uchar RC_size;
uchar blockAddr; //Selection operation block address 0 to 63
String mynum = "";
str[1] = 0x4400;
//Find tags, return tag type
status = myRFID.AddicoreRFID_Request(PICC_REQIDL, str);
if (status == MI_OK)
{
Serial.println("RFID tag detected");
Serial.print(str[0],BIN);
Serial.print(" , ");
Serial.print(str[1],BIN);
Serial.println(" ");
}
//Anti-collision, return tag serial number 4 bytes
status = myRFID.AddicoreRFID_Anticoll(str);
if (status == MI_OK)
{
checksum1 = str[0] ^ str[1] ^ str[2] ^ str[3];
Serial.println("The tag's number is : ");
//Serial.print(2);
Serial.print(str[0]);
Serial.print(" , ");
Serial.print(str[1],BIN);
Serial.print(" , ");
Serial.print(str[2],BIN);
Serial.print(" , ");
Serial.print(str[3],BIN);
Serial.print(" , ");
Serial.print(str[4],BIN);
Serial.print(" , ");
Serial.println(checksum1,BIN);
// Should really check all pairs, but for now we'll just use the first
if(str[0] == 156) //You can change this to the first byte of your tag by finding the card's ID through the Serial Monitor
{
Serial.print("Hello Craig!\n");
} else if(str[0] == 244) { //You can change this to the first byte of your tag by finding the card's ID through the Serial Monitor
Serial.print("Hello Erin!\n");
}
Serial.println();
delay(1000);
}
myRFID.AddicoreRFID_Halt(); //Command tag into hibernation
}
위와 같은 코드입니다.
해당 코드는 자신이 가지고 있는 카드정보를
수정하기 전의 코드입니다.
이대로 실행해서 결과를 한번 보겠습니다.
RFID-RC522 rfid-master ample code 실행결과를보면
제가 가지고 있는 RFID CARD의 UID는
0x22 0xA9 0x75 0x1D입니다.(HEX코드)
하지만 수정 전 Addicore_RFID_Example.ino의
마지막 부분을 보면
if (status == MI_OK)
{
checksum1 = str[0] ^ str[1] ^ str[2] ^ str[3];
Serial.println("The tag's number is : ");
//Serial.print(2);
Serial.print(str[0]);
Serial.print(" , ");
Serial.print(str[1],BIN);
Serial.print(" , ");
Serial.print(str[2],BIN);
Serial.print(" , ");
Serial.print(str[3],BIN);
Serial.print(" , ");
Serial.print(str[4],BIN);
Serial.print(" , ");
Serial.println(checksum1,BIN);
// Should really check all pairs, but for now we'll just use the first
if(str[0] == 156) //You can change this to the first byte of your tag by finding the card's ID through the Serial Monitor
{
Serial.print("Hello Craig!\n");
} else if(str[0] == 244) { //You can change this to the first byte of your tag by finding the card's ID through the Serial Monitor
Serial.print("Hello Erin!\n");
}
Serial.println();
delay(1000);
}
UID 첫번째 부분의 값이 156(10진수)일때와 244(10진수)일때
문구를 띄워주는 형식으로 되어있습니다.
그렇다면 이 부분을 자신이 가지고 있는 카드의 정보와
맞게 고처주면 사용자 구분을 할 수 있다는 이야기가됩니다.
밑에 UID비교부분과 표현되는 방식을 16진수로 바꾼
프로그램을 첨부하겠습니다.
(제 카드의 UID첫번째 부분이 0x22였으니 10진수로 34입니다.)
// Example sketch to read the ID from an Addicore 13.56MHz RFID tag
// as found in the RFID AddiKit found at:
// http://www.addicore.com/RFID-AddiKit-with-RC522-MIFARE-Module-RFID-Cards-p/126.htm
#include <AddicoreRFID.h>
#include <SPI.h>
#define uchar unsigned char
#define uint unsigned int
//4 bytes tag serial number, the first 5 bytes for the checksum byte
uchar serNumA[5];
uchar fifobytes;
uchar fifoValue;
AddicoreRFID myRFID; // create AddicoreRFID object to control the RFID module
/////////////////////////////////////////////////////////////////////
//set the pins
/////////////////////////////////////////////////////////////////////
const int chipSelectPin = 10;
const int NRSTPD = 5;
//Maximum length of the array
#define MAX_LEN 16
void setup() {
Serial.begin(9600); // RFID reader SOUT pin connected to Serial RX pin at 9600bps
// start the SPI library:
SPI.begin();
pinMode(chipSelectPin,OUTPUT); // Set digital pin 10 as OUTPUT to connect it to the RFID /ENABLE pin
digitalWrite(chipSelectPin, LOW); // Activate the RFID reader
pinMode(NRSTPD,OUTPUT); // Set digital pin 10 , Not Reset and Power-down
digitalWrite(NRSTPD, HIGH);
myRFID.AddicoreRFID_Init();
}
void loop()
{
uchar i, tmp, checksum1;
uchar status;
uchar str[MAX_LEN];
uchar RC_size;
uchar blockAddr; //Selection operation block address 0 to 63
String mynum = "";
str[1] = 0x4400;
//Find tags, return tag type
status = myRFID.AddicoreRFID_Request(PICC_REQIDL, str);
if (status == MI_OK)
{
Serial.println("RFID tag detected");
Serial.print(str[0],HEX);
Serial.print(" , ");
Serial.print(str[1],HEX);
Serial.println(" ");
}
//Anti-collision, return tag serial number 4 bytes
status = myRFID.AddicoreRFID_Anticoll(str);
if (status == MI_OK)
{
checksum1 = str[0] ^ str[1] ^ str[2] ^ str[3];
Serial.println("The tag's number is : ");
//Serial.print(2);
Serial.print(str[0],HEX);
Serial.print(" , ");
Serial.print(str[1],HEX);
Serial.print(" , ");
Serial.print(str[2],HEX);
Serial.print(" , ");
Serial.print(str[3],HEX);
Serial.print(" , ");
Serial.print(str[4],HEX);
Serial.print(" , ");
Serial.println(checksum1,HEX);
// Should really check all pairs, but for now we'll just use the first
if(str[0] == 34) //You can change this to the first byte of your tag by finding the card's ID through the Serial Monitor
{
Serial.print("Hello AddLife Studio!\n");
} else if(str[0] == 244) { //You can change this to the first byte of your tag by finding the card's ID through the Serial Monitor
Serial.print("Hello Erin!\n");
}
else{
Serial.print("Access Failure\n");
}
Serial.println();
delay(1000);
}
myRFID.AddicoreRFID_Halt(); //Command tag into hibernation
}
수정된 프로그램의 결과를 보도록 하겠습니다.
결과를 보면 표현방식이 바이너리방식에서 Hex로
변경되었고 첫번째 22를 판독하여 Hellow AddLife Studio
라는 문구를 띄우는데 성공하였습니다!!
바이너리방식에서 Hex방식으로 바꾼이유는
앞의 전체 블럭을 읽어오는 프로그램과
표현방식을 동일하게 하여 좀더 보기 편하게
하기 위함입니다. :)
이번 포스팅은 여기까지 입니다.
다음 포스팅에서는 읽기뿐 아니라 쓰기까지 해볼 예정입니다.
그리고 이론에 대해서도 좀더 자세히 알아보겠습니다.
더욱 유익한 포스팅으로 돌아오겠습니다.
by 애드라이프
'아두이노 > 아두이노 중급' 카테고리의 다른 글
아두이노(Arduino) 중급 RFID - RC522 모듈로 NFC사용하기 #2 (심화편!!) (1) | 2020.05.02 |
---|---|
아두이노(Arduino) 중급 WIFI모듈 NodeMCU(ESP8266) - LED제어(Blynk) (0) | 2018.12.15 |
아두이노(Arduino) 중급 WIFI모듈 WeMos D1 R2 - LED제어(Blynk) (0) | 2018.12.14 |
아두이노(Arduino) 중급 WIFI모듈 WeMos D1 Mini 3편 - LED제어 (0) | 2018.12.11 |
아두이노(Arduino) 중급 WIFI모듈 WeMos D1 Mini 2편 - Blynk설치 (0) | 2018.12.10 |