[英]error LNK2001: unresolved external symbol CWbemProviderGlue::FrameworkLogoffDLL(wchar_t const *)" in Visual Studio 2019
有一些最初為 Windows 2000 和 WMI SDK 設計的代碼。 我正在嘗試解決 linker 錯誤。 在嘗試了什么是未定義的引用/未解決的外部符號錯誤中引用的選項后,我該如何解決? 無法找到解決方案。
未解決的符號錯誤:
1>WmiProvider.obj : error LNK2001: unresolved external symbol "__declspec(dllimport) public: __thiscall Provider::Provider(wchar_t const *,wchar_t const *)" (__imp_??0Provider@@QAE@PB_W0@Z)
1>WmiProvider.obj : error LNK2001: unresolved external symbol "__declspec(dllimport) public: bool __thiscall CInstance::SetCHString(wchar_t const *,char const *)" (__imp_?SetCHString@CInstance@@QAE_NPB_WPBD@Z)
1>dllmain.obj : error LNK2001: unresolved external symbol "__declspec(dllimport) public: static int __stdcall CWbemProviderGlue::FrameworkLogoffDLL(wchar_t const *)" (__imp_?FrameworkLogoffDLL@CWbemProviderGlue@@SGHPB_W@Z)
1>dllmain.obj : error LNK2001: unresolved external symbol "__declspec(dllimport) public: static int __stdcall CWbemProviderGlue::FrameworkLoginDLL(wchar_t const *)" (__imp_?FrameworkLoginDLL@CWbemProviderGlue@@SGHPB_W@Z)
我試過添加代碼:
#pragma comment(lib,"Framedyn.lib")
並嘗試將 lib 添加到framedyn.lib linker 選項,但仍然出現相同的錯誤。
該項目定義了以下內容以允許在 Windows XP 上運行:
#define _WIN32_WINNT 0x0501
項目設置包括:
示例用法:
case DLL_PROCESS_ATTACH:
ghModule = hInstDLL;
bRet = CWbemProviderGlue::FrameworkLoginDLL(L"WmiProvider");
break;
CL.exe 和 MSBUILD.exe 從以下位置加載WbemGlue.h :
C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\Include\WbemGlue.h
link.exe 從以下位置加載FrameDyn.lib :
C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\Lib\FrameDyn.Lib
dumpbin /exports "C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\Lib\FrameDyn.Lib" 將 FrameworkLoginDLL 的條目顯示為:
?FrameworkLoginDLL@CWbemProviderGlue@@SGHPBG@Z (public: static int __stdcall CWbemProviderGlue::FrameworkLoginDLL(unsigned short const *))
?FrameworkLoginDLL@CWbemProviderGlue@@SGHPBGPAJ@Z (public: static int __stdcall CWbemProviderGlue::FrameworkLoginDLL(unsigned short const *,long *))
查看符號差異是當我編譯 Visual Studio 時正在尋找FrameworkLoginDLL@CWbemProviderGlue@@SGHPB_W@Z而 lib 文件末尾有一個 G 並且沒有W ie **FrameworkLoginDLL@CWbemProviderGlue@@SGHPBG @Z**
舊的 MSDN 文檔(從 2001 年 8 月開始)指定了這種用途:
當將 DLL_PROCESS_ATTACH 值發送到 DllMain 以確定是否可以加載提供程序服務器時調用 FrameworkLoginDLL 方法。
static BOOL WINAPI CWbemProviderGlue::FrameworkLoginDLL(
LPCWSTR name
);
要求:
此處的當前文檔指定使用:
BOOL FrameworkLoginDLL(
LPCWSTR name
);
有以下要求:
使用桌面 C++ 向導創建新的 Visual Studio 2019 項目,選擇 DLL 和所有其他默認值,使用此代碼重現相同的問題:
#include "framework.h"
#include <FwCommon.h>
#pragma comment(lib,"FrameDyn.lib")
BOOL APIENTRY DllMain( HMODULE hModule,
DWORD ul_reason_for_call,
LPVOID lpReserved
)
{
BOOL bRet = TRUE;
switch (ul_reason_for_call)
{
case DLL_PROCESS_ATTACH:
bRet = CWbemProviderGlue::FrameworkLoginDLL(L"WmiProvider");
case DLL_THREAD_ATTACH:
case DLL_THREAD_DETACH:
case DLL_PROCESS_DETACH:
break;
}
return bRet;
}
拆解符號 linker 正在嘗試使用獲取以下內容:
__imp_public: static int __stdcall CWbemProviderGlue::FrameworkLoginDLL(wchar_t const *)
對實際.lib 文件中的符號進行拆解:
public: static int __stdcall CWbemProviderGlue::FrameworkLoginDLL(unsigned short const *)
WbemGlue.h 中的定義
static BOOL WINAPI FrameworkLoginDLL(LPCWSTR name);
出現此問題是因為 MSVC 正在尋找符號FrameworkLoginDLL@CWbemProviderGlue@@SGHPB_W@Z但 lib 文件具有定義FrameworkLoginDLL@CWbemProviderGlue@@SGHPBG@Z 。
使用https://demangler.com/對名稱進行拆解顯示 MSVC 使用的符號是:
__imp_public: static int __stdcall CWbemProviderGlue::FrameworkLoginDLL(wchar_t const *)
lib文件在哪里:
public: static int __stdcall CWbemProviderGlue::FrameworkLoginDLL(unsigned short const *)
通過將C/C++ - Language - Treat WChart As Built in Type下的 Project Properties 設置為No (/Zc:wchar_t-)解決了這個問題
Microsoft 在此處建議有關此設置的以下內容:
如果 /Zc:wchar_t 打開,wchar_t 是編譯為 C++ 的代碼中內置整數類型的關鍵字。 如果指定了 /Zc:wchar_t-(帶減號),或者在編譯為 C 的代碼中,wchar_t 不是內置類型。 相反,wchar_t 在規范 header stddef.h 中被定義為 unsigned short 的 typedef。 (Microsoft 實現在 stddef.h 和其他標准頭文件中包含的另一個 header 中對其進行了定義。)
我們不推薦 /Zc:wchar_t- 因為 C++ 標准要求 wchar_t 是內置類型。 使用 typedef 版本可能會導致可移植性問題。 如果您從早期版本的 Visual Studio 升級並遇到編譯器錯誤 C2664,因為代碼試圖將 wchar_t 隱式轉換為 unsigned short,我們建議您更改代碼以修復錯誤,而不是設置 /Zc:wchar_t-。
/Zc:wchar_t 選項在 C++ 編譯中默認打開,在 C 編譯中被忽略。 /permissive- 選項不影響 /Zc:wchar_t。
Microsoft 將 wchar_t 實現為兩字節無符號值。 它映射到 Microsoft 特定的本機類型 __wchar_t。 有關 wchar_t 的更多信息,請參閱數據類型范圍和基本類型。
如果您編寫的新代碼必須與仍然使用 wchar_t 的 typedef 版本的舊代碼互操作,您可以為 wchar_t 的 unsigned short 和 __wchar_t 變體提供重載,以便您的代碼可以與使用 /Zc 編譯的代碼鏈接: wchar_t 或沒有它編譯的代碼。 否則,您將必須提供兩種不同的庫版本,一種啟用/Zc:wchar_t 啟用,另一種未啟用/Zc:wchar_t。 即使在這種情況下,我們也建議您使用用於編譯新代碼的相同編譯器來構建舊代碼。 切勿混合使用不同編譯器編譯的二進制文件。
當指定 /Zc:wchar_t 時,定義了 _WCHAR_T_DEFINED 和 _NATIVE_WCHAR_T_DEFINED 符號。 有關詳細信息,請參閱預定義宏。
如果您的代碼使用編譯器 COM 全局函數,因為 /Zc:wchar_t 現在默認打開,我們建議您將對 comsupp.lib 的顯式引用(從注釋編譯指示或命令行上)更改為 comsuppw.lib 或comsuppwd.lib。 (如果必須使用 /Zc:wchar_t- 進行編譯,請使用 comsupp.lib。)如果包含 comdef.h header 文件,則會為您指定正確的庫。 有關編譯器 COM 支持的信息,請參閱編譯器 COM 支持。
編譯 C 代碼時不支持 wchar_t 內置類型。 有關 Visual C++ 的一致性問題的更多信息,請參閱非標准行為。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.