summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChristoph M. Becker <cmbecker69@gmx.de>2020-10-07 10:38:30 +0200
committerChristoph M. Becker <cmbecker69@gmx.de>2020-10-07 13:23:50 +0200
commite857dfa7cc9d28174e2328bd3ef74d9c436afda9 (patch)
treeba823159112cdc8bd268fb7f11a4b22111f2a029
parent69ba81d183130b06d52ea1cd4574864ffae5dd84 (diff)
downloadphp-git-e857dfa7cc9d28174e2328bd3ef74d9c436afda9.tar.gz
Fix #80185: jdtounix() fails after 2037
There is no such thing as the "end of the unix epoch", and if it was, it would certainly not be 2037-10-11T02:00:00. There is, however, potential integer overflow which we need to avoid. Closes GH-6288.
-rw-r--r--NEWS3
-rw-r--r--ext/calendar/cal_unix.c6
-rw-r--r--ext/calendar/tests/bug80185.phpt17
-rw-r--r--ext/calendar/tests/bug80185_32bit.phpt17
4 files changed, 41 insertions, 2 deletions
diff --git a/NEWS b/NEWS
index 43ee8d9db2..c7e278e3cd 100644
--- a/NEWS
+++ b/NEWS
@@ -6,6 +6,9 @@ PHP NEWS
. Fixed bug #79423 (copy command is limited to size of file it can copy).
(cmb)
+- Calendar:
+ . Fixed bug #80185 (jdtounix() fails after 2037). (cmb)
+
- MySQLnd:
. Fixed bug #80115 (mysqlnd.debug doesn't recognize absolute paths with
slashes). (cmb)
diff --git a/ext/calendar/cal_unix.c b/ext/calendar/cal_unix.c
index da6a184e6c..d364079bd0 100644
--- a/ext/calendar/cal_unix.c
+++ b/ext/calendar/cal_unix.c
@@ -23,6 +23,8 @@
#include "sdncal.h"
#include <time.h>
+#define SECS_PER_DAY (24 * 3600)
+
/* {{{ proto int unixtojd([int timestamp])
Convert UNIX timestamp to Julian Day */
PHP_FUNCTION(unixtojd)
@@ -62,11 +64,11 @@ PHP_FUNCTION(jdtounix)
}
uday -= 2440588 /* J.D. of 1.1.1970 */;
- if (uday < 0 || uday > 24755) { /* before beginning of unix epoch or behind end of unix epoch */
+ if (uday < 0 || uday > ZEND_LONG_MAX / SECS_PER_DAY) { /* before beginning of unix epoch or greater than representable */
RETURN_FALSE;
}
- RETURN_LONG(uday * 24 * 3600);
+ RETURN_LONG(uday * SECS_PER_DAY);
}
/* }}} */
diff --git a/ext/calendar/tests/bug80185.phpt b/ext/calendar/tests/bug80185.phpt
new file mode 100644
index 0000000000..cd9ddb7d29
--- /dev/null
+++ b/ext/calendar/tests/bug80185.phpt
@@ -0,0 +1,17 @@
+--TEST--
+Bug #80185 (jdtounix() fails after 2037)
+--SKIPIF--
+<?php
+if (!extension_loaded('calendar')) die('skip ext/calendar required');
+if (PHP_INT_SIZE != 8) die("skip for 64bit platforms only");
+?>
+--FILE--
+<?php
+var_dump(jdtounix(2465712));
+var_dump(jdtounix(PHP_INT_MAX / 86400 + 2440588));
+var_dump(jdtounix(PHP_INT_MAX / 86400 + 2440589));
+?>
+--EXPECT--
+int(2170713600)
+int(9223372036854720000)
+bool(false)
diff --git a/ext/calendar/tests/bug80185_32bit.phpt b/ext/calendar/tests/bug80185_32bit.phpt
new file mode 100644
index 0000000000..95ee050171
--- /dev/null
+++ b/ext/calendar/tests/bug80185_32bit.phpt
@@ -0,0 +1,17 @@
+--TEST--
+Bug #80185 (jdtounix() fails after 2037)
+--SKIPIF--
+<?php
+if (!extension_loaded('calendar')) die('skip ext/calendar required');
+if (PHP_INT_SIZE != 4) die("skip for 32bit platforms only");
+?>
+--FILE--
+<?php
+var_dump(jdtounix(2465712));
+var_dump(jdtounix(PHP_INT_MAX / 86400 + 2440588));
+var_dump(jdtounix(PHP_INT_MAX / 86400 + 2440589));
+?>
+--EXPECT--
+bool(false)
+int(2147472000)
+bool(false)