From 83c64db681317c28239f07c5a8e6bb201834f0ba Mon Sep 17 00:00:00 2001 From: Tom Tromey Date: Fri, 23 Mar 2001 19:15:44 +0000 Subject: [PATCH] jni.cc (_Jv_JNI_GetAnyFieldID): Handle unresolved fields. * jni.cc (_Jv_JNI_GetAnyFieldID): Handle unresolved fields. * java/lang/reflect/natField.cc (getType): Use _Jv_ResolveField unconditionally. * include/jvm.h (_Jv_ResolveField): Declare. * include/java-interp.h (_Jv_ResolveField): Don't declare. * resolve.cc (_Jv_ResolveField): No longer conditional on INTERPRETER. From-SVN: r40785 --- libjava/ChangeLog | 10 ++++++++++ libjava/include/java-interp.h | 3 +-- libjava/include/jvm.h | 3 ++- libjava/java/lang/natClass.cc | 6 ++++-- libjava/java/lang/reflect/natField.cc | 15 +++------------ libjava/jni.cc | 12 ++++++++---- libjava/resolve.cc | 24 ++++++++++++------------ 7 files changed, 40 insertions(+), 33 deletions(-) diff --git a/libjava/ChangeLog b/libjava/ChangeLog index 0847094e7bd..a58e14b5160 100644 --- a/libjava/ChangeLog +++ b/libjava/ChangeLog @@ -1,3 +1,13 @@ +2001-03-22 Tom Tromey + + * jni.cc (_Jv_JNI_GetAnyFieldID): Handle unresolved fields. + * java/lang/reflect/natField.cc (getType): Use _Jv_ResolveField + unconditionally. + * include/jvm.h (_Jv_ResolveField): Declare. + * include/java-interp.h (_Jv_ResolveField): Don't declare. + * resolve.cc (_Jv_ResolveField): No longer conditional on + INTERPRETER. + 2001-03-23 Bryce McKinlay Fix for PR libgcj/1736. Thanks to Robert Boehne and Alexandre Oliva diff --git a/libjava/include/java-interp.h b/libjava/include/java-interp.h index acc2eb9d5b7..ebf958bf197 100644 --- a/libjava/include/java-interp.h +++ b/libjava/include/java-interp.h @@ -1,6 +1,6 @@ // java-interp.h - Header file for the bytecode interpreter. -*- c++ -*- -/* Copyright (C) 1999, 2000 Free Software Foundation +/* Copyright (C) 1999, 2000, 2001 Free Software Foundation This file is part of libgcj. @@ -40,7 +40,6 @@ bool _Jv_VerifyClassName (_Jv_Utf8Const *name); bool _Jv_VerifyIdentifier (_Jv_Utf8Const *); bool _Jv_ClassNameSamePackage (_Jv_Utf8Const *name1, _Jv_Utf8Const *name2); void _Jv_DefineClass (jclass, jbyteArray, jint, jint); -void _Jv_ResolveField (_Jv_Field *, java::lang::ClassLoader*); void _Jv_InitField (jobject, jclass, int); void * _Jv_AllocMethodInvocation (jsize size); diff --git a/libjava/include/jvm.h b/libjava/include/jvm.h index 006f1d9adc4..50af7569fb2 100644 --- a/libjava/include/jvm.h +++ b/libjava/include/jvm.h @@ -1,6 +1,6 @@ // jvm.h - Header file for private implementation information. -*- c++ -*- -/* Copyright (C) 1998, 1999, 2000 Free Software Foundation +/* Copyright (C) 1998, 1999, 2000, 2001 Free Software Foundation This file is part of libgcj. @@ -219,6 +219,7 @@ extern "C" void _Jv_CheckArrayStore (jobject array, jobject obj); extern "C" void _Jv_RegisterClass (jclass klass); extern "C" void _Jv_RegisterClasses (jclass *classes); extern void _Jv_UnregisterClass (_Jv_Utf8Const*, java::lang::ClassLoader*); +extern void _Jv_ResolveField (_Jv_Field *, java::lang::ClassLoader*); extern jclass _Jv_FindClass (_Jv_Utf8Const *name, java::lang::ClassLoader *loader); diff --git a/libjava/java/lang/natClass.cc b/libjava/java/lang/natClass.cc index 11f5e50a858..b934ae76389 100644 --- a/libjava/java/lang/natClass.cc +++ b/libjava/java/lang/natClass.cc @@ -678,7 +678,7 @@ java::lang::Class::finalize (void) void java::lang::Class::initializeClass (void) { - // jshort-circuit to avoid needless locking. + // short-circuit to avoid needless locking. if (state == JV_STATE_DONE) return; @@ -713,7 +713,9 @@ java::lang::Class::initializeClass (void) wait (); // Steps 3 & 4. - if (state == JV_STATE_DONE || state == JV_STATE_IN_PROGRESS || thread == self) + if (state == JV_STATE_DONE + || state == JV_STATE_IN_PROGRESS + || thread == self) { _Jv_MonitorExit (this); return; diff --git a/libjava/java/lang/reflect/natField.cc b/libjava/java/lang/reflect/natField.cc index 57421d690b4..0aedc4ea363 100644 --- a/libjava/java/lang/reflect/natField.cc +++ b/libjava/java/lang/reflect/natField.cc @@ -1,6 +1,6 @@ // natField.cc - Implementation of java.lang.reflect.Field native methods. -/* Copyright (C) 1998, 1999, 2000 Free Software Foundation +/* Copyright (C) 1998, 1999, 2000, 2001 Free Software Foundation This file is part of libgcj. @@ -44,17 +44,8 @@ jclass java::lang::reflect::Field::getType () { jfieldID fld = _Jv_FromReflectedField (this); - if (! fld->isResolved()) - { - JvSynchronize sync (declaringClass); - if (! fld->isResolved()) - { - fld->type - = _Jv_FindClassFromSignature(((Utf8Const*) (fld->type))->data, - declaringClass->getClassLoader()); - fld->flags &= ~_Jv_FIELD_UNRESOLVED_FLAG; - } - } + JvSynchronize sync (declaringClass); + _Jv_ResolveField (fld, declaringClass->getClassLoader ()); return fld->type; } diff --git a/libjava/jni.cc b/libjava/jni.cc index a4a12a83f47..7b682f177b7 100644 --- a/libjava/jni.cc +++ b/libjava/jni.cc @@ -1068,8 +1068,13 @@ _Jv_JNI_GetAnyFieldID (JNIEnv *env, jclass clazz, // FIXME: what if field_class == NULL? + java::lang::ClassLoader *loader = clazz->getClassLoader (); while (clazz != NULL) { + // We acquire the class lock so that fields aren't resolved + // while we are running. + JvSynchronize sync (clazz); + jint count = (is_static ? JvNumStaticFields (clazz) : JvNumInstanceFields (clazz)); @@ -1078,12 +1083,11 @@ _Jv_JNI_GetAnyFieldID (JNIEnv *env, jclass clazz, : JvGetFirstInstanceField (clazz)); for (jint i = 0; i < count; ++i) { - // The field is resolved as a side effect of class - // initialization. - JvAssert (field->isResolved ()); - _Jv_Utf8Const *f_name = field->getNameUtf8Const(clazz); + // The field might be resolved or it might not be. It + // is much simpler to always resolve it. + _Jv_ResolveField (field, loader); if (_Jv_equalUtf8Consts (f_name, a_name) && field->getClass() == field_class) return field; diff --git a/libjava/resolve.cc b/libjava/resolve.cc index 4a37365c94a..b0a0565e32e 100644 --- a/libjava/resolve.cc +++ b/libjava/resolve.cc @@ -1,6 +1,6 @@ // resolve.cc - Code for linking and resolving classes and pool entries. -/* Copyright (C) 1999, 2000 Free Software Foundation +/* Copyright (C) 1999, 2000, 2001 Free Software Foundation This file is part of libgcj. @@ -32,6 +32,17 @@ details. */ #include #include +void +_Jv_ResolveField (_Jv_Field *field, java::lang::ClassLoader *loader) +{ + if (! field->isResolved ()) + { + _Jv_Utf8Const *sig = (_Jv_Utf8Const*)field->type; + field->type = _Jv_FindClassFromSignature (sig->data, loader); + field->flags &= ~_Jv_FIELD_UNRESOLVED_FLAG; + } +} + #ifdef INTERPRETER static void throw_internal_error (char *msg) @@ -361,17 +372,6 @@ _Jv_SearchMethodInClass (jclass cls, jclass klass, return 0; } -void -_Jv_ResolveField (_Jv_Field *field, java::lang::ClassLoader *loader) -{ - if (! field->isResolved ()) - { - _Jv_Utf8Const *sig = (_Jv_Utf8Const*)field->type; - field->type = _Jv_FindClassFromSignature (sig->data, loader); - field->flags &= ~_Jv_FIELD_UNRESOLVED_FLAG; - } -} - /** FIXME: this is a terribly inefficient algorithm! It would improve things if compiled classes to know vtable offset, and _Jv_Method had a field for this. -- 2.30.2