📄 jnative.java
字号:
}
/**
* Method registerWindowProc register a WindowProc for the Window.<br>Calling this method is equivalent to call
* <br><i>registerWindowProc(hwnd.getValue(), proc)</i><br>
*
* @param hwnd
* the HANDLE of the window
* @param proc
* a WindowProc object that be called by native events
*
* @return the previous function pointer used as a WindowProc for this
* window.
*
* @exception NativeException
* if the SetWindowLongPtr fails or somthing weird happens
* (can crash too ;) )...
*
*/
public static int registerWindowProc(HWND hwnd, WindowProc proc) throws NativeException {
return nRegisterWindowProc(hwnd.getValue(), proc, false);
}
/**
* Method createCallback when a callback is no more used you should/must
* release it with <code>releaseCallback</code>
*
* @param numParams
* the number of parameters the callback function sould receive
* @param callback
* a Callback object that will handle the callback
*
* @return the native handle of the callback function (this is function
* pointer)
*
* @exception NativeException
* if something goes wrong
*
* @version 5/20/2006
*/
public static int createCallback(int numParams, Callback callback)
throws NativeException {
Integer address = nCreateCallBack(numParams);
getLogger().log(SEVERITY.DEBUG, String.format("registering callback %x\n", address));
callbacks.put(address, callback);
return address;
}
/**
* Method releaseCallback releases a callback previously created with
* <code>createCallback</code>
*
* @param callback
* a Callback
*
* @return true is this callback was released sucessfully
*
* @exception NativeException
*
*/
public static boolean releaseCallback(Callback callback)
throws NativeException {
if(null != callbacks.remove(callback.getCallbackAddress())) {
return nReleaseCallBack(callback.getCallbackAddress());
} else {
return false;
}
}
/**
* Method getAvailableCallbacks
*
* @return the number of callback you can create before JNative runs out
* callbacks.
* @deprecated this method returns always 1000
*/
public static int getAvailableCallbacks() {
return 1000;
}
/**
* Method getCurrentModule
*
* @return the HMODULE associated with the jnative DLL
*
* @exception NativeException
*
*/
public static int getCurrentModule() throws NativeException {
return nGetCurrentModule();
}
/**
* Method getDLLFileExports gets all the names of the functions exported by
* a library
*
* @param dllFile
* the name of a library
* @param demangled
* if true JNative tries to demangle C++ function names
*
* @return a String[] the names of the functions
*
* @exception NativeException
* @exception IllegalAccessException
*
*/
public static String[] getDLLFileExports(String dllFile, boolean demangled)
throws NativeException, InterruptedException {
if (isWindows) {
try {
HANDLE hFile = Kernel32.CreateFile(dllFile,
Kernel32.AccessMask.GENERIC_READ,
Kernel32.ShareMode.FILE_SHARE_READ, null,
Kernel32.CreationDisposition.OPEN_EXISTING,
Kernel32.FileAttribute.FILE_ATTRIBUTE_NORMAL, 0);
if (hFile.equals(HANDLE.INVALID_HANDLE_VALUE)) {
getLogger().log(SEVERITY.DEBUG,
String.format(
">>>ERROR<<< : %s file not found, CreateFile returned an invalid handle\n",
dllFile));
return null;
}
HANDLE hFileMapping = Kernel32.CreateFileMapping(hFile,
(SecurityAttributes) null,
Kernel32.PageAccess.PAGE_READONLY, new DWORD(0),
new DWORD(0), (String) null);
if (hFileMapping.equals(HANDLE.INVALID_HANDLE_VALUE)) {
Kernel32.CloseHandle(hFile);
getLogger().log(SEVERITY.DEBUG,
String.format(">>>ERROR<<< : CreateFileMapping returned a NULL handle\n"));
return null;
}
LONG lpFileBase = Kernel32.MapViewOfFileEx(hFileMapping,
Kernel32.FileMap.FILE_MAP_READ, new DWORD(0),
new DWORD(0), new DWORD(0), new LONG(0));
if (lpFileBase.getValue() == 0) {
Kernel32.CloseHandle(hFileMapping);
Kernel32.CloseHandle(hFile);
getLogger().log(SEVERITY.DEBUG,
String.format(">>>ERROR<<< : MapViewOfFile returned 0\n"));
return null;
}
int IMAGE_DOS_HEADER_SIZE = 14 * 2 + 4 * 2 + 2 * 2 + 10 * 2 + 4;
// Composed of Signature + IMAGE_FILE_HEADER +
// IMAGE_OPTIONAL_HEADER32
// See
// http://www.reactos.org/generated/doxygen/d1/d72/struct__IMAGE__OPTIONAL__HEADER32.html
// for example
// typedef struct _IMAGE_NT_HEADERS32 {
// DWORD Signature;
// IMAGE_FILE_HEADER FileHeader;
// IMAGE_OPTIONAL_HEADER32 OptionalHeader;
// }
int IMAGE_NUMBEROF_DIRECTORY_ENTRIES = 16;
// int IMAGE_DIRECTORY_ENTRY_EXPORT = 0;
int IMAGE_OPTIONAL_HEADER32_SIZE = 24 * 4
+ IMAGE_NUMBEROF_DIRECTORY_ENTRIES * 2 * 4;
int IMAGE_NT_HEADERS32_SIZE = 4 + 5 * 4 + IMAGE_OPTIONAL_HEADER32_SIZE;
int IMAGE_NT_SIGNATURE = 0x00004550;
int IMAGE_EXPORT_DIRECTORY_SIZE = 10 * 4;
Pointer pImg_DOS_Header = new Pointer(new NativeMemoryBlock(
lpFileBase.getValue(), IMAGE_DOS_HEADER_SIZE));
Pointer pImg_NT_Header = new Pointer(new NativeMemoryBlock(
pImg_DOS_Header.getPointer()
+ pImg_DOS_Header
.getAsInt(IMAGE_DOS_HEADER_SIZE - 4),
IMAGE_NT_HEADERS32_SIZE));
if (!Kernel32.IsBadReadPtr(pImg_NT_Header)
|| pImg_NT_Header.getAsInt(0) != IMAGE_NT_SIGNATURE) {
Kernel32.UnmapViewOfFile(lpFileBase);
Kernel32.CloseHandle(hFileMapping);
Kernel32.CloseHandle(hFile);
getLogger().log(SEVERITY.DEBUG,
String.format(
">>>ERROR<<< : IsBadReadPtr returned false, pointer is %d\n",
pImg_NT_Header.getPointer()));
return null;
}
// if (DEBUG)
getLogger().log(SEVERITY.DEBUG,
String.format(
">>>INFO<<< : IsBadReadPtr returned true, pointer is %d\n",
pImg_NT_Header.getPointer()));
// IMAGE_OPTIONAL_HEADER32
Pointer pOptionalHeader = new Pointer(new NativeMemoryBlock(
pImg_NT_Header.getPointer() + IMAGE_NT_HEADERS32_SIZE
- IMAGE_OPTIONAL_HEADER32_SIZE,
IMAGE_OPTIONAL_HEADER32_SIZE));
// (IMAGE_EXPORT_DIRECTORY)
Pointer pImg_Export_Dir = new Pointer(new NativeMemoryBlock(
pOptionalHeader.getAsInt(24 * 4), 4));
if (pImg_Export_Dir.isNull()) {
Kernel32.UnmapViewOfFile(lpFileBase);
Kernel32.CloseHandle(hFileMapping);
Kernel32.CloseHandle(hFile);
getLogger().log(SEVERITY.DEBUG,
String.format(">>>ERROR<<< : pImg_Export_Dir is NULL\n"));
return null;
}
pImg_Export_Dir = new Pointer(new NativeMemoryBlock(DbgHelp
.ImageRvaToVa(pImg_NT_Header, pImg_DOS_Header,
pImg_Export_Dir.asLONG(), NullPointer.NULL)
.getValue(), IMAGE_EXPORT_DIRECTORY_SIZE));
LONG ppdwNames = new LONG(pImg_Export_Dir
.getAsInt(8 * 4/* AddressOfNames */));
ppdwNames = DbgHelp.ImageRvaToVa(pImg_NT_Header,
pImg_DOS_Header, ppdwNames, NullPointer.NULL);
if (ppdwNames.getValue() == 0) {
Kernel32.UnmapViewOfFile(lpFileBase);
Kernel32.CloseHandle(hFileMapping);
Kernel32.CloseHandle(hFile);
getLogger().log(SEVERITY.DEBUG,
String.format(">>>ERROR<<< : ImageRvaToVa returned NULL\n"));
return null;
}
int iNoOfExports = pImg_Export_Dir
.getAsInt(6 * 4/* NumberOfNames */);
String[] pszFunctions = new String[iNoOfExports];
// if (DEBUG)
getLogger().log(SEVERITY.DEBUG, String.format("pszFunctions = %d\n",
pszFunctions.length));
for (int i = 0, ippdwNames = ppdwNames.getValue(); i < iNoOfExports; i++, ippdwNames += 4) {
// if (DEBUG)
getLogger().log(SEVERITY.DEBUG, String.format("ippdwNames[%d] : %d\n", i,
ippdwNames));
LONG szFunc = DbgHelp.ImageRvaToVa(pImg_NT_Header,
pImg_DOS_Header, new LONG(new Pointer(
new NativeMemoryBlock(ippdwNames, 4))
.getAsInt(0)), NullPointer.NULL);
pszFunctions[i] = new Pointer(new NativeMemoryBlock(szFunc
.getValue(), 1000)).getAsString();
// if (DEBUG)
getLogger().log(SEVERITY.DEBUG, pszFunctions[i]);
}
Kernel32.UnmapViewOfFile(lpFileBase);
Kernel32.CloseHandle(hFileMapping);
Kernel32.CloseHandle(hFile);
return pszFunctions;
} catch (IllegalAccessException e) {
getLogger().log(SEVERITY.ERROR, e);
return null;
}
} else if (isLinux) {
try {
String option = "";
if (demangled)
option = "C";
Process p = Runtime.getRuntime().exec(
"/usr/bin/nm -" + option + "Dg --defined-only "
+ dllFile);
BufferedReader br = new BufferedReader(new InputStreamReader(p
.getInputStream()));
String line = br.readLine();
ArrayList<String> l = new ArrayList<String>();
while (line != null) {
l.add(line);
line = br.readLine();
}
br.close();
getLogger().log(SEVERITY.DEBUG, "exit value : " + p.waitFor());
String[] array = new String[l.size()];
int i = 0;
for (String s : l)
array[i++] = s;
return array;
} catch (IOException e) {
getLogger().log(SEVERITY.ERROR, e);
throw new NativeException(e.getMessage());
}
} else {
return null;
}
}
/**
* Method getDLLFileExports gets all the names of the functions exported by
* a library
*
* @param dllFile
* the name of a library
*
* @return a String[] the names of the functions
*
* @exception NativeException
*
*/
public static String[] getDLLFileExports(String dllFile)
throws NativeException, InterruptedException {
return getDLLFileExports(dllFile, false);
}
public static int searchNativePattern(int nativePointer, byte[] pattern,
int maxSize) throws NativeException {
return nGetNativePattern(nativePointer, pattern, maxSize);
}
public static int searchNativePattern(Pointer pointer, byte[] pattern,
int maxSize) throws NativeException {
return nGetNativePattern(pointer.getPointer(), pattern, maxSize);
}
public static String getNativeSideVersion() throws NativeException {
return nGetNativeSideVersion();
}
private static final boolean isWindows;
private static final boolean isLinux;
/**
* Returns true if the current running platfrom is Windows
*
* @return a boolean
*
* @version 1/22/2006
*/
public static boolean isWindows() {
return isWindows;
}
/**
* Returns true if the current running platfrom is Linux
*
* @return a boolean
*
* @version 1/22/2006
*/
public static boolean isLinux() {
return isLinux;
}
private static JNativeLogger logger = null;
public static void setLogger(JNativeLogger _logger) {
logger = _logger;
}
public static JNativeLogger getLogger() {
if(logger == null) {
logger = ConsoleLogger.getInstance(JNative.class);
}
return logger;
}
public static void setLoggingEnabled(boolean b) {
DEBUG = b;
}
public static boolean isLogginEnabled() {
return DEBUG;
}
private static boolean initDone;
private static boolean DEBUG;
/**
* Must be called if running with the property <i>jnative.loadNative=<b>manual</b></i>
* @deprecated this method does nothing now
* @throws NativeException
*/
public static void initCallbacks() throws NativeException {
}
static {
boolean lInit = false;
String debug = System.getProperty("jnative.debug");
if (debug != null) {
try {
setLoggingEnabled(Boolean.parseBoolean(debug));
} catch (Exception e) {
System.err.println("DEBUG messages disabled!");
e.printStackTrace();
setLoggingEnabled(false);
}
} else {
setLoggingEnabled(false);
}
// Manage the type of the Map used
mLibs = Boolean.parseBoolean(""+System.getProperty("jnative.weakRef"))
?
new WeakHashMap<String, LibDesc>()
:
new HashMap<String, LibDesc>();
//if(DEBUG) {
getLogger().log(SEVERITY.DEBUG, "Using a "+mLibs.getClass().getName() + " as native handles storage");
//}
try {
String loadNative = System.getProperty("jnative.loadNative");
//if(DEBUG)
getLogger().log(SEVERITY.DEBUG, "jnative.loadNative property = "+loadNative);
if(loadNative == null || loadNative.equalsIgnoreCase("default")) {
//if(DEBUG)
getLogger().log(SEVERITY.DEBUG, "Using default System.loadLibrary()");
System.loadLibrary("JNativeCpp");
lInit = true;
} else if(loadNative.equalsIgnoreCase("manual")){
//if(DEBUG)
getLogger().log(SEVERITY.DEBUG, "Using manual : you MUST load the library yourself, then init callbacks !");
lInit = true;
} else {
//if(DEBUG)
getLogger().log(SEVERITY.DEBUG, "Trying to load Library from "+loadNative);
System.load(loadNative);
lInit = true;
}
} catch (Throwable e) {
getLogger().log(SEVERITY.ERROR, e);
} finally {
initDone = lInit;
String osName = System.getProperty("os.name");
isWindows = osName.toLowerCase().indexOf("windows") != -1;
isLinux = osName.toLowerCase().indexOf("linux") != -1;
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -