2011-07-27 8 views
5

Estoy en proceso de hacer Java < -> .NET código de interoperabilidad usando una biblioteca nativa entre ellos, hasta ahora las cosas van bastante bien.Java JNIEnv Segmentation Fault

Sin embargo, por alguna razón no puedo ejecutar ningún método en JNIEnv.

System::String^ JNIStringToNet(JNIEnv * env, jstring js) 
{ 
    const char *buf = env->GetStringUTFChars(js, 0); // segfault 

Ahora puede pasar variables de ida y vuelta y hacer todos los otros tipos de comunicación, así que estoy pensando que no he inicializado correctamente este o algo así.

Estoy cargando así:

this.Lib = (LibHandler)Native.loadLibrary(this.Name, LibHandler.class);  

(prefiero Native.loadLibrary porque parece que me permite hacer más con que sea más fácil, como el uso compartido de clases entre varias bibliotecas y desenganche y que rehooking de la JVM sobre la marcha).

Editar:

serio cualquier método:

std::cout << "Getting version:" << std::endl; 
std::cout << env->GetVersion() << std::endl; 

Conseguir versión:

(violación de segmento)

Ideas en WHT JNIEnv sería violación de segmento para cada método? Esto debería ser configurado por la JVM, ¿correcto?

Edición 2:

Esta es una aplicación Java que está llamando una biblioteca de C++ que estará en comunicación con una biblioteca .NET (lo que es una CLR compilado biblioteca de C++, si hay alguna diferencia), para limitar cualquier factor externo. Ni siquiera estoy llamando a la DLL .NET pero solo estoy convirtiendo cadenas que vienen hacia atrás (o bueno ... intentando).

Así por ejemplo de Java:

this.Lib = (LibHandler)Native.loadLibrary(this.Name, LibHandler.class); 
this.Lib.myCPPMethod(); // Segmentation fault during this call, JVM crashes. 

curioso si era el CLR que estaba causando: compilación CLR personas de movilidad reducida y se destiló todo lo que estaba relacionado CLR, todavía lo hace.

Datos 3:

GOT IT para volcar:

# 
# A fatal error has been detected by the Java Runtime Environment: 
# 
# EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x0000000000000000, pid=1596, tid=7248 
# 
# JRE version: 6.0_23-b05 
# Java VM: Java HotSpot(TM) 64-Bit Server VM (19.0-b09 mixed mode windows-amd64 compressed oops) 
# Problematic frame: 
# C 0x0000000000000000 

Así que sí, parece que la JVM no me está dando acceso a la memoria por alguna razón.

Editar 4:

llamada real:

JNIEXPORT jstring JNICALL Query(JNIEnv * env, jobject jobj, jstring start, jstring end) 
{ 
    std::cout << "Getting version:" << std::endl; 
    jint j = env->GetVersion(); 
    return jstring("test"); 
} 

Editar 5:

funciona con el sistema.loadLibrary:

JNIEXPORT void JNICALL Java_LibTest_T(JNIEnv *env, jobject jobj) 
{ 
    std::cout << "Getting version:" << std::endl; 
    jint j = env->GetVersion(); 
    std::cout << j << std::endl; 
} 

Salida:

java -Djava.library.path="(dir)\lib\64" EntryPoint 
Getting version: 
65542 

Ack! Me refiero a algunos avances, pero no puedo descargar bibliotecas de la JVM que están cargadas en System.loadLibrary ¿o sí?

Básicamente necesito poder desconectar estas bibliotecas de la JVM y cambiarlas, además de eso, todas deben "compartir" una sola clase y poder unirse a la clase en tiempo de ejecución ... que es un poco por qué fui con Native.loadLibrary.

Actualmente Puedo hacer esto:

carga el archivo DLL:

this.Lib = (LibHandler)Native.loadLibrary(this.Name, LibHandler.class); 

desengancharlo:

this.Lib = null; 
Runtime.getRuntime().gc(); // Force the JVM to drop it immediately. 

Clase I se carga a todos en:

public interface LibHandler extends Library{ 
    void T(); 
} 

cualquier manera para trabajar de manera similar con System.lo adLibrary?

Editar 6:

dude en llamarme tonto, estoy usando JNA, NO JNI, que es completamente diferente y una enorme fuente de mis problemas .... hay una manera hacer esto con JNI? ¿O puedo hacer que JNIEnv se registre con JNA de alguna manera? Supongo que puedo descartar JNI de la biblioteca de C++ y usar Wstrings directamente.

Voy a volver con esto mañana.

+0

¿Puede dar un poco más ¿detalle? ¿Es este java llamando al código .Net a través de una biblioteca nativa, o .NET llamando a Java a través de una biblioteca nativa? –

+0

¿Está tratando de llamar a la JVM desde .Net o viceversa? Si es el primero, debe usar la API de invocación (busque en Google). Específicamente, debe llamar a JNI_CreateJavaVM –

+0

Disculpe por eso, edite 2 direcciones que ahora. :) Es una llamada de Java a una DLL de C++. – StrangeWill

Respuesta

0

Bueno, me siento mal.

Native.loadLibrary == JNA.

System.loadLibrary == JNI.

El propósito de JNA es que no requiere ningún conocimiento real del entorno de JVM, para que pueda ejecutar las bibliotecas nativas como es, así que en vez de jstring puede utilizar char * ...

Cuestiones relacionadas