DS1307 MikroC Library

General discussion on mikroC.
Author
Message
halvarezo
Posts: 5
Joined: 28 Aug 2008 05:42

DS1307 MikroC Library

#1 Post by halvarezo » 29 Aug 2008 00:24

Is there any DS1307 MikroC library working? It could help me developing my new project which is based on a RTC. Thanks.

dronology
Posts: 106
Joined: 29 Dec 2007 23:48
Location: istanbul
Contact:

#2 Post by dronology » 29 Aug 2008 08:48

Sometime ago I red one of the embedded code-developers (//I dont remember his/her name at the moment, sorry for that) code. It was written about widely used "PCF8530". By a little inspiration and reading datasheet I've my own DS1370 code. Here it is;


Code: Select all


/********************************************************
  *	   Real Time Clock DS1307 Library for 18F4620     *
  *                  (for PIC IC.)                      *
  *                 by Deniz ELMASLI                    *
  * Version 2.0                                         *
  * Creation Date: 28.12.2008   -   10:12 Friday        *
  * Revision Date: 08.06.2008   -   03:42 Saturday      *
  * Ide(s) : Code::Blocks v1.0 (C++ developement)       *
  *          MikroC V7.0                                *
  * Target Platform: PIC                                *
  * MCU : 18F4620                                       *
  * Contact: elmasli@gmail.com                          *
  * Web    : www.dronology.com                          *
  *                                                     *
  *	This code in intended to work with PIC IC. This   *
  * source code contains functions to drive DS1307 real *
  * time clock  . I2C Functions used in ver2.0          *
  *******************************************************

*/


    void start1307s();
    void ds1307_init();
    void ds1307_set_date_time(char day,char mth,char year,char dow,char hr,char min, int sec);
    void ds1307_get_time_date(char *day, char *mth, char *year, char *dow, char *hr, char *min, char *sec);


void ds1307_init(){
    int seconds=0;

    I2C_Start();
    I2C_Wr(0xD0);      // WR to RTC
    I2C_Wr(0x00);      // REG 0
    I2C_Start();
    I2C_Wr(0xD1);      // RD from RTC
    seconds = Bcd2Dec(I2C_Rd(0)); // Read current "seconds" in DS1307
    I2C_Stop();
    seconds = (seconds & 0x7F);

    Delay_ms(50);

    I2C_Start();
    I2C_Wr(0xD0);      // WR to RTC
    I2C_Wr(0x00);      // REG 0
    I2C_Wr(Dec2Bcd(seconds));     // Start oscillator with current "seconds value
    I2C_Start();
    I2C_Wr(0xD0);      // WR to RTC
    I2C_Wr(0x07);      // Control Register
    I2C_Wr(0x80);      // Disable squarewave output pin
    I2C_Stop();
}//~




void ds1307_set_date_time(char day,char mth,char year,char dow,char hr,char min, int sec){
    sec =(sec & 0x7F);
    hr =(hr & 0x3F);

    I2C_Start();
    I2C_Wr(0xD0);               // I2C write address
    I2C_Wr(0x00);               // Start at REG 0 - Seconds
    I2C_Wr(Dec2Bcd(sec));       // REG 0
    I2C_Wr(Dec2Bcd(min));       // REG 1
    I2C_Wr(Dec2Bcd(hr));        // REG 2
    I2C_Wr(Dec2Bcd(dow));       // REG 3
    I2C_Wr(Dec2Bcd(day));       // REG 4
    I2C_Wr(Dec2Bcd(mth));       // REG 5
    I2C_Wr(Dec2Bcd(year));      // REG 6
    I2C_Wr(0x80);               // REG 7 - Disable squarewave output pin
    I2C_Stop();
}//~





void ds1307_get_time_date(char *day, char *mth, char *year, char *dow, char *hr, char *min, char *sec){
    I2C_Start();
    I2C_Wr(0xD0);
    I2C_Wr(0x00);                     // Start at REG 3 - Day of week
    I2C_Start();
    I2C_Wr(0xD1);
    *sec=Bcd2Dec(I2C_Rd(1) & 0x7F);
    *min=Bcd2Dec(I2C_Rd(1) & 0x7F);
    *hr=Bcd2Dec(I2C_Rd(1) & 0x3F);
    *dow=Bcd2Dec(I2C_Rd(1) & 0x7F);   // REG 3
    *day=Bcd2Dec(I2C_Rd(1) & 0x3F);   // REG 4
    *mth=Bcd2Dec(I2C_Rd(1) & 0x1F);   // REG 5
    *year=Bcd2Dec(I2C_Rd(0));         // REG 6
    I2C_Stop();
}//~
Last edited by dronology on 07 Oct 2008 14:58, edited 1 time in total.
R. Giskard Reventlov & R. Daneel Olivaw

http://www.circuitechs.com
http://www.dronology.com

halvarezo
Posts: 5
Joined: 28 Aug 2008 05:42

Thanks

#3 Post by halvarezo » 29 Aug 2008 15:42

Thanks, it could be a great help to me but it is a working code? I mean, did you porbe it on HW. I hope you can help me. Thanks a lot.

dronology
Posts: 106
Joined: 29 Dec 2007 23:48
Location: istanbul
Contact:

#4 Post by dronology » 29 Aug 2008 16:47

If it wasn't working how could I send? I'm not interested in wasting time here by sending rubbish codes to people? Check my previous code developements from my profile and previous messages. And RTC code: Ofcourse it is working. Some addons and modifications can be done. LCD out functions etc. Try to improve this code for your purpose.
R. Giskard Reventlov & R. Daneel Olivaw

http://www.circuitechs.com
http://www.dronology.com

halvarezo
Posts: 5
Joined: 28 Aug 2008 05:42

#5 Post by halvarezo » 29 Aug 2008 16:51

Ok, I'll improve the code for my purpose and I'll Post it. Thanks a lot. I've seen you have done many developements. I am starting with Mikro C because I used to program with MPLAB C18. Thanks for your time.

dronology
Posts: 106
Joined: 29 Dec 2007 23:48
Location: istanbul
Contact:

#6 Post by dronology » 29 Aug 2008 17:00

You are welcome :)
R. Giskard Reventlov & R. Daneel Olivaw

