

;*********************************
;Copyright(C)2002,2003, 2004 by Richard Cappels projects@cappels.org
;http://www.projects.cappels.org
; USES 32 bit binary to packed BCD routine from Atmel applination note.
;Uses AT90S2313 or similar operating at 10 MHz.
;Input, D5, is connected to prescaler. See schematic on website.

;*********************************

;ffmtr040916A	current version


.include "2313def.inc"     

.equ     clock = 10000000          ;clock frequency
.equ     baudrate = 9600          ;choose a baudrate

.equ     baudconstant = (clock/(16*baudrate))-1


.def	delay0		= r2		;delay0..delay2 are delay counters.
.def	delay1		= r3
.def	delay2		= r4
.def	delayreload0	= r6		;delayreload0..delayreload2 are reload values for delay counters.
.def	delayreload1	= r7
.def	delayreload2	= r8
.def	iterations	= r9		;Number of 1 second iterations.
.def	temp		= r16		;General purpose scratch register.
.def	byte0		= r18		;Byte0..Byte4 for binary to bcd conversion.
.def	byte1		= r19
.def	byte2		= r20
.def	byte3		= r21
.def	byte4		= r22

.def	flagreg		= r23



;Definition of flagregister bits
;0	lsb of mode select
;1	middle bit of mode select
;2	msb of mode select
;3	
;4	set to indicate that counting is to stop.
;5	set to indicate counting mode (increment ZH,ZL in interrupt)
;6	set to indicate no more leading zeros
;7	set if 32 bit overflow occured.


;PortD assignments
;0	RXD	 		weak pullup (required by circuit).
;1	TXD	 		input
;2	not used 		weak pullup
;3	prescaler input gate	High to disable, high Z to enable. Toggle to increment.
;4	prescaler reset		output	high to reset
;5	prescaler out		Input
;6	Gate counter (aux)  	Output		
;7	not available on AT90S2313

.equ	DDRDdata	= 0b01011010
.equ	PORTDdata	= 0b11001001

.org    $00
	rjmp	reset			;Power-on and reset vector
.org	$05
	rjmp	T1OFLW			;16 Bit timer overflow
.org	$07
	rjmp	UARTRCV			;UART receive interrupt


reset:     
	ldi     temp,low(ramend)
	out     spl,temp		;set spl.
	ldi     temp,baudconstant     
	out     ubrr,temp		;Load baud rate.
	ldi	temp,$00
	out	DDRB,temp		;Set up PORTB.
	ldi	temp,$FF
	out	PORTB,temp		 	
	ldi	temp,DDRDdata		;Set up PORTD.
	out 	ddrd,temp			
	ldi	temp,PORTDdata		;Weak pullup on UART receive pin.
	out	PORTD,temp
     	sbi     ucr,txen     		;Enable UART transmitter.
     	sbi	ucr,rxen		;Enable UART receiver.
	sbi	ucr,rxcie		;Enable UART receive interrupts.
	ldi	temp,0b10000110		;Enable input to 16 bit counter (Timer/Counter 1). .		
	out	tccr1b,temp
	rcall	Delay1Second		;Wait 2 seconds for display to come up.
	rcall	Delay1Second
        rcall	crlf			;Start new line
	rcall	typemessage		;Send ID message for two seconds before starting.
	rcall	Delay1Second		;Display for 2 seconds before starting measurements.
	ldi	flagreg,1		;Set measurement mode to 1 second frequency measurement.
	wdr				;Reset the watchdog timer -make sure its not about to trip.
	ldi	temp,0b00001111		;Enable the watchdog
	out	wdtcr,temp	


	sei				;Enable interrupts
	rjmp	Main			;Start main execution loop.


TypeSeconds:				;Type symbol 's' to UART.
	push	temp
	ldi	temp,'s'
	rcall	EmitUart
	pop	temp
	ret


Delay:					;Maximum delay is 50529045 cycles (5.05 seconds at 10 MHz).
	mov	delay2,delayreload2	;Minimum delays occurs when constants are 1,1,1.
moretime3:				;Maximum delay occurs when constants are 0,0,0.
	mov	delay1,delayreload1
moretime2:
	mov	delay0,delayreload0
moretime1:
	dec	delay0
	brne	moretime1
	dec	delay1
	brne	moretime2
	dec	delay2
	brne	moretime3
	ret


Delay1Second:				;Delay 1 second. 

