Visual C# Developer Center > Visual C# Forums > Visual C# IDE > First exception very slow when debugging
Ask a questionAsk a question
 

QuestionFirst exception very slow when debugging

  • Friday, September 15, 2006 8:32 AMsoundman32 Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
    My application uses a 3rd party component to do serial comms. As part of the initialisation routines of this component it generates an exception.
    If I am debugging then this exception takes ages to be caught. The release version takes no time at all.

    Why does the first exception take so long, and is there anything I can do about it?

All Replies

  • Tuesday, September 19, 2006 3:31 PMspelger Users MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     
    i have experienced this too with other exceptions, i have no answer for it though.

    scott
  • Wednesday, September 20, 2006 10:45 AMAnson Horton MSFTMSFTUsers MedalsUsers MedalsUsers MedalsUsers MedalsUsers Medals
     

    I can think of a couple of possibilities, so hopefully one of them helps you out :) 

    The VS 2005 (is this 2005 btw?) C# debugger has a number of enhancements over VS 2003 for displaying data.  One of those enhancements is, by default, calling ToString on objects shown in the watch window, locals window, or even the callstack window.  This usually isn't a problem because the vast majority of ToString calls don't have any side-effects and tend to be extremely fast to evaluate.  The ToString call happens in the process that is being debugged, and is referred to as a "FuncEval."  FuncEvals are allotted a 10 second timeout in the debugger (if one ever goes over the limit all further funcevals are cancelled).  Property evaluations are also FuncEvals.  So, it's possible that the callstack is extremely deep and each of the methods on the callstack have a large number of property evaluations or tostrings to evaluate, or that the FuncEvals that are being called simply take an extremely long time.  The example below demonstrates the degenerative case.  If your run this outside of the debugger then the exception happens pretty close to instantaneously; inside the debugger it takes over a minute.

    Code Example

    using System;
    using
    System.Threading;

    class
    ToStringObject
    {
      public override string
    ToString()
      {
        Thread
    .Sleep(9000);  
        return "Slept for 9 seconds!"
    ;
      }
    }

    class
    Program
    {
      static void Main(string
    [] args)
      {
        TestSlowness(new ToStringObject
    (), 0);
      }
     
      static void TestSlowness(ToStringObject o, int
    count)
      {
        if
    (count > 10)
          throw new Exception("Boom!"
    );
      
        TestSlowness(new ToStringObject
    (), count + 1);
      }
    }

    The same example could be written for properties instead of ToString evaluation.  There is an option in Tools | Options | Debugging |  General called "Enable property evaluation and other implicit function calls", with a nested option for "Call ToString() on objects in variable windows."  Try disabling those options and see if performance improves.  Unfortunately this will significantly degrade your general debugging experience, particularly if you need to disable the general "enable property evaluation" option.  If this is the problem then it may be possible to work around it in another way using attributes.

    The second and less likely possiblity is that work the debugger is doing to support Edit and Continue is taking a lot of time.  The debugger will implicitly "unwind" an exception callstack.  This means it basically throws away frames of the callstack to get you back to a point where it would be possible to 'prevent' the exception from happening.  This is extremely useful when combined with Edit and Continue because you can make a change to the code, prevent the exception, and continue as if it never happened.  It's generally not all that expensive of an operation, from what I've seen, but if the exception callstack was quite deep it's possible it's having an effect.  You can disable this behavior in Tools | Options | Debugging | General with the option "Unwind the callstack on unhandled exceptions."  Luckily this doesn't change the experience all that much because the 'exception assistant' (the little window that pops up when an exception is thrown) has a button on it to unwind the callstack when this option is disabled in tools | options.

    Hope that helps!
    Anson