8

I am learning C++, I was trying to write this function to find the largest fibonacci integer that can fit into an integer type:

void findFibThatFitsInAnInt()
{
    int n1 = 1;
    int n2 = 1;
    int fib = 0;
    try
    {
        while ( true )
        {
            fib = n1 + n2;
            n1 = n2;
            n2 = fib;
            cout << "Fibonacci number : " << fib << "\n";
        } 

    }
    catch (overflow_error & e)
    {
        cout << "The largest fib that can fit into an int is : " << fib << "\n";
        cout << e.what() << "\n";
    }

    cout << "The largest fib that can fit into an int is : " << n1 << "\n";
}

But the thing is overflow_error is not caught at all. I know other ways of doing this:

I know that I can write like :

while ( fib >= 0 )
        {
            fib = n1 + n2;
            n1 = n2;
            n2 = fib;
            cout << "Fibonacci number : " << fib << "\n";
        } 

and because fib is just an "int" not an unsigned int, it will eventually become < 0 ( strangely enough ) when it is assigned a value that is larger than the capacity of int type.

Question is : is overflow_error for this kind of capacity issue caught at runtime in C++? Did I misunderstand something about overflow_error? This is what I know from my google foo:

Defines a type of object to be thrown as exception. It can be used to report arithmetic overflow errors (that is, situations where a result of a computation is too large for the destination type)

If overflow_error is ignored for integer overflows is there a way to enable it for my c++ compiler ( visual studio 2013?)

SomeDude
  • 13,876
  • 5
  • 21
  • 44
  • 3
    Why do you think `std::overflow_error` or _any_ exception for that matter will be thrown here? – Captain Obvlious Feb 01 '16 at 19:40
  • won't it catch overflow_error if the int fib is assigned a very large value? – SomeDude Feb 01 '16 at 19:40
  • 2
    see [here](http://en.cppreference.com/w/cpp/error/overflow_error): The only standard library components that throw this exception are std::bitset::to_ulong and std::bitset::to_ullong. – Ami Tavory Feb 01 '16 at 19:41
  • @Captain Obvlious I edited the question to make it clearer. – SomeDude Feb 01 '16 at 19:47
  • The phrase _"can be used to report"_ does not indicate that it _is_ used or that it _is_ thrown automatically for integers. – Captain Obvlious Feb 01 '16 at 19:50
  • 1
    To really push @AlexD's answer, signed integer overflow is **undefined behavior** ( http://blog.llvm.org/2011/05/what-every-c-programmer-should-know.html ). Other languages handle this differently. What you want is probably something like SafeInt ( https://safeint.codeplex.com/ ), or doing the same checks by hand. – Max Lybbert Feb 01 '16 at 19:54
  • For `gcc`, passing the flag `-ftrapv` will catch integer overflow. – ack Mar 25 '18 at 01:33

3 Answers3

11

Short answer: No. Neither C nor C++ will automatically detect integer overflow at runtime.

Here are more details about C++ std::overflow_error:

http://en.cppreference.com/w/cpp/error/overflow_error

std::overflow_error Defined in header <stdexcept>

Defines a type of object to be thrown as exception. It can be used to report arithmetic overflow errors (that is, situations where a result of a computation is too large for the destination type)

The only standard library components that throw this exception are std::bitset::to_ulong and std::bitset::to_ullong.

The mathematical functions of the standard library components do not throw this exception (mathematical functions report overflow errors as specified in math_errhandling). Third-party libraries, however, use this. For example, boost.math throws std::overflow_error if boost::math::policies::throw_on_error is enabled (the default setting).

Here is more information about what you can do in your code to detect and handle integer overflow:

How to detect integer overflow?

Community
  • 1
  • 1
paulsm4
  • 114,292
  • 17
  • 138
  • 190
  • Ok. can you tell me what is the use of bitset types and where they are used? Is there a way to enable overflow_error for integer overflow? – SomeDude Feb 01 '16 at 19:45
  • @svasa There is no switch nor c++ library that enables exceptions for integer owerflows. They are silent by design. – Captain Giraffe Feb 01 '16 at 19:49
  • You can enable integer overflow checking in MSVS by using a [checked](https://msdn.microsoft.com/en-us/library/system.overflowexception%28v=vs.110%29.aspx) block: http://rion.io/2013/04/27/enabling-underflow-and-overflow-checking-within-visual-studio/. Unfortunately, this is Microsoft-specific :( You can also use [Boost](https://msdn.microsoft.com/en-us/library/aa288739%28v=vs.71%29.aspx), and specify `boost::math::policies::throw_on_error`. – paulsm4 Feb 01 '16 at 19:51
  • Hmm, ok. So programmer needs to carefully write his code avoiding overflows , because they are not caught ! – SomeDude Feb 01 '16 at 19:53
  • Yes. C was always like that, and C++ followed. Here is a good discussion: [Integer Overflow is a Menace](https://benjamin.pe/writing/integer-overflow) – paulsm4 Feb 01 '16 at 19:55
  • Marking this as answer for the link where it shows how to enable the overflow detection in VS – SomeDude Feb 01 '16 at 19:56
7

According to the standard (emphasis mine):

5 Expressions [expr]
....

If during the evaluation of an expression, the result is not mathematically defined or not in the range of representable values for its type, the behavior is undefined. [ Note: most existing implementations of C++ ignore integer overflows.

P.S. BTW, please note that

3.9.1 Fundamental types [basic.fundamental]
....

(footnote)
unsigned arithmetic does not overflow because a result that cannot be represented by the resulting unsigned integer type is reduced modulo the number that is one greater than the largest value that can be represented by the resulting unsigned integer type.

Community
  • 1
  • 1
AlexD
  • 32,156
  • 3
  • 71
  • 65
  • Note that undefined behavior allows throwing `std::overflow_error`, so a conforming implementation *may* throw that exception. As everyone else already stated, no implementation does. – Michael Karcher Feb 01 '16 at 20:31
  • Note that undefined behavior also allows "turn a terminating loop into an infinite loop," or "eliding an unrelated `NULL`-check," or "generating an executable that does things that the language standard wouldn't normally allow." And that some implementations do, in fact, take advantage of that definition ( http://blog.llvm.org/2011/05/what-every-c-programmer-should-know.html ). – Max Lybbert Feb 01 '16 at 22:27
4

is overflow_error for this kind of capacity issue caught at runtime in C++?

No, as from the documentation

The only standard library components that throw this exception are std::bitset::to_ulong and std::bitset::to_ullong.

Overflows as induced by intrinsic mathematical operations won't be caught, and just leave you with unexpected results. The exact behavior isn't defined in the standard (great cite in @AlexD 's answer).

Community
  • 1
  • 1
πάντα ῥεῖ
  • 1
  • 13
  • 116
  • 190