avr-libc  2.1.0
Standard C library for AVR-GCC

AVR Libc Home Page

AVRs

AVR Libc Development Pages

Main Page

User Manual

Library Reference

FAQ

Example Projects

time.h
Go to the documentation of this file.
1 /*
2  * (C)2012 Michael Duane Rice All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions are
6  * met:
7  *
8  * Redistributions of source code must retain the above copyright notice, this
9  * list of conditions and the following disclaimer. Redistributions in binary
10  * form must reproduce the above copyright notice, this list of conditions
11  * and the following disclaimer in the documentation and/or other materials
12  * provided with the distribution. Neither the name of the copyright holders
13  * nor the names of contributors may be used to endorse or promote products
14  * derived from this software without specific prior written permission.
15  *
16  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19  * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
20  * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
21  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
22  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
23  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
24  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
25  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
26  * POSSIBILITY OF SUCH DAMAGE.
27  */
28 
29 /* $Id: time_8h_source.html,v 1.1.1.3 2022/01/29 09:21:59 joerg_wunsch Exp $ */
30 
31 /** \file */
32 
33 /** \defgroup avr_time <time.h>: Time
34  \code #include <time.h> \endcode
35  <h3>Introduction to the Time functions</h3>
36  This file declares the time functions implemented in \c avr-libc.
37 
38  The implementation aspires to conform with ISO/IEC 9899 (C90). However, due to limitations of the
39  target processor and the nature of its development environment, a practical implementation must
40  of necessity deviate from the standard.
41 
42 
43 
44  Section 7.23.2.1 clock()
45  The type clock_t, the macro CLOCKS_PER_SEC, and the function clock() are not implemented. We
46  consider these items belong to operating system code, or to application code when no operating
47  system is present.
48 
49  Section 7.23.2.3 mktime()
50  The standard specifies that mktime() should return (time_t) -1, if the time cannot be represented.
51  This implementation always returns a 'best effort' representation.
52 
53  Section 7.23.2.4 time()
54  The standard specifies that time() should return (time_t) -1, if the time is not available.
55  Since the application must initialize the time system, this functionality is not implemented.
56 
57  Section 7.23.2.2, difftime()
58  Due to the lack of a 64 bit double, the function difftime() returns a long integer. In most cases
59  this change will be invisible to the user, handled automatically by the compiler.
60 
61  Section 7.23.1.4 struct tm
62  Per the standard, struct tm->tm_isdst is greater than zero when Daylight Saving time is in effect.
63  This implementation further specifies that, when positive, the value of tm_isdst represents
64  the amount time is advanced during Daylight Saving time.
65 
66  Section 7.23.3.5 strftime()
67  Only the 'C' locale is supported, therefore the modifiers 'E' and 'O' are ignored.
68  The 'Z' conversion is also ignored, due to the lack of time zone name.
69 
70  In addition to the above departures from the standard, there are some behaviors which are different
71  from what is often expected, though allowed under the standard.
72 
73  There is no 'platform standard' method to obtain the current time, time zone, or
74  daylight savings 'rules' in the AVR environment. Therefore the application must initialize
75  the time system with this information. The functions set_zone(), set_dst(), and
76  set_system_time() are provided for initialization. Once initialized, system time is maintained by
77  calling the function system_tick() at one second intervals.
78 
79  Though not specified in the standard, it is often expected that time_t is a signed integer
80  representing an offset in seconds from Midnight Jan 1 1970... i.e. 'Unix time'. This implementation
81  uses an unsigned 32 bit integer offset from Midnight Jan 1 2000. The use of this 'epoch' helps to
82  simplify the conversion functions, while the 32 bit value allows time to be properly represented
83  until Tue Feb 7 06:28:15 2136 UTC. The macros UNIX_OFFSET and NTP_OFFSET are defined to assist in
84  converting to and from Unix and NTP time stamps.
85 
86  Unlike desktop counterparts, it is impractical to implement or maintain the 'zoneinfo' database.
87  Therefore no attempt is made to account for time zone, daylight saving, or leap seconds in past dates.
88  All calculations are made according to the currently configured time zone and daylight saving 'rule'.
89 
90  In addition to C standard functions, re-entrant versions of ctime(), asctime(), gmtime() and
91  localtime() are provided which, in addition to being re-entrant, have the property of claiming
92  less permanent storage in RAM. An additional time conversion, isotime() and its re-entrant version,
93  uses far less storage than either ctime() or asctime().
94 
95  Along with the usual smattering of utility functions, such as is_leap_year(), this library includes
96  a set of functions related the sun and moon, as well as sidereal time functions.
97 */
98 
99 #ifndef TIME_H
100 #define TIME_H
101 
102 #ifdef __cplusplus
103 extern "C" {
104 #endif
105 
106 #include <inttypes.h>
107 #include <stdlib.h>
108 
109  /** \ingroup avr_time */
110  /* @{ */
111 
112  /**
113  time_t represents seconds elapsed from Midnight, Jan 1 2000 UTC (the Y2K 'epoch').
114  Its range allows this implementation to represent time up to Tue Feb 7 06:28:15 2136 UTC.
115  */
116  typedef uint32_t time_t;
117 
118  /**
119  The time function returns the systems current time stamp.
120  If timer is not a null pointer, the return value is also assigned to the object it points to.
121  */
122  time_t time(time_t *timer);
123 
124  /**
125  The difftime function returns the difference between two binary time stamps,
126  time1 - time0.
127  */
128  int32_t difftime(time_t time1, time_t time0);
129 
130 
131  /**
132  The tm structure contains a representation of time 'broken down' into components of the
133  Gregorian calendar.
134 
135  The value of tm_isdst is zero if Daylight Saving Time is not in effect, and is negative if
136  the information is not available.
137 
138  When Daylight Saving Time is in effect, the value represents the number of
139  seconds the clock is advanced.
140 
141  See the set_dst() function for more information about Daylight Saving.
142 
143  */
144  struct tm {
145  int8_t tm_sec; /**< seconds after the minute - [ 0 to 59 ] */
146  int8_t tm_min; /**< minutes after the hour - [ 0 to 59 ] */
147  int8_t tm_hour; /**< hours since midnight - [ 0 to 23 ] */
148  int8_t tm_mday; /**< day of the month - [ 1 to 31 ] */
149  int8_t tm_wday; /**< days since Sunday - [ 0 to 6 ] */
150  int8_t tm_mon; /**< months since January - [ 0 to 11 ] */
151  int16_t tm_year; /**< years since 1900 */
152  int16_t tm_yday; /**< days since January 1 - [ 0 to 365 ] */
153  int16_t tm_isdst; /**< Daylight Saving Time flag */
154  };
155 
156 #ifndef __DOXYGEN__
157  /* We have to provide clock_t / CLOCKS_PER_SEC so that libstdc++-v3 can
158  be built. We define CLOCKS_PER_SEC via a symbol _CLOCKS_PER_SEC_
159  so that the user can provide the value on the link line, which should
160  result in little or no run-time overhead compared with a constant. */
161  typedef unsigned long clock_t;
162  extern char *_CLOCKS_PER_SEC_;
163 #define CLOCKS_PER_SEC ((clock_t) _CLOCKS_PER_SEC_)
164  extern clock_t clock(void);
165 #endif /* !__DOXYGEN__ */
166 
167  /**
168  This function 'compiles' the elements of a broken-down time structure, returning a binary time stamp.
169  The elements of timeptr are interpreted as representing Local Time.
170 
171  The original values of the tm_wday and tm_yday elements of the structure are ignored,
172  and the original values of the other elements are not restricted to the ranges stated for struct tm.
173 
174  On successful completion, the values of all elements of timeptr are set to the appropriate range.
175  */
176  time_t mktime(struct tm * timeptr);
177 
178  /**
179  This function 'compiles' the elements of a broken-down time structure, returning a binary time stamp.
180  The elements of timeptr are interpreted as representing UTC.
181 
182  The original values of the tm_wday and tm_yday elements of the structure are ignored,
183  and the original values of the other elements are not restricted to the ranges stated for struct tm.
184 
185  Unlike mktime(), this function DOES NOT modify the elements of timeptr.
186  */
187  time_t mk_gmtime(const struct tm * timeptr);
188 
189  /**
190  The gmtime function converts the time stamp pointed to by timer into broken-down time,
191  expressed as UTC.
192  */
193  struct tm *gmtime(const time_t * timer);
194 
195  /**
196  Re entrant version of gmtime().
197  */
198  void gmtime_r(const time_t * timer, struct tm * timeptr);
199 
200  /**
201  The localtime function converts the time stamp pointed to by timer into broken-down time,
202  expressed as Local time.
203  */
204  struct tm *localtime(const time_t * timer);
205 
206  /**
207  Re entrant version of localtime().
208  */
209  void localtime_r(const time_t * timer, struct tm * timeptr);
210 
211  /**
212  The asctime function converts the broken-down time of timeptr, into an ascii string in the form
213 
214  Sun Mar 23 01:03:52 2013
215  */
216  char *asctime(const struct tm * timeptr);
217 
218  /**
219  Re entrant version of asctime().
220  */
221  void asctime_r(const struct tm * timeptr, char *buf);
222 
223  /**
224  The ctime function is equivalent to asctime(localtime(timer))
225  */
226  char *ctime(const time_t * timer);
227 
228  /**
229  Re entrant version of ctime().
230  */
231  void ctime_r(const time_t * timer, char *buf);
232 
233  /**
234  The isotime function constructs an ascii string in the form
235  \code2013-03-23 01:03:52\endcode
236  */
237  char *isotime(const struct tm * tmptr);
238 
239  /**
240  Re entrant version of isotime()
241  */
242  void isotime_r(const struct tm *, char *);
243 
244  /**
245  A complete description of strftime() is beyond the pale of this document.
246  Refer to ISO/IEC document 9899 for details.
247 
248  All conversions are made using the 'C Locale', ignoring the E or O modifiers. Due to the lack of
249  a time zone 'name', the 'Z' conversion is also ignored.
250  */
251  size_t strftime(char *s, size_t maxsize, const char *format, const struct tm * timeptr);
252 
253  /**
254  Specify the Daylight Saving function.
255 
256  The Daylight Saving function should examine its parameters to determine whether
257  Daylight Saving is in effect, and return a value appropriate for tm_isdst.
258 
259  Working examples for the USA and the EU are available..
260 
261  \code #include <util/eu_dst.h>\endcode
262  for the European Union, and
263  \code #include <util/usa_dst.h>\endcode
264  for the United States
265 
266  If a Daylight Saving function is not specified, the system will ignore Daylight Saving.
267  */
268  void set_dst(int (*) (const time_t *, int32_t *));
269 
270  /**
271  Set the 'time zone'. The parameter is given in seconds East of the Prime Meridian.
272  Example for New York City:
273  \code set_zone(-5 * ONE_HOUR);\endcode
274 
275  If the time zone is not set, the time system will operate in UTC only.
276  */
277  void set_zone(int32_t);
278 
279  /**
280  Initialize the system time. Examples are...
281 
282  From a Clock / Calendar type RTC:
283  \code
284  struct tm rtc_time;
285 
286  read_rtc(&rtc_time);
287  rtc_time.tm_isdst = 0;
288  set_system_time( mktime(&rtc_time) );
289  \endcode
290 
291  From a Network Time Protocol time stamp:
292  \code
293  set_system_time(ntp_timestamp - NTP_OFFSET);
294  \endcode
295 
296  From a UNIX time stamp:
297  \code
298  set_system_time(unix_timestamp - UNIX_OFFSET);
299  \endcode
300 
301  */
302  void set_system_time(time_t timestamp);
303 
304  /**
305  Maintain the system time by calling this function at a rate of 1 Hertz.
306 
307  It is anticipated that this function will typically be called from within an
308  Interrupt Service Routine, (though that is not required). It therefore includes code which
309  makes it simple to use from within a 'Naked' ISR, avoiding the cost of saving and restoring
310  all the cpu registers.
311 
312  Such an ISR may resemble the following example...
313  \code
314  ISR(RTC_OVF_vect, ISR_NAKED)
315  {
316  system_tick();
317  reti();
318  }
319  \endcode
320  */
321  void system_tick(void);
322 
323  /**
324  Enumerated labels for the days of the week.
325  */
326  enum _WEEK_DAYS_ {
327  SUNDAY,
328  MONDAY,
329  TUESDAY,
330  WEDNESDAY,
331  THURSDAY,
332  FRIDAY,
333  SATURDAY
334  };
335 
336  /**
337  Enumerated labels for the months.
338  */
339  enum _MONTHS_ {
340  JANUARY,
341  FEBRUARY,
342  MARCH,
343  APRIL,
344  MAY,
345  JUNE,
346  JULY,
347  AUGUST,
348  SEPTEMBER,
349  OCTOBER,
350  NOVEMBER,
351  DECEMBER
352  };
353 
354  /**
355  Return 1 if year is a leap year, zero if it is not.
356  */
358 
359  /**
360  Return the length of month, given the year and month, where month is in the range 1 to 12.
361  */
362  uint8_t month_length(int16_t year, uint8_t month);
363 
364  /**
365  Return the calendar week of year, where week 1 is considered to begin on the
366  day of week specified by 'start'. The returned value may range from zero to 52.
367  */
368  uint8_t week_of_year(const struct tm * timeptr, uint8_t start);
369 
370  /**
371  Return the calendar week of month, where the first week is considered to begin on the
372  day of week specified by 'start'. The returned value may range from zero to 5.
373  */
374  uint8_t week_of_month(const struct tm * timeptr, uint8_t start);
375 
376  /**
377  Structure which represents a date as a year, week number of that year, and day of week.
378  See http://en.wikipedia.org/wiki/ISO_week_date for more information.
379  */
380  struct week_date {
381  int year; /**< year number (Gregorian calendar) */
382  int week; /**< week number (#1 is where first Thursday is in) */
383  int day; /**< day within week */
384  };
385 
386  /**
387  Return a week_date structure with the ISO_8601 week based date corresponding to the given
388  year and day of year. See http://en.wikipedia.org/wiki/ISO_week_date for more
389  information.
390  */
391  struct week_date * iso_week_date( int year, int yday);
392 
393  /**
394  Re-entrant version of iso-week_date.
395  */
396  void iso_week_date_r( int year, int yday, struct week_date *);
397 
398  /**
399  Convert a Y2K time stamp into a FAT file system time stamp.
400  */
401  uint32_t fatfs_time(const struct tm * timeptr);
402 
403  /** One hour, expressed in seconds */
404 #define ONE_HOUR 3600
405 
406  /** Angular degree, expressed in arc seconds */
407 #define ONE_DEGREE 3600
408 
409  /** One day, expressed in seconds */
410 #define ONE_DAY 86400
411 
412  /** Difference between the Y2K and the UNIX epochs, in seconds. To convert a Y2K
413  timestamp to UNIX...
414  \code
415  long unix;
416  time_t y2k;
417 
418  y2k = time(NULL);
419  unix = y2k + UNIX_OFFSET;
420  \endcode
421  */
422 #define UNIX_OFFSET 946684800
423 
424  /** Difference between the Y2K and the NTP epochs, in seconds. To convert a Y2K
425  timestamp to NTP...
426  \code
427  unsigned long ntp;
428  time_t y2k;
429 
430  y2k = time(NULL);
431  ntp = y2k + NTP_OFFSET;
432  \endcode
433  */
434 #define NTP_OFFSET 3155673600
435 
436  /*
437  * ===================================================================
438  * Ephemera
439  */
440 
441  /**
442  Set the geographic coordinates of the 'observer', for use with several of the
443  following functions. Parameters are passed as seconds of North Latitude, and seconds
444  of East Longitude.
445 
446  For New York City...
447  \code set_position( 40.7142 * ONE_DEGREE, -74.0064 * ONE_DEGREE); \endcode
448  */
449  void set_position(int32_t latitude, int32_t longitude);
450 
451  /**
452  Computes the difference between apparent solar time and mean solar time.
453  The returned value is in seconds.
454  */
455  int16_t equation_of_time(const time_t * timer);
456 
457  /**
458  Computes the amount of time the sun is above the horizon, at the location of the observer.
459 
460  NOTE: At observer locations inside a polar circle, this value can be zero during the winter,
461  and can exceed ONE_DAY during the summer.
462 
463  The returned value is in seconds.
464  */
465  int32_t daylight_seconds(const time_t * timer);
466 
467  /**
468  Computes the time of solar noon, at the location of the observer.
469  */
470  time_t solar_noon(const time_t * timer);
471 
472  /**
473  Return the time of sunrise, at the location of the observer. See the note about daylight_seconds().
474  */
475  time_t sun_rise(const time_t * timer);
476 
477  /**
478  Return the time of sunset, at the location of the observer. See the note about daylight_seconds().
479  */
480  time_t sun_set(const time_t * timer);
481 
482  /** Returns the declination of the sun in radians. */
483  double solar_declination(const time_t * timer);
484 
485  /**
486  Returns an approximation to the phase of the moon.
487  The sign of the returned value indicates a waning or waxing phase.
488  The magnitude of the returned value indicates the percentage illumination.
489  */
490  int8_t moon_phase(const time_t * timer);
491 
492  /**
493  Returns Greenwich Mean Sidereal Time, as seconds into the sidereal day.
494  The returned value will range from 0 through 86399 seconds.
495  */
496  unsigned long gm_sidereal(const time_t * timer);
497 
498  /**
499  Returns Local Mean Sidereal Time, as seconds into the sidereal day.
500  The returned value will range from 0 through 86399 seconds.
501  */
502  unsigned long lm_sidereal(const time_t * timer);
503 
504  /* @} */
505 #ifdef __cplusplus
506 }
507 #endif
508 
509 #endif /* TIME_H */
int8_t tm_mday
Definition: time.h:148
void isotime_r(const struct tm *, char *)
Definition: isotime_r.c:41
void set_zone(int32_t)
char * ctime(const time_t *timer)
Definition: ctime.c:40
_MONTHS_
Definition: time.h:339
int8_t tm_min
Definition: time.h:146
int32_t difftime(time_t time1, time_t time0)
Definition: difftime.c:38
int8_t moon_phase(const time_t *timer)
Definition: moon_phase.c:40
struct week_date * iso_week_date(int year, int yday)
Definition: iso_week_date.c:44
int16_t tm_yday
Definition: time.h:152
int16_t tm_isdst
Definition: time.h:153
unsigned long gm_sidereal(const time_t *timer)
Definition: gm_sidereal.c:49
void asctime_r(const struct tm *timeptr, char *buf)
Definition: asctime_r.c:49
uint8_t week_of_month(const struct tm *timeptr, uint8_t start)
Definition: week_of_month.c:42
unsigned long lm_sidereal(const time_t *timer)
Definition: lm_sidereal.c:39
int week
Definition: time.h:382
void ctime_r(const time_t *timer, char *buf)
Definition: ctime_r.c:37
void iso_week_date_r(int year, int yday, struct week_date *)
Definition: iso_week_date_r.c:49
time_t mk_gmtime(const struct tm *timeptr)
Definition: mk_gmtime.c:40
signed int int16_t
Definition: stdint.h:88
signed char int8_t
Definition: stdint.h:78
int day
Definition: time.h:383
time_t solar_noon(const time_t *timer)
Definition: solar_noon.c:40
time_t sun_set(const time_t *timer)
Definition: sun_set.c:38
double solar_declination(const time_t *timer)
Definition: solar_declination.c:50
int16_t tm_year
Definition: time.h:151
int8_t tm_sec
Definition: time.h:145
signed long int int32_t
Definition: stdint.h:98
int8_t tm_hour
Definition: time.h:147
uint8_t week_of_year(const struct tm *timeptr, uint8_t start)
Definition: week_of_year.c:42
char * isotime(const struct tm *tmptr)
Definition: isotime.c:40
int16_t equation_of_time(const time_t *timer)
Definition: equation_of_time.c:54
unsigned char uint8_t
Definition: stdint.h:83
Definition: time.h:380
int8_t tm_wday
Definition: time.h:149
unsigned long int uint32_t
Definition: stdint.h:103
Definition: time.h:144
time_t sun_rise(const time_t *timer)
Definition: sun_rise.c:38
_WEEK_DAYS_
Definition: time.h:326
void set_position(int32_t latitude, int32_t longitude)
time_t mktime(struct tm *timeptr)
Definition: mktime.c:43
uint8_t is_leap_year(int16_t year)
uint8_t month_length(int16_t year, uint8_t month)
int8_t tm_mon
Definition: time.h:150
time_t time(time_t *timer)
Definition: time.c:41
uint32_t time_t
Definition: time.h:116
void set_dst(int(*)(const time_t *, int32_t *))
Definition: set_dst.c:41
char * asctime(const struct tm *timeptr)
Definition: asctime.c:40
int year
Definition: time.h:381
void gmtime_r(const time_t *timer, struct tm *timeptr)
Definition: gmtime_r.c:38
size_t strftime(char *s, size_t maxsize, const char *format, const struct tm *timeptr)
Definition: strftime.c:87
void set_system_time(time_t timestamp)
Definition: set_system_time.c:42
uint32_t fatfs_time(const struct tm *timeptr)
int32_t daylight_seconds(const time_t *timer)
Definition: daylight_seconds.c:43
struct tm * localtime(const time_t *timer)
Definition: localtime.c:40
struct tm * gmtime(const time_t *timer)
Definition: gmtime.c:41
void system_tick(void)
void localtime_r(const time_t *timer, struct tm *timeptr)
Definition: localtime_r.c:43