构建依赖于其他两个DLL的DLL的错误

时间:2013-01-15 22:26:15

标签: windows visual-c++ dll java-native-interface

背景

我正在尝试构建一个通过JNI使用现有本机库的Java程序。本机项目有两个组件,每个组件都构建一个共享库:

  1. 构建core.libcore.dll
  2. 的核心组件
  3. 依赖于核心组件的应用程序组件,并构建application.libapplication.dll
  4. 使用SWIG,我创建了一个application_wrap.c文件和相应的Java文件,以便我可以使用JNI访问本机库。

    我想要做的是构建一个包含此application_jni.dll文件的新共享库(让我们称之为application_wrap.c),以便我可以在我的Java程序中加载它:

    System.loadLibrary("application_jni");
    

    问题

    不幸的是,我似乎无法弄清楚如何在Windows上使用Visual Studio编译器执行此操作。这是我尝试过的:

    首先,编译SWIG生成的application_wrap.c文件。这会产生application_wrap.obj,似乎工作正常。

    cl /I "path/to/core/headers" /I "path/to/application/headers" -c application_wrap.c
    

    接下来,将application_wrap.obj与现有共享库链接以创建新的共享库:

    link /dll /out:application_jni.dll application_wrap.obj core.lib application.lib
    

    这会导致大量错误,如下所示:

    application_wrap.obj : error LNK2019: unresolved external symbol __imp__function_in_core referenced in function_in_application_wrap
    

    知道可能导致这些错误的原因是什么?我没有很多在Windows上编译的经验,所以如果发现我在编译或链接阶段遗漏了一些标志(甚至误解了dll的工作方式),我也不会感到惊讶。

    一些额外的笔记

    运行

    dumpbin /exports core.lib
    

    表明错误消息提到的所有函数实际上都是由核心共享库导出的。

    修改

    在Pavel的建议中,我写了一个简单的C程序,看看它是否会链接。我使用了与上面相同的编译和链接命令,并遇到了同样的错误。

    C程序test.c

    #include "application.h"
    
    int main() {
      function_in_application();
    }
    

    错误:

    test.obj : error LNK2019: unresolved external symbol __imp__function_in_application referenced in function _main
    

1 个答案:

答案 0 :(得分:1)

库无法链接,因为core.dllapplication.dll编译为64位,cl.exe的默认目标是32位。链接器失败,因为我试图将32位obj文件链接到两个64位dll's。编译64位的所有内容解决了这个问题。

一些需要注意的事情

  • 如果安装了64位编译器,则通过运行带有与目标平台相对应的参数的cl.exe脚本(例如“amd64”),使vcvarsall.bat目标位为64位。可以找到更深入的说明here
  • 默认情况下,Visual Studio Express 2010的默认版本不会安装64位编译器。您可能需要再次运行setup.exe并检查相应的自定义安装选项以进行安装。
  • Visual Studio Express 2012的默认版本附带64位编译器。我卸载了2010版本,安装了2012版本,之后没有任何问题。