Comment passer C les structures d'avant en arrière pour le code Java dans JNI?

J'ai quelques fonctions C qui je suis en appel par JNI qui prennent un pointeur sur une structure, et quelques autres fonctions qui allouera/libérer un pointeur vers le même type de structure, de sorte qu'il est un peu plus facile à traiter avec mon wrapper. Étonnamment, la JNI documentation dit très peu de choses sur la façon de traiter avec les structures C.

Mon C fichier d'en-tête ressemble à ceci:

typedef struct _MyStruct {
  float member;
} MyStruct;

MyStruct* createNewMyStruct();
void processData(int *data, int numObjects, MyStruct *arguments);

Le correspondant JNI C wrapper fichier contient:

JNIEXPORT jobject JNICALL
Java_com_myorg_MyJavaClass_createNewMyStruct(JNIEnv *env, jobject this) {
  return createNewMyStruct();
}

JNIEXPORT void JNICALL
Java_com_myorg_MyJavaClass_processData(JNIEnv *env, jobject this, jintArray data,
                                       jint numObjects, jobject arguments) {
  int *actualData = (*env)->GetIntArrayElements(env, data, NULL);
  processData(actualData, numObjects, arguments);
  (*env)->ReleaseIntArrayElements(env, data, actualData, NULL);
}

...et enfin, la classe Java correspondante:

public class MyJavaClass {
  static { System.loadLibrary("MyJniLibrary"); }

  private native MyStruct createNewMyStruct();
  private native void processData(int[] data, int numObjects, MyStruct arguments);

  private class MyStruct {
    float member;
  }

  public void test() {
    MyStruct foo = createNewMyStruct();
    foo.member = 3.14159f;
    int[] testData = new int[10];
    processData(testData, 10, foo);
  }
}

Malheureusement, ce code d'accidents de la JVM juste après frapper createNewMyStruct(). Je suis un peu nouveau pour JNI et n'ont aucune idée de ce que le problème pourrait être.

Modifier: je tiens à noter que le code C est très vanille C, est bien testé et a été porté à partir d'un iPhone de projet. Aussi, ce projet est à l'aide de l'Android NDK cadre, ce qui vous permet d'exécuter le code C code à partir d'un projet Android à partir de l'intérieur de JNI. Cependant, je ne pense pas que c'est strictement un NDK question... il semble qu'un JNI programme d'installation/de l'initialisation erreur de ma part.

  • Quelque chose de plus précis à propos de l'erreur? Un message d'erreur?
  • Nope, c'est juste accidents de la JRE. C'est un écueil à propos des relations avec JNI...
  • Le CheckJNI fonctionnalité a été ajoutée pour trouver le code commun des erreurs avant qu'ils ne deviennent Heisenbugs. Il est activé par défaut dans l'émulateur. Voir la jni-conseils et incorporé-vm-contrôle docs android.git.kernel.org/?p=platform/... pour plus d'informations sur l'activation sur un appareil.
  • Jetez un oeil à la JNA (et voir aussi l'article).
  • Vous pouvez également passer nio.DirectByteBuffers par JNI et d'analyser la mémoire sur l'île de Java, en utilisant par exemple github.com/marc-christian-schulze/structs4java
InformationsquelleAutor Nik Reiman | 2010-10-13