STM32——NFC門(mén)禁模塊(RC522)(含代碼)

大家好,今天給大家介紹,文章末尾附有本畢業(yè)設(shè)計(jì)的論文和源碼的獲取方式,也可現(xiàn)在直接進(jìn)群免費(fèi)領(lǐng)取。

點(diǎn)擊這里找小助理0元領(lǐng)取:

1. 前言(包括一些個(gè)人理解)

(2021/11/1編輯)
在項(xiàng)目需要做一個(gè)NFC門(mén)禁功能的時(shí)候,突然發(fā)現(xiàn)有個(gè)RC522丟在我的桌面,甚至不知道它上面的引腳什么意思(還不會(huì)SPI通訊),搜索關(guān)鍵詞“RC522”去看博客搜索資料,發(fā)現(xiàn)了很多都在說(shuō)扇區(qū),塊,S50(M1)卡,然后就給代碼,一開(kāi)始我還以為S50是內(nèi)嵌在這個(gè)模塊里面的一個(gè)存儲(chǔ)器,然后越看越怪,后面去淘寶搜索S50,才發(fā)現(xiàn)S50其實(shí)是我們的門(mén)禁卡,RC522是用來(lái)感應(yīng)和判斷的。


  • PCD是接近式卡。PICC是接近式耦合設(shè)備。
  • 在通信過(guò)程中實(shí)際上是使用PCD命令控制RC522發(fā)出PICC命令與卡進(jìn)行交互。

2. RC522門(mén)禁工作過(guò)程


  • 過(guò)程:尋卡->防沖突->選卡->操作卡
  • PCD命令
/*MFRC522命令集,中文手冊(cè)P59*/ #define MFRC_IDLE              		0x00 //取消當(dāng)前命令的執(zhí)行 #define MFRC_TRANSMIT          		0x04 //發(fā)送FIFO緩沖區(qū)內(nèi)容 #define MFRC_RECEIVE           		0x08 //激活接收器接收數(shù)據(jù) #define MFRC_TRANSCEIVE        		0x0C //發(fā)送并接收數(shù)據(jù) #define MFRC_AUTHENT           		0x0E //執(zhí)行Mifare認(rèn)證(驗(yàn)證密鑰) #define MFRC_RESETPHASE        		0x0F //復(fù)位MFRC522 #define MFRC_CALCCRC           		0x03 //激活CRC計(jì)算 #define MFRC_NOCMDCHANGE            0x07 //無(wú)命令改變
  • PICC命令
/*Mifare1卡片命令字*/ #define PICC_REQIDL           	0x26 //尋天線區(qū)內(nèi)未進(jìn)入休眠狀態(tài)的卡 #define PICC_REQALL           	0x52 //尋天線區(qū)內(nèi)全部卡 #define PICC_ANTICOLL1        	0x93 //防沖撞 #define PICC_ANTICOLL2        	0x95 //防沖撞 #define PICC_AUTHENT1A        	0x60 //驗(yàn)證A密鑰 #define PICC_AUTHENT1B        	0x61 //驗(yàn)證B密鑰 #define PICC_READ             	0x30 //讀塊 #define PICC_WRITE            	0xA0 //寫(xiě)塊 #define PICC_DECREMENT        	0xC0 //減值(扣除) #define PICC_INCREMENT        	0xC1 //增值(充值) #define PICC_TRANSFER         	0xB0 //轉(zhuǎn)存(傳送) #define PICC_RESTORE          	0xC2 //恢復(fù)(重儲(chǔ)) #define PICC_HALT             	0x50 //休眠

3. CubeMx配置

3.1 SPI通訊的配置

打開(kāi)SPI模式設(shè)置為:Full-Duplex Master(全雙工主機(jī)模式)

  • 分頻設(shè)置為8~256都行,這樣隨之波特率也會(huì)改變,波特率越小通信速度越快
  • Clock Phase (CPHA) 設(shè)置為第一個(gè)上升沿這里一定要1Edge
  • 不開(kāi)啟CRC檢測(cè)

3.2 SDA和REST引腳的配置


隨后再定義兩個(gè)普通的OUTPUT輸出的引腳作為復(fù)位和使能引腳

4. 外設(shè)代碼函數(shù)編寫(xiě)

4.1 主函數(shù)能調(diào)用的接口函數(shù)

  • 初始化
