diff --git a/README.md b/README.md index 1793f88f..df2f2e3b 100644 --- a/README.md +++ b/README.md @@ -384,8 +384,8 @@ __Example__ Creates a new java Proxy for the given interface. Functions passed in will run on the v8 main thread and not a new thread. -The returned object has two methods ref() and unref() which you can use to maintain references to prevent premature -garbage collection. You must call these methods to ensure the proxy stays around. +The returned object has a method unref() which you can use to free the object for +garbage collection. __Arguments__ diff --git a/compile-java-code.sh b/compile-java-code.sh index 2e241b40..bc52d6fe 100755 --- a/compile-java-code.sh +++ b/compile-java-code.sh @@ -8,3 +8,6 @@ javac ${JAVAC_OPTS} *.java cd ../src-java/node javac ${JAVAC_OPTS} *.java + +cd ../../ +javah -classpath src-java -d ./src node.NodeDynamicProxyClass diff --git a/src-java/node/NodeDynamicProxyClass.class b/src-java/node/NodeDynamicProxyClass.class index 90a4f563..9584b6ee 100644 Binary files a/src-java/node/NodeDynamicProxyClass.class and b/src-java/node/NodeDynamicProxyClass.class differ diff --git a/src-java/node/NodeDynamicProxyClass.java b/src-java/node/NodeDynamicProxyClass.java index 56991a8e..223c39ff 100644 --- a/src-java/node/NodeDynamicProxyClass.java +++ b/src-java/node/NodeDynamicProxyClass.java @@ -1,8 +1,10 @@ package node; -public class NodeDynamicProxyClass implements java.lang.reflect.InvocationHandler -{ +import java.util.HashSet; + +public class NodeDynamicProxyClass implements java.lang.reflect.InvocationHandler { private native Object callJs(long ptr, java.lang.reflect.Method m, Object[] args) throws Throwable; + private native void unref(long ptr) throws Throwable; public long ptr; public NodeDynamicProxyClass(String path, long ptr) { @@ -25,11 +27,7 @@ public Object invoke(Object proxy, java.lang.reflect.Method m, Object[] args) th return result; } - public void ref() { - - } - - public void unref() { - + public void unref() throws Throwable { + unref(this.ptr); } } diff --git a/src/java.cpp b/src/java.cpp index e98e0878..ad14bf53 100644 --- a/src/java.cpp +++ b/src/java.cpp @@ -356,6 +356,7 @@ void Java::destroyJVM(JavaVM** jvm, JNIEnv** env) { if(result->IsNativeError()) { return ThrowException(result); } + dynamicProxyData->jsObject = v8::Persistent::New(result); return scope.Close(result); } @@ -989,3 +990,11 @@ JNIEXPORT jobject JNICALL Java_node_NodeDynamicProxyClass_callJs(JNIEnv *env, jo } return dynamicProxyData->result; } + +JNIEXPORT void JNICALL Java_node_NodeDynamicProxyClass_unref(JNIEnv *env, jobject src, jlong ptr) { + DynamicProxyData* dynamicProxyData = (DynamicProxyData*)ptr; + if(!dynamicProxyDataVerify(dynamicProxyData)) { + return; + } + dynamicProxyData->jsObject.Clear(); +} diff --git a/src/javaObject.cpp b/src/javaObject.cpp index dca7036c..e6a0a2ca 100644 --- a/src/javaObject.cpp +++ b/src/javaObject.cpp @@ -97,6 +97,8 @@ JavaObject::~JavaObject() { jfieldID ptrField = env->GetFieldID(nodeDynamicProxyClass, "ptr", "J"); DynamicProxyData* proxyData = (DynamicProxyData*)(long)env->GetLongField(m_obj, ptrField); if(dynamicProxyDataVerify(proxyData)) { + proxyData->markerStart = 0; + proxyData->markerEnd = 0; delete proxyData; } } diff --git a/src/node_NodeDynamicProxyClass.h b/src/node_NodeDynamicProxyClass.h index 3b7b67cf..93b414d2 100644 --- a/src/node_NodeDynamicProxyClass.h +++ b/src/node_NodeDynamicProxyClass.h @@ -15,6 +15,14 @@ extern "C" { JNIEXPORT jobject JNICALL Java_node_NodeDynamicProxyClass_callJs (JNIEnv *, jobject, jlong, jobject, jobjectArray); +/* + * Class: node_NodeDynamicProxyClass + * Method: unref + * Signature: (J)V + */ +JNIEXPORT void JNICALL Java_node_NodeDynamicProxyClass_unref + (JNIEnv *, jobject, jlong); + #ifdef __cplusplus } #endif diff --git a/src/utils.cpp b/src/utils.cpp index 13063af7..c9f3015e 100644 --- a/src/utils.cpp +++ b/src/utils.cpp @@ -694,7 +694,7 @@ int dynamicProxyDataVerify(DynamicProxyData* data) { return 1; } - printf("*** ERROR: Lost reference to the dynamic proxy. You must maintain a reference in javascript land using ref() and unref(). ***\n"); + printf("*** ERROR: Lost reference to the dynamic proxy. You must maintain a reference in javascript land using ref() and unref(). (%p) ***\n", data); return 0; } diff --git a/src/utils.h b/src/utils.h index aef6393a..59cdd19f 100644 --- a/src/utils.h +++ b/src/utils.h @@ -35,6 +35,7 @@ struct DynamicProxyData { Java* java; std::string interfaceName; v8::Persistent functions; + v8::Persistent jsObject; std::string methodName; jobjectArray args; jobject result;