storing result of a Class getField call?
Tom Tromey
tromey@redhat.com
Fri Jun 15 10:59:00 GMT 2001
>>>>> "Marcus" == Marcus G Daniels <mgd@swarm.org> writes:
Sorry about the delay in my reply.
Marcus> In some JNI code that works with Sun JDK 1.3 and Kaffe 1.0.6,
Marcus> I'm stashing the results of a Class getField call in a
Marcus> variable and globalrefing it. By watching the unmark_for_gc
Marcus> call in jni.cc I can see that the reference to the Field is
Marcus> not explicitly removed from the JNI `ref_table', however, some
Marcus> time after caching the result of the getField call (when I
Marcus> wish to use and reuse and reuse the stashed Field), the object
Marcus> that is there has changed.
Offhand I couldn't say what is going on here. Given that it works
when you disable GC, I would guess that the object is being collected.
This might happen if, for some reason, the `ref_table' is not being
scanned.
A few things I thought of that you could try:
* You could run your program in the debugger and put a finalizer on
the Field which will cause an abort when it is finalized (see
`fail_on_finalization' in prims.cc).
If it is finalized then you'll know that it is being collected.
* You could try registering `ref_table' as a root in _Jv_JNI_Init.
Initially you could do this just by calling the appropriate GC
function directly.
In theory this shouldn't be required though :-(
Marcus> Likewise, if I do a lookup of the Field immediately adjacent
Marcus> to the use I wish to make, it also works.
Marcus> It seems fishy that this last workaround works as well as it
Marcus> does if there is more general GC problem.
I'm not too suprised. When you ask for a Field a new object is
created from the reflection data in the Class. This reflection data
cannot be GCd; it is static.
If you could write a simple test case in the form of the tests in
gcc/libjava/testsuite/libjava.jni, I could check it in and perhaps
investigate it.
Tom
More information about the Java
mailing list