;**** includes **** 2012/7/8 ck=4Mhz
.include "m88pdef.inc"

.macro	ldiw	;	ldiw	Z(X,Y),var
	ldi	@0L,low(@1)
	ldi	@0H,high(@1)
.endm
.macro	stsi
	ldi	r16,@1
	sts	@0,r16
.endm
.macro	sti
	ldi	r16,@1
	st	@0,r16
.endm
.MACRO subi16	;subi16	ra,rb,0xHHHH
                 subi	@1,low(@2)
                 sbci	@0,high(@2)
.ENDMACRO 
.MACRO cpi16	;cpi16	ra,rb,0xHHHH	;ra:rb-0xHHHH	set flags:N,C
		push	@0
		push	@1
		subi	@1,low(@2)
		sbci	@0,high(@2)
cp162:	pop	@1
		pop	@0
.ENDMACRO
.MACRO subi24	;subi24	ra,rb,rc,0xHHHHHH
                 subi	@2,low(@3)
                 sbci	@1,high(@3)
                 sbci	@0,byte3(@3)
.ENDMACRO 
.MACRO cpi24	;cpi24	ra,rb,rc,0xHHHHHH	;ra:rb:rc-0xHHHHHH	set flags:N,C
		push	@0
		push	@1
		push	@2
		subi	@2,low(@3)
		sbci	@1,high(@3)
		sbci	@0,byte3(@3)
		pop	@2
		pop	@1
		pop	@0
.ENDMACRO
;*****************************
;* レジスタ変数　設定 *
;*****************************

.def	temp1	= r16
.def	temp2	= r17
.def	temp3	= r18
.def	temp4	= r19
.def	lcd_data= r20
.def	data	= r21

;*****************************
;*　 ビット　設定　　*
;*****************************
;**  PORTC  ***
;.equ			= 0; th
;.equ			= 1
;.equ			= 2
;.equ			= 3
;.equ			= 4
;.equ			= 5 
;.equ			= 7 
;**  PORTD  ***

;.equ		= 0
.equ	lcd_rs	= 1
.equ	lcd_rw	= 2
.equ	lcd_enb	= 3
.equ	lcd_db4 = 4
.equ	lcd_db5 = 5
.equ	lcd_db6 = 6
.equ	lcd_db7 = 7
;**  PORTB  ***
.equ	ds_dat	= 0	;DS18B20 data
;.equ			= 1
;.equ			= 2
;.equ			= 3
;.equ			= 4
;.equ			= 5 
;.equ			= 7 

.dseg
dsp_dat:	.byte 32
sp_dat:		.byte 9

;.eseg	;EEPROM add


