动态 dll 加载和 googletest

Dynamic dll load and googletest

我有几个基于 MFC 的项目 (DLL)。我想在里面添加一些 GTest/GMock 测试。

我需要以最小的努力完成它,所以我的计划是:

  1. 将测试文件添加到每个库并 link 它针对 gmock.lib
  2. 准备一个单独的可执行文件,它会像这样用最少的 main() 动态加载所需的 dll:

    int main(int argc, char** argv)
    { 
        LoadLibrary(argv[1]);
        testing::InitGoogleMock(&argc, argv);
    
        const int status = RUN_ALL_TESTS();
    
        return status;
    }
    

问题是来自已加载库的测试对我的 exe 文件不可见(dll 确实已加载和初始化)。输出为:

[==========] Running 0 tests from 0 test cases.
[==========] 0 tests from 0 test cases ran. (0 ms total)
[  PASSED  ] 0 tests.

看来我应该以某种方式将测试从 dll 文件引入到 exe 中,但我找不到任何信息。 我的方法可以吗?或者也许还有其他简单的方法?

将要执行的测试在编译时确定。您正在做的只是在 运行 时间使用显式 DLL 加载(函数 LoadLibrary)将 DLL 加载到进程地址 space。

首先,我建议您根本不要向您的 DLL 项目添加测试。单元测试代码无需位于将部署给最终用户的 DLL 中。另一个问题是,当您使用显式 DLL 加载时,您必须从 DLL 中显式检索函数地址并使用它来调用函数:

https://msdn.microsoft.com/en-us/library/784bt7z7.aspx

这不适合你想要的。你应该做的是:

  1. 将测试(使用来自所有所需 DLL 的函数)添加到将构建可执行文件的项目,该可执行文件将 运行 来自所有 DLL 的单元测试。
  2. 添加函数的头文件路径和 classes(来自所有需要的 DLL)作为构建此可执行文件的项目的附加包含目录。
  3. Link 这个可执行文件到 gmock.lib
  4. 使用 dllimport 存储 class 属性设置隐式 DLL 加载,因此您不必编写代码来显式获取 DLL 中将在单元测试中使用的函数地址。

有关隐式 DLL 加载的详细信息,请参阅:

https://msdn.microsoft.com/en-us/library/d14wsce5.aspx

编辑:

由于切换到隐式链接不适合您,因此请修改您的方法:

首先,向每个 DLL 添加一个额外的导出函数,运行s 单元测试:

void runTests(int argc, char *argv[])
{
    testing::InitGoogleMock(&argc, argv);
    const int status = RUN_ALL_TESTS();
}

然后,在可执行文件的主函数中,遍历所有 DLL 并使用以下代码为每个 DLL 执行导出的函数:

HMODULE hDLL = LoadLibraryA("MyDLL");
if(hDLL != NULL)
{
    fpRunTests runTestsFun = (fpRunTests)GetProcAddress(hDLL, "runTests");
    if(!runTestsFun)
    {
        // Handle the error
        FreeLibrary(hDLL);
    }
    else
    {
        // Call the function which runs tests
        runTestsFun(argc, argv);
    }
}