http://www.circuitechs.com
http://www.dronology.com

petrd
Posts: 82
Joined: 14 Feb 2008 11:04
Location: Russia, Voronezh

Code for DS1307

#7 Post by petrd » 25 Sep 2008 07:10

I try use any code, but i have problem. I write may code, which based on exemples for EasyPic5. Work this code tested on EasyPic5 and PIC16F887.
1. Code for init DS1307:

Code: Select all

 * Description:
     This project is simple demonstration how to set date and time on DS1307
     RTC (real-time clock). The code use MSSP module at PORTC.
     The example sets the following:
       TIME: 09:00:00
       DATE: 25/09/2008
     Please refer to DS1307 datasheet for more information on format date
     settings.
 * Test configuration:
     MCU:             PIC16F887
     Dev.Board:       EasyPIC5
     Oscillator:      HS, 8.000MHz
     Ext. Modules:    IC RTC (DS1307)
     SW:              mikroC v8.2.0.0
 * NOTES:
      - For proper I2C communication, pins on PORTC must be in the pull-up mode,
        RC3 - pin 6 DS1307  - SCL,
        RC4 - pin 5 DS1307 - SDA,
        and the LEDs on board switched OFF!
*/

void main() {
   I2C_Init(100000);     // initialize full master mode
   I2C_Start();          // issue start signal
   I2C_Wr(0xD0);         // address DS1307
   I2C_Wr(0);            // start from word at address (REG0)
   I2C_Wr(0x80);         // write $80 to REG0. (pause counter + 0 sec)
   I2C_Wr(0);            // write 0 to minutes word to (REG1)
   I2C_Wr(0x09);         // write 12 to hours word (24-hours mode)(REG2)
   I2C_Wr(0x05);         // write 5 - Thursday (REG3)
   I2C_Wr(0x25);         // write 25 to date word (REG4)
   I2C_Wr(0x09);         // write 9 (September) to month word (REG5)
   I2C_Wr(0x08);         // write 08 to year word (REG6)
   I2C_Stop();           // issue stop signal

   I2C_Start();          // issue start signal
   I2C_Wr(0xD0);         // address DS1307
   I2C_Wr(0);            // start from word at address 0
   I2C_Wr(0);            // write 0 to REG0 (enable counting + 0 sec)
   I2C_Stop();           // issue stop signal
}//~!
2. Code for read DS1307:

Code: Select all

 * Description:
     This project is simple demonstration how to read date and time from DS1307
     RTC (real-time clock). The code MCU use MSSP module at PORTC.
     Date and time are printed at LCD.
 * Test configuration:
     MCU:             PIC16F887
     Dev.Board:       EasyPIC5
     Oscillator:      HS, 8.000MHz
     Ext. Modules:    IC RTC (DS1307), LCD 2x16 chars
     SW:              mikroC v8.2.0.0
 * NOTES:
     - For proper I2C communication, pins on PORTC must be in the pull-up mode,
       RC3 - pin 6 DS1307  - SCL,
       RC4 - pin 5 DS1307 - SDA,
       and the LEDs on board switched OFF!
*/

unsigned char sec, min1, hr, week_day, day, mn, year;
char *txt, tnum[4];

void Zero_Fill(char *value) {    // fill text repesentation
  if (value[1] == 0) {           //      with leading zero
    value[1] = value[0];
    value[0] = 48;
    value[2] = 0;
  }
}//~

//--------------------- Reads time and date information from RTC (DS1307)
void Read_Time(char *sec, char *min, char *hr, char *week_day, char *day, char *mn, char *year) {
  I2C_Start();
  I2C_Wr(0xD0);
  I2C_Wr(0);
  I2C_Repeated_Start();
  I2C_Wr(0xD1);
  *sec =I2C_Rd(1);
  *min =I2C_Rd(1);
  *hr =I2C_Rd(1);
  *week_day =I2C_Rd(1);
  *day =I2C_Rd(1);
  *mn =I2C_Rd(1);
  *year =I2C_Rd(0);
  I2C_Stop();
}//~

//-------------------- Formats date and time
void Transform_Time(char  *sec, char *min, char *hr, char *week_day, char *day, char *mn, char *year) {
  *sec  =  ((*sec & 0x70) >> 4)*10 + (*sec & 0x0F);
  *min  =  ((*min & 0xF0) >> 4)*10 + (*min & 0x0F);
  *hr   =  ((*hr & 0x30) >> 4)*10 + (*hr & 0x0F);
  *week_day =(*week_day & 0x07);
  *day  =  ((*day & 0xF0) >> 4)*10 + (*day & 0x0F);
  *mn   =  ((*mn & 0x10) >> 4)*10 + (*mn & 0x0F);
  *year =  ((*year & 0xF0)>>4)*10+(*year & 0x0F);
}//~