/*************************************************************************************** * 函數(shù)名稱:PCD_Init * 功能描述:讀寫(xiě)器初始化 * 入口參數(shù):無(wú) * 出口參數(shù):無(wú) * 返 回 值:無(wú) * 說(shuō)    明:無(wú) ***************************************************************************************/
void PCD_Init(void)
{  MFRC_Init();      //MFRC管腳配置  PCD_Reset();      //PCD復(fù)位  并初始化配置  PCD_AntennaOff(); //關(guān)閉天線  PCD_AntennaOn();   //開(kāi)啟天線  PCD_Reset(); }
  • 尋卡
/*************************************************************************************** * 函數(shù)名稱:PCD_Request * 功能描述:尋卡 * 入口參數(shù): -RequestMode:尋卡方式 * PICC_REQIDL:尋天線區(qū)內(nèi)未進(jìn)入休眠狀態(tài) * PICC_REQALL:尋天線區(qū)內(nèi)全部卡 * -pCardType:用于保存卡片類型 * 出口參數(shù):-pCardType:卡片類型 * 0x4400:Mifare_UltraLight * 0x0400:Mifare_One(S50) * 0x0200:Mifare_One(S70) * 0x0800:Mifare_Pro(X) * 0x4403:Mifare_DESFire * 返 回 值:-status:錯(cuò)誤代碼(PCD_OK、PCD_NOTAGERR、PCD_ERR) * 說(shuō)    明:無(wú) ***************************************************************************************/
char PCD_Request(uint8_t RequestMode, uint8_t *pCardType)
{  int status;  uint16_t unLen;  uint8_t CmdFrameBuf[MFRC_MAXRLEN];  MFRC_ClrBitMask(MFRC_Status2Reg, 0x08);//關(guān)內(nèi)部溫度傳感器  MFRC_WriteReg(MFRC_BitFramingReg, 0x07); //存儲(chǔ)模式,發(fā)送模式,是否啟動(dòng)發(fā)送等  MFRC_SetBitMask(MFRC_TxControlReg, 0x03);//配置調(diào)制信號(hào)13.56MHZ  CmdFrameBuf[0] = RequestMode;  status = MFRC_CmdFrame(MFRC_TRANSCEIVE, CmdFrameBuf, 1, CmdFrameBuf, &unLen);  if((status == PCD_OK) && (unLen == 0x10))  {  *pCardType = CmdFrameBuf[0];  *(pCardType + 1) = CmdFrameBuf[1];  }  return status; }
  • 防沖撞

4.2 二級(jí)內(nèi)部調(diào)用函數(shù)

  • 宏定義
  • MFRC管腳配置
  • PCD復(fù)位 并初始化配置
  • 關(guān)閉天線
  • 開(kāi)啟天線
  • RC與M1卡通訊幀函數(shù)

4.3 第三級(jí)最底層函數(shù)

  • 讀一個(gè)寄存器
  • 設(shè)置寄存器的位
  • 清除寄存器的位

4.4 頭文件

5. 使用教程

//先用CubeMx初始化 PCD_Init();//RC522初始化 /*
* 函數(shù)功能:驗(yàn)證刷卡人,以及發(fā)送上位機(jī)刷卡人身份
* 參    數(shù):無(wú)
* 返 回 值:無(wú)
* 注    意:無(wú)
* 作    者:蘇釋州
*/ void NFC(void) { //尋卡 if (PCD_Request(PICC_REQALL, RxBuffer)!=0)//返回值為0,代表尋卡成功;并把卡類型存入RxBuffer中) { /*果然這里要清空一下不然就會(huì)亂,會(huì)有一些RxBuffer沒(méi)用的在那里占位*/ memset(RxBuffer, 0, sizeof(RxBuffer));//清空字符串 return;//如果不加這個(gè)判斷的話,則會(huì)無(wú)論尋卡是否成功都會(huì)有值000 } //防沖撞 if (PCD_Anticoll(RxBuffer)!=0)//防沖撞,完成這部就可以簡(jiǎn)單地 讀取卡號(hào) { memset(RxBuffer, 0, sizeof(RxBuffer));//清空字符串 return;//如果不加這個(gè)判斷的話,則會(huì)無(wú)論尋卡是否成功都會(huì)擾亂卡號(hào) } //處理卡號(hào)數(shù)據(jù) sprintf(Card_ID,"%x%x%x%x",RxBuffer[0],RxBuffer[1],RxBuffer[2],RxBuffer[3]); //對(duì)卡號(hào)進(jìn)行權(quán)限的判斷 if(strcmp(Card_ID,"b59dfcaa")==0)//賣(mài)家配的卡 {
		DoorControl(1);//開(kāi)門(mén) HAL_TIM_Base_Start_IT(&htim5);//開(kāi)門(mén)的時(shí)候開(kāi)啟定時(shí)器5的中斷,進(jìn)入關(guān)門(mén)計(jì)時(shí) memset(RxBuffer, 0, sizeof(RxBuffer));//清空字符串,這里要清除RxBuffer才行,否則Card_ID又會(huì)被組起來(lái) } else if(strcmp(Card_ID,"e1eff3cc")==0)//劉駿帆手機(jī)本科生證 {
		DoorControl(1);//開(kāi)門(mén) HAL_TIM_Base_Start_IT(&htim5);//開(kāi)啟定時(shí)器5的中斷 memset(RxBuffer, 0, sizeof(RxBuffer));//清空字符串,這里要清除RxBuffer才行,否則Card_ID又會(huì)被組起來(lái) } else {
		DoorControl(1);//開(kāi)門(mén) HAL_TIM_Base_Start_IT(&htim5);//開(kāi)啟定時(shí)器5的中斷 memset(RxBuffer, 0, sizeof(RxBuffer));//清空字符串 }
    HAL_Delay(100); return;
}

完整代碼可進(jìn)群免費(fèi)領(lǐng)取!!!

嵌入式物聯(lián)網(wǎng)的學(xué)習(xí)之路非常漫長(zhǎng),不少人因?yàn)閷W(xué)習(xí)路線不對(duì)或者學(xué)習(xí)內(nèi)容不夠?qū)I(yè)而錯(cuò)失高薪offer。不過(guò)別擔(dān)心,我為大家整理了一份150多G的學(xué)習(xí)資源,基本上涵蓋了嵌入式物聯(lián)網(wǎng)學(xué)習(xí)的所有內(nèi)容。點(diǎn)擊下方鏈接,0元領(lǐng)取學(xué)習(xí)資源,讓你的學(xué)習(xí)之路更加順暢!記得點(diǎn)贊、關(guān)注、收藏、轉(zhuǎn)發(fā)哦!

點(diǎn)擊這里找小助理0元領(lǐng)取:

the end

評(píng)論(0)