.cseg
	 	 rjmp	RESET   ;各種ﾘｾｯﾄ
	 	 reti  ;rjmp	 EXT_INT0	 ;外部割り込み要求0
	 	 reti  ;rjmp	 EXT_INT1	 ;外部割り込み要求1
	 	 reti  ;rjmp	 PCINT0		 ;ﾋﾟﾝ変化割り込み要求0
	 	 reti  ;rjmp	 PCINT1	 	;ﾋﾟﾝ変化割り込み要求1
	 	 reti  ;rjmp	 PC_INT2	 ;ﾋﾟﾝ変化割り込み要求2
	 	 reti  ;rjmp	 WDT_OVF	 ;ｳｫｯﾁﾄﾞｯｸﾞ計時完了
	 	 reti  ;rjmp	 TIM2_COMPA	 ;ﾀｲﾏ/ｶｳﾝﾀ2比較A一致
	 	 reti  ;rjmp	 TIM2_COMPB	 ;ﾀｲﾏ/ｶｳﾝﾀ2比較B一致
	 	 reti  ;rjmp	 TIM2_OVF	 ;ﾀｲﾏ/ｶｳﾝﾀ2溢れ
	 	 reti  ;rjmp	 TIM1_CAPT	 ;ﾀｲﾏ/ｶｳﾝﾀ1捕獲発生
	 	 rjmp	 TIM1_COMPA		 ;ﾀｲﾏ/ｶｳﾝﾀ1比較A一致
	 	 reti  ;rjmp	 TIM1_COMPB	 ;ﾀｲﾏ/ｶｳﾝﾀ1比較B一致
	 	 reti  ;rjmp	 TIM1_OVF	 ;ﾀｲﾏ/ｶｳﾝﾀ1溢れ
	 	 reti  ;rjmp	 TIM0_COMPA	 ;ﾀｲﾏ/ｶｳﾝﾀ0比較A一致
	 	 reti  ;rjmp	 TIM0_COMPB	 ;ﾀｲﾏ/ｶｳﾝﾀ0比較B一致
	 	 reti  ;rjmp	 TIM0_OVF	 ;ﾀｲﾏ/ｶｳﾝﾀ0溢れ
	 	 reti  ;rjmp	 SPI_STC	 ;SPI転送完了
	 	 reti  ;rjmp	 USART_RXC	 ;USART 受信完了
	 	 reti  ;rjmp	 USART_UDRE	 ;USART 送信ﾊﾞｯﾌｧ空
	 	 reti  ;rjmp	 USART_TXC	 ;USART 送信完了
	 	 reti  ;rjmp	 ADC_	 	;ADC変換完了
		 reti  ;rjmp	 EE_RDY	 	;EEPROM操作可
	 	 reti  ;rjmp	 ANA_COMP	 ;ｱﾅﾛｸﾞ比較器出力遷移
	 	 reti  ;rjmp	 TWI	 	;2線直列ｲﾝﾀｰﾌｪｰｽ状態変化
	 	 reti  ;rjmp	 SPM_RDY	 ;SPM命令操作可
RESET:
	ldi	R16,HIGH(RAMEND)	;RAM最終ｱﾄﾞﾚｽ上位を取得
	out	SPH,R16	 ;ｽﾀｯｸ ﾎﾟｲﾝﾀ上位を初期化
	ldi	R16,LOW(RAMEND)	;RAM最終ｱﾄﾞﾚｽ下位を取得
	out	SPL,R16	 ;ｽﾀｯｸ ﾎﾟｲﾝﾀ下位を初期化
start:
	ldi	r16,0x80	;set cpu clk 4MHz
	sts	CLKPR,r16
	ldi	r16,0x01	;1/2		
	sts	CLKPR,r16

	ldi	temp1,0xfe	; pd0 in port pull up
	out	DDRD,temp1	; pd1~7 out port
	ldi	temp1,0x01	; pd1~7 low	
	out	PORTD,temp1
	
	ldi	temp1,0x01	; pb0 out port "1"
	out	DDRB,temp1	; pb1~7 in port
	ldi	temp1,0xff	; pb1~7 pull up		
	out	PORTB,temp1

	ldi	temp1,0x00	; pc0~5 in port
	out	DDRC,temp1	
	ldi	temp1,0x7f	; pc0~6 pull up
	out	PORTC,temp1	


; LCD - Initialize LCD controller
lcd_init:
	ldi	temp1,15	; wait for 15+ms
	rcall	wait_ms		; /
	rcall	lcd_int		; /
	ldi	temp1,5		; Wait for 4.1ms+
	rcall	wait_ms		; /
	rcall	lcd_int		; /
	ldi	temp1,100 	;wait for 100us+
	rcall	wait_us		; /
	rcall	lcd_int		; /
	ldi	lcd_data,0x20
	rcall	lcd_cmd
	ldi	temp1,100 		;wait for 100us+
	rcall	wait_us			; /
	ldi	lcd_data,0x28	; Data=4bit, Line=2, Font=5x7
	rcall	lcd_cmd			; /
	ldi	lcd_data,0x0c	; Display=ON, Cursor=OFF, Blink=OFF
	rcall	lcd_cmd			; /
	ldi	lcd_data,6		; Increment, No shift
	rcall	lcd_cmd			; /
	ldi	lcd_data,1		; clear ,homepos
	rcall	lcd_cmd
	ldi	lcd_data,0x84
 	rcall	lcd_cmd
	ldi	lcd_data,'O'
	rcall	lcd_dsp
	ldi	lcd_data,'K'
	rcall	lcd_dsp

