[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[lmi] Integer overflow warnings in bourn_cast with clang
From: |
Vadim Zeitlin |
Subject: |
[lmi] Integer overflow warnings in bourn_cast with clang |
Date: |
Thu, 6 Apr 2017 02:24:43 +0200 |
Hello,
I can confirm that bourn_cast test compiles and passes with g++ 6.3 as
well as with 4.9 normally used for testing. Unfortunately it does not
compile with clang 4.0, giving several errors:
In file included from bourn_cast_test.cpp:49:
bourn_cast.hpp:134:35: error: overflow in expression; result is
-9223372036854775808 with type 'long long' [-Werror,-Winteger-overflow]
if(From(to_traits::max()) + 1 <= from)
^
bourn_cast.hpp:134:35: error: overflow in expression; result is -2147483648
with type 'int' [-Werror,-Winteger-overflow]
bourn_cast.hpp:134:35: error: overflow in expression; result is -2147483648
with type 'int' [-Werror,-Winteger-overflow]
bourn_cast.hpp:134:35: error: overflow in expression; result is
-9223372036854775808 with type 'long' [-Werror,-Winteger-overflow]
bourn_cast.hpp:134:35: error: overflow in expression; result is
-9223372036854775808 with type 'long long' [-Werror,-Winteger-overflow]
bourn_cast.hpp:134:35: error: overflow in expression; result is
-9223372036854775808 with type 'long long' [-Werror,-Winteger-overflow]
bourn_cast.hpp:134:35: error: overflow in expression; result is -2147483648
with type 'int' [-Werror,-Winteger-overflow]
bourn_cast.hpp:134:35: error: overflow in expression; result is
-9223372036854775808 with type 'long long' [-Werror,-Winteger-overflow]
bourn_cast.hpp:134:35: error: overflow in expression; result is -2147483648
with type 'int' [-Werror,-Winteger-overflow]
bourn_cast.hpp:134:35: error: overflow in expression; result is -2147483648
with type 'int' [-Werror,-Winteger-overflow]
10 errors generated.
Of course, all of those are actually different instances of the same error
(notice that it happens even for e.g. bourn_cast<int,int>() because the
code in this line 134 is still compiled even if it's not being executed).
The trivial patch
---------------------------------- >8 --------------------------------------
diff --git a/bourn_cast.hpp b/bourn_cast.hpp
index 358952f..cebaac7 100644
--- a/bourn_cast.hpp
+++ b/bourn_cast.hpp
@@ -131,7 +131,7 @@ inline To bourn_cast(From from)
throw std::runtime_error("Cannot cast NaN to integral.");
if(from < to_traits::lowest())
throw std::runtime_error("Cast would transgress lower limit.");
- if(From(to_traits::max()) + 1 <= from)
+ if(From(to_traits::max()) <= from - 1)
throw std::runtime_error("Cast would transgress upper limit.");
To const r = static_cast<To>(from);
if(r != from)
---------------------------------- >8 --------------------------------------
fixes it while allowing the tests to still pass, but I'm not sure at all if
this doesn't introduce some other problem, I'm afraid this code has become
too complicated for me to reason about it with certainty.
Still, it does seem wrong to add 1 to the maximally representable value of
type "To" without being certain that it is _strictly_ less than that of
type "From".
Regards,
VZ