且构网

分享程序员开发的那些事...
且构网 - 分享程序员编程开发的那些事

SEHException没有抓到的try / catch

更新时间:2023-02-04 12:37:36

由于.NET 4中,一些 SEHException 取值表示损坏的进程状态,以及被称为损坏状态异常。这些都是像段错误/访问冲突,其中异常内存损坏已被检测后抛出。

Since .NET 4, some SEHExceptions indicate corrupted process states, and are termed "corrupted state exceptions". These are things like segfaults/access violations, where the exception is thrown after memory corruption has been detected.

虽然这些错误仍然映射回托管的.NET SEHExceptions ,他们不开捕默认情况下,所以尝试{...}赶上(例外前){...} 将无法处理它们。

While these errors are still mapped back to managed .NET SEHExceptions, they are not catchable by default, so try { ... } catch (Exception ex) { ... } won't handle them.

您可以通过选择在对处理这些异常(无论是属性或在您的应用程序的配置文件政策变化),但不推荐,因为你的程序现在可以处理无效数据:

You can opt-in to handling these exceptions (either via an attribute or a policy change in your app's config file), but it is not recommended, as your program could now be processing invalid data:

在CLR一直用同样的机制由程序本身引起的异常交付SEH例外管理code。这不是一个问题,只要code不会尝试来处理异常情况,它不能合理地处理。访问冲突后,大多数程序不能安全地继续执行。不幸的是,CLR的异常处理模式一直鼓励用户通过允许程序在System.Exception的层次结构的顶部捕捉任何异常捕获这些严重的错误。但是,这是很少做正确的事。

The CLR has always delivered SEH exceptions to managed code using the same mechanisms as exceptions raised by the program itself. This isn't a problem as long as code doesn't attempt to handle exceptional conditions that it cannot reasonably handle. Most programs cannot safely continue execution after an access violation. Unfortunately, the CLR's exception handling model has always encouraged users to catch these serious errors by allowing programs to catch any exception at the top of the System.Exception hierarchy. But this is rarely the right thing to do.

写作赶上(例外五)是一种常见的编程错误,因为未处理的异常,造成严重的后果。但是,你可能会说,如果你不知道什么是错误将被功能得到提升,您应该防止所有可能的错误,当你的程序调用该函数。这似乎是行动的一个合理的过程,直到你想想这意味着什么,继续执行,当你的过程可能是处于损坏状态。有时候,放弃并再次尝试是***的选择:没有人愿意看到一个屈臣氏对话框,但***重新启动你的程序,而不是你的数据损坏

Writing catch (Exception e) is a common programming error because unhandled exceptions have serious consequences. But you might argue that if you don't know what errors will be raised by a function, you should protect against all possible errors when your program calls that function. This seems like a reasonable course of action until you think about what it means to continue execution when your process is possibly in a corrupted state. Sometimes aborting and trying again is the best option: nobody likes to see a Watson dialog, but it's better to restart your program than to have your data corrupted.

从上下文他们不了解所产生的程序捕获异常是一个严重的问题。但是你不能使用异常规格或其他契约机制解决问题。它是管理程序能够接收的SEH异常通知,因为CLR是多种应用和主机平台很重要。一些主机,如SQL Server,需要有自己的应用程序的过程中完全控制。管理code,与原生code互操作,有时必须处理本地C ++异常或SEH例外。

Programs catching exceptions arising from contexts they don't understand is a serious problem. But you can't solve the problem by using exceptions specifications or some other contract mechanism. And it's important that managed programs be able to receive notification of SEH exceptions because the CLR is a platform for many kinds of applications and hosts. Some hosts, such as SQL Server, need to have total control of their application's process. Managed code that interoperates with native code sometimes must deal with native C++ exceptions or SEH exceptions.

不过,大多数程序员谁写赶上(例外五)真的不希望赶***问冲突。他们会preFER时发生灾难性错误,而不是让程序蹒跚处于未知状态下,执行他们的计划停止。这对于主机管理加载项,如Visual Studio或Microsoft Office程序中尤其如此。如果某个加载项会导致访问冲突,然后吞下异常,主机可以做损害自己的状态(或用户文件),而没有意识到出事了。

But most programmers who write catch (Exception e) don't really want to catch access violations. They'd prefer that execution of their program stops when a catastrophic error occurs rather than letting the program limp along in an unknown state. This is especially true for programs that host managed add-ins such as Visual Studio or Microsoft Office. If an add-in causes an access violation and then swallows the exception, the host could be doing damage to its own state (or user files) without ever realizing something went wrong.

文章这句话是(在MSDN杂志)进入更多的细节。

如果你决定处理这些异常,有很多考虑 - 为文章指出这是非常困难的编写正确的code处理一个自定义搜索引擎,并继续安全运行的进程

If you do decide to handle these exceptions, there is a lot to consider - as the article states "It's very difficult to write correct code that handles a CSE and continues running the process safely."

在特定的,任何最后块除了已经越过了的没有的被执行(因此,如任何文件句柄晃来晃去,直到收集),并且可以跳过甚至约束的执行区!

In particular, any finally blocks that the exception has passed over have not been executed (so, e.g. any file handles are dangling until collected), and even constrained execution regions may be skipped!

此外,你应该报告这是微软的一个错误,因为 GetAssemblyName 不应该抛出这种异常。

In addition, you should probably report this as a bug to Microsoft, as GetAssemblyName shouldn't be throwing this kind of exception.