;With the values 50,0,255; 235,21,1 this routine delays 10003509 machine cycles.
;This is a little long, but it is the best timing for the prototype with its
;particular crystal. When using a precision 10 MHz oscillator, these delay 
;numbers can be set to get closer 10,000,000 machine cycles.

	ldi	temp,50			;Call Delay routine with one set of constants.
	mov	delayreload0,temp	
	ldi	temp,0
	mov	delayreload1,temp
	ldi	temp,255
	mov	delayreload2,temp
	rcall	Delay

	ldi	temp,235		;Call Delay routine with another set of constants.
	mov	delayreload0,temp	
	ldi	temp,21
	mov	delayreload1,temp
	ldi	temp,1
	mov	delayreload2,temp
	rcall	Delay
	wdr				;Reset the watchdog timer.	
	ret	


measurefreq:				;Measure frequency for 1, 10, and 100 seconds.
					;100 milliseconds has its own routine.
	ldi	temp,$00		;Clear 16 bit counter.
	out	tcnt1h,temp
	out	tcnt1l,temp
	clr	ZL			;Clear ZL  which is the overflow counter.
	sbi	PORTD,4			;Pulse prescaler reset
	cbi	PORTD,4
	ldi	temp,0b10000000		;Enable overflow interrupts from 16 bit timer.
	out	TIMSK,temp
	cbi	DDRD,3			;Make gate pin high impedance.
	cbi	PORTD,3			;Gate signal into prescaler - turn off pullup.
AnotherSecond:
	rcall	Delay1Second		;Delay 1 second.
	dec	iterations		;Measure more than 1 second if necessary/
	brne	AnotherSecond
	sbi	DDRD,3			;Make gate signal low Z.
	sbi	PORTD,3			;Disable signal into prescaler.
	clr	temp	
	out	TIMSK,temp		;Disable overflow interrupts. 
					;Note: using tccr1b to disable counter causes 1+.
	ret







Meas1Sec:				;Label measurement as 1 second timebase.
	ldi	temp,'1'
	rcall	EmitUart
	rcall	TypeSeconds
	rcall	crlf		
	ldi	temp,1			;Take 1 second measurement.
	mov	iterations,temp
	rcall	measurefreq
	rcall	displaycounter
	rjmp	main

Meas10Sec:				;Label measurement as 10 second timebase.
	ldi	temp,'1'
	rcall	EmitUart
	ldi	temp,'0'
	rcall	EmitUart
	rcall	TypeSeconds
	rcall	crlf	
	ldi	temp,10			;Take 10 second measurement.
	mov	iterations,temp
	rcall	measurefreq
	rcall	displaycounter
	rjmp	main

Meas100Sec:				;Label measurement as 100 second timebase.
	ldi	temp,'1'
	rcall	EmitUart
	ldi	temp,'0'
	rcall	EmitUart
	ldi	temp,'0'
	rcall	EmitUart
	rcall	TypeSeconds
	rcall	crlf
	ldi	temp,100		;Take 100 second measurement.
	mov	iterations,temp
	rcall	measurefreq
	rcall	displaycounter
	rjmp	main

Main:					;Main execution loop. Called routines jump back here.	
	mov	temp,flagreg		;Get mode number from flagreg.
	andi	temp,0b00000111
	cpi	temp,0			;If mode 0, measure with 100 ms timebase.
	breq	Meas100ms
	cpi	temp,1			;If mode 1, measure with 1 second timebase.
	breq	Meas1Sec
	cpi	temp,2			;If mode 2, measure with 10 second timebase.
	breq	Meas10Sec
	cpi	temp,3			;If mode 3, measure with 100 second timebase.
	breq	Meas100Sec
	cpi	temp,4			;If mode 4, count until reset or mode left..
	breq	counting
	rjmp	main



