I am just practicing how to use shift registers to expand a microcontroller's output. So far I'm only practicing using assembler language, I haven't yet dabbled in using C or BASIC with microcontrollers.
Here is a schematic I made:

The shift registers im using is the 4094 and the microcontroller is PIC16F84A, with oscillator set to 4MHz.
I wrote a program that will count from 0 to 29, wherein the ones place is at the bottom, and then display 1 in all the segments after that for a brief duration, then loop back to the start.
It sort of works..
My problem is that in some frames, the output doesn't come out right, but when the program loops back to the start and reaches that same frame it then comes out okay but then other frames don't come out right.
Basically, everytime it runs it seems like on some frames the output randomly don't display the numbers properly and there is no way to predict on which frames the error will occur.
Please help me find what is wrong with my program, or circuit.
Here is the source code:
include <p16f84a.inc>
__CONFIG _CP_OFF & _WDT_OFF & _XT_OSC & _PWRTE_ON
cblock 0x20
d1
d2
d3
temp
digit
placer
endc
CONFIG bsf STATUS, RP0
clrf PORTB
bcf STATUS, RP0
clrf PORTB
movlw d'200'
movwf temp
Flush bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto Flush
START bsf PORTB, 3 ;Set OE
movlw d'7'
movwf placer ;placer starts at 7
movfw placer
movwf digit
call ZERO
decfsz digit, f
goto $-2
bsf PORTB, 2
bcf PORTB, 2
call DELAY
decf placer ;placer is now 6
movfw placer
movwf digit
call ONE
call ONES
movfw placer
movwf digit
call TWO
call ONES
movfw placer
movwf digit
call THREE
call ONES
movfw placer
movwf digit
call FOUR
call ONES
movfw placer
movwf digit
call FIVE
call ONES
movfw placer
movwf digit
call SIX
call ONES
movfw placer
movwf digit
call SEVEN
call ONES
movfw placer
movwf digit
call EIGHT
call ONES
movfw placer
movwf digit
call NINE
call ONES
decf placer ;placer is now 5
movfw placer
movwf digit
call ZERO
call TENS
movfw placer
movwf digit
call ONE
call TENS
movfw placer
movwf digit
call TWO
call TENS
movfw placer
movwf digit
call THREE
call TENS
movfw placer
movwf digit
call FOUR
call TENS
movfw placer
movwf digit
call FIVE
call TENS
movfw placer
movwf digit
call SIX
call TENS
movfw placer
movwf digit
call SEVEN
call TENS
movfw placer
movwf digit
call EIGHT
call TENS
movfw placer
movwf digit
call NINE
call TENS
movfw placer
movwf digit
call ZERO
call TWENTY
movfw placer
movwf digit
call ONE
call TWENTY
movfw placer
movwf digit
call TWO
call TWENTY
movfw placer
movwf digit
call THREE
call TWENTY
movfw placer
movwf digit
call FOUR
call TWENTY
movfw placer
movwf digit
call FIVE
call TWENTY
movfw placer
movwf digit
call SIX
call TWENTY
movfw placer
movwf digit
call SEVEN
call TWENTY
movfw placer
movwf digit
call EIGHT
call TWENTY
movfw placer
movwf digit
call NINE
call TWENTY
call ENDER
goto START
ONES call ZERO
decfsz digit, f
goto $-2
bsf PORTB, 2
bcf PORTB, 2
call DELAY
return
TENS call ONE
call ZERO
decfsz digit, f
goto $-2
bsf PORTB, 2
bcf PORTB, 2
call DELAY
return
TWENTY call TWO
call ZERO
decfsz digit, f
goto $-2
bsf PORTB, 2
bcf PORTB, 2
call DELAY
return
ENDER call ONE
call ONE
call ONE
call ONE
call ONE
call ONE
call ONE
bsf PORTB, 2
bcf PORTB, 2
call DELAYLONG
goto START
;;;;;;Digits Subroutines;;;;;;;;;;;
ZERO bcf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'6'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
ONE bcf PORTB, 0
movlw d'5'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
return
TWO bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
THREE bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bcf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'4'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
FOUR bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
return
FIVE bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
return
SIX bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'5'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
return
SEVEN bcf PORTB, 0
movlw d'5'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'3'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
EIGHT bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'7'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
NINE bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'4'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
DELAY movlw d'2'
movwf d1
movlw d'24'
movwf d2
movlw d'167'
movwf d3
LOOP decfsz d3, f
goto LOOP
decfsz d2,f
goto LOOP
decfsz d1,f
goto LOOP
return
DELAYLONG movlw d'18'
movwf d1
movlw d'24'
movwf d2
movlw d'167'
movwf d3
LOOP2 decfsz d3, f
goto LOOP2
decfsz d2,f
goto LOOP2
decfsz d1,f
goto LOOP2
return
END
Here is a schematic I made:

