arch/x86/kernel/x86_init.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
get_rtc_noop() is used when an RTC is unavailable, but leaves its output
argument untouched. When CONFIG_INIT_STACK_ALL_ZERO is not enabled,
timekeeping_init() may therefore receive a nonzero invalid persistent
clock value and warn:
"Persistent clock returned invalid value"
Initialize the output to zero, the documented representation of an
unsupported persistent clock.
Fixes: c311ed6183f4 ("x86/init: Allow DT configured systems to disable RTC at boot time")
Cc: stable@vger.kernel.org
Signed-off-by: Naman Jain <namjain@linux.microsoft.com>
---
arch/x86/kernel/x86_init.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/arch/x86/kernel/x86_init.c b/arch/x86/kernel/x86_init.c
index 252c5827d0634..3b9b41820c84c 100644
--- a/arch/x86/kernel/x86_init.c
+++ b/arch/x86/kernel/x86_init.c
@@ -37,7 +37,7 @@ static void iommu_shutdown_noop(void) { }
bool __init bool_x86_init_noop(void) { return false; }
void x86_op_int_noop(int cpu) { }
int set_rtc_noop(const struct timespec64 *now) { return -EINVAL; }
-void get_rtc_noop(struct timespec64 *now) { }
+void get_rtc_noop(struct timespec64 *now) { *now = (struct timespec64){0}; }
static __initconst const struct of_device_id of_cmos_match[] = {
{ .compatible = "motorola,mc146818" },
--
2.43.0
On Mon, Aug 31, 2026 at 08:25:28AM +0000, Naman Jain wrote:
> get_rtc_noop() is used when an RTC is unavailable, but leaves its output
> argument untouched. When CONFIG_INIT_STACK_ALL_ZERO is not enabled,
> timekeeping_init() may therefore receive a nonzero invalid persistent
> clock value and warn:
> "Persistent clock returned invalid value"
>
> Initialize the output to zero, the documented representation of an
> unsupported persistent clock.
>
> Fixes: c311ed6183f4 ("x86/init: Allow DT configured systems to disable RTC at boot time")
> Cc: stable@vger.kernel.org
> Signed-off-by: Naman Jain <namjain@linux.microsoft.com>
> ---
> arch/x86/kernel/x86_init.c | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/arch/x86/kernel/x86_init.c b/arch/x86/kernel/x86_init.c
> index 252c5827d0634..3b9b41820c84c 100644
> --- a/arch/x86/kernel/x86_init.c
> +++ b/arch/x86/kernel/x86_init.c
> @@ -37,7 +37,7 @@ static void iommu_shutdown_noop(void) { }
> bool __init bool_x86_init_noop(void) { return false; }
> void x86_op_int_noop(int cpu) { }
> int set_rtc_noop(const struct timespec64 *now) { return -EINVAL; }
> -void get_rtc_noop(struct timespec64 *now) { }
> +void get_rtc_noop(struct timespec64 *now) { *now = (struct timespec64){0}; }
Hi Naman,
Could be
*now = (struct timespec64){};
to save a byte :)
LGTM.
Reviewed-by: Roman Kisel <vdso@mailbox.org>
>
> static __initconst const struct of_device_id of_cmos_match[] = {
> { .compatible = "motorola,mc146818" },
> --
> 2.43.0
>
On 9/12/2026 9:05 AM, Roman Kisel wrote:
> On Mon, Aug 31, 2026 at 08:25:28AM +0000, Naman Jain wrote:
>> get_rtc_noop() is used when an RTC is unavailable, but leaves its output
>> argument untouched. When CONFIG_INIT_STACK_ALL_ZERO is not enabled,
>> timekeeping_init() may therefore receive a nonzero invalid persistent
>> clock value and warn:
>> "Persistent clock returned invalid value"
>>
>> Initialize the output to zero, the documented representation of an
>> unsupported persistent clock.
>>
>> Fixes: c311ed6183f4 ("x86/init: Allow DT configured systems to disable RTC at boot time")
>> Cc: stable@vger.kernel.org
>> Signed-off-by: Naman Jain <namjain@linux.microsoft.com>
>> ---
>> arch/x86/kernel/x86_init.c | 2 +-
>> 1 file changed, 1 insertion(+), 1 deletion(-)
>>
>> diff --git a/arch/x86/kernel/x86_init.c b/arch/x86/kernel/x86_init.c
>> index 252c5827d0634..3b9b41820c84c 100644
>> --- a/arch/x86/kernel/x86_init.c
>> +++ b/arch/x86/kernel/x86_init.c
>> @@ -37,7 +37,7 @@ static void iommu_shutdown_noop(void) { }
>> bool __init bool_x86_init_noop(void) { return false; }
>> void x86_op_int_noop(int cpu) { }
>> int set_rtc_noop(const struct timespec64 *now) { return -EINVAL; }
>> -void get_rtc_noop(struct timespec64 *now) { }
>> +void get_rtc_noop(struct timespec64 *now) { *now = (struct timespec64){0}; }
>
> Hi Naman,
>
> Could be
>
> *now = (struct timespec64){};
>
> to save a byte :)
hi Roman,
Thanks for reviewing.
Tianyu pointed out offline that this is handled in yet another way in
jailhouse code:
arch/x86/kernel/jailhouse.c
static void jailhouse_get_wallclock(struct timespec64 *now)
{
memset(now, 0, sizeof(now));
}
Regards,
Naman
>
> LGTM.
> Reviewed-by: Roman Kisel <vdso@mailbox.org>
>
>>
>> static __initconst const struct of_device_id of_cmos_match[] = {
>> { .compatible = "motorola,mc146818" },
>> --
>> 2.43.0
>>
> On 09/14/2026 4:31 AM PDT Naman Jain <namjain@linux.microsoft.com> wrote:
>
>
> On 9/12/2026 9:05 AM, Roman Kisel wrote:
> > On Mon, Aug 31, 2026 at 08:25:28AM +0000, Naman Jain wrote:
[...]
> >> +void get_rtc_noop(struct timespec64 *now) { *now = (struct timespec64){0}; }
> >
> > Hi Naman,
> >
> > Could be
> >
> > *now = (struct timespec64){};
> >
> > to save a byte :)
>
> hi Roman,
> Thanks for reviewing.
>
> Tianyu pointed out offline that this is handled in yet another way in
> jailhouse code:
>
> arch/x86/kernel/jailhouse.c
> static void jailhouse_get_wallclock(struct timespec64 *now)
> {
> memset(now, 0, sizeof(now));
> }
Appreciate sharing! Makes sense to me, looks way more explicit. Most
importantly imo, the memset isn't actually producing a call here so
the clock no-op stays cheap when choosing `memset` over ` = {}`.
One can see that the kernel build compiles ` = {0}`, ` = {}` into
pxor ...
movups ...
on x64 in the above. I made sure the memset "call" is relaxed/optimized
away into the same sequence `pxor ...; movups ...`.
>
> Regards,
> Naman
>
> >
> > LGTM.
> > Reviewed-by: Roman Kisel <vdso@mailbox.org>
> >
> >>
> >> static __initconst const struct of_device_id of_cmos_match[] = {
> >> { .compatible = "motorola,mc146818" },
> >> --
> >> 2.43.0
> >>
© 2016 - 2026 Red Hat, Inc.