VS2008 LIB的升級改造

今天用VS2019編譯一個在VS2008下Coding的工程的時候,VS給出了一堆鏈接錯誤信息,如下圖所示的一些錯誤:

 

Error 47 error LNK2019: unresolved external symbol "public: __thiscall std::_Mutex::~_Mutex(void)" (??1_Mutex@std@@QAE@XZ) referenced in function "public: void __thiscall std::ios_base::clear(int,bool)" (?clear@ios_base@std@@QAEXH_N@Z) D:\server\mysqlpp.lib(dbdriver.obj) server

Error 48 error LNK2001: unresolved external symbol "public: __thiscall std::_Mutex::~_Mutex(void)" (??1_Mutex@std@@QAE@XZ) D:\server\mysqlpp.lib(datetime.obj) server

Error 49 error LNK2001: unresolved external symbol "public: __thiscall std::_Mutex::~_Mutex(void)" (??1_Mutex@std@@QAE@XZ) D:\server\mysqlpp.lib(stadapter.obj) server

Error 50 error LNK2001: unresolved external symbol "public: __thiscall std::_Mutex::~_Mutex(void)" (??1_Mutex@std@@QAE@XZ) D:\server\mysqlpp.lib(sqlstream.obj) server

Error 51 error LNK2001: unresolved external symbol "public: __thiscall std::_Mutex::~_Mutex(void)" (??1_Mutex@std@@QAE@XZ) D:\server\mysqlpp.lib(connection.obj) server

Error 52 error LNK2001: unresolved external symbol "public: __thiscall std::_Mutex::~_Mutex(void)" (??1_Mutex@std@@QAE@XZ) D:\server\mysqlpp.lib(mystring.obj) server

Error 53 error LNK2001: unresolved external symbol "public: __thiscall std::_Mutex::~_Mutex(void)" (??1_Mutex@std@@QAE@XZ) D:\server\mysqlpp.lib(row.obj) server

Error 54 error LNK2001: unresolved external symbol "public: __thiscall std::_Mutex::~_Mutex(void)" (??1_Mutex@std@@QAE@XZ) D:\server\mysqlpp.lib(query.obj) server

Error 55 error LNK2001: unresolved external symbol "long const std::_BADOFF" (?_BADOFF@std@@3JB) D:\server\mysqlpp.lib(dbdriver.obj) server

Error 56 error LNK2001: unresolved external symbol "long const std::_BADOFF" (?_BADOFF@std@@3JB) D:\server\mysqlpp.lib(datetime.obj) server

Error 57 error LNK2001: unresolved external symbol "long const std::_BADOFF" (?_BADOFF@std@@3JB) D:\server\mysqlpp.lib(stadapter.obj) server

Error 58 error LNK2001: unresolved external symbol "long const std::_BADOFF" (?_BADOFF@std@@3JB) D:\server\mysqlpp.lib(sqlstream.obj) server

Error 59 error LNK2001: unresolved external symbol "long const std::_BADOFF" (?_BADOFF@std@@3JB) D:\server\mysqlpp.lib(connection.obj) server

Error 60 error LNK2001: unresolved external symbol "long const std::_BADOFF" (?_BADOFF@std@@3JB) D:\server\mysqlpp.lib(mystring.obj) server

Error 61 error LNK2001: unresolved external symbol "long const std::_BADOFF" (?_BADOFF@std@@3JB) D:\server\mysqlpp.lib(row.obj) server

Error 62 error LNK2001: unresolved external symbol "long const std::_BADOFF" (?_BADOFF@std@@3JB) D:\server\mysqlpp.lib(query.obj) server

Error 63 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(qparms.obj) server

Error 64 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(sqlstream.obj) server

Error 65 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(options.obj) server

Error 66 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(field_types.obj) server

Error 67 error LNK2019: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) referenced in function "public: char __thiscall mysqlpp::SQLTypeAdapter::at(unsigned int)const " (?at@SQLTypeAdapter@mysqlpp@@QBEDI@Z) D:\server\mysqlpp.lib(stadapter.obj) server

Error 68 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(manip.obj) server

Error 69 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(null.obj) server

Error 70 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(datetime.obj) server

Error 71 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(type_info.obj) server

Error 72 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(vallist.obj) server

Error 73 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(field_names.obj) server

Error 74 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(query.obj) server

Error 75 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(dbdriver.obj) server