Meas100ms:				;Take 100 millisecond measurement -special case.
					;Label measurement as with 1 second timebase.
	ldi	temp,'0'
	rcall	EmitUart
	ldi	temp,'.'
	rcall	EmitUart
	ldi	temp,'1'
	rcall	EmitUart
	rcall	TypeSeconds
	rcall	crlf
	cbr	flagreg,0b10000000	;Clear 32 bit overflow flag.
	ldi	temp,$00		;Clear 16 bit counter.
	out	tcnt1h,temp
	out	tcnt1l,temp	
	clr	ZL			;Clear ZL  which is the overflow counter.	
	sbi	PORTD,4			;Pulse prescaler reset
	cbi	PORTD,4	
	ldi	temp,0b10000000		;Enable overflow interrupts from 16 bit timer.
	out	TIMSK,temp
	cbi	DDRD,3			;Make gate pin high impedance.
	cbi	PORTD,3			;Gate signal into prescaler - turn off pullup.
	rcall	Delay100ms		;Delay 100 milliseconds second.
	sbi	DDRD,3			;Make gate signal low Z.
	sbi	PORTD,3			;Disable signal into prescaler.
	clr	temp	
	out	TIMSK,temp		;Disable overflow interrupts. 
					;Note: using tccr1b to disable counter causes 1+.
	rcall	delay100ms		;Limit updates to 5 times per second.
	rcall	displaycounter
	rjmp	main


Delay100ms:
	ldi	temp,130		;100 ms delay routine.			
	mov	delayreload0,temp	
	ldi	temp,254
	mov	delayreload1,temp
	ldi	temp,10
	mov	delayreload2,temp
	rcall	Delay

	ldi	temp,1			
	mov	delayreload0,temp	
	ldi	temp,1
	mov	delayreload1,temp
	ldi	temp,229
	mov	delayreload2,temp
	rcall	Delay	
	wdr				;Reset the watchdog timer.
	ret




Counting:				;Count and display results until a flag goes true.
	ldi	flagreg,$24		;Establish flagreg values.
	cbi	DDRD,3			;Make gate pin high impedance.
	cbi	PORTD,3			;Gate signal into prescaler - turn off pullup.
	sbi	PORTD,4			;Make sure prescaler counter is in reset.
	cbi	PORTD,6			;Make sure counting input (aux input) is gated on.
	ldi	temp,$00		;Clear 16 bit counter.
	out	tcnt1h,temp
	out	tcnt1l,temp
	clr	ZL			;Clear Z register, which is the overflow counter.
	clr	ZH
	ldi	temp,0b10000000		;Enable overflow interrupts from 16 bit timer.
	out	TIMSK,temp	
KeepCounting:				;Wait for flag to go high, signaling end of counting.
	sbrc	flagreg,4
	rjmp	CountingDone		;At this point, 
					;LSB is in tcnt1l, Move to byte0
					;Next B is in tcnt1h. Move to byte1
					;Next B in in ZL. Move to byte2
					;MSB is in ZH
	clr	XL			;Use XL to count the digits for placement of commans and decimal points
	andi	flagreg,0b10111111	;Clear nonzero flag.
					;move counter contents to input for number conversion
	in	byte0,tcnt1l		;Move contents of on-chip 16 bit coutner into conversion registers.
	in	byte1,tcnt1h		
	mov	byte2,ZL		;Move MSB into conversion register.
	mov	byte3,ZH
	rcall	Conv32bit2bcd		;Get binary data in byte0..byte 3 into byte0..byte4.
	mov	temp,byte4
	rcall	bcdEmitUart
	mov	temp,byte3
	rcall	bcdEmitUart
	mov	temp,byte2
	rcall	bcdEmitUart
	mov	temp,byte1
	rcall	bcdEmitUart
	mov	temp,byte0
	rcall	bcdEmitUart
	sbrc	flagreg,7		;If flagreg bit 7 (32 bit overflow) is set, send warning.
	rcall	warnoflow		
	rcall	crlf			;New line on display.
	rcall	TypeCounting		;Type word "Counting" on display via UART.
	rcall	Delay100ms		;Display 10 times per second.
	wdr				;Reset the watchdog timer.
	rjmp	KeepCounting
CountingDone:
	sbi	DDRD,3			;Make gate signal low Z.
	sbi	PORTD,3			;Disable signal into prescaler.
	clr	temp		
	out	TIMSK,temp		;Disable overflow interrupts. 
	sbi	PORTD,3			;Make input a high impedance - temporarily ungate the prescaler.
	sbi	DDRD,3
	cbi	PORTD,4			;Make sure prescaler counter is not in reset.
	sbi	PORTD,6			;Make sure counting input (aux input) is gated off.	
	rjmp	main



