I recently discovered a hard to find bug in a project I am working on. The problem was that we did a calculation that had a uint32_t result and stored that in a uint64_t variable. We expected the result to be a uint64_t because we knew that the result can be too big for a 32 bit unsigned integer.
My question is: is there a way to make the compiler (or a static analysis tool like clang-tidy) warn me when something like this happens?
An example:
#include <iostream>
constexpr uint64_t MUL64 { 0x00000000ffffffff };
constexpr uint32_t MUL32 { 0xffffffff };
int main() {
const uint32_t value { 0xabababab };
const uint64_t value1 { MUL64 * value }; // the result is a uint64_t because
// MUL64 is a uint64_t
const uint64_t value2 { MUL32 * value }; // i'd like to have a warning here
if (value1 == value2) {
std::cout << "Looks good!\n";
return EXIT_SUCCESS;
}
std::cout << "Whoopsie\n";
return EXIT_FAILURE;
}
Edit:
The overflow was expected, i.e. we knew that we would need an uint64_t to store the calculated value. We also know how to fix the problem and we changed it later to something like:
const uint64_t value2 { static_cast<uint64_t>(MUL32) * value };
That way the upper 32 bits aren't cut off during the calculation. But things like that may still happen from time to time, and I just want to know whether there is way to detect this kind of mistakes.
Thanks in advance!
Greetings,
Sebastian