From 5a5c5cdeb92f4012fc75fd717bfea06598f68f12 Mon Sep 17 00:00:00 2001 From: Pavel Reichl Date: Tue, 20 Jan 2015 16:27:41 -0500 Subject: UTIL: convert GeneralizedTime to unix time MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit New utility function *sss_utc_to_time_t* to convert GeneralizedTime to unix time. Reviewed-by: Lukáš Slebodník Reviewed-by: Jakub Hrozek --- src/util/util.c | 53 ++++++++++++++++++++++++++++++++++++++++++++++++++ src/util/util.h | 3 +++ src/util/util_errors.c | 1 + src/util/util_errors.h | 1 + 4 files changed, 58 insertions(+) (limited to 'src/util') diff --git a/src/util/util.c b/src/util/util.c index 613c559bb..cfd26a58b 100644 --- a/src/util/util.c +++ b/src/util/util.c @@ -18,6 +18,7 @@ along with this program. If not, see . */ +#include "config.h" #include #include #include @@ -26,6 +27,7 @@ #include #include #include +#include #include "util/util.h" #include "util/sss_utf8.h" @@ -904,3 +906,54 @@ errno_t sss_fd_nonblocking(int fd) return EOK; } + +/* Convert GeneralizedTime (http://en.wikipedia.org/wiki/GeneralizedTime) + * to unix time (seconds since epoch). Use UTC time zone. + */ +errno_t sss_utc_to_time_t(const char *str, const char *format, time_t *_unix_time) +{ + char *end; + struct tm tm; + size_t len; + time_t ut; + + if (str == NULL) { + return EINVAL; + } + + len = strlen(str); + if (str[len-1] != 'Z') { + DEBUG(SSSDBG_TRACE_INTERNAL, + "%s does not seem to be in UTZ time zone.\n", str); + return ERR_TIMESPEC_NOT_SUPPORTED; + } + + memset(&tm, 0, sizeof(tm)); + + end = strptime(str, format, &tm); + /* not all characters from format were matched */ + if (end == NULL) { + DEBUG(SSSDBG_TRACE_INTERNAL, + "String [%s] failed to match format [%s].\n", str, format); + return EINVAL; + } + + /* str is 'longer' than format */ + if (*end != '\0') { + DEBUG(SSSDBG_TRACE_INTERNAL, + "String [%s] is longer than format [%s].\n", str, format); + return EINVAL; + } + + ut = mktime(&tm); + if (ut == -1) { + DEBUG(SSSDBG_TRACE_INTERNAL, + "mktime failed to convert [%s].\n", str); + return EINVAL; + } + + tzset(); + ut -= timezone; + *_unix_time = ut; + return EOK; +} diff --git a/src/util/util.h b/src/util/util.h index 22d6ef0a4..829cf567a 100644 --- a/src/util/util.h +++ b/src/util/util.h @@ -648,4 +648,7 @@ int set_seuser(const char *login_name, const char *seuser_name, const char *mlsrange); int del_seuser(const char *login_name); +/* convert time from generalized form to unix time */ +errno_t sss_utc_to_time_t(const char *str, const char *format, time_t *unix_time); + #endif /* __SSSD_UTIL_H__ */ diff --git a/src/util/util_errors.c b/src/util/util_errors.c index 16d16fc77..bfae5cd18 100644 --- a/src/util/util_errors.c +++ b/src/util/util_errors.c @@ -65,6 +65,7 @@ struct err_string error_to_str[] = { { "LDAP search returned a referral" }, /* ERR_REFERRAL */ { "Error setting SELinux user context" }, /* ERR_SELINUX_CONTEXT */ { "Username format not allowed by re_expression" }, /* ERR_REGEX_NOMATCH */ + { "Time specification not supported" }, /* ERR_TIMESPEC_NOT_SUPPORTED */ }; diff --git a/src/util/util_errors.h b/src/util/util_errors.h index 97e210e31..069d4b78a 100644 --- a/src/util/util_errors.h +++ b/src/util/util_errors.h @@ -90,6 +90,7 @@ enum sssd_errors { ERR_REFERRAL, ERR_SELINUX_CONTEXT, ERR_REGEX_NOMATCH, + ERR_TIMESPEC_NOT_SUPPORTED, ERR_LAST /* ALWAYS LAST */ }; -- cgit