/* * libopensync - A synchronization framework * Copyright (C) 2004-2005 Armin Bauer * Copyright (C) 2006-2008 Daniel Gollub * Copyright (C) 2007 Chris Frey * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. * * You should have received a copy of the GNU Lesser General Public * License along with this library; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA * */ #ifndef _OPENSYNC_TIME_H_ #define _OPENSYNC_TIME_H_ /** * @defgroup OSyncTimeAPI OpenSync Time * @ingroup OSyncFormat * @brief The public part of the OSyncTimeAPI * */ /** * @defgroup OSyncTimeFormatting Time formatting helpers * @ingroup OSyncTimeAPI * @brief Helper functions for formatting time strings, stripping out * invalid characters, etc. */ /*@{*/ /* * Time formatting helper */ /** @brief Function returns a date-timestamp in OSyncTime Spec format * OSyncTime Spec format is YYYYMMDDTHHMMSSZ with Z optional. * Input format can be in ISO 8601, including dashes and timezone * offsets, and the returned timestamp will adjust it to UTC. * * @param vtime The timestamp which gets converted to a valid osync date-timestamp * @returns vtime date-timestring (the caller is responsible for freeing) */ OSYNC_EXPORT char *osync_time_timestamp(const char *vtime); /** @brief Function returns a date without timestamp in OSyncTime Spec format * * @param vtime The timestamp which gets converted to a single datestamp * @returns valid single datestamp YYYYMMDD (the caller is responsible for freeing) */ OSYNC_EXPORT char *osync_time_datestamp(const char *vtime); /** @brief Function returns TRUE if vtime is a valid datestamp (YYYYMMDD) * * @returns FALSE if vtime includes a timestamp, TRUE on a single datestamp */ OSYNC_EXPORT osync_bool osync_time_isdate(const char *vformat); /** @brief Function returns TRUE if vtime is in UTC (YYYYMMDDTHH:MM:SSZ) * * @returns FALSE if vtime includes no Zulu, TRUE if the timestamp is UTC */ OSYNC_EXPORT osync_bool osync_time_isutc(const char *vformat); /*@}*/ /*****************************************************************************/ /** * @defgroup OSyncTimeStringToStruct String to struct converters. * @ingroup OSyncTimeAPI * @brief Helper functions for converting time between vtime formatted * strings and struct tm time structures. These functions are not * smart in any way, with regards to timezones or daylight saving * time, nor do they need to be. * */ /*@{*/ /** @brief Function converts vtime to tm struct * * @param vtime The formatted timestamp (YYYYMMDDTHHMMSS) * @param error An OSyncError struct * @returns struct tm (caller is responsible for freeing), NULL on error */ OSYNC_EXPORT struct tm *osync_time_vtime2tm(const char *vtime, OSyncError **error); /** @brief Function converts struct tm in vtime string * * YYYYMMDDTHHMMSS[Z] * Returned timezone is equal to the timezone of struct tm. * * @param time The tm struct which gets converted * @param is_utc If struct tm is UTC time is_utc have to be TRUE * @param error An OSyncError struct * @returns vtime formatted as YYYYMMDDTHHMMSS[Z] (caller is responsible for freeing) */ OSYNC_EXPORT char *osync_time_tm2vtime(const struct tm *time, osync_bool is_utc, OSyncError **error); /*@}*/ /*****************************************************************************/ /** * @defgroup OSyncTimeUnixTimeConverters Unix time converters * @ingroup OSyncTimeAPI * @brief Helper functions for converting to and from unix time_t * timestamps. Includes functions supporting vtime strings, * and struct tm's in local and UTC time. * */ /*@{*/ /** @brief Function converts vtime to unix time * * @param offset Seconds of UTC offset * @param vtime The osync formmatted timestamp * @param error An OSyncError struct * @returns Unix timestamp in time_t (UTC), ((time_t)-1) on error */ OSYNC_EXPORT time_t osync_time_vtime2unix(const char *vtime, int offset, OSyncError **error); /** @brief Function converts unix timestamp to vtime in UTC * * @param timestamp The unix timestamp which gets converted * @param error An OSyncError struct * @returns vtime formatted as YYYYMMDDTHHMMSSZ (caller is responsible for freeing) */ OSYNC_EXPORT char *osync_time_unix2vtime(const time_t *timestamp, OSyncError **error); /* Unix time_t converters */ /** @brief Function converts struct tm, in localtime, to unix timestamp. * This is the same as calling mktime(), except that * localtime is not modified, and tm_isdst is always * forced to -1. Aka, mktime(). * * @param localtime The struct tm, in localtime, which gets converted * @param error An OSyncError struct * @returns time_t (in UTC of course), ((time_t)-1) on error */ OSYNC_EXPORT time_t osync_time_localtm2unix(const struct tm *localtime, OSyncError **error); /** @brief Function converts struct tm, in utc, to unix timestamp. * * @param utctime The struct tm, in utc, which gets converted * @param error An OSyncError struct * @returns time_t (in UTC of course), ((time_t)-1) on error * * This algorithm abuses the POSIX time functions, only because * there seems to be no standard API to do this more simply. * We could use the tm2utc() and tm2localtime() functions defined * farther on, but those are just simple math, and assume completely * that the offset provided is perfectly accurate. This is not * always the case, when all you have is a random date in a tm struct. * * If there is a better way, I'd love to know! - cdfrey */ OSYNC_EXPORT time_t osync_time_utctm2unix(const struct tm *utctime, OSyncError **error); /** @brief Function converts unix timestamp to struct tm in localtime. * This is the same as calling localtime_r(), except you * have to free the returned value. Aka, localtime(). * * @param timestamp The unixtimestamp which gets converted * @param error An OSyncError struct * @returns: struct tm (in localtime) (Caller is responsible for freeing!), * NULL on error */ OSYNC_EXPORT struct tm *osync_time_unix2localtm(const time_t *timestamp, OSyncError **error); /** @brief Function converts unix timestamp to struct tm in utc. * This is the same as calling gmtime_r(), except you * have to free the returned value. Aka, gmtime(). * * @param timestamp The unixtimestamp which gets converted * @paran error An OSyncError struct * @returns: struct tm (in UTC) (Caller is responsible for freeing), NULL on error */ OSYNC_EXPORT struct tm *osync_time_unix2utctm(const time_t *timestamp, OSyncError **error); /*@}*/ /*****************************************************************************/ /** * @defgroup OSyncTimeTimezoneHelpers Timezone helpers * @ingroup OSyncTimeAPI * @brief Helper functions for working with timezones, and doing * conversions with user-specified timezone offsets. * Note that in all functions below that require a timezone offset, * they *require* the caller to be completely accurate with it, * including in the DST case. The result is only as accurate * as the offset you provide. * */ /*@{*/ /** @brief Function gets offset of parameter time between UTC and * localtime in seconds east of UTC. (i.e. east is positive, * west is negative) * * @param local The point in time when the offset have to be calculated, * specified in localtime (need for CEST/CET) * @param error An OSyncError struct. Always check if error is set using * osync_error_is_set(error) before using the return value * @return Seconds of timezone offset. On error, sets the error parameter, * and the return value cannot be relied upon. */ OSYNC_EXPORT int osync_time_timezone_diff(const struct tm *local, OSyncError **error); /** @brief Parse an ISO 8601 timestamp string, and if a timezone offset * exists, return an offset suitable for feeding into vtime2unix(). * (seconds east of UTC.. i.e. east is positive, west is negative) * * @param iso_vtime String containing an ISO 8601 timestamp string, in the * format of YYYYMMDDTHHMMSS-HHMM or YYYY-MM-DDTHH:MM:SS-HH:MM. * @param found Pointer to an int. Will be set to 1 if a valid offset was * found, or 0 if not. Not all timestamps have a timezone offset. * If not found, 0 will also be returned as the offset. * @param error An OSyncError struct. Always check if error is set using * osync_error_is_set(error) before using the return value. A non- * existing timezone offset is not an error, but a mal-formed one, * like "-03:0" is an error. * @return Seconds of timezone offset. On error, sets the error parameter, * and the return value will be zero. If no offset is found in the * string, return is zero. */ OSYNC_EXPORT int osync_time_parse_iso_timezone_diff(const char *iso_vtime, int *found, OSyncError **error); /** @brief Function converts (struct tm) ltime from localtime to UTC. * Paramter offset is used as UTC offset. Note that _only_ the * following fields can be relied upon in the result: * tm_sec, tm_min, tm_hour, tm_mday, tm_mon, tm_year. * * @param ltime The struct tm which gets converted to UTC timezone * @param offset Seconds of UTC offset, in seconds east of UTC. * @param error An OSyncError struct * @returns struct tm in UTC (caller is responsible for freeing), NULL on error */ OSYNC_EXPORT struct tm *osync_time_tm2utc(const struct tm *ltime, int offset, OSyncError **error); /** @brief Function converts (struct tm) utime from UTC to localtime * Paramter offset is used as UTC offset. Note that _only_ the * following fields can be relied upon in the result: * tm_sec, tm_min, tm_hour, tm_mday, tm_mon, tm_year. * * @param utime The struct tm which gets converted to localtime * @param offset Seconds of UTC offset, in seconds east of UTC. * @param error An OSyncError struct * @returns struct tm in localtime (caller is responsible for freeing), * NULL on error */ OSYNC_EXPORT struct tm *osync_time_tm2localtime(const struct tm *utime, int offset, OSyncError **error); /** @brief Functions converts a localtime vtime stamp to a UTC vtime stamp * * @param localtime The local timestamp in vtime format * @param offset Seconds of UTC offset, in seconds east of UTC. * @param error An OSyncError struct * @returns vtime in UTC timezone (caller is responsible for freeing), * NULL on error */ OSYNC_EXPORT char *osync_time_vtime2utc(const char* localtime, int offset, OSyncError **error); /** @brief Functions converts a UTC vtime stamp to a localtime vtime stamp * * @param utc The timestap in UTC timezone which gets converted to localtime * @param offset The offset in seconds between UTC and localtime * @param error An OSyncError struct * @returns vtime in local timezon (caller is preponsible for freeing), * NULL on error */ OSYNC_EXPORT char *osync_time_vtime2localtime(const char* utc, int offset, OSyncError **error); /** @brief Function converts UTC offset string in offset in seconds * * @param offset The offset string of the form a timezone field (Example +0200) * @error An OSyncError struct * @returns seconds of UTC offset. On error, osync_error_is_set(error) is * true, and the return value is 0. */ OSYNC_EXPORT int osync_time_utcoffset2sec(const char *offset, OSyncError **error); /*@}*/ /*****************************************************************************/ /** * @defgroup OSyncTimeBackwardCompatibility Backward compatibility functions. * @ingroup OSyncTimeAPI * @brief These functions should only be used as workaround for plugins * which only support localtime without any timezone information. * * XXX This functions should only be used as workaround for plugins which * only supports localtime without any timezone information. */ /*@{*/ /** @brief Functions converts timestamps of vcal to localtime * * @param vcal The vcalendar which has to be converted. * @param error An OSyncError struct * @return modified vcalendar with local timestamps (related to system time). * Rely on error to detect error, not return value. */ OSYNC_EXPORT char *osync_time_vcal2localtime(const char *vcal, OSyncError **error); /** @brief Functions converts timestamps of vcal to UTC * * @param vcal The vcalendar which has to be converted. * @param error An OSyncError struct * @return modified vcalendar with UTC timestamps (related to system time) * Rely on error to detect error, not return value. */ OSYNC_EXPORT char *osync_time_vcal2utc(const char *vcal, OSyncError **error); /*@}*/ /*****************************************************************************/ /** * @defgroup OSyncTimeAlarmDurationFormat Alarm duration format helpers. * @ingroup OSyncTimeAPI * @brief Functions for converting alarm durations to and from string formats. * */ /*@{*/ /** @brief Functions converts seconds in duration before or after alarm event * * @param seconds * @returns ical alarm duration string (caller is preponsible for freeing) */ OSYNC_EXPORT char *osync_time_sec2alarmdu(int seconds); /** @brief Functions converts alarm duration event to seconds needed for reminder of vcal/ical * * TODO: Test support for ALARM after/before end and after start * * @param alarm * @returns seconds of alarm and duration */ OSYNC_EXPORT int osync_time_alarmdu2sec(const char *alarm); /*@}*/ /*****************************************************************************/ /** * @defgroup OSyncTimeRecurrence Recurring time calculators. * @ingroup OSyncTimeAPI * @brief Functions related to calculating recurring dates. * */ /*@{*/ /** @brief Function converts a week day string to the struct tm wday integer. * * FIXME: how do we handle iCal weekday strings with multiple days? * something like the following? * int osync_time_str2wday(const char *weekday, int *wdaymap); * * @param swday string of the week day * @returns integer of the weekday (Sunday = 0), or -1 on error */ OSYNC_EXPORT int osync_time_str2wday(const char *swday); /** @brief Function determines the exact date of relative information. * It is used for example to determine the last sunday of a month (-1SU) * in a specific year. * Note that the RFC2445 spec states that a weekday without * a prefixed numeric value means *every* weekday in the month. * This function will fail in such a case and return NULL. * Also note that if byday contains multiple weekdays in its * string (e.g. -1SU,MO) only the first weekday will be used (SU). * * @param byday string of the relative day of month modifier * @param bymonth calendar number of the month (January = 1) * @param year calendar year (e.g. 1970, 2007, etc) * @param error An OSyncError struct * @returns struct tm of the relative information date with 00:00:00 timestamp * or NULL on error. * (Caller is responsible for freeing) */ OSYNC_EXPORT struct tm *osync_time_relative2tm(const char *byday, const int bymonth, const int year, OSyncError **error); /*@}*/ #endif /*_OPENSYNC_TIME_H_*/