Skip to content

Commit

Permalink
drivers: rtc: rpi_pico: Add support for the Raspberry Pi Pico RTC
Browse files Browse the repository at this point in the history
This adds the minimal get_time/set_time support for the rp2040 and
enables support by default on the Pico boards. This doesn't support
configuring the clock source or alarm interrupts yet.

Signed-off-by: Andrew Featherstone <andrew.featherstone@gmail.com>
  • Loading branch information
ajf58 committed Nov 7, 2023
1 parent ec52722 commit 6526cfb
Show file tree
Hide file tree
Showing 9 changed files with 148 additions and 0 deletions.
5 changes: 5 additions & 0 deletions boards/arm/rpi_pico/rpi_pico-common.dtsi
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,11 @@
status = "okay";
};

&rtc {
clocks = <&xtal_clk>;
status = "okay";
};

&adc {
status = "okay";
pinctrl-0 = <&adc_default>;
Expand Down
1 change: 1 addition & 0 deletions drivers/rtc/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -17,3 +17,4 @@ zephyr_library_sources_ifdef(CONFIG_RTC_SHELL rtc_shell.c)
zephyr_library_sources_ifdef(CONFIG_RTC_FAKE rtc_fake.c)
zephyr_library_sources_ifdef(CONFIG_RTC_SMARTBOND rtc_smartbond.c)
zephyr_library_sources_ifdef(CONFIG_RTC_ATMEL_SAM rtc_sam.c)
zephyr_library_sources_ifdef(CONFIG_RTC_RPI_PICO rtc_rpi_pico.c)
1 change: 1 addition & 0 deletions drivers/rtc/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -51,5 +51,6 @@ source "drivers/rtc/Kconfig.mc146818"
source "drivers/rtc/Kconfig.sam"
source "drivers/rtc/Kconfig.stm32"
source "drivers/rtc/Kconfig.smartbond"
source "drivers/rtc/Kconfig.rpi_pico"

endif # RTC
9 changes: 9 additions & 0 deletions drivers/rtc/Kconfig.rpi_pico
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
# Copyright (c) 2023 Andrew Featherstone
# SPDX-License-Identifier: Apache-2.0

config RTC_RPI_PICO
bool "Raspberry Pi Pico RTC driver"
default y
depends on DT_HAS_RASPBERRYPI_PICO_RTC_ENABLED
select PICOSDK_USE_RTC
depends on RESET
102 changes: 102 additions & 0 deletions drivers/rtc/rtc_rpi_pico.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
/*
* SPDX-License-Identifier: Apache-2.0
*/


#include <zephyr/drivers/rtc.h>
#include <zephyr/irq.h>
#include <zephyr/kernel.h>
#include <zephyr/logging/log.h>

#include <hardware/rtc.h>

#define DT_DRV_COMPAT raspberrypi_pico_rtc

/* struct tm start time: 1st, Jan, 1900 */
#define TM_YEAR_REF 1900

struct rtc_rpi_pico_data {
struct k_mutex lock;
};

LOG_MODULE_REGISTER(rtc_rpi, CONFIG_RTC_LOG_LEVEL);

static int rtc_rpi_pico_init(const struct device *dev)
{
struct rtc_rpi_pico_data *data = dev->data;

k_mutex_init(&data->lock);
rtc_init();
return 0;
}

static int rtc_rpi_pico_set_time(const struct device *dev, const struct rtc_time *timeptr)
{
struct rtc_rpi_pico_data *data = dev->data;

int16_t real_year = (int16_t)timeptr->tm_year + TM_YEAR_REF;

if (real_year > 4095) {
return -EINVAL;
}

if (timeptr->tm_wday == -1) {
/* day of the week is expected */
return -EINVAL;
}

LOG_INF("Setting clock");

datetime_t time = {
.year = real_year,
.month = timeptr->tm_mon + 1,
.day = timeptr->tm_mday,
.dotw = timeptr->tm_wday,
.hour = timeptr->tm_hour,
.min = timeptr->tm_min,
.sec = timeptr->tm_sec,
};

int err = k_mutex_lock(&data->lock, K_FOREVER);
if (err) {

Check warning on line 61 in drivers/rtc/rtc_rpi_pico.c

View workflow job for this annotation

GitHub Actions / Run compliance checks on patch series (PR)

LINE_SPACING

drivers/rtc/rtc_rpi_pico.c:61 Missing a blank line after declarations
return err;
}
if (!rtc_set_datetime(&time)) {
err = -EINVAL;
}
k_mutex_unlock(&data->lock);

return err;
}

static int rtc_rpi_pico_get_time(const struct device *dev, struct rtc_time *timeptr)
{
datetime_t time;
if (!rtc_get_datetime(&time)) {

Check warning on line 75 in drivers/rtc/rtc_rpi_pico.c

View workflow job for this annotation

GitHub Actions / Run compliance checks on patch series (PR)

LINE_SPACING

drivers/rtc/rtc_rpi_pico.c:75 Missing a blank line after declarations
return -EINVAL;
}

timeptr->tm_sec = time.sec;
timeptr->tm_min = time.min;
timeptr->tm_hour = time.hour;
timeptr->tm_mday = time.day;
timeptr->tm_mon = time.month - 1;
timeptr->tm_year = time.year - TM_YEAR_REF;
timeptr->tm_wday = time.dotw;
/* unknown values */
timeptr->tm_yday = -1;
timeptr->tm_isdst = -1;
timeptr->tm_nsec = 0;

return 0;
}

static const struct rtc_driver_api rtc_rpi_pico_driver_api = {
.set_time = rtc_rpi_pico_set_time,
.get_time = rtc_rpi_pico_get_time,
};

static struct rtc_rpi_pico_data rtc_data;

DEVICE_DT_INST_DEFINE(0, &rtc_rpi_pico_init, NULL, &rtc_data, NULL, POST_KERNEL,
CONFIG_RTC_INIT_PRIORITY, &rtc_rpi_pico_driver_api);
8 changes: 8 additions & 0 deletions dts/arm/rpi_pico/rp2040.dtsi
Original file line number Diff line number Diff line change
Expand Up @@ -241,6 +241,14 @@
resets = <&reset RPI_PICO_RESETS_RESET_PIO1>;
status = "disabled";
};

