今天給51黑電子論壇的朋友們共享一個功能很全的密碼鎖proteus仿真,是用51單片機制作的,下面是原理圖:
0.png (44.54 KB, 下載次數: 70)
下載附件
2016-10-9 21:57 上傳
0.png (69.67 KB, 下載次數: 55)
下載附件
2016-10-9 21:58 上傳
單片機密碼鎖仿真工程文件及所有完整程序等資料下載地址:
http://www.zg4o1577.cn/bbs/dpj-56304-1.html
密碼鎖的51單片機源程序:
- #include<AT89x51.h>
- #include"intrins.h"
- #include"key.h"
- #include"xsh.h"
- #include"24c02.h"
- #define ulong unsigned long
- bit BJCB=0;//報警標志
- XG=0,//修改密碼標志位
- BJ=0,//報警標志位
- SJ=0;//鎖鍵盤標志位
- // xg=0;//修改密碼標志位
- uchar PSWD0_0[16]={0};//密碼輸入緩存存儲單元
- //uchar code PSWD0_1[16]={1,2,3,4,5,6,7,8,1,2,3,4,5,6,7,8};//用戶初始密碼存儲單元
- //uchar PSWD1_0[16]={0};//讀出密碼緩存存儲單元
- uchar PSWD1_1[16]={1,2,3,4,5,6,7,8,1,2,3,4,5,6,7,8};////管理員初始密碼存儲單元
- sbit OUT=P3^5;//輸出端口
- sbit L1=P0^2;//上電指示
- sbit L2=P0^1;//開鎖指示
- sbit L3=P0^0;//報警指示
- uint mg=0,//密碼個數
- KSC=0,//開鎖次數
- BJC=0,//報警次數
- TCNTY=0,//用戶按鍵定時次數累加
- TCNTG=0,//管理員輸入密碼定時次數
- yhsh,//用戶輸入標志位
- glsh,//管理員輸標志位
- shw;//密碼輸完標志位
- void yhmimaxig();//密碼修改程序
- void glmimaxig();//管理員修改程序
- void bjyin(ulong t)
- {
- ulong c;
- uint n;
- for(c=0;c<t;c++)
- {
- for(n=0;n<50;n++); //延時
- BEEP=~BEEP; //取反輸出到喇叭的信號
- }
- }
- void delay_10ms(void)
- {
- uint i = 1000;
- while(i--);
- }
- //////////////定時中斷服務函數//////////////////////////////////////
- void timer0() interrupt 1
- {
- uint i;
- TH0=(65536-50000)/256; //對TH0 TL0賦值50MS定時
- TL0=(65536-50000)%256; //重裝計數初值
- if(yhsh==1)
- {
- TCNTY++;//用戶定時計數
- if(shw==1)
- {
- TR0=0;
- TCNTY=0;
- }
- if(TCNTY==400)
- {
- TR0=0;//關閉T0定時器
- TCNTY=0;
- mg=0;//密碼個數清零
- L1=1;
- for(i=0;i<2;i++)//聲光報警電路
- {
- L3=0;
- bjyin(1000);
- L3=1;
- delay(1000);
- }
- L1=0;
- }
- }
- else if(glsh==1)
- {
- TCNTG++;//管理員定時計數
- if(shw==1)
- {
- TR0=0;
- TCNTG=0;
- }
- if(TCNTG==400)
- {
- TR0=0;//關閉T0定時器
- TCNTG=0;
- mg=0;//密碼個數清零
- L1=1;
- for(i=0;i<2;i++)//聲光報警電路
- {
- L3=0;
- bjyin(1000);
- L3=1;
- delay(1000);
- }
- L1=0;
- }
- }
- }
-
- void main()
- {
- uint i;
- TMOD=0x01; //定時器工作在方式1
- ET0=1;
- EA=1;
- TH0=(65536-50000)/256; //對TH0 TL0賦值
- TL0=(65536-50000)%256; //使定時器0.05秒中斷一次
- //Read_page24c02(0x00,PSWD1_1,16);//向24c02里讀用戶初始密碼
- //i2cWrite24LC16B(0,0X20);
- /////////////第一次向24c02里寫入初始管理員密碼、用戶密碼、開鎖次數/////////////////////
- for(i=0;i<16;i++) //用一次寫一個向24c02里寫
- {
- i2cWrite24LC16B(PSWD1_1[i],i);
- delay_10ms;
- }
- for(i=0;i<16;i++) //用一次寫一個向24c02里寫
- {
- i2cWrite24LC16B(PSWD1_1[i],0x10+i);
- delay_10ms;
- } //proteus仿真時用,燒程序時,第一次用,第二次不用。
- KSC=i2cRead24LC16B(0X20);
- loop: L1=0;//上電紅燈亮
- L2=1;//開鎖成功后綠燈亮
- L3=1;//輸錯時黃燈亮報警
- OUT=0;//開信號關閉
- display_0(KSC);//開鎖前顯示
-
- ///////////密碼輸入/////////////////
- if(SJ==0)//鎖鍵盤標志位為0
- {
- do
- {
- flag=0;//鍵盤標志位
- key();
- if(flag==1&&num==12) //判斷是否為管理員功能鍵按下
- {
- goto gl;
- }
- if(flag==1&&num<=9)
- {
- PSWD0_0[mg]=num;
- mg++;//密碼個數
- }
- if(flag==1&&num==14&&mg>=1)//輸入錯誤刪除
- {
- mg=mg-1;
- }
- if(mg==1) //有密碼鍵按下開定時器限時
- {
- TR0=1;
- yhsh=1;
- }
- }
- while(num!=15);
- if(mg!=16)
- {
- for(i=mg;i<16;i++)
- {
- PSWD0_0[i]=0;
- }
- }
- /////////////////密碼比較電路////////////////////////////
- if(flag==1&&num==15)
- { flag=0;
- yhsh=0;
- shw=1;
- num=0;
- for(i=0;i<16;i++) //從24c02里讀出16個密碼
- {
- PSWD1_1[i]=i2cRead24LC16B(i);
- delay_10ms;
- }
- for(i=0;i<16;i++)
- {
- if(PSWD1_1[i]!=PSWD0_0[i])
- {
- BJCB=1;
- break;
- }
- else
- BJCB=0;
-
- }
- }
- if(BJCB!=0)
- {
- BJC++;
- if(BJC!=3)
- {
- BJCB=0; //第一次和第二次報警
- delay(500);
- mg=0;//密碼個數清零
- L1=1;
- for(i=0;i<3;i++)//聲光報警電路
- {
- L3=0;
- display_3();
- bjyin(1000);
- L3=1;
- delay(1000);
- }
- goto loop;
- }
- else if(BJC==3)
- {
- BJC=0;
- BJCB=0;
- display_5();//三次輸入密碼失敗,自鎖
- SJ=1;//鎖鍵盤標志位
- mg=0;//密碼個數清零
- L1=1;
- for(i=0;i<2;i++)//聲光報警電路
- {
- L3=0;
- bjyin(1000);
- L3=1;
- delay(1000);
- }
- goto loop;
- }
- }
- else
- if(BJCB==0)
- {
- KSC++;
- display_1(KSC);
- i2cWrite24LC16B(KSC,0X20);
- if(KSC==100)
- {
- SJ=1;
- }
- L2=0;
- L1=1;
- OUT=1;
- mg=0;//密碼個數清零
- loop1:do //鍵盤掃描等待功能鍵按下
- {
- flag=0;
- key();
- if(flag)
- {
- flag=0;
- switch(num)
- {
- case 13:
- {
- display_2();
- do
- {
- flag=0;//鍵盤標志位
- key();
- if(flag==1&&num<=9)
- {
- PSWD0_0[mg]=num;
- mg++;//密碼個數
- }
- if(flag==1&&num==14&&mg>=1)//輸入錯誤刪除
- {
- mg=mg-1;
- }
- if(mg==16)
- {
- do //鍵盤掃描等待功能鍵按下
- {
- flag=0;
- key();
- }
- while(num!=15);
- }
- }
- while(num!=15);
- if(mg!=16&&num==15)
- {
- for(i=mg;i<16;i++)
- {
- PSWD0_0[i]=0;
- }
- }
- if(flag==1&&num==15)
- {
- flag=0;
- mg=0;
- for(i=0;i<16;i++) //用一次寫一個向24c02里寫
- {
- i2cWrite24LC16B(PSWD0_0[i],i);
- delay_10ms;
- }
- display_1(KSC);
- do //鍵盤掃描等待功能鍵按下
- {
- flag=0;
- key();
- }
- while(num!=11); //按下返回鍵,鎖鎖返回
- {
- goto loop;
- }
- }
- };break;
-
- case 11: {
- goto loop;
- //break;
- }
- }
- }
- }
- while(flag!=0);//如果設置密碼鍵按下
- goto loop1;
- // i2cWrite24c02_page(0x00,PSWD1_1,mg);
- }
- }
- else
- {
- do
- {
- flag=0;
- key();
- }
- while(num!=12);//判斷是否為管理員功能鍵按下
- gl:do//管理員輸入密碼
- {
- flag=0;
- key();
- if(flag==1&&num<=9)
- {
- PSWD0_0[mg]=num;
- mg++;//密碼個數
- }
- if(flag==1&&num==14&&mg>=1)//刪除鍵按下
- {
- mg=mg-1;
- }
- if(mg==1)
- {
- TR0=1;
- }//開定時器TO限5秒開鎖
- }
- while(num!=15);
- if(mg!=16&&num==15)
- {
- for(i=mg;i<16;i++)
- {
- PSWD0_0[i]=0;
- }
- }
- //////////管理員密碼比較///////////////////////
- //Read_page24c02(0x10,PSWD0_1,16)
- for(i=0;i<16;i++) //從24c02里讀出16個密碼
- {
- PSWD1_1[i]=i2cRead24LC16B((0x10+i));
- delay_10ms;
- }
- if(flag==1&&num==15)
- { flag=0;
- shw=1;
- num=0;
- for(i=0;i<mg;i++)
- {
- if(PSWD1_1[i]!=PSWD0_0[i])
- { BJCB=1;
- break;
- }
- else
- BJCB=0;
- }
- }
- if(BJCB!=0)
- {
- BJC++;
- if(BJC!=3)
- {
- BJCB=0; //第一次和第二次報警
-
- mg=0;//密碼個數清零
- L1=1;
- for(i=0;i<2;i++)//聲光報警電路
- {
- L3=0;
- display_3();
- bjyin(1000);
- L3=1;
- delay(1000);
- }
- display_1(KSC);
- goto loop;
- }
- else
- {
- BJCB=0;
- display_5();//三次輸入密碼失敗,自鎖
- mg=0;//密碼個數清零
- delay(10000);
- display_1(KSC);
- goto loop;
- }
- }
- else
- {
- SJ=0;
- display_4();//管理員開鎖顯示
- mg=0;
- L2=0;
- L1=1;
- L3=0;//密碼個數清零
- do //鍵盤掃描等待功能鍵按下
- {
- flag=0;
- key();
- }
- while(flag==0); //如果設置密碼鍵按下
- if(flag==1&&num==13)
- {
- flag=0;
- display_2();
- do
- {
- flag=0;//鍵盤標志位
- key();
- if(flag==1&&num<=9)
- {
- PSWD0_0[mg]=num;
- mg++;//密碼個數
- }
- if(flag==1&&num==14&&mg>=1)//輸入錯誤刪除
- {
- mg=mg-1;
- }
- if(mg==16)
- {
- do //鍵盤掃描等待功能鍵按下
- {
- flag=0;
- key();
- }
- while(num!=15);
- }
- }
- while(num!=15);
- if(mg!=16&&num==15)
- {
- for(i=mg;i<16;i++)
- {
- PSWD0_0[i]=0;
- }
- }
- if(flag==1&&num==15)
- {
- flag=0;
- mg=0;
- for(i=0;i<16;i++) //用一次寫一個向24c02里寫
- {
- i2cWrite24LC16B(PSWD0_0[i],(0x10+i));
- delay_10ms;
- }
- display_4();
- do //鍵盤掃描等待功能鍵按下
- {
- flag=0;
- key();
- }
- while(num!=11); //按下返回鍵,鎖鎖返回
- {
- goto loop;
- }
- }
- }
- if(flag==1&&num==10)
- {
- KSC=0;
- i2cWrite24LC16B(KSC,0X20);
- display_1(KSC);
- do //鍵盤掃描等待功能鍵按下
- {
- flag=0;
- key();
- }
- while(num!=11);//按下返回鍵,鎖鎖返回
- goto loop;
- }
- if(flag==1&&num==11)//按下返回鍵,鎖鎖返回
- {
- goto loop;
- }
- }
- }
- }
復制代碼
|