internal jvmtiError AddGlobalReference(JvmtiEnvironment environment, JniEnvironment nativeEnvironment, jobject obj) { long tag; jvmtiError error = environment.GetTag(obj, out tag); if (error != jvmtiError.None) { return(error); } if (tag == 0) { return(jvmtiError.IllegalArgument); } _globalReferences.AddOrUpdate(tag, t => { return(Tuple.Create(nativeEnvironment.NewGlobalReference(obj), 1)); }, (t, v) => { if (v.Item2 == 0) { return(Tuple.Create(nativeEnvironment.NewGlobalReference(obj), 1)); } else { return(Tuple.Create(v.Item1, v.Item2 + 1)); } }); return(jvmtiError.None); }
internal jclass FindBaseClass(JvmtiEnvironment environment, JniEnvironment nativeEnvironment, jclass classHandle, string signature) { string currentSignature; string genericSignature; JvmtiErrorHandler.ThrowOnFailure(environment.GetClassSignature(classHandle, out currentSignature, out genericSignature)); if (currentSignature == signature) { return((jclass)nativeEnvironment.NewGlobalReference(classHandle)); } jclass superClass = nativeEnvironment.GetSuperclass(classHandle); if (superClass == jclass.Null) { return(jclass.Null); } jclass result = FindBaseClass(environment, nativeEnvironment, superClass, signature); nativeEnvironment.DeleteLocalReference(superClass); return(result); }
private jthread CreateAgentThread(JniEnvironment nativeEnvironment) { jclass @class = nativeEnvironment.FindClass("java/lang/Thread"); if (@class == jclass.Null) throw new Exception("ERROR: JNI: Cannot find java/lang/Thread with FindClass."); jmethodID method = nativeEnvironment.GetMethodId(@class, "<init>", "()V"); if (method == jmethodID.Null) throw new Exception("Cannot find Thread constructor method."); jthread result = (jthread)nativeEnvironment.NewObject(@class, method); if (result == jthread.Null) throw new Exception("Cannot create new Thread object"); jthread agentThread = (jthread)nativeEnvironment.NewGlobalReference(result); if (result == jthread.Null) throw new Exception("Cannot create a new global reference for the agent thread."); // don't need to keep the local reference around nativeEnvironment.DeleteLocalReference(result); return agentThread; }