commit ed647df512786b3c94429dd5c864715301e03ea5 Author: Ethan A Merritt Date: Tue Mar 11 16:31:23 2025 -0700 guard against trying to format a huge number as a time The time formatting code does not handle time_in_seconds > 1.e12 (sometime in the year 33658). Bug 2779 diff --git src/mouse.c src/mouse.c index ba0609290..a6110f5ff 100644 --- src/mouse.c +++ src/mouse.c @@ -619,6 +619,11 @@ static char * xDateTimeFormat(double x, char *b, int mode) { struct tm tm; + if (fabs(x) > 1.e12) { /* Some time in the year 33688 */ + int_warn(NO_CARET, "time value out of range"); + *b = '\0'; + return b; + } switch (mode) { case MOUSE_COORDINATES_XDATE: commit 3270021820ff6ac7a6d77b77fe69777129937994 Author: Ethan A Merritt Date: Wed Mar 12 19:56:13 2025 -0700 check valid range on time value before trying to format it Absurdly large time values (number of seconds) cause failures in the routines that populate a time structure and format the result. The program does complain about an invalid time value but only after the failures have already occurred. E.g. print strftime("%Y", 1.e14) Now a check for fabs(time) > 1.e12 is the first thing in f_strftime(). Bug 2779 diff --git src/internal.c src/internal.c index 53be8d409..2d8812e49 100644 --- src/internal.c +++ src/internal.c @@ -1905,30 +1905,37 @@ f_strftime(union argument *arg) int_error(NO_CARET, "First parameter to strftime must be a format string"); - /* Prepare format string. - * Make sure the resulting string not empty by adding a space. - * Otherwise, the return value of gstrftime doesn't give enough - * information. - */ - fmtlen = strlen(fmt.v.string_val) + 1; - fmtstr = gp_alloc(fmtlen + 1, "f_strftime: fmt"); - strncpy(fmtstr, fmt.v.string_val, fmtlen); - strncat(fmtstr, " ", fmtlen); - buflen = 80 + 2*fmtlen; - buffer = gp_alloc(buflen, "f_strftime: buffer"); - - /* Get time_str */ - length = gstrftime(buffer, buflen, fmtstr, real(&val)); - if (length == 0 || length >= buflen) - int_error(NO_CARET, "String produced by time format is too long"); - - /* Remove trailing space */ - assert(buffer[length-1] == ' '); - buffer[length-1] = NUL; + /* Range check */ + if (!(fabs(real(&val)) < 1.e12)) { + int_warn(NO_CARET, "time value out of range"); + buffer = strdup(" "); + + } else { + /* Prepare format string. + * Make sure the resulting string not empty by adding a space. + * Otherwise, the return value of gstrftime doesn't give enough + * information. + */ + fmtlen = strlen(fmt.v.string_val) + 1; + fmtstr = gp_alloc(fmtlen + 1, "f_strftime: fmt"); + strncpy(fmtstr, fmt.v.string_val, fmtlen); + strncat(fmtstr, " ", fmtlen); + buflen = 80 + 2*fmtlen; + buffer = gp_alloc(buflen, "f_strftime: buffer"); + + /* Get time_str */ + length = gstrftime(buffer, buflen, fmtstr, real(&val)); + if (length == 0 || length >= buflen) + int_error(NO_CARET, "String produced by time format is too long"); + + /* Remove trailing space */ + assert(buffer[length-1] == ' '); + buffer[length-1] = NUL; + free(fmtstr); + } gpfree_string(&val); gpfree_string(&fmt); - free(fmtstr); push(Gstring(&val, buffer)); free(buffer);