summaryrefslogtreecommitdiff
path: root/firmware/common/timefuncs.c
diff options
context:
space:
mode:
authorMichael Sevakis <jethead71@rockbox.org>2017-01-26 21:08:55 -0500
committerMichael Sevakis <jethead71@rockbox.org>2017-11-21 07:52:02 -0500
commitf4c42213062170ddfcc706b3c5ed19f47517c253 (patch)
tree65f8058970e97d939660cf1e39f844a06df66f84 /firmware/common/timefuncs.c
parent12bc24adbf919dc945928b2dcda74d51d33708f7 (diff)
downloadrockbox-f4c42213062170ddfcc706b3c5ed19f47517c253.tar.gz
rockbox-f4c42213062170ddfcc706b3c5ed19f47517c253.zip
Convert i.MX31 and AMS target to use RTC interrupt
Instead of checking ticks, set a sticky dirty flag that indicates that the RTC needs to be read. This gives a timely update and more accurate readout without actually reading the RTC until it changes. The implementation should atomically read the flag and clear it. Setting the flag would typically happen in an RTC tick ISR. Change-Id: I6fd325f22845029a485c502c884812d3676026ea
Diffstat (limited to 'firmware/common/timefuncs.c')
-rw-r--r--firmware/common/timefuncs.c45
1 files changed, 33 insertions, 12 deletions
diff --git a/firmware/common/timefuncs.c b/firmware/common/timefuncs.c
index c8819ea76e..50addad27a 100644
--- a/firmware/common/timefuncs.c
+++ b/firmware/common/timefuncs.c
@@ -24,13 +24,21 @@
24 24
25#include "kernel.h" 25#include "kernel.h"
26#include "rtc.h" 26#include "rtc.h"
27#ifdef HAVE_RTC_IRQ
28#include "rtc-target.h"
29#endif
27#include "timefuncs.h" 30#include "timefuncs.h"
28#include "debug.h" 31#include "debug.h"
29 32
30static struct tm tm; 33static struct tm tm;
31 34
32#if !CONFIG_RTC 35#if !CONFIG_RTC
33static void fill_default_tm(struct tm *tm) 36static inline bool rtc_dirty(void)
37{
38 return true;
39}
40
41static inline int rtc_read_datetime(struct tm *tm)
34{ 42{
35 tm->tm_sec = 0; 43 tm->tm_sec = 0;
36 tm->tm_min = 0; 44 tm->tm_min = 0;
@@ -38,9 +46,9 @@ static void fill_default_tm(struct tm *tm)
38 tm->tm_mday = 1; 46 tm->tm_mday = 1;
39 tm->tm_mon = 0; 47 tm->tm_mon = 0;
40 tm->tm_year = 70; 48 tm->tm_year = 70;
41 tm->tm_wday = 1; 49 tm->tm_wday = 4;
42 tm->tm_yday = 0; /* Not implemented for now */ 50 tm->tm_yday = 0;
43 tm->tm_isdst = -1; /* Not implemented for now */ 51 return 1;
44} 52}
45#endif /* !CONFIG_RTC */ 53#endif /* !CONFIG_RTC */
46 54
@@ -58,24 +66,37 @@ bool valid_time(const struct tm *tm)
58 else 66 else
59 return true; 67 return true;
60} 68}
61#endif /* CONFIG_RTC */
62 69
63struct tm *get_time(void) 70/* Don't read the RTC more than once per second
71 * returns true if the rtc needs to be read
72 * targets may override with their own implementation
73 */
74#ifndef HAVE_RTC_IRQ
75static inline bool rtc_dirty(void)
64{ 76{
65#if CONFIG_RTC
66 static long timeout = 0; 77 static long timeout = 0;
67 78
68 /* Don't read the RTC more than once per second */ 79 /* Don't read the RTC more than once per second */
69 if (TIME_AFTER(current_tick, timeout)) 80 if (TIME_AFTER(current_tick, timeout))
70 { 81 {
71 /* Once per second, 1/10th of a second off */ 82 /* Once per second, 1/5th of a second off */
72 timeout = HZ * (current_tick / HZ + 1) + HZ / 5; 83 timeout = current_tick / HZ * HZ + 6*HZ / 5;
84 return true;
85 }
86
87 return false;
88}
89#endif /* HAVE_RTC_IRQ */
90#endif /* CONFIG_RTC */
91
92struct tm *get_time(void)
93{
94 if (rtc_dirty())
95 {
73 rtc_read_datetime(&tm); 96 rtc_read_datetime(&tm);
74 tm.tm_isdst = -1; /* Not implemented for now */ 97 tm.tm_isdst = -1; /* Not implemented for now */
75 } 98 }
76#else /* No RTC */ 99
77 fill_default_tm(&tm);
78#endif /* RTC */
79 return &tm; 100 return &tm;
80} 101}
81 102