class.c (layout_class): Don't lay the superclass out if it's already being laid out.
authorAlexandre Petit-Bianco <apbianco@cygnus.com>
Wed, 24 Jan 2001 08:08:36 +0000 (08:08 +0000)
committerAlexandre Petit-Bianco <apbianco@gcc.gnu.org>
Wed, 24 Jan 2001 08:08:36 +0000 (00:08 -0800)
2001-01-23  Alexandre Petit-Bianco  <apbianco@cygnus.com>

* class.c (layout_class): Don't lay the superclass out if it's
already being laid out.
* jcf-parse.c (handle_innerclass_attribute): New function.
(HANDLE_INNERCLASSES_ATTRIBUTE): Invoke
handle_innerclasses_attribute.
(jcf_parse): Don't load an innerclasses if it's already being
laid out.
* jcf-write.c (append_innerclass_attribute_entry): Static
`anonymous_name' and its initialization deleted. `ocii' and `ini'
to be zero for anonymous classes.

2001-01-23  Alexandre Petit-Bianco  <apbianco@cygnus.com>

* class.c (set_constant_value): Set DECL_FIELD_FINAL_IUD if
necessary.
* jcf-parse.c (set_source_filename): Use
MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC if necessary.

2001-01-23  Alexandre Petit-Bianco  <apbianco@cygnus.com>

* expr.c (build_jni_stub): Set DECL_CONTEXT on `meth_var' so it
gets a unique asm name.

2001-01-23  Alexandre Petit-Bianco  <apbianco@cygnus.com>

* jcf-parse.c (HANDLE_END_METHODS): Nullify current_method.
(HANDLE_START_FIELD): Invoke MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC
if necessary.
(HANDLE_SYNTHETIC_ATTRIBUTE): New macro.
* jcf-reader.c (get_attribute): Handle `Synthetic' attribute.
* parse.y (lookup_package_type_and_set_next): Deleted.
(resolve_package): Removed unnecessary code.
(find_applicable_accessible_methods_list): `finit$' can't be
  inherited.
* verify.c (pop_argument_types): Added missing prototype.

(http://gcc.gnu.org/ml/gcc-patches/2001-01/msg01812.html)

From-SVN: r39230

gcc/java/ChangeLog
gcc/java/class.c
gcc/java/expr.c
gcc/java/jcf-parse.c
gcc/java/jcf-reader.c
gcc/java/jcf-write.c
gcc/java/parse.y
gcc/java/verify.c

index 912d12652c8070ead706bd8f2d66b9f7c0d5ee64..c610918465c2a36d713902aa41244da52ba1ffee 100644 (file)
@@ -1,3 +1,41 @@
+2001-01-23  Alexandre Petit-Bianco  <apbianco@cygnus.com>
+
+       * class.c (layout_class): Don't lay the superclass out if it's
+       already being laid out.
+       * jcf-parse.c (handle_innerclass_attribute): New function.
+       (HANDLE_INNERCLASSES_ATTRIBUTE): Invoke
+       handle_innerclasses_attribute.
+       (jcf_parse): Don't load an innerclasses if it's already being
+       laid out.
+       * jcf-write.c (append_innerclass_attribute_entry): Static
+       `anonymous_name' and its initialization deleted. `ocii' and `ini'
+       to be zero for anonymous classes.
+
+2001-01-23  Alexandre Petit-Bianco  <apbianco@cygnus.com>
+
+       * class.c (set_constant_value): Set DECL_FIELD_FINAL_IUD if
+       necessary.
+       * jcf-parse.c (set_source_filename): Use
+       MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC if necessary.
+
+2001-01-23  Alexandre Petit-Bianco  <apbianco@cygnus.com>
+
+       * expr.c (build_jni_stub): Set DECL_CONTEXT on `meth_var' so it
+       gets a unique asm name.
+
+2001-01-23  Alexandre Petit-Bianco  <apbianco@cygnus.com>
+
+       * jcf-parse.c (HANDLE_END_METHODS): Nullify current_method.
+       (HANDLE_START_FIELD): Invoke MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC
+       if necessary.
+       (HANDLE_SYNTHETIC_ATTRIBUTE): New macro.
+       * jcf-reader.c (get_attribute): Handle `Synthetic' attribute.
+       * parse.y (lookup_package_type_and_set_next): Deleted.
+       (resolve_package): Removed unnecessary code.
+       (find_applicable_accessible_methods_list): `finit$' can't be
+       inherited.
+       * verify.c (pop_argument_types): Added missing prototype.
+
 2001-01-23  Bryce McKinlay  <bryce@albatross.co.nz>
 
        * config-lang.in: Disable java by default.
