Can I call the functions of a C-executable from Java?


I use the JNI to start a Java Application out of C. While this is quickly done as long as I'm using a console Application, whith a Swing-GUI things get a bit tricky.

To keep the application "alive" I use a while loop that just runs as long as GUI is not closed. While this loop runs it always requests, if the application is still running by requesting a boolean value.

    if(JNI_FALSE == env->CallBooleanMethod(obj, boolMethod))
        javaRunning = false;

This value is changed when the Java function WindowClosing(Event) is called to indicate that the user closes the window.

Unfortunately this does not work if I close the window. The C-Application still tries to request the boolean value, even though the window is already closed. It obviously is not able to fetch the boolean before the window closes. A better approach would be to call the C-Code from Java to inform it about the "WindowClosing" event.

Well as far as I can see, this would be possible if the C-Code is loaded by Java (using a DLL) but not via the invocation interface were C instanciates and starts the Java application. Maybe anyone knows how to get around with this.

Alright after a while of try/error; I just realized that sometimes it can be helpful just to check which methods are available in the JNI (RTFM ;) )

Anyway, its not really black magic and yes indeed possible and as some guys voted here theres obviously some interest in this question.

So what we can do if we want to open a native method to be callable from Java, even if it is in a exec? We have to register it and hand over a function pointer! Thats how it looks like in C:

//this is the function that shall be called from Java code
void JNICALL setWindowClosed(JNIEnv *env, jobject self, jboolean b){
    statusByte = (b==JNI_TRUE) ? true : false;

int main(){
JNIEnv* env;
JavaVM* jvm;
create JavaVM and instantiate desired class

jclass cls = env->FindClass("ClassName");

//we have our class - now register our function
JNINativeMethod nativeMethod; = "setWindowClosing"; //this is the corresponding name in Java
nativeMethod.signature = "(Z)V"; //parameter contains a boolean and returns void
nativeMethod.fnPtr = setWindowClosed; //pointer to our function
env->RegisterNatives(cls, &nativeMethod, 1); //register native method to Java

In addition we need to place a function with the name above in the Java code:

private native void setWindowClosing(boolean b);

Thats it - call the function in Java and it will use the implementation in C/C++. If my window closes now my application shuts down properly :)