2 * Bacula floating point time and date routines -- John Walker
4 * Later double precision integer time/date routines -- Kern Sibbald
9 Bacula® - The Network Backup Solution
11 Copyright (C) 2000-2006 Free Software Foundation Europe e.V.
13 The main author of Bacula is Kern Sibbald, with contributions from
14 many others, a complete list can be found in the file AUTHORS.
15 This program is Free Software; you can redistribute it and/or
16 modify it under the terms of version two of the GNU General Public
17 License as published by the Free Software Foundation plus additions
18 that are listed in the file LICENSE.
20 This program is distributed in the hope that it will be useful, but
21 WITHOUT ANY WARRANTY; without even the implied warranty of
22 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
23 General Public License for more details.
25 You should have received a copy of the GNU General Public License
26 along with this program; if not, write to the Free Software
27 Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
30 Bacula® is a registered trademark of John Walker.
31 The licensor of Bacula is the Free Software Foundation Europe
32 (FSFE), Fiduciary Program, Sumatrastrasse 25, 8006 Zürich,
33 Switzerland, email:ftf@fsfeurope.org.
37 /* Concerning times. There are a number of differnt time standards
38 * in Bacula (fdate_t, ftime_t, time_t (Unix standard), btime_t, and
39 * utime_t). fdate_t and ftime_t are deprecated and should no longer
40 * be used, and in general, Unix time time_t should no longer be used,
41 * it is being phased out.
43 * Epoch is the base of Unix time in seconds (time_t, ...)
44 * and is 1 Jan 1970 at 0:0 UTC
46 * The major two times that should be left are:
47 * btime_t (64 bit integer in microseconds base Epoch)
48 * utime_t (64 bit integer in seconds base Epoch)
54 /* Formatted time for user display: dd-Mon-yyyy hh:mm */
55 char *bstrftime(char *dt, int maxlen, utime_t tim)
57 time_t ttime = (time_t)tim;
60 /* ***FIXME**** the format and localtime_r() should be user configurable */
61 (void)localtime_r(&ttime, &tm);
62 strftime(dt, maxlen, "%d-%b-%Y %H:%M", &tm);
66 /* Formatted time for user display: dd-Mon-yyyy hh:mm:ss */
67 char *bstrftimes(char *dt, int maxlen, utime_t tim)
69 time_t ttime = (time_t)tim;
72 /* ***FIXME**** the format and localtime_r() should be user configurable */
73 (void)localtime_r(&ttime, &tm);
74 strftime(dt, maxlen, "%d-%b-%Y %H:%M:%S", &tm);
79 /* Formatted time for user display: dd-Mon hh:mm */
80 char *bstrftime_ny(char *dt, int maxlen, utime_t tim)
82 time_t ttime = (time_t)tim;
85 /* ***FIXME**** the format and localtime_r() should be user configurable */
86 (void)localtime_r(&ttime, &tm);
87 strftime(dt, maxlen, "%d-%b %H:%M", &tm);
92 /* Formatted time for user display: dd-Mon-yy hh:mm (no century) */
93 char *bstrftime_nc(char *dt, int maxlen, utime_t tim)
95 time_t ttime = (time_t)tim;
98 /* ***FIXME**** the format and localtime_r() should be user configurable */
99 (void)localtime_r(&ttime, &tm);
100 /* NOTE! since the compiler complains about %y, I use %y and cut the century */
101 strftime(dt, maxlen, "%d-%b-%Y %H:%M", &tm);
107 /* Unix time to standard time string yyyy-mm-dd hh:mm:ss */
108 char *bstrutime(char *dt, int maxlen, utime_t tim)
110 time_t ttime = (time_t)tim;
112 (void)localtime_r(&ttime, &tm);
113 strftime(dt, maxlen, "%Y-%m-%d %H:%M:%S", &tm);
117 /* Convert standard time string yyyy-mm-dd hh:mm:ss to Unix time */
118 utime_t str_to_utime(char *str)
123 /* Check for bad argument */
124 if (!str || *str == 0) {
128 if (sscanf(str, "%d-%d-%d %d:%d:%d", &tm.tm_year, &tm.tm_mon, &tm.tm_mday,
129 &tm.tm_hour, &tm.tm_min, &tm.tm_sec) != 6) {
137 if (tm.tm_year >= 1900) {
142 tm.tm_wday = tm.tm_yday = 0;
148 return (utime_t)ttime;
153 * Bacula's time (btime_t) is an unsigned 64 bit integer that contains
154 * the number of microseconds since Epoch Time (1 Jan 1970) UTC.
157 btime_t get_current_btime()
160 if (gettimeofday(&tv, NULL) != 0) {
161 tv.tv_sec = (long)time(NULL); /* fall back to old method */
164 return ((btime_t)tv.tv_sec) * 1000000 + (btime_t)tv.tv_usec;
167 /* Convert btime to Unix time */
168 time_t btime_to_unix(btime_t bt)
170 return (time_t)(bt/1000000);
173 /* Convert btime to utime */
174 utime_t btime_to_utime(btime_t bt)
176 return (utime_t)(bt/1000000);
180 * Return the week of the month, base 0 (wom)
181 * given tm_mday and tm_wday. Value returned
182 * can be from 0 to 4 => week1, ... week5
184 int tm_wom(int mday, int wday)
186 int fs; /* first sunday */
187 fs = (mday%7) - wday;
192 // Dmsg3(100, "mday=%d wom=0 wday=%d <= fs=%d\n", mday, wday, fs);
195 int wom = 1 + (mday - fs - 1) / 7;
196 // Dmsg4(100, "mday=%d wom=%d wday=%d fs=%d\n", mday, wom, wday, fs);
201 * Given a Unix date return the week of the year.
202 * The returned value can be 0-53. Officially
203 * the weeks are numbered from 1 to 53 where week1
204 * is the week in which the first Thursday of the
205 * year occurs (alternatively, the week which contains
206 * the 4th of January). We return 0, if the week of the
207 * year does not fall in the current year.
209 int tm_woy(time_t stime)
211 int woy, fty, tm_yday;
214 memset(&tm, 0, sizeof(struct tm));
215 (void)localtime_r(&stime, &tm);
216 tm_yday = tm.tm_yday;
220 (void)localtime_r(&time4, &tm);
221 fty = 1 - tm.tm_wday;
225 woy = tm_yday - fty + 4;
232 /* Deprecated. Do not use. */
233 void get_current_time(struct date_time *dt)
239 (void)gmtime_r(&now, &tm);
240 Dmsg6(200, "m=%d d=%d y=%d h=%d m=%d s=%d\n", tm.tm_mon+1, tm.tm_mday, tm.tm_year+1900,
241 tm.tm_hour, tm.tm_min, tm.tm_sec);
244 Dmsg2(200, "jday=%f jmin=%f\n", dt->julian_day_number, dt->julian_day_fraction);
246 Dmsg6(200, "m=%d d=%d y=%d h=%d m=%d s=%d\n", tm.tm_mon+1, tm.tm_mday, tm.tm_year+1900,
247 tm.tm_hour, tm.tm_min, tm.tm_sec);
252 /* date_encode -- Encode civil date as a Julian day number. */
254 /* Deprecated. Do not use. */
255 fdate_t date_encode(uint32_t year, uint8_t month, uint8_t day)
258 /* Algorithm as given in Meeus, Astronomical Algorithms, Chapter 7, page 61 */
264 ASSERT(day > 0 && day < 32);
274 /* Determine whether date is in Julian or Gregorian calendar based on
275 canonical date of calendar reform. */
277 if ((year < 1582) || ((year == 1582) && ((month < 9) || (month == 9 && day < 5)))) {
280 a = ((int) (y / 100));
284 return (((int32_t) (365.25 * (y + 4716))) + ((int) (30.6001 * (m + 1))) +
288 /* time_encode -- Encode time from hours, minutes, and seconds
289 into a fraction of a day. */
291 /* Deprecated. Do not use. */
292 ftime_t time_encode(uint8_t hour, uint8_t minute, uint8_t second,
293 float32_t second_fraction)
295 ASSERT((second_fraction >= 0.0) || (second_fraction < 1.0));
296 return (ftime_t) (((second + 60L * (minute + 60L * hour)) / 86400.0)) +
300 /* date_time_encode -- Set day number and fraction from date
303 /* Deprecated. Do not use. */
304 void date_time_encode(struct date_time *dt,
305 uint32_t year, uint8_t month, uint8_t day,
306 uint8_t hour, uint8_t minute, uint8_t second,
307 float32_t second_fraction)
309 dt->julian_day_number = date_encode(year, month, day);
310 dt->julian_day_fraction = time_encode(hour, minute, second, second_fraction);
313 /* date_decode -- Decode a Julian day number into civil date. */
315 /* Deprecated. Do not use. */
316 void date_decode(fdate_t date, uint32_t *year, uint8_t *month,
319 fdate_t z, f, a, alpha, b, c, d, e;
328 alpha = floor((z - 1867216.25) / 36524.25);
329 a = z + 1 + alpha - floor(alpha / 4);
333 c = floor((b - 122.1) / 365.25);
334 d = floor(365.25 * c);
335 e = floor((b - d) / 30.6001);
337 *day = (uint8_t) (b - d - floor(30.6001 * e) + f);
338 *month = (uint8_t) ((e < 14) ? (e - 1) : (e - 13));
339 *year = (uint32_t) ((*month > 2) ? (c - 4716) : (c - 4715));
342 /* time_decode -- Decode a day fraction into civil time. */
344 /* Deprecated. Do not use. */
345 void time_decode(ftime_t time, uint8_t *hour, uint8_t *minute,
346 uint8_t *second, float32_t *second_fraction)
350 ij = (uint32_t) ((time - floor(time)) * 86400.0);
351 *hour = (uint8_t) (ij / 3600L);
352 *minute = (uint8_t) ((ij / 60L) % 60L);
353 *second = (uint8_t) (ij % 60L);
354 if (second_fraction != NULL) {
355 *second_fraction = (float32_t)(time - floor(time));
359 /* date_time_decode -- Decode a Julian day and day fraction
360 into civil date and time. */
362 /* Deprecated. Do not use. */
363 void date_time_decode(struct date_time *dt,
364 uint32_t *year, uint8_t *month, uint8_t *day,
365 uint8_t *hour, uint8_t *minute, uint8_t *second,
366 float32_t *second_fraction)
368 date_decode(dt->julian_day_number, year, month, day);
369 time_decode(dt->julian_day_fraction, hour, minute, second, second_fraction);
372 /* tm_encode -- Encode a civil date and time from a tm structure
373 * to a Julian day and day fraction.
376 /* Deprecated. Do not use. */
377 void tm_encode(struct date_time *dt,
381 uint8_t month, day, hour, minute, second;
383 year = tm->tm_year + 1900;
384 month = tm->tm_mon + 1;
389 dt->julian_day_number = date_encode(year, month, day);
390 dt->julian_day_fraction = time_encode(hour, minute, second, 0.0);
394 /* tm_decode -- Decode a Julian day and day fraction
395 into civil date and time in tm structure */
397 /* Deprecated. Do not use. */
398 void tm_decode(struct date_time *dt,
402 uint8_t month, day, hour, minute, second;
404 date_decode(dt->julian_day_number, &year, &month, &day);
405 time_decode(dt->julian_day_fraction, &hour, &minute, &second, NULL);
406 tm->tm_year = year - 1900;
407 tm->tm_mon = month - 1;
415 /* date_time_compare -- Compare two dates and times and return
416 the relationship as follows:
423 /* Deprecated. Do not use. */
424 int date_time_compare(struct date_time *dt1, struct date_time *dt2)
426 if (dt1->julian_day_number == dt2->julian_day_number) {
427 if (dt1->julian_day_fraction == dt2->julian_day_fraction) {
430 return (dt1->julian_day_fraction < dt2->julian_day_fraction) ? -1 : 1;
432 return (dt1->julian_day_number - dt2->julian_day_number) ? -1 : 1;