This is one of those "what if" questions that have been bugging me lately, so if you're not into that kind of conversation, consider yourself fore- warned.
I'm trying to understand the possible reasons why filters have been added to .NET. The reason why this question has some relevance (at least to me) is that filters seem to be the only thing that *absolutely* require a two- pass exception handling mechanism. Let me explain what I mean: Normally, when an exception is thrown, the runtime could start walking down the stack frame performing local unwind for fault and finally blocks until it either finds a catch block that matches the exception that was thrown or it terminates the thread. The presence of filters in the specification (Partition II, Section 18 "Exception Handling" is what I'm looking at) means that the runtime must do significantly more. First it needs to walk down the stack in a first pass to find whether there is a filter willing to handle the exception (let's call it the filter phase). The first pass must maintain the original stack due to the (as yet not implemented) EXCEPTION_CONTINUE_EXECUTION return code, which could instruct the EE to run the filter and continue the execution at the instruction following the one that caused the exception. Only after this first pass happens, the second pass can perform normal, stack destructive unwinding. The case pro: I can see three reasons why having filters makes sense. Unfortunately, I don't think these reasons are enough and I'd like to hear your collective opinion: Pro 1. The handling just described is very similar (the same in fact) with the way SEH works on Win32. (I vaguely recall reading somewhere that this style of exception handling provides "continuation semantics"). This being the case, the original designers of .NET might have felt they should include it in the runtime. Pro 2. The second reason might be that VBs On Error / Resume Next constructs are implemented easier this way. If you go to the trouble of disassembling a simple On Error program you'll see what I mean. Pro 3. The third reason might be that this handling can provide a really cool integration with debuggers - a program that throws an unhandled exception can bring up a debugger that points to the exact instruction that threw the exception and still preserve all the stack frames in the process. All these are valid reasons I suppose. The case against is cost and functionality. Cost first: Against 1. The cost of handling every exception is *in theory* twice the cost it would have been if filters would not have existed. It is important to emphasize the difference between theory and practice and I'll get back to that in a second. Against 2. The fact that Win32 handles SEH that way could possibly ease the implementation of exceptions on Windows, but at the same time makes them harder to implement on non-Windows platforms. Besides, since the EE engine is an abstraction layer, it is unclear why it would borrow so heavily from it's primary implementation platform. This refutes point Pro 1. above. Against 3. On Error/Resume Next is, if not deprecated, at least discouraged. New constructs that resemble the C#/C++/Java style are the preferred way VB should handle exceptions. Making such a dramatic change in order to support a language feature that is already on it's way out, so to speak, does not seem justified. Moreover, my sense is that Resume Next can be implemented without filters anyway due to a language loophole which says that the execution will resume in the same function that contains the On Error statement (not where the exception was generated). This point refutes point Pro 2. above. 3. The debugging infrastructure, while cool on its own merit, in theory should not impose performance penalties on every single exception handling scenario. Again, this is theory and practice might work differently, but that's the best I can come up with to refute point Pro 3 above. Functionality: 4. Neither C++ nor C# from what I can tell (and here I'm looking at Section 15.10 The try statement of the "C# Specification") (nor Java for that matter) require this type of construct. Unless there are other languages out there that absolutely would benefit from this feature, the cross-language argument does not stand up to scrutiny. (Question to the group - anybody knows a language that *requires* filters + continuation semantic like the one offered by .NET's filters? I'm too ignorant to know :-)) 5. In a world where inevitably .NET is compared to Java, it seems that having a framework that *seems* to require a high cost in handling exceptions from the get-go is not in the best interest of .NET. (Please, please, no flames.) The case for filters could be made much stronger if there is a significant family of languages out there that would benefit from the type of semantic available through filters. I don't have knowledge of that family, but maybe the group does? Before I go, a note on the difference between theory and practice in single vs. double pass exceptions: It is true that a Java JVM would not require a two pass algorithm for exception handling, but my guess is that it uses one anyway in order to create a correct stack trace. But that's just guessing on my part. Thanks for your patience reading this. Cristian You can read messages from the Advanced DOTNET archive, unsubscribe from Advanced DOTNET, or subscribe to other DevelopMentor lists at http://discuss.develop.com.