index f98a5d75bb452f8aefac21881cec5ea9d9b6b078..3d88143d36bc4aabef2fcaa2c626e5f09b513bdc 100644 (file)
@@ -743,7 +743,11 @@ set_constant_value (field, constant)
     warning ("duplicate ConstanValue atribute for field '%s'",
             IDENTIFIER_POINTER (DECL_NAME (field)));
   else
-    DECL_INITIAL (field) = constant;
+    {
+      DECL_INITIAL (field) = constant;
+      if (FIELD_FINAL (field))
+       DECL_FIELD_FINAL_IUD (field) = 1;
+    }
 }
 
 /* Count the number of Unicode chars encoded in a given Ut8 string. */
@@ -1655,7 +1659,7 @@ layout_class (this_class)
     }
   CLASS_BEING_LAIDOUT (this_class) = 1;
 
-  if (super_class)
+  if (super_class && !CLASS_BEING_LAIDOUT (super_class))
     {
       tree maybe_super_class 
        = maybe_layout_super_class (super_class, this_class);
index 8dadacb35a4917ea0456e2584c2dc3d0e3ca8247..f42cc4510043542019ba9038f619aea73ba5b147 100644 (file)
@@ -2024,6 +2024,7 @@ build_jni_stub (method)
   TREE_STATIC (meth_var) = 1;
   TREE_PUBLIC (meth_var) = 0;
   DECL_EXTERNAL (meth_var) = 0;
+  DECL_CONTEXT (meth_var) = method;
   make_decl_rtl (meth_var, NULL);
   meth_var = pushdecl_top_level (meth_var);
 
index a4178c016d7de95739fca627678de16f9aaf065c..10baf59dc5bdc1d927e1b58b660ee85a843a9301 100644 (file)
@@ -85,6 +85,7 @@ static tree parse_roots[3] = { NULL_TREE, NULL_TREE, NULL_TREE };
 static struct JCF main_jcf[1];
 
 /* Declarations of some functions used here.  */
+static void handle_innerclass_attribute PARAMS ((int count, JCF *));
 static tree give_name_to_class PARAMS ((JCF *jcf, int index));
 static void parse_zip_file_entries PARAMS ((void));
 static void process_zip_dir PARAMS ((FILE *));
@@ -158,7 +159,10 @@ set_source_filename (jcf, index)
 { int sig_index = SIGNATURE; \
   current_field = add_field (current_class, get_name_constant (jcf, NAME), \
                             parse_signature (jcf, sig_index), ACCESS_FLAGS); \
- set_java_signature (TREE_TYPE (current_field), JPOOL_UTF (jcf, sig_index)); }
+ set_java_signature (TREE_TYPE (current_field), JPOOL_UTF (jcf, sig_index)); \
+ if ((ACCESS_FLAGS) & ACC_FINAL) \
+   MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC (current_field); \
+}
 
 #define HANDLE_END_FIELDS() \
   (current_field = NULL_TREE)