timer1_set:
	stsi	TIMSK1,1<<OCIE1A	;タイマ１比較A一致割込み許可
	stsi	TCCR1B,(1<<WGM12)|(1<<CS11)|(1<<CS10)	;タイマ１比較A一致後クリア、TCK=CK/64
	stsi	OCR1AH,high(62500)	;割込み周期　10s
	stsi	OCR1AL, low(62500)	;1s/(1/4M/64)=62500
	stsi	TCNT1H,0
	stsi	TCNT1L,0
	sei

main:
	rjmp main

	
TIM1_COMPA:
	rcall	ds_int
	tst	temp2
	breq	t_c_1
	ldi	lcd_data,0x84
 	rcall	lcd_cmd
	ldi	lcd_data,'E'
	rcall	lcd_dsp
	ldi	lcd_data,'1'
	rcall	lcd_dsp
t_c_0:
	rjmp t_c_0

t_c_1:
	ldi	data,0xcc	;skip rom
	rcall	com_send
	ldi	data,0x44	;convert T
	rcall	com_send
	ldi	temp1,250
	rcall	wait_ms
	ldi	temp1,250
	rcall	wait_ms
	ldi	temp1,230
	rcall	wait_ms
convert1:
	ldi	temp1,10
	rcall	wait_ms
	rcall	read_d
	tst	temp2
	breq	convert1
	rcall	ds_int
	ldi	data,0xcc	;skip rom
	rcall	com_send
	ldi	data,0xbe	;read scratchpad
	rcall	com_send
	rcall	read_scr
	rcall	dsp
	rcall	temp_dsp
	reti

temp_dsp:
	ldi	lcd_data,0xC6
 	rcall	lcd_cmd
	lds	r22,sp_dat
	lds	r23,sp_dat+1
	tst	r23
	brpl	temp_dsp1
	andi r23,0x0f
	clr	r24
	neg	r22
	sbc	r24,r23
	ldi	lcd_data,'-'
	rcall	lcd_dsp
	mov temp2,r24
	rjmp	temp_dsp2
temp_dsp1:
	ldi	lcd_data,' '
	rcall	lcd_dsp
	andi	r23,0x0f
	mov temp2,r23
temp_dsp2:
	mov temp1,r22
	;temp2:temp1 x10/16=10xdeg
	lsl	temp1
	rol	temp2		;x2
	mov	temp3,temp1
	mov	temp4,temp2
	lsl	temp1
	rol	temp2
	lsl	temp1
	rol	temp2		;x8
	add	temp3,temp1			;L2:L1
	adc	temp4,temp2	;x10(2+8)	;H2:H1
	andi	temp3,0xf0	;L2:00
	swap	temp3		;00:L2
	mov	temp1,temp4	;H2:H1
	swap	temp1		;H1:H2
	mov	temp2,temp1	;H1:H2
	andi	temp1,0xf0	;H1:00
	or	temp1,temp3	;H1:L2
	andi	temp2,0x0f	;00:H2
	rcall	bindec40	;r1,r2,r3,r4
	tst	r1
	brne	temp_dsp3
	ldi	lcd_data,' '
	rjmp	temp_dsp4
temp_dsp3:
	ldi	lcd_data,0x30
	add	lcd_data,r1
temp_dsp4:
	rcall	lcd_dsp		;百位
	or	r1,r2
	brne	temp_dsp5
	ldi	lcd_data,' '
	rjmp	temp_dsp6
temp_dsp5:
	ldi	lcd_data,0x30
	add	lcd_data,r2
temp_dsp6:
	rcall	lcd_dsp		;十位
	ldi	lcd_data,0x30
	add	lcd_data,r3
	rcall	lcd_dsp		;一位
	ldi	lcd_data,'.'
	rcall	lcd_dsp	
	ldi	lcd_data,0x30
	add	lcd_data,r4
	rcall	lcd_dsp		;0.1位
	ldi	lcd_data,0xdf
	rcall	lcd_dsp	
	ldi	lcd_data,'C'
	rcall	lcd_dsp
	ret

dsp:
	ldi	lcd_data,0x80
 	rcall	lcd_cmd
	ldi	temp4,8
	ldiw	x,sp_dat
