【发布时间】:2014-10-22 16:22:34
【问题描述】:
我们一直在修复 Delphi XE6 中 VCL 中的错误。到目前为止,该文件夹包含:
| VCL Source Fixes
|----- Vcl.ComCtrls.pas
|----- Winapi.CommCtrl.pas
然后我们将文件夹添加到我们的 Library 搜索路径:
在此过程中,我们了解到我们必须将修复限制在implementation 部分仅限。否则interface 部分中符号的哈希签名会改变。这会导致链接器意识到 DCU 中的符号与他们期望的版本不同。
Barry Kelly 对此行为有很好的解释:
重要的概念是符号版本。保存 DCU 时,Delphi 会根据符号的接口声明 计算哈希,并将其与符号相关联。使用该符号的其他单元也存储符号版本。这样,与大多数 C 链接器不同,避免了由陈旧符号引起的链接时冲突。
这样做的结果是,您应该能够将 Classes.pas 添加到您的项目中,并且几乎可以随心所欲地修改它的 implementation 部分,并且仍然能够静态地 strong> 与其他 RTL 和 VCL 以及第三方库的链接,即使是那些仅以对象格式提供的库。
注意事项:
- 内联例程;内联例程的主体是符号版本的一部分
- 泛型;泛型类型和方法的实现部分是各自符号版本的一部分
所以我们煞费苦心地将错误修复限制在实现部分(例如,引入新的破解程序类,而不是覆盖面向公众的类中的方法)。
然后
然后我去Vcl.Themes.pas 进行修复。我从简单的开始,复制文件并将其放在修复文件夹中:
| VCL Source Fixes
|----- Vcl.ComCtrls.pas
|----- Winapi.CommCtrl.pas
|----- Vcl.Themes.pas
即使我(还没有)修改过Vcl.Themes.pas,编译器还是会卡住它:
[dcc32 致命错误] Vcl.Themes.pas(2074): F2051 Unit Vcl.Forms 是用不同版本的 Vcl.Themes.TMouseTrackControlStyleHook 编译的
为什么
重要的问题是:
为什么会这样?
编译器无法意识到完全相同的文件是完全相同的文件是怎么回事? XE6 附带的 VCL 源是否可能不正确,并且与 DCU 中附带的不匹配?它与图书馆搜索顺序有关吗?它是否与内联、泛型、迭代器、平台、调试 dcus、64 位编译器、ifdef、代码完成、协同、开箱即用有关?
除了试图回答为什么之外,还有其他隐含的问题:
为什么它适用于其他两个文件,但不适用于这个?
为什么我什至没有更改文件时它会失败?
你有什么尝试?
- 尝试将
VCL Source Fixes在搜索路径中上下移动 - 尝试开启使用调试数据库
- 尝试切换到 64 位平台
- 尝试删除我项目文件夹中的所有
dcu文件(尽管没有删除 Delphi XE6 附带的D:\Programs\Embarcadero\Studio\14.0\lib\win32\release\Vcl.Themes.dcu) - 关闭 XE6 并重新运行它
- 去温迪家吃午饭
我当然想修复它。但除了想要修复它之外,我还想了解它为什么会失败。编译器没有使用魔法、巫术或类似 Q 的能力。它是一台确定性机器,按照一组固定的(未记录的)规则运行。
为什么会这样?
另见
【问题讨论】:
-
对不起,伊恩,但你运气不好。你需要绕道而行。我试图说服 Marco 这是坏了,但他不相信我。 blog.marcocantu.com/blog/…marco 本来是负责开发关系的,所以当他不听我们的时候上帝会帮助我们
-
通常编译器设置会产生影响。也许是 RTTI 设置。沃伦似乎认为这可能是一个线索。
-
@DavidHeffernan 原来是这样。我会等几天,然后将答案附加到问题中。
-
@DavidHeffernan,XE6 中的某些代码生成存在缺陷,请参阅Regression, Invalid code gen when referencing consts defined in classes or records。已解决,但没有可用的更新或补丁。 XE6 不会被我们用于生产。
标签: delphi delphi-xe6