;********************************************************** ;********************************************************** ;This program repeatedly light the 7-Segments that connected to PORTB with mode number from 0 to 3. ;The program use the look-up table to determifrom the state of the 7-segments ;We use (CC) 7-Segments and connect RB1 to a,RB2 to b, RB3 to c .....and RB7 to g ;We connect RB0 to external switch to change modes ;The Four modes display different patterns to the leds connecting to PORTA Outputs ;It uses a PIC16F84 running at crystal oscillator of frecuency 4MHz. ;********************************************************** ;********************************************************** #include "p16f84A.inc" ;********************************************************** ; Macro definitions push macro movwf WTemp ; WTemp must be reserved in all banks swapf STATUS,W ; store in W without affecting status bits movwf StatusTemp ; save STATUS endm pop macro swapf StatusTemp,W ; unswap STATUS nibbles into W movwf STATUS ; restore STATUS swapf WTemp,F ; unswap W nibbles swapf WTemp,W ; restore W without affecting STATUS endm ;********************************************************** ;********************************************************** Zero equ B'01111110' ; 7-Segment Code for Zero One equ B'00001100' ; 7-Segment Code for One Two equ B'10110110' ; 7-Segment Code for Two Three equ B'10011110' ; 7-Segment Code for Three ;********************************************************** ; User-defined variables cblock 0x20 WTemp StatusTemp Count_S Count_L Number Arithmatic And_Mask XOR_Mask Count endc ;********************************************************** ; Start of executable code org 0x00 ;Reset vector nop goto Main org 0x04 goto INT_SVC ; jump to the interrupt service routine ;;;;;;; Main program ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Main call Initial ;Initialize everything MainLoop call Mode0 sleep call Mode1 sleep call Mode2 sleep call Mode3 sleep goto MainLoop ;Do it again ;;;;;;; Initial subroutine ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; ; This subroutine performs all initializations of variables and registers. Initial bsf STATUS,RP0 ;Set register access to bank 1 clrf TRISA ;Set up all bits of PORTA as outputs clrf TRISB ;Set up all bits of PORTB as outputs bsf TRISB,0 ;Set up RB0 as input bcf STATUS,RP0 ;Set register access to bank 0 movlw Zero ;Turn on the Seven_Segnemts with Number Zero movwf PORTB clrf Number bsf INTCON,INTE ;enable RB0 interrupt source bsf INTCON,GIE ;enable global interrupts return ;;;;;;;Mode0 subroutine ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Mode0 movlw 1 movwf PORTA bcf STATUS,C L00 call Large_Delay rlf PORTA,F movf PORTA,F btfss STATUS,Z goto L00 movlw b'00010000' movwf PORTA bcf STATUS,C L01 call Large_Delay rrf PORTA,F movf PORTA,F btfss STATUS,Z goto L01 return ;;;;;;;Mode1 subroutine ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Mode1 clrf And_Mask comf And_Mask,F clrw iorlw b'00011111' clrf Arithmatic iorwf Arithmatic,F L10 movwf PORTA call Large_Delay decf Arithmatic,F movf Arithmatic,W andwf And_Mask,W btfss STATUS,Z goto L10 return ;;;;;;;Mode2 subroutine ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Mode2 movlw b'00011011' movwf XOR_Mask movlw b'00010001' movwf PORTA call Large_Delay movf PORTA,W xorlw b'00011011' movwf PORTA call Large_Delay movlw 6 subwf PORTA,F call Large_Delay movf PORTA,W addlw 6 movwf PORTA call Large_Delay movf PORTA,W xorwf XOR_Mask,W movwf PORTA call Large_Delay return ;;;;;;;Mode3 subroutine ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Mode3 movlw 0A movwf Count movlw 1 L30 sublw 0 movwf PORTA call Large_Delay movf PORTA,W decfsz Count,F goto L30 return ;;;;;;; Delay subroutines ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;********************************************************** Small_Delay movlw D'250' movwf Count_S Dell_S nop nop decfsz Count_S,F goto Dell_S return ;********************************************************** Large_Delay movlw D'56' movwf Count_L Dell_L call Small_Delay nop incfsz Count_L,F goto Dell_L return ;********************************************************** ; RB0_Sub Routine RB0_Sub bcf INTCON, INTF ; Clear the RB0 interrupt flag clrwdt incf Number,F ;Display the next number call Seven_Segment_Table ; use look-up table to change the 7-Segments movwf PORTB ; move the result to PORTB so the 7-segment will light return ;;;;;;; 7-Seg subroutine ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Seven_Segment_Table movf Number,W ; copy the present state of the LEDs into W andlw b'00000011' addwf PCL, F ; change PC retlw Zero ; return the7-Segment Code for Zero retlw One ; return the7-Segment Code for One retlw Two ; return the7-Segment Code for Two retlw Three ; return the7-Segment Code for Three ;********************************************************** ; Interrupt Service Routine INT_SVC push btfsc INTCON, INTF ; Check for a RB0 interrupt call RB0_Sub ; btfsc ... ; Check for another interrupt ; call ... pop retfie ;********************************************************** end