Merge pull request #796 from kernelkit/rtc

Support for save/restore system clock from file
This commit is contained in:
Joachim Wiberg
2024-11-05 13:05:59 +01:00
committed by GitHub
19 changed files with 761 additions and 23 deletions
+8
View File
@@ -33,6 +33,14 @@
};
};
/*
* RTC has no valid bit, and this board does not connect any
* backup power (e.g. supercap) to it, so it returns garbage
* after every cold reset.
*/
&cp0_rtc {
status = "disabled";
};
/* UART0 (Console) */
+49
View File
@@ -106,6 +106,8 @@ config QEMU_DTB_EXTEND
depends on QEMU_LOADER_UBOOT
default y if QEMU_aarch64
if QEMU_ROOTFS_INITRD
config QEMU_RW
string "Writable /cfg layer"
depends on QEMU_ROOTFS_INITRD
@@ -123,6 +125,8 @@ config QEMU_RW_VAR
default "var.ext4"
endif
endif
config QEMU_VPD
bool "Emulate a Vital Product Data (VPD) Memory"
@@ -137,6 +141,51 @@ config QEMU_APPEND
config QEMU_EXTRA
string "Extra QEMU options"
comment "RTC"
choice
prompt "Mode"
default QEMU_RTC_UTC
config QEMU_RTC_UTC
bool "UTC"
config QEMU_RTC_LOCAL
bool "Local time"
config QEMU_RTC_RANDOM
bool "Random"
endchoice
choice
prompt "Clock"
default QEMU_CLOCK_HOST
config QEMU_CLOCK_HOST
bool "Host clock"
config QEMU_CLOCK_RT
bool "Independent (monotonic)"
config QEMU_CLOCK_VM
bool "Virtual"
endchoice
config QEMU_RTC
string
default "utc" if QEMU_RTC_UTC
default "localtime" if QEMU_RTC_LOCAL
default "random" if QEMU_RTC_RANDOM
config QEMU_CLOCK
string
default "host" if QEMU_CLOCK_HOST
default "rt" if QEMU_CLOCK_RT
default "vm" if QEMU_CLOCK_VM
comment "Networking"
choice
+36 -7
View File
@@ -261,7 +261,25 @@ EOF
wdt_args()
{
echo -n "-device i6300esb -rtc clock=host"
echo -n "-device i6300esb "
}
random_date()
{
rand=$(($(date +%_s) * $$ + $(date +%N | sed 's/^0*//')))
when=$((rand % 7258118400)) # 1970 - 2200
date -d "@$when" +"%Y-%m-%dT%H:%M:%S"
}
rtc_args()
{
rtc="${CONFIG_QEMU_RTC:-utc}"
clock="${CONFIG_QEMU_CLOCK:-host}"
if [ "$rtc" = "random" ]; then
rtc=$(random_date)
fi
echo -n "-rtc base=$rtc,clock=$clock"
}
gdb_args()
@@ -273,11 +291,19 @@ gdb_args()
run_qemu()
{
if [ "$CONFIG_QEMU_ROOTFS_VSCSI" = "y" ]; then
qemu-img create -f qcow2 -o backing_file=$CONFIG_QEMU_ROOTFS -F raw $CONFIG_QEMU_ROOTFS.qcow2 > /dev/null
if ! qemu-img check "${CONFIG_QEMU_ROOTFS}.qcow2"; then
rm -f "${CONFIG_QEMU_ROOTFS}.qcow2"
fi
if [ ! -f "${CONFIG_QEMU_ROOTFS}.qcow2" ]; then
echo "Creating qcow2 disk image for Qemu ..."
qemu-img create -f qcow2 -o backing_file="$CONFIG_QEMU_ROOTFS" \
-F raw "${CONFIG_QEMU_ROOTFS}.qcow2" > /dev/null
fi
fi
local qemu
read qemu <<EOF
$CONFIG_QEMU_MACHINE -m $CONFIG_QEMU_MACHINE_RAM \
$CONFIG_QEMU_MACHINE -nodefaults -m $CONFIG_QEMU_MACHINE_RAM \
$(loader_args) \
$(rootfs_args) \
$(serial_args) \
@@ -286,16 +312,23 @@ run_qemu()
$(host_args) \
$(net_args) \
$(wdt_args) \
$(rtc_args) \
$(vpd_args) \
$(gdb_args) \
$CONFIG_QEMU_EXTRA
EOF
echo "Starting Qemu :: Ctrl-a x -- exit | Ctrl-a c -- toggle console/monitor"
line=$(stty -g)
stty raw
if [ "$CONFIG_QEMU_KERNEL" ]; then
$qemu -append "$(append_args)" "$@"
else
$qemu "$@"
fi
stty "$line"
}
dtb_args()
@@ -401,8 +434,4 @@ fi
generate_dot
echo "Starting Qemu :: Ctrl-a x -- exit | Ctrl-a c -- toggle console/monitor"
line=$(stty -g)
stty raw
run_qemu $(dtb_args)
stty "$line"
+1 -1
View File
@@ -146,7 +146,7 @@ mount_overlay home "$cfgsrc" /home
mount_overlay root "$cfgsrc" /root
mount_bind "$varsrc" /var
[ "$vlibsrc" ] && mount_bind "$vlibsrc" /var/lib
[ -n "$vlibsrc" ] && mount_bind "$vlibsrc" /var/lib
for tag in $(ls /sys/bus/virtio/devices/*/mount_tag 2>/dev/null); do
if [ "$(cat $tag | tr -d '\0')" = hostfs ]; then
+2
View File
@@ -142,6 +142,8 @@ BR2_PACKAGE_FINIT_PLUGIN_HOTPLUG=y
BR2_PACKAGE_FINIT_PLUGIN_HOOK_SCRIPTS=y
BR2_PACKAGE_FINIT_PLUGIN_MODULES_LOAD=y
BR2_PACKAGE_FINIT_PLUGIN_RTC=y
BR2_PACKAGE_FINIT_RTC_DATE="2024-11-04 10:54:00"
BR2_PACKAGE_FINIT_RTC_FILE="/var/lib/misc/rtc"
BR2_PACKAGE_FINIT_PLUGIN_TTY=y
BR2_PACKAGE_FINIT_PLUGIN_URANDOM=y
BR2_PACKAGE_IITO=y
+2
View File
@@ -122,6 +122,8 @@ BR2_PACKAGE_FINIT_PLUGIN_HOTPLUG=y
BR2_PACKAGE_FINIT_PLUGIN_HOOK_SCRIPTS=y
BR2_PACKAGE_FINIT_PLUGIN_MODULES_LOAD=y
BR2_PACKAGE_FINIT_PLUGIN_RTC=y
BR2_PACKAGE_FINIT_RTC_DATE="2024-11-04 10:54:00"
BR2_PACKAGE_FINIT_RTC_FILE="/var/lib/misc/rtc"
BR2_PACKAGE_FINIT_PLUGIN_TTY=y
BR2_PACKAGE_FINIT_PLUGIN_URANDOM=y
BR2_PACKAGE_IITO=y
+2
View File
@@ -183,6 +183,8 @@ BR2_PACKAGE_FINIT_PLUGIN_HOTPLUG=y
BR2_PACKAGE_FINIT_PLUGIN_HOOK_SCRIPTS=y
BR2_PACKAGE_FINIT_PLUGIN_MODULES_LOAD=y
BR2_PACKAGE_FINIT_PLUGIN_RTC=y
BR2_PACKAGE_FINIT_RTC_DATE="2024-11-04 10:54:00"
BR2_PACKAGE_FINIT_RTC_FILE="/var/lib/misc/rtc"
BR2_PACKAGE_FINIT_PLUGIN_TTY=y
BR2_PACKAGE_FINIT_PLUGIN_URANDOM=y
BR2_PACKAGE_IITO=y
+2
View File
@@ -173,6 +173,8 @@ BR2_PACKAGE_FINIT_PLUGIN_HOTPLUG=y
BR2_PACKAGE_FINIT_PLUGIN_HOOK_SCRIPTS=y
BR2_PACKAGE_FINIT_PLUGIN_MODULES_LOAD=y
BR2_PACKAGE_FINIT_PLUGIN_RTC=y
BR2_PACKAGE_FINIT_RTC_DATE="2024-11-04 10:54:00"
BR2_PACKAGE_FINIT_RTC_FILE="/var/lib/misc/rtc"
BR2_PACKAGE_FINIT_PLUGIN_TTY=y
BR2_PACKAGE_FINIT_PLUGIN_URANDOM=y
BR2_PACKAGE_IITO=y
+2
View File
@@ -146,6 +146,8 @@ BR2_PACKAGE_FINIT_PLUGIN_HOTPLUG=y
BR2_PACKAGE_FINIT_PLUGIN_HOOK_SCRIPTS=y
BR2_PACKAGE_FINIT_PLUGIN_MODULES_LOAD=y
BR2_PACKAGE_FINIT_PLUGIN_RTC=y
BR2_PACKAGE_FINIT_RTC_DATE="2024-11-04 10:54:00"
BR2_PACKAGE_FINIT_RTC_FILE="/var/lib/misc/rtc"
BR2_PACKAGE_FINIT_PLUGIN_TTY=y
BR2_PACKAGE_FINIT_PLUGIN_URANDOM=y
BR2_PACKAGE_IITO=y
+2
View File
@@ -126,6 +126,8 @@ BR2_PACKAGE_FINIT_PLUGIN_HOTPLUG=y
BR2_PACKAGE_FINIT_PLUGIN_HOOK_SCRIPTS=y
BR2_PACKAGE_FINIT_PLUGIN_MODULES_LOAD=y
BR2_PACKAGE_FINIT_PLUGIN_RTC=y
BR2_PACKAGE_FINIT_RTC_DATE="2024-11-04 10:54:00"
BR2_PACKAGE_FINIT_RTC_FILE="/var/lib/misc/rtc"
BR2_PACKAGE_FINIT_PLUGIN_TTY=y
BR2_PACKAGE_FINIT_PLUGIN_URANDOM=y
BR2_PACKAGE_IITO=y
+18 -1
View File
@@ -9,8 +9,25 @@ All notable changes to the project are documented in this file.
### Changes
- Support for showing interfaces owned by running containers in the CLI
command `show interfaces`. This also adds support for showing the
peer interface of VETH pairs. Issue #626
- Reboot system on kernel "oops", on "oops" the kernel now panics and
reboots after 20 seconds. Issue #740
- Update static factory-config for NanoPi R2S: enable NACM, securing all
passwords, and enabling `iburst` for the NTP client. Issue #750
- Updated QoS documentation with pictures and more information on VLAN
interface ingress/egress priority handling.
interface ingress/egress priority handling, issue #759
- Disable RTC device in Styx device tree, issue #794
- Support for saving and restoring system clock from a disk file. This
allows restoring the system clock to a sane date in case the RTC is
disabled or does not have a valid time, issue #794
### Fixes
- Fix #685: DSA conduit interface not always detected, randomly causing
major issues configuring systems with multiple switch cores
- Fix #778: reactivate OpenSSL backend for libssh/libssh2 for NanoPI R2S.
This fixes a regression in v24.10.0 causing loss of NETCONF supprt
[v24.10.1][] - 2024-10-18
@@ -1,7 +1,7 @@
From 46ffa81f5c88ce95db011369d8bfb802313e4217 Mon Sep 17 00:00:00 2001
From: Joachim Wiberg <troglobit@gmail.com>
Date: Thu, 17 Oct 2024 14:23:24 +0200
Subject: [PATCH 1/2] Only mark rdeps dirty if main service is nohup
Subject: [PATCH 1/6] Only mark rdeps dirty if main service is nohup
Organization: Addiva Elektronik
This patch changes a behavior that's been default since Finit 4.0,
@@ -1,7 +1,7 @@
From 119e66a7e9c95283918639b51dd03a3d666955f8 Mon Sep 17 00:00:00 2001
From: Joachim Wiberg <troglobit@gmail.com>
Date: Mon, 28 Oct 2024 10:58:04 +0100
Subject: [PATCH 2/2] Reset color attributes and clear screen when starting up
Subject: [PATCH 2/6] Reset color attributes and clear screen when starting up
Organization: Addiva Elektronik
Some boot loaders, like GRUB, leave background color artifacts from
@@ -0,0 +1,196 @@
From 0c0e880f3fdd38f7bbde618408378dc0a19ff005 Mon Sep 17 00:00:00 2001
From: Joachim Wiberg <troglobit@gmail.com>
Date: Sun, 3 Nov 2024 09:39:46 +0100
Subject: [PATCH 3/6] plugins: refactor rtc.so
Organization: Addiva Elektronik
Factor out time_set() and time_get() for readability and reuse.
Signed-off-by: Joachim Wiberg <troglobit@gmail.com>
---
plugins/rtc.c | 116 +++++++++++++++++++++++++++++---------------------
1 file changed, 68 insertions(+), 48 deletions(-)
diff --git a/plugins/rtc.c b/plugins/rtc.c
index 238791f..9520c7d 100644
--- a/plugins/rtc.c
+++ b/plugins/rtc.c
@@ -68,6 +68,60 @@ static void tz_restore(char *tz)
tzset();
}
+static int time_set(struct tm *tm)
+{
+ struct tm fallback = { 0 };
+ struct timeval tv = { 0 };
+ char tz[128];
+ int rc = 0;
+
+ tz_set(tz, sizeof(tz));
+
+ if (!tm) {
+ logit(LOG_NOTICE, "Resetting system clock to kernel default, %s.", rtc_timestamp);
+ tm = &fallback;
+
+ /* Attempt to set RTC to a sane value ... */
+ tv.tv_sec = rtc_date_fallback;
+ if (!gmtime_r(&tv.tv_sec, tm)) {
+ rc = 1;
+ goto out;
+ }
+ }
+
+ tm->tm_isdst = -1; /* Use tzdata to figure it out, please. */
+ tv.tv_sec = mktime(tm);
+ if (tv.tv_sec == (time_t)-1 || tv.tv_sec < rtc_date_fallback) {
+ errno = EINVAL;
+ rc = 2;
+ } else {
+ if (settimeofday(&tv, NULL) == -1)
+ rc = 1;
+ }
+out:
+ tz_restore(tz);
+ return rc;
+}
+
+static int time_get(struct tm *tm)
+{
+ struct timeval tv = { 0 };
+ char tz[128];
+ int rc = 0;
+
+ tz_set(tz, sizeof(tz));
+
+ rc = gettimeofday(&tv, NULL);
+ if (rc < 0 || tv.tv_sec < rtc_date_fallback)
+ rc = 2;
+ else
+ gmtime_r(&tv.tv_sec, tm);
+
+ tz_restore(tz);
+
+ return rc;
+}
+
static int rtc_open(void)
{
char *alt[] = {
@@ -91,10 +145,8 @@ static int rtc_open(void)
static void rtc_save(void *arg)
{
- struct timeval tv = { 0 };
struct tm tm = { 0 };
int fd, rc = 0;
- char tz[128];
if (rescue) {
dbg("Skipping %s plugin in rescue mode.", __FILE__);
@@ -105,38 +157,26 @@ static void rtc_save(void *arg)
if (fd < 0)
return;
- tz_set(tz, sizeof(tz));
- rc = gettimeofday(&tv, NULL);
- if (rc < 0 || tv.tv_sec < rtc_date_fallback) {
+ if ((rc = time_get(&tm))) {
print_desc(NULL, "System clock invalid, not saving to RTC");
- invalid:
- logit(LOG_ERR, "System clock invalid, before %s, not saving to RTC", rtc_timestamp);
- rc = 2;
- goto out;
+ } else {
+ print_desc(NULL, "Saving system clock (UTC) to RTC");
+ rc = ioctl(fd, RTC_SET_TIME, &tm);
}
- print_desc(NULL, "Saving system time (UTC) to RTC");
-
- gmtime_r(&tv.tv_sec, &tm);
- if (ioctl(fd, RTC_SET_TIME, &tm) < 0) {
- if (EINVAL == errno)
- goto invalid;
- rc = 1;
- goto out;
+ if (rc && errno == EINVAL) {
+ logit(LOG_ERR, "System clock invalid, before %s, not saving to RTC", rtc_timestamp);
+ rc = 2;
}
-out:
- tz_restore(tz);
print(rc, NULL);
close(fd);
}
static void rtc_restore(void *arg)
{
- struct timeval tv = { 0 };
struct tm tm = { 0 };
int fd, rc = 0;
- char tz[128];
if (rescue) {
dbg("Skipping %s plugin in rescue mode.", __FILE__);
@@ -149,16 +189,19 @@ static void rtc_restore(void *arg)
return;
}
- tz_set(tz, sizeof(tz));
- if (ioctl(fd, RTC_RD_TIME, &tm) < 0) {
+ if ((rc = ioctl(fd, RTC_RD_TIME, &tm)) < 0) {
char msg[120];
snprintf(msg, sizeof(msg), "Failed restoring system clock, %s",
EINVAL == errno ? "RTC time is too old" :
ENOENT == errno ? "RTC has no saved time" : "see log for details");
print_desc(NULL, msg);
+ } else {
+ print_desc(NULL, "Restoring system clock (UTC) from RTC");
+ rc = time_set(&tm);
+ }
- invalid:
+ if (rc) {
logit(LOG_ERR, "Failed restoring system clock from RTC.");
if (EINVAL == errno)
logit(LOG_ERR, "RTC time is too old (before %s)", rtc_timestamp);
@@ -167,33 +210,10 @@ static void rtc_restore(void *arg)
else
logit(LOG_ERR, "RTC error code %d: %s", errno, strerror(errno));
- /* Been here already? */
- if (rc)
- goto out;
-
- /* Attempt to set RTC to a sane value ... */
- tv.tv_sec = rtc_date_fallback;
- if (!gmtime_r(&tv.tv_sec, &tm))
- goto out;
-
- logit(LOG_NOTICE, "Resetting RTC to kernel default, %s.", rtc_timestamp);
+ time_set(NULL);
rc = 2;
}
- if (!rc)
- print_desc(NULL, "Restoring system clock (UTC) from RTC");
- tm.tm_isdst = -1; /* Use tzdata to figure it out, please. */
- tv.tv_sec = mktime(&tm);
- if (tv.tv_sec == (time_t)-1 || tv.tv_sec < rtc_date_fallback) {
- errno = EINVAL;
- goto invalid;
- }
-
- if (settimeofday(&tv, NULL) == -1)
- rc = 1;
-
-out:
- tz_restore(tz);
print(rc, NULL);
close(fd);
}
--
2.43.0
@@ -0,0 +1,239 @@
From bc8118d515839dc598f437aa01f07a771646968d Mon Sep 17 00:00:00 2001
From: Joachim Wiberg <troglobit@gmail.com>
Date: Sun, 3 Nov 2024 09:47:16 +0100
Subject: [PATCH 4/6] Fix #418: support systems with a broken RTC
Organization: Addiva Elektronik
This patch introduces a new configure option --with-rtc-file=FILE. When
enabled the RTC plugin detects missing RTC device and falls back to save
and restore system time from a file instead. When --with-rtc-file is
used without an argument the default file is /var/lib/misc/rtc, but the
feature itself is disabled by default.
The usefulness of this feature may not be obvious at first, but some
systems are equipped with an RTC that resets to a random date at power
on. This can be really bad in the case the date is far in the future,
because an NTP sync would then cause time skips backwards, which shows
up in logs and causes a whole lot of pain in alarm systems.
The solution is to disable the RTC driver or device tree node, and when
Finit starts up, the RTC plugin detects a the device node and instead
restores time from the last save game. Meaning time will always only
move forwards.
NOTE: when Finit is built --with-rtc-file we always save to disk, but
only restore from the "save game" if restoring from RTC fails.
If the system has no RTC we always restore from disk.
As an added bonus, this change also makes sure to periodically
sync also the RTC with the system clock. Useful for systems
that do not run an NTP client.
Signed-off-by: Joachim Wiberg <troglobit@gmail.com>
---
configure.ac | 12 ++++++
plugins/rtc.c | 105 ++++++++++++++++++++++++++++++++++++++++++++++----
2 files changed, 110 insertions(+), 7 deletions(-)
diff --git a/configure.ac b/configure.ac
index 483457f..ae7cd23 100644
--- a/configure.ac
+++ b/configure.ac
@@ -180,6 +180,10 @@ AC_ARG_WITH(rtc-date,
AS_HELP_STRING([--with-rtc-date=DATE], [If RTC date/time is too old, restore to DATE, format "YYYY-MM-DD HH:MM", default "2000-01-01 00:00"]),
[rtc_date=$withval], [rtc_date=no])
+AC_ARG_WITH(rtc-file,
+ AS_HELP_STRING([--with-rtc-file=FILE], [If RTC is missing, save and restore system clock from this file, default: no]),
+ [rtc_file=$withval], [rtc_file=no])
+
### Enable features ###########################################################################
# Create config.h from selected features and fallback defaults
@@ -281,6 +285,13 @@ AS_IF([test "x$rtc_date" != "xno"], [
AC_DEFINE(RTC_TIMESTAMP_CUSTOM, "$rtc_date", [Custom RTC restore date, default: 2000-01-01 00:00])], [
rtc_date=""])
+AS_IF([test "x$rtc_file" != "xno"], [
+ AS_IF([test "x$rtc_file" = "xyes"], [
+ rtc_file=/var/lib/misc/rtc])
+ AC_EXPAND_DIR(rtcfile_path, "$rtc_file")
+ AC_DEFINE_UNQUOTED(RTC_FILE, "$rtcfile_path", [Save and restore system time from this file if /dev/rtc is missing.])],[
+ AC_DEFINE_UNQUOTED(RTC_FILE, NULL)])
+
AS_IF([test "x$with_keventd" != "xno"], [with_keventd=yes])
AS_IF([test "x$with_sulogin" != "xno"], [
@@ -387,6 +398,7 @@ Behavior:
Boot heading..........: $heading
Plugins...............: $plugins
RTC restore date......: $RTC_DATE
+ RTC fallback file.....: $rtc_file
Optional features:
Install doc/..........: $enable_doc
diff --git a/plugins/rtc.c b/plugins/rtc.c
index 9520c7d..9b4eeae 100644
--- a/plugins/rtc.c
+++ b/plugins/rtc.c
@@ -36,8 +36,15 @@
#include "helpers.h"
#include "plugin.h"
-/* Kernel RTC driver validates against this date for sanity check */
+/*
+ * Kernel RTC driver validates against this date for sanity check. The
+ * on NTP sync the driver can also update the RTC every 11 mins. We use
+ * the same update interval to handle manual time set and file save.
+ */
#define RTC_TIMESTAMP_BEGIN_2000 "2000-01-01 00:00:00"
+#define RTC_FMT "%Y-%m-%d %H:%M:%S"
+#define RTC_PERIOD (11 * 60 * 1000)
+
#ifdef RTC_TIMESTAMP_CUSTOM
static char *rtc_timestamp = RTC_TIMESTAMP_CUSTOM;
#else
@@ -45,6 +52,10 @@ static char *rtc_timestamp = RTC_TIMESTAMP_BEGIN_2000;
#endif
static time_t rtc_date_fallback = 946684800LL;
+static char *rtc_file = RTC_FILE;
+static uev_t rtc_timer;
+
+
static void tz_set(char *tz, size_t len)
{
char *ptr;
@@ -122,6 +133,68 @@ static int time_get(struct tm *tm)
return rc;
}
+static void file_save(void *arg)
+{
+ struct tm tm = { 0 };
+ int rc = 0;
+ FILE *fp;
+
+ fp = fopen(rtc_file, "w");
+ if (!fp) {
+ logit(LOG_WARNING, "Failed saving system clock to %s, code %d: %s",
+ rtc_file, errno, strerror(errno));
+ return;
+ }
+
+ if ((rc = time_get(&tm))) {
+ logit(LOG_ERR, "System clock invalid, before %s, not saving", rtc_timestamp);
+ print_desc(NULL, "System clock invalid, skipping");
+ } else {
+ char buf[32] = { 0 };
+
+ print_desc(NULL, "Saving system clock to file");
+ strftime(buf, sizeof(buf), RTC_FMT, &tm);
+ fprintf(fp, "%s\n", buf);
+ }
+
+ print(rc, NULL);
+ fclose(fp);
+}
+
+static void file_restore(void *arg)
+{
+ struct tm tm = { 0 };
+ int rc = 1;
+ FILE *fp;
+
+ if (!rtc_file) {
+ logit(LOG_NOTICE, "System has no RTC (missing driver?), skipping restore.");
+ return;
+ }
+
+ print_desc(NULL, "Restoring system clock from backup");
+
+ fp = fopen(rtc_file, "r");
+ if (fp) {
+ char buf[32];
+
+ if (fgets(buf, sizeof(buf), fp)) {
+ chomp(buf);
+ strptime(buf, RTC_FMT, &tm);
+ rc = time_set(&tm);
+ }
+ fclose(fp);
+ } else
+ logit(LOG_WARNING, "Missing %s", rtc_file);
+
+ if (rc) {
+ time_set(NULL);
+ rc = 2;
+ }
+
+ print(rc, NULL);
+}
+
static int rtc_open(void)
{
char *alt[] = {
@@ -185,7 +258,7 @@ static void rtc_restore(void *arg)
fd = rtc_open();
if (fd < 0) {
- logit(LOG_NOTICE, "System has no RTC (missing driver?), skipping restore.");
+ file_restore(arg);
return;
}
@@ -210,21 +283,37 @@ static void rtc_restore(void *arg)
else
logit(LOG_ERR, "RTC error code %d: %s", errno, strerror(errno));
- time_set(NULL);
- rc = 2;
- }
+ print(2, NULL);
+
+ /* Try restoring from last save game */
+ if (rtc_file)
+ file_restore(arg);
+ } else
+ print(0, NULL);
- print(rc, NULL);
close(fd);
}
+
+static void save(void *arg)
+{
+ rtc_save(arg);
+ file_save(arg);
+}
+
+static void update(uev_t *w, void *arg, int events)
+{
+ save(arg);
+}
+
+
static plugin_t plugin = {
.name = __FILE__,
.hook[HOOK_BASEFS_UP] = {
.cb = rtc_restore
},
.hook[HOOK_SHUTDOWN] = {
- .cb = rtc_save
+ .cb = save
}
};
@@ -237,6 +326,8 @@ PLUGIN_INIT(plugin_init)
else
rtc_timestamp = RTC_TIMESTAMP_BEGIN_2000;
+ uev_timer_init(ctx, &rtc_timer, update, NULL, RTC_PERIOD, RTC_PERIOD);
+
plugin_register(&plugin);
}
--
2.43.0
@@ -0,0 +1,73 @@
From 6be16f2f6d093ef495d0fe4313f7b05b4ba3e08f Mon Sep 17 00:00:00 2001
From: Joachim Wiberg <troglobit@gmail.com>
Date: Sun, 3 Nov 2024 10:38:38 +0100
Subject: [PATCH 5/6] Fix buggy --with-rtc-date=DATE, introduced in Finit v4.4
Organization: Addiva Elektronik
In 42ef3d3c, for v4.4-rc1, support for setting a custom RTC restore date
was introduced. Unfortunately the configure script was wrong and caused
config.h to contain
#define RTC_TIMESTAMP_CUSTOM "$rtc_date"
instead of
#define RTC_TIMESTAMP_CUSTOM "2023-04-10 14:35:42"
Furthermore, the error handling for strptime() was wrong, so the restore
date was always reverted to the default.
This patch fixes both issues and extends the DATE of --with-rtc-date to
also include seconds.
Signed-off-by: Joachim Wiberg <troglobit@gmail.com>
---
configure.ac | 4 ++--
plugins/rtc.c | 8 +++++---
2 files changed, 7 insertions(+), 5 deletions(-)
diff --git a/configure.ac b/configure.ac
index ae7cd23..58b78ac 100644
--- a/configure.ac
+++ b/configure.ac
@@ -177,7 +177,7 @@ AC_ARG_WITH(plugin-path,
[plugin_path=$withval], [plugin_path=yes])
AC_ARG_WITH(rtc-date,
- AS_HELP_STRING([--with-rtc-date=DATE], [If RTC date/time is too old, restore to DATE, format "YYYY-MM-DD HH:MM", default "2000-01-01 00:00"]),
+ AS_HELP_STRING([--with-rtc-date=DATE], [If RTC date/time is too old, restore to DATE, format "YYYY-MM-DD HH:MM:SS", default "2000-01-01 00:00:00"]),
[rtc_date=$withval], [rtc_date=no])
AC_ARG_WITH(rtc-file,
@@ -282,7 +282,7 @@ AS_IF([test "x$with_random_seed" != "xno"], [
AC_DEFINE_UNQUOTED(RANDOMSEED, "$random_path", [Improve random at boot by seeding it with sth from before.])])
AS_IF([test "x$rtc_date" != "xno"], [
- AC_DEFINE(RTC_TIMESTAMP_CUSTOM, "$rtc_date", [Custom RTC restore date, default: 2000-01-01 00:00])], [
+ AC_DEFINE_UNQUOTED(RTC_TIMESTAMP_CUSTOM, "$rtc_date", [Custom RTC restore date, default: 2000-01-01 00:00])], [
rtc_date=""])
AS_IF([test "x$rtc_file" != "xno"], [
diff --git a/plugins/rtc.c b/plugins/rtc.c
index 9b4eeae..a733f75 100644
--- a/plugins/rtc.c
+++ b/plugins/rtc.c
@@ -321,10 +321,12 @@ PLUGIN_INIT(plugin_init)
{
struct tm tm = { 0 };
- if (!strptime(rtc_timestamp, "%Y-%m-%d %H:%M", &tm))
- rtc_date_fallback = mktime(&tm);
- else
+ if (!strptime(rtc_timestamp, RTC_FMT, &tm)) {
+ logit(LOG_ERR, "Invalid restore date '%s', reverting to '%s'",
+ rtc_timestamp, RTC_TIMESTAMP_BEGIN_2000);
rtc_timestamp = RTC_TIMESTAMP_BEGIN_2000;
+ } else
+ rtc_date_fallback = mktime(&tm);
uev_timer_init(ctx, &rtc_timer, update, NULL, RTC_PERIOD, RTC_PERIOD);
--
2.43.0
@@ -0,0 +1,85 @@
From 49c0557cedd8d3c1a2f74d27fa7db83dd529914a Mon Sep 17 00:00:00 2001
From: Joachim Wiberg <troglobit@gmail.com>
Date: Sun, 3 Nov 2024 20:49:04 +0100
Subject: [PATCH 6/6] plugins: reduce log level LOG_ERR -> LOG_WARNING
Organization: Addiva Elektronik
These plugins signal success and failure directly to the console, the
user should inspect syslog for more information.
This change is a follow-up to 340cae4, where kernel logs of LOG_ERR and
higher are allowed to log directly to the console. Since syslogd has
not been started before these plugins, the log messages would otherwise
leak to the console.
Signed-off-by: Joachim Wiberg <troglobit@gmail.com>
---
plugins/rtc.c | 14 +++++++-------
plugins/urandom.c | 2 +-
2 files changed, 8 insertions(+), 8 deletions(-)
diff --git a/plugins/rtc.c b/plugins/rtc.c
index a733f75..96203a0 100644
--- a/plugins/rtc.c
+++ b/plugins/rtc.c
@@ -147,7 +147,7 @@ static void file_save(void *arg)
}
if ((rc = time_get(&tm))) {
- logit(LOG_ERR, "System clock invalid, before %s, not saving", rtc_timestamp);
+ logit(LOG_WARNING, "System clock invalid, before %s, not saving", rtc_timestamp);
print_desc(NULL, "System clock invalid, skipping");
} else {
char buf[32] = { 0 };
@@ -238,7 +238,7 @@ static void rtc_save(void *arg)
}
if (rc && errno == EINVAL) {
- logit(LOG_ERR, "System clock invalid, before %s, not saving to RTC", rtc_timestamp);
+ logit(LOG_WARNING, "System clock invalid, before %s, not saving to RTC", rtc_timestamp);
rc = 2;
}
@@ -275,13 +275,13 @@ static void rtc_restore(void *arg)
}
if (rc) {
- logit(LOG_ERR, "Failed restoring system clock from RTC.");
+ logit(LOG_WARNING, "Failed restoring system clock from RTC.");
if (EINVAL == errno)
- logit(LOG_ERR, "RTC time is too old (before %s)", rtc_timestamp);
+ logit(LOG_WARNING, "RTC time is too old (before %s)", rtc_timestamp);
else if (ENOENT == errno)
- logit(LOG_ERR, "RTC has no previously saved (valid) time.");
+ logit(LOG_WARNING, "RTC has no previously saved (valid) time.");
else
- logit(LOG_ERR, "RTC error code %d: %s", errno, strerror(errno));
+ logit(LOG_WARNING, "RTC error code %d: %s", errno, strerror(errno));
print(2, NULL);
@@ -322,7 +322,7 @@ PLUGIN_INIT(plugin_init)
struct tm tm = { 0 };
if (!strptime(rtc_timestamp, RTC_FMT, &tm)) {
- logit(LOG_ERR, "Invalid restore date '%s', reverting to '%s'",
+ logit(LOG_WARNING, "Invalid restore date '%s', reverting to '%s'",
rtc_timestamp, RTC_TIMESTAMP_BEGIN_2000);
rtc_timestamp = RTC_TIMESTAMP_BEGIN_2000;
} else
diff --git a/plugins/urandom.c b/plugins/urandom.c
index b9f6039..6f82779 100644
--- a/plugins/urandom.c
+++ b/plugins/urandom.c
@@ -154,7 +154,7 @@ static void setup(void *arg)
close(fd);
free(rpi);
if (rc < 0)
- logit(LOG_ERR, "Failed adding entropy to kernel random pool: %s", strerror(err));
+ logit(LOG_WARNING, "Failed adding entropy to kernel random pool: %s", strerror(err));
print_result(rc < 0);
return;
fallback:
--
2.43.0
+15 -2
View File
@@ -165,7 +165,6 @@ config BR2_PACKAGE_FINIT_PLUGIN_RTC
For lxc/docker application builds you do not need this.
if BR2_PACKAGE_FINIT_PLUGIN_RTC
config BR2_PACKAGE_FINIT_RTC_DATE
string "Fallback RTC date"
help
@@ -184,7 +183,21 @@ config BR2_PACKAGE_FINIT_RTC_DATE
Ensuring the default system time to be closer to actual time
for a period after releasing a firmware image.
endif
config BR2_PACKAGE_FINIT_RTC_FILE
string "Fallback file if /dev/rtc is missing"
help
For systems with broken RTC, where the default value can be
completely random, e.g., a time far in the future, it might
be better to disable the RTC driver or device tree node.
Enable this to allow the RTC plugin to save and restore the
system clock from a file when the plugin does not find any
usable device node.
Since /var/lib/misc is usually persistent across reboots, we
recommend using: /var/lib/misc/rtc
endif # RTC_PLUGIN
config BR2_PACKAGE_FINIT_PLUGIN_TTY
bool "TTY plugin"
+27 -10
View File
@@ -13,11 +13,19 @@ FINIT_DEPENDENCIES = host-pkgconf libite libuev
FINIT_INSTALL_STAGING = YES
FINIT_D = $(TARGET_DIR)/etc/finit.d
# Create configure script using autoreconf when building from git
# Create configure script using autoreconf when building from git,
# or when patching any of the GNU build files (*.ac, *.am, etc.)
#FINIT_VERSION = 438d6b4e638418a2a22024a3cead2f47909d72b9
#FINIT_SITE = $(call github,troglobit,finit,$(FINIT_VERSION))
#FINIT_AUTORECONF = YES
#FINIT_DEPENDENCIES += host-automake host-autoconf host-libtool
FINIT_AUTORECONF = YES
FINIT_DEPENDENCIES += host-automake host-autoconf host-libtool
# Strip "" from variables
FINIT_HOSTNAME = $(call qstrip,$(BR2_TARGET_GENERIC_HOSTNAME))
FINIT_GROUP = $(call qstrip,$(BR2_PACKAGE_FINIT_INITCTL_GROUP))
FINIT_FSTAB = $(call qstrip,$(BR2_PACKAGE_FINIT_CUSTOM_FSTAB))
FINIT_RTC_DATE = $(call qstrip,$(BR2_PACKAGE_FINIT_RTC_DATE))
FINIT_RTC_FILE = $(call qstrip,$(BR2_PACKAGE_FINIT_RTC_FILE))
# Buildroot defaults to /usr for both prefix and exec-prefix, this we
# must override because we want to install into /sbin and /bin for the
@@ -31,7 +39,7 @@ FINIT_CONF_OPTS = \
--disable-contrib \
--disable-rescue \
--disable-silent-rules \
--with-group=$(BR2_PACKAGE_FINIT_INITCTL_GROUP)
--with-group="$(FINIT_GROUP)"
ifeq ($(BR2_ROOTFS_MERGED_USR),y)
FINIT_CONF_OPTS += --exec-prefix=/usr
@@ -40,8 +48,8 @@ FINIT_CONF_OPTS += --exec-prefix=
endif
ifeq ($(BR2_PACKAGE_FINIT_ADVANCED),y)
ifneq ($(BR2_PACKAGE_FINIT_CUSTOM_FSTAB),)
FINIT_CONF_OPTS += --with-fstab=$(BR2_PACKAGE_FINIT_CUSTOM_FSTAB)
ifneq ($(FINIT_FSTAB),)
FINIT_CONF_OPTS += --with-fstab="$(FINIT_FSTAB)"
else
FINIT_CONF_OPTS += --without-fstab
endif
@@ -101,12 +109,18 @@ else
FINIT_CONF_OPTS += --disable-rtc-plugin
endif
ifeq ($(BR2_PACKAGE_FINIT_RTC_DATE),y)
FINIT_CONF_OPTS += --with-rtc-date="$(BR2_PACKAGE_FINIT_RTC_DATE)"
ifneq ($(FINIT_RTC_DATE),)
FINIT_CONF_OPTS += --with-rtc-date="$(FINIT_RTC_DATE)"
else
FINIT_CONF_OPTS += --without-rtc-date
endif
ifneq ($(FINIT_RTC_FILE),)
FINIT_CONF_OPTS += --with-rtc-file="$(FINIT_RTC_FILE)"
else
FINIT_CONF_OPTS += --without-rtc-file
endif
ifeq ($(BR2_PACKAGE_FINIT_PLUGIN_TTY),y)
FINIT_CONF_OPTS += --enable-tty-plugin
else
@@ -119,8 +133,11 @@ else
FINIT_CONF_OPTS += --disable-urandom-plugin
endif
ifneq ($(SKELETON_INIT_COMMON_HOSTNAME),)
FINIT_CONF_OPTS += --with-hostname="$(SKELETON_INIT_COMMON_HOSTNAME)"
ifneq ($(FINIT_HOSTNAME),)
FINIT_CONF_OPTS += --with-hostname="$(FINIT_HOSTNAME)"
else
FINIT_CONF_OPTS += --without-hostname
endif
# Disable/Enable features depending on other packages