Library for Maxim DS3232M super-accurate, I2C based Real Time Clock chip with 234 bytes of user RAM. Library includes user RAM read/write operations along with CRC routines for accessing the user RAM area.

Dependents:   ds3232m_HelloWorld

Revision:
1:0975d4a9b513
Parent:
0:30a7faf58768
Child:
2:a9a8027a7cb2
--- a/ds3232m.cpp	Mon Dec 08 20:15:16 2014 +0000
+++ b/ds3232m.cpp	Fri Dec 19 20:22:13 2014 +0000
@@ -26,6 +26,10 @@
 char RtcCtlReg = 0;
 char RtcStatReg = 0;
 
+#ifdef RTOS_H
+extern Mutex MutexI2C0;              //lock/unlock I2C requests
+#endif  //RTOS_H
+
 //--------------------------------------------------------------------------------------------------------------------------------------//
 // constructor with fixed frequency 
 
@@ -63,11 +67,17 @@
     buffer[5] = DecToBCD(time.mon);
     buffer[6] = DecToBCD(time.year - 2000);
 
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232SECONDS);
     for(int i = 0; i < 7; i++) _i2c_->write(buffer[i]);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
 }
 
 //--------------------------------------------------------------------------------------------------------------------------------------//
@@ -75,6 +85,9 @@
 
 void ds3232m::getTime(Time_rtc& time) {
     char buffer[7];
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232SECONDS);
@@ -83,6 +96,9 @@
     for(int i = 0; i < 7; i++) buffer[i] = _i2c_->read(1);
     int rtcgarbage = (_i2c_->read(0)); //final junk read
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
     
     time.sec = BCDToDec(buffer[0]);
     time.min = BCDToDec(buffer[1]);
@@ -97,6 +113,9 @@
 // retrieve the control and status registers
 
 void ds3232m::getControlStatusRegs() {
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232CTLREG);
@@ -105,6 +124,9 @@
     RtcCtlReg = _i2c_->read(1);
     RtcStatReg = _i2c_->read(0);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
 }
     
 //--------------------------------------------------------------------------------------------------------------------------------------//
@@ -117,11 +139,17 @@
     } else {
         RtcCtlReg |= DS3232_EOSCN_BIT;
     }
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232CTLREG);
     _i2c_->write(RtcCtlReg);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
 }
 
 //--------------------------------------------------------------------------------------------------------------------------------------//
@@ -143,11 +171,17 @@
     getControlStatusRegs();
     if((checkTempBusy()) == true) return false;     //is already busy
     RtcCtlReg |= DS3232_CONV_BIT;
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232CTLREG);
     _i2c_->write(RtcCtlReg);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
     return true;
 }
 
@@ -158,6 +192,9 @@
 float ds3232m::getTemperature() {
     getControlStatusRegs();
     if((checkTempBusy()) == false) return(255.0);     //is already busy
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232TEMPERATURE);
@@ -166,6 +203,10 @@
     int8_t temp3232a = (_i2c_->read(1));
     uint8_t temp3232b = _i2c_->read(0);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
+
     float temp3232 = float(temp3232a);
     //for positive temp
     if((temp3232b == 0x40) && (temp3232a >= 0)) temp3232 += 0.25;
@@ -181,6 +222,9 @@
 // get seconds register
 
 int ds3232m::getSeconds() {
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232SECONDS);
@@ -188,6 +232,9 @@
     _i2c_->write(RTCI2CADDRESS + 1);
     int seconds3232 = (_i2c_->read(0));
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
     int xbcd = BCDToDec(seconds3232);
     return(xbcd);
 }
@@ -196,11 +243,17 @@
 // clears all user memory inside the DS3232M.  Top 2 locations - reserved for CRC, also set to 00 since CRC value is 0x00 0x00
 
 void ds3232m::clearRAM() {
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232RAMBOTTOM);
     for(int i = DS3232RAMBOTTOM; i < 256; i++) _i2c_->write(NULL);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
 }
 
 //--------------------------------------------------------------------------------------------------------------------------------------//
@@ -215,6 +268,9 @@
     if((offset + length) > 0xfe) return(1);
     if(offset < 0x14) return(2);
     if(length == 0) return(4);
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(offset);
@@ -223,6 +279,9 @@
     for(int i = 0; i < length; i++) buffer[i] = _i2c_->read(1);
     _i2c_->read(0);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
     if(LoadRTCRam() == false) return(8);
     return(0);
 }
@@ -238,11 +297,17 @@
     if((offset + length) > 0xfe) return(1);
     if(offset < 0x14) return(2);
     if(length == 0) return(4);
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(offset);
     for(int i = 0; i < length; i++) _i2c_->write(buffer[i]);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
     addCRC16();
     return(0);
 }
@@ -263,11 +328,17 @@
         RtcStatReg &= ~DS3232_EN32KHZ_BIT;
         RtcStatReg &= ~DS3232_BB32KHZ_BIT;
     }
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232STATREG);
     _i2c_->write(RtcStatReg);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
 }
 
 //--------------------------------------------------------------------------------------------------------------------------------------//
@@ -286,11 +357,17 @@
         RtcCtlReg |= DS3232_INTCN_BIT;
         RtcCtlReg &= ~DS3232_BBSQW_BIT;
     }
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232CTLREG);
     _i2c_->write(RtcCtlReg);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
 }
 
 //--------------------------------------------------------------------------------------------------------------------------------------//
@@ -352,6 +429,9 @@
 char RTCbuffer[256];
 
 bool ds3232m::LoadRTCRam() {
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(0x00);
@@ -363,7 +443,13 @@
     }
     RTCbuffer[i] = _i2c_->read(0);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
     uint16_t calcdCRC = calculateCRC16(RTCbuffer, DS3232RAMBOTTOM, (DS3232RAMCRC16 - DS3232RAMBOTTOM));
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232RAMCRC16);
@@ -371,6 +457,9 @@
     _i2c_->write(RTCI2CADDRESS + 1);
     uint16_t storedCRC = (_i2c_->read(1) << 8) + (_i2c_->read(0) & 0xff);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
     if(storedCRC != calcdCRC) return false;
     return true;
 }
@@ -382,10 +471,17 @@
 void ds3232m::addCRC16() {
     LoadRTCRam();
     uint16_t resultCRC = calculateCRC16(RTCbuffer, DS3232RAMBOTTOM, (DS3232RAMCRC16 - DS3232RAMBOTTOM)); //0x14 is offset from 0 in buffer, 230 is length //
+#ifdef RTOS_H
+    MutexI2C0.lock();
+#endif
     _i2c_->start();
     _i2c_->write(RTCI2CADDRESS);
     _i2c_->write(DS3232RAMCRC16);
     _i2c_->write(resultCRC >> 8);
     _i2c_->write(resultCRC & 0xff);
     _i2c_->stop();
+#ifdef RTOS_H
+    MutexI2C0.unlock();
+#endif
 }
+