0

我有一个 WinForms 应用程序,我希望能够在其中提供 HTML 编辑功能。因此,我将Lutz Roeder 的 HTML Writer从 C# 转换为 VB.NET,并将其从 windows 窗体转换为自定义用户控件,该控件现在托管在 MDI 子窗体中。

在我关闭父 MDI 之前一切正常,在这种情况下它会崩溃,并且我无法捕获异常。

我已将编辑器控件隔离到一个不执行任何其他操作的小型 WinForms 应用程序中,并验证问题仍然存在。

我还打开了非托管代码调试(我使用的是 VS2010,为 x86 和 Framework 3.5 编译),我得到的只是:

Windows has triggered a breakpoint in HtmlEditorMdi.exe.
This may be due to a corruption of the heap, which indicates a bug in HtmlEditorMdi.exe or any of the DLLs it has loaded.
This may also be due to the user pressing F12 while HtmlEditorMdi.exe has focus.
The output window may have more diagnostic information.

我注意到的唯一一件事是,如果我在打开包含编辑器的表单后离开很长一段时间,它不会崩溃。

我真正欣赏的是一些关于如何去寻找这个问题的想法。当然,我在 C# 到 VB 的转换中可能犯了一个错误,但我很难知道去哪里找。

编辑

我已经运行了带有调试器的应用程序,但它并没有给我任何有用的东西。

我得到的只是 Windows 的“应用程序已停止工作”消息,问题详细信息中包含以下内容:

Problem signature:
  Problem Event Name:   APPCRASH
  Application Name: HtmlEditorMdi.exe
  Application Version:  1.0.0.0
  Application Timestamp:    4cfb74c7
  Fault Module Name:    mscorwks.dll
  Fault Module Version: 2.0.50727.4952
  Fault Module Timestamp:   4bebd49a
  Exception Code:   c0000005
  Exception Offset: 000022b5
  OS Version:   6.1.7600.2.0.0.256.1
  Locale ID:    2057
  Additional Information 1: 0a9e
  Additional Information 2: 0a9e372d3b4ad19135b953a78882e789
  Additional Information 3: 0a9e
  Additional Information 4: 0a9e372d3b4ad19135b953a78882e789

我可以看到这是一个访问冲突,但即使我去Debug > Exceptions > Win32 Exceptions并勾选c0000005,当它中断时我没有得到任何有用的东西 - 只是“没有可用的源”。

4

2 回答 2

1

您引用的第一条消息是由 Windows 堆管理器在发现内部堆结构被破坏时生成的。当它看到附加了调试器时,它会显示该诊断。第二个引用的块是当它绕过诊断(没有附加调试器)时发生的事情,当它试图释放损坏堆中的内存时,它会在硬件异常上爆炸。

堆损坏的问题在于,真正的损坏是在生成诊断之前很长时间完成的。您可以在“调用堆栈”窗口中看到导致诊断的堆栈跟踪,您需要启用 Microsoft 符号服务器以获取 Windows 函数的有意义的符号。但它不会告诉你关于真正造成损害的代码的任何有用信息,这需要时间机器。

这种堆损坏总是由非托管代码引起的。AccessViolation 异常是 C/C++ 程序员众所周知的祸害,也是托管代码流行的一个重要原因。虽然 Lutz 的源代码都是托管的,但它包含很多P/Invoke 和 COM 接口声明。没有调试它们的好方法,你没有源代码。

当您将其中一个声明转换为 VB.NET 时,它们会出现微妙的错误,这当然是可能发生这种情况的一种方式。也有可能是虫子一直都在,只是现在才抬起丑陋的脑袋。幸运的你。顺便说一句,我不认为代码是 64 位干净的,强制它在 32 模式下运行以进行可能的快速修复。对于您的主 EXE 项目:项目 + 属性,编译选项卡,向下滚动,高级编译选项,目标 CPU = x86。仅当您在 64 位版本的 Windows 上运行时才有意义。

除此之外,我建议您按原样使用 C# 项目。在解决方案中混合语言是 .NET 中非常受支持的方案。

于 2010-12-05T14:19:03.013 回答
0

windbg调试器是这类问题的“大炮”。它经常可以通过告诉您处理的异常等来为您提供线索。唯一的问题是它不容易使用并且学习曲线非常高。

于 2010-12-05T15:15:19.350 回答