JNA - Нарушение доступа, JVM завершает работу
Вопрос
Я вызываю DLL с передачей ей объекта функции обратного вызова.Одна из функций - простая печать.Затем у меня есть цикл из 100 итераций, просто печатающий индекс и несколько отпечатков после цикла.
Вот C-код
extern "C" int Start(void* callback(CString))
{
for(int j=0; j<100; j++)
callback(AConvertToString(j));
callback("in Start called from Java");
callback("another line");
}
Вот Java-код
public interface MyDll extends Library{
MyDll INSTANCE = (MyDll) Native.loadLibrary("MyDll",MyDll.class);
public interface MyCallback extends StdCallCallback {
public boolean callback(String msg);
}
public int Start(MyCallback callback);
}
//in main:
...
MyDll myDll = (MyDll)MyDll.INSTANCE;
myDll.Start(new MyDll.MyCallback() {
public boolean callback(String msg) {
System.out.println(msg);
return true;
}
});
На выходе получаются числа 0..41 (ДА, 41!!!не 99), а затем "при запуске вызывается с Java", за которым следует ужасный сбой:
#
# An unexpected error has been detected by Java Runtime Environment:
#
# EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x7c809823, pid=468, tid=2636
#
# Java VM: Java HotSpot(TM) Client VM (10.0-b23 mixed mode, sharing windows-x86)
# Problematic frame:
# C [kernel32.dll+0x9823]
Я много читал (и здесь тоже), но не могу найти проблему.Я запускаю JRE на Java6.У меня на компьютере 1,5 ГБ оперативной памяти.DLL не используется никаким другим процессом (проблем с параллелизмом нет).
Спасибо, Азриэль
Решение
Попробуйте записать свой MyCallback как com.sun.jna.Обратный вызов вместо этого как com.sun.jna.win32.StdCallLibrary.StdCallCallback :
public interface MyDll extends Library{
MyDll INSTANCE = (MyDll) Native.loadLibrary("MyDll",MyDll.class);
public interface MyCallback extends Callback {
public boolean callback(String msg);
}
public int Start(MyCallback callback);
}
С уважением, Эммануэль Жирар
Другие советы
В моем случае при разработке телекоммуникационного приложения, использующего win32 dll, все было наоборот.
Используя com.sun.jna.Library и com.sun.jna.Callback, при возврате с обратного вызова всегда происходил сбой виртуальной машины.
После изменения на com.sun.jna.win32.StdCallLibrary и com.sun.jna.win32.StdCallLibrary.StdCallCallback проблема была решена.