【问题标题】:LNK2001 unresolved external symbol for SHA3 class membersSHA3​​ 类成员的 LNK2001 未解析的外部符号
【发布时间】:2018-06-01 12:08:05
【问题描述】:

我需要在我的程序中计算 SHA3 并在我的套接字中使用 AES,并决定使用 crypto++ 库。

我是 Visual Studio 环境的新手,之前没有在 Visual Studio 方面的经验,但我在 g++ (linux/mingw-w64) 上有过广泛的工作。我正在使用的第三方库之一推荐使用 Visual Studios(与 g++ 一起使用时会导致链接器错误)。

我收到链接器错误。 错误:

LNK2001 unresolved external symbol "public: virtual void __cdecl CryptoPP::SHA3::Update(unsigned char const *,unsigned __int64)" (?Update@SHA3@CryptoPP@@UEAAXPEBE_K@Z) ConsoleApplication2 C:\Users\Admin\source\repos\ConsoleApplication2\ConsoleApplication2\ConsoleApplication2.obj 1   

LNK2019 unresolved external symbol "public: virtual void __cdecl CryptoPP::SHA3::Restart(void)" (?Restart@SHA3@CryptoPP@@UEAAXXZ) referenced in function "public: __cdecl CryptoPP::SHA3::SHA3(unsigned int)" (??0SHA3@CryptoPP@@QEAA@I@Z)  ConsoleApplication2 C:\Users\Admin\source\repos\ConsoleApplication2\ConsoleApplication2\ConsoleApplication2.obj 1   

Error   LNK2001 unresolved external symbol "public: virtual void __cdecl CryptoPP::SHA3::TruncatedFinal(unsigned char *,unsigned __int64)" (?TruncatedFinal@SHA3@CryptoPP@@UEAAXPEAE_K@Z)   ConsoleApplication2 C:\Users\Admin\source\repos\ConsoleApplication2\ConsoleApplication2\ConsoleApplication2.obj 1

相同的代码在 g++ 中正常工作(mingw-w64 - 我正在使用在 mingw-w64 中创建的 dll)

操作系统:Windows 10 Pro 64 位

开发环境:Visual Studios 2017

目标:调试 x64

来源:

#include <sha3.h>
#include <filters.h>
#include <hex.h>
#include <string>
#include <iostream>
#include <vector>
#include <algorithm>
#include <iostream>
#include <base64.h>

int main()
{
    CryptoPP::SHA3_512 hash;

    std::cout << hash.AlgorithmName() << " Test." << std::endl;

    std::string in = "The quick brown fox jumps over the lazy dog";
    std::vector<CryptoPP::byte> out(hash.DigestSize());

    hash.CalculateTruncatedDigest(&out[0], hash.DigestSize(), reinterpret_cast<CryptoPP::byte*>(&in[0]), in.size());

    std::cout << in << std::endl;

    std::cout.setf(std::ios::hex, std::ios::basefield);

    for_each(out.begin(), out.end(), [](CryptoPP::byte i) {
        printf("%x", i);
    });

    std::cout << "Original String : " << str << std::endl;
    return 0;
}

请告诉我如何在某个公共文件夹中加载(复制)所有生成的 dll,就像 gcc 中的 make install 命令(工具)一样。

编辑:

我在附加依赖项中添加了 cryptopp.lib,并在附加库目录中添加了包含 cryptopp.lib 和 cryptopp.dll 的文件夹。我在 Path 环境变量中添加了目录。我在cryptolib项目中生成dll期间在Debug x64配置中选择了多线程调试Dll。

【问题讨论】:

  • 您需要有 .lib 和 .dll 文件。转到您的项目-> 右键单击​​属性-> 在链接部分下选择输入-> 在此处提及您要使用的所有 .lib dll。然后提供 dll 的路径,您将它们放在 Linker->Genera-> 附加包含目录中
  • @StraightCirle,这样做仍然没有成功。对不起,我应该在我的原始帖子中提到。
  • 另见 Crypto++ wiki 上的 FIPS DLL。旧的/过时的 FIPS DLL 不包括 SHA3,因为 SHA3 早于最后一次 FIPS 验证。您可能希望避免使用 FIPS DLL,而只使用静态库。静态库称为cryptlib.lib。 wiki 上另一个感兴趣的页面是Visual Studio

标签: c++ visual-studio crypto++


【解决方案1】:

Paul Sanders 说的很对,你想从 crypto++ DLL 中使用的类和函数必须用 _declspec(dllexport) / _declspec(dllimport) 限定。

其中一些已经完成,如Crypto++ wiki page for Fips dll 中所述。它通过预处理器宏CRYPTOPP_DLL 工作,该宏在crypto++ 标头config.h 中定义并在fips140.h 中使用。

但有一个问题 - 并非您想要的所有算法都在 FIPS 中,并且正如您所发现的,它们不会导出以在 DLL 中使用。您可以修改其他标头以添加 DLL 导出/导入,但请注意 wiki 页面建议:“如果您确实需要 DLL,则提供链接到静态库的包装 DLL。”。与其包装您使用的每个 crypto++ 算法的每个组件,不如将整个操作封装到一个高级类或函数中,然后从您的包装 DLL 导出/导入它会更方便。

GCC 默认导出所有内容,这就是共享库在 Linux 上为您工作的原因。

【讨论】:

    【解决方案2】:

    您需要将您的应用与(我相信)cryptopp.lib 相关联。这可能有 32 位和 64 位的不同版本(我相信导入表中的名称不同),因此请确保使用正确的版本。

    您可以通过解决方案资源管理器告诉 Visual Studio 执行此操作 -> 右键单击​​项目名称 -> 属性 -> 链接器 -> 输入 -> 附加依赖项。然后重新构建。

    您的应用需要能够在运行时找到 DLL,而不是在链接时。如果不能,当您尝试运行它时,您将收到一条错误消息告诉您。将 DLL 复制到与可执行文件相同的目录是人们通常会做的事情(我希望在 Visual Studio 中使用 mingw 创建的 DLL 没有问题)。

    【讨论】:

    • 我在附加依赖项“cryptopp.lib”中添加了 .lib。我在 cryptolib 项目的 dll 生成期间在 Debug x64 configuration 中选择了 Multi Threaded Debug Dll。
    • 成功了吗?我在猜测 .lib 文件的名称,如果它作为包的一部分到达,我不知道你会在磁盘上的什么位置找到它。如果您有有用的附加信息,您可以编辑我的帖子。 OTOH,如果您自己构建 cryptolib DLL,那么您应该确保 Properties -> C++ -> Code Generation -> Runtime Library 与您的应用程序匹配(您当然会知道在哪里可以找到 .lib)。
    • 它没有用。 cryptopp.lib 和 cryptopp.dll 是我在 Visual Studios 2017 中的 Debug x64 配置和运行时库设置为多线程调试 DLL (/MDd) 下构建 cryptopp 后生成的。我正在同一运行时库模型下按应用程序构建。我在其他库中指定了 cryptopp.lib 并添加了必要的路径。
    • 同样的错误信息?将crypto++ 构建为静态库可能更容易,它实际上并不需要是 DLL。不过,您需要创建一个新的项目文件(我的意思是构建静态库)。你现在用的那个是哪里来的?它是随包装提供的吗?
    • 这个项目的系统架构要求我使用共享库。使用 g++(mingw-w64) 时,我已将系统部署为 libcryptopp 作为共享库。如果所有其他选项都用尽了,那么我会构建一个静态库,但在那之前我将不得不尝试解决链接器问题。
    猜你喜欢
    • 2020-04-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多