diff options
author | tromey <tromey@138bc75d-0d04-0410-961f-82ee72b054a4> | 2005-06-24 22:48:33 +0000 |
---|---|---|
committer | tromey <tromey@138bc75d-0d04-0410-961f-82ee72b054a4> | 2005-06-24 22:48:33 +0000 |
commit | 0e306e0a8846851477785f3b33c99512b26ab783 (patch) | |
tree | de416528940c92c7487c2e3625d257a047026d0d /libjava | |
parent | f17c1d00667e1ba9c80876a618ab047076e13db7 (diff) | |
download | gcc-0e306e0a8846851477785f3b33c99512b26ab783.tar.gz |
* java/lang/natClassLoader.cc (_Jv_UnregisterClass): Handle case
where class' name is NULL.
(_Jv_FindClass): Don't wait for class state.
* java/lang/natVMClassLoader.cc (defineClass): Only unregister if
name found.
* include/java-interp.h (_Jv_DefineClass): Updated.
* defineclass.cc (_Jv_DefineClass): Added 'name_result' argument.
(struct _Jv_ClassReader): Likewise.
(found_name): New field.
(handleClassBegin): Set *found_name.
(_Jv_VerifyMethodSignature): Handle case where ptr==NULL.
(handleClassBegin): Throw error if super class not set.
(read_methods): Correctly call check_tag and prepare_pool_entry.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@101301 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'libjava')
-rw-r--r-- | libjava/ChangeLog | 16 | ||||
-rw-r--r-- | libjava/defineclass.cc | 40 | ||||
-rw-r--r-- | libjava/include/java-interp.h | 3 | ||||
-rw-r--r-- | libjava/java/lang/natClassLoader.cc | 10 | ||||
-rw-r--r-- | libjava/java/lang/natVMClassLoader.cc | 6 |
5 files changed, 53 insertions, 22 deletions
diff --git a/libjava/ChangeLog b/libjava/ChangeLog index 51820665d2a..fca7044704c 100644 --- a/libjava/ChangeLog +++ b/libjava/ChangeLog @@ -1,5 +1,21 @@ 2005-06-24 Tom Tromey <tromey@redhat.com> + * java/lang/natClassLoader.cc (_Jv_UnregisterClass): Handle case + where class' name is NULL. + (_Jv_FindClass): Don't wait for class state. + * java/lang/natVMClassLoader.cc (defineClass): Only unregister if + name found. + * include/java-interp.h (_Jv_DefineClass): Updated. + * defineclass.cc (_Jv_DefineClass): Added 'name_result' argument. + (struct _Jv_ClassReader): Likewise. + (found_name): New field. + (handleClassBegin): Set *found_name. + (_Jv_VerifyMethodSignature): Handle case where ptr==NULL. + (handleClassBegin): Throw error if super class not set. + (read_methods): Correctly call check_tag and prepare_pool_entry. + +2005-06-24 Tom Tromey <tromey@redhat.com> + * boehm.cc (_Jv_MarkObj): Handle case where field's type is NULL. 2005-06-24 Tom Tromey <tromey@redhat.com> diff --git a/libjava/defineclass.cc b/libjava/defineclass.cc index 7564957dc43..e0e209cbfd2 100644 --- a/libjava/defineclass.cc +++ b/libjava/defineclass.cc @@ -70,7 +70,8 @@ static void throw_class_circularity_error (jstring msg) * public or private members here. */ -struct _Jv_ClassReader { +struct _Jv_ClassReader +{ // do verification? Currently, there is no option to disable this. // This flag just controls the verificaiton done by the class loader; @@ -104,6 +105,9 @@ struct _Jv_ClassReader { // the classes associated interpreter data. _Jv_InterpClass *def_interp; + // The name we found. + _Jv_Utf8Const **found_name; + /* check that the given number of input bytes are available */ inline void check (int num) { @@ -219,7 +223,8 @@ struct _Jv_ClassReader { } _Jv_ClassReader (jclass klass, jbyteArray data, jint offset, jint length, - java::security::ProtectionDomain *pd) + java::security::ProtectionDomain *pd, + _Jv_Utf8Const **name_result) { if (klass == 0 || length < 0 || offset+length > data->length) throw_internal_error ("arguments to _Jv_DefineClass"); @@ -229,6 +234,7 @@ struct _Jv_ClassReader { len = length; pos = 0; def = klass; + found_name = name_result; def->size_in_bytes = -1; def->vtable_method_count = -1; @@ -279,11 +285,15 @@ struct _Jv_ClassReader { */ }; +// Note that *NAME_RESULT will only be set if the class is registered +// with the class loader. This is how the caller can know whether +// unregistration is require. void _Jv_DefineClass (jclass klass, jbyteArray data, jint offset, jint length, - java::security::ProtectionDomain *pd) + java::security::ProtectionDomain *pd, + _Jv_Utf8Const **name_result) { - _Jv_ClassReader reader (klass, data, offset, length, pd); + _Jv_ClassReader reader (klass, data, offset, length, pd, name_result); reader.parse(); /* that's it! */ @@ -499,9 +509,9 @@ void _Jv_ClassReader::read_methods () int attributes_count = read2u (); check_tag (name_index, JV_CONSTANT_Utf8); - prepare_pool_entry (descriptor_index, JV_CONSTANT_Utf8); + prepare_pool_entry (name_index, JV_CONSTANT_Utf8); - check_tag (name_index, JV_CONSTANT_Utf8); + check_tag (descriptor_index, JV_CONSTANT_Utf8); prepare_pool_entry (descriptor_index, JV_CONSTANT_Utf8); handleMethod (i, access_flags, name_index, @@ -930,11 +940,11 @@ _Jv_ClassReader::handleClassBegin (int access_flags, int this_class, int super_c pool_data[this_class].clazz = def; pool_tags[this_class] = JV_CONSTANT_ResolvedClass; - if (super_class == 0 && ! (access_flags & Modifier::INTERFACE)) + if (super_class == 0) { - // FIXME: Consider this carefully! - if (! _Jv_equalUtf8Consts (def->name, java::lang::Object::class$.name)) - throw_no_class_def_found_error ("loading java.lang.Object"); + // Note that this is ok if we are defining java.lang.Object. + // But there is no way to have this class be interpreted. + throw_class_format_error ("no superclass reference"); } def->state = JV_STATE_PRELOADING; @@ -946,6 +956,11 @@ _Jv_ClassReader::handleClassBegin (int access_flags, int this_class, int super_c // lock here, as our caller has acquired it. _Jv_RegisterInitiatingLoader (def, def->loader); + // Note that we found a name so that unregistration can happen if + // needed. + *found_name = def->name; + + jclass the_super = NULL; if (super_class != 0) { // Load the superclass. @@ -953,8 +968,7 @@ _Jv_ClassReader::handleClassBegin (int access_flags, int this_class, int super_c _Jv_Utf8Const* super_name = pool_data[super_class].utf8; // Load the superclass using our defining loader. - jclass the_super = _Jv_FindClass (super_name, - def->loader); + jclass the_super = _Jv_FindClass (super_name, def->loader); // This will establish that we are allowed to be a subclass, // and check for class circularity error. @@ -1547,7 +1561,7 @@ _Jv_VerifyMethodSignature (_Jv_Utf8Const*sig) while (ptr && UTF8_PEEK (ptr, limit) != ')') ptr = _Jv_VerifyOne (ptr, limit, false); - if (UTF8_GET (ptr, limit) != ')') + if (! ptr || UTF8_GET (ptr, limit) != ')') return false; // get the return type diff --git a/libjava/include/java-interp.h b/libjava/include/java-interp.h index 061520013d7..5155557c769 100644 --- a/libjava/include/java-interp.h +++ b/libjava/include/java-interp.h @@ -36,7 +36,8 @@ struct _Jv_ResolvedMethod; void _Jv_InitInterpreter (); void _Jv_DefineClass (jclass, jbyteArray, jint, jint, - java::security::ProtectionDomain *); + java::security::ProtectionDomain *, + _Jv_Utf8Const **); void _Jv_InitField (jobject, jclass, int); void * _Jv_AllocMethodInvocation (jsize size); diff --git a/libjava/java/lang/natClassLoader.cc b/libjava/java/lang/natClassLoader.cc index fb3515b5a78..43016bf5e63 100644 --- a/libjava/java/lang/natClassLoader.cc +++ b/libjava/java/lang/natClassLoader.cc @@ -107,6 +107,10 @@ _Jv_FindClassInCache (_Jv_Utf8Const *name) void _Jv_UnregisterClass (jclass the_class) { + // This can happen if the class could not be defined properly. + if (! the_class->name) + return; + JvSynchronize sync (&java::lang::Class::class$); jint hash = HASH_UTF(the_class->name); @@ -328,12 +332,6 @@ _Jv_FindClass (_Jv_Utf8Const *name, java::lang::ClassLoader *loader) } } } - else - { - // We need classes to be in the hash while we're loading, so - // that they can refer to themselves. - _Jv_Linker::wait_for_state (klass, JV_STATE_LOADED); - } return klass; } diff --git a/libjava/java/lang/natVMClassLoader.cc b/libjava/java/lang/natVMClassLoader.cc index 2e7b90da789..bffbfc067db 100644 --- a/libjava/java/lang/natVMClassLoader.cc +++ b/libjava/java/lang/natVMClassLoader.cc @@ -71,16 +71,18 @@ java::lang::VMClassLoader::defineClass (java::lang::ClassLoader *loader, klass->name = name2; } + _Jv_Utf8Const *found_name = NULL; try { - _Jv_DefineClass (klass, data, offset, length, pd); + _Jv_DefineClass (klass, data, offset, length, pd, &found_name); } catch (java::lang::Throwable *ex) { klass->state = JV_STATE_ERROR; klass->notifyAll (); - _Jv_UnregisterInitiatingLoader (klass, klass->loader); + if (found_name != NULL) + _Jv_UnregisterInitiatingLoader (klass, klass->loader); // If EX is not a ClassNotFoundException, that's ok, because we // account for the possibility in defineClass(). |