IKVM11  11
Java SE 11 Virtual Machine for .NET
Loading...
Searching...
No Matches
IKVM.Runtime.JNI.JNINativeLoader Class Reference

Static Public Member Functions

static long LoadLibrary (string filename, RuntimeJavaType fromClass)
 Initiates a load of the given JNI library by the specified class loader.
 
static void UnloadLibrary (long handle, RuntimeJavaType fromClass)
 Initiates an unload of the given native library for the specified class loader.
 

Static Public Attributes

static readonly object SyncRoot = new object()
 

Detailed Description

Manages the set of loaded native JNI libraries.

Definition at line 38 of file JNINativeLoader.cs.

Member Function Documentation

◆ LoadLibrary()

static long IKVM.Runtime.JNI.JNINativeLoader.LoadLibrary ( string filename,
RuntimeJavaType fromClass )
static

Initiates a load of the given JNI library by the specified class loader.

Parameters
filename
fromClass
Returns

Definition at line 53 of file JNINativeLoader.cs.

54 {
55 JVM.Context.Diagnostics.GenericJniInfo($"loadLibrary: '{filename}' fromClass '{fromClass}'");
56
57 lock (SyncRoot)
58 {
59 nint p = 0;
60
61 try
62 {
63 // attempt to load the native library
64 if ((p = LibJvm.Instance.JVM_LoadLibrary(filename)) == 0)
65 {
66 JVM.Context.Diagnostics.GenericJniInfo($"Failed to load library: path = '{filename}', message = {"NULL handle returned."}");
67 return 0;
68 }
69
70 // find whether the native library was already loaded
71 foreach (var h in fromClass.ClassLoader.GetNativeLibraries())
72 {
73 if (h == p)
74 {
75 LibJvm.Instance.JVM_UnloadLibrary(p);
76 JVM.Context.Diagnostics.GenericJniWarning("Library was already loaded, returning same reference");
77 return p;
78 }
79 }
80
81 // library was loaded by another classloader, that's a link error
82 if (loaded.Contains(p))
83 {
84 var msg = $"Native library '{filename}' already loaded in another classloader.";
85 JVM.Context.Diagnostics.GenericJniError($"UnsatisfiedLinkError: {msg}");
86 throw new java.lang.UnsatisfiedLinkError(msg);
87 }
88
89 JVM.Context.Diagnostics.GenericJniInfo($"Library loaded: {filename}, handle = 0x{p:X}");
90
91 try
92 {
93 var onload = LibJvm.Instance.JVM_FindLibraryEntry(p, NativeLibrary.MangleExportName("JNI_OnLoad", sizeof(nint) + sizeof(nint)));
94 if (onload != 0)
95 {
96 JVM.Context.Diagnostics.GenericJniInfo($"Calling JNI_OnLoad on: {filename}");
97 var f = new JNIFrame();
98 int v;
99 var w = f.Enter(ikvm.@internal.CallerID.create(fromClass.ClassObject, fromClass.ClassObject.getClassLoader()));
100 try
101 {
102 v = Marshal.GetDelegateForFunctionPointer<JNI_OnLoadFunc>(onload)(JavaVM.pJavaVM, null);
103 JVM.Context.Diagnostics.GenericJniInfo($"JNI_OnLoad returned: 0x{v:X8}");
104 }
105 finally
106 {
107 f.Leave();
108 }
109
110 if (JNIVM.IsSupportedJNIVersion(v) == false)
111 {
112 var msg = $"Unsupported JNI version 0x{v:X} required by {filename}";
113 JVM.Context.Diagnostics.GenericJniError($"UnsatisfiedLinkError: {msg}");
114 throw new java.lang.UnsatisfiedLinkError(msg);
115 }
116 }
117 }
118 catch (EntryPointNotFoundException)
119 {
120 // JNI_OnLoad entry point doesn't exist and isn't required
121 }
122
123 // record addition of native library
124 loaded.Add(p);
125 fromClass.ClassLoader.RegisterNativeLibrary(p);
126 return p;
127 }
128 catch (DllNotFoundException e)
129 {
130 JVM.Context.Diagnostics.GenericJniInfo($"Failed to load library: path = '{filename}', error = DllNotFoundException, message = {e.Message}");
131 return 0;
132 }
133 catch (Exception e)
134 {
135 JVM.Context.Diagnostics.GenericJniInfo($"Failed to load library: path = '{filename}', error = Exception, message = {e.Message}");
136 LibJvm.Instance.JVM_UnloadLibrary(p);
137 throw;
138 }
139 }
140 }
static readonly object SyncRoot

◆ UnloadLibrary()

static void IKVM.Runtime.JNI.JNINativeLoader.UnloadLibrary ( long handle,
RuntimeJavaType fromClass )
static

Initiates an unload of the given native library for the specified class loader.

Parameters
handle
loader

Definition at line 147 of file JNINativeLoader.cs.

148 {
149 var p = (nint)handle;
150
151 lock (SyncRoot)
152 {
153 JVM.Context.Diagnostics.GenericJniInfo($"Unloading library: handle = 0x{handle:X}, class = {fromClass}");
154
155 try
156 {
157 var onunload = LibJvm.Instance.JVM_FindLibraryEntry(p, NativeLibrary.MangleExportName("JNI_OnUnload", sizeof(nint) + sizeof(nint)));
158 if (onunload != 0)
159 {
160 JVM.Context.Diagnostics.GenericJniInfo($"Calling JNI_OnUnload on: handle = 0x{handle:X}");
161
162 var f = new JNIFrame();
163 var w = f.Enter(ikvm.@internal.CallerID.create(fromClass.ClassObject, fromClass.ClassObject.getClassLoader()));
164 try
165 {
166 Marshal.GetDelegateForFunctionPointer<JNI_OnUnloadFunc>(onunload)(JavaVM.pJavaVM, null);
167 }
168 finally
169 {
170 f.Leave();
171 }
172 }
173 }
174 catch (EntryPointNotFoundException)
175 {
176 // JNI_OnUnload entry point doesn't exist and isn't required
177 }
178
179 // remove record of native library
180 loaded.Remove(p);
181 fromClass.ClassLoader.UnregisterNativeLibrary(p);
182 LibJvm.Instance.JVM_UnloadLibrary(p);
183 }
184 }

Member Data Documentation

◆ SyncRoot

readonly object IKVM.Runtime.JNI.JNINativeLoader.SyncRoot = new object()
static

Definition at line 44 of file JNINativeLoader.cs.


The documentation for this class was generated from the following file: