;*************************************************************************** ; ; File Name :'DS1602.asm" ; Title : ; Date : ; Version : ; Support telephone :765 287 1987 David B. VanHorn ; Support fax :765 287 1989 ; Support Email :dvanhorn@cedar.net ; Target MCU :AT90S8515 ; ; DESCRIPTION ; ;Handlers for Dallas DS1602 RTC chip on port A4,5,6 ; ; DEFINITIONS ; ; ;***************************************************************************; ; M O D I F I C A T I O N H I S T O R Y ; ; ; rev. date who why ; ---- -------- --- ------------------------------------------ ; 0.01 97.07.21 dvh Creation ; 0.02 97.09.22 dvh Created skeleton ; 0.03 97.10.13 dvh coding for DS1602 ; 0.04 97.10.16 dvh Coded all commands and conversations ; 0.05 97.10.21 dvh Tested most functions OK ; 0.06 97.10.22 dvh Debugged data output from RTC ; ;Routine Input Output ; ;Get_Rtime None TIME_Buf ;WORKING ;Get_Etime None Time_Buf ;WORKING ;Put_Rtime Time_Buf None ; ;Put_Etime Time_Buf None ; ;Clear_Rtime None Timer cleared ;WORKING ;Clear_Etime None Timer cleared ;WORKING ;Set_Time_Trim Temp None ;00ABC000 ;******************************************************************** ;I/O is coded to port A, bits 4,5,6 change this in the last routines, ;below WRITE_RTC_BUF ;Requires an 8 byte buffer in memory, located at RTC_BUF ;******************************************************************** ;This clock chip counts seconds from powerup, or you can load the seconds ;counter to any value and continue counting upward. This makes a unix-like ;clock very easy to implement. There are two counters, one can be set to ;some start time, and the other can be reset at powerup, or used for other ;purposes. ;******************************************************************** ;Get the time buffer out of the RTC. ; GET_RTIME: ;Takes Binary from clock, loads to RTC_BUF push TEMP rcall Open_Clock ; ldi TEMP,$81 ;RTC command, Read Continuous counter rcall PUT_RTC_BYTE ; rcall Read_RTC_Buf ;reads into the FIRST four bytes of RTC_BUF rcall Close_Clock ; pop TEMP ret ;******************************** ; ;Put the time buffer into the RTC ; PUT_RTIME: ;Takes binary data from RTC_BUF push TEMP rcall Open_Clock ; ldi TEMP,$80 ;RTC command rcall PUT_RTC_BYTE ; rcall Write_RTC_Buf ; rcall Close_Clock ; pop TEMP ret ; ;Get the time buffer out of the RTC. ; GET_ETIME: ;Takes Binary from clock, loads to RTC_BUF push TEMP rcall Open_Clock ; ldi TEMP,$41 ;RTC command rcall PUT_RTC_BYTE ; rcall Read_RTC_Buf2 ;Reads into the LAST 4 bytes of RTC_BUF rcall Close_Clock ; pop TEMP ret ;******************************** ; ;Put the time buffer into the RTC ; PUT_ETIME: ;Takes binary data from RTC_BUF push TEMP rcall Open_Clock ldi TEMP,$40 ;RTC command, Write VCC Active counter rcall PUT_RTC_BYTE ; rcall Write_RTC_Buf ; rcall Close_Clock ; pop TEMP ret ; ; ; Clear_ETIME: ;Nukes elapsed time counter (Powerup) push TEMP rcall Open_Clock ; ldi TEMP,$02 ;RTC command, Clear VCC Active counter rcall PUT_RTC_BYTE ; rcall Close_Clock pop TEMP ret ; ; ; Clear_RTIME: ;Nukes Realtime time counter (Powerup) push TEMP rcall Open_Clock ; ldi TEMP,$04 ;RTC command, Clear Continuous counter rcall PUT_RTC_BYTE ; rcall Close_Clock ; pop TEMP ret ; ; ; Set_TIME_Trim: ;Input bits in position in TEMP push TEMP rcall Open_Clock ; pop TEMP ; ori TEMP,$C0 ; andi TEMP,$F8 ; rcall PUT_RTC_BYTE ; rcall Close_Clock ; pop TEMP ; ret ;********************************** ; ;A pair of nearly identical buffer read ;and write routines ; Read_RTC_BUF: rcall GET_RTC_Byte sts (RTC_BUF+0),TEMP rcall GET_RTC_Byte sts (RTC_BUF+1),TEMP rcall GET_RTC_Byte sts (RTC_BUF+2),TEMP rcall GET_RTC_Byte sts (RTC_BUF+3),TEMP ret Read_RTC_BUF2: rcall GET_RTC_Byte sts (RTC_BUF+4),TEMP rcall GET_RTC_Byte sts (RTC_BUF+5),TEMP rcall GET_RTC_Byte sts (RTC_BUF+6),TEMP rcall GET_RTC_Byte sts (RTC_BUF+7),TEMP ret Write_RTC_BUF: lds TEMP,(RTC_BUF+0) rcall Put_RTC_Byte lds TEMP,(RTC_BUF+1) rcall Put_RTC_Byte lds TEMP,(RTC_BUF+2) rcall Put_RTC_Byte lds TEMP,(RTC_BUF+3) rcall Put_RTC_Byte ret ;******************************** ; ;Move a nybble out of the RTC. ;Output in TEMP ; GET_RTC_Byte: push LOOP ; rcall GET_RTC_BIT ; rcall GET_RTC_BIT ; rcall GET_RTC_BIT ; rcall GET_RTC_BIT ; rcall GET_RTC_BIT ; rcall GET_RTC_BIT ; rcall GET_RTC_BIT ; rcall GET_RTC_BIT ; cbi PORTA,6 ; sbi PORTA,5 ;Make sure data always goes high on exit (OC!) pop LOOP ; ret ; ; ; ;Move a byte out to the RTC. ;Input in Temp ; Put_RTC_Byte: push LOOP ; rcall PUT_RTC_BIT ; rcall PUT_RTC_BIT ; rcall PUT_RTC_BIT ; rcall PUT_RTC_BIT ; rcall PUT_RTC_BIT ; rcall PUT_RTC_BIT ; rcall PUT_RTC_BIT ; rcall PUT_RTC_BIT ; cbi PORTA,6 ; sbi PORTA,5 ;Make sure data always goes high on exit (OC!) ;Exits with data high, and clock low pop LOOP ; ret ; ; ;********************************** ; ;Lowest level, what it takes to clock a bit ;I/O in TEMP ; ;PA6 RTC Clock ;PA5 RTC Data ;PA4 RTC /RESET ; ; ; GET_RTC_BIT: sbi PORTA,5 ;Set for read (Open collector) sbi PORTA,6 ; in LOOP,PINA ;Read data into LOOP from PINA (bit 5) rol Loop ;5-6 rol Loop ;6-7 rol Loop ;7-C ror TEMP ;C-7 Puts into msb, first bit ends up as lsb cbi PORTA,6 ;Set clock low(next data is now ready) ret ; ; ; Put_RTC_BIT: ror TEMP ;LSB First brcs P_RTC_One ; P_RTC_Zero: cbi PORTA,5 ;Make data bit zero rjmp P_RTC_Clock ; P_RTC_One: sbi PORTA,5 ;Make data bit one P_RTC_Clock: sbi PORTA,6 ;Clock 1 cbi PORTA,6 ;Clock 0 ret ; ; ; Open_Clock: cbi PORTA,6 ;Take clock low sbi PORTA,4 ;Take /reset high ret ; ; ; Close_Clock: sbi PORTA,6 ;Take clock high(jic), see appnote cbi PORTA,4 ;Take /reset low, NEVER while clock is low ret