shadow-maint / shadow

Upstream shadow tree
Other
292 stars 228 forks source link

Use getdate(3); remove get_date() #944

Closed alejandro-colomar closed 6 months ago

alejandro-colomar commented 6 months ago

@kenion, @jubalh, before I start investigating into the second (actually, the first) part of the bug that you reported, I was wondering if this would fix it by chance. Maybe something inside get_date() is broken, and this solves it. Would you mind testing with these patches?

kenion commented 6 months ago

@alejandro-colomar with patches #942 #944 applied, chage does not seem to accept non-numeric date formats at all. It prints the following error message and the usage:

localhost:/home/gus/20230214 # chage gus -d yesterday chage: invalid date 'yesterday'

localhost:/home/gus/20230214 # chage gus -d 'Feb 12, 2024' chage: invalid date 'Feb 12, 2024'

alejandro-colomar commented 6 months ago

@alejandro-colomar with patches #942 #944 applied, chage does not seem to accept non-numeric date formats at all. It prints the following error message and the usage:

localhost:/home/gus/20230214 # chage gus -d yesterday chage: invalid date 'yesterday'

localhost:/home/gus/20230214 # chage gus -d 'Feb 12, 2024' chage: invalid date 'Feb 12, 2024'

Hmmm, I'll have to debug that thing. Thanks for trying!

kenion commented 6 months ago

For what it's worth, I was testing with 4.14.3 with the patches applied.

alejandro-colomar commented 6 months ago

v1b changes:

$ git range-diff gh/master..gh/getdate shadow/master..getdate 
1:  1b054708 < -:  -------- lib/strtoday.c: strtoday(): Fix calculation
2:  1d61c562 = 1:  781724c7 lib/strtoday.c: strtoday(): Reimplement in terms of getdate(3)+mktime(3)
3:  a8fd09ac = 2:  6028ac4e lib/getdate.[yh]: Remove get_date()
alejandro-colomar commented 6 months ago

Here's the reason why getdate(3) isn't working:

$ cat strtoday.c 
#define _XOPEN_SOURCE 500
#include <ctype.h>
#include <err.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
#include <time.h>

#include <a2i/str2i.h>

#define DAY  ((time_t) 24 * 3600)

static long strtoday(const char *str);

int
main(int argc, char *argv[])
{
    if (argc != 2)
        errx(EXIT_FAILURE, "argc should be 2.");

    strtoday(argv[1]);
}

static long
strtoday(const char *str)
{
    bool        isnum = true;
    time_t      t;
    struct tm   *tp;
    const char  *s = str;

    if ((NULL == str) || ('\0' == *str))
        return -1;

    /* If a numerical value is provided, this is already a number of
     * days since EPOCH.
     */
    if ('-' == *s) {
        s++;
    }
    while (' ' == *s) {
        s++;
    }
    while (isnum && ('\0' != *s)) {
        if (!isdigit (*s)) {
            isnum = false;
        }
        s++;
    }
    if (isnum) {
        long retdate;
        if (str2sl(&retdate, str) == -1) {
            return -2;
        }
        return retdate;
    }

fprintf(stderr, "ALX: %s: %s(): %d\n", __FILE__, __func__, __LINE__);
    tp = getdate(str);
fprintf(stderr, "ALX: getdate(): %p\n", (void *) tp);
fprintf(stderr, "ALX: getdate_err: %d\n", getdate_err);
    if (tp == NULL)
        return -2;
fprintf(stderr, "ALX: %s: %s(): %d\n", __FILE__, __func__, __LINE__);

    t = mktime(tp);
fprintf(stderr, "ALX: mktime(): %jd\n", (intmax_t) t);
    if ((time_t) -1 == t)
        return -2;
fprintf(stderr, "ALX: %s: %s(): %d\n", __FILE__, __func__, __LINE__);

    return t / DAY;
}
$ ./a.out today
ALX: strtoday.c: strtoday(): 62
ALX: getdate(): (nil)
ALX: getdate_err: 1
$ man_section $(man -w getdate) ERRORS
getdate(3)                 Library Functions Manual                 getdate(3)

ERRORS
       The following errors are returned via getdate_err (for getdate()) or as
       the function result (for getdate_r()):

       1   The DATEMSK environment variable is not defined, or its value is an
           empty string.

       2   The template file specified by DATEMSK cannot be opened for
           reading.

       3   Failed to get file status information.

       4   The template file is not a regular file.

       5   An error was encountered while reading the template file.

       6   Memory allocation failed (not enough memory available).

       7   There is no line in the file that matches the input.

       8   Invalid input specification.

Linux man-pages (unreleased)        (date)                          getdate(3)

So it seems the problem is with DATEMSK. We would need to specify a file with the formats we support.