The shift registers im using is the 4094 and the microcontroller is PIC16F84A, with oscillator set to 4MHz.
I wrote a program that will count from 0 to 29, wherein the ones place is at the bottom, and then display 1 in all the segments after that for a brief duration, then loop back to the start.
It sort of works..
My problem is that in some frames, the output doesn't come out right, but when the program loops back to the start and reaches that same frame it then comes out okay but then other frames don't come out right.
Basically, everytime it runs it seems like on some frames the output randomly don't display the numbers properly and there is no way to predict on which frames the error will occur.
Please help me find what is wrong with my program, or circuit.
Here is the source code:
include <p16f84a.inc>
__CONFIG _CP_OFF & _WDT_OFF & _XT_OSC & _PWRTE_ON
cblock 0x20
d1
d2
d3
temp
digit
placer
endc
CONFIG bsf STATUS, RP0
clrf PORTB
bcf STATUS, RP0
clrf PORTB
movlw d'200'
movwf temp
Flush bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto Flush
START bsf PORTB, 3 ;Set OE
movlw d'7'
movwf placer ;placer starts at 7
movfw placer
movwf digit
call ZERO
decfsz digit, f
goto $-2
bsf PORTB, 2
bcf PORTB, 2
call DELAY
decf placer ;placer is now 6
movfw placer
movwf digit
call ONE
call ONES
movfw placer
movwf digit
call TWO
call ONES
movfw placer
movwf digit
call THREE
call ONES
movfw placer
movwf digit
call FOUR
call ONES
movfw placer
movwf digit
call FIVE
call ONES
movfw placer
movwf digit
call SIX
call ONES
movfw placer
movwf digit
call SEVEN
call ONES
movfw placer
movwf digit
call EIGHT
call ONES
movfw placer
movwf digit
call NINE
call ONES
decf placer ;placer is now 5
movfw placer
movwf digit
call ZERO
call TENS
movfw placer
movwf digit
call ONE
call TENS
movfw placer
movwf digit
call TWO
call TENS
movfw placer
movwf digit
call THREE
call TENS
movfw placer
movwf digit
call FOUR
call TENS
movfw placer
movwf digit
call FIVE
call TENS
movfw placer
movwf digit
call SIX
call TENS
movfw placer
movwf digit
call SEVEN
call TENS
movfw placer
movwf digit
call EIGHT
call TENS
movfw placer
movwf digit
call NINE
call TENS
movfw placer
movwf digit
call ZERO
call TWENTY
movfw placer
movwf digit
call ONE
call TWENTY
movfw placer
movwf digit
call TWO
call TWENTY
movfw placer
movwf digit
call THREE
call TWENTY
movfw placer
movwf digit
call FOUR
call TWENTY
movfw placer
movwf digit
call FIVE
call TWENTY
movfw placer
movwf digit
call SIX
call TWENTY
movfw placer
movwf digit
call SEVEN
call TWENTY
movfw placer
movwf digit
call EIGHT
call TWENTY
movfw placer
movwf digit
call NINE
call TWENTY
call ENDER
goto START
ONES call ZERO
decfsz digit, f
goto $-2
bsf PORTB, 2
bcf PORTB, 2
call DELAY
return
TENS call ONE
call ZERO
decfsz digit, f
goto $-2
bsf PORTB, 2
bcf PORTB, 2
call DELAY
return
TWENTY call TWO
call ZERO
decfsz digit, f
goto $-2
bsf PORTB, 2
bcf PORTB, 2
call DELAY
return
ENDER call ONE
call ONE
call ONE
call ONE
call ONE
call ONE
call ONE
bsf PORTB, 2
bcf PORTB, 2
call DELAYLONG
goto START
;;;;;;Digits Subroutines;;;;;;;;;;;
ZERO bcf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'6'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
ONE bcf PORTB, 0
movlw d'5'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
return
TWO bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
THREE bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bcf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'4'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
FOUR bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
return
FIVE bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
return
SIX bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'5'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
return
SEVEN bcf PORTB, 0
movlw d'5'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bsf PORTB, 0
movlw d'3'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
EIGHT bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'7'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
NINE bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'2'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
bcf PORTB, 0
bsf PORTB, 1
bcf PORTB, 1
bsf PORTB, 0
movlw d'4'
movwf temp
bsf PORTB, 1
bcf PORTB, 1
decfsz temp, f
goto $-3
return
DELAY movlw d'2'
movwf d1
movlw d'24'
movwf d2
movlw d'167'
movwf d3
LOOP decfsz d3, f
goto LOOP
decfsz d2,f
goto LOOP
decfsz d1,f
goto LOOP
return
DELAYLONG movlw d'18'
movwf d1
movlw d'24'
movwf d2
movlw d'167'
movwf d3
LOOP2 decfsz d3, f
goto LOOP2
decfsz d2,f
goto LOOP2
decfsz d1,f
goto LOOP2
return
END