Repeat the exception with the correct line numbers in the stack trace

You can apparently throw an exception without dropping the stack trace in .NET.

However, it does not work.

The main use that I perform is as follows:

[WebMethod] public void ExceptionTest() { try { throw new Exception("An Error Happened"); } catch (Exception ex) { evlWebServiceLog.WriteEntry(ex.ToString(), EventLogEntryType.Error); throw; } } 

The problem is that the line number in the exception is in the line of the throw; line throw; , and not in the source line throw new .

I tested it in a simple exe project and without logging in the windows log line. It does not matter, the stack trace always has the wrong line number in it, which makes it less useful.

Why is he doing this? How to do it right?

+6
source share
2 answers

You will not lose the original exception if you put it in an internal exception.

 [WebMethod] public void ExceptionTest() { try { throw new Exception("An Error Happened"); } catch (Exception ex) { evlWebServiceLog.WriteEntry(ex.ToString(), EventLogEntryType.Error); throw new Exception("Your message", ex); } } 
+4
source

I used the following years. I don’t know if there is a less β€œdodgy” way to achieve this in more modern .Net infrastructures:

 public void PreserveStackTrace(Exception ex) { MethodInfo preserve = ex.GetType().GetMethod("InternalPreserveStackTrace", BindingFlags.Instance | BindingFlags.NonPublic); preserve.Invoke(ex,null); } 

To use this:

 [WebMethod] public void ExceptionTest() { try { throw new Exception("An Error Happened"); } catch (Exception ex) { evlWebServiceLog.WriteEntry(ex.ToString(), EventLogEntryType.Error); PreserveStackTrace(ex); throw ex; } } 

Update : based on @dcastro's comment, I would suggest that the extension method is at 4.5 (at <4.5 it could still be an extension wrapping the above method):

 public static void ReThrow(this Exception ex) { var exInfo = ExceptionDispatchInfo.Capture(ex); exInfo.Throw(); } 

So you just have:

  catch (Exception ex) { evlWebServiceLog.WriteEntry(ex.ToString(), EventLogEntryType.Error); ex.ReThrow(); } 
+3
source

All Articles