A feature complete driver for the ISL1208 real time clock from Intersil.

Dependents:   ISL1208_HelloWorld

Committer:
neilt6
Date:
Thu Nov 07 17:58:43 2013 +0000
Revision:
2:f33dbb2535a3
Parent:
0:697ca602e934
Child:
3:115e4dacfe07
Minor improvements

Who changed what in which revision?

UserRevisionLine numberNew contents of line
neilt6 0:697ca602e934 1 /* ISL1208 Driver Library
neilt6 0:697ca602e934 2 * Copyright (c) 2013 Neil Thiessen
neilt6 0:697ca602e934 3 *
neilt6 0:697ca602e934 4 * Licensed under the Apache License, Version 2.0 (the "License");
neilt6 0:697ca602e934 5 * you may not use this file except in compliance with the License.
neilt6 0:697ca602e934 6 * You may obtain a copy of the License at
neilt6 0:697ca602e934 7 *
neilt6 0:697ca602e934 8 * http://www.apache.org/licenses/LICENSE-2.0
neilt6 0:697ca602e934 9 *
neilt6 0:697ca602e934 10 * Unless required by applicable law or agreed to in writing, software
neilt6 0:697ca602e934 11 * distributed under the License is distributed on an "AS IS" BASIS,
neilt6 0:697ca602e934 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
neilt6 0:697ca602e934 13 * See the License for the specific language governing permissions and
neilt6 0:697ca602e934 14 * limitations under the License.
neilt6 0:697ca602e934 15 */
neilt6 0:697ca602e934 16
neilt6 0:697ca602e934 17 #include "ISL1208.h"
neilt6 0:697ca602e934 18
neilt6 0:697ca602e934 19 ISL1208::ISL1208(PinName sda, PinName scl) : m_I2C(sda, scl)
neilt6 0:697ca602e934 20 {
neilt6 2:f33dbb2535a3 21 //Set the I2C bus frequency to 400kHz
neilt6 2:f33dbb2535a3 22 m_I2C.frequency(400000);
neilt6 0:697ca602e934 23 }
neilt6 0:697ca602e934 24
neilt6 0:697ca602e934 25 bool ISL1208::open(OscillatorMode mode)
neilt6 0:697ca602e934 26 {
neilt6 0:697ca602e934 27 //Probe for the ISL1208 using a Zero Length Transfer
neilt6 0:697ca602e934 28 if (!m_I2C.write(m_ADDR, NULL, 0)) {
neilt6 0:697ca602e934 29 //Read the current status register
neilt6 0:697ca602e934 30 char sr = read8(REG_CTL_SR);
neilt6 0:697ca602e934 31
neilt6 0:697ca602e934 32 //Configure the oscillator mode
neilt6 0:697ca602e934 33 if (mode == OSCILLATOR_CRYSTAL)
neilt6 0:697ca602e934 34 sr &= ~(1 << 6);
neilt6 0:697ca602e934 35 else
neilt6 0:697ca602e934 36 sr |= (1 << 6);
neilt6 0:697ca602e934 37
neilt6 0:697ca602e934 38 //Disable auto reset for BAT and ALM bits
neilt6 0:697ca602e934 39 sr &= ~(1 << 7);
neilt6 0:697ca602e934 40
neilt6 0:697ca602e934 41 //Write the new status register
neilt6 0:697ca602e934 42 write8(REG_CTL_SR, sr);
neilt6 0:697ca602e934 43
neilt6 0:697ca602e934 44 //Return success
neilt6 0:697ca602e934 45 return true;
neilt6 0:697ca602e934 46 } else {
neilt6 0:697ca602e934 47 //Return failure
neilt6 0:697ca602e934 48 return false;
neilt6 0:697ca602e934 49 }
neilt6 0:697ca602e934 50 }
neilt6 0:697ca602e934 51
neilt6 2:f33dbb2535a3 52 time_t ISL1208::time()
neilt6 0:697ca602e934 53 {
neilt6 0:697ca602e934 54 //Setup a tm structure based on the RTC
neilt6 0:697ca602e934 55 struct tm timeinfo;
neilt6 0:697ca602e934 56 timeinfo.tm_sec = bcd2bin(read8(REG_RTC_SC));
neilt6 0:697ca602e934 57 timeinfo.tm_min = bcd2bin(read8(REG_RTC_MN));
neilt6 0:697ca602e934 58
neilt6 0:697ca602e934 59 //Make sure we get the proper hour regardless of the mode
neilt6 0:697ca602e934 60 char hours = read8(REG_RTC_HR);
neilt6 0:697ca602e934 61 if (hours & (1 << 7)) {
neilt6 0:697ca602e934 62 //RTC is in 24-hour mode
neilt6 0:697ca602e934 63 timeinfo.tm_hour = bcd2bin(hours & 0x3F);
neilt6 0:697ca602e934 64 } else {
neilt6 0:697ca602e934 65 //RTC is in 12-hour mode
neilt6 0:697ca602e934 66 timeinfo.tm_hour = bcd2bin(hours & 0x1F);
neilt6 0:697ca602e934 67
neilt6 0:697ca602e934 68 //Check for the PM flag
neilt6 0:697ca602e934 69 if (hours & (1 << 5))
neilt6 0:697ca602e934 70 timeinfo.tm_hour += 12;
neilt6 0:697ca602e934 71 }
neilt6 0:697ca602e934 72
neilt6 0:697ca602e934 73 //Continue reading the registers
neilt6 0:697ca602e934 74 timeinfo.tm_mday = bcd2bin(read8(REG_RTC_DT));
neilt6 0:697ca602e934 75 timeinfo.tm_mon = bcd2bin(read8(REG_RTC_MO)) - 1;
neilt6 0:697ca602e934 76 timeinfo.tm_year = bcd2bin(read8(REG_RTC_YR)) + 100;
neilt6 0:697ca602e934 77 timeinfo.tm_wday = bcd2bin(read8(REG_RTC_DW));
neilt6 0:697ca602e934 78
neilt6 0:697ca602e934 79 //Return as a timestamp
neilt6 0:697ca602e934 80 return mktime(&timeinfo);
neilt6 0:697ca602e934 81 }
neilt6 0:697ca602e934 82
neilt6 0:697ca602e934 83 void ISL1208::time(time_t t)
neilt6 0:697ca602e934 84 {
neilt6 0:697ca602e934 85 //Convert the time to a tm
neilt6 0:697ca602e934 86 struct tm *timeinfo = localtime(&t);
neilt6 0:697ca602e934 87
neilt6 0:697ca602e934 88 /* The clock has an 8 bit wide bcd-coded register (they never learn)
neilt6 0:697ca602e934 89 * for the year. tm_year is an offset from 1900 and we are interested
neilt6 0:697ca602e934 90 * in the 2000-2099 range, so any value less than 100 is invalid.
neilt6 0:697ca602e934 91 */
neilt6 0:697ca602e934 92 if (timeinfo->tm_year < 100)
neilt6 0:697ca602e934 93 return;
neilt6 0:697ca602e934 94
neilt6 0:697ca602e934 95 //Read the old SR register value
neilt6 0:697ca602e934 96 char sr = read8(REG_CTL_SR);
neilt6 0:697ca602e934 97
neilt6 0:697ca602e934 98 //Enable RTC writing
neilt6 0:697ca602e934 99 write8(REG_CTL_SR, sr | (1 << 4));
neilt6 0:697ca602e934 100
neilt6 0:697ca602e934 101 //Write the current time
neilt6 0:697ca602e934 102 write8(REG_RTC_SC, bin2bcd(timeinfo->tm_sec));
neilt6 0:697ca602e934 103 write8(REG_RTC_MN, bin2bcd(timeinfo->tm_min));
neilt6 0:697ca602e934 104 write8(REG_RTC_HR, bin2bcd(timeinfo->tm_hour) | (1 << 7)); //24-hour mode
neilt6 0:697ca602e934 105 write8(REG_RTC_DT, bin2bcd(timeinfo->tm_mday));
neilt6 0:697ca602e934 106 write8(REG_RTC_MO, bin2bcd(timeinfo->tm_mon + 1));
neilt6 0:697ca602e934 107 write8(REG_RTC_YR, bin2bcd(timeinfo->tm_year - 100));
neilt6 0:697ca602e934 108 write8(REG_RTC_DW, bin2bcd(timeinfo->tm_wday & 7));
neilt6 0:697ca602e934 109
neilt6 0:697ca602e934 110 //Disable RTC writing
neilt6 0:697ca602e934 111 write8(REG_CTL_SR, sr);
neilt6 0:697ca602e934 112 }
neilt6 0:697ca602e934 113
neilt6 2:f33dbb2535a3 114 bool ISL1208::powerFailed()
neilt6 0:697ca602e934 115 {
neilt6 0:697ca602e934 116 //Read the 8-bit register value
neilt6 0:697ca602e934 117 char value = read8(REG_CTL_SR);
neilt6 0:697ca602e934 118
neilt6 0:697ca602e934 119 //Return the status of the RTCF bit
neilt6 0:697ca602e934 120 if (value & (1 << 0))
neilt6 0:697ca602e934 121 return true;
neilt6 0:697ca602e934 122 else
neilt6 0:697ca602e934 123 return false;
neilt6 0:697ca602e934 124 }
neilt6 0:697ca602e934 125
neilt6 2:f33dbb2535a3 126 bool ISL1208::batteryFlag()
neilt6 0:697ca602e934 127 {
neilt6 0:697ca602e934 128 //Read the 8-bit register value
neilt6 0:697ca602e934 129 char value = read8(REG_CTL_SR);
neilt6 0:697ca602e934 130
neilt6 0:697ca602e934 131 //Return the status of the BAT bit
neilt6 0:697ca602e934 132 if (value & (1 << 1))
neilt6 0:697ca602e934 133 return true;
neilt6 0:697ca602e934 134 else
neilt6 0:697ca602e934 135 return false;
neilt6 0:697ca602e934 136 }
neilt6 0:697ca602e934 137
neilt6 2:f33dbb2535a3 138 void ISL1208::clearBatteryFlag()
neilt6 0:697ca602e934 139 {
neilt6 0:697ca602e934 140 //Read the current 8-bit register value
neilt6 0:697ca602e934 141 char value = read8(REG_CTL_SR);
neilt6 0:697ca602e934 142
neilt6 0:697ca602e934 143 //Clear the BAT bit
neilt6 0:697ca602e934 144 value &= ~(1 << 1);
neilt6 0:697ca602e934 145
neilt6 0:697ca602e934 146 //Write the value back out
neilt6 0:697ca602e934 147 write8(REG_CTL_SR, value);
neilt6 0:697ca602e934 148 }
neilt6 0:697ca602e934 149
neilt6 2:f33dbb2535a3 150 bool ISL1208::alarmFlag()
neilt6 0:697ca602e934 151 {
neilt6 0:697ca602e934 152 //Read the 8-bit register value
neilt6 0:697ca602e934 153 char value = read8(REG_CTL_SR);
neilt6 0:697ca602e934 154
neilt6 0:697ca602e934 155 //Return the status of the ALM bit
neilt6 0:697ca602e934 156 if (value & (1 << 2))
neilt6 0:697ca602e934 157 return true;
neilt6 0:697ca602e934 158 else
neilt6 0:697ca602e934 159 return false;
neilt6 0:697ca602e934 160 }
neilt6 0:697ca602e934 161
neilt6 2:f33dbb2535a3 162 void ISL1208::clearAlarmFlag()
neilt6 0:697ca602e934 163 {
neilt6 0:697ca602e934 164 //Read the current 8-bit register value
neilt6 0:697ca602e934 165 char value = read8(REG_CTL_SR);
neilt6 0:697ca602e934 166
neilt6 0:697ca602e934 167 //Clear the ALM bit
neilt6 0:697ca602e934 168 value &= ~(1 << 2);
neilt6 0:697ca602e934 169
neilt6 0:697ca602e934 170 //Write the value back out
neilt6 0:697ca602e934 171 write8(REG_CTL_SR, value);
neilt6 0:697ca602e934 172 }
neilt6 0:697ca602e934 173
neilt6 2:f33dbb2535a3 174 ISL1208::OutputFrequency ISL1208::foutFrequency()
neilt6 0:697ca602e934 175 {
neilt6 0:697ca602e934 176 //Read the 8-bit register value
neilt6 0:697ca602e934 177 char value = read8(REG_CTL_INT);
neilt6 0:697ca602e934 178
neilt6 0:697ca602e934 179 //Return the lower nibble
neilt6 0:697ca602e934 180 return (OutputFrequency)(value & 0x0F);
neilt6 0:697ca602e934 181 }
neilt6 0:697ca602e934 182
neilt6 0:697ca602e934 183 void ISL1208::foutFrequency(OutputFrequency freq)
neilt6 0:697ca602e934 184 {
neilt6 0:697ca602e934 185 //Read the current 8-bit register value
neilt6 0:697ca602e934 186 char value = read8(REG_CTL_INT);
neilt6 0:697ca602e934 187
neilt6 0:697ca602e934 188 //Clear the old frequency bits
neilt6 0:697ca602e934 189 value &= 0xF0;
neilt6 0:697ca602e934 190
neilt6 0:697ca602e934 191 //Set the new frequency bits
neilt6 0:697ca602e934 192 value |= freq;
neilt6 0:697ca602e934 193
neilt6 0:697ca602e934 194 //Write the value back out
neilt6 0:697ca602e934 195 write8(REG_CTL_INT, value);
neilt6 0:697ca602e934 196 }
neilt6 0:697ca602e934 197
neilt6 2:f33dbb2535a3 198 bool ISL1208::outputOnBattery()
neilt6 0:697ca602e934 199 {
neilt6 0:697ca602e934 200 //Read the 8-bit register value
neilt6 0:697ca602e934 201 char value = read8(REG_CTL_INT);
neilt6 0:697ca602e934 202
neilt6 0:697ca602e934 203 //Return the status of the FOBATB bit
neilt6 0:697ca602e934 204 if (value & (1 << 4))
neilt6 0:697ca602e934 205 return false;
neilt6 0:697ca602e934 206 else
neilt6 0:697ca602e934 207 return true;
neilt6 0:697ca602e934 208 }
neilt6 0:697ca602e934 209
neilt6 0:697ca602e934 210 void ISL1208::outputOnBattery(bool output)
neilt6 0:697ca602e934 211 {
neilt6 0:697ca602e934 212 //Read the current 8-bit register value
neilt6 0:697ca602e934 213 char value = read8(REG_CTL_INT);
neilt6 0:697ca602e934 214
neilt6 0:697ca602e934 215 //Set or clear the FOBATB bit
neilt6 0:697ca602e934 216 if (output)
neilt6 0:697ca602e934 217 value &= ~(1 << 4);
neilt6 0:697ca602e934 218 else
neilt6 0:697ca602e934 219 value |= (1 << 4);
neilt6 0:697ca602e934 220
neilt6 0:697ca602e934 221 //Write the value back out
neilt6 0:697ca602e934 222 write8(REG_CTL_INT, value);
neilt6 0:697ca602e934 223 }
neilt6 0:697ca602e934 224
neilt6 2:f33dbb2535a3 225 ISL1208::PowerMode ISL1208::powerMode()
neilt6 0:697ca602e934 226 {
neilt6 0:697ca602e934 227 //Read the 8-bit register value
neilt6 0:697ca602e934 228 char value = read8(REG_CTL_INT);
neilt6 0:697ca602e934 229
neilt6 0:697ca602e934 230 //Return the status of the LPMODE bit
neilt6 0:697ca602e934 231 if (value & (1 << 5))
neilt6 0:697ca602e934 232 return POWER_LPMODE;
neilt6 0:697ca602e934 233 else
neilt6 0:697ca602e934 234 return POWER_NORMAL;
neilt6 0:697ca602e934 235 }
neilt6 0:697ca602e934 236
neilt6 0:697ca602e934 237 void ISL1208::powerMode(PowerMode mode)
neilt6 0:697ca602e934 238 {
neilt6 0:697ca602e934 239 //Read the current 8-bit register value
neilt6 0:697ca602e934 240 char value = read8(REG_CTL_INT);
neilt6 0:697ca602e934 241
neilt6 0:697ca602e934 242 //Set or clear the LPMODE bit
neilt6 0:697ca602e934 243 if (mode == POWER_LPMODE)
neilt6 0:697ca602e934 244 value |= (1 << 5);
neilt6 0:697ca602e934 245 else
neilt6 0:697ca602e934 246 value &= ~(1 << 5);
neilt6 0:697ca602e934 247
neilt6 0:697ca602e934 248 //Write the value back out
neilt6 0:697ca602e934 249 write8(REG_CTL_INT, value);
neilt6 0:697ca602e934 250 }
neilt6 0:697ca602e934 251
neilt6 2:f33dbb2535a3 252 ISL1208::AlarmMode ISL1208::alarmMode()
neilt6 0:697ca602e934 253 {
neilt6 0:697ca602e934 254 //Read the 8-bit register value
neilt6 0:697ca602e934 255 char value = read8(REG_CTL_INT);
neilt6 0:697ca602e934 256
neilt6 0:697ca602e934 257 //Return the status of the ALME and IM bits
neilt6 0:697ca602e934 258 if (value & (1 << 6)) {
neilt6 0:697ca602e934 259 if (value & (1 << 7))
neilt6 0:697ca602e934 260 return ALARM_INTERRUPT;
neilt6 0:697ca602e934 261 else
neilt6 0:697ca602e934 262 return ALARM_SINGLE;
neilt6 0:697ca602e934 263 } else
neilt6 0:697ca602e934 264 return ALARM_DISABLED;
neilt6 0:697ca602e934 265 }
neilt6 0:697ca602e934 266
neilt6 0:697ca602e934 267 void ISL1208::alarmMode(AlarmMode mode)
neilt6 0:697ca602e934 268 {
neilt6 0:697ca602e934 269 //Read the current 8-bit register value
neilt6 0:697ca602e934 270 char value = read8(REG_CTL_INT);
neilt6 0:697ca602e934 271
neilt6 0:697ca602e934 272 //Set or clear the ALME and IM bit
neilt6 0:697ca602e934 273 if (mode != ALARM_DISABLED) {
neilt6 0:697ca602e934 274 value |= (1 << 6);
neilt6 0:697ca602e934 275 if (mode == ALARM_INTERRUPT)
neilt6 0:697ca602e934 276 value |= (1 << 7);
neilt6 0:697ca602e934 277 else
neilt6 0:697ca602e934 278 value &= ~(1 << 7);
neilt6 0:697ca602e934 279 } else
neilt6 0:697ca602e934 280 value &= ~(1 << 6);
neilt6 0:697ca602e934 281
neilt6 0:697ca602e934 282 //Write the value back out
neilt6 0:697ca602e934 283 write8(REG_CTL_INT, value);
neilt6 0:697ca602e934 284 }
neilt6 0:697ca602e934 285
neilt6 2:f33dbb2535a3 286 float ISL1208::analogTrim()
neilt6 0:697ca602e934 287 {
neilt6 0:697ca602e934 288 //Read the 8-bit register value
neilt6 0:697ca602e934 289 char value = read8(REG_CTL_ATR);
neilt6 0:697ca602e934 290
neilt6 0:697ca602e934 291 //Mask off the top 2 bits
neilt6 0:697ca602e934 292 value &= 0x3F;
neilt6 0:697ca602e934 293
neilt6 0:697ca602e934 294 //Invert bit 5
neilt6 0:697ca602e934 295 value ^= 1 << 5;
neilt6 0:697ca602e934 296
neilt6 0:697ca602e934 297 //Add an offset of 4.5pF (unit[atr] = 0.25pF)
neilt6 0:697ca602e934 298 value += 2 * 9;
neilt6 0:697ca602e934 299
neilt6 0:697ca602e934 300 //Return the analog trim in pF
neilt6 0:697ca602e934 301 return value * 0.25;
neilt6 0:697ca602e934 302 }
neilt6 0:697ca602e934 303
neilt6 0:697ca602e934 304 void ISL1208::analogTrim(float trim)
neilt6 0:697ca602e934 305 {
neilt6 0:697ca602e934 306 //Range limit trim
neilt6 0:697ca602e934 307 if (trim < 4.5)
neilt6 0:697ca602e934 308 trim = 4.5;
neilt6 0:697ca602e934 309 else if (trim > 20.25)
neilt6 0:697ca602e934 310 trim = 20.25;
neilt6 0:697ca602e934 311
neilt6 0:697ca602e934 312 //Convert the analog trim value to a 6-bit integer
neilt6 0:697ca602e934 313 char value = (char)(trim / 0.25);
neilt6 0:697ca602e934 314
neilt6 0:697ca602e934 315 //Remove the offset of 4.5pF (unit[atr] = 0.25pF)
neilt6 0:697ca602e934 316 value -= 2 * 9;
neilt6 0:697ca602e934 317
neilt6 0:697ca602e934 318 //Invert bit 5
neilt6 0:697ca602e934 319 value ^= 1 << 5;
neilt6 0:697ca602e934 320
neilt6 0:697ca602e934 321 //Read the current 8-bit register value
neilt6 0:697ca602e934 322 char reg = read8(REG_CTL_ATR);
neilt6 0:697ca602e934 323
neilt6 0:697ca602e934 324 //Clear the old ATR bits
neilt6 0:697ca602e934 325 reg &= 0xC0;
neilt6 0:697ca602e934 326
neilt6 0:697ca602e934 327 //Add the new ATR bits
neilt6 0:697ca602e934 328 reg |= value;
neilt6 0:697ca602e934 329
neilt6 0:697ca602e934 330 //Write the value back out
neilt6 0:697ca602e934 331 write8(REG_CTL_ATR, reg);
neilt6 0:697ca602e934 332 }
neilt6 0:697ca602e934 333
neilt6 2:f33dbb2535a3 334 ISL1208::BatteryModeATR ISL1208::batteryModeATR()
neilt6 0:697ca602e934 335 {
neilt6 0:697ca602e934 336 //Read the 8-bit register value
neilt6 0:697ca602e934 337 char value = read8(REG_CTL_ATR);
neilt6 0:697ca602e934 338
neilt6 0:697ca602e934 339 //Shift out the ATR bits
neilt6 0:697ca602e934 340 value >>= 6;
neilt6 0:697ca602e934 341
neilt6 0:697ca602e934 342 //Return the value as a BatteryModeATR enum
neilt6 0:697ca602e934 343 return (BatteryModeATR)value;
neilt6 0:697ca602e934 344 }
neilt6 0:697ca602e934 345
neilt6 0:697ca602e934 346 void ISL1208::batteryModeATR(BatteryModeATR atr)
neilt6 0:697ca602e934 347 {
neilt6 0:697ca602e934 348 //Read the current 8-bit register value
neilt6 0:697ca602e934 349 char value = read8(REG_CTL_ATR);
neilt6 0:697ca602e934 350
neilt6 0:697ca602e934 351 //Clear the old battery mode ATR bits
neilt6 0:697ca602e934 352 value &= 0x3F;
neilt6 0:697ca602e934 353
neilt6 0:697ca602e934 354 //Add the new battery mode ATR bits
neilt6 0:697ca602e934 355 value |= (atr << 6);
neilt6 0:697ca602e934 356
neilt6 0:697ca602e934 357 //Write the value back out
neilt6 0:697ca602e934 358 write8(REG_CTL_ATR, value);
neilt6 0:697ca602e934 359 }
neilt6 0:697ca602e934 360
neilt6 2:f33dbb2535a3 361 ISL1208::DigitalTrim ISL1208::digitalTrim()
neilt6 0:697ca602e934 362 {
neilt6 0:697ca602e934 363 //Read the 8-bit register value
neilt6 0:697ca602e934 364 char value = read8(REG_CTL_DTR);
neilt6 0:697ca602e934 365
neilt6 0:697ca602e934 366 //Mask off the reserved bit
neilt6 0:697ca602e934 367 value &= ~(1 << 7);
neilt6 0:697ca602e934 368
neilt6 0:697ca602e934 369 //Return the value as a DigitalTrim enum
neilt6 0:697ca602e934 370 return (DigitalTrim)value;
neilt6 0:697ca602e934 371 }
neilt6 0:697ca602e934 372
neilt6 0:697ca602e934 373 void ISL1208::digitalTrim(DigitalTrim dtr)
neilt6 0:697ca602e934 374 {
neilt6 0:697ca602e934 375 //Read the current 8-bit register value (to preserve the reserved bit)
neilt6 0:697ca602e934 376 char value = read8(REG_CTL_DTR);
neilt6 0:697ca602e934 377
neilt6 0:697ca602e934 378 //Clear the old DTR bits
neilt6 0:697ca602e934 379 value &= 0xF8;
neilt6 0:697ca602e934 380
neilt6 0:697ca602e934 381 //Add the new DTR bits
neilt6 0:697ca602e934 382 value |= dtr;
neilt6 0:697ca602e934 383
neilt6 0:697ca602e934 384 //Write the value back out
neilt6 0:697ca602e934 385 write8(REG_CTL_DTR, value);
neilt6 0:697ca602e934 386 }
neilt6 0:697ca602e934 387
neilt6 2:f33dbb2535a3 388 time_t ISL1208::alarmTime()
neilt6 0:697ca602e934 389 {
neilt6 0:697ca602e934 390 //Setup a tm structure based on the RTC
neilt6 0:697ca602e934 391 struct tm timeinfo;
neilt6 0:697ca602e934 392
neilt6 0:697ca602e934 393 //MSB of each alarm register is an enable bit
neilt6 0:697ca602e934 394 timeinfo.tm_sec = bcd2bin(read8(REG_ALM_SCA) & 0x7F);
neilt6 0:697ca602e934 395 timeinfo.tm_min = bcd2bin(read8(REG_ALM_MNA) & 0x7F);
neilt6 0:697ca602e934 396 timeinfo.tm_hour = bcd2bin(read8(REG_ALM_HRA) & 0x3F);
neilt6 0:697ca602e934 397 timeinfo.tm_mday = bcd2bin(read8(REG_ALM_DTA) & 0x3F);
neilt6 0:697ca602e934 398 timeinfo.tm_mon = bcd2bin(read8(REG_ALM_MOA) & 0x1F) - 1;
neilt6 0:697ca602e934 399 timeinfo.tm_wday = bcd2bin(read8(REG_ALM_DWA) & 0x03);
neilt6 0:697ca602e934 400
neilt6 0:697ca602e934 401 //The alarm doesn't store the year, so get it from the RTC section
neilt6 0:697ca602e934 402 timeinfo.tm_year = bcd2bin(read8(REG_RTC_YR)) + 100;
neilt6 0:697ca602e934 403
neilt6 0:697ca602e934 404 //Return as a timestamp
neilt6 0:697ca602e934 405 return mktime(&timeinfo);
neilt6 0:697ca602e934 406 }
neilt6 0:697ca602e934 407
neilt6 0:697ca602e934 408 void ISL1208::alarmTime(time_t t, bool sc, bool mn, bool hr, bool dt, bool mo, bool dw)
neilt6 0:697ca602e934 409 {
neilt6 0:697ca602e934 410 //Convert the time to a tm
neilt6 0:697ca602e934 411 struct tm *timeinfo = localtime(&t);
neilt6 0:697ca602e934 412
neilt6 0:697ca602e934 413 //Write the new alarm time components (if enabled)
neilt6 0:697ca602e934 414 if (sc)
neilt6 0:697ca602e934 415 write8(REG_ALM_SCA, bin2bcd(timeinfo->tm_sec) | 0x80);
neilt6 0:697ca602e934 416 else
neilt6 0:697ca602e934 417 write8(REG_ALM_SCA, 0x0);
neilt6 0:697ca602e934 418 if (mn)
neilt6 0:697ca602e934 419 write8(REG_ALM_MNA, bin2bcd(timeinfo->tm_min) | 0x80);
neilt6 0:697ca602e934 420 else
neilt6 0:697ca602e934 421 write8(REG_ALM_MNA, 0x0);
neilt6 0:697ca602e934 422 if (hr)
neilt6 0:697ca602e934 423 write8(REG_ALM_HRA, bin2bcd(timeinfo->tm_hour) | 0x80);
neilt6 0:697ca602e934 424 else
neilt6 0:697ca602e934 425 write8(REG_ALM_HRA, 0x0);
neilt6 0:697ca602e934 426 if (hr)
neilt6 0:697ca602e934 427 write8(REG_ALM_DTA, bin2bcd(timeinfo->tm_mday) | 0x80);
neilt6 0:697ca602e934 428 else
neilt6 0:697ca602e934 429 write8(REG_ALM_DTA, 0x0);
neilt6 0:697ca602e934 430 if (mo)
neilt6 0:697ca602e934 431 write8(REG_ALM_MOA, bin2bcd(timeinfo->tm_mon + 1) | 0x80);
neilt6 0:697ca602e934 432 else
neilt6 0:697ca602e934 433 write8(REG_ALM_MOA, 0x0);
neilt6 0:697ca602e934 434 if (dw)
neilt6 0:697ca602e934 435 write8(REG_ALM_DWA, bin2bcd(timeinfo->tm_wday & 7) | 0x80);
neilt6 0:697ca602e934 436 else
neilt6 0:697ca602e934 437 write8(REG_ALM_DWA, 0x0);
neilt6 0:697ca602e934 438 }
neilt6 0:697ca602e934 439
neilt6 2:f33dbb2535a3 440 unsigned short ISL1208::sram()
neilt6 0:697ca602e934 441 {
neilt6 0:697ca602e934 442 //Return the complete contents of the SRAM
neilt6 0:697ca602e934 443 return read16(REG_USR_USR1);
neilt6 0:697ca602e934 444 }
neilt6 0:697ca602e934 445
neilt6 0:697ca602e934 446 void ISL1208::sram(unsigned short data)
neilt6 0:697ca602e934 447 {
neilt6 0:697ca602e934 448 //Write the complete contents of the SRAM
neilt6 0:697ca602e934 449 write16(REG_USR_USR1, data);
neilt6 0:697ca602e934 450 }
neilt6 0:697ca602e934 451
neilt6 0:697ca602e934 452 char ISL1208::read8(char reg)
neilt6 0:697ca602e934 453 {
neilt6 0:697ca602e934 454 //Select the register
neilt6 0:697ca602e934 455 m_I2C.write(m_ADDR, &reg, 1);
neilt6 0:697ca602e934 456
neilt6 0:697ca602e934 457 //Read the 8-bit register
neilt6 0:697ca602e934 458 m_I2C.read(m_ADDR, &reg, 1);
neilt6 0:697ca602e934 459
neilt6 0:697ca602e934 460 //Return the byte
neilt6 0:697ca602e934 461 return reg;
neilt6 0:697ca602e934 462 }
neilt6 0:697ca602e934 463
neilt6 0:697ca602e934 464 void ISL1208::write8(char reg, char data)
neilt6 0:697ca602e934 465 {
neilt6 0:697ca602e934 466 //Create a temporary buffer
neilt6 0:697ca602e934 467 char buff[2];
neilt6 0:697ca602e934 468
neilt6 0:697ca602e934 469 //Load the register address and 8-bit data
neilt6 0:697ca602e934 470 buff[0] = reg;
neilt6 0:697ca602e934 471 buff[1] = data;
neilt6 0:697ca602e934 472
neilt6 0:697ca602e934 473 //Write the data
neilt6 0:697ca602e934 474 m_I2C.write(m_ADDR, buff, 2);
neilt6 0:697ca602e934 475 }
neilt6 0:697ca602e934 476
neilt6 0:697ca602e934 477 unsigned short ISL1208::read16(char reg)
neilt6 0:697ca602e934 478 {
neilt6 0:697ca602e934 479 //Create a temporary buffer
neilt6 0:697ca602e934 480 char buff[2];
neilt6 0:697ca602e934 481
neilt6 0:697ca602e934 482 //Select the register
neilt6 0:697ca602e934 483 m_I2C.write(m_ADDR, &reg, 1);
neilt6 0:697ca602e934 484
neilt6 0:697ca602e934 485 //Read the 16-bit register
neilt6 0:697ca602e934 486 m_I2C.read(m_ADDR, buff, 2);
neilt6 0:697ca602e934 487
neilt6 0:697ca602e934 488 //Return the combined 16-bit value
neilt6 0:697ca602e934 489 return (buff[0] << 8) | buff[1];
neilt6 0:697ca602e934 490 }
neilt6 0:697ca602e934 491
neilt6 0:697ca602e934 492 void ISL1208::write16(char reg, unsigned short data)
neilt6 0:697ca602e934 493 {
neilt6 0:697ca602e934 494 //Create a temporary buffer
neilt6 0:697ca602e934 495 char buff[3];
neilt6 0:697ca602e934 496
neilt6 0:697ca602e934 497 //Load the register address and 16-bit data
neilt6 0:697ca602e934 498 buff[0] = reg;
neilt6 0:697ca602e934 499 buff[1] = data >> 8;
neilt6 0:697ca602e934 500 buff[2] = data;
neilt6 0:697ca602e934 501
neilt6 0:697ca602e934 502 //Write the data
neilt6 0:697ca602e934 503 m_I2C.write(m_ADDR, buff, 3);
neilt6 0:697ca602e934 504 }
neilt6 0:697ca602e934 505
neilt6 0:697ca602e934 506 unsigned int ISL1208::bcd2bin(unsigned char val)
neilt6 0:697ca602e934 507 {
neilt6 0:697ca602e934 508 return (val & 0x0F) + (val >> 4) * 10;
neilt6 0:697ca602e934 509 }
neilt6 0:697ca602e934 510
neilt6 0:697ca602e934 511 char ISL1208::bin2bcd(unsigned int val)
neilt6 0:697ca602e934 512 {
neilt6 0:697ca602e934 513 return ((val / 10) << 4) + val % 10;
neilt6 0:697ca602e934 514 }