Jaa


Writing exception handlers as separate methods may prove to be a good idea

Flowers At the Botanical park

Let us consider a scenario where you catch some exception and in the exception handler do some costly operation. You can write that code in either of the following ways

Method-1 : Separate method call

 public class Program
{
    public static void Main(string[] args)
    {
        try
        {
            using (DataStore ds = new DataStore())
            {
                // ...
            }
        }
        catch (Exception ex)
        {
            ErrorReporter(ex);
        }
    }

    private static void ErrorReporter(Exception ex)
    {
        string path = System.IO.Path.GetTempFileName();
        ErrorDumper ed = new ErrorDumper(path, ex);
        ed.WriteError();

        XmlDocument xmlDoc = new XmlDocument();
        xmlDoc.Load(path);
        RemoteErrorReporter er = new RemoteErrorReporter(xmlDoc);
        er.ReportError();
    }
}

-

Method-2 : Inline

 public static void Main(string[] args)
{
    try
    {
        using (DataStore ds = new DataStore())
        {
            // ...
        }
    }
    catch (Exception ex)
    {
        string path = System.IO.Path.GetTempFileName();
        ErrorDumper ed = new ErrorDumper(path, ex);
        ed.WriteError();

        XmlDocument xmlDoc = new XmlDocument();
        xmlDoc.Load(path);
        RemoteErrorReporter er = new RemoteErrorReporter(xmlDoc);
        er.ReportError();
    }
}

-

The simple difference is that in the first case the exception handler is written as a separate method and in the second case it is placed directly inline inside the handler itself.

The question is which is better in terms of performance?

In case you do have significant code and type reference in the handler and you expect the exception to be thrown rarely in an application execution then the Method-1 is going to be more performant.

The reason is that just before executing a method the whole method gets jitted. The jitted code contains stubs to the other method's it will call but it doesn't do a recursive jitting. This means when Main gets called it gets jitted but the method ErrorReporter is still not jitted. So in case the exception is never fired all the code inside ErrorReporter never gets Jitted. This might prove to be significant saving in terms of time and space if the handling code is complex and refers to type not already referenced.

However, if the code is inline then the moment Main gets jitted all the code inside the catch block gets jitted. This is expensive not only because it leads to Jitting of code that is never executed but also because all types referenced in the catch block is also resolved resulting in loading a bunch of dlls after searching though the disk. In our example above System.Xml.dll and the other dll containing remote error reporting gets loaded even though they will never be used. Since disk access, loading assemblies and type resolution are slow, the simple change can prove to give some saving.

Comments

  • Anonymous
    July 09, 2008
    Does passing the exception to a handler method have an impact on the trace?

  • Anonymous
    July 09, 2008
    It doesn't if you do a rethrow. Obviously if you re-create an exception then the trace gets reset. This would be a problem even if you do that directly in the catch block

  • Anonymous
    August 06, 2008
    Note that this can have problems for OutOfMemoryExceptions for the same reason that it's good in the general case - if you're out of memory, and now you have to try and JIT the exception method...

  • Anonymous
    September 11, 2008
    Mark this is exactly the reason you should never try to handle the OutOfMem or stack overflow exceptions