//-------------------- Output values to LCD
void Display_Time(char sec, char min, char hr, char week_day, char day, char mn, char year) {
   switch(week_day){
     case 1: txt="Sun"; break;
     case 2: txt="Mon"; break;
     case 3: txt="Tue"; break;
     case 4: txt="Wed"; break;
     case 5: txt="Thu"; break;
     case 6: txt="Fri"; break;
     case 7: txt="Sat"; break;
   }
   LCD_Out(1,1,txt);

   ByteToStr(day,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(1,6,txt);
   
   ByteToStr(mn,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(1,9,txt);
   
   ByteToStr(year,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(1,14,txt);
   
   ByteToStr(hr,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(2,6,txt);
   
   ByteToStr(min,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(2,9,txt);
   
   ByteToStr(sec,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(2,12,txt);
}//~

//------------------ Performs project-wide init
void Init_Main() {
  ANSEL=0;
  ANSELH=0;
  Lcd_Config(&PORTB, 4, 5, 6, 3, 2, 1, 0); // Lcd_Init_EP5, see Autocomplete
  I2C_Init(100000);                        // initialize I2C
  LCD_Chr(1,8,'.');
  LCD_Chr(1,11,'.');
  txt = "Time:";
  LCD_Out(2,1,txt);
  LCD_Chr(2,8,':');
  LCD_Chr(2,11,':');
  txt = "20";
  LCD_Out(1,12,txt);
  LCD_Cmd(LCD_CURSOR_OFF);
}//~

//----------------- Main procedure
void main() {
  Init_Main();                                               // perform initialization
  while (1) {
    Read_Time(&sec,&min1,&hr,&week_day,&day,&mn,&year);      // read time from RTC(DS1307)
    Transform_Time(&sec,&min1,&hr,&week_day,&day,&mn,&year); // format date and time
    Display_Time(sec, min1, hr, week_day, day, mn, year);    // prepare and display on LCD
    Delay_ms(1000);                                          // wait 1s
  }
}//
Best regards!

masterblastersachin
Posts: 34
Joined: 07 May 2008 10:01
Location: BANGALORE

Re: Code for DS1307

#8 Post by masterblastersachin » 26 Sep 2008 12:52

petrd wrote:I try use any code, but i have problem. I write may code, which based on exemples for EasyPic5. Work this code tested on EasyPic5 and PIC16F887.
1. Code for init DS1307:

Code: Select all

 * Description:
     This project is simple demonstration how to set date and time on DS1307
     RTC (real-time clock). The code use MSSP module at PORTC.
     The example sets the following:
       TIME: 09:00:00
       DATE: 25/09/2008
     Please refer to DS1307 datasheet for more information on format date
     settings.
 * Test configuration:
     MCU:             PIC16F887
     Dev.Board:       EasyPIC5
     Oscillator:      HS, 8.000MHz
     Ext. Modules:    IC RTC (DS1307)
     SW:              mikroC v8.2.0.0
 * NOTES:
      - For proper I2C communication, pins on PORTC must be in the pull-up mode,
        RC3 - pin 6 DS1307  - SCL,
        RC4 - pin 5 DS1307 - SDA,
        and the LEDs on board switched OFF!
*/

void main() {
   I2C_Init(100000);     // initialize full master mode
   I2C_Start();          // issue start signal
   I2C_Wr(0xD0);         // address DS1307
   I2C_Wr(0);            // start from word at address (REG0)
   I2C_Wr(0x80);         // write $80 to REG0. (pause counter + 0 sec)
   I2C_Wr(0);            // write 0 to minutes word to (REG1)
   I2C_Wr(0x09);         // write 12 to hours word (24-hours mode)(REG2)
   I2C_Wr(0x05);         // write 5 - Thursday (REG3)
   I2C_Wr(0x25);         // write 25 to date word (REG4)
   I2C_Wr(0x09);         // write 9 (September) to month word (REG5)
   I2C_Wr(0x08);         // write 08 to year word (REG6)
   I2C_Stop();           // issue stop signal

   I2C_Start();          // issue start signal
   I2C_Wr(0xD0);         // address DS1307
   I2C_Wr(0);            // start from word at address 0
   I2C_Wr(0);            // write 0 to REG0 (enable counting + 0 sec)
   I2C_Stop();           // issue stop signal
}//~!
2. Code for read DS1307:

Code: Select all

 * Description:
     This project is simple demonstration how to read date and time from DS1307
     RTC (real-time clock). The code MCU use MSSP module at PORTC.
     Date and time are printed at LCD.
 * Test configuration:
     MCU:             PIC16F887
     Dev.Board:       EasyPIC5
     Oscillator:      HS, 8.000MHz
     Ext. Modules:    IC RTC (DS1307), LCD 2x16 chars
     SW:              mikroC v8.2.0.0
 * NOTES:
     - For proper I2C communication, pins on PORTC must be in the pull-up mode,
       RC3 - pin 6 DS1307  - SCL,
       RC4 - pin 5 DS1307 - SDA,
       and the LEDs on board switched OFF!
*/

unsigned char sec, min1, hr, week_day, day, mn, year;
char *txt, tnum[4];

void Zero_Fill(char *value) {    // fill text repesentation
  if (value[1] == 0) {           //      with leading zero
    value[1] = value[0];
    value[0] = 48;
    value[2] = 0;
  }
}//~

//--------------------- Reads time and date information from RTC (DS1307)
void Read_Time(char *sec, char *min, char *hr, char *week_day, char *day, char *mn, char *year) {
  I2C_Start();
  I2C_Wr(0xD0);
  I2C_Wr(0);
  I2C_Repeated_Start();
  I2C_Wr(0xD1);
  *sec =I2C_Rd(1);
  *min =I2C_Rd(1);
  *hr =I2C_Rd(1);
  *week_day =I2C_Rd(1);
  *day =I2C_Rd(1);
  *mn =I2C_Rd(1);
  *year =I2C_Rd(0);
  I2C_Stop();
}//~

//-------------------- Formats date and time
void Transform_Time(char  *sec, char *min, char *hr, char *week_day, char *day, char *mn, char *year) {
  *sec  =  ((*sec & 0x70) >> 4)*10 + (*sec & 0x0F);
  *min  =  ((*min & 0xF0) >> 4)*10 + (*min & 0x0F);
  *hr   =  ((*hr & 0x30) >> 4)*10 + (*hr & 0x0F);
  *week_day =(*week_day & 0x07);
  *day  =  ((*day & 0xF0) >> 4)*10 + (*day & 0x0F);
  *mn   =  ((*mn & 0x10) >> 4)*10 + (*mn & 0x0F);
  *year =  ((*year & 0xF0)>>4)*10+(*year & 0x0F);
}//~

//-------------------- Output values to LCD
void Display_Time(char sec, char min, char hr, char week_day, char day, char mn, char year) {
   switch(week_day){
     case 1: txt="Sun"; break;
     case 2: txt="Mon"; break;
     case 3: txt="Tue"; break;
     case 4: txt="Wed"; break;
     case 5: txt="Thu"; break;
     case 6: txt="Fri"; break;
     case 7: txt="Sat"; break;
   }
   LCD_Out(1,1,txt);

   ByteToStr(day,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(1,6,txt);
   
   ByteToStr(mn,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(1,9,txt);
   
   ByteToStr(year,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(1,14,txt);
   
   ByteToStr(hr,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(2,6,txt);
   
   ByteToStr(min,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(2,9,txt);
   
   ByteToStr(sec,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(2,12,txt);
}//~

//------------------ Performs project-wide init
void Init_Main() {
  ANSEL=0;
  ANSELH=0;
  Lcd_Config(&PORTB, 4, 5, 6, 3, 2, 1, 0); // Lcd_Init_EP5, see Autocomplete
  I2C_Init(100000);                        // initialize I2C
  LCD_Chr(1,8,'.');
  LCD_Chr(1,11,'.');
  txt = "Time:";
  LCD_Out(2,1,txt);
  LCD_Chr(2,8,':');
  LCD_Chr(2,11,':');
  txt = "20";
  LCD_Out(1,12,txt);
  LCD_Cmd(LCD_CURSOR_OFF);
}//~

//----------------- Main procedure
void main() {
  Init_Main();                                               // perform initialization
  while (1) {
    Read_Time(&sec,&min1,&hr,&week_day,&day,&mn,&year);      // read time from RTC(DS1307)
    Transform_Time(&sec,&min1,&hr,&week_day,&day,&mn,&year); // format date and time
    Display_Time(sec, min1, hr, week_day, day, mn, year);    // prepare and display on LCD
    Delay_ms(1000);                                          // wait 1s
  }
}//
Best regards!
hello sir , i burrn this program to 16F877A,
when i m reading the ds1307 ,at first second it displays the correct value but after one second it displays random values on lcd....
is it a DS1307 chips problem or something else is there....
Last edited by masterblastersachin on 07 Oct 2008 12:03, edited 1 time in total.
SACHIN
http://belgaum.myminicity.com/

petrd
Posts: 82
Joined: 14 Feb 2008 11:04
Location: Russia, Voronezh

#9 Post by petrd » 28 Sep 2008 19:13

hello sir , i burrn this program to 16F877A,
when i m reading the ds1307 ,at first second it displays the correct value but after one second it displays random values on lcd....
is it a DS1307 chips problem or something else is there....
Hi!
Now i'm testing code with MCU PIC16F877A - code work.
For PIC16F877A i'm write:

Code: Select all

void Init_Main() {
  //ANSEL=0;
  //ANSELH=0;
  ADCON1=7;
In config word i set: DEBUG_off, LVP_off, WDT_off, HS_OSC.
In may circuit pull-up resistors (10 k) set on external board, near DS1307 and pull-up resistors RC3 and RC4 on EasyPic5 - off. I used LCD WH1602B-YYH-CTK.

masterblastersachin
Posts: 34
Joined: 07 May 2008 10:01
Location: BANGALORE

Re: Code for DS1307

#10 Post by masterblastersachin » 01 Oct 2008 09:07

petrd wrote:I try use any code, but i have problem. I write may code, which based on exemples for EasyPic5. Work this code tested on EasyPic5 and PIC16F887.
1. Code for init DS1307:

Code: Select all

 * Description:
     This project is simple demonstration how to set date and time on DS1307
     RTC (real-time clock). The code use MSSP module at PORTC.
     The example sets the following:
       TIME: 09:00:00
       DATE: 25/09/2008
     Please refer to DS1307 datasheet for more information on format date
     settings.
 * Test configuration:
     MCU:             PIC16F887
     Dev.Board:       EasyPIC5
     Oscillator:      HS, 8.000MHz
     Ext. Modules:    IC RTC (DS1307)
     SW:              mikroC v8.2.0.0
 * NOTES:
      - For proper I2C communication, pins on PORTC must be in the pull-up mode,
        RC3 - pin 6 DS1307  - SCL,
        RC4 - pin 5 DS1307 - SDA,
        and the LEDs on board switched OFF!
*/

void main() {
   I2C_Init(100000);     // initialize full master mode
   I2C_Start();          // issue start signal
   I2C_Wr(0xD0);         // address DS1307
   I2C_Wr(0);            // start from word at address (REG0)
   I2C_Wr(0x80);         // write $80 to REG0. (pause counter + 0 sec)
   I2C_Wr(0);            // write 0 to minutes word to (REG1)
   I2C_Wr(0x09);         // write 12 to hours word (24-hours mode)(REG2)
   I2C_Wr(0x05);         // write 5 - Thursday (REG3)
   I2C_Wr(0x25);         // write 25 to date word (REG4)
   I2C_Wr(0x09);         // write 9 (September) to month word (REG5)
   I2C_Wr(0x08);         // write 08 to year word (REG6)
   I2C_Stop();           // issue stop signal

   I2C_Start();          // issue start signal
   I2C_Wr(0xD0);         // address DS1307
   I2C_Wr(0);            // start from word at address 0
   I2C_Wr(0);            // write 0 to REG0 (enable counting + 0 sec)
   I2C_Stop();           // issue stop signal
}//~!
2. Code for read DS1307:

Code: Select all

 * Description:
     This project is simple demonstration how to read date and time from DS1307
     RTC (real-time clock). The code MCU use MSSP module at PORTC.
     Date and time are printed at LCD.
 * Test configuration:
     MCU:             PIC16F887
     Dev.Board:       EasyPIC5
     Oscillator:      HS, 8.000MHz
     Ext. Modules:    IC RTC (DS1307), LCD 2x16 chars
     SW:              mikroC v8.2.0.0
 * NOTES:
     - For proper I2C communication, pins on PORTC must be in the pull-up mode,
       RC3 - pin 6 DS1307  - SCL,
       RC4 - pin 5 DS1307 - SDA,
       and the LEDs on board switched OFF!
*/

unsigned char sec, min1, hr, week_day, day, mn, year;
char *txt, tnum[4];

void Zero_Fill(char *value) {    // fill text repesentation
  if (value[1] == 0) {           //      with leading zero
    value[1] = value[0];
    value[0] = 48;
    value[2] = 0;
  }
}//~

//--------------------- Reads time and date information from RTC (DS1307)
void Read_Time(char *sec, char *min, char *hr, char *week_day, char *day, char *mn, char *year) {
  I2C_Start();
  I2C_Wr(0xD0);
  I2C_Wr(0);
  I2C_Repeated_Start();
  I2C_Wr(0xD1);
  *sec =I2C_Rd(1);
  *min =I2C_Rd(1);
  *hr =I2C_Rd(1);
  *week_day =I2C_Rd(1);
  *day =I2C_Rd(1);
  *mn =I2C_Rd(1);
  *year =I2C_Rd(0);
  I2C_Stop();
}//~

//-------------------- Formats date and time
void Transform_Time(char  *sec, char *min, char *hr, char *week_day, char *day, char *mn, char *year) {
  *sec  =  ((*sec & 0x70) >> 4)*10 + (*sec & 0x0F);
  *min  =  ((*min & 0xF0) >> 4)*10 + (*min & 0x0F);
  *hr   =  ((*hr & 0x30) >> 4)*10 + (*hr & 0x0F);
  *week_day =(*week_day & 0x07);
  *day  =  ((*day & 0xF0) >> 4)*10 + (*day & 0x0F);
  *mn   =  ((*mn & 0x10) >> 4)*10 + (*mn & 0x0F);
  *year =  ((*year & 0xF0)>>4)*10+(*year & 0x0F);
}//~

//-------------------- Output values to LCD
void Display_Time(char sec, char min, char hr, char week_day, char day, char mn, char year) {
   switch(week_day){
     case 1: txt="Sun"; break;
     case 2: txt="Mon"; break;
     case 3: txt="Tue"; break;
     case 4: txt="Wed"; break;
     case 5: txt="Thu"; break;
     case 6: txt="Fri"; break;
     case 7: txt="Sat"; break;
   }
   LCD_Out(1,1,txt);

   ByteToStr(day,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(1,6,txt);
   
   ByteToStr(mn,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(1,9,txt);
   
   ByteToStr(year,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(1,14,txt);
   
   ByteToStr(hr,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(2,6,txt);
   
   ByteToStr(min,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(2,9,txt);
   
   ByteToStr(sec,tnum);
   txt = rtrim(tnum);
   Zero_Fill(txt);
   LCD_Out(2,12,txt);
}//~

//------------------ Performs project-wide init
void Init_Main() {
  ANSEL=0;
  ANSELH=0;
  Lcd_Config(&PORTB, 4, 5, 6, 3, 2, 1, 0); // Lcd_Init_EP5, see Autocomplete
  I2C_Init(100000);                        // initialize I2C
  LCD_Chr(1,8,'.');
  LCD_Chr(1,11,'.');
  txt = "Time:";
  LCD_Out(2,1,txt);
  LCD_Chr(2,8,':');
  LCD_Chr(2,11,':');
  txt = "20";
  LCD_Out(1,12,txt);
  LCD_Cmd(LCD_CURSOR_OFF);
}//~

//----------------- Main procedure
void main() {
  Init_Main();                                               // perform initialization
  while (1) {
    Read_Time(&sec,&min1,&hr,&week_day,&day,&mn,&year);      // read time from RTC(DS1307)
    Transform_Time(&sec,&min1,&hr,&week_day,&day,&mn,&year); // format date and time
    Display_Time(sec, min1, hr, week_day, day, mn, year);    // prepare and display on LCD
    Delay_ms(1000);                                          // wait 1s
  }
}//
Best regards!
thanks dear this code works ,the problem occurs becuase of i didn't pull up the i2c pins high..............
thanks every body.............
Last edited by masterblastersachin on 07 Oct 2008 12:02, edited 1 time in total.
SACHIN
http://belgaum.myminicity.com/

masterblastersachin
Posts: 34
Joined: 07 May 2008 10:01
Location: BANGALORE

adjust the time of RTC using 4 keys

#11 Post by masterblastersachin » 03 Oct 2008 08:16

hello ,
i want to introduce the 4 keys in the previously posted program to adjust the timimg....
1key as--> set
2nd key-->up
3rd key-->down
4th key --> ok....
if i want to set the time press the set key,
for posioning the cursor to hour or min or sec press the set key ....
for adjusting the time use up or down key...
after setting the time press OK key for displaying new time....
please help me.....
how can i do it....
thanking you....
SACHIN
http://belgaum.myminicity.com/

Mohan
Posts: 12
Joined: 23 Jan 2008 12:27
Location: Pondicherry
Contact:

#12 Post by Mohan » 06 Oct 2008 14:32

Hi,

Try this out. I used the code at http://www.mikroe.com/forum/viewtopic.php?t=15813

and adapted for EP5, PIC16F877A, 8Mhz crystal & DS1307
LCD at PORTB with EP5 default config, PORTD pull down, Switch Jumper J17 set to VCC

Code: Select all

// Definitions for I2C devices BIOS
#define DS1307_HWAddress 0xD0      // Hardware address of the RTC

// Keypad Port and lines
#define KEYPAD_PORT      PORTD     // Select keypad port
#define KEYPAD_MENU      F0        // Menu/Exit
#define KEYPAD_SELECT    F1        // Select
#define KEYPAD_INC       F2        // Inc number
#define KEYPAD_DEC       F3        // Dec number
#define KEYPAD_RESET     F7        // Reset

#ifndef HIGH
#define HIGH 1
#define LOW  0
#endif // HIGH + LOW

unsigned char   bSec, bMin, bStd, bDay, bMon, bYear, oldstate;
unsigned int    uSec, uMin, uStd, uDay, uMon, uYear;
unsigned char   output[21];

extern void menu( void);
extern void StoreToRTC( void);
extern void InitDisplay( void);
extern void Set_Position( unsigned char Sign);
extern void IncDecSign( unsigned Sign, unsigned direct);
extern unsigned char DS1307_Read(unsigned char Addr);
extern void DS1307_Write(unsigned char Addr, unsigned char Data);

// Reads a byte from the DS1307 (software controlled)
// Input: address to write to
// Output: the byte value in the memory position
// Desc: the function reads a single byte (Data) at a time to the data address indicated in Addr.
unsigned char DS1307_Read(unsigned char Addr)
{
  unsigned char AddrBuff;
  AddrBuff=DS1307_HWAddress;
  I2C_Start();                       // Issue I2C start signal
  I2C_Wr(AddrBuff);               // Send hardware address for writting
  I2C_Wr(Addr);                   // Send the data address
  I2C_Repeated_Start();
  AddrBuff.F0=HIGH;                       // Configure the data direction bit for reading
  I2C_Wr(AddrBuff);               // Send device address
  AddrBuff=I2C_Rd(0);           // Read the byte from the slave and NACK to end comms
  I2C_Stop();                        // Free up the bus
  return(AddrBuff);
}

// Writes a byte to the DS1307 (software controlled)
// Input: address to write to, value to be written
// Output: none
// Desc: the function writes a single byte (Data) at a time to the data address indicated in DataAddr.
void DS1307_Write(unsigned char Addr, unsigned char Data)
{
  I2C_Start();                       // Issue I2C start signal
  I2C_Wr(DS1307_HWAddress);       // Send hardware address for writting
  I2C_Wr(Addr);                   // Send low byte of the data address
  I2C_Wr(Data);                   // Send the data
  I2C_Stop();                        // Free the bus
   return;
}

void InitDisplay( void)
{
  Lcd_Config(&PORTB, 4, 5, 6, 3, 2, 1, 0); // Lcd_Init_EP5, see Autocomplete
  Lcd_Cmd(LCD_CLEAR);
  Lcd_Cmd(LCD_CURSOR_OFF);   // Turn off cursor
  Lcd_Out( 1, 1, "Time: 00:00:00");
  Lcd_Out( 2, 1, "Date: 00.00.0000");
  Delay_ms( 2000);
}

void Reset_Clock( void)
{
  bStd = 0;
  bMin = 0;
  bSec = 0;
  bDay = 18;
  bMon = 7;
  bYear = 8;
  StoreToRTC();
  InitDisplay();
}

void Set_Position( unsigned char Sign)
{
  switch( Sign)
  {
    case 0:  uStd = (unsigned int)bStd;
             sprinti(&output, "%02u", uStd);
             Lcd_Out( 1, 7, output);
             Lcd_Out( 1, 8, "");
             Lcd_Cmd(LCD_BLINK_CURSOR_ON);
             break;
    case 1:  uMin = (unsigned int)bMin;
             sprinti(&output, "%02u", uMin);
             Lcd_Out( 1, 10, output);
             Lcd_Out( 1, 11, "");
             Lcd_Cmd(LCD_BLINK_CURSOR_ON);
             break;
    case 2:  uSec = (unsigned int)bSec;
             sprinti(&output, "%02u", uSec);
             Lcd_Out( 1, 13, output);
             Lcd_Out( 1, 14, "");
             Lcd_Cmd(LCD_BLINK_CURSOR_ON);
             break;
    case 3:  uDay = (unsigned int)bDay;
             sprinti(&output, "%02u", uDay);
             Lcd_Out( 2, 7, output);
             Lcd_Out( 2, 8, "");
             Lcd_Cmd(LCD_BLINK_CURSOR_ON);
             break;
    case 4:  uMon = (unsigned int)bMon;
             sprinti(&output, "%02u", uMon);
             Lcd_Out( 2, 10, output);
             Lcd_Out( 2, 11, "");
             Lcd_Cmd(LCD_BLINK_CURSOR_ON);
             break;
    case 5:  uYear = (unsigned int)bYear + 2000;
             sprinti(&output, "%04u", uYear);
             Lcd_Out( 2, 13, output);
             Lcd_Out( 2, 16, "");
             Lcd_Cmd(LCD_BLINK_CURSOR_ON);
             break;
  };
}

void IncDecSign( unsigned Sign, unsigned direct)
{
  switch( Sign)
  {
    case 0:  if( !direct)
             {
               bStd++;
               if( bStd > 23)
                 bStd = 23;
             } else {
               if( bStd > 0)
                 bStd--;
             };
             uStd = (unsigned int)bStd;
             break;
    case 1:  if( !direct)
             {
               bMin++;
               if( bMin > 59)
                 bMin = 59;
             } else {
               if( bMin > 0)
                 bMin--;
             };
             uMin = (unsigned int)bMin;
             break;
    case 2:  if( !direct)
             {
               bSec++;
               if( bSec > 59)
                 bSec = 59;
             } else {
               if( bSec > 0)
                 bSec--;
             };
             uSec = (unsigned int)bSec;
             break;
    case 3:  if( !direct)
             {
               bDay++;
               if( bDay > 31)
                 bDay = 31;
             } else {
               if( bDay > 0)
                 bDay--;
             };
             uDay = (unsigned int)bDay;
             break;
    case 4:  if( !direct)
             {
               bMon++;
               if( bMon > 12)
                 bMon = 12;
             } else {
               if( bMon > 0)
                 bMon--;
             };
             uMon = (unsigned int)bMon;
             break;
    case 5:  if( !direct)
             {
               bYear++;
               if( bYear > 99)
                 bYear = 99;
             } else {
               if( bYear > 0)
                 bYear--;
             };
             uYear = (unsigned int)bYear + 2000;
             break;
  };
}

// Store all Settings into DS1307
/////////////////////////////////
void StoreToRTC( void)
{
  Lcd_Cmd(Lcd_CLEAR);
  Lcd_Cmd(Lcd_CURSOR_OFF);
  Lcd_Out( 1, 1, "  Store to RTC");
  bSec = (((bSec / 10) << 4) & 0xF0) + ((bSec-(bSec / 10) * 10) & 0b00001111);
  DS1307_Write( 0x00, bSec);
  bMin = (((bMin / 10) << 4) & 0xF0) + ((bMin-(bMin / 10) * 10) & 0b00001111);
  DS1307_Write( 0x01, bMin);
  bStd = (((bStd / 10) << 4) & 0xF0) + ((bStd-(bStd / 10) * 10) & 0b00001111);
  DS1307_Write( 0x02, bStd);
  // bDay = ((bDay & 0x30) >> 4)*10 + (bDay & 0b00001111);
  bDay = (((bDay / 10) << 4) & 0x30) + ((bDay-(bDay / 10) * 10) & 0b00001111);
  DS1307_Write( 0x04, bDay);
  bMon = (((bMon / 10) << 4) & 0x10) + ((bMon-(bMon / 10) * 10) & 0b00001111);
  DS1307_Write( 0x05, bMon);
  bYear = (((bYear / 10) << 4) & 0xC0) + ((bYear-(bYear / 10) * 10) & 0b00001111);
  DS1307_Write( 0x06, bYear);
  delay_ms( 2000);
}

// KeyPort, input via button
//////////////////////////////
// F0 = Menu/Exit
// F1 = Select
// F2 = INC Number
// F3 = DEC Number
// F7 = Reset Clock-Chip
void menu( void)
{
  unsigned char   Sig;

  Sig = 0;

  Lcd_Out( 1, 1, " Set");
  Lcd_Out( 2, 1, "    ");
  Lcd_Cmd(LCD_BLINK_CURSOR_ON);

  Set_Position( Sig);
  Delay_ms( 2000);

  do
  {
    // Menu key pressed?
    ////////////////////
    if (KEYPAD_PORT.KEYPAD_MENU == 1) {
      delay_ms( 250);
      break;
    };

    if( KEYPAD_PORT.KEYPAD_SELECT == 1) {
      delay_ms( 250);
      Sig++;
      if( Sig > 5)
        Sig = 0;
      Set_Position( Sig);
    };

    // Increment
    if( KEYPAD_PORT.KEYPAD_INC == 1) {
      delay_ms( 100);
      IncDecSign( Sig, 0);
      Set_Position( Sig);
    };

    // Decrement
    if( KEYPAD_PORT.KEYPAD_DEC == 1) {
      delay_ms( 100);
      IncDecSign( Sig, 1);
      Set_Position( Sig);
    };

    Delay_ms( 100);
  } while( 1);

  // Store all Settings in DS1307
  ///////////////////////////////
  StoreToRTC();

  // Exit to Clock

  Lcd_Cmd(Lcd_CURSOR_OFF);


  // Refresh Display
  InitDisplay();
}

void main( void)
{
  TRISD  = 0b10001111;
  PORTB  = 0x00;
  TRISC  = 0x00;
  PORTC  = 0b00;
  TRISD  = 0x00;
  PORTD  = 0x00;
  TRISE  = 0x00;
  PORTE  = 0x00;
  ADCON1 = 7;        // disable analog inputs

  I2C_Init(100000);                        // initialize I2C
  I2C_Start();          // issue start signal
  I2C_Wr(0xD0);         // address DS1307
  I2C_Wr(0);            // start from word at address 0
  I2C_Wr(0);            // write 0 to REG0 (enable counting + 0 sec)
  I2C_Stop();           // issue stop signal

  InitDisplay();
  oldstate = 0;

  // Clock Routine
  ////////////////
  do
  {
    delay_ms( 100);
    bSec = DS1307_Read( 0x00);
    bSec = ((bSec & 0xF0) >> 4)*10 + (bSec & 0b00001111);
    uSec = (unsigned int)bSec;
    bMin = DS1307_Read( 0x01);
    bMin = ((bMin & 0xF0) >> 4)*10 + (bMin & 0b00001111);
    uMin = (unsigned int)bMin;
    bStd = DS1307_Read( 0x02);
    bStd = ((bStd & 0xF0) >> 4)*10 + (bStd & 0b00001111);
    uStd = (unsigned int)bStd;

    bDay = DS1307_Read( 0x04);
    bDay = ((bDay & 0x30) >> 4)*10 + (bDay & 0b00001111);
    uDay = (unsigned int)bDay;
    bMon = DS1307_Read( 0x05);
    bMon = ((bMon & 0x10) >> 4)*10 + (bMon & 0b00001111);
    uMon = (unsigned int)bMon;
    bYear= DS1307_Read( 0x06);
    bYear = ((bYear & 0xC0)>> 4)*10 + (bYear & 0b00001111);
    uYear = (unsigned int)bYear + 2000;

    sprinti(&output, "%02u:%02u:%02u", uStd, uMin, uSec);
    Lcd_out( 1, 7 , output);
    sprinti(&output, "%02u.%02u.%04u", uDay, uMon, uYear);
    Lcd_out( 2, 7 , output);

    // Menu key pressed?
    ////////////////////
    if( KEYPAD_PORT.KEYPAD_MENU == 1) {
      delay_ms( 250);
      menu();
    } else if( KEYPAD_PORT.KEYPAD_RESET == 1) {
      delay_ms( 250);
      Reset_Clock();
    };

  } while( 1);
}
Hobbyist, Pondicherry
India

masterblastersachin
Posts: 34
Joined: 07 May 2008 10:01
Location: BANGALORE

#13 Post by masterblastersachin » 06 Oct 2008 14:44

thanx yaar.....
SACHIN
http://belgaum.myminicity.com/

majerv
Posts: 26
Joined: 26 Sep 2008 00:54

18F4550 RTC Problem

#14 Post by majerv » 20 Oct 2008 12:11

Hi Folks!

I've tried dronology's program on a 16F877 and it runs perfect, but not on a 18F4550. I've connected the SDA(pin5) to the RB0 of the PIC and SCL(pin6) to the RB1. I don't know what the problem could be.

I think it must be a config problem.

Any Idea?

Thanx...

dronology
Posts: 106
Joined: 29 Dec 2007 23:48
Location: istanbul
Contact:

Re: 18F4550 RTC Problem

#15 Post by dronology » 21 Oct 2008 13:29

Dear majerv,

It seems that 18F4550 and 18F4620 (my code based on 4620) have huge differences. SDA and SCL pins of 4620 are located on PORTC. SDA->RC4 and SCL->RC3. I checked 4550. SCL pin is located on RB1 and SDA is located on RB0. On 4550 RB0 and RB1 pins contain extra properties such as Analog input and interrupt. Have you disabled analog-inputs and interrupts on this chip before using DS1307 codes?
R. Giskard Reventlov & R. Daneel Olivaw

http://www.circuitechs.com
http://www.dronology.com

Post Reply

Return to “mikroC General”