forked from pool/mariadb
66 lines
2.0 KiB
Diff
66 lines
2.0 KiB
Diff
|
From b69191bbb2278fce92b470e8e3abafe048166e39 Mon Sep 17 00:00:00 2001
|
||
|
From: =?UTF-8?q?Marko=20M=C3=A4kel=C3=A4?= <marko.makela@mariadb.com>
|
||
|
Date: Fri, 18 Feb 2022 16:31:54 +0200
|
||
|
Subject: [PATCH] MDEV-26645: Fix UB in Item_func_plus and Item_func_minus
|
||
|
|
||
|
An integer overflow in an expression like a+b or a-b is undefined behavior.
|
||
|
The compiler is allowed to assume that no such overflow is possible,
|
||
|
and optimize away some code accordingly.
|
||
|
|
||
|
Item_func_plus::int_op(), Item_func_minus::int_op(): Always check
|
||
|
for overflow.
|
||
|
|
||
|
Depending on the compiler and the compilation options, a test might fail:
|
||
|
|
||
|
CURRENT_TEST: main.func_math
|
||
|
mysqltest: At line 425: query 'SELECT 9223372036854775807 + 9223372036854775807' succeeded - should have failed with errno 1690...
|
||
|
|
||
|
A similar bug had been fixed earlier in
|
||
|
commit 328edf8560dbf1941ce314fa112e0db05d9f97f1.
|
||
|
---
|
||
|
sql/item_func.cc | 12 ++----------
|
||
|
1 file changed, 2 insertions(+), 10 deletions(-)
|
||
|
|
||
|
diff --git a/sql/item_func.cc b/sql/item_func.cc
|
||
|
index 60efc55d8785c..452bc74cc8215 100644
|
||
|
--- a/sql/item_func.cc
|
||
|
+++ b/sql/item_func.cc
|
||
|
@@ -1,5 +1,5 @@
|
||
|
/* Copyright (c) 2000, 2015, Oracle and/or its affiliates.
|
||
|
- Copyright (c) 2009, 2021, MariaDB
|
||
|
+ Copyright (c) 2009, 2022, MariaDB
|
||
|
|
||
|
This program is free software; you can redistribute it and/or modify
|
||
|
it under the terms of the GNU General Public License as published by
|
||
|
@@ -1163,14 +1163,10 @@ longlong Item_func_plus::int_op()
|
||
|
}
|
||
|
}
|
||
|
|
||
|
-#ifndef WITH_UBSAN
|
||
|
- res= val0 + val1;
|
||
|
-#else
|
||
|
if (res_unsigned)
|
||
|
res= (longlong) ((ulonglong) val0 + (ulonglong) val1);
|
||
|
else
|
||
|
- res= val0+val1;
|
||
|
-#endif /* WITH_UBSAN */
|
||
|
+ res= val0 + val1;
|
||
|
|
||
|
return check_integer_overflow(res, res_unsigned);
|
||
|
|
||
|
@@ -1333,14 +1329,10 @@ longlong Item_func_minus::int_op()
|
||
|
goto err;
|
||
|
}
|
||
|
}
|
||
|
-#ifndef WITH_UBSAN
|
||
|
- res= val0 - val1;
|
||
|
-#else
|
||
|
if (res_unsigned)
|
||
|
res= (longlong) ((ulonglong) val0 - (ulonglong) val1);
|
||
|
else
|
||
|
res= val0 - val1;
|
||
|
-#endif /* WITH_UBSAN */
|
||
|
|
||
|
return check_integer_overflow(res, res_unsigned);
|
||
|
|