rtc: rtc@4005c000 {
compatible = "raspberrypi,pico-rtc";
reg = <0x4005c000 DT_SIZE_K(4)>;
interrupts = <25 RPI_PICO_DEFAULT_IRQ_PRIORITY>;
resets = <&reset RPI_PICO_RESETS_RESET_RTC>;
status = "disabled";
};
};

pinctrl: pin-controller {
Expand Down
12 changes: 12 additions & 0 deletions dts/bindings/rtc/raspberrypi,pico-rtc.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
# Copyright (c) 2023 Andrew Featherstone <andrew.featherstone@gmail.com>
# SPDX-License-Identifier: Apache-2.0

description: RaspberryPi Pico RTC

compatible: "raspberrypi,pico-rtc"

include: [rtc.yaml, reset-device.yaml]

properties:
reg:
required: true
5 changes: 5 additions & 0 deletions modules/hal_rpi_pico/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -115,6 +115,11 @@ if(CONFIG_HAS_RPI_PICO)
zephyr_include_directories_ifdef(CONFIG_PICOSDK_USE_CLAIM
${rp2_common_dir}/hardware_claim/include)

zephyr_library_sources_ifdef(CONFIG_PICOSDK_USE_RTC
${rp2_common_dir}/hardware_rtc/rtc.c)
zephyr_include_directories_ifdef(CONFIG_PICOSDK_USE_RTC
${rp2_common_dir}/hardware_rtc/include)

# Some flash driver functions must be executed from the RAM.
# Originally pico-sdk places them in the RW data section, so this
# implementation does the same.
Expand Down
5 changes: 5 additions & 0 deletions modules/hal_rpi_pico/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -49,3 +49,8 @@ config PICOSDK_USE_TIMER
bool
help
Use the TIMER driver from pico-sdk

config PICOSDK_USE_RTC
bool
help
Use the RTC driver from pico-sdk

0 comments on commit 6526cfb

Please sign in to comment.