JNI вызывает метод Java из C ++ - PullRequest
       20

JNI вызывает метод Java из C ++

3 голосов
/ 22 октября 2011

У меня проблема с JNI, я вызываю метод из C ++ в Java.

Я пытаюсь вызвать метод void, который принимает логическое значение.Мой Java-код выглядит следующим образом:

public void setStatus(boolean bool) {
    // Do stuff...
}

public native void initialize(int defaultPort);

В моем C ++-коде я создаю структуру, которая содержит env и объект и передает его в поток:

JNIEXPORT void JNICALL Java_com_device_client_HostConnection_initialize
  (JNIEnv * env, jobject obj, jint port)
{
    struct javaInfo* data = (struct javaInfo*) malloc(sizeof(struct javaInfo));
    data->env = env;
    data->javaObjHost = obj;

    pthread_t pth;
    pthread_create(&pth, NULL, startServer, (void *) data);

    free(data);
}

Вфактическая функция, я пытаюсь получить класс, а затем MethodID и затем вызвать метод void, как показано ниже:

void *startServer(void* arg) {
    struct javaInfo* data = (struct javaInfo*) arg; 
    JNIEnv* env = data->env;
    jobject javaObjHost = data->javaObjHost;

    cls = env->GetObjectClass(javaObjHost);
    mid = env->GetMethodID(cls, "setStatus", "(Z)V");
    if (mid == 0) {
        exit(-1);
    }
    env->CallVoidMethod(javaObjHost, mid, true);
}

Мне сложно отлаживать с помощью JNI.Я попытался поместить точку останова в Eclipse в setStatus (), но она никогда не вызывается.exit () также не вызывается.Программы останавливаются на секунду или две, затем продолжаются.Я не уверен, что происходит.

Может ли кто-нибудь помочь мне?

Большое спасибо.

1 Ответ

6 голосов
/ 22 октября 2011

Вы не можете передавать указатели env другим потокам. Вам необходимо присоединиться к потоку в JVM.

В исходном потоке под названием GetJavaVM для получения указателя JavaVM:

JavaVM *vm = 0;
env->GetJavaVM(&vm);

Затем в другом потоке присоедините виртуальную машину к этому потоку и получите новый указатель env:

vm->AttachCurrentThread(&env, 0);
...