【问题标题】:32 bit program on 64 bit computer doesn't crash on NullReferenceException64 位计算机上的 32 位程序不会在 NullReferenceException 上崩溃
【发布时间】:2014-03-23 03:07:36
【问题描述】:

我有一段代码会抛出 NullReferenceException:

dataSource.DataSource = GetView();

它抛出是因为dataSourcenullGetView 返回 DataTable

但是,当在一台计算机(64 位)上运行时,程序继续运行,没有任何问题。例外确实发生了,因为当我迈出一步时,我最终完全到了其他地方。调试器并没有停止。

当在另一个(32 位)上运行时,它会抛出异常并且我的调试器停止。

我的程序是为 32 位编译的。当我切换到“任何 CPU”时,64 位计算机确实会因异常而崩溃。

更新我知道如何解决我的问题(事实上我已经知道了)。我只想知道这是某种已知的行为还是可能由多种原因引起的。

修复方法是 1) 选择“任何 CPU”(这会导致 64 位机器崩溃)和 2) 在运行此部分之前检查 dataSource 是否为空。

【问题讨论】:

  • 为什么不附上一小段你有问题的代码?
  • @Eiver 我添加了代码。但问题不在于代码。我知道它为什么会抛出异常。它应该扔掉它。
  • @BartFriederichs 我认为这里的重点是它可能不会直接甚至微弱地影响比特数。有很多因素在起作用,根据我的经验,很容易让自己相信某件事,因为它是你能看到的唯一区别,而事实并非如此。
  • 你的问题基本上是“当我运行一个你没有的程序时,我的机器上发生了一些奇怪的事情”。好的,这是一个有趣的故事,但不是一个承认这里的任何人给你解释的故事。如果您想了解它,请创建重现行为的最小可能程序并发布。然后我们实际上可以在不同的机器上尝试看看会发生什么。
  • @BartFriederichs - 很简单。您的代码更有可能出现错误,然后编译器出现代码优化错误。有问题的控件并不新,它已被数十万个应用程序使用,单行已被数十万个应用程序使用。

标签: c# 32-bit


【解决方案1】:

太多的 cmets 无法使重复链接可见,所以我将其作为答案。这是在 64 位版本的 Vista 和 Win7 上调试 32 位程序时的一个已知问题。当调度程序处理 Windows 消息并且消息的事件处理程序抛出未捕获的异常时,消息调度程序中通常有一个后挡板来捕获未处理的异常。 通常会触发 Winforms 上的 Application.ThreadException 事件,WPF 上的 Dispatcher.UnhandledException 事件。

然而,当您调试程序时,这些事件非常尴尬,它使诊断未处理的异常变得困难。因此,当您启动带有调试器的程序时,会禁用此支持以允许调试器查看异常并显示异常助手。帮助您解决问题。

Microsoft 对源自 64 位窗口管理器并多次遍历 Wow64 仿真层边界的某些消息存在问题。他们无法弄清楚如何让未处理的异常遍历这些层,异常信息与代码模型密切相关。所以他们做了他们唯一能做的其他事情,他们捕获异常。这通常会激活“应用程序兼容性”对话框,允许用户选择将异常视为良性,每个人都在此对话框上单击“是”,因为他们不知道对话框要求什么并且希望他们的程序兼容。

这对您的调试尝试非常致命,调试器无法再看到未处理的异常,因为 Windows 捕获并吞下了它。所以你得到了你所描述的,代码只是停止运行,没有任何提示。您只能在“输出”窗口中看到第一次机会异常通知,很容易错过。

我之前发布了有关此问题的答案,并记录了该问题的解决方法。你会发现它here

【讨论】:

  • 我认为你应该得到 +1 只是因为我不明白你所说的大部分内容。
  • 感谢您的解释。我从另一个答案中读到了this piece,让我想知道“由于复杂的原因,我们无法将异常传播回 64 位操作系统(amd64 和 IA64)。”这句话。有这方面的资源吗?
  • 嗯,这很复杂。 Wow64 仿真的确切工作方式完全没有记录。反正帮不了你。更新到 Windows 8 会有所帮助。
猜你喜欢
  • 1970-01-01
  • 2020-03-17
  • 1970-01-01
  • 2018-05-16
  • 2016-10-28
  • 2012-04-17
  • 1970-01-01
  • 2011-03-18
  • 1970-01-01
相关资源
最近更新 更多