; FILE: 		count.asm
; AUTHOR: 		JMY
; DATE: 		24th March 2005
; DESCRIPTION: 	Count to 255 at 1 second intervals and display on a seven 
; 				segment display in binary. 
; 				The pause subroutine takes apx. 0.2 sec.
; 				Pause is called 5 times

	list	p=16F84		; select processor type
	radix	hex			; define radix as hexadecimal
;	#include "p16f84.inc"
;----------------------------------------------------------------------
;	cpu equates (memory map)
portA	equ	0x05
trisa	equ	0x05

portB	equ	0x06		;port B address
trisb	equ 0x06		;trisB address in register bank 1

indf	equ	0x00		;indirect file register
fsr		equ	0x04		;indirect address register

Status	equ 	0x03		;status register
RP0		equ 5			;bit 5 of status register
RP1 	equ	6			;bit 6 of status register

nCount	equ	0x0d		; pause routine inner loop counter
mCount	equ	0x0e		; pause routine outer loop counter
oCount	equ	0x0F

eventFlag	equ	0x11	; event handler started flag

temp	equ 0x10		; temp variable

LEDa	equ	0x00		; LED segment a bit of Port B
LEDb	equ	0x01		; LED segment b bit of Port B

SW_B	equ	0x01		; Black switch bitmask for Port A
SW_G	equ	0x02		; Green switch bitmask for Port A

;----------------------------------------------------------------------

	org	0x000

start
	bcf		Status,RP0	; clear bank selection bits in the status reg
	bcf		Status,RP1

	bsf		Status,RP0	; select bank 1

	movlw	0x03		; Set switch pins as inputs
	movwf	trisa		

	movlw	0x00		; load w with 0x00
	movwf	trisb		; load it into trisb to make portb all outputs
	bcf		Status,RP0	; reselect bank 0

	clrf	portB		; clear all lines low
	bsf		eventFlag,0	; make sure no events are registered

main_loop
	movf	portA,w		; read Port A
	movwf	temp
	comf	temp,w
	andlw	SW_B		; test black switch
	andwf 	eventFlag,w
	movwf	temp
	btfsc	temp,0		; test bit 0 of temp (black switch) for a 1
	call 	event_black_switch
	
	movf	portA,w		; read Port A
	movwf 	temp
	comf	temp,w
	andlw	SW_B		; test black switch
	movwf	temp
	btfss 	temp,0		; test bit 0 of temp
	bsf		eventFlag,0	; clear flag to allow event handler for black button

	goto	main_loop


event_black_switch
	bcf		eventFlag,0	; flag to show we've done the event
	movf	portB,w		; read port B
	xorlw	0x01		; compliment port B bit 0
	movwf	portB		; write value back to port B
	call 	beep		; short beep
	return


beep
	movlw	0x07		; set w = 255 decimal
	movwf	mCount		; mCount = w: outer loop counter
loadN_beep
	movlw	0xff		; set w = 255 decimal
	movwf	nCount		; nCount = w: inner loop counter
decN_beep
	bsf		portB,7		; set sounder output high
	call 	short_pause ; wait 125µs
	bcf		portB,7		; set sounder output low
	call	short_pause ; wait 125µs

	decfsz	nCount, f	; nCount--
	goto	decN_beep		; if nCount != 0 then repeat nCount--

	decfsz	mCount, f	; else decrement Count
	goto	loadN_beep		; if mCount != 0 then return
	return


;--------------------------------------------------------------------
;subroutine pause: lets waste some time....
;
;inputs: nothing
;outputs: nothing
;
;does: nothing but waste some time
;corrupts: register W
;
;description: two loops using "mCount" and "nCount" register files
;			  "mCount" is the outer loop counter (255 down to zero)
;			  "nCount" is the inner loop counter (255 down to zero)
;
;--------------------------------------------------------------------
short_pause	

	movlw	0x29		; set w = 41 decimal
	movwf	oCount		; nCount = w: inner loop counter
decN
	decfsz	oCount, f	; nCount--
	goto	decN		; if nCount != 0 then repeat nCount--

	return				; else exit subroutine



	end
