; ; IR Decode ; Decode and display NEC IR codes ; Derived from IR Widget ; 2006-10-19 Revision 1.00 ; ; Keivn Timmerman ; irwidget [@t] compendiumarcana [d0t] com ; www.compendiumarcana.com/irwidget ; include #define FIRSTREG 0x20 #define PGMSIZE 1024 ; Configuration bits __config _CPD_OFF & _CP_OFF & _BODEN_ON & _MCLRE_OFF & _PWRTE_ON & _WDT_ON & _INTRC_OSC_CLKOUT errorlevel -220 ; Stupid MPLAB complains about IDLOCS org 0x2000 ; IDLOCS ;dw 'I','R','D','0' ; IR Decode Rev 0 errorlevel +220 BANK1 equ 0x80 ; Reduce assembler whining radix dec ; Default radix of decimal ; --- I/O ; 8 Ground ; bMode equ 0 ; 7 pMode equ GPIO ; bSerTx equ 1 ; 6 Serial data to host PC pSerTx equ GPIO ; bIRDetect equ 2 ; 5 IR Detector module input pIRDetect equ GPIO ; bDTR equ 3 ; 4 DTR pDTR equ GPIO ; bOscOut equ 4 ; 3 Osc Out ; bIRDemod equ 5 ; 2 IR Demodulator module input pIRDemod equ GPIO ; ; 1 Power ; asio_out_port set pSerTx asio_out_bit set bSerTx cblock FIRSTREG ; Registers last_time asio_data asio_flags asio_bit_time temp1 time_save ir_state ir_bit ir_data0 ir_data1 ir_data2 ir_data3 endc org 0x0000 ; - Start of program memory nop ; clrf GPIO ; All outputs off goto skip_isr ; Jump over the ISR ; org 0x0004 ; - ISR goto $ ; Let the watchdog handle this ; ; skip_isr ; ; - Initiailize periferals ; ; movlw (1<=10 btfsc STATUS,C ; addlw 'A'-('0'+10) ; >=10, use offset of 'A' addlw '0'+10 ; Offset of '0' ;goto asio_tx ; ; ; ; ; ; ----- Async serial transmission ----- asio_tx ; bsf asio_out_port,asio_out_bit ; Start bit clrwdt ; Clear watchdog movwf asio_data ; Move W to tx data register movlw 9 ; 8 data bits + stop bit movwf asio_flags ; call asio_delay ; Wait one bit time nop ; asiotbl ; rrf asio_data,F ; Shift out a bit btfsc STATUS,C ; Is it a zero? goto $+4 ; No.. nop ; Precise timing bsf asio_out_port,asio_out_bit ; goto $+3 ; bcf asio_out_port,asio_out_bit ; goto $+1 ; call asio_delay ; Wait one bit time decfsz asio_flags,F ; Dec bit count goto asiotbl ; Not zero, do next bit... retlw 0 ; Return ; ; ; asio_delay ; --- Delay N + 14 cycles with one cycle granularity ; Special case of 0xFF will delay only 9 cycles ; W=1, C=1 upon exit ; comf asio_bit_time,W ; Get compliment of bit time to W bsf STATUS,C ; Carry must be set upon exit btfsc STATUS,Z ; Test for special case of max bit rate (0xFF) retlw 1 ; Max rate, exit without delay... btfsc asio_bit_time,0 ; Add one cycle if bit 0 of bit time is set goto $+1 ; btfss asio_bit_time,1 ; Add two cycles if bit 1 of bit time is set goto $+3 ; goto $+1 ; nop ; #ifdef CORE12 ; addwf four,W ; 12 bit core lacks addlw, so use addwf with a constant ; stored in a register #else ; addlw 4 ; Add 4 to W until overflow #endif ; btfss STATUS,C ; Each loop interation takes 4 cycles goto $-2 ; retlw 1 ; Set W to 1 and return ; ; ; end ; ;