Is there a way to prevent Visual Studio from breaking on exceptions in a specific method?

后端 未结 3 1681
暖寄归人
暖寄归人 2021-02-07 19:55

I know I can control the way Visual Studio handles exceptions according to their type and to the fact that they\'re eventually caught using the \"Exception\" dialog.

How

3条回答
  •  你的背包
    2021-02-07 20:17

    What you can do is use Concord, the debug engine that ships with Visual Studio (starting with version 2012). It's quite extensible through a nice managed API (and deployable using vsix technology), but it's not fully documented.

    Concord has the concept of debug monitors, that we can hook using the IDkmDebugMonitorExceptionNotification Interface

    The cool thing is this interface can monitor all exceptions thrown. It can also "suppress" any detected exception event, which is exactly what we need.

    What I suggest is to start with the Hello World sample: . Download it, and make sure it runs as expected for you.

    Now, just modify HelloWorld.vsdconfigxml like this:

    
    
    
    
    
      
      
        
          
            
            
            
          
        
      
    
    
    

    Then, just create an ExceptionHandler.cs class and put something like this in there:

    public class ExceptionHandler : IDkmDebugMonitorExceptionNotification
    {
        private bool _unhandledDetected;
    
        // we're being called!
        public void OnDebugMonitorException(DkmExceptionInformation exception, DkmWorkList workList, DkmEventDescriptorS eventDescriptor)
        {
            if (_unhandledDetected)
            {
                // this will cause the program to terminate
                eventDescriptor.Suppress();
                return;
            }
    
            if (exception.ProcessingStage.HasFlag(DkmExceptionProcessingStage.Unhandled))
            {
                _unhandledDetected = true;
            }
            else if (exception.ProcessingStage.HasFlag(DkmExceptionProcessingStage.Thrown))
            {
                if (SuppressException(exception))
                {
                    eventDescriptor.Suppress();
                }
            }
        }
    
        // should we suppress a thrown (1st chance) exception?
        private bool SuppressException(DkmExceptionInformation exception)
        {
            // implement any custom logic in here, for example use the exception's name
            if (exception.Name == typeof(ArgumentOutOfRangeException).FullName)
            {
                // for example, use the module (assembly) name
                var clrAddress = (DkmClrInstructionAddress)exception.InstructionAddress;
                var clrModule = clrAddress.ModuleInstance;
                if (clrModule.Name == "TheUglyOne.dll")
                    return true; // we don't want this one!
            }
            return false;
        }
    }
    

    When you run the project, you should see all exceptions being monitored (regardless of your 'just my code' and/or exception triggers settings), so what you just need to do is implement some logic to suppress the ones you really don't want to see. I've not checked but I suppose you could build your logic using custom attributes as the Dkm classes provide quite a lot of .NET metadata information.

    Note: as you can see, there is some trickery to make sure the program will terminate normally.

提交回复
热议问题