X-Git-Url: https://git.cameronkatri.com/pw-darwin.git/blobdiff_plain/0b3bc144008c93d61f3720daf8aeff915df65ede..fcf4b2f12ab5618542cc036a40239eedd658f95a:/pw/psdate.c diff --git a/pw/psdate.c b/pw/psdate.c index d77f1e3..8c833b5 100644 --- a/pw/psdate.c +++ b/pw/psdate.c @@ -1,4 +1,6 @@ /*- + * SPDX-License-Identifier: BSD-2-Clause-FreeBSD + * * Copyright (C) 1996 * David L. Nugent. All rights reserved. * @@ -22,42 +24,27 @@ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. - * - * $FreeBSD$ */ -#include +#ifndef lint +static const char rcsid[] = + "$FreeBSD$"; +#endif /* not lint */ + +#include +#include #include #include -#include +#include #include "psdate.h" -static int -a2i(char const ** str) -{ - int i = 0; - char const *s = *str; - - if (isdigit(*s)) { - i = atoi(s); - while (isdigit(*s)) - ++s; - *str = s; - } - return i; -} - -static int +int numerics(char const * str) { - int rc = isdigit(*str); - if (rc) - while (isdigit(*str) || *str == 'x') - ++str; - return rc && !*str; + return (str[strspn(str, "0123456789x")] == '\0'); } static int @@ -69,15 +56,15 @@ aindex(char const * arr[], char const ** str, int len) mystr[len] = '\0'; l = strlen(strncpy(mystr, *str, len)); for (i = 0; i < l; i++) - mystr[i] = (char) tolower(mystr[i]); + mystr[i] = (char) tolower((unsigned char)mystr[i]); for (i = 0; arr[i] && strcmp(mystr, arr[i]) != 0; i++); if (arr[i] == NULL) i = -1; else { /* Skip past it */ - while (**str && isalpha(**str)) + while (**str && isalpha((unsigned char)**str)) ++(*str); /* And any following whitespace */ - while (**str && (**str == ',' || isspace(**str))) + while (**str && (**str == ',' || isspace((unsigned char)**str))) ++(*str); } /* Return index */ return i; @@ -92,61 +79,73 @@ weekday(char const ** str) return aindex(days, str, 3); } -static int -month(char const ** str) -{ - static char const *months[] = - {"jan", "feb", "mar", "apr", "may", "jun", "jul", - "aug", "sep", "oct", "nov", "dec", NULL}; - - return aindex(months, str, 3); -} - static void -parse_time(char const * str, int *hour, int *min, int *sec) +parse_datesub(char const * str, struct tm *t) { - *hour = a2i(&str); - if ((str = strchr(str, ':')) == NULL) - *min = *sec = 0; - else { - ++str; - *min = a2i(&str); - *sec = ((str = strchr(str, ':')) == NULL) ? 0 : atoi(++str); + struct tm tm; + locale_t l; + int i; + char *ret; + const char *valid_formats[] = { + "%d-%b-%y", + "%d-%b-%Y", + "%d-%m-%y", + "%d-%m-%Y", + "%H:%M %d-%b-%y", + "%H:%M %d-%b-%Y", + "%H:%M %d-%m-%y", + "%H:%M %d-%m-%Y", + "%H:%M:%S %d-%b-%y", + "%H:%M:%S %d-%b-%Y", + "%H:%M:%S %d-%m-%y", + "%H:%M:%S %d-%m-%Y", + "%d-%b-%y %H:%M", + "%d-%b-%Y %H:%M", + "%d-%m-%y %H:%M", + "%d-%m-%Y %H:%M", + "%d-%b-%y %H:%M:%S", + "%d-%b-%Y %H:%M:%S", + "%d-%m-%y %H:%M:%S", + "%d-%m-%Y %H:%M:%S", + "%H:%M\t%d-%b-%y", + "%H:%M\t%d-%b-%Y", + "%H:%M\t%d-%m-%y", + "%H:%M\t%d-%m-%Y", + "%H:%M\t%S %d-%b-%y", + "%H:%M\t%S %d-%b-%Y", + "%H:%M\t%S %d-%m-%y", + "%H:%M\t%S %d-%m-%Y", + "%d-%b-%y\t%H:%M", + "%d-%b-%Y\t%H:%M", + "%d-%m-%y\t%H:%M", + "%d-%m-%Y\t%H:%M", + "%d-%b-%y\t%H:%M:%S", + "%d-%b-%Y\t%H:%M:%S", + "%d-%m-%y\t%H:%M:%S", + "%d-%m-%Y\t%H:%M:%S", + NULL, + }; + + l = newlocale(LC_ALL_MASK, "C", NULL); + + memset(&tm, 0, sizeof(tm)); + for (i=0; valid_formats[i] != NULL; i++) { + ret = strptime_l(str, valid_formats[i], &tm, l); + if (ret && *ret == '\0') { + t->tm_mday = tm.tm_mday; + t->tm_mon = tm.tm_mon; + t->tm_year = tm.tm_year; + t->tm_hour = tm.tm_hour; + t->tm_min = tm.tm_min; + t->tm_sec = tm.tm_sec; + freelocale(l); + return; + } } -} + freelocale(l); -static void -parse_datesub(char const * str, int *day, int *mon, int *year) -{ - int i; - - static char const nchrs[] = "0123456789 \t,/-."; - - if ((i = month(&str)) != -1) { - *mon = i; - if ((i = a2i(&str)) != 0) - *day = i; - } else if ((i = a2i(&str)) != 0) { - *day = i; - while (*str && strchr(nchrs + 10, *str) != NULL) - ++str; - if ((i = month(&str)) != -1) - *mon = i; - else if ((i = a2i(&str)) != 0) - *mon = i - 1; - } else - return; - - while (*str && strchr(nchrs + 10, *str) != NULL) - ++str; - if (isdigit(*str)) { - *year = atoi(str); - if (*year > 1900) - *year -= 1900; - else if (*year < 32) - *year += 100; - } + errx(EXIT_FAILURE, "Invalid date"); } @@ -173,12 +172,11 @@ parse_date(time_t dt, char const * str) if (dt == 0) dt = time(NULL); - while (*str && isspace(*str)) + while (*str && isspace((unsigned char)*str)) ++str; if (numerics(str)) { - val = strtol(str, &p, 0); - dt = val ? val : dt; + dt = strtol(str, &p, 0); } else if (*str == '+' || *str == '-') { val = strtol(str, &p, 0); switch (*p) { @@ -232,8 +230,8 @@ parse_date(time_t dt, char const * str) * Skip past any weekday prefix */ weekday(&str); - str = strncpy(tmp, str, sizeof tmp - 1); - tmp[sizeof tmp - 1] = '\0'; + strlcpy(tmp, str, sizeof(tmp)); + str = tmp; T = localtime(&dt); /* @@ -245,7 +243,7 @@ parse_date(time_t dt, char const * str) else { int j = 1; - while (q[j] && isupper(q[j])) + while (q[j] && isupper((unsigned char)q[j])) ++j; if (q[j] == '\0') *q = '\0'; @@ -254,43 +252,7 @@ parse_date(time_t dt, char const * str) } } - /* - * See if there is a time hh:mm[:ss] - */ - if ((p = strchr(tmp, ':')) == NULL) { - - /* - * No time string involved - */ - T->tm_hour = T->tm_min = T->tm_sec = 0; - parse_datesub(tmp, &T->tm_mday, &T->tm_mon, &T->tm_year); - } else { - char datestr[64], timestr[64]; - - /* - * Let's chip off the time string - */ - if ((q = strpbrk(p, " \t")) != NULL) { /* Time first? */ - int l = q - str; - - strncpy(timestr, str, l); - timestr[l] = '\0'; - strncpy(datestr, q + 1, sizeof datestr); - datestr[sizeof datestr - 1] = '\0'; - parse_time(timestr, &T->tm_hour, &T->tm_min, &T->tm_sec); - parse_datesub(datestr, &T->tm_mday, &T->tm_mon, &T->tm_year); - } else if ((q = strrchr(tmp, ' ')) != NULL) { /* Time last */ - int l = q - tmp; - - strncpy(timestr, q + 1, sizeof timestr); - timestr[sizeof timestr - 1] = '\0'; - strncpy(datestr, tmp, l); - datestr[l] = '\0'; - } else /* Bail out */ - return dt; - parse_time(timestr, &T->tm_hour, &T->tm_min, &T->tm_sec); - parse_datesub(datestr, &T->tm_mday, &T->tm_mon, &T->tm_year); - } + parse_datesub(tmp, T); dt = mktime(T); } return dt;