我有第三方.NET程序集和大型Java應用程序。我需要從Java應用程序調用.NET類庫提供的方法。該程序集不支持COM。 我已經搜索的淨,到目前爲止我有以下:從Java調用.NET程序集:JVM崩潰
C#代碼(cslib.cs):
using System;
namespace CSLib
{
public class CSClass
{
public static void SayHi()
{
System.Console.WriteLine("Hi");
}
}
}
與(使用.NET 3.5,但是當使用2.0同樣的情況)編譯:
csc /target:library cslib.cs
C++代碼(clib.cpp):
#include <jni.h>
#using <CSLib.dll>
using namespace CSLib;
extern "C" _declspec(dllexport) void Java_CallCS_callCS(JNIEnv* env, jclass cls) {
CSLib::CSClass::SayHi();
}
與(使用VC 2008和工具編譯,但是第當使用2003和工具電子同樣的情況):
cl /clr /LD clib.cpp
mt -manifest clib.dll.manifest -outputresource:clib.dll;2
Java代碼(CallCS.java):
class CallCS {
static {
System.loadLibrary("clib");
}
private static native void callCS();
public static void main(String[] args) {
callCS();
}
}
當我嘗試運行Java類,Java虛擬機崩潰時調用的方法(它能夠加載庫):
# # An unexpected error has been detected by Java Runtime Environment: # # Internal Error (0xe0434f4d), pid=3144, tid=3484 # # Java VM: Java HotSpot(TM) Client VM (10.0-b19 mixed mode, sharing windows-x86) # Problematic frame: # C [kernel32.dll+0x22366] # ... Java frames: (J=compiled Java code, j=interpreted, Vv=VM code) j CallCS.callCS()V+0 j CallCS.main([Ljava/lang/String;)V+0 v ~StubRoutines::call_stub
但是,如果我創建加載clib.dll並調用導出函數Java_CallCS_callCS普通CPP的應用程序,一切都OK了。 我已經在x86和x64環境中嘗試了這一點,結果是一樣的。我還沒有嘗試過其他版本的Java,但我需要在1.5.0上運行代碼。
而且,如果我修改clib.cpp調用的系統方法,一切工作正常甚至從Java:
#include <jni.h>
#using <mscorlib.dll>
using namespace System;
extern "C" _declspec(dllexport) void Java_CallCS_callCS(JNIEnv* env, jclass cls) {
System::Console::WriteLine("It works");
}
爲了結束:
- 我能夠從Java調用系統方法 - > clib.dll - > mscorlib.dll
- 我可以從CPPApp調用任何方法 - > clib.dll - > cslib.dll
- 我無法從Java調用任何方法 - > clib.dll - > cs lib.dll
我知道一個解決方法,使用1.上面 - 我可以使用反射裝載assmebly和調用所需的方法只使用系統調用,但代碼變得凌亂,我希望更好解。
我知道dotnetfromjava項目,它使用了反射方法,但不希望增加比所需更多的複雜性。但是,如果沒有其他方式,我會使用類似的東西。
我也看過ikvm.net,但我的理解是它使用它自己的JVM(用C#編寫)來完成這個魔術。但是,在虛擬機下運行整個Java應用程序對我來說是不行的。
謝謝。
的C++代碼實際上是C++/CLI嗎? – Gili 2009-09-25 16:08:58
是的,/ clr選項指定 – Kcats 2009-10-05 08:47:38