Метод функции JNI_CreateJavaVM не работает и не может быть отлажен - PullRequest
0 голосов
/ 21 июня 2019

Метод функции JNI_CreateJavaVM не работает и не может быть отлажен.

  • Среда разработки - win10 x64, версия jdk - 1.8

  • Visual Studio 2017 Community Edition Написание проекта на C ++


Я изучаю JNI. Я пытаюсь запустить The Invocation API. Следующий URL является примером официальной документации сайта.
Нажмите здесь !

Я собрал проект и добавил зависимость проекта, содержащую jvm.lib. И я положил jvm.dll в каталог проекта. Я успешно запустил эту программу.

Main.test() - это метод печати hello world. Но программа завершается при выполнении JNI_CreateJavaVM, консоль показывает, что возвращаемое значение равно 1.

Я не могу заняться отладкой, я не знаю, что случилось.

#include <jni.h>


int main() {
    printf("begin..........\n");
    JavaVM *jvm;       /* denotes a Java VM */
    JNIEnv *env;       /* pointer to native method interface */
    JavaVMInitArgs vm_args; /* JDK/JRE 6 VM initialization arguments */
    JavaVMOption* options = new JavaVMOption[1];
    char optionString[] = "-Djava.class.path =D:/Program Files/Java/jdk1.8.0_191/lib/";
    options[0].optionString = optionString;
    vm_args.version = JNI_VERSION_1_8;
    vm_args.nOptions = 1;
    vm_args.options = options;
    vm_args.ignoreUnrecognized = false;
    /* load and initialize a Java VM, return a JNI interface
     * pointer in env */

    int res = JNI_CreateJavaVM(&jvm, (void**)&env, &vm_args);
    printf("result=%d", res);
    delete options;
    /* invoke the Main.test method using the JNI */
    jclass cls = env->FindClass("Main");
    jmethodID mid = env->GetStaticMethodID(cls, "test", "(I)V");
    env->CallStaticVoidMethod(cls, mid, 100);
    /* We are done. */
    jvm->DestroyJavaVM();
    return 0;
}

Я ожидаю, что этот jvm может быть вызван, но он принудительно завершается, когда программа выполняется для `int res = JNI_CreateJavaVM (& jvm, (void **) & env, & vm_args); Где я не прав? Почему не работает?

Выход из экрана введите описание изображения здесь

jvm.dll расположение введите описание изображения здесь

jvm.lib linker каталоги дополнительных библиотек введите описание изображения здесь

Дополнительные зависимости компоновщика jvm.lib введите описание изображения здесь

1 Ответ

2 голосов
/ 22 июня 2019

Classpath

Между клавишей и знаком равенства есть пробел.Пробел должен быть удален.

char optionString[] = "-Djava.class.path =D:/Program Files/Java/jdk1.8.0_191/lib/";

Значение Classpath

Значение java.class.path должно указывать на базовый каталог, где находятся ваши скомпилированные файлы .class.

Похоже, вы не используете имя пакета, тогда это каталог, в котором находится Main.class, поэтому, вероятно, он должен выглядеть примерно так:

char optionString[] = "-Djava.class.path=c:/Users/name/MyJavaPrograms/classes";

Нарушение прав доступа

SEGV (или исключение 0xC0000005) также преднамеренно генерируется при запуске JVM для проверки определенных функций ЦП / ОС.

см. Этот точный ответ:https://stackoverflow.com/a/36258856

В Visual Studio, когда отображается диалоговое окно исключения, просто отключите его, чтобы оно там сломалось.Это не даст вам увидеть его снова при следующем запуске программы.

Java

Просто для полноты: метод Java должен выглядеть следующим образом:

public class Main {

public static void test(int num) {
    System.out.println("Java: test called with '" + num + "'");
}

...

Конфигурация Visual Studio

Необходимо найти файл jvm.dll.В Visual Studio в разделе Свойства конфигурации / Отладка / Среда добавьте PATH =% PATH%;\ bin \ server

Для последующего развертывания вы можете подумать о том, чтобы поместить всю JRE в подпапку вашего приложения и указать на нее относительный путь.

Демо

Наконец короткое демо (здесь добавлено \ n printf("result=%d\n", res);, чтобы иметь отдельную строку):

Demo

...