Skip to content

Commit

Permalink
force 64-bit integers for year calculations to avoid overflow (closes #3
Browse files Browse the repository at this point in the history
)
  • Loading branch information
s-u committed Oct 26, 2016
1 parent edd53e7 commit 314e8b6
Show file tree
Hide file tree
Showing 2 changed files with 7 additions and 2 deletions.
2 changes: 2 additions & 0 deletions NEWS
Expand Up @@ -8,6 +8,8 @@ NEWS for fasttime package
o fix handling of year 2100 which is not a leap year. The
supported date range in fastPOSIXct() is now 1970..2199.

o fix 32-bit integer overflow when computing year offset (#3)


0.1-1 2015-07-27
o properly generate NA for invalid entries
Expand Down
7 changes: 5 additions & 2 deletions src/tparse.c
Expand Up @@ -2,13 +2,16 @@

#include <Rinternals.h>
#include <stdlib.h>
#include <stdint.h>

#define DIGIT(X) ((X) >= '0' && (X) <= '9')

/* start of each month in seconds */
static const int cml[] = { 0, 0, 2678400, 5097600, 7776000, 10368000, 13046400, 15638400,
18316800, 20995200, 23587200, 26265600, 28857600, 31536000 };

typedef int64_t time_int_t;

SEXP parse_ts(SEXP str, SEXP sRequiredComp) {
SEXP res;
double *tsv;
Expand All @@ -34,10 +37,10 @@ SEXP parse_ts(SEXP str, SEXP sRequiredComp) {
continue;
} else {
/* adjust for all leap years prior to the current one */
ts += ((int)((y + 1) / 4)) * 86400;
ts += ((time_int_t)((y + 1) / 4)) * (time_int_t) 86400;
if (y > 130) /* 2100 is an exception - not a leap year */
ts -= 86400;
ts += y * 31536000;
ts += ((time_int_t) y) * ((time_int_t) 31536000);
comp++;
while (*c && !DIGIT(*c)) c++;
if (*c) {
Expand Down

0 comments on commit 314e8b6

Please sign in to comment.