@@ -182,7 +186,8 @@ set_source_filename (jcf, index)
 
 #define HANDLE_END_METHODS() \
 { tree handle_type = CLASS_TO_HANDLE_TYPE (current_class); \
-  if (handle_type != current_class) layout_type (handle_type); }
+  if (handle_type != current_class) layout_type (handle_type); \
+  current_method = NULL_TREE; }
 
 #define HANDLE_CODE_ATTRIBUTE(MAX_STACK, MAX_LOCALS, CODE_LENGTH) \
 { DECL_MAX_STACK (current_method) = (MAX_STACK); \
@@ -214,27 +219,16 @@ set_source_filename (jcf, index)
 
 /* Link seen inner classes to their outer context and register the
    inner class to its outer context. They will be later loaded.  */
-#define HANDLE_INNERCLASSES_ATTRIBUTE(COUNT)                             \
-{                                                                        \
-  int c = (count);                                                       \
-  while (c--)                                                            \
-    {                                                                    \
-      tree class = get_class_constant (jcf, JCF_readu2 (jcf));           \
-      tree decl = TYPE_NAME (class);                                     \
-      if (DECL_P (decl) && !CLASS_COMPLETE_P (decl))                     \
-       {                                                                 \
-         tree outer = TYPE_NAME (get_class_constant (jcf,                \
-                                                     JCF_readu2 (jcf))); \
-         tree alias = get_name_constant (jcf, JCF_readu2 (jcf));         \
-         JCF_SKIP (jcf, 2);                                              \
-         DECL_CONTEXT (decl) = outer;                                    \
-         DECL_INNER_CLASS_LIST (outer) =                                 \
-           tree_cons (decl, alias, DECL_INNER_CLASS_LIST (outer));       \
-         CLASS_COMPLETE_P (decl) = 1;                                    \
-       }                                                                 \
-      else                                                               \
-       JCF_SKIP (jcf, 6);                                                \
-    }                                                                    \
+#define HANDLE_INNERCLASSES_ATTRIBUTE(COUNT) \
+  handle_innerclass_attribute (COUNT, jcf)
+
+#define HANDLE_SYNTHETIC_ATTRIBUTE()                                   \
+{                                                                      \
+  /* Irrelevant decls should have been nullified by the END macros. */ \
+  if (current_method)                                                  \
+    DECL_ARTIFICIAL (current_method) = 1;                              \
+  else                                                                 \
+    DECL_ARTIFICIAL (current_field) = 1;                               \
 }
 
 #include "jcf-reader.c"
@@ -440,6 +434,46 @@ get_name_constant (jcf, index)
   return name;
 }
 
+/* Handle reading innerclass attributes. If a non zero entry (denoting
+   a non anonymous entry) is found, We augment the inner class list of
+   the outer context with the newly resolved innerclass.  */
+
+static void
+handle_innerclass_attribute (count, jcf)
+     int count;
+     JCF *jcf;
+{
+  int c = (count);
+  while (c--)
+    {
+      /* Read inner_class_info_index. This may be 0 */
+      int icii = JCF_readu2 (jcf);
+      /* Read outer_class_info_index. If the innerclasses attribute
+        entry isn't a member (like an inner class) the value is 0. */
+      int ocii = JCF_readu2 (jcf);
+      /* Read inner_name_index. If the class we're dealing with is
+        an annonymous class, it must be 0. */
+      int ini = JCF_readu2 (jcf);
+      /* If icii is 0, don't try to read the class. */
+      if (icii >= 0)
+       {
+         tree class = get_class_constant (jcf, icii);
+         tree decl = TYPE_NAME (class);
+          /* Skip reading further if ocii is null */
+          if (DECL_P (decl) && !CLASS_COMPLETE_P (decl) && ocii)
+           {
+             tree outer = TYPE_NAME (get_class_constant (jcf, ocii));
+             tree alias = (ini ? get_name_constant (jcf, ini) : NULL_TREE);
+             DECL_CONTEXT (decl) = outer;
+             DECL_INNER_CLASS_LIST (outer) =
+               tree_cons (decl, alias, DECL_INNER_CLASS_LIST (outer));
+             CLASS_COMPLETE_P (decl) = 1;
+            }
+       }
+      JCF_SKIP (jcf, 2);
+    }
+}
+
 static tree
 give_name_to_class (jcf, i)
      JCF *jcf;
@@ -677,7 +711,12 @@ jcf_parse (jcf)
   /* And if we came across inner classes, load them now. */
   for (current = DECL_INNER_CLASS_LIST (TYPE_NAME (current_class)); current;
        current = TREE_CHAIN (current))
-    load_class (DECL_NAME (TREE_PURPOSE (current)), 1);
+    {
+      tree name = DECL_NAME (TREE_PURPOSE (current));
+      tree decl = IDENTIFIER_GLOBAL_VALUE (name);
+      if (decl && !CLASS_BEING_LAIDOUT (TREE_TYPE (decl)))
+       load_class (name, 1);
+    }
 }
 
 void
index 4db90657d093f951738313d574c16178e638e1c4..f34bddb6e755c5f2a7331a3bb8b64815c31dbd74 100644 (file)
@@ -205,6 +205,13 @@ DEFUN(get_attribute, (jcf),
       HANDLE_INNERCLASSES_ATTRIBUTE (count);
     }
   else
