JNI "env->GetStaticMethodID()" abgestürztes Programm

Bin ich versucht, rufen Sie eine Java-Funktion von C++.
Das ist mein code bisher:

#include <jni.h>

typedef struct JavaVMCreationResult {
    JavaVM* jvm;
    JNIEnv* env;
} JVMCreationResult;

JVMCreationResult* CreateJavaVM() {
    JavaVM* jvm;
    JNIEnv* env;

    JavaVMInitArgs args;

    JavaVMOption opts[1];
    opts[0].optionString = "-Djava.class.path=C:\\MyJavaClasses";

    args.version = JNI_VERSION_1_6;
    args.nOptions = 1;
    args.options = opts;
    args.ignoreUnrecognized = JNI_TRUE;

    JNI_GetDefaultJavaVMInitArgs(&args);

    JNI_CreateJavaVM(&jvm, (void **) &env, &args);

    JavaVMCreationResult* cres;
    cres->jvm = jvm;
    cres->env = env;

    return cres;
}

int main() {
    JVMCreationResult* cres = CreateJavaVM();
    JavaVM* jvm = cres->jvm;
    JNIEnv* env = cres->env;

    jclass cls = env->FindClass("Main");
    jmethodID mid = env->GetStaticMethodID(cls, "main", "([Ljava/lang/String;)V"); //the evil line
}

Ich bin mit Code::Blocks mit MinGW-GCC auf Windows 7.

Die Letzte Zeile in der main () - Funktion, die das Programm stürzt ab, aber der compiler beschwert sich nicht über alles. (Auskommentieren der jmethodID mid = env->GetSta... Linie macht das Programm nicht "abstürzt")

Ich habe verwendet javap -s Main zu erhalten, die richtige Methode, Signatur, auch die Klasse ist eine gültige Java-Klasse.

Können Sie mir sagen, warum das Programm abstürzt ? In diesem Beispiel wird nur gezeigt, überall im Internet, aber es funktioniert nicht für mich. 🙁

Dies ist die Java-Klasse:

public class Main {
    public static void main(String[] args) {
        System.out.println("This is from Java !");
    }
}

LÖSUNG

Ich würde nicht gedacht haben, es scheint eine Unlogik zu mir, dass das Programm nicht abstürzt, früher, wenn die struct nicht initialisiert. Aber das war wirklich das Problem.

Dies ist die vollständige und funktionierenden code !

#include <jni.h>

#ifndef null
#define null NULL
#endif

typedef struct JavaVMCreationResult {
    JavaVM* jvm;
    JNIEnv* env;
} JVMCreationResult;

JVMCreationResult* CreateJavaVM() {
    JavaVM* jvm;
    JNIEnv* env;

    JavaVMInitArgs args;

    JavaVMOption opts[1];
    opts[0].optionString = "-Djava.class.path=C:\\Users\\Claudia\\Desktop";

    args.version = JNI_VERSION_1_6;
    args.nOptions = 1;
    args.options = opts;
    args.ignoreUnrecognized = JNI_TRUE;

    JNI_GetDefaultJavaVMInitArgs(&args);

    JNI_CreateJavaVM(&jvm, (void **) &env, &args);

    JVMCreationResult* cres = new JVMCreationResult();
    cres->jvm = jvm;
    cres->env = env;

    return cres;
}

int main() {
    JVMCreationResult* cres = CreateJavaVM();
    JavaVM* jvm = cres->jvm;
    JNIEnv* env = cres->env;

    jclass cls = env->FindClass("Main");
    if (cls) {
        printf("Yes !\n");
    }
    else {
        printf("No !\n");
    }
    jmethodID mid = env->GetStaticMethodID(cls, "main", "([Ljava/lang/String;)V");
    env->CallStaticVoidMethod(cls, mid);

    printf("At end of Program.");
}
  • Deine variable "cres" ist ein Punkt in der CreateJavaVM nennen, die noch nie initialisiert, also bist du wahrscheinlich dereferenzieren eines null-oder anderweitig ungültigen Zeiger auf diesen Punkt.
  • Würde das nicht bedeuten sollte das Programm Abstürzen, an der Stelle JavaVM* jvm = cres->jvm; ? Und warum ist es nicht initialisiert ? (Ich bin kein C++ Experte, begann vor einigen Wochen.) Dank
  • Wie Sie wissen, kracht es in der letzten Zeile von main()?
  • Yep, cres ist nicht verweist auf Speicher zugewiesen. Wenn überhaupt sollte es crash auf cres->jvm = jvm eigentlich.
  • Ich weiß es, weil es funktioniert, wenn ich die folgende Zeile auskommentiert werden. Ach so, ich sollte das Schlüsselwort new, verwenden ? (Wie gesagt, ziemlich neu in C++ und Zeiger) Seltsam, wenn dies wirklich das Problem, der compiler gar nicht beklagen, dass "null-pointer".
  • Compiler nicht erkennen kann null-Zeiger, da Sie generiert eine run-time.

InformationsquelleAutor Niklas R | 2011-09-26
Schreibe einen Kommentar