Wrote some tests on Java JNI. Lesson learned: it is ok to return a local reference from JNI. Just don't explicitly call DeleteLocalRef on it otherwise Java side will get a null value.
Regions highlighted on the graph:
(1) Running the JNI calls normally, freeing local references as it goes. Everything works as expected.
(2) Running the JNI calls without explicitly freeing local references. It is still fine. There were reclaimable objects left in the memory. But triggering the GC (from VisualVM) will free up the space.
(3) Running the JNI calls incorrectly by freeing the local
references before returning from JNI. Memory usage normal. But the
program printout should indicate 0 test case passed. This is because
null is returned instead of the expected
(4) !! This will cause OutOfMemoryError !!. The JNI calls explicitly create global references without freeing them, causing out-of-memory issue.