Skip to content

Commit dceaa71

Browse files
authored
fix(query): interval total microseconds add overflow check (#17215)
1 parent 1bf05c3 commit dceaa71

File tree

4 files changed

+30
-3
lines changed

4 files changed

+30
-3
lines changed

Cargo.lock

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

src/common/column/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@ either = { workspace = true }
3333
ethnum = { workspace = true }
3434
foreign_vec = { workspace = true }
3535
hex = { workspace = true }
36+
log = { workspace = true }
3637
match-template = { workspace = true }
3738
num-traits = { workspace = true }
3839
serde = { workspace = true, features = ["rc"], optional = true }

src/common/column/src/types/native.rs

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ use borsh::BorshSerialize;
2525
use bytemuck::Pod;
2626
use bytemuck::Zeroable;
2727
use databend_common_base::base::OrderedFloat;
28+
use log::error;
2829
use serde_derive::Deserialize;
2930
use serde_derive::Serialize;
3031

@@ -319,9 +320,21 @@ impl months_days_micros {
319320
}
320321

321322
pub fn total_micros(&self) -> i64 {
322-
(self.months() as i64 * MICROS_PER_MONTH)
323-
+ (self.days() as i64 * MICROS_PER_DAY)
324-
+ self.microseconds()
323+
let months_micros = (self.months() as i64).checked_mul(MICROS_PER_MONTH);
324+
let days_micros = (self.days() as i64).checked_mul(MICROS_PER_DAY);
325+
326+
months_micros
327+
.and_then(|months_micros| days_micros.map(|days_micros| months_micros + days_micros))
328+
.and_then(|total_micros| total_micros.checked_add(self.microseconds()))
329+
.unwrap_or_else(|| {
330+
error!(
331+
"interval is out of range: months={}, days={}, micros={}",
332+
self.months(),
333+
self.days(),
334+
self.microseconds()
335+
);
336+
0
337+
})
325338
}
326339
}
327340

tests/sqllogictests/suites/query/functions/02_0079_function_interval.test

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -142,3 +142,15 @@ query T
142142
SELECT to_years(10);
143143
----
144144
10 years
145+
146+
onlyif http
147+
query T
148+
select to_interval('1200000000 months');
149+
----
150+
100000000 years
151+
152+
onlyif http
153+
query T
154+
select to_interval('120000000000 months');
155+
----
156+
00:00:00

0 commit comments

Comments
 (0)