Welcome to Experts Exchange

Add your voice to the tech community where 5M+ people, just like you, are talking about what matters.

  • Help others & share knowledge
  • Earn cash & points
  • Learn & ask questions
Solved

JNI Invocation interface - Callback from java to C++

Posted on 2009-07-07
2
1,330 Views
Last Modified: 2013-12-14
Hi,
I am trying to use JNI invocation interface to start a java program from a c++ dll and then receive call back from the java program (it happens to be a socket server , so i need to know when someone is connecting to the socket server(java) )  . The problem is i can not find any documentation of call back in JNI invocation interface. I put my code here and can someone please tell me what I am doing wrong or point me in the right direction of some proper documentation on this matter (callback from java in JNI invocation interface.)

I have some clue about it though. I could pass a pointer to a function ( that is declared in my cpp ) to  the java program and then from the java program i could convert that pointer to a method and call it. But i do not know how to do it. So if anyone can provide me a sample code to do it , it will also be accepted as a solution.

Regards,
Shrouk Khan
// java code
public class Prog 
{
	public native void callcpp(); // trying to use this as a call back to cpp dll
	static{
		System.loadLibrary("CPPDll");
	}
    public static void main(String[] args) {
	
         System.out.println("Java program started, now going to do call back from java:  " + args[0]); //
       new Prog().callcpp(); // call a method in cpp
		 
    }
   
}
 
 
// dll code for starting the java program and receiving call back:
 
Callback  Connected=NULL;
int WINEXPORT start_java() //this is where i start the java program by calling its main metho
{
	
	printf("Inside \n");
	JNIEnv *env;
	JavaVM *jvm;
	jint res;
	jclass cls;
	jmethodID mid;
	jstring jstr;
	jclass stringClass;
	jobjectArray args;
 
	JavaVMInitArgs vm_args;
	JavaVMOption options[1];
	options[0].optionString =
		"-Djava.class.path=" USER_CLASSPATH;
	vm_args.version = 0x00010002;
	vm_args.options = options;
	vm_args.nOptions = 1;
	vm_args.ignoreUnrecognized = JNI_TRUE;
	/* Create the Java VM */
	res =JNI_CreateJavaVM(&jvm, (void **)&env, &vm_args);
	printf("JVM Created \n");
	if (res < 0) {
		printf("cant create \n");
	}
 
	cls = env->FindClass("Prog");
	printf("class found  \n");
	if (cls == 0) {
		goto destroy;
	}
 
	mid = env->GetStaticMethodID(cls, "main",
		"([Ljava/lang/String;)V");
	if (mid == 0) {
		goto destroy;
	}
	jstr = env->NewStringUTF(" from C!");
	if (jstr == 0) {
		goto destroy;
	}
	stringClass = env->FindClass("java/lang/String");
	args = env->NewObjectArray( 1, stringClass, jstr);
	if (args == 0) {
		goto destroy;
	}
	env->CallStaticVoidMethod(cls, mid, args);
 
destroy:
	if (env->ExceptionOccurred()) 
	{
		env->ExceptionDescribe();
	}
	jvm->DestroyJavaVM();
	return 1;
}
 
Callback  Connected=NULL;
 
JNIEXPORT void JNICALL 
Java_Prog_callcpp(JNIEnv *env, jobject obj)
{
	Connected();
	printf("Call back received from java !\n");
	return;
}

Open in new window

0
Comment
Question by:Softverkpro
  • 2
2 Comments
 

Accepted Solution

by:
Softverkpro earned 0 total points
ID: 24810394
Hi, okay after 5 days of obsessing over this problem i figured out the solution. The problem
arises because I am using the DLL to load the java program (the DLL is actually loaded from c# ,
so the whole flow of control is like this : C# GUI --> C++ Dll (custom JNI wrapper) --> Java
Server ) . But the following snippet in my java code:

static
{
       System.loadLibrary("CPPDll");
}

instructs the java to load the cpp dll (the caller) even before cpp dll is able to load the java program. So it instantly crashes! The solution is to move that instruction to some place which will be called well after the java has started running.

So, this following Snippet solved the problem.

(i only needed to change my java code, cpp code was fine.)
public class Prog 
{
	public native void callcpp();
	
		
	
    public static void main(String[] args) {
		 System.loadLibrary("CPPDll");
         System.out.println("Hello world " + args[0]);
         System.out.println("Trying to callback");
		 callback();
		 System.out.println("Finished");
    }
    public static void callback() {
  		System.out.println("Inside callback");
         new Prog().callcpp();
         System.out.println("done calling callback");
    }
}

Open in new window

0
 

Author Comment

by:Softverkpro
ID: 24810399
actually it is possible (i think!) to just use some super expensive third party library's like the ones from TeamDev but then again I or anyone else would not learn anything and keep hitting into problems like this. So i decided to write the library on my own. :)
0

Featured Post

Free Tool: ZipGrep

ZipGrep is a utility that can list and search zip (.war, .ear, .jar, etc) archives for text patterns, without the need to extract the archive's contents.

One of a set of tools we're offering as a way to say thank you for being a part of the community.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
varialbe initialization 11 37
web application structure 18 99
maven module vs maven project 3 46
Android development question 2 53
Here is a helpful source code for C++ Builder programmers that allows you to manage and manipulate HTML content from C++ code, while also handling HTML events like onclick, onmouseover, ... Some objects defined and used in this source include: …
Go is an acronym of golang, is a programming language developed Google in 2007. Go is a new language that is mostly in the C family, with significant input from Pascal/Modula/Oberon family. Hence Go arisen as low-level language with fast compilation…
This tutorial covers a practical example of lazy loading technique and early loading technique in a Singleton Design Pattern.
The viewer will learn how to use NetBeans IDE 8.0 for Windows to connect to a MySQL database. Open Services Panel: Create a new connection using New Connection Wizard: Create a test database called eetutorial: Create a new test tabel called ee…

839 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question