Tuesday, February 5, 2008

Uncaught exceptions

I could look it up, but do you happen to know what happens if there is no exception handler for an exception that is thrown?

#include <stdexcept>                                                                                   
#include <iostream>

struct MyRTExc: public std::runtime_error { MyRTExc(): std::runtime_error("") {} };
struct MyOwnExc { };

int main()
{
int step = 0;
try {
step = 1;
throw MyOwnExc();
step = 2;
throw MyRTExc();
step = 3;
}
catch(std::exception exc)
{
std::cerr << "probably MyRTExc" << std::endl;
}
std::cerr << "step=" << step << std::endl;
return 0;
}
[Note: I corrected the syntax today]

Without trying it out: It just could be, that step=2 in the end, right? Because I have no exception handler installed for MyOwnExc the code just continues with the next instruction after the throw. The next throw behaves as exptected and leaves before step=3 so the final step would be 2.

Guideline: Install exception handlers for any exceptions that you throw.

Update: The relevant section in the C++ Specification is "15.5.1" which says that when no fitting handler can be found terminate() must be called. But I think the above guideline still stands, at least for good programming style reasons.

5 comments:

towi said...

The GCC (g++ 4.1) does:

will17@linux-x64:~> ./a.out

terminate called after throwing an instance of 'MyOwnExc'

Aborted

which is not what I said above.
That seems to me completly sane behaviour.

Anonymous said...

That performing "=2" would really be strange - Stoustrup explicitely states that the current control flow is stopped immediately by throwing an exception.
If that execption is not catched somewhere upward - the control stack is walked up and up - until the top level is reached and there the program aborts/terminates.

So when someone trying out this test and is then facing "=2" or "=3" - I state: the used compiler had some severe bug!

Maybe then the optimizer did some false-optimizing!?

Please check this out and re-report your results!

towi said...

any source for that Stroustrup citation? Section, Paragraph, Page?

towi said...

Ok, and also Microsoft seems to implement this behaviour:

From thier C++ doc
"""
If a matching handler is still not found, or if an exception occurs while unwinding, but before the handler gets control, the predefined run-time function terminate is called. If an exception occurs after throwing the exception, but before the unwind begins, terminate is called.
"""

I definitly thought I could remember an occassion where I had a "I just continue". But I think I remember wrongly.

towi said...

I found the relevant C++ Specification:

"""
15.5.1 - The terminate() function

-1- In the following situations exception handling must be abandoned for less subtle error handling techniques:
[...]
* when the exception handling mechanism cannot find a handler for a thrown exception
"""

My program above _should_ behave that it just aborts.