|
- /*
- * ds1302.c:
- * Real Time clock
- *
- * Copyright (c) 2013 Gordon Henderson.
- ***********************************************************************
- * This file is part of wiringPi:
- * https://projects.drogon.net/raspberry-pi/wiringpi/
- *
- * wiringPi is free software: you can redistribute it and/or modify
- * it under the terms of the GNU Lesser General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * wiringPi is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with wiringPi. If not, see <http://www.gnu.org/licenses/>.
- ***********************************************************************
- */
-
- #include <stdio.h>
- #include <stdlib.h>
- #include <stdint.h>
- #include <stdarg.h>
-
- #include <wiringPi.h>
-
- #include "ds1302.h"
-
- // Register defines
-
- #define RTC_SECS 0
- #define RTC_MINS 1
- #define RTC_HOURS 2
- #define RTC_DATE 3
- #define RTC_MONTH 4
- #define RTC_DAY 5
- #define RTC_YEAR 6
- #define RTC_WP 7
- #define RTC_TC 8
- #define RTC_BM 31
-
-
- // Locals
-
- static int dPin, cPin, sPin ;
-
- /*
- * dsShiftIn:
- * Shift a number in from the chip, LSB first. Note that the data is
- * sampled on the trailing edge of the last clock, so it's valid immediately.
- *********************************************************************************
- */
-
- static unsigned int dsShiftIn (void)
- {
- uint8_t value = 0 ;
- int i ;
-
- pinMode (dPin, INPUT) ; delayMicroseconds (1) ;
-
- for (i = 0 ; i < 8 ; ++i)
- {
- value |= (digitalRead (dPin) << i) ;
- digitalWrite (cPin, HIGH) ; delayMicroseconds (1) ;
- digitalWrite (cPin, LOW) ; delayMicroseconds (1) ;
- }
-
- return value;
- }
-
-
- /*
- * dsShiftOut:
- * A normal LSB-first shift-out, just slowed down a bit - the Pi is
- * a bit faster than the chip can handle.
- *********************************************************************************
- */
-
- static void dsShiftOut (unsigned int data)
- {
- int i ;
-
- pinMode (dPin, OUTPUT) ;
-
- for (i = 0 ; i < 8 ; ++i)
- {
- digitalWrite (dPin, data & (1 << i)) ; delayMicroseconds (1) ;
- digitalWrite (cPin, HIGH) ; delayMicroseconds (1) ;
- digitalWrite (cPin, LOW) ; delayMicroseconds (1) ;
- }
- }
-
-
- /*
- * ds1302regRead: ds1302regWrite:
- * Read/Write a value to an RTC Register or RAM location on the chip
- *********************************************************************************
- */
-
- static unsigned int ds1302regRead (const int reg)
- {
- unsigned int data ;
-
- digitalWrite (sPin, HIGH) ; delayMicroseconds (1) ;
- dsShiftOut (reg) ;
- data = dsShiftIn () ;
- digitalWrite (sPin, LOW) ; delayMicroseconds (1) ;
-
- return data ;
- }
-
- static void ds1302regWrite (const int reg, const unsigned int data)
- {
- digitalWrite (sPin, HIGH) ; delayMicroseconds (1) ;
- dsShiftOut (reg) ;
- dsShiftOut (data) ;
- digitalWrite (sPin, LOW) ; delayMicroseconds (1) ;
- }
-
-
- /*
- * ds1302rtcWrite: ds1302rtcRead:
- * Writes/Reads the data to/from the RTC register
- *********************************************************************************
- */
-
- unsigned int ds1302rtcRead (const int reg)
- {
- return ds1302regRead (0x81 | ((reg & 0x1F) << 1)) ;
- }
-
- void ds1302rtcWrite (int reg, unsigned int data)
- {
- ds1302regWrite (0x80 | ((reg & 0x1F) << 1), data) ;
- }
-
-
- /*
- * ds1302ramWrite: ds1302ramRead:
- * Writes/Reads the data to/from the RTC register
- *********************************************************************************
- */
-
- unsigned int ds1302ramRead (const int addr)
- {
- return ds1302regRead (0xC1 | ((addr & 0x1F) << 1)) ;
- }
-
- void ds1302ramWrite (const int addr, const unsigned int data)
- {
- ds1302regWrite ( 0xC0 | ((addr & 0x1F) << 1), data) ;
- }
-
- /*
- * ds1302clockRead:
- * Read all 8 bytes of the clock in a single operation
- *********************************************************************************
- */
-
- void ds1302clockRead (int clockData [8])
- {
- int i ;
- unsigned int regVal = 0x81 | ((RTC_BM & 0x1F) << 1) ;
-
- digitalWrite (sPin, HIGH) ; delayMicroseconds (1) ;
-
- dsShiftOut (regVal) ;
- for (i = 0 ; i < 8 ; ++i)
- clockData [i] = dsShiftIn () ;
-
- digitalWrite (sPin, LOW) ; delayMicroseconds (1) ;
- }
-
-
- /*
- * ds1302clockWrite:
- * Write all 8 bytes of the clock in a single operation
- *********************************************************************************
- */
-
- void ds1302clockWrite (const int clockData [8])
- {
- int i ;
- unsigned int regVal = 0x80 | ((RTC_BM & 0x1F) << 1) ;
-
- digitalWrite (sPin, HIGH) ; delayMicroseconds (1) ;
-
- dsShiftOut (regVal) ;
- for (i = 0 ; i < 8 ; ++i)
- dsShiftOut (clockData [i]) ;
-
- digitalWrite (sPin, LOW) ; delayMicroseconds (1) ;
- }
-
-
- /*
- * ds1302trickleCharge:
- * Set the bits on the trickle charger.
- * Probably best left alone...
- *********************************************************************************
- */
-
- void ds1302trickleCharge (const int diodes, const int resistors)
- {
- if (diodes + resistors == 0)
- ds1302rtcWrite (RTC_TC, 0x5C) ; // Disabled
- else
- ds1302rtcWrite (RTC_TC, 0xA0 | ((diodes & 3) << 2) | (resistors & 3)) ;
- }
-
-
-
-
- /*
- * ds1302setup:
- * Initialise the chip & remember the pins we're using
- *********************************************************************************
- */
-
- void ds1302setup (const int clockPin, const int dataPin, const int csPin)
- {
- dPin = dataPin ;
- cPin = clockPin ;
- sPin = csPin ;
-
- digitalWrite (dPin, LOW) ;
- digitalWrite (cPin, LOW) ;
- digitalWrite (sPin, LOW) ;
-
- pinMode (dPin, OUTPUT) ;
- pinMode (cPin, OUTPUT) ;
- pinMode (sPin, OUTPUT) ;
-
- ds1302rtcWrite (RTC_WP, 0) ; // Remove write-protect
- }
|