C++ Builder 2010中出现奇怪的“随机”内部编译器错误

3

我有一些代码,将许多TNotifyEvents放入一个向量中。

std::vector<TNotifyEvent> m_availableCallbacks;

这是应用程序主窗体的一个成员。在窗体构造函数中,它被填充了事件。

m_availableCallbacks.push_back(ReadoutLastValue);
m_availableCallbacks.push_back(ReadoutCurrentDay);
m_availableCallbacks.push_back(ReadoutLastDay);
m_availableCallbacks.push_back(Readout7Days);
m_availableCallbacks.push_back(Readout1Month);
m_availableCallbacks.push_back(ReadoutChooseTimeSpan);
m_availableCallbacks.push_back(ReadoutAllData);

这个向量被迭代并用于创建弹出菜单,并为该弹出菜单中的元素分配通知事件。
在本地编译没有问题。当我在构建服务器上编译它(运行TeamCity 6.5)时,我在第二个push_back调用处得到了一个内部编译器错误。
我尝试在构建代理上通过编辑cbproj文件禁用智能缓存预编译头。这产生了一个成功的构建。所以我从所有cbproj文件中删除了使用智能缓存预编译头的指令并提交了更改。我告诉TeamCity进行“干净的检出”,再次在同一位置得到了相同的内部编译器错误。奇怪的是,在失败后运行新的编译会成功,所以这感觉非常随机。
到底发生了什么?我习惯于在其他C++编译器中很好地传递函数指针(由自己创建)。是TNotifyEvents的内部处理有问题还是编译器不稳定且容易破坏?
看看使用TNotifyEvents的其他代码,它们不能在引用或指针上工作,所以我没有尝试过。而且,由于代码(当它编译时)按预期工作,因此似乎不是问题所在。
更新:
我可以补充说,当我重新运行编译并成功后,TeamCity的日志显示跳过了包含此代码的FrontEnd.cpp文件。
[10:04:37]: [MakeObjs] CallTarget
[10:04:37]:   [CallTarget] _CppDepCheck
[10:04:44]:     [_CppDepCheck] MessageMap
[10:04:44]:       [MessageMap] Skipping: ..., FrontEnd.cpp, ...

为了使这种情况能够发挥作用,内部编译器错误发生时必须已经成功进行了编译。否则,它怎么可能跳过编译文件并在编译形式下神奇地出现和被使用呢? :)
更新2
经过调查,我可以确认仅在发布模式下编译时才会发生这种情况。在我的本地机器上,即使在IDE中也会发生这种情况。我尝试了一些设置,例如禁用所有优化、生成最快的代码等等,并在每次尝试之间清理构建。但是这个内部编译器错误并没有消失。不过,我确实设法让它抱怨另一个文件中的另一个位置。将设置恢复到之前的状态并不能使错误回到FrontEnd.cpp文件。这个编译器感觉有点不稳定 :)
事实上,我开始在整个代码中都遇到内部编译器错误,不得不重新启动IDE才能编译任何东西。

当我在BCB2010中广泛使用函数指针时,我也遇到了类似的ICE问题。对我来说,当将一个裸函数指针传递给一个期望boost :: function作为其参数的函数时,问题会随机出现。相反,传递boost :: bind(&class:function,this)似乎可以为我解决它。到目前为止... - Roddy
1个回答

0

这似乎与 std::vector 有关。不确定它是自己损坏了还是由于 bcc 处理方式的问题。但是,将其作为测试切换到 C 风格数组后,ICE 消失了,并且现在在调试和发布模式下都可以正常工作。

TNotifyEvent m_availableCallbacks[7];

我本来想避免这种情况,因为向向量添加新事件几乎只需要一行代码。现在还需要记住更多的变化。但是,最好让应用程序编译。

如果我错误地认为这是BCC中的错误,请纠正我,这样我就可以尽快回到使用向量了 :)...否则,我希望Embarcadero尽快修复这个问题。


对于那些感兴趣的人,这已经被报告给 Embarcadero,编号为 106025。 - inquam

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接