diff options
author | Simon Glass <sjg@chromium.org> | 2021-01-22 16:10:20 -0700 |
---|---|---|
committer | Commit Bot <commit-bot@chromium.org> | 2021-02-02 09:27:32 +0000 |
commit | 086efb5aaab014a31ef2bd1ee54662e4698b522d (patch) | |
tree | 9271fe7fc75def695add371cf546c7c5f4e6bc4e | |
parent | 53a4c4aaeb1cc1ced18cd2d308a7005c25cbf547 (diff) | |
download | chrome-ec-086efb5aaab014a31ef2bd1ee54662e4698b522d.tar.gz |
zephyr: Enable base support for real-time-clock (RTC)
Add Kconfig options for the various RTC features. Add stubs for the
actual implementation, to be implemented using Zephyr API calls to the
RTC driver, when available.
The duplication of RTC functions across different chips can be
addressed in b/179055201
Also add the <init.h> header to zephyr_host_command.h since otherwise
we get a build error. It seems better to have the header there than in
the files that use DECLARE_CONSOLE_COMMAND().
BUG=b:178230662, b:179055201
BRANCH=none
TEST=build volteer for zephyr, try rtc and rtc_alarm command
make BOARD=volteer -j8
Change-Id: I036b1f3d91543a357ad779e475a03584759a3de4
Signed-off-by: Simon Glass <sjg@chromium.org>
Reviewed-on: https://chromium-review.googlesource.com/c/chromiumos/platform/ec/+/2645570
Reviewed-by: Yuval Peress <peress@chromium.org>
Commit-Queue: Yuval Peress <peress@chromium.org>
-rw-r--r-- | common/rtc.c | 3 | ||||
-rw-r--r-- | zephyr/Kconfig | 54 | ||||
-rw-r--r-- | zephyr/shim/include/config_chip.h | 20 | ||||
-rw-r--r-- | zephyr/shim/include/zephyr_host_command.h | 2 | ||||
-rw-r--r-- | zephyr/shim/src/CMakeLists.txt | 1 | ||||
-rw-r--r-- | zephyr/shim/src/rtc.c | 167 |
6 files changed, 246 insertions, 1 deletions
diff --git a/common/rtc.c b/common/rtc.c index 8a2fbc7139..670e86d707 100644 --- a/common/rtc.c +++ b/common/rtc.c @@ -9,7 +9,8 @@ #include "rtc.h" static uint16_t days_since_year_start[12] = { -0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334}; + 0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334 +}; /* Conversion between calendar date and seconds eclapsed since 1970-01-01 */ uint32_t date_to_sec(struct calendar_date time) diff --git a/zephyr/Kconfig b/zephyr/Kconfig index 6b5f9e8ec5..002dbcaa9c 100644 --- a/zephyr/Kconfig +++ b/zephyr/Kconfig @@ -413,6 +413,60 @@ config PLATFORM_EC_PWM support variable brightness LEDs, backlight controls, and variable-speed fans. +config PLATFORM_EC_RTC + bool "Real-time clock (RTC)" + default y + help + Enable support for a real-time clock. Typically this is available + on-chip in the EC. It provides a way to track the passage of time + in terms of second and minutes. Once set, and provided that it has a + suitable power source, it should be able to keep reasonably accurate + time over a period of days and weeks. + + The starting EC clock is typically set by the AP, since it has access + to the outside world and can often obtain the current time when + desired. + +if PLATFORM_EC_RTC + +config PLATFORM_EC_CONSOLE_CMD_RTC + bool "Console command: rtc" + default y + help + This command allows getting and setting the current RTC value. The + value is in seconds since the Epoch (midnight on 1/1/70). You can + convert this to a human date on the command line with 'date -u -d @n' + where n is the numeric value. To convert a time to seconds, use: + + date -d '1970-01-01 UTC + n seconds' + +config PLATFORM_EC_CONSOLE_CMD_RTC_ALARM + bool "Console command: rtc_alarm" + depends on PLATFORM_EC_CONSOLE_CMD_RTC + default y + help + This command supports setting a real-time-clock (RTC) alarm that + causes an interrupt when the timer reaches that point. To set the + alarm: + + rtc <sec> [<usec>] + + where: + <sec> is the number of seconds since the epoch + <usec> is the optional number of microseconds (fractional seconds) + +config PLATFORM_EC_HOSTCMD_RTC + bool "Host command: EC_CMD_RTC_GET_VALUE etc." + depends on PLATFORM_EC_HOSTCMD + default y + help + Enables support for EC_CMD_RTC_GET_VALUE, EC_CMD_RTC_SET_VALUE, + EC_CMD_RTC_GET_ALARM and EC_CMD_RTC_SET_ALARM which colectively allow + the AP to control the EC's real-time-clock. The AP typically makes + use of the EC's RTC to avoid needing a discrete RTC chip on the board. + +endif # PLATFORM_EC_RTC + config PLATFORM_EC_CONSOLE_CMD_SHMEM bool "Console command: shmem" default y diff --git a/zephyr/shim/include/config_chip.h b/zephyr/shim/include/config_chip.h index bf03614453..db5e5ad1b4 100644 --- a/zephyr/shim/include/config_chip.h +++ b/zephyr/shim/include/config_chip.h @@ -850,4 +850,24 @@ enum battery_type { #define CONFIG_CMD_STACKOVERFLOW #endif +#undef CONFIG_RTC +#ifdef CONFIG_PLATFORM_EC_RTC +#define CONFIG_RTC +#endif + +#undef CONFIG_CMD_RTC +#ifdef CONFIG_PLATFORM_EC_CONSOLE_CMD_RTC +#define CONFIG_CMD_RTC +#endif + +#undef CONFIG_CMD_RTC_ALARM +#ifdef CONFIG_PLATFORM_EC_CONSOLE_CMD_RTC_ALARM +#define CONFIG_CMD_RTC_ALARM +#endif + +#undef CONFIG_HOSTCMD_RTC +#ifdef CONFIG_PLATFORM_EC_HOSTCMD_RTC +#define CONFIG_HOSTCMD_RTC +#endif + #endif /* __CROS_EC_CONFIG_CHIP_H */ diff --git a/zephyr/shim/include/zephyr_host_command.h b/zephyr/shim/include/zephyr_host_command.h index 5ac93bae6e..d8ee0c2c9b 100644 --- a/zephyr/shim/include/zephyr_host_command.h +++ b/zephyr/shim/include/zephyr_host_command.h @@ -10,6 +10,8 @@ #endif #define __CROS_EC_ZEPHYR_HOST_COMMAND_H +#include <init.h> + /** Node in a list of host-command handlers */ struct zshim_host_command_node { struct host_command *cmd; diff --git a/zephyr/shim/src/CMakeLists.txt b/zephyr/shim/src/CMakeLists.txt index 1a4a75025e..c0cf045fd4 100644 --- a/zephyr/shim/src/CMakeLists.txt +++ b/zephyr/shim/src/CMakeLists.txt @@ -16,6 +16,7 @@ zephyr_sources_ifdef(CONFIG_PLATFORM_EC_HOSTCMD host_command.c) zephyr_sources_ifdef(CONFIG_PLATFORM_EC_MKBP_EVENT mkbp_event.c) zephyr_sources_ifdef(CONFIG_PLATFORM_EC_PANIC panic.c) zephyr_sources_ifdef(CONFIG_PLATFORM_EC_PWM pwm.c) +zephyr_sources_ifdef(CONFIG_PLATFORM_EC_RTC rtc.c) zephyr_sources_ifdef(CONFIG_PLATFORM_EC_TIMER hwtimer.c) zephyr_sources_ifdef(CONFIG_PLATFORM_EC_I2C i2c.c) zephyr_sources_ifdef(CONFIG_CROS_EC system.c) diff --git a/zephyr/shim/src/rtc.c b/zephyr/shim/src/rtc.c new file mode 100644 index 0000000000..9c9d8c30ae --- /dev/null +++ b/zephyr/shim/src/rtc.c @@ -0,0 +1,167 @@ +/* Copyright 2021 The Chromium OS Authors. All rights reserved. + * Use of this source code is governed by a BSD-style license that can be + * found in the LICENSE file. + */ + +#include <kernel.h> +#include <zephyr.h> + +#include "console.h" +#include "host_command.h" +#include "util.h" + +/* + * Microseconds will be ignored. The WTC register only + * stores wakeup time in seconds. + * Set seconds = 0 to disable the alarm + */ +void system_set_rtc_alarm(uint32_t seconds, uint32_t microseconds) +{ + /* TODO(b/178230662): Implement this */ +} + +void system_reset_rtc_alarm(void) +{ + /* TODO(b/178230662): Implement this */ +} + +/* + * Return the seconds remaining before the RTC alarm goes off. + * Returns 0 if alarm is not set. + */ +uint32_t system_get_rtc_alarm(void) +{ + /* + * Return 0: + * 1. If alarm is not set to go off, OR + * 2. If alarm is set and has already gone off + */ + + /* TODO(b/178230662): Implement this */ + return 0; +} + +/* MTC functions */ +uint32_t system_get_rtc_sec(void) +{ + /* TODO(b/178230662): Implement this */ + return 0; +} + +void system_set_rtc(uint32_t seconds) +{ + /* TODO(b/178230662): Implement this */ +} + +/* Console commands */ +void print_system_rtc(enum console_channel ch) +{ + uint32_t sec = system_get_rtc_sec(); + + cprintf(ch, "RTC: 0x%08x (%d.00 s)\n", sec, sec); +} + +/* + * TODO(b/179055201): This is similar to the same function in some of the + * chip-specific code. We should factor out the common parts. + */ +#ifdef CONFIG_PLATFORM_EC_CONSOLE_CMD_RTC +static int command_system_rtc(int argc, char **argv) +{ + if (argc == 3 && !strcasecmp(argv[1], "set")) { + char *e; + unsigned int t = strtoi(argv[2], &e, 0); + + if (*e) + return EC_ERROR_PARAM2; + + system_set_rtc(t); + } else if (argc > 1) { + return EC_ERROR_INVAL; + } + + print_system_rtc(CC_COMMAND); + + return EC_SUCCESS; +} +DECLARE_CONSOLE_COMMAND(rtc, command_system_rtc, "[set <seconds>]", + "Get/set real-time clock"); + +#ifdef CONFIG_PLATFORM_EC_CONSOLE_CMD_RTC_ALARM +/** + * Test the RTC alarm by setting an interrupt on RTC match. + */ +static int command_rtc_alarm_test(int argc, char **argv) +{ + int s = 1, us = 0; + char *e; + + ccprintf("Setting RTC alarm\n"); + /* TODO(b/178230662): Implement enabling RTC interrupt */ + + if (argc > 1) { + s = strtoi(argv[1], &e, 10); + if (*e) + return EC_ERROR_PARAM1; + } + if (argc > 2) { + us = strtoi(argv[2], &e, 10); + if (*e) + return EC_ERROR_PARAM2; + } + + system_set_rtc_alarm(s, us); + + return EC_SUCCESS; +} +DECLARE_CONSOLE_COMMAND(rtc_alarm, command_rtc_alarm_test, + "[seconds [microseconds]]", "Test alarm"); +#endif /* CONFIG_PLATFORM_EC_CONSOLE_CMD_RTC_ALARM */ +#endif /* CONFIG_PLATFORM_EC_CONSOLE_CMD_RTC */ + +#ifdef CONFIG_PLATFORM_EC_HOSTCMD_RTC +static enum ec_status system_rtc_get_value(struct host_cmd_handler_args *args) +{ + struct ec_response_rtc *r = args->response; + + r->time = system_get_rtc_sec(); + args->response_size = sizeof(*r); + + return EC_RES_SUCCESS; +} +DECLARE_HOST_COMMAND(EC_CMD_RTC_GET_VALUE, system_rtc_get_value, + EC_VER_MASK(0)); + +static enum ec_status system_rtc_set_value(struct host_cmd_handler_args *args) +{ + const struct ec_params_rtc *p = args->params; + + system_set_rtc(p->time); + return EC_RES_SUCCESS; +} +DECLARE_HOST_COMMAND(EC_CMD_RTC_SET_VALUE, system_rtc_set_value, + EC_VER_MASK(0)); + +static enum ec_status system_rtc_set_alarm(struct host_cmd_handler_args *args) +{ + const struct ec_params_rtc *p = args->params; + + system_set_rtc_alarm(p->time, 0); + return EC_RES_SUCCESS; +} +DECLARE_HOST_COMMAND(EC_CMD_RTC_SET_ALARM, system_rtc_set_alarm, + EC_VER_MASK(0)); + +static enum ec_status system_rtc_get_alarm(struct host_cmd_handler_args *args) +{ + struct ec_response_rtc *r = args->response; + + r->time = system_get_rtc_alarm(); + args->response_size = sizeof(*r); + + return EC_RES_SUCCESS; +} +DECLARE_HOST_COMMAND(EC_CMD_RTC_GET_ALARM, system_rtc_get_alarm, + EC_VER_MASK(0)); + +#endif /* CONFIG_PLATFORM_EC_HOSTCMD_RTC */ |