Arduino library for the PCF8573 RTC I2C chip with Power Fail Detector.
The library makes it easy to set and read time, set alarm registers and access status flags of the PCF8573 chip.
In the Arduino IDE:
- Open LIBRARY MANAGER
- Search phrase
PCF8573 - Find the PCF8573 by Ignacy110 library in the list
- Click INSTALL
- Download the repository as .zip file.
- In the Arduino IDE, select: Sketch → Include Library → Add .ZIP Library...
- Select the downloaded .zip file.
The PCF8573 chip requires the following components:
- 32.768 kHz crystal oscillator - connected between OSCI and OSCO pins
- a trim capacitor can be added to fine-tune the precision of timekeeping - a trimmer is connected between OSCI and VDD pins
- SDA and SCL pull-up resistors (4.7 kΩ) - if your board does not have such resistors
- a 100 nF capacitor between VDD and VSS1
Warning
The 100 nF capacitor can be omitted, but this is not recommended. In the final version of the project with this or other integrated circuits it is worth including it.
| Symbol | Pin | Description | I/O | How to connect |
|---|---|---|---|---|
| A0 | 1 | address input | input | to GND |
| A1 | 2 | address input | input | to GND |
| COMP | 3 | comparator output | output | not connected |
| SDA | 4 | I2C SDA | transmission | to the SDA pin in your microcontroller |
| SCL | 5 | I2C SCL | transmission | to the SCL pin in your microcontroller |
| EXTPF | 6 | enable power fail flag input | input | to GND |
| PFIN | 7 | power fail flag input | input | to GND |
| VSS2 | 8 | GND for the I2C interface | power | to GND |
| MIN | 9 | one pulse per minute output | output | not connected |
| SEC | 10 | one pulse per second output | output | not connected |
| FSET | 11 | oscillator tuning output | output | not connected |
| TEST | 12 | test input | input | to GND |
| OSCI | 13 | oscillator input | osc. input | Crystal oscillator (32.768 kHz) |
| OSCO | 14 | oscillator input/output | osc. input/output | Crystal oscillator (32.768 kHz) |
| VSS1 | 15 | GND for the clock (RTC) | power | to GND |
| VDD | 16 | 5V (typical value) common positive supply | power | to VCC |
The last column shows the simplest way to connect the PCF8573 chip.
Note
If the outputs are not used they may not be connected.
Caution
Don't leave inputs unconnected to VCC or GND. Leaving inputs floating may cause incorrect system operation!
Depending on your application, you may connect the chip differently. For instance, output pins can be used to read the COMP flag or the one-second/one-minute pulses directly in hardware. Additionally, setting inputs to VCC instead of GND allows you to modify the PCF8573 I2C address or change the behavior of the Power Fail Detector.
The address of the PCF8573 chip is set via inputs A0 and A1. Table of assigned addresses:
| A1 input state | A0 input state | PCF8573 address |
|---|---|---|
| GND | GND | 0x68 |
| GND | VCC | 0x69 |
| VCC | GND | 0x6A |
| VCC | VCC | 0x6B |
To use this library, your application must include the <Wire.h> library, which enables I2C communication with the chip.
Include this library <PCF8573.h>.
Before using the library methods, you need to create an instance of the PCF8573 class e.g. PCF8573 rtc(0x68); where the parameter is the I2C address set via pins A0 and A1. In short this object represents the physical PCF8573 chip with a given address 0x68 connected via I2C.
To use the PCF8573, you must initialize the I2C communication by calling Wire.begin(); and Wire.setClock(100000); in the setup() function.
Example:
#include <Wire.h> // library required for I2C communication
#define WIRE_CLOCK 100000 // set the wire transmission clock
#include <PCF8573.h> // PCF8573 library
PCF8573 rtc(0x68); // create an rtc object with address of our PCF8573 chip
void setup()
{
Wire.begin(); // start I2C communication to communicate with PCF8573 chip
Wire.setClock(WIRE_CLOCK); // set defined wire transmission clock
}All available methods and their syntax are described in paragraph 4.
This program sets the time to 12:34 and displays it on the Serial Monitor (in Arduino IDE). You can see how minutes and later hours increment.
#include <Wire.h> // library required for I2C communication
#define WIRE_CLOCK 100000 // set the wire transmission clock
#include <PCF8573.h> // PCF8573 library
PCF8573 rtc(0x68); // create an rtc object with address of our PCF8573 chip
void setup()
{
Serial.begin(115200); // start serial communication for serial monitor
Wire.begin(); // start I2C communication to communicate with PCF8573 chip
Wire.setClock(WIRE_CLOCK); // set defined wire transmission clock
rtc.setTime(PCF8573::time::HOURS, 12); // setting hours
rtc.setTime(PCF8573::time::MINUTES, 34); // setting minutes
}
void loop()
{
Serial.print("\nHour:\t");
Serial.println(rtc.readTime(PCF8573::time::HOURS)); // display hours
Serial.print("Minute:\t");
Serial.println(rtc.readTime(PCF8573::time::MINUTES)); // display minutes
delay(5000);
}Tip
More examples are in the examples folder.
The PCF8573 allows you to:
- set and read the time
- set and read the alarm time
- set and read flags
- use additional control functions
Important
All methods provided by this library are member functions of the PCF8573 class.
Therefore they must be called using the created object, for example rtc.
You can use the following methods to perform these activities:
To set the time, use the setTime() method which requires a time field identifier and your value e.g. setTime(PCF8573::time::HOURS, 7) that means set the hours register to 7.
setTime() parameters:
| Function | setTime() | accepted values |
|---|---|---|
| Set hours | setTime(PCF8573::time::HOURS, value); |
0 to 23 |
| Set minutes | setTime(PCF8573::time::MINUTES, value); |
0 to 59 |
| Set days | setTime(PCF8573::time::DAYS, value); |
1 to 28 / 29 1 to 30 1 to 31 |
| Set months | setTime(PCF8573::time::MONTHS, value); |
1 to 12 |
Note
The DAYS register accepts values appropriate to the month.
Warning
Incorrect values sent may cause the chip to malfunction!
Important
Leap year support (February 29) must be handled externally because the PCF8573 does not have a year counter.
To read the time, use the readTime() method which requires a time field identifier e.g. readTime(PCF8573::time::MINUTES) that means read the minutes register. This method returns a uint8_t value.
readTime() parameters:
| Function | readTime() |
|---|---|
| Read hours | readTime(PCF8573::time::HOURS); |
| Read minutes | readTime(PCF8573::time::MINUTES); |
| Read days | readTime(PCF8573::time::DAYS); |
| Read months | readTime(PCF8573::time::MONTHS); |
The alarm works like an alarm clock. When the alarm time matches the current time, the COMP flag is set to 1, indicating that the hour has struck. More details in section 4.3 Flags operation.
To set the alarm time, use the setAlarmTime() method which requires a time field identifier and your value e.g. setAlarmTime(PCF8573::time::DAYS, 21) that means set the days alarm register to 21.
setAlarmTime() parameters:
| Function | setAlarmTime() | accepted values |
|---|---|---|
| Set alarm hours | setAlarmTime(PCF8573::time::HOURS, value); |
0 to 23 |
| Set alarm minutes | setAlarmTime(PCF8573::time::MINUTES, value); |
0 to 59 |
| Set alarm days | setAlarmTime(PCF8573::time::DAYS, value); |
1 to 28 / 29 1 to 30 1 to 31 |
| Set alarm months | setAlarmTime(PCF8573::time::MONTHS, value); |
1 to 12 |
To read the alarm time, use the readAlarmTime() method which requires a time field identifier e.g. readAlarmTime(PCF8573::time::MONTHS) that means read the months alarm register. This method returns a uint8_t value.
readAlarmTime() parameters:
| Function | readAlarmTime() |
|---|---|
| Read alarm hours | readAlarmTime(PCF8573::time::HOURS); |
| Read alarm minutes | readAlarmTime(PCF8573::time::MINUTES); |
| Read alarm days | readAlarmTime(PCF8573::time::DAYS); |
| Read alarm months | readAlarmTime(PCF8573::time::MONTHS); |
The PCF8573 chip has 3 flags:
| Flag | Description | Method of set (0 to 1) |
Method of reset (1 to 0) |
|---|---|---|---|
| POWF | The flag indicates a detected power failure (more information about Power Fail Detector and POWF flag in chapter 5) |
When a power failure occurs | By setting the time or alarm time |
| COMP | The flag indicates that the alarm has been triggered when the alarm time matches the current time. | When alarm time is the same as RTC time | By user |
| NODA | The flag says to ignore the date when comparing the alarm and time (when comparing it only looks at hours and minutes) | By user | By user |
To read the flag, use the readFlag() method which requires a time field identifier e.g. readFlag(PCF8573::flag::COMP) that means read the COMP flag register. This method returns a bool value.
readFlag() parameters:
| Function | readFlag() |
|---|---|
| Read POWF flag | readFlag(PCF8573::flag::POWF); |
| Read COMP flag | readFlag(PCF8573::flag::COMP); |
| Read NODA flag | readFlag(PCF8573::flag::NODA); |
To reset the flag, use the resetCOMPflag() or resetNODAflag() method. Reset means changing the state of the flag from 1 to 0.
To set the flag, use the setNODAflag() method. Set means changing the state of the flag from 0 to 1.
Note
Using methods for flags, you can:
- read one of three flags:
POWF,COMP,NODA; - reset one of two flags:
COMP,NODA; - set one:
NODA;
resetPrescaler() method - reset prescaler, including seconds counter, without affecting the minute counter
Tip
It is good to use resetPrescaler() method when you set minutes. Because this method resets the seconds counter so you can start counting minutes precisely from a given moment.
In your code:
rtc.setTime(PCF8573::time::HOURS, 9); // setting hours
rtc.setTime(PCF8573::time::MINUTES, 11); // setting minutes
rtc.resetPrescaler(); // resetting seconds counterIn this example you set time 09:11:00.
Without resetPrescaler() function you can set 09:11:xx where xx has the value at which the chip stopped counting (so random value).
Power Fail Detector sets the POWF flag to 1 when a power failure occurs.
There are two types of power failure detection - internal and external.
Internal mode: The flag indicates a detected power failure - VDD-VSS1 voltage reaches approximately 1.2V or less (Voltage of 1.2V due to the design of the PCF8573 chip to work with 1.2 V nickel cadmium battery).
External mode: To use external power failure detection, the EXTPF input must be at logic HIGH (e.g. connected to VCC).
The POWF flag is set based on the PFIN input. If it goes to LOW state, the system interprets it as a power failure.
| EXTPF input state | PFIN input state | Function |
|---|---|---|
| LOW | LOW | Power Fail Detector - Internal mode |
| LOW | HIGH | test mode - don't use |
| HIGH | LOW | Power Fail Detector - External mode - power supply failure detected |
| HIGH | HIGH | Power Fail Detector - External mode - power supply status correct |
Important
Power Fail Detector does not reset the POWF flag to 0. To reset this flag, you must set the time or alarm time.
This library was inspired by the PCF8574 Arduino library by MSZ98: https://github.com/MSZ98/pcf8574
It is an independent implementation for the PCF8573 RTC chip.