我不确定我是否完全理解了您的设置,以及您是否需要从eclipse完成此操作。无论如何,我有兴趣使用JNI和Cocoa库编写一个小测试程序,仅仅是为了尝试调试obj-c/c代码。
我成功地完成了这个设置,并且也成功地调试了代码。我使用IntelliJ进行Java开发,使用Xcode进行objc/c部分开发,但在eclipse中进行Java部分开发很简单。
因此,您应该能够完全按照我的项目结构进行设置,并开始调试。从那里,您应该能够将这些知识应用到您自己更复杂的代码中。
这就是我开始的方式:
- 通过选择Cocoa Library在Xcode中创建一个新项目。
![Cocoa Library](https://istack.dev59.com/ZiY6S.webp)
- 将项目命名为
libnative
,并将其类型设置为动态。
![Choose Options](https://istack.dev59.com/X2b6W.webp)
![enter image description here](https://istack.dev59.com/rU1oq.webp)
现在是添加代码的时候了。请注意,使用此设置需要使用
<JavaVM/jni.h>
。将
libnative.m
更新为以下代码:
#import "libnative.h"
#include <JavaVM/jni.h>
@implementation libnative
@end
#ifdef __cplusplus
extern "C" {
#endif
#ifndef VEC_LEN
#define VEC_LEN(v) (sizeof(v)/sizeof(v[0]))
#endif
static JavaVM *javaVM;
static void print();
static JNINativeMethod Main_methods[] =
{
{ "print", "()V", (void*)print },
};
static struct {
const char *class_name;
JNINativeMethod *methods;
int num_methods;
} native_methods[] = {
{ "com/stackoverflow/Main", Main_methods, VEC_LEN(Main_methods) },
};
JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *jvm, void *reserved) {
JNIEnv *env = 0;
jclass cls = 0;
jint rs = 0;
if ((*jvm)->GetEnv(jvm, (void**)&env, JNI_VERSION_1_4)) {
return JNI_ERR;
}
javaVM = jvm;
for (unsigned int i = 0; i < VEC_LEN(native_methods); i++) {
cls = (*env)->FindClass(env, native_methods[i].class_name);
if (cls == NULL) {
return JNI_ERR;
}
rs = (*env)->RegisterNatives(env, cls, native_methods[i].methods, native_methods[i].num_methods);
assert(rs == JNI_OK);
}
return JNI_VERSION_1_4;
}
static void print(JNIEnv *env, jclass cls) {
printf("Hello from C");
}
#ifdef __cplusplus
}
#endif
com.stackoverflow.Main.java
package com.stackoverflow;
public class Main {
static native void print();
static {
System.out.println(System.getProperty("java.library.path"));
System.loadLibrary("native");
}
public static void main(String[] args) {
System.out.println("Loading native");
Main.print();
}
}
- 在
Main.print();
前一行设置断点。使用以下JVM选项启动调试器:
-Djava.library.path="/Users/maba/Library/Developer/Xcode/DerivedData/libnative-cquleqohzyhghnercyqdwpnznjdf/Build/Products/Debug/"
这行文字有点长,也是用户特定的。你需要自己查找目录名称,但它们与我的基本相同,除了生成的libnative-cquleqohzyhghnercyqdwpnznjdf
路径。
程序应该正在运行并等待断点。现在是时候将Xcode调试器附加到运行的应用程序上。
选择菜单Product
-> Attach to Process >
并指向下拉列表中System
部分中运行的java
进程。如果有多个java
进程,则最可能是具有最高PID的那个,但不总是。你需要尝试一下。
在C代码中的printf("Hello from C");
行上创建一个断点。
返回Java IDE并继续从停止的地方执行。
返回Xcode并查看它正在等待断点!
![At Breakpoint](https://istack.dev59.com/bYka5.webp)
如我之前所述,这是一种非常简单的处理 obj-c/JNI 的方法,而您的项目可能相当庞大,但通过这个小测试项目,您至少可以看到它是如何工作的,然后继续进行自己的项目设置。