displaycounter:				;Display contents of counter via UART.
					;At this point, 
					;LSB is in external prescaler, Move to byte0
					;Next B is in tcnt1l. Move to byte1
					;Next B in in tcnt1h. Move to byte2
					;MSB is in ZL
	clr	XL			;Use XL to count the digits for placement of commans and decimal points
	andi	flagreg,0b10111111	;Clear nonzero flag.
					;move counter contents to input for number conversion
	in	byte1,tcnt1l		;Move contents of on-chip 16 bit coutner into conversion registers.
	in	byte2,tcnt1h		
	mov	byte3,ZL		;Move MSB into conversion register.
	ldi	byte0,$FF		;First move contents of off-chip prescaler to byte0
	ldi	temp,$00		;Clear 16 bit counter.
	out	tcnt1h,temp
	out	tcnt1l,temp
					
MorPs:					;if count timer not equal to zero, toggle.
	in	temp,tcnt1l
	tst	temp
	brne	PsDone	
	dec	byte0			;Decrement byte0
	cbi	PORTD,3			;Advance prescaler one count
	sbi	PORTD,3
	rjmp	MorPs		
PsDone:
	rcall	Conv32bit2bcd		;Get binary data in byte0..byte 3 into byte0..byte4.
	mov	temp,byte4
	rcall	bcdEmitUart
	mov	temp,byte3
	rcall	bcdEmitUart
	mov	temp,byte2
	rcall	bcdEmitUart
	mov	temp,byte1
	rcall	bcdEmitUart
	mov	temp,byte0
	rcall	bcdEmitUart
	sbrc	flagreg,7		;If flagreg bit 7 (32 bit overflow) is set, send warning.
	rcall	warnoflow
	rcall	crlf
	ret


bcdEmitUart:				;Emit two digite BCD in temp through UART.
	push	temp
	swap	temp
	andi	temp,0b00001111
	ori	temp,$30
	rcall	EmitNoLeadZero
	pop	temp
	andi	temp,0b00001111
	ori	temp,$30
	rcall	EmitNoLeadZero
	ret



PlaceMark:				;Place comma or period as appropriate. 
					;based on digit count (XL) and mode (flagreg 0..2)			
MakeModeByte:				
	push	temp			;Preserve temp.- must pop temp from stack in calling routine.
	mov	temp,flagreg		;Make state byte from mode and digit counter
	andi	temp,0b00000111		;Mask off all but mode value from flagreg.
	cpi	temp,4
	brne	NotMode4		;If in mode 4, make it look like mode 1.
	ldi	temp,1
NotMode4:	

	swap	temp			;Get mode into upper nybble.
	or	temp,XL			;Get digit count into lower nybble.



	cpi	temp,$02		;Place commas and decimal point depending upon 
	breq	docomma			;the mode and digit count.
	cpi	temp,$05
	breq	docomma
	cpi	temp,$08
	breq	docomma
	cpi	temp,$11
	breq	docomma
	cpi	temp,$14
	breq	docomma
	cpi	temp,$17
	breq	docomma
	cpi	temp,$23
	breq	docomma
	cpi	temp,$26
	breq	docomma
	
;
	
	cpi	temp,$32
	breq	docomma
	cpi	temp,$35
	breq	docomma
	cpi	temp,$1A
	breq	dodpoint
	cpi	temp,$29
	breq	dodpoint
	cpi	temp,$38
	breq	dodpoint
	cpi	temp,$0A
	breq	doohdot
	pop	temp
	ret


docomma:				;Type a comma on the display via UART.
	ldi	temp,','
	rcall	EmitUart
	pop	temp
	ret

dodpoint:				;Type a decimal point on display via UART.
	ldi	temp,'.'
	rcall	EmitUart
	pop	temp
	ret

doohdot:				;Type "0." on display via UART.
	ldi	temp,'0'
	rcall	EmitUart
	ldi	temp,'.'
	rcall	EmitUart
	pop	temp
	ret





EmitNoLeadZero:				;Emit number if not a leading zero, otherwise a space.
	inc	XL			;Increment digit count
					;Make sure decimal point and zeros shown in modes 2,3.
	mov	XH,flagreg		;Make state byte from mode and digit counter
	andi	XH,0b00000111		;Mask off all but mode value from flagreg.	
	swap	XH			;Get mode into upper nybble.
	or	XH,XL			;Get digit count into lower nybble.
	cpi	XH,$29			;Set flag to show zeros to rt of decimal point
	brne	NO29			;in mode 2.
	ori	flagreg,0b01000000	;Set flagreg to allow sending leading zeros
