2016-04-15 2 views
3

Ich bin weg von this Beispiel dafür, wie geht ein com.sun.jna.Structure enthält eine com.sun.jna.StringArray von Java in nativen C-Code unter Verwendung von JNA, passieren und Probleme beim erfolgreichen Abrufen der Strukturinhalte im C-Code.Wie ein com.sun.jna.Structure von Java passieren in C auf struct, JNA mit

Beachten Sie, dass ich eine Struktur erfolgreich aus dem C-Code an eine Struktur in Java übergeben kann, aber ich habe Probleme beim Erstellen einer Struktur im Java-Code und erfolgreich senden sie an den C-Code als eine Struktur.

Dies ist der Code in Frage:

String[] user_name_array = new String[3]; 
user_name_array[0] = "test_user_1"; 
user_name_array[1] = "test_user_2"; 
user_name_array[2] = "test_user_3"; 
StringList.ByReference members = new StringList.ByReference(); 
members.length = 3; 
members.strings = new StringArray(user_name_array); 
MyNativeLibrary.myMethod(members); 

einfach genug scheint, aber es funktioniert nicht.

Es wird erfolgreich in den C-Code wie erwartet, aber der Zeiger in der Struktur ist leer, und die Länge ist Null. Hier

ist die Stringstruktur im Java:

public static class StringList extends Structure { 
    public volatile long length; 
    public volatile Pointer strings; 
    public static class ByValue extends StringList implements Structure.ByValue {} 
    public static class ByReference extends StringList implements Structure.ByReference { 
     public ByReference() { } 
     public ByReference(Pointer p) { super(p); read(); } 
    } 
    public StringList() { } 
    public StringList(Pointer p) { super(p); read(); } 
} 

Hier ist die entsprechende Struktur im C-Code:

typedef struct string_list { 
    uint64_t length; 
    const char **strings; 
} string_list; 

Und hier ist die Methodendefinition im C-Code:

Mit ndk-gdb, und in diese Funktion, das ist es, was es ist zeigt:

(gdb) break my_method 
(gdb) cont 
Continuing. 

Breakpoint 1, my_method (members=0x9bee77b0) at ../app/my_code_file.c:368 
(gdb) p *members 
$1 = {length = 0, strings = 0x0} 

Es scheint, wie es funktionieren sollte, also warum sind nicht die Werte, die sie in den C-Code zu machen? Was vermisse ich?

Beachten Sie auch, dass ich erfolgreich einen String direkt mit dem C-Code aus dem Java-Code senden kann, wenn sie nicht innerhalb einer Struktur ist:

Java:

//This works! 
StringList members = MyNativeLib.myTestFunction(3, new StringArray(user_name_array)); 

C:

//This works! 
string_list* my_test_function(uint64_t length, const char **strings) 
{ 
    //...... 
} 

Es scheint, dass JNA in diesem Fall wie erwartet funktioniert. Also, warum funktioniert es nicht mit einer Struktur as the documentation states it should?

+0

Mögliches Duplikat von [übergeben String-Array von Java zu C mit JNI] (http://stackoverflow.com/questions/5972207/passing-string-array-from-java-to-c-with-jni) –

+2

@ DougStevenson Es sieht so aus, als ob es eine Lösung dafür ist, wie man ein StringArray weitergibt, nicht wie man eine Structure mit einem StringArray weitergibt, also kein gutes Dupe-Ziel .... –

+1

Sie werden keine automatische Zuordnung von Java-Strukturen zu C-Strukturen bekommen . Sie müssen die interessierenden Elemente programmgesteuert aus einem übergebenen Objekt mithilfe von JNI extrahieren, wobei String-Arrays die beste Methode zur Verarbeitung darstellen. Es ist irgendwie schmerzhaft. –

Antwort

3

Markieren Sie die Felder nicht als flüchtig. Wenn Sie das tun, schreibt JNA nicht in sie, es sei denn, Sie machen ein explizites Structure.writeField().