From 08d8c350b7ed77c9f7da99be603952cbcb3a202e Mon Sep 17 00:00:00 2001 From: Alexey Milovidov Date: Sun, 26 Apr 2020 19:22:44 +0300 Subject: [PATCH] Fix overflow at beginning of unix epoch for fractional timezones #9335 --- base/common/DateLUTImpl.h | 9 ++++----- ...262_fractional_timezone_near_start_of_epoch.reference | 3 +++ .../01262_fractional_timezone_near_start_of_epoch.sql | 3 +++ 3 files changed, 10 insertions(+), 5 deletions(-) create mode 100644 tests/queries/0_stateless/01262_fractional_timezone_near_start_of_epoch.reference create mode 100644 tests/queries/0_stateless/01262_fractional_timezone_near_start_of_epoch.sql diff --git a/base/common/DateLUTImpl.h b/base/common/DateLUTImpl.h index cb41d2ef1c1..6841598b7ca 100644 --- a/base/common/DateLUTImpl.h +++ b/base/common/DateLUTImpl.h @@ -287,8 +287,8 @@ public: if (offset_is_whole_number_of_hours_everytime) return (t / 60) % 60; - time_t date = find(t).date; - return (t - date) / 60 % 60; + UInt32 date = find(t).date; + return (UInt32(t) - date) / 60 % 60; } inline time_t toStartOfMinute(time_t t) const { return t / 60 * 60; } @@ -301,9 +301,8 @@ public: if (offset_is_whole_number_of_hours_everytime) return t / 3600 * 3600; - time_t date = find(t).date; - /// Still can return wrong values for time at 1970-01-01 if the UTC offset was non-whole number of hours. - return date + (t - date) / 3600 * 3600; + UInt32 date = find(t).date; + return date + (UInt32(t) - date) / 3600 * 3600; } /** Number of calendar day since the beginning of UNIX epoch (1970-01-01 is zero) diff --git a/tests/queries/0_stateless/01262_fractional_timezone_near_start_of_epoch.reference b/tests/queries/0_stateless/01262_fractional_timezone_near_start_of_epoch.reference new file mode 100644 index 00000000000..9a0204fb029 --- /dev/null +++ b/tests/queries/0_stateless/01262_fractional_timezone_near_start_of_epoch.reference @@ -0,0 +1,3 @@ +1970-01-01 08:16:40 +16 +1970-01-01 08:00:00 diff --git a/tests/queries/0_stateless/01262_fractional_timezone_near_start_of_epoch.sql b/tests/queries/0_stateless/01262_fractional_timezone_near_start_of_epoch.sql new file mode 100644 index 00000000000..62ecc000ab4 --- /dev/null +++ b/tests/queries/0_stateless/01262_fractional_timezone_near_start_of_epoch.sql @@ -0,0 +1,3 @@ +SELECT toDateTime(10000, 'Asia/Calcutta'); +SELECT toMinute(toDateTime(10000, 'Asia/Calcutta')); +SELECT toStartOfHour(toDateTime(10000, 'Asia/Calcutta'));