本設計開發了一款基于單片機的指紋識別電子密碼鎖系統。該系統以ATmeg16單片機作為模塊核心,通過串口通信控制ZAZ-010指紋模塊實現錄取指紋并存儲指紋數據,并通過HS12864-15C液晶顯示比對流程及比對結果,輔以直流繼電器與發光二極管模擬開鎖的動作。本系統具有體積小、性價比高、傳輸速度快、適合家庭及單位使用。
程序的巡檢過程: 首先對各模塊進行初始化,檢測在有無按鍵按下,如果按下判斷是那一個按鍵,并作出判斷是否調用相應子程序;當按鍵1按下后,調用通信模塊子程序,錄入指紋并將其存入模塊緩沖區,同理當按鍵2按下后,效果相同。
依次當按鍵3按下時,將指紋模塊兩緩沖區中的指紋特征文件合成特征模板并存儲與指紋模板庫中,當4按鍵按下后搜索指紋并比對.當指紋模塊中有指紋存儲時直接按4鍵同樣也可進行比對。
程序關鍵的就是對指紋模塊的通信控制, 考慮到處理過程太過冗長,限于篇幅只能將其省略,如需查看,可以看附錄1。其它命令發送子函數因大部分的命令大體格式基本相同。
液晶鍵盤測試程序見附錄2:
液晶鍵盤測試程序結果如圖 4-3所示:
- #include<avr/io.h>
- #include<util/delay.h>
- //#include<avr/pgmspace.h>
- #define uchar unsigned char
- #define uint unsigned int
- #define key1 0x01
- #define key2 0x02
- #define key3 0x04
- #define key4 0x08
- static uchar k=0;
- uchar name00[]={" "};
- uchar name01[]={" 歡迎使用 "};
- uchar name02[]={"單片機指紋密碼鎖"};
- uchar name03[]={" "};
- uchar name04[]={" 指紋采集開始 "};
- uchar name05[]={" 指紋對比開始 "};
- uchar name06[]={" 指紋存儲開始 "};
- uchar name07[]={" 一次采集 "};
- uchar name08[]={" 二次采集 "};
- uchar name09[]={" 錄入成功 "};
- uchar name10[]={" 錄入失敗 "};
- uchar name11[]={" 收包有錯 "};
- uchar name12[]={"傳感器上無手指 "};
- uchar name13[]={" 生成特征成功 "};
- uchar name14[]={"圖想亂生不成特征"};
- uchar name15[]={"圖象正常特征點少"};
- uchar name16[]={"指紋模板合并成功"};
- uchar name17[]={"指紋模板合并失敗"};
- uchar name18[]={" 非同一手指 "};
- uchar name19[]={" 存儲成功 "};
- uchar name20[]={" 寫指紋庫出錯 "};
- uchar name21[]={" 指紋匹配 "};
- uchar name22[]={" 指紋不匹配 "};
- uchar name23[]={" 密碼正確 "};
- uchar name24[]={" 密碼不正確 "};
- uchar FP_1[6]={};
- uchar FP_2[6]={};
- uchar FP_Pack_Head[6]={0xEF,0x01,0xFF,0xFF,0xFF,0xFF}; //協議包頭
- uchar FP_Get_Img[6]={0x01,0x00,0x03,0x01,0x0,0x05}; //獲得指紋圖像
- uchar FP_Search_0_9[11]={0x01,0x0,0x08,0x04,0x01,0x0,0x0,0x0,0x13,0x0,0x21}; //搜索0-9號指紋
- uchar FP_Img_To_Buffer1[7]={0x01,0x0,0x04,0x02,0x01,0x0,0x08}; //將圖像放入到BUFFER1
- uchar FP_Img_To_Buffer2[7]={0x01,0x0,0x04,0x02,0x02,0x0,0x09}; //將圖像放入到BUFFER2
- uchar FP_Reg_Model[6]={0x01,0x0,0x03,0x05,0x0,0x09}; //將BUFFER1跟BUFFER2合成特征模版
- volatile uchar FP_Save_Finger1[9]={0x01,0x00,0x06,0x06,0x01,0x00,0x0B,0x00,0x19};//將BUFFER1中的特征碼存放到指定的位置
- volatile uchar FP_Save_Finger2[9]={0x01,0x00,0x06,0x06,0x01,0x00,0x0C,0x00,0x1A};//將BUFFER1中的特征碼存放到指定的位置
- volatile uchar FP_Save_Finger3[9]={0x01,0x00,0x06,0x06,0x01,0x00,0x0D,0x00,0x1B};//將BUFFER1中的特征碼存放到指定的位置
- uchar yb=0x80;
- //初始化 UART 子程序
- void UART_Init(void)
- {
- UCSRB = 0x00; //disable while setting baud rate
- UCSRA = 0x00; //Bit1為1則倍速發送
- UCSRC = 0x06; //傳送一楨數據位為8位
- UBRRL = 0x07; //波特率:57600 Bps
- UBRRH = 0x00; //誤差率:0.000%
- UCSRB = 0x18;
- }
- //發送八位數據
- void UART_Send_Byte( uchar ucData)
- {
- while(!(UCSRA&(1<<UDRE))); //等待緩沖區為空
- UDR = ucData;
- }
- //接收八位數據
- uchar UART_Receive_Byte(void)
- {
- while(!(UCSRA&(1<<RXC)));//等待緩沖區為空
-
- return UDR;
- }
- //_獲得指紋圖像命令
- void Cmd_Get_Img(void)
- {
- uchar i,j;
- for(i=0;i<6;i++) //發送包頭與模塊地址
- UART_Send_Byte(FP_Pack_Head[i]);
- for(i=0;i<6;i++) //發送命令 0x1d
- UART_Send_Byte(FP_Get_Img[i]);
- for(i=0;i<6;i++)
- FP_1[i]=UART_Receive_Byte();
- for(i=0;i<6;i++)
- FP_2[i]=UART_Receive_Byte();
- j=FP_2[3];
- if (j==0x00)
- {_delay_ms(100000);
- reset ();
- display6();}
- if (j==0x01)
- {reset();
- wr_com(yb);
- outChinese(0x90,8,name11);}
- if (j==0x02)
- {_delay_ms(100000);
- reset();
- display7();}
- if (j==0x03)
- { reset();
- wr_com(yb);
- outChinese(0x90,8,name10);}
- }
- //講圖像轉換成特征碼存放在Buffer1中
- void Cmd_Img_To_Buffer1(void)
- {
- uchar i,j;
- for(i=0;i<6;i++) //發送包頭與模塊地址
- {
- UART_Send_Byte(FP_Pack_Head[i]);
- }
-
- for(i=0;i<7;i++) //發送命令 將圖像轉換成 特征碼 存放在 CHAR_buffer1
- {
- UART_Send_Byte(FP_Img_To_Buffer1[i]);
- }
- for(i=0;i<6;i++)
- {
- FP_1[i]=UART_Receive_Byte();}
- for(i=0;i<6;i++)
- {
- FP_2[i]=UART_Receive_Byte();}
- j=FP_2[3];
- if (j==0x00)
- {_delay_ms(100000);
- reset ();
- display8();}
- if (j==0x06)
- {_delay_ms(100000);
- reset ();
- display9();}
- if (j==0x07)
- {_delay_ms(100000);
- reset ();
- display10();}
- }
- //將圖像轉換成特征碼存放在Buffer2中
- void Cmd_Img_To_Buffer2(void)
- {
- uchar i,j;
- for(i=0;i<6;i++) //發送包頭
- {
- UART_Send_Byte(FP_Pack_Head[i]);
- }
-
- for(i=0;i<7;i++) //發送命令 將圖像轉換成 特征碼 存放在 CHAR_buffer2
- {
- UART_Send_Byte(FP_Img_To_Buffer2[i]);
- }
- for(i=0;i<6;i++)
- {
- FP_1[i]=UART_Receive_Byte();}
- for(i=0;i<6;i++)
- {
- FP_2[i]=UART_Receive_Byte();}
- j=FP_2[3];
- if (j==0x00)
- {_delay_ms(100000);
- reset ();
- display8();}
- if (j==0x06)
- {_delay_ms(100000);
- reset ();
- display9();}
- if (j==0x07)
- {_delay_ms(100000);
- reset ();
- display10();}
- }
- //將BUFFER1 跟 BUFFER2 中的特征碼合并成指紋模版
- void Cmd_Reg_Model(void)
- {
- uchar i,j;
- for(i=0;i<6;i++) //發送包頭與模塊地址
- {
- UART_Send_Byte(FP_Pack_Head[i]);
- }
- for(i=0;i<6;i++) //命令合并指紋模版
- {
- UART_Send_Byte(FP_Reg_Model[i]);
- }
- for(i=0;i<6;i++)
- {
- FP_1[i]=UART_Receive_Byte();}
- for(i=0;i<6;i++)
- {
- FP_2[i]=UART_Receive_Byte(); }
- j=FP_2[3];
- if (j==0x00)
- {_delay_ms(400000);
- reset ();
- display11();}
- if (j==0x0a)
- {_delay_ms(400000);
- reset ();
- display12();
- while(1);}
- }
- //將并成后的指紋模版存儲到指紋模塊flash模板庫中
- void Store_Char_Model(void)
- { uchar i,j;
- for(i=0;i<6;i++) //發送包頭與模塊地址
- {
- UART_Send_Byte(FP_Pack_Head[i]);
- }
- if(k==0)
- { for(i=0;i<9;i++) //命令存儲指紋模版
- {
- UART_Send_Byte( FP_Save_Finger1[i] );
- }
- }
- if(k==1)
- { for(i=0;i<9;i++) //命令存儲指紋模版
- {
- UART_Send_Byte( FP_Save_Finger2[i] );
- }
- }
- if(k==2)
- { for(i=0;i<9;i++) //命令存儲指紋模版
- {
- UART_Send_Byte( FP_Save_Finger3[i] );
-
- }
- }
- for(i=0;i<6;i++)
- {
- FP_1[i]=UART_Receive_Byte();}
- for(i=0;i<6;i++)
- {
- FP_2[i]=UART_Receive_Byte(); }
- j=FP_2[3];
- if(j==0x00)
- {_delay_ms(400000);
- reset ();
- display13();}
- if(j==0x18)
- {_delay_ms(300000);
- reset ();
- display14();}
- }
- //搜索與BUFFER1中特征碼相符合的指紋模版
- void search_Char_Mode(void)
- { uchar i,j;
- for(i=0;i<6;i++) //發送包頭與模塊地址
- {
- UART_Send_Byte(FP_Pack_Head[i]);
- }
- for(i=0;i<11;i++) //命令搜索指紋模版
- {
- UART_Send_Byte(FP_Search_0_9[i]);
-
- }
- for(i=0;i<6;i++)
- {
- FP_1[i]=UART_Receive_Byte();}
- for(i=0;i<10;i++)
- {
- FP_2[i]=UART_Receive_Byte(); }
- j=FP_2[3];
- if(j==0x00)
- {_delay_ms(100000);
- reset ();
- display15();}
- if(j==0x09)
- {_delay_ms(100000);
- reset ();
- display16();}
- void keyboard( void)
- { unsigned char Keyvalue;//鍵盤值
- //端口初始化
- DDRC=~_BV(PC0)& ~_BV(PC1)& ~_BV(PC2)& ~_BV(PC3);
- while(1)
- { Keyvalue=(PINC&0x0F);
- if (Keyvalue!=0x0f)
- {//有鍵按下
- _delay_ms(20);
- Keyvalue=(PINC&0x0F);
- if (Keyvalue==0X0F)
- break;//如果延時去抖后,沒有檢測到鍵按下,退出本次循環
- //如果有按鍵
- if(! (Keyvalue& key1))
- {reset ();
- display2();
- UART_Init();
- Cmd_Get_Img();
- Cmd_Img_To_Buffer1();
- }//按鍵1的處理部分
- if(! (Keyvalue& key2))
- { reset ();
- display3();
- UART_Init();
- Cmd_Get_Img();
- Cmd_Img_To_Buffer2();
- }//按鍵2的處理部分
- if(! (Keyvalue& key3))
- { reset ();
- display4();
- UART_Init();
- Cmd_Reg_Model();
- Store_Char_Model();
- k++; }//按鍵3的處理部分
- if(! (Keyvalue& key4))
- { reset ();
- display5();
- UART_Init();
- Cmd_Get_Img();
- Cmd_Img_To_Buffer1();
- search_Char_Mode();
- }//按鍵4的處理部分
- }
- _delay_ms(20);
- }
- }
- void check_busy (void) //讀取忙碌狀態
- {
- DDRA=0;
- PORTA=0xff;
- PORTB&=0xfb; //RS=0
- PORTB|=0x02; //RW=1;
- PORTB|=0x01;PORTB|=0x01; //E=1;
- while((PINA&0x80)==0x80);
- PORTB&=0xfe;
- //E =0;
- }
- void wr_com(unsigned char value) //寫指令,寫指令時必須為RS=0;RW=0;
- {check_busy();
- PORTB&=0xfe; //E=0;
- PORTB&=0xfb; //RS=0
- PORTB&=0xfd; //RW=0;
- DDRA=0xff;
- PORTA=value;
- PORTB|=0x01; //E=1;
- _delay_us(20); //如果沒有延時就必須要加查忙指令
- PORTB&=0xfe;
- DDRA=0x00; //E=0;
- }
- void wr_data(unsigned char sj) //寫數據,寫數據時必須為 RS=1;RW=0;
- {check_busy();
- PORTB&=0xfe; //E=0;
- PORTB|=0x04; //RS=1;
- PORTB&=0xfd; //RW=0;
- DDRA=0xff;
- PORTA=sj;
- PORTB|=0x01; //E=1;
- _delay_us(20); //如果沒有延時就必須要加查忙指令
- PORTB&=0xfe;
- DDRA=0x00; ////E=0;
- }
- void reset (void)
- {
- wr_com(0x01);//清屏
- wr_com(0x08);//關顯示
- wr_com(0x03);//歸位
- wr_com(0x30);//功能設置
- wr_com(0x0f);//開顯示
- wr_com(0x01);//清屏
- }
- //******************************************************************/
- //outChinese 為函數名
- //place 為顯示地址的首地址
- //unit 字符長度
- //charcode[] 要顯示數據的內容
- void outChinese(unsigned char place,unsigned char unit,unsigned char charcode[] )
- {
- unsigned char i;
- wr_com(place);
- for(i=0;i<unit*2;i++)//一個漢字為兩個字符
- wr_data(charcode[i]);
- }
- void display1(void)
- {wr_com(yb);
- //ydgb();
- outChinese(0x80,8,name00);//第一行:80-87H
- outChinese(0x90,8,name01);//第二行:90-97H
- outChinese(0x88,8,name02);//第三行:88-8FH
- outChinese(0x98,8,name03);//第四行:98-9FH
-
- }
復制代碼 以上的Word格式文檔51黑下載地址:
設計文檔.doc
(1.27 MB, 下載次數: 14)
2020-12-18 09:54 上傳
點擊文件名下載附件
|