与 DLL 不工作的共享全局变量
Shared global variable with DLL not working
我正在尝试让一些在 Mac 上运行的代码在 Windows 上运行。该代码涉及在 DLL、静态库和主程序之间共享数据。我怀疑问题的出现是因为 Unix 和 Windows 处理全局变量的方式不同(例如,参见 the answers here)。但是,我还没有想出如何解决它。这是一个最小的例子:
我的 Visual Studio 2019 解决方案包含三个项目。
项目1制作静态库MarinaLib.lib
Header 是 MarinaLib.h
#pragma once
#include "Marina.h"
Class header 是 Marina.h
#pragma once
class Marina
{
public:
static Marina* get_marina();
protected:
static Marina* marina_instance;
};
源文件是Marina.cpp
#include "Marina.h"
Marina* Marina::marina_instance { nullptr };
Marina* Marina::get_marina()
{
if( !marina_instance )
marina_instance = new Marina();
return marina_instance;
}
项目 2 生成 DLL MarinaDLL.dll。它 #define
s MARINADLL_EXPORTS
第一个源文件dllmain.cpp
// dllmain.cpp : Defines the entry point for the DLL application.
#include "framework.h"
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}
Header 文件 MarinaDLL.h 是
#pragma once
#ifdef MARINADLL_EXPORTS
#define QUERY_DECLSPEC __declspec(dllexport)
#else
#define QUERY_DECLSPEC __declspec(dllimport)
#endif
QUERY_DECLSPEC void query_marina();
第二个源文件是marinaDLL.cpp
#include "MarinaDLL.h"
#include "..\MarinaLib\Marina.h"
void query_marina()
{
auto inst = Marina::get_marina();
}
项目 3 生成可执行文件 MarinaExample.exe 而不是 #define
MARINADLL_EXPORTS
。它链接 MarinaLib.lib 和 MarinaDLL.lib
源文件MarinaExample.cpp是
#include "MarinaLib.h"
#include "MarinaDLL.h"
int main()
{
auto instance = Marina::get_marina();
query_marina();
}
第一行main()
,代码输入Marina::get_marina()
。 marina_instance
是 nullptr
所以代码创建了一个新的 Marina
并使 marina_instance
指向它。这很好。
在 main()
的第二行,代码输入 query_marina()
并从那里进入 Marina::get_marina()
。此时 marina_instance
是 nullptr
这不是我想要的。我希望它保持以前的 non-null 值。
我在类似代码中看到了一些解决问题的示例,但它们似乎不适用于我的情况。关于如何解决这个问题有什么建议吗?
谢谢。
将导出修饰符添加到 class 定义并导出整个 class。
在 dll 和 lib 构建中定义 QUERY_DECLSPEC=export ,在 exe 构建中定义为 import :
class QUERY_DECLSPEC Marina
{
public:
static Marina* get_marina();
protected:
static Marina* marina_instance;
};
我正在尝试让一些在 Mac 上运行的代码在 Windows 上运行。该代码涉及在 DLL、静态库和主程序之间共享数据。我怀疑问题的出现是因为 Unix 和 Windows 处理全局变量的方式不同(例如,参见 the answers here)。但是,我还没有想出如何解决它。这是一个最小的例子:
我的 Visual Studio 2019 解决方案包含三个项目。
项目1制作静态库MarinaLib.lib
Header 是 MarinaLib.h
#pragma once
#include "Marina.h"
Class header 是 Marina.h
#pragma once
class Marina
{
public:
static Marina* get_marina();
protected:
static Marina* marina_instance;
};
源文件是Marina.cpp
#include "Marina.h"
Marina* Marina::marina_instance { nullptr };
Marina* Marina::get_marina()
{
if( !marina_instance )
marina_instance = new Marina();
return marina_instance;
}
项目 2 生成 DLL MarinaDLL.dll。它 #define
s MARINADLL_EXPORTS
第一个源文件dllmain.cpp
// dllmain.cpp : Defines the entry point for the DLL application.
#include "framework.h"
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return TRUE;
}
Header 文件 MarinaDLL.h 是
#pragma once
#ifdef MARINADLL_EXPORTS
#define QUERY_DECLSPEC __declspec(dllexport)
#else
#define QUERY_DECLSPEC __declspec(dllimport)
#endif
QUERY_DECLSPEC void query_marina();
第二个源文件是marinaDLL.cpp
#include "MarinaDLL.h"
#include "..\MarinaLib\Marina.h"
void query_marina()
{
auto inst = Marina::get_marina();
}
项目 3 生成可执行文件 MarinaExample.exe 而不是 #define
MARINADLL_EXPORTS
。它链接 MarinaLib.lib 和 MarinaDLL.lib
源文件MarinaExample.cpp是
#include "MarinaLib.h"
#include "MarinaDLL.h"
int main()
{
auto instance = Marina::get_marina();
query_marina();
}
第一行main()
,代码输入Marina::get_marina()
。 marina_instance
是 nullptr
所以代码创建了一个新的 Marina
并使 marina_instance
指向它。这很好。
在 main()
的第二行,代码输入 query_marina()
并从那里进入 Marina::get_marina()
。此时 marina_instance
是 nullptr
这不是我想要的。我希望它保持以前的 non-null 值。
我在类似代码中看到了一些解决问题的示例,但它们似乎不适用于我的情况。关于如何解决这个问题有什么建议吗?
谢谢。
将导出修饰符添加到 class 定义并导出整个 class。
在 dll 和 lib 构建中定义 QUERY_DECLSPEC=export ,在 exe 构建中定义为 import :
class QUERY_DECLSPEC Marina
{
public:
static Marina* get_marina();
protected:
static Marina* marina_instance;
};