我正在Eclipse中编写一个简单的演示JNI项目,以集成Java和C代码。我已经为Eclipse安装了CDT插件来执行此操作。
使用this project structure,我将HelloJNI java文件放在Eclipse的“(默认包)”中,并且使用makefile生成HelloJNI.h C头文件没有问题。

我的Makefile:

# Define a variable for classpath
CLASS_PATH = ../bin

# Define a virtual path for .class in the bin directory
vpath %.class $(CLASS_PATH)

# $* matches the target filename without the extension
HelloJNI.h : HelloJNI.class
javah -classpath $(CLASS_PATH) HelloJNI


问题是我无法弄清楚如何使它与Hello.com.example等包(而不是默认包)中的HelloJNI.java一起使用。即this structure。当运行相同的make目标时,我得到错误输出:


  make:***没有规则将目标设置为“ HelloJNI.h”所需的目标“ HelloJNI.class”。停止。


我试图将包名称添加到javah命令中:

javah -classpath $(CLASS_PATH) com.example.HelloJNI


...但是得到同样的错误。

我试图将类路径更改为:

CLASS_PATH = ../bin/com/example


...但是出现以下错误:


  制作HelloJNI.h
  
  javah -classpath ../bin/com/example HelloJNI
  
  错误:找不到“ HelloJNI”的类文件。


为了使这项工作有效,我需要对我的makefile做些什么?

最佳答案

javah实用程序希望您为其提供要分析的类的全限定名称,并且希望根据该名称找到相对于类路径的该类。因此,如果类的名称是com.example.HelloJNI,那么您可能会告诉make类似这样的内容:

CLASS_DIR = ../bin

HelloJNI.h : $(CLASS_DIR)/com/example/HelloJNI.class
    javah -force -classpath $(CLASS_DIR) com.example.HelloJNI


您可以根据需要打扮一下。我在自己的Makefile中使用了一些DRYer和更多的自动化功能,但是我试图了解关键点。尤其是:


表达正确的先决条件文件(.class文件,在正确的目录中)。如果您没有正确执行此操作,则最终将导致有时不需要重新构建标头和/或不需要重新构建标头。
-classpath指定一个适当的javah;这遵循用于表达类路径的常规Java规则。
将正确的完全限定的类名指定为javah
使用-force选项,否则javah将拒绝替换已经存在的标头。当您手动调用javah时,该默认行为是合理的,但是当您尝试使用make保持JNI标头为最新时,它将使您感到混乱。当然,因此您不能对这些标头进行手动修改,因为这样的修改很可能被破坏。

09-10 04:00