将 C++ 项目升级到 VS2010,现在得到 AccessViolationException
Posted
技术标签:
【中文标题】将 C++ 项目升级到 VS2010,现在得到 AccessViolationException【英文标题】:Upgraded C++ project to VS2010, now get AccessViolationException 【发布时间】:2011-06-15 18:58:14 【问题描述】:我们最近从 VS2005 -> VS2010 升级了一些 C++ 代码。
此 C++ 代码称为 RFA_RMDS,它是 Reuters RFA 库的内部包装器。这个包装器被一些 C# 代码依次使用。所以,要清楚:
C# -> C++ Wrapper (RFA_RMDS) -> Reuters RFA 库。
升级后,应用程序在实例化 RFA 客户端时抛出 AccessViolationException(如下) - 但仅限于 Windows 7。也就是说,它在 Windows XP 上运行良好。
此外,使用 VS2005 版本的 C++ 包装器的应用程序的早期版本在 Windows 7 和 Windows XP 上都可以正常工作。
这使我相信升级是导致此异常的原因。但是,因为我不是 C++ 开发人员(我们现在真的没有),我不知道如何解决这个问题。
还有几点:
应用程序在 Windows 7 上以 32 位模式运行,因为可执行文件已被 CorFlags 修改。 使用 VS2005 C++ 包装器的早期版本的应用程序在 Windows 7 和 Win XP 上都可以正常工作。 C++ 包装器以 .NET 2.0 为目标,尽管它曾经以 .NET 3.5(C# 代码的目标)为目标。即使针对 .NET 3.5 也存在问题。 Windows 7 机器包含 Microsoft Visual C++ 2005(x86??/x64)、2008 (x86/x64) 和 2010 (x86) 的可再发行组件。如果我应该提供更多信息,请告诉我 - 也许还有如何获得它。
非常感谢任何提示/建议/解决方案,即使是最基本的东西。谢谢。
堆栈跟踪
AccessViolationException 尝试读取或写入受保护的内存。这通常表明其他内存已损坏。 在 std.basic_string,std::allocator >.dtor(basic_string\,std::allocator >* ) 在 c:\buildagent\work\ef735b7d6bb58dc3\rfa_rmds\rfa_rmds\apploggerclient.cpp:line 70 中的 AppLoggerClient.processEvent(AppLoggerClient* , Event* event) 在 c:\buildagent\work\ef735b7d6bb58dc3\rfa_rmds\rfa_rmds\messageloop.cpp:line 51 中的 CWM.WindowProc(HWND__* hwnd, UInt32 uMsg, UInt32 wParam, Int32 lParam) 在 DispatchMessageW(tagMSG* ) 在 c:\program files\microsoft sdks\windows\v6.0a\include\winuser.h:line 3052 中的 DispatchMessage(tagMSG* lpMsg) 在 c:\buildagent\work\ef735b7d6bb58dc3\rfa_rmds\rfa_rmds\messageloop.cpp:line 89 中的 CWM.run(CWM*) 在 RFA_RMDS.RFA_Frame.Start() 在 c:\buildagent\work\ef735b7d6bb58dc3\rfa_rmds\rfa_rmds\rfa_frame.cpp:line 122 在 RFA_RMDS.RFA_FrameManager.WorkerThreadFunction() 在 c:\buildagent\work\ef735b7d6bb58dc3\rfa_rmds\rfa_rmds\rfa_framemanager.cpp:line 126 在 System.Threading.ThreadHelper.ThreadStart_Context(对象状态) 在 System.Threading.ExecutionContext.runTryCode(对象 userData) 在 System.Runtime.CompilerServices.RuntimeHelpers.ExecuteCodeWithGuaranteedCleanup(TryCode 代码,CleanupCode backoutCode,对象 userData) 在 System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext,ContextCallback 回调,对象状态) 在 System.Threading.ExecutionContext.Run(ExecutionContext executionContext,ContextCallback 回调,对象状态) 在 System.Threading.ThreadHelper.ThreadStart()VS2010 C++ 命令行
/I"..\..\RFA-6.3\Include" /I"..\..\RFA-6.3\Include\TIBMsg" /I"..\..\RFA-6.3\Include\SessionLayer" / I"..\..\RFA-6.3\Include\Common" /I"..\..\RFA-6.3\Include\Logger" /I"..\..\RFA-6.3\Include\Config" /Zi /clr:oldSyntax /nologo /W3 /WX- /O2 /Oy- /GL /D "WIN32" /D "NDEBUG" /D "_WINDLL" /D "_UNICODE" /D "UNICODE" /EHa /MD / GS /fp:precise /Zc:wchar_t /Zc:forScope /Yu"StdAfx.h" /Fp"Release\RFA_RMDS.pch" /Fa"Release\" /Fo"Release\" /Fd"Release\vc90.pdb" /Gd /TP /FU"c:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\System.Data.dll" /FU"c:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\System.dll" /FU"c:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\System.Xml.dll" /analyze- /errorReport:queueVS2005 C++ 命令行
/Od /I "..\..\RFA-6.3\Include" /I "..\..\RFA-6.3\Include\TIBMsg" /I "..\..\RFA-6.3\Include\SessionLayer " /I "..\..\RFA-6.3\Include\Common" /I "..\..\RFA-6.3\Include\Logger" /I "..\..\RFA-6.3\Include\ Config" /D "WIN32" /D "_DEBUG" /D "_WINDLL" /D "_UNICODE" /D "UNICODE" /FD /EHa /MDd /Yu"stdafx.h" /Fp"Debug\RFA_RMDS.pch" / Fo"Debug\\" /Fd"Debug\vc80.pdb" /W3 /nologo /c /Zi /clr:oldSyntax /TP /errorReport:prompt /FU "c:\WINDOWS\Microsoft.NET\Framework\v2.0.50727 \System.dll" /FU "c:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\System.Data.dll" /FU "c:\WINDOWS\Microsoft.NET\Framework\v2.0.50727\System.XML .dll"VS2010 链接器命令行
/OUT:"F:\checkout\gl\global\trunk\client\modules\RFASource\DotNet2.0\RFA_RMDS\Release\RFA_RMDS.dll" /INCREMENTAL:NO /NOLOGO /LIBPATH:"..\..\RFA -6.3\Libs" /DLL "msvcprt.lib" "msvcrt.lib" "ws2_32.lib" "RFA6_Common80.lib" "RFA6_Config80.lib" "RFA6_Logger80.lib" "RFA6_Data80.lib" "RFA6_Connections80.lib" "RFA6_Connections_MD80. lib”“RFA6_SessionLayer80.lib”“AnsiPage80.lib”“libTibMsg.lib”“dacslock.lib”“Shell32.lib”“Shlwapi.lib”“kernel32.lib”“user32.lib”“gdi32.lib”“winspool。 lib" "comdlg32.lib" "advapi32.lib" "shell32.lib" "ole32.lib" "oleaut32.lib" "uuid.lib" "odbc32.lib" "odbccp32.lib" /MANIFEST /ManifestFile:"Release\ RFA_RMDS.dll.intermediate.manifest" /ALLOWISOLATION /MANIFESTUAC:"level='asInvoker' uiAccess='false'" /DEBUG /PDB:"F:\checkout\gl\global\trunk\client\modules\RFASource\DotNet2. 0\RFA_RMDS\Release\RFA_RMDS.pdb" /PGD:"F:\checkout\gl\global\trunk\client\modules\RFASource\DotNet2.0\RFA_RMDS\Release\RFA_RMDS.pgd" /LTCG /TLBID:1 / DYNAMICBASE:NO /FIXED:NO /MACHINE:X86 /ERRORR报告:队列VS2005 链接器命令行
/OUT:"F:\checkout\gl\global\trunk\client\modules\RFASource_VS2005\DotNet2.0\RFA_RMDS\Debug\RFA_RMDS.dll" /INCREMENTAL /NOLOGO /LIBPATH:"..\..\RFA-6.3 \Libs" /DLL /MANIFEST /MANIFESTFILE:"Debug\RFA_RMDS.dll.intermediate.manifest" /DEBUG /ASSEMBLYDEBUG /PDB:"f:\checkout\gl\global\trunk\client\modules\RFASource_VS2005\DotNet2.0\ RFA_RMDS\Debug\RFA_RMDS.pdb" /MACHINE:X86 /FIXED:No /ERRORREPORT:PROMPT msvcprt.lib msvcrt.lib ws2_32.lib RFA6_Common80.lib RFA6_Config80.lib RFA6_Logger80.lib RFA6_Data80.lib RFA6_Connections80.lib RFA6_Connections_MD80.lib RFA6_libSessionLayer80. AnsiPage80.lib libTibMsg.lib dacslock.lib Shell32.lib Shlwapi.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32。库【问题讨论】:
似乎std::string
正在从其析构函数中抛出异常,这是不对的。是否重新编译了所有依赖代码(即第三方库等)?
您的堆损坏可能是由于某处的链接不一致或不兼容。重建所有库和项目,如果需要,请确保在目标机器上部署正确的 VC 运行时,您可以从 microsoft 下载 VC redist。
@rubenvb:唯一的依赖代码是 Microsoft.VisualC 8.0.0.0 和 mscorlib/System/System.Data/System.Xml - 都是 2.0.0.0。
@AJG95:我从干净的结帐中重建了 RFA_RMDS。在发布之前,我还在 Windows 7 机器上安装了 Microsoft Visual C++ 2010 x86 redistributable - 10.0.30319。而且 Windows 7 盒子还包含 Microsoft Visual C++ 2005 (更有可能是升级暴露的代码中存在缺陷或潜在错误,而不是升级本身导致错误。非确定性或未定义的行为(例如,当您取消引用未初始化的指针时会发生什么),很容易在构建、执行环境或编译器之间更改,甚至在发布和调试之间或直接或通过调试器运行时更改.
我将首先使用您拥有的调试信息,例如查看..\rfa_rmds\apploggerclient.cpp:line 70
(和之前)发生的情况。它导致一个字符串对象被删除,如果这是一个显式的delete
,指针是否有效?如果它正在删除一个字符串数组,是否使用了正确的delete[]
运算符?如果是auto
对象超出范围,是否有其他错误(例如缓冲区溢出)导致对象损坏?
验证这些事情的最简单方法是在调试器中执行代码。然而,执行环境的改变往往会改变非确定性错误的行为,所以为什么你可能不再得到异常,你可能仍然能够观察到其他错误行为,例如通过无效指针写入或数据损坏。
【讨论】:
【参考方案2】:将 rfa 日志从默认应用启动位置(Windows 7 漫游)移至 c:\temp。
【讨论】:
我认为根据我在 RFA 方面的经验,这是一个很好的起点 -【参考方案3】:我遇到了同样的问题。原来,在其中一个原生项目中,Platform Toolset
被设置为v100
而不是v90
。
【讨论】:
【参考方案4】:这是一个猜测,基于两个因素:错误在 DLL 中,错误在 std::string 析构函数中。这向我表明,您在 DLL 外部构建了一个字符串,并试图在 DLL 内部销毁。由于 DLL 和应用程序有自己的内存管理器副本(除非您使用跨 DLL 边界工作的自定义分配器),任何一个分配器和另一个释放器都可能导致崩溃。避免这种情况的一种方法是在各处动态链接 RTL,因此您只有一个内存管理器副本,或者创建自定义分配器以避免多个内存管理器(更多工作)。
【讨论】:
【参考方案5】:UAC 是这里的问题吗?有时 RFA 需要访问注册表或文件系统。我猜这可能是个问题。
【讨论】:
以上是关于将 C++ 项目升级到 VS2010,现在得到 AccessViolationException的主要内容,如果未能解决你的问题,请参考以下文章
将crm 4插件项目从visual studio 2005升级到visual studio 2010
将解决方案 C++ 从 VS2005 升级到 VS2012 出现错误 LNK1181