+#endif
+#ifdef HANDLE_SYNTHETIC_ATTRIBUTE
+  if (name_length == 9 && memcmp (name_data, "Synthetic", 9) == 0)
+    {
+      HANDLE_SYNTHETIC_ATTRIBUTE ();
+    }
+  else
 #endif
     {
 #ifdef PROCESS_OTHER_ATTRIBUTE
index b66db937245d5f50ae407adb1db80579874094e6..1106a75953051b6aaf07433eb1cc1110f84160f3 100644 (file)
@@ -3216,27 +3216,24 @@ append_innerclasses_attribute_entry (state, decl, name)
      struct jcf_partial *state;
      tree decl, name;
 {
-  static tree anonymous_name = NULL_TREE;
-  int icii, ocii, ini, icaf;
+  int icii, icaf;
+  int ocii = 0, ini = 0;
   unsigned char *ptr = append_chunk (NULL, 8, state);
 
-  if (!anonymous_name)
+  icii = find_class_constant (&state->cpool, TREE_TYPE (decl));
+
+  /* Sun's implementation seems to generate ocii to 0 for inner
+     classes (which aren't considered members of the class they're
+     in.) The specs are saying that if the class is anonymous,
+     inner_name_index must be zero. */
+  if (!ANONYMOUS_CLASS_P (TREE_TYPE (decl)))
     {
-      anonymous_name = get_identifier ("");
-      ggc_add_tree_root (&anonymous_name, 1);
+      ocii = find_class_constant (&state->cpool, 
+                                 TREE_TYPE (DECL_CONTEXT (decl)));
+      ini = find_utf8_constant (&state->cpool, name);
     }
-
-  icii = find_class_constant (&state->cpool, TREE_TYPE (decl));
-  ocii = find_class_constant (&state->cpool, TREE_TYPE (DECL_CONTEXT (decl))); 
-
-  /* The specs are saying that if the class is anonymous,
-     inner_name_index must be zero. But the implementation makes it
-     point to an empty string. */
-  ini = find_utf8_constant (&state->cpool,
-                           (ANONYMOUS_CLASS_P (TREE_TYPE (decl)) ? 
-                            anonymous_name : name));
   icaf = get_access_flags (decl);
-  
+
   PUT2 (icii); PUT2 (ocii); PUT2 (ini);  PUT2 (icaf);
 }
 
index 73c0496e87790145979e0bf9f7a333113fe6691e..187c5e97c79ed6aa44fad4dbbe4cf75a10658aae 100644 (file)
@@ -113,7 +113,6 @@ static int check_pkg_class_access PARAMS ((tree, tree));
 static void register_package PARAMS ((tree));
 static tree resolve_package PARAMS ((tree, tree *));
 static tree lookup_package_type PARAMS ((const char *, int));
-static tree lookup_package_type_and_set_next PARAMS ((const char *, int, tree *));
 static tree resolve_class PARAMS ((tree, tree, tree, tree));
 static void declare_local_variables PARAMS ((int, tree, tree));
 static void source_start_java_method PARAMS ((tree));
@@ -6822,35 +6821,6 @@ resolve_package (pkg, next)
 
   *next = EXPR_WFL_QUALIFICATION (pkg);
 
-  /* Try the current package. */
-  if (ctxp->package && !strncmp (name, IDENTIFIER_POINTER (ctxp->package),  
-                                IDENTIFIER_LENGTH (ctxp->package)))
-    {
-      type_name = 
-       lookup_package_type_and_set_next (name, 
-                                         IDENTIFIER_LENGTH (ctxp->package), 
-                                         next );
-      if (type_name)
-       return type_name;
-    }
-
-  /* Search in imported package */
-  for (current = ctxp->import_list; current; current = TREE_CHAIN (current))
-    {
-      tree current_pkg_name = EXPR_WFL_NODE (TREE_PURPOSE (current));
-      int len = IDENTIFIER_LENGTH (current_pkg_name);
-      if (!strncmp (name, IDENTIFIER_POINTER (current_pkg_name), len))
-       {
-         tree left, dummy;
-         
-         breakdown_qualified (&left, &dummy, current_pkg_name);
-         len = IDENTIFIER_LENGTH (left);
-         type_name = lookup_package_type_and_set_next (name, len, next);
-         if (type_name)
-           break;
-       }
-    }
-
   /* Try to progressively construct a type name */
   if (TREE_CODE (pkg) == EXPR_WITH_FILE_LOCATION)
     for (acc = NULL_TREE, current = EXPR_WFL_QUALIFICATION (pkg); 
@@ -6870,27 +6840,6 @@ resolve_package (pkg, next)
   return type_name;
 }
 
-static tree
-lookup_package_type_and_set_next (name, len, next)
-     const char *name;
-     int len;
-     tree *next;
-{
-  const char *ptr;
-  tree type_name = lookup_package_type (name, len);
-
-  if (!type_name)
-    return NULL;
-  
-  ptr = IDENTIFIER_POINTER (type_name);
-  while (ptr && (ptr = strchr (ptr, '.'))) 
-    {
-      *next = TREE_CHAIN (*next);
-      ptr++;
-    }
-  return type_name;
-}
-
 static tree
 lookup_package_type (name, from)
      const char *name;
@@ -10559,6 +10508,16 @@ find_applicable_accessible_methods_list (lc, class, name, arglist)
       search_applicable_methods_list (lc, TYPE_METHODS (class), 
                                      name, arglist, &list, &all_list);
 
+      /* When looking finit$, we turn LC to 1 so that we only search
+        in class. Note that we should have found something at
+        this point. */
+      if (ID_FINIT_P (name))
+       {
+         lc = 1;
+         if (!list)
+           fatal ("finit$ not found in class -- find_applicable_accessible_methods_list");
+       }
+
       /* We must search all interfaces of this class */
       if (!lc)
       {
index 3f24391cecce3ce6ab6b851b86a871a594379ccb..f25fff12bd881d0bf87e6897b051df850b0928e4 100644 (file)
@@ -38,6 +38,7 @@ static tree merge_types PARAMS ((tree, tree));
 static const char *check_pending_block PARAMS ((tree));
 static void type_stack_dup PARAMS ((int, int));
 static int start_pc_cmp PARAMS ((const PTR, const PTR));
+static char *pop_argument_types PARAMS ((tree));
 
 extern int stack_pointer;