Loading and uninstalling local code in JNI technology
JNI refers to "Java local call interface ". Using this technology, Java can call local code written for Java in other languages (including c ++. On Windows, this may be a DLL, and on Linux, it may be a so.
My experiment passed on windows, so the local code I mentioned is a DLL dynamic link library.
1. Implement JNI
1) Write a main. Java file as follows.
Class main {
Public static native void Hello ();
Public static void main (string ARGs [])
{
System. Load ("C: // T. dll ");
Hello ();
}
}
Explanation: the native-modified Hello function is a local call interface, which has no function body because the function body is in the T. dll that I will generate. The main function is the entry of the main class. It loads T. dll and then calls the hello function, which is so simple!
2) Compile main. Java
Command: javac main. Java
Explanation: If there is no problem, the main. Class file is generated. For Java, This is a compiled executable file.
3) generate the local code library ---- "T. dll"
3.1) generate the C ++ header file ---- "Main. h"
Command: javah main
Explanation: If there is no problem, the "Main. H" file has been generated. The content of the file I generated is as follows. Note the declaration of java_main_hello function, which is the helllo function in Java.
/* Do not edit this file-it is machine generated */
# Include <JNI. h>
/* Header for class main */
# Ifndef _ included_main
# DEFINE _ included_main
# Ifdef _ cplusplus
Extern "C "{
# Endif
/*
* Class: Main
* Method: Hello
* Signature: () V
*/
Jniexport void jnicall java_main_hello
(Jnienv *, jclass );
# Ifdef _ cplusplus
}
# Endif
# Endif
3.2) use VC to generate a DLL project. My main program file is as follows. Note the implementation of the java_main_hello function.
// T. cpp: defines the entry point for the DLL application.
//
# Include "stdafx. H"
# Ifdef _ managed
# Pragma managed (push, off)
# Endif
# Include "Main. H"
Jniexport void jnicall java_main_hello (jnienv *, jclass)
{
MessageBox (0, l "hello", l "Have you used the HL script language? ", Mb_ OK );
}
Bool apientry dllmain (hmodule,
DWORD ul_reason_for_call,
Lpvoid lpreserved
)
{
Return true;
}
# Ifdef _ managed
# Pragma managed (POP)
# Endif
3.3) Compile the C ++ project to generate T. dll and copy it to the C root directory.
4) execute main. Class
Command: Java main
Explanation: If there is no problem, the pop-up MessageBox is displayed.
2. Uninstall the local code library
If, as shown in the preceding figure, the process will exit after the main execution, and T. dll will be uninstalled. However, in the actual application, the process will continue and the T. dll must be uninstalled. I finally found this method on the Internet to share with you!
1) modify the main class code. The content of the new main. Java file is as follows. Note that the content is different from that at the beginning (especially the unloadnativelibs function)
Import java. util .*;
Import java. Lang. Reflect .*;
Class main {
Public static native void Hello ();
Private void unloadnativelibs () throws throwable {
Classloader = This. getclass (). getclassloader ();
Field field = classloader. Class. getdeclaredfield ("nativelibraries ");
Field. setaccessible (true );
Vector libs = (vector) field. Get (classloader );
Iterator it = libs. iterator ();
Object O;
While (it. hasnext ())
{
O = it. Next ();
Method finalize = O. getclass (). getdeclaredmethod ("finalize", new class [0]);
Finalize. setaccessible (true );
Finalize. Invoke (O, new object [0]);
}
}
Public Boolean freelibrary (){
Boolean result = true;
Try {
Unloadnativelibs ();
} Catch (throwable e ){
Result = false;
}
Return result;
}
Public static void main (string ARGs [])
{
System. Load ("C: // T. dll ");
Hello ();
New Main (). freelibrary ();
Int I = 0;
For (I = 0; I <10000; I ++)
{
System. GC ();
}
}
}
Explanation: in the main function, when (). after freelibrary is called, the program starts a long loop. During this loop, the process does not exit, but I can delete T. DLL, which indicates it has been uninstalled.