diff options
author | Tom Tromey <tromey@redhat.com> | 2003-08-12 20:34:51 +0000 |
---|---|---|
committer | Tom Tromey <tromey@gcc.gnu.org> | 2003-08-12 20:34:51 +0000 |
commit | aecf41099bac0258050c052bdc1892e8b4a5d145 (patch) | |
tree | b0eccc2bad8dc4ad0fc0c2540ee347467640fdec /gcc/java/class.c | |
parent | b9172475adce3fec9e36fe6b98eeedba31c0d1f0 (diff) | |
download | gcc-aecf41099bac0258050c052bdc1892e8b4a5d145.zip gcc-aecf41099bac0258050c052bdc1892e8b4a5d145.tar.gz gcc-aecf41099bac0258050c052bdc1892e8b4a5d145.tar.bz2 |
parse.y (java_check_regular_methods): Typo fixes.
* parse.y (java_check_regular_methods): Typo fixes. Call
check_interface_throws_clauses. Use
check_concrete_throws_clauses.
(check_interface_throws_clauses): New function.
(check_concrete_throws_clauses): New function.
(hack_is_accessible_p): New function.
(find_most_specific_methods_list): Added FIXME.
* typeck.c (lookup_do): Use `flags' argument to decide what to
do. Reimplemented.
(lookup_argument_method_generic): New function.
(lookup_argument_method2): Removed.
* jcf.h (ACC_INVISIBLE): New define.
* jcf-write.c (generate_classfile): Skip invisible methods.
* class.c (add_miranda_methods): New function.
(layout_class_methods): Use it.
(get_access_flags_from_decl): Use ACC_INVISIBLE.
* java-tree.h (METHOD_INVISIBLE): New define.
(lang_decl_func) [invisible]: New field.
(lookup_argument_method_generic): Declare.
(SEARCH_INTERFACE): New define.
(SEARCH_SUPER): Likewise.
(SEARCH_ONLY_INTERFACE): Likewise.
(SEARCH_VISIBLE): Likewise.
(lookup_argument_method2): Removed declaration.
From-SVN: r70388
Diffstat (limited to 'gcc/java/class.c')
-rw-r--r-- | gcc/java/class.c | 74 |
1 files changed, 67 insertions, 7 deletions
diff --git a/gcc/java/class.c b/gcc/java/class.c index fbec8d0..620a8a2 100644 --- a/gcc/java/class.c +++ b/gcc/java/class.c @@ -57,6 +57,7 @@ static tree get_dispatch_table (tree, tree); static int supers_all_compiled (tree type); static void add_interface_do (tree, tree, int); static tree maybe_layout_super_class (tree, tree); +static void add_miranda_methods (tree, tree); static int assume_compiled (const char *); static tree build_method_symbols_entry (tree); @@ -1034,6 +1035,8 @@ get_access_flags_from_decl (tree decl) access_flags |= ACC_ABSTRACT; if (METHOD_STRICTFP (decl)) access_flags |= ACC_STRICT; + if (METHOD_INVISIBLE (decl)) + access_flags |= ACC_INVISIBLE; return access_flags; } abort (); @@ -1747,14 +1750,14 @@ layout_class (tree this_class) { tree super_class = CLASSTYPE_SUPER (this_class); tree field; - + class_list = tree_cons (this_class, NULL_TREE, class_list); if (CLASS_BEING_LAIDOUT (this_class)) { char buffer [1024]; char *report; tree current; - + sprintf (buffer, " with `%s'", IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (this_class)))); obstack_grow (&temporary_obstack, buffer, strlen (buffer)); @@ -1808,8 +1811,9 @@ layout_class (tree this_class) layout_type (this_class); - /* Also recursively load/layout any superinterfaces, but only if class was - loaded from bytecode. The source parser will take care of this itself. */ + /* Also recursively load/layout any superinterfaces, but only if + class was loaded from bytecode. The source parser will take care + of this itself. */ if (!CLASS_FROM_SOURCE_P (this_class)) { tree basetype_vec = TYPE_BINFO_BASETYPES (this_class); @@ -1837,14 +1841,61 @@ layout_class (tree this_class) } } - /* Convert the size back to an SI integer value */ - TYPE_SIZE_UNIT (this_class) = + /* Convert the size back to an SI integer value. */ + TYPE_SIZE_UNIT (this_class) = fold (convert (int_type_node, TYPE_SIZE_UNIT (this_class))); CLASS_BEING_LAIDOUT (this_class) = 0; class_list = TREE_CHAIN (class_list); } +static void +add_miranda_methods (tree base_class, tree search_class) +{ + tree basetype_vec = TYPE_BINFO_BASETYPES (search_class); + int i, n = TREE_VEC_LENGTH (basetype_vec); + for (i = 1; i < n; ++i) + { + tree method_decl; + tree elt = TREE_VEC_ELT (basetype_vec, i); + if (elt == NULL_TREE) + break; + elt = BINFO_TYPE (elt); + + /* Note that order matters here. However, all the base classes + will have been laid out at this point, so the order will + always be correct. Also, this code must match similar layout + code in the runtime. */ + for (method_decl = TYPE_METHODS (elt); + method_decl; method_decl = TREE_CHAIN (method_decl)) + { + tree sig, override; + + /* An interface can have <clinit>. */ + if (ID_CLINIT_P (DECL_NAME (method_decl))) + continue; + + sig = build_java_argument_signature (TREE_TYPE (method_decl)); + override = lookup_argument_method (base_class, + DECL_NAME (method_decl), sig); + if (override == NULL_TREE) + { + /* Found a Miranda method. Add it. */ + tree new_method; + sig = build_java_signature (TREE_TYPE (method_decl)); + new_method + = add_method (base_class, + get_access_flags_from_decl (method_decl), + DECL_NAME (method_decl), sig); + METHOD_INVISIBLE (new_method) = 1; + } + } + + /* Try superinterfaces. */ + add_miranda_methods (base_class, elt); + } +} + void layout_class_methods (tree this_class) { @@ -1866,11 +1917,20 @@ layout_class_methods (tree this_class) else dtable_count = integer_zero_node; + if (CLASS_ABSTRACT (TYPE_NAME (this_class))) + { + /* An abstract class can have methods which are declared only in + an implemented interface. These are called "Miranda + methods". We make a dummy method entry for such methods + here. */ + add_miranda_methods (this_class, this_class); + } + TYPE_METHODS (this_class) = nreverse (TYPE_METHODS (this_class)); for (method_decl = TYPE_METHODS (this_class); method_decl; method_decl = TREE_CHAIN (method_decl)) - dtable_count = layout_class_method (this_class, super_class, + dtable_count = layout_class_method (this_class, super_class, method_decl, dtable_count); TYPE_NVIRTUALS (this_class) = dtable_count; |