Electronic Sculpture Archive
|
|
my_ds1302.cCode ListingBelow is my driver for using the Dallas Semiconductor DS1302 serial real time clock with Custom Computer Services' PIC C compiler. There are functions to access the time RAM and the user RAM. To use this code you will also need my standard header file of convenience labels, my_prefs.h. As with all my code listings, you may need to copy them to an editor which supports 4-char tabs to see and print them correctly. /* 09-17-99 Bruce Cannon Modified CCS DS1302 RTC driver. Sort of half way between what they did and what I would do if I had more time. Could use some work. In general, should call initialize_DS1302() to set up charger and unwrite-protect before using. And to be most secure, should write protect after setting. */ /**************************************************************************************** Pin labels and data constants. ****************************************************************************************/ #define DS_SCLK RA1 #define DS_IO RA2 #define _DS_RST RA3 //To write to any register use as-is. To read, make LSB hi (add one): #define SC_ADDR 0x80 #define MN_ADDR 0x82 #define HR_ADDR 0x84 #define DT_ADDR 0x86 #define MT_ADDR 0x88 #define DY_ADDR 0x8A #define YR_ADDR 0x8C #define WRITE_PROTECT 0x8E //To write to the write-protect bit, #define PROTECT 128 //which is bit seven. #define UNPROTECT 0 // " #define TRICKLE_CHARGER 0x90 //To write to the charger setup register. #define CLOCK_BURST 0xBE //To write to all time registers at once. #define NV_ADDR 0xC0 #define CLOCK_HALT_FLAG 0x80 //If secs reg >= this value, clock stopped. /****************************************************************************************
Switches.
****************************************************************************************/
#define CHARGE_SETTINGS 0xA6 //Charger enabled, one diode, 4k resistor.
//Rem out to prevent charging (power up default)./**************************************************************************************** Prototypes. ****************************************************************************************/ void initialize_DS1302(); //Call after power up. void write_DS1302(byte cmd, byte data); //A single data element. byte read_DS1302(byte cmd); // " void write_DS1302_byte(byte cmd); // " void write_DS_NVR(address,data); //Write to DS1302's user NVR. byte read_DS_NVR(address); //Read from DS1302's user NVR. /****************************************************************************************
Functions.
****************************************************************************************/
void initialize_DS1302()
{
output_low(_DS_RST);
output_low(DS_SCLK);
write_DS1302(WRITE_PROTECT,UNPROTECT);
//write_DS1302(TRICKLE_CHARGER,CHARGE_SETTINGS);
if((read_DS1302(SC_ADDR) >= CLOCK_HALT_FLAG)) //If clock stopped,
{
write_DS1302(SC_ADDR,0); //start it.
}
}
void write_DS1302_byte(byte cmd)
{
byte i; for(i=0;i<=7;++i)
{
output_bit(DS_IO, shift_right(&cmd,1,0) );
output_high(DS_SCLK);
output_low(DS_SCLK);
}
}
void write_DS1302(byte cmd, byte data)
{
output_high(_DS_RST);
write_DS1302_byte(cmd);
write_DS1302_byte(data);
output_low(_DS_RST);
}
byte read_DS1302(byte cmd)
{
byte i,data;output_high(_DS_RST); write_DS1302_byte(cmd | 0x01); //Set LSB hi for read request. for(i=0;i<=7;++i)
{
shift_right(&data,1,input(DS_IO));
output_high(DS_SCLK);
delay_us(2);
output_low(DS_SCLK);
delay_us(2);
}
output_low(_DS_RST);
return(data);
}
void write_DS_NVR(byte address, byte data)
{
address <<= 1; //Shift up one bit (LSB is write flag).
address |= NV_ADDR; //Set NVRAM access bits.
write_DS1302(address, data); //Save the value.
}
byte read_DS_NVR(byte address)
{
address <<= 1; //Shift up one bit (LSB is write flag).
address |= NV_ADDR; //Set NVRAM access bits.
return(read_DS1302(address)); //Get the value and pass it back.
}
|
|
|
Site contents licensed under a |
|