2012-04-29 65 views
0

我遇到了用C++编写的DLL的问题。有一些非常奇怪的行为继续,我一直无法自己解决。当C++ DLL程序退出时:运行时检查失败#2

很难描述到底发生了什么,但我会尽我所能。基本上我有一个类,在我的DLL中有一个私有属性和一个公共构造函数。 当我初始化这个类,然后退出程序时,我得到一个错误。

“运行时检查失败#2 - 堆栈围绕变量 '测试' 是 损坏”

我有2项目这里:

  1. 的DLL命名“testdll”。
  2. 命名为“测试”控制台测试程序。

我把这个错误归结为最简单的可重复的形式来试图缩小可能的原因,下面你会发现我的代码。

工程 “testdll”,文件testdll.h:

#include <string> 

class testdll 
{ 
public: 
__declspec(dllexport) testdll(); // Empty but same error if prams are used. 

private: 
std::string _var; 
}; 

工程 “testdll”,文件testdll.cpp:

#include "testdll.h" 

testdll::testdll() 
{ 
} 

项目的 “测试”,文件testdll .H:

#include <string> 

class testdll 
{ 
public: 
    __declspec(dllimport) testdll(); 
}; 

项目的 “测试”,stdafx.h文件:

#pragma once 

#include "targetver.h" 

#include <tchar.h> 

项目的 “测试”,文件TEST.CPP:

#include "stdafx.h" 
#include "testdll.h" 

int _tmain(int argc, _TCHAR* argv[]) 
{ 
testdll test; 

return 0; 
} 

如果你想我可以在视觉送你C++ 2010解决方案文件,以您选择的归档格式。请帮忙!我不知道发生了什么事。

可选信息: 语言(或软件):C++

已经尝试过: 删除构造函数的定义,它的工作原理,但不是一个可用的解决方案,也没有说明这个问题。也使我所有的私人物业成为指针作品,但我不应该这样做。

回答

1

您正在使用两个头文件,它们不声明相同的类。一个有std :: string成员,另一个没有。这非常糟糕,编译器没有为堆栈帧上的对象预留足够的空间。这是运行时错误告诉你的。顺便说一句,非常好的功能,这种错误是难以置信的难以诊断,否则。

您可能进入了这个pickle,因为您只将__declspec(dllexport)应用于构造函数而不是整个类。您需要编写头文件,以便它可以用于您的DLL项目您的exe项目。这应该是这样的:

#undef DLLEXPORT 
#ifdef BUILDING_MYDLL 
# define DLLEXPORT __declspec(dllexport) 
#else 
# define DLLEXPORT __declspec(dllimport) 
#endif 

class DLLEXPORT testdll 
{ 
public: 
    testdll(); 
private: 
    std::string _var; 
}; 

右键单击您的DLL项目,属性,C/C++,预处理,预处理定义。追加BUILDING_MYDLL

并删除exe项目目录中的testdll.h文件。设置C/C++常规附加包含目录设置,以便编译器可以在testdll项目目录中找到标题(例如.. \ testdll)

0

导出类和类成员从一个DLL是非常非常脆弱的,因为你刚刚发现。如果库和客户端都不使用完全相同的类布局(取决于各种编译器设置),那么事情就会失败。

对于您的情况,您可能在class testdll中使用std::string的不兼容版本。也许一个是为了调试而编译的,一个是为了发布。或者一个使用静态运行时库,另一个使用DLL运行时。谁能说?

无论如何,只要您从DLL中导出C++功能,就可以将自己锁定在该编译器的版本和设置中。这是一个维护噩梦。

使用仅v表的基类或C兼容包装函数。

+0

DLL项目和使用它的测试项目都在相同的解决方案中文件,所以这些类型的环境问题不应该造成这一点,据我所知。 – Aloxis 2012-04-29 06:23:19

+0

@Aloxis:仍然有许多每个项目设置需要处理,必须完美匹配。另外,并非所有的设置都可以使用。 'std :: string'分配内存,两个项目都必须设置为使用共享运行时分配器(使用DLL运行时库)。 – 2012-04-29 06:28:10

+0

我不知道这意味着什么,明天我会看看它,当我没有那么疲惫,看看它是否能解决这个问题。非常感谢您花时间回答。 – Aloxis 2012-04-29 06:53:36

相关问题