Reputation: 1136
What is the scope of exception handling in C#. I am currently reviewing some code from another programmer on my team and he has a function laid out somewhat like this:
private void function1() {
try {
function2();
}
catch (Exception ex) {
EmailException(ex.message());
}}
private void function2() {
try {
// Do stuff
}
catch (Exception ex) {
// Handle it here
}}
The bulk of the processing code is in function2. However his reporting handling is in function1. Will an exception in function2 kick back to the function1 handler that sends the report?
Edit: Thanks for your responses, they all were very helpful!
Upvotes: 3
Views: 1945
Reputation: 81159
In .net, when an exception occurs, the system will search through the nested try
blocks on the stack to determine if there is a catch
block that can catch the exception. This occurs before any finally
blocks run. If there isn't any block that can catch the exception, the system will invoke an "unhandled exception" handler without running any finally
blocks.
If the system that does determine that there is a block that can catch the exception, it will start unwinding the stack and run finally
blocks associated with inner try
blocks until either it has unwound the stack all the way to the catch
block it found, or an exception gets thrown in the execution of a finally
block. In the latter situation, the previous exception will be abandoned and not processed further; exception handling will start afresh with the newly-thrown exception.
Although there is a semantic difference between wanting to catch an exception, versus merely wanting to act upon it (but let it be regarded as uncaught), there is no clean way to express that distinction in C#; code which catches an exception is expected to resolve it. The best one can do in C# is use a catch
(indicating to the system's exception-processing logic to think one is going to catch the exception) and then use a throw
, to indicate one doesn't want to resolve it after all (this will occur after inner "finally" blocks have run). In some other languages such as vb.net, it is possible to act upon exceptions, without catching them, before finally
blocks run. While there aren't a huge number of cases where a catch
and throw
is different from capturing an exception without catch
ing it, there are few cases where the distinction matters. If one is using C# and one wishes to avoid being hostile to surrounding code which might want to capture exceptions from inner code before finalizer blocks run, the best approach is probably to write an exception-handling wrapper method written in vb (or have someone else do it), compile it to a DLL, and then use lambdas to feed such a function methods for it to invoke within a suitable try/filter/catch/finally block.
Upvotes: 1
Reputation: 52645
Will an exception in function2 kick back to the function1 handler that sends the report?
No unless
trow
or trow ex
from function2's exception blockThreadAbortException
Upvotes: 2
Reputation: 42343
Only if
a) function2
re-throws the original exception with throw
or a new exception with throw new ...
b) an unexpected exception occurs inside function2
's catch block or after it (which actually in this case is impossible since the catch
block is the last thing that happens in function2
).
Upvotes: 4
Reputation: 50225
Assuming // Handle it here
does not rethrow the exception, function1
will never see the original exception.
It is possible function2
will raise a new issue in its catch
though, much like it's possible EmailException
could err in function1
.
Upvotes: 4
Reputation: 98746
No, an exception propagates only until it is caught.
However, you can re-throw the exception at the end of the catch
in function2
, leading to the desired behaviour:
private void function2() {
try {
// Do stuff
}
catch (Exception ex) {
// Handle it here
throw; // <- Re-throw the exception.
// Note this is different from `throw ex;`
}
}
Upvotes: 2