从D2006移植到XE5后偶发访问冲突在XP兼容模式下不会发生

时间:2014-04-05 19:35:29

标签: delphi windows-7 access-violation delphi-xe5

我们有一个大型应用程序在Delphi 2006中运行良好。我们已将其移至XE5并且经常出现偶发的访问冲突。我们正在使用VCL表单和一些DevExpress以及其他第三方组件。我们在Windows 7 Professional中使用Delphi XE Enterprise,版本19.0.14356.6604。

我们已经在这里和其他地方看到了在移植到XE5之后有关A / V的帖子,但是没有发现任何与我们的问题相关的内容。

以下是我们对A / V的了解:

  • 它们通常出现在同一地址:0x50059f27。有时它们发生在0x5005eb86,通常是在另一个地址触发了A / V之后。
  • 它们来自应用程序中的各种不同位置和操作。
  • 它们不是100%可重复的。有时重建项目会消除一个触发器,但是其他东西会触发它。它们似乎在构建中保持相当一致的可重复性。
  • 它们通常与打开对话框或激活返回大量记录(1,000 +)的查询相关联。
  • D2006版本(我们在XP机箱或XP虚拟机上运行)不会发生这种情况。 - 当我们在XP-SP3兼容模式下运行XE5应用程序时,它们不会发生。
  • 如果我们在典型的A / V之后中断,则指针将位于第562行的System.pas中,位于{$IFDEF CPUX86}的{​​{1}} asm部分中。下面附加了代码部分。该行为procedure Move(const Source; var Dest; Count: NativeInt);

我们猜测这个问题与我们的应用程序如何处理Windows 7内存管理有关,但我们不知道如何找出它出错的地方。附加了一个示例调用堆栈。

有人可以建议我们如何解决此问题吗?是否有第三方调试工具可以提供帮助?我们可以使用Delphi IDE工具来尝试跟踪它吗?可能有用的文章?

非常感谢任何建议。

以下是发生A / V的System.pas代码部分:

FILD QWORD PTR [EAX] {Last 8}

以下是来自Call Stack的示例:

    @@LargeForwardMove: {4-Byte Aligned}
    PUSH    EDX
    FILD    QWORD PTR [EAX] {First 8}
    LEA     EAX, [EAX+ECX-8]
    LEA     ECX, [ECX+EDX-8]
    FILD    QWORD PTR [EAX] {Last 8}      // <- Debug break pointer will be here. 
    PUSH    ECX
    NEG     ECX
    AND     EDX, -8 {8-Byte Align Writes}
    LEA     ECX, [ECX+EDX+8]
    POP     EDX

1 个答案:

答案 0 :(得分:4)

这看起来像是程序中的一个简单错误。发布后可能会访问内存。或缓冲区溢出。你需要做的是一些调试。您需要的工具是:

  1. 启用范围检查编译器选项。这可以找到大多数缓冲区溢出。
  2. 具有完整调试设置的FastMM完整版。这应该指出免费后的访问错误。
  3. madExcept。这将在异常点提供堆栈跟踪。这是至关重要的,因为它可以让你看到你在代码中如何达到这一点。这反过来可以帮助您查看正在传递的数据,并且应该为您提供有关您做错了什么的线索。我知道你有一个堆栈跟踪,但它看起来并不正确。毕竟,TBitBtn.Click并未直接致电Move
  4. 不要自欺欺人的事实,你不会在XP上看到错误,这意味着责任在于操作系统。或者以某种方式,您需要在不同版本的操作系统中以不同方式处理内存。许多应用程序编程错误在某些系统上是良性的,但在其他系统上却是明显的。你的程序在任何地方都被破坏的可能性很高,但你偶然会在某些时候侥幸逃脱。