dsp1:
	ld	data,x+
	rcall	hex_dsp
	dec	temp4
	brmi	dsp2
	brne	dsp1
	ldi	lcd_data,0xC0
 	rcall	lcd_cmd
	rjmp	dsp1
dsp2:
	ret

hex_dsp:
	ldi	temp1,0xf0
	and	temp1,data
	swap	temp1
	cpi	temp1,10
	brcc	hex_dsp1
	ldi	lcd_data,0x30
	rjmp	hex_dsp2
hex_dsp1:
	ldi	lcd_data,0x37
hex_dsp2:
	add	lcd_data,temp1
	rcall	lcd_dsp

	andi	data,0x0f
	cpi	data,10
	brcc	hex_dsp3
	ldi	lcd_data,0x30
	rjmp	hex_dsp4
hex_dsp3:
	ldi	lcd_data,0x37
hex_dsp4:
	add	lcd_data,data
	rcall	lcd_dsp
	ret

	

read_scr:
	ldi	temp4,9
	ldiw	x,sp_dat
r_s_1:
	ldi	temp3,8
	clr	data
r_s_2:
	rcall	read_d
	lsr	temp2
	ror	data
	dec	temp3
	brne	r_s_2		
	st	x+,data
	dec	temp4
	brne	r_s_1
	ret


com_send:
	ldi	temp3,8
com_send1:
	lsr	data
	brcs	com_send2
	rcall	send0
	rjmp	com_send3
com_send2:
	rcall	send1	
com_send3:
	dec	temp3
	brne	com_send1
	ret

ds_int:
	clr temp2
	cbi PORTB,ds_dat
	ldi temp1,250	;bus low 480us+
	rcall wait_us
	ldi temp1,250
	rcall wait_us
	sbi PORTB,ds_dat

	ldi temp1,70	;wait 60+(60~240)us  -> 210
	rcall wait_us
	cbi DDRB,ds_dat	;input pull up
	sbic PINB,ds_dat
	ldi temp2,1	;no dev
	ldi temp1,250	;wait 480+(500=210+250+40)
	rcall wait_us
	ldi temp1,180
	rcall wait_us
	sbi DDRB,ds_dat	;output high
	ret

send0:
	cbi PORTB,ds_dat
	ldi temp1,70	;bus low 60~120us
	rcall wait_us
	sbi PORTB,ds_dat
	ldi temp1,5	;wait 1us+
	rcall wait_us
	ret
send1:
	cbi PORTB,ds_dat
	ldi temp1,5	;bus low 1~15us
	rcall wait_us
	sbi PORTB,ds_dat
	ldi temp1,70	;wait 60us+ 
	rcall wait_us
	ret

read_d:	;return bit 0:temp2=0,1:temp2=1 
	clr temp2
	cbi PORTB,ds_dat
	ldi temp1,2	;bus low 1us+
	rcall wait_us	
	cbi DDRB,ds_dat	;input
	ldi temp1,10	; ~15us 2+10
	rcall wait_us
	sbic PINB,ds_dat
	ldi temp2,1
	ldi temp1,60	;wait 49us+ 
	rcall wait_us
	sbi PORTB,ds_dat
	sbi DDRB,ds_dat	;output high
	ret		

			
;-----------------------------------------------;
; LCD - Send a data/cmd into LCD
	;PORTD   7   6   5   4   3   2    1   0
	;write   <-data(H/L)->  enb r/w  r/s  -
	;read   BF   -   -   -   -   -    -   -  
 
lcd_int:	; Internal reset
	ldi	lcd_data,0x30	; data='0011',RW = "L", RS = "L",E = "L"
	out	PORTD,lcd_data	
	sbi	PORTD,lcd_enb	; E = "H"
	nop			; I/O delay
	nop			; I/O delay
	nop			; I/O delay
	cbi	PORTD,lcd_enb	; E = "L"
	ret

lcd_dsp:
	rcall	lcd_bfch
	ldi	temp3,0x02	; RW = "L",RS = "H",E = "L",data='xxxx'
	rjmp	lcd_cmd1
lcd_cmd:
	rcall	lcd_bfch
	ldi	temp3,0		; RW = "L",RS = "L",E = "L",data='xxxx'