NO29:
	cpi	XH,$38			;Set flag to show zeros to ret of decimal point
	brne	NO38			;In mode 3.
	ori	flagreg,0b01000000	;Set flagreg to allow sending leading zeros
NO38:
	cpi	temp,'0'
	breq	ItsAZero
	ori	flagreg,0b01000000	;Set nonzero flag.
	rcall	EmitUart
	rcall	PlaceMark
	ret
ItsAZero:
	sbrs	flagreg,6
	rjmp	QX21
	rcall	emitUart
	rcall	PlaceMark
	ret
QX21:
	cpi	XL,10
	breq	EmitUart
	ldi	temp,$20
	rjmp	EmitUart

EmitUart:				;Send RFChar via UART, preserves content of RFChar
	sbis    usr,udre		;Wait for data to arrive.
	rjmp    EmitUart     
	out     udr,temp		;Send byte.
	ret			

crlf:
	ldi	temp,$0A
	rcall	EmitUart
	ldi	temp,$0D
	rcall	EmitUart
	ret

TypeMessage:				;Type greeting
	push	ZL
	push	ZH
	ldi	ZH,high(2*Message)	;Load high part of byte address into ZH
	ldi	ZL,low(2*Message)	;Load low part of byte address into ZL
	rcall	SendRomstring		;Send it
	pop	ZH
	pop	ZL
	ret
	
Message:
	.db     "ffmtr040916A" 
	.db	$0A,$0D
	.db     $00,$00




TypeCounting:				;Type the word "Counting" via UART.
	push	ZL
	push	ZH
	ldi	ZH,high(2*Countmessage)	;Load high part of byte address into ZH
	ldi	ZL,low(2*Countmessage)	;Load low part of byte address into ZL
	rcall	SendRomstring		;Send it
	pop	ZH
	pop	ZL
	ret
	
Countmessage:
	.db     "Counting" 
	.db	$0A,$0D
	.db     $00,$00



SendRomstring:	;Send string pointed to by ZH,ZL.
	lpm				; Load byte from program memory into r0
	tst	r0			; Check if we've reached the end of the message
	breq	stringdone		; If so, return
	mov	temp,r0
	rcall	EmitUart
	adiw	ZL,1			; Increment Z registers
	rjmp	SendRomstring
stringdone:
    	ret


WarnOflow:				;Type "+" to indicate overflow
	push	temp
	ldi	temp,'+'
	rcall	EmitUart
	pop	temp
	ret


Conv32bit2bcd:				;Input: r18.19,20.21 (binary); out: r18,19,20,21,22 (bcd)
					;Listed above as lsB first, msB last.
		push	r16		;Save registers not needed for 
		push	r17
		push	r23		;input or output.
		push	r24
		rcall	Bin4BCD		;Do the conversion
		mov	r18,r20
		mov	r19,r21
		mov	r20,r22
		mov	r21,r23
		mov	r22,r24
		pop	r24		;Restore saved registers.
		pop	r23
		pop	r17
		pop	r16
		ret
	

;******** 32 bit binary to packed BCD routines from Atmel application note *************
; Call bin4bcd			r18r19r20r21       >>>         r20r21r22r23r24


Bin2BCD20:      mov     r16,r20         ;for compatibility with Math32
                mov     r17,r21         ;
Bin2BCD16:      ldi     r22,0xff      ;initialize digit 4
binBCD_4:       inc     r22           ;
                subi    r16,low(10000);subiw fbin,10000
                sbci    r17,high(10000)
                brcc    binBCD_4        ;
                ldi     r21,0x9f      ;initialize digits 3 and 2


binBCD_3:       subi    r21,0x10      ;
                subi    r16,low(-1000);subiw fbin,1000
                sbci    r17,high(-1000)
                brcs    binBCD_3        ;
binBCD_2:       inc     r21           ;
                subi    r16,low(100)  ;subiw fbin,100
                sbci    r17,high(100) ;
                brcc    binBCD_2        ;
                ldi     r20,0xa0      ;initialize digits 1 and 0
binBCD_1:       subi    r20,0x10      ;
                subi    r16,-10       ;subi fbin,10
                brcs    binBCD_1        ;
                add     r20,r16     ;
binBCD_ret:     ret                     


;* r18:r19:r20:r21  >>>  r20:r21:r22:r23:r24  <== this one.
;*           hex                              dec
;*       r18r19r20r21       >>>         r20r21r22r23r24

