|
;***********************************************************************
;*
;* Number :DS1820
;* File Name :"DS1820.asm"
;* Title :AVR alapu DS1820 thermometer + RS232 interface
;* - LM16x21A Driver via Lattice ispLSI2032
;*
;* Date :2000.06.12.
;* Version :1.0
;* Support telephone :+36-70-333-4034
;* Support fax :
;* Support E-mail :info@vfx.hu
;* Target MCU :AT90S2313
;*
;* DESCRIPTION
;* kezeli a következő eszközöket:
;* - DS1820 Thermometer unit
;* - Fulduplex RS232 port
;* - SS0=0 & SS1=0 akkor az LCD port az SPI target
;*
;* AT90S2313 lábkiosztás
;*
;* RESET 1. 20. VCC
;* * RxD (PD0) 2. 19. (PB7) SCK *
;* * TxD (PD1) 3. 18. (PB6) MISO *
;* XTAL2 4. 17. (PB5) MOSI *
;* XTAL1 5. 16. (PB4) SS0 *
;* INT0 (PD2) 6. 15. (PB3 OC1) LED0
;* INT1 (PD3) 7. 14. (PB2) SS1 *
;* (T0 PD4) 8. 13. PB1 {AIN1} AT45D CS
;* DS1820 T1 (PD5) 9. 12. PB0 {AIN0}
;* GND 10. 11. {PD6 ICP}
;*
;* Kristályfrekvencia: f=1.8432 MHz (T=0.54253 us)
;*
;* * a csillagos IO labak fix huzalozasuak, masra nem hasznalhatok fel!!!
;***********************************************************************
.include "2313def.inc"
;**************************************************************************
;* Hardware Def.
.EQU DS1820_BIT = 5 ;Dallas 1-Wire bus
.EQU DS1820_PORT =DDRD ;Dallas Port cime
.EQU LEDPORT = DDRB
.EQU LED = 3 ;A LED bitcime
;SPI selector - 00 LCD
.EQU SS0PORT= DDRB
.EQU SS0= BP4
.EQU SS1PORT= DDRB
.EQU SS1= BP2
;**************************************************************************
;* UART Def
.EQU BaudRate=11 ;11 - 9600
;7 - 14400
;5 - 19200
;1 - 57600
;***************************************************************************
;***** Divide Subroutine Register Variables
.def drem16uL=r14
.def drem16uH=r15
.def dres16uL=r16
.def dres16uH=r17
.def dd16uL =r16
.def dd16uH =r17
.def dv16uL =r18
.def dv16uH =r19
;***************************************************************************
;* SPI Master, Mode 0, MSB-first
;*
;* MAJOR ROUTINES:
;* init_spi: initializes the port lines used for SPI.
;* No calling requirements, returns nothing.
;* ena_AT: forces SCK low, and activates /SS signal.
;* No calling requirements, returns nothing.
;* disa_AT: brings /SS signal hi (inactive).
;* No calling requirements, returns nothing.
;* rw_spi: sends/receives an 8-bit data.
;* Must set up data to be sent in (spi_lo)
;* prior to calling; it returns received data in
;* the same register (spi_lo register).
;*
;*
.equ sck = 7 ;PB7 pin
.equ miso = 6 ;PB6 pin
.equ mosi = 5 ;PB5 pin
.equ ATss = 1 ;PB4=1 , PB2=0 pin AT45D041 CS ???????
.def spi_lo = R0 ;change as needed
.def temp = R16 ;misc usage, must be in upper regs for IMMED mode
.def ATComm = R20 ;AT45Dxxx command parameter register
.def ATPoint = R21 ;AT45Dxxx Buffer Pointer register
.def ATPageL = R21 ;AT45Dxxx Page Address low
.def ATPageH = R22 ;AT45Dxxx Page Address hi
.def LCDLo = R20 ;LCD Low byte
.def LCDHi = R21 ;
.equ BFSeg = 32 ;32 byte r/w
.macro Select_LCD
CBI SS0PORT+1,SS0
cbi SS1PORT+1,SS1
.endm
;***************************************************************************
;*
;* SPI MACROS
;* Program Macros
.macro AT_active
cbi portb,ATss
.endm
.macro AT_inactive
sbi portb,ATss
.endm
.macro sck_hi
sbi portb,sck
.endm
.macro sck_lo
cbi portb,sck
.endm
.macro mosi_hi
sbi portb,mosi
.endm
.macro mosi_lo
cbi portb,mosi
.endm
;.macro addi
; subi @0, -@1 ;subtract the negative of an immediate value
;.endm
.macro set_delay ;set up the time delay amount, from 1 to 7
subi @0, (@1 << 5) ;NOTE: THIS shift affects INC macro (below)!
.endm
.macro inc_delay ;bump the delay counter
subi @0, -(1 << 5) ;shift value here must be same as above!
.endm
;******************************************************************************
;**** CONST
;;;;.EQU RPMFACT = 17280 ;RPM= RPMFACT/IMP*100
.EQU T0Freq=220 ;1.8432MHz = 50Hz
;FLAGS
.EQU Active = 2 ;Imo Active bit
;******************************************************************************
;**** VARIABLES
.DSEG
DS1: .BYTE 1 ;Flagbitek
; 0. = 1 RPM overflow
; 1. = 1 Velocity overflow
; 2. = 1 Immo. Active
; 4. = 1 LED kijelzo frissites kell
CNT1: .BYTE 2 ;Interupt COUNTER
DS3: .BYTE 4 ;RealTime Clock
DS4: .BYTE 2 ;UART Transmit Interrupt rutin cime
DS5: .BYTE 2 ;UART Receive Interrupt rutin cime
DS6: .BYTE 2 ;UART Transmit Buffer Address
DS7: .BYTE 2 ;Fordulatszam binaris
DS8: .BYTE 2 ;Sebesseg bin
DS9: .BYTE 2 ;Fordulatszamalalo start
DS10: .BYTE 2 ;SebessegSZAMLALO start
DS11: .BYTE 1 ;TEMP az UART RX-hez
CRC: .BYTE 1 ;DS1820 CRC GENERATOR HASZNALJA
DSRD: .BYTE 10 ;Ide olvassa be a DS Chipet
DS12: .BYTE 1 ;Bad CRC szamlalo
IOBuff: .BYTE BFSeg ;AT45Dxxx IO munkaterulet
;*Variables Offset to Y
.EQU FLAGS = DS1-DS1 ;Z+0
.EQU RTC = DS3-DS1 ;RealTime Clock
.EQU UTx = DS4-DS1 ;UART Transmit Interrupt rutin cime
.EQU URx = DS5-DS1 ;UART Receive Interrupt rutin cime
.EQU TXT = DS6-DS1 ;UART Transmit Buffer Address
.EQU RPMB = DS7-DS1 ;Fordulatszam binaris
.EQU VELB = DS8-DS1 ;Sebesseg bin
.EQU RPMC = DS9-DS1 ;Fordulatszamalalo start
.EQU VELC = DS10-DS1 ;SebessegSZAMLALO start
.EQU TEMP = DS11-DS1 ;TEMP az UART RX-hez
.EQU CRCoff = CRC-DS1 ;CRC
.EQU CNT1L = CNT1-DS1 ;CNT1
.EQU CNT1H = CNT1-DS1+1
.EQU BadCRC = DS12-DS1 ;
;**************************************************************************************
.ESEG
KEY1: .DB 0x01
.DB 0x88
.DB 0xDD
.DB 0x07
.DB 0x02
.DB 0x00
.DB 0x00
KEY2: .DB 0x01
.DB 0x6D
.DB 0xB9
.DB 0x07
.DB 0x02
.DB 0x00
.DB 0x00
;*****************************************************************************
;**** I N T E R R U P T S
;****
;*****************************************************************************
.CSEG
rjmp RESET ;Reset Handle
rjmp EXT_INTO ;IRQ0 Handle
rjmp EXT_INT1 ;IRQ1 Handle
rjmp TIM_CAPT1 ;Timer1 capture Handle
rjmp TIM_COMP1 ;Timer1 compare Handle
rjmp TIM_OVF1 ;Timer1 overflow Handle
rjmp TIM_OVF0 ;Timer0 overflow Handle
rjmp UART_RXC ;UART RX Complete Handle
rjmp UART_DRE ;UDR Empty Handle
rjmp UART_TXC ;UART TX Complete Handle
rjmp ANA_COMP ;Analog Comparator Handle
;***********
;* RESET
;***********
RESET: CLI ;GLOBAL INTERRUP DIS.
LDI R16,42 ;Sleep enable, Idle mode,INT0, INT1 fall-edge sens.
OUT MCUCR,R16
LDI R16,RAMEND
OUT SPL,R16 ;STACK A BELSO RAM VEGETOL INDUL LEFELE
LDI R16,0 ;INT0, INT1 Disabled
OUT GIMSK,R16 ;7. = 1 EXT INT1 ACTIVE
;6. = 1 EXT INT0 ACTIVE
LDI R16,2
OUT TIMSK,R16 ;7. = 1 TC1 OWRF EN. *
;6. = 1 TC1 COMP MATCH EN.
;3. = 1 TC1 INP CAPTURE EN.
;1. = 1 TC0 OWRF EN. *
LDI R16,0
OUT TCCR1A,R16 ;TC1 Disconected from OC1 pin, PWM Dis.
LDI R16,3
OUT TCCR1B,R16 ;Input Capture Dis., f=CLK/64
LDI R16,T0Freq
OUT TCNT0,R16 ;50Hz
LDI R16,5
OUT TCCR0,R16 ;f(TC1)=CLK/1024
LDI YL,LOW(DS1)
LDI YH,HIGH(DS1) ;BAZIS 'X' +0
LDI R16,0
STD Y+CRCoff,R16 ;CRC=0
STD Y+CNT1L,R16
STD Y+CNT1H,R16 ;CNT1=0
STD Y+RTC+0,R16 ;RealTime Clock=1970\01\01
STD Y+RTC+1,R16
STD Y+RTC+2,R16
STD Y+RTC+3,R16
STD Y+BadCRC,R16 ;BadCRC=0
LDI R16,(1< R0
ADIW ZL,1
MOV R16,R0
STD Y+TXT+0,ZL
STD Y+TXT+1,ZH
CPI R16,0
BRNE MoreTXT ;VAN MEG SZOVEG
LDI R16,low(UReti)
STD Y+UTx+0,R16
LDI R16,high(UReti)
STD Y+UTx+1,R16 ;UART TX INT. ADDR
CPSE R16,R16 ;AZERT, HOGY AKOVETKEZO SOR KIMARADJON
MoreTXT: OUT UDR,R16
POP R0
POP R16
POP ZL
OUT SREG,ZL
POP ZH
POP ZL
RETI
;*************************************************************************
;* Text Const
;*
Copyr: .DB "(C) 2000, DS1820 Thermometer V1.0 ", 10,13
Ready: .DB "Ready>>",0
Hiba: .DB "Error..",10,13,0
;***********************************************************************
;***********************************************************************
;******** M A I N ********
;******** ********
;***********************************************************************
Main: LDI R16,10
STD Y+CNT1L,R16
LDI R16,0
STD Y+CNT1H,R16 ;CNT1=25 0.5s
wait: ;SLEEP
ldd R16,Y+TEMP
CPI R16,'R'
BREQ WHTROM
CPI R16,'r'
BREQ WHTROM
CPI R16,'T'
BREQ RDTH
CPI R16,'t'
BREQ RDTH
rjmp Csokkent
RDTH: cli
rcall ReadTh
sei
brcc CMDsEND ;ha nincs eszkoz a buszon, akkor kihagy
rcall ComuteT ;R22,R23 a korigalt hom
MOV R0,R23
rcall TOUART
MOV R0,R22
rcall TOUART
Wt6: SBIS USR,UDRE ;a kovetkezo kimarad, ha a TX reg ures
RJMP Wt6
LDI R16,' '
OUT UDR,R16
Wt7: SBIS USR,UDRE ;a kovetkezo kimarad, ha a TX reg ures
RJMP Wt7
LDI R16,' '
OUT UDR,R17
LDI XL,LOW(DSRD)
LDI XH,HIGH(DSRD) ;ide olvasta a DS Chipet
LDI R19,8 ;8 byteot kuldunk ki
rjmp WHTR1
WHTROM: CLI
rcall ReadROM
SEI
brcc CMDsEND ;ha nincs eszkoz a buszon, akkor kihagy
LDI R19,8 ;8 byteot kuldunk ki
LDI XL,LOW(DSRD)
LDI XH,HIGH(DSRD) ;ide olvasta a DS Chipet
WHTR1: LD R16,X+
MOV R0,R16
rcall TOUART
Wt4: SBIS USR,UDRE ;a kovetkezo kimarad, ha a TX reg ures
RJMP Wt4
LDI R16,' '
OUT UDR,R16
dec R19
BRNE WHTR1
CMDsEND: SBIS USR,UDRE ;a kovetkezo kimarad, ha a TX reg ures
RJMP CMDsEND
LDI R16,13
OUT UDR,R16
Wt9: SBIS USR,UDRE ;a kovetkezo kimarad, ha a TX reg ures
RJMP Wt9
LDI R16,10
OUT UDR,R16
LDI R16,0
std Y+TEMP,R15 ;a parancssort kinullazzuk
Csokkent: LDD R24,Y+CNT1L
LDD R25,Y+CNT1H
OR R24,R25
BRNE wait
;Kell-e villogni?
LDD R16,Y+FLAGS
SBRS R16,Active ;a kovetkezo kimarad ha az Active=1
rjmp Main
; Led villogtato
LEDvil: SBIS LEDPORT+1,LED ;kihagy, ha LED=1
RJMP Led_be
CBI LEDPORT+1,LED ;LED eg
RJMP Main
Led_be: SBI LEDPORT+1,LED ;LED nem eg
RJMP Main
;CRC-t ellenorzi
; LD R1,X+ ;olvasott CRC
; LDD R0,Y+CRCOff ;szamolt CRC
; CP R1,R0
; BREQ CRCOK ;GoodCRC
;R0-ban levo byte kiirasa az uartra (HEX)
TOUART: LDI R17,48
LDI R18,7
Wt1: SBIS USR,UDRE ;a kovetkezo kimarad, ha a TX reg ures
RJMP Wt1
MOV R16,R0
SWAP R16
ANDI R16,0x0F
CPI R16,10
BRCS Kicsi1
ADD R16,R18
Kicsi1: ADD R16,R17
OUT UDR,R16
Wt2: SBIS USR,UDRE ;a kovetkezo kimarad, ha a TX reg ures
RJMP Wt2
MOV R16,R0
ANDI R16,0x0F
CPI R16,10
BRCS Kicsi0
ADD R16,R18
Kicsi0: ADD R16,R17
OUT UDR,R16
ret
.include "div16.asm"
.include "SPI.asm"
;************************************************************************
;*********************** 1-Wire Bus *************************************
;************************************************************************
;------------------------------------------------------------------------
;Kiolvasott DS chip tartalmat osszehasonlitja az EEpromban taroltakkal
;
; R14 a KEY Offsetcime
;
;C=0 Nem jo
;C=1 Kulcs jo
DScomp:
LDI XL,LOW(DSRD)
LDI XH,HIGH(DSRD) ;ide olvassa DS Chipet
OUT EEAR,R24 ;EEPROM address
LDI R16,7 ;CRC-vel egyutt 8 byte comp.
Cikl2: RCALL EERead_seq ;EEPrombol akovetkezo elem R0-ba
LD R1,X+
SUB R1,R0
BRNE Rossz
DEC R16
BRNE Cikl2
SEC
RET
Rossz: CLC
RET
;***********************************************************************
;.......................................................................
;Read DS1820
;c=1 Chip kiolvasva
;c=0 Chip nincs
;(Beolvas egy chippet az Y-ban megadott cimre)
;
;Hasznalja a R18, R17, R16, R3, R2, R0;
;.......................................................................
ReadROM:
LDI XL,LOW(DSRD)
LDI XH,HIGH(DSRD) ;ide olvassa DS Chipet
LDI R16,0
STD Y+CRCoff,R16 ;CRC=0 ;
RCALL TouchReset
BRCS RDS1 ;ESZKOZ A BUSZON VAN
CLC
RET
RDS1: LDI R16,0x33 ;SEARCH ROM COMMAND
MOV R0,R16
LDI R19,7 ;7-SZER OLVASUNK BE
RCALL TouchByte
RDS2: LDI R16,0xFF ;BEOLVASUNK 8 BITET
MOV R0,R16
RCALL TouchByte
ST X+,R1
RCALL CRCGEN
DEC R19
BRNE RDS2
LDI R16,0xFF ;BEOLVASSUK A CRCT
MOV R0,R16
RCALL TouchByte
ST X+,R1
LDI R19,0xFF
RDS3: DEC R19
BRNE RDS3
SEC ;CHIP RENDBEN
RET
;****************************************************************************
;******* TOUCHBYTE
;****************************************************************************
;
;R0-ban megadott byte-ot kiküldi a touchmemory-nak
;és szimultán beolvas egy byte-ot onnan az R1-be
;Hasznalja a R17, R16 R3, R2
;
TouchByte:
LDI R17,8 ;[1]
BIT_LOOP:
ROR R1 ;[1]
RCALL TOUCHBIT ;[3]
ROR R0 ;[1]
DEC R17 ;[1]
BRNE BIT_LOOP ;[1/2]
RET ;[1]
TOUCHBIT:
SBI DS1820_PORT,DS1820_BIT ;[2]
LDI R16,3 ;[1]
BW0: DEC R16 ;[1]
BRNE BW0 ;[1/2]
SBRC R0,0 ;[1/2]
CBI DS1820_PORT,DS1820_BIT ;[2]
LDI R16,8 ;[1]
BW1: DEC R16 ;[1]
BRNE BW1 ;[1/2]
IN R2,DS1820_PORT-1 ;[1]
BST R2,DS1820_BIT ;[1]
BLD R1,7 ;[1]
LDI R16,26 ;[1]
TCHL: DEC R16 ;[1]
BRNE TCHL ;[1/2]
CBI DS1820_PORT,DS1820_BIT ;[2]
RET ;[4]
;*******************************************************************************
;****** T O U C H R E S E T
;*******************************************************************************
;
;Inicialization procedure "Reset and PreSence Pulses"
;
; Ez a rutin egy Reset jelet general a mikrovrzerlo ketiranyu DS_BIT nevu laban,
;a Touch Memory fele es figyeli a visszajovo PreSence jelet.
;Ha a PreSence jel megerkezett, akkor C=1 kulonben C=0 (nincs eszkoz a buszon)
;
; |-Master Rx "Presence Pulse"-|
; |---Master Reset Tx Pulse---| |----t(RSTH)---------------|
; __ t(RSTL) _____ _____ \\ ___
; \ / \ / \
; \_________________________/ \______/ \__ ...
; |-----|-------|
; t(PDH) t(PDL)
; t(R) <-- |-|
;
; 480us<=t(RSTL)< . t(RSTL)+t(R)<960us
; 480us<=t(RSTH)<
; 15us<=t(PDH)<=60us
; 60us<=t(PDL)<=240us
;
; C-flag = 1 DS1990A a buszon van
; = 0 DS1990A nincs a buszon
;
; R16
; Testelt jol mukodik
; Cyc:
TouchReset:
SBI DS1820_PORT,DS1820_BIT ;[2] 1-wire = Master LOW , Start the reset pulse
LDI R16,222 ;[1]
TR0: NOP ;[1]
DEC R16 ;[1]
BRNE TR0 ;[1/2] 480us wait with data low
SBI DS1820_PORT+1,DS1820_BIT ;[2] 1-wire =Active Hi
nop ;[1]
CBI DS1820_PORT,DS1820_BIT ;[2] 1-wire HI (felengedve)
CBI DS1820_PORT+1,DS1820_BIT ;[2] 1-wire = Tri-state
nop ;[1]
SBIS DS1820_PORT-1,DS1820_BIT ;[1/2]
RJMP Short ;[2] ha egybol Low az rossz
LDI R16,21 ;[1]
TR1: SBIS DS1820_PORT-1,DS1820_BIT ;[1/2]
RJMP WL ;[2] Exit loop if line low
DEC R16 ;[1]
BRNE TR1 ;[1/2] us wait with data low
RJMP SHORT ;[2] Line could not go low
WL: LDI R16,87 ;[1]
TR3: SBIC DS1820_PORT-1,DS1820_BIT ;[1/2]
RJMP WH ;[2] Exit loop if line hi
DEC R16 ;[1]
BRNE TR3 ;[1/2] us wait with data low
SHORT: CLC ;[1] Error
RET ;[4]
WH: SEC ;[1] RESET OK.
RET ;[4]
;*************************************************************************
;.........................................................................
; DS1990A CRC GENERATOR
;IN: R1
;USE: R21,R20, R4,R3, R0, R18
;.........................................................................
CRCGEN: PUSH R1
LDI R20,8
LDI R18,0x18
PUSH R1
CRC_L: LDD R3,Y+CRCoff ;CRC
EOR R1,R3
ROR R1
MOV R1,R3
BRCC ZERO
EOR R1,R18
ZERO: ROR R1
STD Y+CRCoff,R1
POP R1
SEC
SBRS R1,0
CLC
ROR R1
PUSH R1
DEC R20
BRNE CRC_L
POP R1
POP R1
RET
;***********************************************************************
;.......................................................................
;Read DS1820
;c=1 Chip kiolvasva
;c=0 Chip nincs
;(Beolvas egy chippet az Y-ban megadott cimre)
;
;Hasznalja a R18, R17, R16, R3, R2, R0;
;.......................................................................
ReadTh:
LDI XL,LOW(DSRD)
LDI XH,HIGH(DSRD) ;ide olvassa DS Chipet
LDI R16,0
STD Y+CRCoff,R16 ;CRC=0
RCALL TouchReset
BRCS DSVAN ;ESZKOZ A BUSZON VAN
CLC
RET
DSVAN: LDI R16,0xCC ;Skip ROM Command
MOV R0,R16
RCALL TouchByte
LDI R16,0x44 ;Convert T Command
MOV R0,R16
RCALL TouchByte
nop
nop
nop
nop
nop
nop
nop
DSW1: SBIS DS1820_PORT-1,DS1820_BIT ;ha 1 akkor a kovetkezo kimarad
RJMP DSW1 ;varunk mig a komvertalas vege nincs
nop
nop
LDI R16,0
STD Y+CRCoff,R16 ;CRC=0 ;
RCALL TouchReset
BRCS DS2VAN ;ESZKOZ A BUSZON VAN
CLC
RET
DS2VAN:
LDI R16,0xCC ;Skip ROM Command
MOV R0,R16
RCALL TouchByte
LDI R16,0xBE ;Read Scratchpad command.
MOV R0,R16
RCALL TouchByte
nop
nop
LDI R19,8 ;8-SZOR OLVASUNK BE
DS2T: LDI R16,0xFF ;BEOLVASUNK 8 BITET
MOV R0,R16
RCALL TouchByte
ST X+,R1
RCALL CRCGEN
DEC R19
BRNE DS2T
LDI R16,0xFF ;BEOLVASSUK A CRCT
MOV R0,R16
RCALL TouchByte
ST X+,R1
LDI R19,0xFF
DS3T: DEC R19
BRNE DS3T
RCALL TouchReset
SEC ;CHIP RENDBEN
RET
;Tc=8T-2+(8*Count-8*Remainder)/8Count
ComuteT: LDI ZL,LOW(DSRD)
LDI ZH,HIGH(DSRD) ;ide olvassa DS Chipet
LDD dd16uL,Z+7 ;CPC
LDI dd16uH,0
LDD R22,Z+6 ;CRM
LDI R23,0
LSL dd16uL ;8*CPC
ROL dd16uH
LSL dd16uL
ROL dd16uH
LSL dd16uL
ROL dd16uH
LSL R22 ;8*CRM
ROL R23
LSL R22
ROL R23
LSL R22
ROL R23
SUB dd16uL,R22
SBC dd16uH,R23
LDD dv16uL,Z+7 ;CPC
LDI dv16uH,0
MOV R0,dv16uL
OR r0,dv16uH
BRNE DIV1 ;0-VAL NEM OSZTUNK
LDI R16,0
LDI R17,0
RJMP LKI1
DIV1: RCALL div16u ;OSZTAS eredmeny az R16,R17-ben
LKI1: CLC
SBCI dres16uL,2
SBCI dres16uH,0 ;eredmeny-2
LDD R22,Z+0 ;Temperature
LDD R23,Z+1
CBR R22,1 ;Truncate 0.5C
LSL R22 ;8*T
ROL R23
LSL R22
ROL R23
LSL R22
ROL R23
ADD R22,dres16uL ;R22,R23 a korigalt homerseklet
ADC R23,dres16uH
ret
;***************************************************************************
;*
;* EERead_seq
;*
;* This subroutine increments the address stored in EEAR and reads the
;* EEPROM into the register variable "EEdrd_s".
;*
;* Number of words :8515 ; 7 + return
;* Number of cycles :8515 ; 11 + return (if EEPROM is ready)
;* Low Registers used :R0
;* High Registers used: :R24
;*
;***************************************************************************
EERead_seq:
sbic EECR,EEWE ;if EEWE not clear
rjmp EERead_seq ; wait more
;The above sequence for EEWE = 0
;can be skipped if no write is initiated.
in R24,EEAR ;get address low 8515
inc R24 ;increment address 8515
out EEAR,R24 ;output address 8515
sbi EECR,EERE ;set EEPROM Read strobe
;This instruction takes 4 clock cycles since
;it halts the CPU for two clock cycles
in R0,EEDR ;get data
ret
;***************************************************************************
;*
;* FUNCTION
;* ena_LCD
;*
;* DESCRIPTION
;* Init data & clock lines, then assert /CS for LCD.
;*
;* CODE SIZE:
;* 4 words
;*
;***************************************************************************
ena_LCD:
sck_lo ;(should already be there...)
mosi_lo
Select_LCD
ret
;* LCDlo, LCDHi - kikuldese
RW_LCD:
mov spi_lo,LCDHi ;Mov Command byte
rcall ena_LCD ;activate /CS
rcall rw_spi ;send Command byte
mov spi_lo,LCDLo ;Mov Command byte
rcall rw_spi ;send Command byte
ret
;**** A P P L I C A T I O N N O T E A V R 2 0 0 ************************
;*
;* Title: Multiply and Divide Routines
;* Version: 1.1
;* Last updated: 97.07.04
;* Target: AT90Sxxxx (All AVR Devices)
;*
;* Support E-mail: avr@atmel.com
;*
;* DESCRIPTION
;* This Application Note lists subroutines for the following
;* Divide applications. Routines are straight-line implementations
;* optimized for speed:
;*
;* 16 / 16 = 16 + 16 bit unsigned
;*
;***************************************************************************
;***************************************************************************
;*
;* "div16u" - 16/16 Bit Unsigned Division
;*
;* This subroutine divides the two 16-bit numbers
;* "dd16uH:dd16uL" (dividend) and "dv16uH:dv16uL" (divisor).
;* The result is placed in "dres16uH:dres16uL" and the remainder in
;* "drem16uH:drem16uL".
;*
;* Number of words :196 + return
;* Number of cycles :148/173/196 (Min/Avg/Max)
;* Low registers used :2 (drem16uL,drem16uH)
;* High registers used :4 (dres16uL/dd16uL,dres16uH/dd16uH,dv16uL,dv16uH)
;*
;***************************************************************************
;***** Code
div16u: clr drem16uL ;clear remainder Low byte
sub drem16uH,drem16uH;clear remainder High byte and carry
rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_1 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_2 ;else
d16u_1: sec ; set carry to be shifted into result
d16u_2: rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_3 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_4 ;else
d16u_3: sec ; set carry to be shifted into result
d16u_4: rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_5 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_6 ;else
d16u_5: sec ; set carry to be shifted into result
d16u_6: rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_7 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_8 ;else
d16u_7: sec ; set carry to be shifted into result
d16u_8: rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_9 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_10 ;else
d16u_9: sec ; set carry to be shifted into result
d16u_10:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_11 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_12 ;else
d16u_11:sec ; set carry to be shifted into result
d16u_12:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_13 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_14 ;else
d16u_13:sec ; set carry to be shifted into result
d16u_14:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_15 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_16 ;else
d16u_15:sec ; set carry to be shifted into result
d16u_16:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_17 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_18 ;else
d16u_17: sec ; set carry to be shifted into result
d16u_18:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_19 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_20 ;else
d16u_19:sec ; set carry to be shifted into result
d16u_20:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_21 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_22 ;else
d16u_21:sec ; set carry to be shifted into result
d16u_22:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_23 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_24 ;else
d16u_23:sec ; set carry to be shifted into result
d16u_24:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_25 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_26 ;else
d16u_25:sec ; set carry to be shifted into result
d16u_26:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_27 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_28 ;else
d16u_27:sec ; set carry to be shifted into result
d16u_28:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_29 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_30 ;else
d16u_29:sec ; set carry to be shifted into result
d16u_30:rol dd16uL ;shift left dividend
rol dd16uH
rol drem16uL ;shift dividend into remainder
rol drem16uH
sub drem16uL,dv16uL ;remainder = remainder - divisor
sbc drem16uH,dv16uH ;
brcc d16u_31 ;if result negative
add drem16uL,dv16uL ; restore remainder
adc drem16uH,dv16uH
clc ; clear carry to be shifted into result
rjmp d16u_32 ;else
d16u_31:sec ; set carry to be shifted into result
d16u_32:rol dd16uL ;shift left dividend
rol dd16uH
ret
|
|