lcd_cmd1:
	mov	temp2,lcd_data
	swap	temp2
	andi	temp2,0xf0	;data_L save

	andi lcd_data,0xf0   ;data_H set
	or	lcd_data,temp3
	out	PORTD,lcd_data	; PORTD = data_H,RW
	sbi	PORTD,lcd_enb	; E = "H"
	mov	lcd_data,temp2	; 
	or	lcd_data,temp3	;data_L set
	nop						
	cbi	PORTD,lcd_enb	; E = "L"
	nop			; I/O delay				
	out	PORTD,lcd_data	; PORTD = data_L,RW
					
	sbi	PORTD,lcd_enb	; E = "H"
	nop			; I/O delay
	nop			; I/O delay
	nop			; I/O delay
	cbi	PORTD,lcd_enb	; E = "L"
	ret

lcd_bfch:
	cbi	DDRD,lcd_db7	; lcd_db7 = INPUT
	sbi	PORTD,lcd_db7	; pullup
	sbi	PORTD,lcd_rw	; RW = "H"
	cbi	PORTD,lcd_rs	; RS = "L"
lcd_bfch1:
	sbi	PORTD,lcd_enb	; E = "H"
	nop			; I/O delay
	nop			; I/O delay
	in	temp1,PIND
	cbi	PORTD,lcd_enb	; E = "L"
	nop
	nop
	sbi	PORTD,lcd_enb	; E = "H"
	nop			; I/O delay
	nop			; I/O delay
	in	temp2,PIND
	cbi	PORTD,lcd_enb	; E = "L"

	andi	temp1,0x80	; Wait until busy flag becomes zero.
	brne	lcd_bfch1
	sbi	DDRD,lcd_db7	; lcd_db7 = OUTPUT
	cbi	PORTD,lcd_db7	; clear
	ret
;*********************************************
wait_us:	;base 4MHz	
				;temp1　us (4clocks)
	nop			; 1clocks
	dec	temp1		; 1clocks
	brne	wait_us		; 2clocks
	ret
;*********************************************	
wait_ms:	;temp1　ms at 4MHz
	ldi	temp2,50	;80*50=4000clocks
wait_ms_01:
	ldi	temp3,19    	;1clocks  4*(19+1)=80
wait_ms_02:
	nop			; 1clocks
	dec	temp3		; 1clocks
	brne	wait_ms_02	; 2clocks
	dec	temp2		; 1clocks
	brne	wait_ms_01	; 2clocks
	dec	temp1		; 1clocks	
	brne	wait_ms		; 2clocks
	ret


;***************************************************************************
;*
;* "bindec" - 16-bit Binary to dec 
;*  bin:=temp2:temp1  dec=r5,r0,r1,r2,r3,r4
;***************************************************************************
bindec60:	;<99999 if 100,0000+ then r5=10+
	clr	r5
	clr r0
bindec61:
	cpi24	temp3,temp2,temp1,100000
	brcs	bindec62
	inc r5
	subi24	temp3,temp2,temp1,100000
	rjmp	bindec61
bindec62:
	tst temp3
	breq	bindec51
	inc r0
	subi24	temp3,temp2,temp1,10000
	rjmp	bindec62
bindec50:	;>9999
	clr	r0
bindec51:
	cpi16	temp2,temp1,10000
	brcs	bindec40
	subi16	temp2,temp1,10000
	inc	r0
	rjmp	bindec51
bindec40:	;>999
	clr	r1
bindec41:
	cpi16	temp2,temp1,1000
	brcs	bindec30
	subi16	temp2,temp1,1000
	inc	r1
	rjmp	bindec41
bindec30:	;>99
	clr	r2
bindec31:
	cpi16	temp2,temp1,100
	brcs	bindec20
	subi16	temp2,temp1,100
	inc	r2
	rjmp	bindec31
bindec20:	;>9
	clr	r3
bindec21:
	cpi	temp1,10
	brcs	bindec10
	subi	temp1,10
	inc	r3
	rjmp	bindec21
bindec10:	;<10
;	clr	r4
	mov	r4,temp1
	ret

 
