diff options
Diffstat (limited to 'drivers/rtc')
| -rw-r--r-- | drivers/rtc/Makefile | 1 | ||||
| -rw-r--r-- | drivers/rtc/class.c | 3 | ||||
| -rw-r--r-- | drivers/rtc/rtc-core.h | 1 | ||||
| -rw-r--r-- | drivers/rtc/rtc-efi-platform.c | 1 | ||||
| -rw-r--r-- | drivers/rtc/rtc-sa1100.h | 1 | ||||
| -rw-r--r-- | drivers/rtc/systohc.c | 53 |
6 files changed, 45 insertions, 15 deletions
diff --git a/drivers/rtc/Makefile b/drivers/rtc/Makefile index 7230014c92af..0bf1fc02b82c 100644 --- a/drivers/rtc/Makefile +++ b/drivers/rtc/Makefile | |||
| @@ -1,3 +1,4 @@ | |||
| 1 | # SPDX-License-Identifier: GPL-2.0 | ||
| 1 | # | 2 | # |
| 2 | # Makefile for RTC class/drivers. | 3 | # Makefile for RTC class/drivers. |
| 3 | # | 4 | # |
diff --git a/drivers/rtc/class.c b/drivers/rtc/class.c index 2ed970d61da1..722d683e0b0f 100644 --- a/drivers/rtc/class.c +++ b/drivers/rtc/class.c | |||
| @@ -161,6 +161,9 @@ static struct rtc_device *rtc_allocate_device(void) | |||
| 161 | 161 | ||
| 162 | device_initialize(&rtc->dev); | 162 | device_initialize(&rtc->dev); |
| 163 | 163 | ||
| 164 | /* Drivers can revise this default after allocating the device. */ | ||
| 165 | rtc->set_offset_nsec = NSEC_PER_SEC / 2; | ||
| 166 | |||
| 164 | rtc->irq_freq = 1; | 167 | rtc->irq_freq = 1; |
| 165 | rtc->max_user_freq = 64; | 168 | rtc->max_user_freq = 64; |
| 166 | rtc->dev.class = rtc_class; | 169 | rtc->dev.class = rtc_class; |
diff --git a/drivers/rtc/rtc-core.h b/drivers/rtc/rtc-core.h index ecab76a3207c..513b9bedd2c8 100644 --- a/drivers/rtc/rtc-core.h +++ b/drivers/rtc/rtc-core.h | |||
| @@ -1,3 +1,4 @@ | |||
| 1 | /* SPDX-License-Identifier: GPL-2.0 */ | ||
| 1 | #ifdef CONFIG_RTC_INTF_DEV | 2 | #ifdef CONFIG_RTC_INTF_DEV |
| 2 | 3 | ||
| 3 | extern void __init rtc_dev_init(void); | 4 | extern void __init rtc_dev_init(void); |
diff --git a/drivers/rtc/rtc-efi-platform.c b/drivers/rtc/rtc-efi-platform.c index 1a7f1d1bc174..6c037dc4e3dc 100644 --- a/drivers/rtc/rtc-efi-platform.c +++ b/drivers/rtc/rtc-efi-platform.c | |||
| @@ -1,3 +1,4 @@ | |||
| 1 | // SPDX-License-Identifier: GPL-2.0 | ||
| 1 | /* | 2 | /* |
| 2 | * Moved from arch/ia64/kernel/time.c | 3 | * Moved from arch/ia64/kernel/time.c |
| 3 | * | 4 | * |
diff --git a/drivers/rtc/rtc-sa1100.h b/drivers/rtc/rtc-sa1100.h index 2c79c0c57822..cc724f5b07bc 100644 --- a/drivers/rtc/rtc-sa1100.h +++ b/drivers/rtc/rtc-sa1100.h | |||
| @@ -1,3 +1,4 @@ | |||
| 1 | /* SPDX-License-Identifier: GPL-2.0 */ | ||
| 1 | #ifndef __RTC_SA1100_H__ | 2 | #ifndef __RTC_SA1100_H__ |
| 2 | #define __RTC_SA1100_H__ | 3 | #define __RTC_SA1100_H__ |
| 3 | 4 | ||
diff --git a/drivers/rtc/systohc.c b/drivers/rtc/systohc.c index b4a68ffcd06b..0c177647ea6c 100644 --- a/drivers/rtc/systohc.c +++ b/drivers/rtc/systohc.c | |||
| @@ -10,6 +10,7 @@ | |||
| 10 | /** | 10 | /** |
| 11 | * rtc_set_ntp_time - Save NTP synchronized time to the RTC | 11 | * rtc_set_ntp_time - Save NTP synchronized time to the RTC |
| 12 | * @now: Current time of day | 12 | * @now: Current time of day |
| 13 | * @target_nsec: pointer for desired now->tv_nsec value | ||
| 13 | * | 14 | * |
| 14 | * Replacement for the NTP platform function update_persistent_clock64 | 15 | * Replacement for the NTP platform function update_persistent_clock64 |
| 15 | * that stores time for later retrieval by rtc_hctosys. | 16 | * that stores time for later retrieval by rtc_hctosys. |
| @@ -18,30 +19,52 @@ | |||
| 18 | * possible at all, and various other -errno for specific temporary failure | 19 | * possible at all, and various other -errno for specific temporary failure |
| 19 | * cases. | 20 | * cases. |
| 20 | * | 21 | * |
| 22 | * -EPROTO is returned if now.tv_nsec is not close enough to *target_nsec. | ||
| 23 | ( | ||
| 21 | * If temporary failure is indicated the caller should try again 'soon' | 24 | * If temporary failure is indicated the caller should try again 'soon' |
| 22 | */ | 25 | */ |
| 23 | int rtc_set_ntp_time(struct timespec64 now) | 26 | int rtc_set_ntp_time(struct timespec64 now, unsigned long *target_nsec) |
| 24 | { | 27 | { |
| 25 | struct rtc_device *rtc; | 28 | struct rtc_device *rtc; |
| 26 | struct rtc_time tm; | 29 | struct rtc_time tm; |
| 30 | struct timespec64 to_set; | ||
| 27 | int err = -ENODEV; | 31 | int err = -ENODEV; |
| 28 | 32 | bool ok; | |
| 29 | if (now.tv_nsec < (NSEC_PER_SEC >> 1)) | ||
| 30 | rtc_time64_to_tm(now.tv_sec, &tm); | ||
| 31 | else | ||
| 32 | rtc_time64_to_tm(now.tv_sec + 1, &tm); | ||
| 33 | 33 | ||
| 34 | rtc = rtc_class_open(CONFIG_RTC_SYSTOHC_DEVICE); | 34 | rtc = rtc_class_open(CONFIG_RTC_SYSTOHC_DEVICE); |
| 35 | if (rtc) { | 35 | if (!rtc) |
| 36 | /* rtc_hctosys exclusively uses UTC, so we call set_time here, | 36 | goto out_err; |
| 37 | * not set_mmss. */ | 37 | |
| 38 | if (rtc->ops && | 38 | if (!rtc->ops || (!rtc->ops->set_time && !rtc->ops->set_mmss64 && |
| 39 | (rtc->ops->set_time || | 39 | !rtc->ops->set_mmss)) |
| 40 | rtc->ops->set_mmss64 || | 40 | goto out_close; |
| 41 | rtc->ops->set_mmss)) | 41 | |
| 42 | err = rtc_set_time(rtc, &tm); | 42 | /* Compute the value of tv_nsec we require the caller to supply in |
| 43 | rtc_class_close(rtc); | 43 | * now.tv_nsec. This is the value such that (now + |
| 44 | * set_offset_nsec).tv_nsec == 0. | ||
| 45 | */ | ||
| 46 | set_normalized_timespec64(&to_set, 0, -rtc->set_offset_nsec); | ||
| 47 | *target_nsec = to_set.tv_nsec; | ||
| 48 | |||
| 49 | /* The ntp code must call this with the correct value in tv_nsec, if | ||
| 50 | * it does not we update target_nsec and return EPROTO to make the ntp | ||
| 51 | * code try again later. | ||
| 52 | */ | ||
| 53 | ok = rtc_tv_nsec_ok(rtc->set_offset_nsec, &to_set, &now); | ||
| 54 | if (!ok) { | ||
| 55 | err = -EPROTO; | ||
| 56 | goto out_close; | ||
| 44 | } | 57 | } |
| 45 | 58 | ||
| 59 | rtc_time64_to_tm(to_set.tv_sec, &tm); | ||
| 60 | |||
| 61 | /* rtc_hctosys exclusively uses UTC, so we call set_time here, not | ||
| 62 | * set_mmss. | ||
| 63 | */ | ||
| 64 | err = rtc_set_time(rtc, &tm); | ||
| 65 | |||
| 66 | out_close: | ||
| 67 | rtc_class_close(rtc); | ||
| 68 | out_err: | ||
| 46 | return err; | 69 | return err; |
| 47 | } | 70 | } |
