Code:
LIST P=16F676 ; DIRECTIVE TO DEFINE PROCESSOR ;-------------------------------------------------------------------------------------------------------------------------------------- ; VARIABLES USED IN BANK 0 (HEX 20-5F), ALSO ACCESSABLE FROM FROM BANK 1 (HEX A0-DF) EEPROMCOUNT EQU 0X49 ; USED IN THE FIVE-FOLD EEPROM SAVE EEPROMADDR EQU 0X50 ; USED IN THE FIVE-FOLD EEPROM SAVE EEPROMDATA EQU 0X51 ; USED IN THE FIVE-FOLD EEPROM SAVE MAJORITY EQU 0x52 ; USED IN THE EEPROM LOAD SUBROUTINE TO CALCULATE THE RESULT OF THE MAJORITY CHECK ;-------------------------------------------------------------------------------------------------------------------------------------- EEPROM_SAVE_5 BANK1 ; WRITE ONE BYTE FIVE-FOLD INTO PIC INTERNAL EEPROM MOVLW D'5' ; PREPARE FIVE-FOLD SAVE MOVWF EEPROMCOUNT ; EESAVE_5_LOOP BTFSC EECON1,WR ; EACH EEPROM BYTE WRITE CAN TAKE UP TO 6 MILLISECONDS, DID WE FINISH ANY PREVIOUS WRITE ? GOTO EESAVE_5_LOOP ; NO, NOT YET, WAIT A BIT MORE MOVF EEPROMADDR,W ; YES, MAKE SURE THE EEPROM ADDRESS AND DATA BYTES HOLD THE RIGHT VALUE, MOVWF EEADR ; THE STATUS OF THESE BYTES AFTER A WRITE IS UNKNOWN (AND UNDOCUMENTED) MOVF EEPROMDATA,W ; MOVWF EEDATA ; BSF EECON1,WREN ; ENABLE EEPROM WRITES ; BCF INTCON,GIE ; DISABLE INTERRUPTS < ARE ALREADY DISABLED > MOVLW H'55' ; WRITE UNLOCK CODE 1 MOVWF EECON2 ; UNLOCK WRITE MOVLW H'AA' ; WRITE UNLOCK CODE 2 MOVWF EECON2 ; UNLOCK WRITE BSF EECON1,WR ; ACTIVATE WRITE BCF EECON1,WREN ; DISABLE EEPROM WRITES ; BSF INTCON,GIE ; RE-ENABLE INTERRUPTS < WILL BE ENABLED ELSEWHERE > INCF EEPROMADDR,F ; SELECT NEXT WRITE ADDRESS DECFSZ EEPROMCOUNT,F ; DID WE WRITE ALL FIVE BYTES ? GOTO EESAVE_5_LOOP ; NO, GO WRITE NEXT BYTE RETURN ; DONE ;-------------------------------------------------------------------------------------------------------------------------------------- EEPROM_READ ; THE VALUES ARE STORED IN PIC INTERNAL EEPROM. DUE TO POWER FAILURE DURING SAVES OR DUE TO ; OTHER CAUSES THE STORED VALUES MAY BECOME ERRORNOUS. TO MAKE SURE WE GET THE RIGHT VALUES ; WE STORE THEM IN FIVE-FOLD. USING A MAJORITY CHECK WE CAN CIRCUMVENT FALSE BYTES. ; WE WANT AT LEAST THREE OUT OF FIVE (MAJORITY CHECK): ; TRUTH TABLE: KARNAUGH MAP: ; ; EDCBA Y DE DE DE DE ; 0 00000 0 CBA 00 01 10 11 ; 1 00001 0 ; 2 00010 0 000 0 0 0 0 ; 3 00011 0 001 0 0 0 1 ; 4 00100 0 010 0 0 0 1 ; 5 00101 0 011 0 1 1 1 ; 6 00110 0 100 0 0 0 1 ; 7 00111 1 101 0 1 1 1 ; 8 01000 0 110 0 1 1 1 ; 9 01001 0 111 1 1 1 1 ; 10 01010 0 ; 11 01011 1 ; 12 01100 0 ; 13 01101 1 ; 14 01110 1 ; 15 01111 1 ; 16 10000 0 ; 17 10001 0 BOOLEAN EQUATIONS: ; 18 10010 0 ; 19 10011 1 RESULT = A AND B AND C ; 20 10100 0 OR ; 21 10101 1 (A OR B OR C) AND D AND E ; 22 10110 1 OR ; 23 10111 1 (A OR B) AND NOT(A XOR B XOR C) AND (D OR E) ; 24 11000 0 ; 25 11001 1 ; 26 11010 1 ; 27 11011 1 ; 28 11100 1 ; 29 11101 1 ; 30 11110 1 ; 31 11111 1 BANK1 ; READ BYTE FROM PIC INTERNAL EEPROM, USE MAJORITY CHECK ONE THE FIVE-FOLD VALUE BSF EECON1,RD ; PERFORM THE EEPROM READ OPERATION, CURRENT ADDRESS: A BTFSC EECON1,RD ; MAKE SURE THE READ HAS FINISHED, SEEMS TO BE A PROBLEM ON SOME PIC'S GOTO $-1 ; COMF EEDATA,W ; W = NOT(A) INCF EEADR,F ; SELECT NEXT READ ADDRESS: B BSF EECON1,RD ; PERFORM THE EEPROM READ OPERATION BTFSC EECON1,RD ; GOTO $-1 ; XORWF EEDATA,W ; W = NOT(A XOR B) INCF EEADR,F ; NEXT ADDRESS: C BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; XORWF EEDATA,W ; W = NOT(A XOR B XOR C) MOVWF MAJORITY ; R = NOT(A XOR B XOR C) INCF EEADR,F ; NEXT ADDRESS: D BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; MOVF EEDATA,W ; W = D INCF EEADR,F ; NEXT ADDRESS: E BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; IORWF EEDATA,W ; W = D OR E ANDWF MAJORITY,F ; R = (D OR E) AND NOT(A XOR B XOR C) MOVLW D'4' ; SUBWF EEADR,F ; NEXT ADDRESS: A BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; MOVF EEDATA,W ; W = A INCF EEADR,F ; NEXT ADDRESS: B BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; IORWF EEDATA,W ; W = A OR B ANDWF MAJORITY,F ; R = (A OR B) AND (D OR E) AND NOT(A XOR B XOR C) DECF EEADR,F ; NEXT ADDRESS: A BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; MOVF EEDATA,W ; W = A INCF EEADR,F ; NEXT ADDRESS: B BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; IORWF EEDATA,W ; W = A OR B INCF EEADR,F ; NEXT ADDRESS: C BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; IORWF EEDATA,W ; W = A OR B OR C INCF EEADR,F ; NEXT ADDRESS: D BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; ANDWF EEDATA,W ; W = (A OR B OR C) AND D INCF EEADR,F ; NEXT ADDRESS: E BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; ANDWF EEDATA,W ; W = (A OR B OR C) AND D AND E IORWF MAJORITY,F ; R = ((A OR B OR C) AND D AND E) OR ((D OR E) AND NOT(A XOR B XOR C)) MOVLW D'4' ; SUBWF EEADR,F ; NEXT ADDRESS: A BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; MOVF EEDATA,W ; W = A INCF EEADR,F ; NEXT ADDRESS: B BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; ANDWF EEDATA,W ; W = A AND B INCF EEADR,F ; NEXT ADDRESS: C BSF EECON1,RD ; BTFSC EECON1,RD ; GOTO $-1 ; ANDWF EEDATA,W ; W = A AND B AND C IORWF MAJORITY,W ; W = (A AND B AND C) OR ((A OR B OR C) AND D AND E) OR ((D OR E) AND NOT(A XOR B XOR C)) RETURN ; DONE, RETURN WITH VALUE IN W REGISTER ;--------------------------------------------------------------------------------------------------------------------------------------