Bin4BCD:  
	      	rcall   Bin2BCD20       ;
                clr     r23           ;initial highest bytes of result
                ldi     r24,0xfe      ;
binBCD_loop:    subi    r20,-0x33     ;add 0x33 to digits 1 and 0
                sbrs    r20,3         ;if bit 3 clear
                subi    r20,0x03      ;       sub 3
                sbrs    r20,7         ;if bit 7 clear
                subi    r20,0x30      ;       sub $30
                subi    r21,-0x33     ;add 0x33 to digits 3 and 2
                sbrs    r21,3         ;if bit 3 clear
                subi    r21,0x03      ;       sub 3
                sbrs    r21,7         ;if bit 7 clear
                subi    r21,0x30      ;       sub $30
                subi    r22,-0x33     ;add 0x33 to digits 5 and 4
                sbrs    r22,3         ;if bit 3 clear
                subi    r22,0x03      ;       sub 3
                sbrs    r22,7         ;if bit 7 clear
                subi    r22,0x30      ;       sub $30
                lsl     r18           ;
                rol     r19           ;shift lower word
                rol     r20           ;through all bytes
                rol     r21           ;
                rol     r22           ;
                rol     r23           ;
                rol     r24           ;
                brmi    binBCD_loop     ;7 shifts w/o correction of MSD
                rol     r17           ;since Bin2BCD r17 = 0xff
                brcc    binBCD_ret    ;so as to do 16_lsl in total
                subi    r23,-0x33     ;add 0x33 to digits 7 and 6
                sbrs    r23,3         ;if bit 3 clear
                subi    r23,0x03      ;       sub 3
                sbrs    r23,7         ;if bit 7 clear
                subi    r23,0x30      ;       sub $30
                subi    r24,-0x03     ;add 0x03 to digit 8 only
                sbrs    r24,3         ;if bit 3 clear
                subi    r24,0x03      ;       sub 3
                rjmp    binBCD_loop     ;
                
;************End of binary to bcd conversion routine**********



T1OFLW:
		push	temp		;Save temp then save status register in temp.
		in	temp,sreg
		sbrc	flagreg,5
		rjmp	countermode
		inc	ZL		;Increment 8 bit ZL register upon overflow of 16 bit counter.
		rjmp	fmetermodes	
countermode:	adiw	ZL,1	
fmetermodes:
		brne	NoOverflow
		sbr	flagreg,0b10000000	;Set 32 bit overflow flag (very reare event)
NoOverflow:	out	sreg,temp	;Restore status regiser then restore temp.
		pop	temp
		reti


UARTRCV:				;UART receive interrupt
	push	temp			;Save temp then save status register.
	in	temp,sreg
	push	temp
	in	temp,usr
	in	temp,udr		;Read the char.
	andi	temp,$DF		;Make upper-case ascii
	cpi	temp,'R'		;If 'R' reset counters if mode 4 (Counting mode).
	breq	resetcounter
conint2:				;Branch above returns here if not 'R' in mode 4.	
	mov	temp,flagreg		;Increment mode (flagret 0..2)
	andi	temp,0b00000111		;Maximum count is 4
	inc	temp
	cpi	temp,$05		;If its mode 5, that's one too many, warp around to zero.	
	breq	modemaxed	
contint:				;Branch above returns here after resetting temp to 1.
	andi	flagreg,0b11111000
	or	flagreg,temp	
	ori	flagreg,0b00010000	;Set flagreg bit 4 to leave counting mode.
	ldi	temp,1			;Set timer counters to time out early.
	mov	iterations,temp		
	mov	delayreload0,temp	
	mov	delayreload1,temp
	mov	delayreload2,temp

intdone:
	pop	temp			;Restore status regiser then restore temp.
	out	sreg,temp	
	pop	temp
	reti

modemaxed:
	ldi	temp,0			;Lowest mode number is 0.
	rjmp	contint
	
resetcounter:				;If in mode 4, counter mode, reset counter.

	mov	temp,flagreg
	andi	temp,0b00000111
	cpi	temp,4
	brne	conint2			;If not mode 4, continue as if any other key.

	ldi	temp,$00		;Clear 16 bit counter.
	out	tcnt1h,temp
	out	tcnt1l,temp
	clr	ZL			;Clear ZL,ZH which is the overflow counter.
	clr	ZH
	rjmp	intdone	


.exit					;Assemble stops at this line in document.


