Java不会从使用swig创建的.dll中调用函数

时间:2014-12-23 22:16:30

标签: java c++ swig

我使用swig和cmake为学习目的创建了java的动态库。我无法从我创建的同一个库中调用java中的函数。 swig doc告诉我这是伪造编译并将swig包装器文件链接到我的本机库的结果,但我非常确定我是用cmake build做的。

CMakeList.txt

cmake_minimum_required (VERSION 2.6)

FIND_PACKAGE(SWIG REQUIRED)
find_package(Java REQUIRED COMPONENTS Runtime Development)
find_package(JNI REQUIRED)
INCLUDE(${SWIG_USE_FILE})
set(JAVA ${java_include_path} )
INCLUDE_DIRECTORIES(${JAVA} ${JAVA}/win32)
INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR})
SET_SOURCE_FILES_PROPERTIES(hello.i PROPERTIES CPLUSPLUS ON)
SET_SOURCE_FILES_PROPERTIES(hello.i PROPERTIES SWIG_FLAGS "-includeall")
SWIG_ADD_MODULE(hello java hello.i  hello.cpp)
SWIG_LINK_LIBRARIES(hello ${Java_LIBRARIES} ${JNI_LIBRARIES} ${CMAKE_CURRENT_SOURCE_DIR})

HELLO.CPP

#include "hello.hpp"

int adding(const int x, const int y)
{

  return y + x;
}

hello.hpp

int adding(const int x, const int y);

hello.i

 %module hello
 %{
   #include "hello.hpp"
 %}
int adding(const int x, const int y);

有人能告诉我在创建动态库时我做错了什么吗?感谢您的帮助。

我之所以知道这是因为eclipse中的错误消息

Exception in thread "main" java.lang.UnsatisfiedLinkError: hello.helloJNI.adding(II)I
    at hello.helloJNI.adding(Native Method)
    at hello.hello.adding(hello.java:14)
    at hello.Main.main(Main.java:14)

这与文档谈论的错误消息相同。

1 个答案:

答案 0 :(得分:1)

错误消息中缺少的符号是JNI包装器的一部分,而不是库本身的一部分。

通常这意味着在第一次调用之前,您没有为SWIG模块的本机部分调用System.loadLibrary()。您的CMake文件看起来已经正确地链接了实现,因此它不是您从文档中引用的错误情况。

以及手动调用:

System.loadLibrary("hello"); // The name of your DLL here

来自您的main方法我希望在我定位Java时在SWIG界面文件中使用以下内容:

%pragma(java) jniclasscode=%{
  static {
    try {
        System.loadLibrary("hello"); // The name of your DLL here
    } catch (UnsatisfiedLinkError e) {
      System.err.println("Native code library failed to load. \n" + e);
      System.exit(1);
    }
  }
%}

这会导致本机库在需要之前自动加载,这对Java程序员来说似乎是最自然的。