top of page

Accessing I2C Real-Time Clock (RTC) from Linux

May 30, 2024

3 min read

1

161

I2C Real-Time Clocks (RTCs) play a crucial role in embedded systems, providing accurate timekeeping capabilities for applications ranging from data logging to scheduling tasks. Linux offers robust support for interfacing with I2C RTCs, enabling developers to read and set the system time, configure alarms, and implement time-sensitive functionality seamlessly. This article serves as a comprehensive guide on accessing I2C RTCs from Linux, covering device detection, driver selection, sysfs interface usage, and example code snippets.


1. Understanding I2C RTCs:

I2C RTCs are specialized ICs designed to maintain accurate timekeeping information, including date, time, and alarms, using the Inter-Integrated Circuit (I2C) communication protocol. These RTCs typically feature a battery backup to ensure continuous operation in the event of a power loss, making them ideal for applications requiring reliable timekeeping functionality.


2. Device Detection and Identification:

Before accessing an I2C RTC from Linux, it's essential to detect and identify the RTC connected to the I2C bus. Linux provides utilities like "i2cdetect" to scan the I2C bus and identify active devices. By running "i2cdetect -y <bus_number>", users can identify the address of the connected I2C RTC.


3. Kernel Driver Selection:

Linux offers several kernel drivers for managing I2C RTCs, including generic drivers like "rtc-ds1307" and vendor-specific drivers tailored to specific RTC ICs. Choose an appropriate kernel driver based on the target RTC and system requirements.


4. Sysfs Interface Usage:

The sysfs interface in Linux provides a convenient mechanism for interacting with I2C RTCs, offering virtual files for reading and setting date/time information, configuring alarms, and monitoring RTC status. By navigating the sysfs hierarchy, users can access and manipulate RTC data using standard file I/O operations.


5. Example Code Snippets:

Below are example code snippets demonstrating how to read and set the system time using an I2C RTC from a Linux userspace application:


Example 1: Reading Current System Time from I2C RTC


#include <stdio.h>

#include <fcntl.h>

#include <unistd.h>

#include <sys/ioctl.h>

#include <linux/i2c-dev.h>

#include <linux/rtc.h>


#define RTC_ADDRESS 0x68


int main()

{

int file;

struct rtc_time rtc_tm;


// Open I2C bus

file = open("/dev/i2c-0", O_RDWR);

if (file < 0) {

perror("Failed to open I2C bus");

return 1;

}


// Set RTC address

if (ioctl(file, I2C_SLAVE, RTC_ADDRESS) < 0) {

perror("Failed to set I2C address");

close(file);

return 1;

}


// Read RTC time

if (ioctl(file, RTC_RD_TIME, &rtc_tm) < 0) {

perror("Failed to read RTC time");

close(file);

return 1;

}


printf("Current RTC Time: %02d:%02d:%02d\n", rtc_tm.tm_hour, rtc_tm.tm_min, rtc_tm.tm_sec);


close(file);

return 0;

}



Example 2: Setting System Time using I2C RTC


#include <stdio.h>

#include <fcntl.h>

#include <unistd.h>

#include <sys/ioctl.h>

#include <linux/i2c-dev.h>

#include <linux/rtc.h>


#define RTC_ADDRESS 0x68


int main()

{

int file;

struct rtc_time rtc_tm;


// Open I2C bus

file = open("/dev/i2c-0", O_RDWR);

if (file < 0) {

perror("Failed to open I2C bus");

return 1;

}


// Set RTC address

if (ioctl(file, I2C_SLAVE, RTC_ADDRESS) < 0) {

perror("Failed to set I2C address");

close(file);

return 1;

}


// Set new RTC time (e.g., 10:30:00)

rtc_tm.tm_sec = 0;

rtc_tm.tm_min = 30;

rtc_tm.tm_hour = 10;


if (ioctl(file, RTC_SET_TIME, &rtc_tm) < 0) {

perror("Failed to set RTC time");

close(file);

return 1;

}


printf("RTC Time Set Successfully\n");


close(file);

return 0;

}


Accessing I2C RTCs from Linux involves device detection, kernel driver selection, and leveraging the sysfs interface for interacting with RTC data. With the provided guidance and example code snippets, developers can integrate RTC functionality into Linux-based embedded systems effectively, enabling reliable timekeeping and scheduling capabilities for various applications.


#linuxdevicedrivers #ldd #linuxlovers



May 30, 2024

3 min read

1

161

bottom of page