Error 76 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xran(void)" (?_Xran@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(tcp_connection.obj) server

Error 82 error LNK2001: unresolved external symbol "public: static void __cdecl std::_String_base::_Xlen(void)" (?_Xlen@_String_base@std@@SAXXZ) D:\server\mysqlpp.lib(null.obj) server

 

 

問題總結:

       因爲靜態鏈接庫mysqlpp.lib在舊版本IDE上編譯的,所以string類中符號被解析成形如 static void __cdecl _Xran()或static void __cdecl _Xlen() 

       而在高版本的VS2019上string中的_Xran與_Xlen符號則被解析成了__declspec(noreturn) void _Xran() const或__declspec(noreturn) void _Xlen() const

       所以纔會在鏈接過程中出現上述開頭出現的一堆問題

#include <string>

namespace std2008

{

class _String_base_2008

{

public:

{

__declspec(dllexport) void _Xlen2008(void) const;

__declspec(dllexport) void _Xran2008(void) const;

};

};

void std2008::_String_base_2008::_Xran2008 () const

{

std::_String_base::_Xran ();

}

void std2008::_String_base_2008::_Xlen2008 () const

{

std::_String_base::_Xlen ();

}

Save this code as "compat.cpp" and compile with

cl /D_DLL_EXPORT /EHsc /LD compat.cpp /link

Now lets examine the lib file, that has been created:

dumpbin /exports compat.lib

In my case it looks like this:

Dump of file compat.lib

File Type: LIBRARY

Exports

ordinal name

?_Xlen2008@_String_base_2008@std2008@@QBEXXZ (public: void __thiscall std2008::_String_base_2008::_Xlen2008(void)const )

?_Xran2008@_String_base_2008@std2008@@QBEXXZ (public: void __thiscall std2008::_String_base_2008::_Xran2008(void)const )

When looking at the linker errors about missing symbols, you see the decoration that is required. In your case its "?_Xran@_String_base@std@@SAXXZ" and "?_Xlen@_String_base@std@@SAXXZ"

The last step is to tell the linker to create a library that maps the standard decorated names to a another name using the symbols from your linker error and the names taken from dumpbin.

Cl /EHsc /LD compat.cpp /link /export:?_Xran@_String_base@std@@SAXXZ=?_Xran2008@_String_base_2008@std2008@@QBEXXZ /export:?_Xlen@_String_base@std@@SAXXZ=?_Xlen2008@_String_base_2008@std2008@@QBEXXZ

Cl /EHsc /LD compat1.cpp /link /export:??0exception@std@@QAE@ABQBD@Z=??exception_2008@std2008@@QAEXABQBD@Z

Now add the "compat.lib" library as additional library to your project and now it should link successfully.

Compact.c代碼

#include <string>

namespace std2008

{

class _String_base_2008

{

public:

__declspec(dllexport) void _Xlen2008(void) const;

__declspec(dllexport) void _Xran2008(void) const;

};

};

void std2008::_String_base_2008::_Xran2008 () const

{

std::_String_base::_Xran ();

}

void std2008::_String_base_2008::_Xlen2008 () const

{

std::_String_base::_Xlen ();

}

生成DLL和LIB

cl /D_DLL_EXPORT /EHsc /LD compat.cpp /link

生成可用的LIB

Cl /EHsc /LD compat.cpp /link /export:?_Xran@_String_base@std@@SAXXZ=?_Xran2008@_String_base_2008@std2008@@QBEXXZ /export:?_Xlen@_String_base@std@@SAXXZ=?_Xlen2008@_String_base_2008@std2008@@QBEXXZ

 

Compact1.c代碼

#include <string>

namespace std2008

{

class exception_2008

{

public:

__declspec(dllexport) exception_2008(char const * const & ch);

};

};

std2008::exception_2008::exception_2008(char const * const & ch)

{

std::exception::exception (ch);

}

生成DLL和LIB

cl /D_DLL_EXPORT /EHsc /LD compat1.cpp /link

生成可用的LIB

Cl /EHsc /LD compat1.cpp /link /export:??0

exception@std@@QAE@ABQBD@Z=??exception_2008@std2008@@QAEXABQBD@Z

 

將生成的compat.dll和compat1.dll拷貝至EXE目錄,compat.lib和compat1.lib則拷貝至源文件與mysqlpp.lib同一目錄中,即可順利編譯了!!

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章