本keil c51程序适用uPC1621/uPC1622及兼容的红外遥控器芯片,占用外部中断0和定时器1,以中断方式解码,节省系统资源,以查询方式检测遥控信号是否有效.
解码思路:
红外线经一体化接受头解码放到后送到单片机的外部中断0,单片机设置外部中断下降沿触发,T0和T1为16位定时器,T0在系统启动后定时5ms.T1在外部中断0启动后开始定时,初值为0,每次在INT0中断后先读T1计数值,并重设初值为0,而且判断T1的计数值,
- //Fosc=11.0592MHz
- //statesforandvariablesIRdataprocessing;
- typedefenum{
- IR_idle,
- IR_waitstart,
- IR_getaddr,
- IR_getaddrinv,
- IR_getdata,
- IR_getdatainv
- }_IRstate;
- _IRstateIRstate=IR_idle;
- unsignedcharIRaddr=0xff;
- unsignedchar_IRaddr=0xff;
- unsignedcharIRdata=0xff;
- unsignedchar_IRdata=0xff;
- unsignedcharIR_repeat=0;
- unsignedcharIR_ready=0;
- unsignedcharIR_poweron=0;
- //bitir_done=0;
- //timeconstants
- unsignedintIRtimer=0;//IRtimeout
- //cpu初始化
- voidcpu_init(void)
- {
- TMOD=0X11;//T0andT1十六位定时
- TH0=0xee;//fosc=11.0592M,timer=5ms
- TL0=0x00;
- TR0=1;//runtimer0;
- TF0=0;
- ET0=1;//enabletmr0overflowinterrupt
- IT0=1;//int0edgesensitive
- EX0=1;//enable"int0"
- EA=1;//globalinteruptenable
- }
- //T0中断
- voidtmrint()interrupt1
- {
- TH0=0xee;
- TL0=0x00;
- if(IRtimer)//IR接收超时
- --IRtimer;//
- else
- {
- IRstate=IR_idle;
- //IR_poweron=0;
- }
- }
- //Fosc=11.0592MHz
- #definemsec_12p50x2d00
- #definemsec_150x3600
- #definemsec_90x2066
- //#definemsec_90x1066
- #definemsec_2p50x900
- #definemsec_0p90x33d
- #definemsec_1p680x610
- //voidIRint()interrupt0(void)
- //WhentheIRreceivepingoeslowandinterruptisgenerated
- //IRiscollectedbystartingtimer2inthefirstfallingedgeofthepin
- //thenoneveryotherfallingedge,thetimervalueissavedandthetimerrestarted.
- //thecapturedtimeisthenusedtogettheIRdata
- //a"startofdata"is13.5Msec,a"1"is2.25Msec,a"0"is1.12msecanda"repeat"is11.25msec.
- //thecounterincrementsat1.085Usec
- //Iallowafairlylargetolerancetotimejitterbuttherearenofalsetriggersseen.
- voidIRint()interrupt0
- {
- staticunsignedcharbits;
- unsignedshorttime;
- switch(IRstate)
- {
- caseIR_idle:
- TL1=0;
- TH1=0;
- TR1=1;
- IRstate=IR_waitstart;
- IRtimer=26;
- break;
- caseIR_waitstart://P2_4=!P2_4;
- TR1=0;
- time=TH1;
- time=(time<<8)+TL1;;
- TL1=0;
- TH1=0;
- TR1=1;
- if((time>msec_12p5)&&(time<msec_15))//greaterthan12.5Msec&lessthan15msec=startcode
- {
- IRaddr=0;
- _IRaddr=0;
- IRdata=0;
- _IRdata=0;
- bits=1;
- IRstate=IR_getaddr;
- }
- elseif((time>msec_9)&&(time<msec_12p5))//lessthan12.5Msecandgreaterthan9msec=Repeatcode
- {
- IR_repeat=2;
- IRstate=IR_idle;
- }
- else
- {//toshort,baddatajustgotoidle
- IRstate=IR_idle;
- }
- break;
- caseIR_getaddr://P2_4=!P2_4;
- TR1=0;
- time=TH1;
- time=(time<<8)+TL1;;
- TL1=0;
- TH1=0;
- TR1=1;
- if((time>msec_2p5)||(time<msec_0p9))//if>2.5msecorshorterthan.9Msecbaddata,gotoidle
- {
- IRstate=IR_idle;
- break;
- }
- if(time>msec_1p68)//greaterthan1.68Msecisa1
- {
- IRaddr|=bits;
- }
- bits=bits<<1;
- if(!bits)
- {
- IRstate=IR_getaddrinv;
- bits=1;
- }
- break;
- caseIR_getaddrinv://P2_4=!P2_4;
- TR1=0;
- time=TH1;
- time=(time<<8)+TL1;;
- TL1=0;
- TH1=0;
- TR1=1;
- if((time>msec_2p5)||(time<msec_0p9))//if>2.5msecorshorterthan.9Msecbaddata,gotoidle
- {
- IRstate=IR_idle;
- break;
- }
- if(time>msec_1p68)//greaterthan1.68Msecisa1
- {
- _IRaddr|=bits;
- }
- bits=bits<<1;
- if(!bits)
- {
- IRstate=IR_getdata;;
- bits=1;
- }
- break;
- caseIR_getdata:
- TR1=0;
- time=TH1;
- time=(time<<8)+TL1;;
- TL1=0;
- TH1=0;
- TR1=1;
- if((time>msec_2p5)||(time<msec_0p9))//if>2.5msecorshorterthan.9Msecbaddata,gotoidle
- {
- IRstate=IR_idle;
- break;
- }
- if(time>msec_1p68)//greaterthan1.68Msecisa1
- {
- IRdata|=bits;
- }
- bits=bits<<1;
- if(!bits)
- {
- IRstate=IR_getdatainv;
- bits=1;
- }
- break;
- caseIR_getdatainv:
- TR1=0;
- time=TH1;
- time=(time<<8)+TL1;;
- TL1=0;
- TH1=0;
- TR1=1;
- if((time>msec_2p5)||(time<msec_0p9))//if>2.5msecorshorterthan.9Msecbaddata,gotoidle
- {
- IRstate=IR_idle;
- break;
- }
- if(time>msec_1p68)//greaterthan1.68Msecisa1
- {
- _IRdata|=bits;
- }
- bits=bits<<1;
- if(!bits)//wehaveitall,nowwemakesureitisaNECcodefromtheCHSIRtransmitter
- {//makesureaddress,~addressarecorrect,data,~dataarecorrectandaddressis0.
- IR_ready=((IRaddr^_IRaddr)==0xff)&&((IRdata^_IRdata)==0xff)&&(IRaddr==0);
- if(IR_ready)
- {
- IRstate=IR_idle;
- }
- }
- break;
- default:
- IRstate=IR_idle;
- break;
- }
- }
- voidmain(void)
- {
- cpu_init();
- while(1)
- {
- if(IR_ready)
- {
- IR_ready=0;
- switch(IRdata)
- {
- case0x45://1
- //yourcode
- break;
- case0x44://3
- //yourcode
- break;
- case0x43://4
- //yourcode
- break;
- case0x08://prev
- //yourcode
- break;
- case0x5a://next
- //yourcode
- break;
- default:
- break;
- &n bsp;}
- }
- }
- }