DS1302 RTC Library

Even though the DS1302 RTC (Real Time Clock) device has been available for many years now, and could be classed as legacy, it still does its job well. There are also a plethora of inexpensive boards available that contain one, so as an introduction to RTCs, it is worth trying one out with the code below.

The DS1302 device uses an SPI serial interface that shares the data input and output line, so it only requires three pins to connect to it from the microcontroller. It also contains a mechanism for trickle charging a backup battery or super capacitor that can be connected to it so that it keeps its time and date if power is removed.

The Positron8 library and demo firmware can be downloaded from here:
Positron8 - DS1302 RTC.zip. The file also has a Proteus simulation project within it. One of the demo programs is listed below:

'
' /\\\\\\\\\
' /\\\///////\\\
' \/\\\ \/\\\ /\\\ /\\\
' \/\\\\\\\\\\\/ /\\\\\ /\\\\\\\\\\ /\\\\\\\\ /\\\\\\\\\\\ /\\\\\\\\\\\ /\\\\\\\\\
' \/\\\//////\\\ /\\\///\\\ \/\\\////// /\\\/////\\\ \////\\\//// \////\\\//// \////////\\\
' \/\\\ \//\\\ /\\\ \//\\\ \/\\\\\\\\\\ /\\\\\\\\\\\ \/\\\ \/\\\ /\\\\\\\\\\
' \/\\\ \//\\\ \//\\\ /\\\ \////////\\\ \//\\/////// \/\\\ /\\ \/\\\ /\\ /\\\/////\\\
' \/\\\ \//\\\ \///\\\\\/ /\\\\\\\\\\ \//\\\\\\\\\\ \//\\\\\ \//\\\\\ \//\\\\\\\\/\\
' \/// \/// \///// \////////// \////////// \///// \///// \////////\//
' Let's find out together what makes a PIC Tick!
'
' Read from a DS1302 RTC
' And display the time and date on an LCD, and transmit them to a serial terminal
'
' Written for the Positron8 BASIC compiler by Les Johnson.
'

Device = 18F25K20 ' Tell the compiler what device to compile for
Declare Xtal = 16 ' Tell the compiler what frequency the device is operating at (in MHz)
'
' Setup USART1
'

Declare HSerial1_Baud = 9600 ' Set the Baud rate to 9600
Declare HRsout1_Pin = PORTC.6 ' Set the TX pin
'
' Setup the Alphanumeric LCD
'

Declare LCD_DTPin = PORTA.0 ' The LCD's Dt4 to Dt7 lines connect to PORTA.0 to PORTA.3
Declare LCD_ENPin = PORTA.4 ' Connects to the LCD's EN line
Declare LCD_RSPin = PORTA.5 ' Connects to the LCD's RS line
Declare LCD_Interface = 4 ' The LCD is going to use a 4-line interface
Declare LCD_Lines = 2 ' The LCD has 2 lines
Declare LCD_Type = Alphanumeric ' The LCD is an Hitachi alphanumeric type
'
' Set the pins to use for the SPI interface to the DS1302 RTC chip
'

Symbol DS1302_CE_Pin = PORTC.0 ' Connects to the CE pin of the DS1302
Symbol DS1302_SCLK_Pin = PORTC.1 ' Connects to the SCLK pin of the DS1302
Symbol DS1302_DAT_Pin = PORTC.2 ' Connects to the DAT pin of the DS1302
Include "DS1302.inc" ' Load the DS1302 library into the program
'
' Create a variable for the demo
'

Dim bPrevSeconds As Byte = $FF ' Holds the previous seconds value

'----------------------------------------------------------------------------
' The main program starts here
' Read the time and date from the DS1302 RTC device
' And display them on the LCD and a serial terminal, when the seconds value increments
'

Main:
DS1302_Init() ' Initialise the DS1302 RTC device
Cls ' Clear the LCD's display
Do ' Create a loop
DS1302_GetTime() ' Read the time from the DS1302 RTC device
If RTC_bSecond <> bPrevSeconds Then ' Has the seconds value changed?
DS1302_GetDate() ' Yes. So read the date from the DS1302 RTC device
DS1302_GetDay() ' Read the day from the DS1302 RTC device

DS1302_GetDatePost(RTC_bDate) ' Find the post text for the Date value
DS1302_GetDayName(RTC_bDay) ' Convert the Day of the Week value into a day name
DS1302_GetMonthName(RTC_bMonth) ' Convert the Month value into a month name
'
' Transmit the ASCII date and time to a serial terminal
'

HRSOutLn "Time = ", Dec2 RTC_bHour, ":",_ ' \
Dec2 RTC_bMinute, ":",_ ' | Serially transmit the time as ASCII
Dec2 RTC_bSecond ' /

HRSOutLn "Date = ", RTC_DayName, " ",_ ' \
Dec RTC_bDate, RTC_DatePost, " ",_ ' | Serially transmit the date as ASCII
"of ", RTC_MonthName, " ", _
' |
"20",
Dec2 RTC_bYear ' /
'
' Display the date and time on the LCD
'

Print At 1, 1, Dec2 RTC_bHour, ":",_ ' \
Dec2 RTC_bMinute, ":",_ ' | Display the time on line 1 of the LCD
Dec2 RTC_bSecond ' /
'
' Make the month text upper case so it displays better on the LCD
'
RTC_MonthName =
ToUpper(RTC_MonthName)
Print At 2, 1, Dec RTC_bDate, " ",_ ' \
RTC_MonthName, " ", _
' | Display the date on line 2 of the LCD
"20",
Dec2 RTC_bYear, " " ' /
EndIf
bPrevSeconds = RTC_bSecond
' Transfer the current seconds value into the previous seconds variable
Loop ' Do it forever

Below is a screenshot of the demo program above, working within the Proteus simulator:

Below is a video of the Proteus simulator running the demo program and displaying the date and time on an LCD, and on a serial teminal.