[PCH] discriminators for java lang_* structures
Geoffrey Keating
geoffk@romulus.sfbay.redhat.com
Fri Apr 26 00:55:00 GMT 2002
This patch adds discriminators to the java lang_type and lang_decl
structures, so that the GC mechanism can work out where the pointers
are.
Bootstrapped & tested on i686-pc-linux-gnu with GC checking.
--
Geoff Keating <geoffk@redhat.com>
===File ~/patches/pchbranch-javadesc.patch==================
2002-04-11 Geoffrey Keating <geoffk@redhat.com>
* java-tree.h (MAYBE_CREATE_VAR_LANG_DECL_SPECIFIC): Set
descriminator for DECL_LANG_SPECIFIC.
(struct lang_decl_func): Rename from struct lang_decl.
(enum lang_decl_desc): New.
(struct lang_decl): Make it a union. Update all the accessor macros.
(struct lang_type): Use gengtype.
* class.c (add_method_1): Set descriminator for DECL_LANG_SPECIFIC.
* decl.c (java_dup_lang_specific_decl): All lang_decl structures
are now the same size.
(lang_mark_tree): Use gengtype to mark TYPE_LANG_SPECIFIC;
use descriminator to mark DECL_LANG_SPECIFIC.
Index: java/class.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/java/class.c,v
retrieving revision 1.124.6.3
diff -p -u -p -r1.124.6.3 class.c
--- java/class.c 6 Apr 2002 00:08:51 -0000 1.124.6.3
+++ java/class.c 25 Apr 2002 22:52:43 -0000
@@ -678,6 +678,7 @@ add_method_1 (handle_class, access_flags
DECL_LANG_SPECIFIC (fndecl)
= (struct lang_decl *) ggc_alloc_cleared (sizeof (struct lang_decl));
+ DECL_LANG_SPECIFIC (fndecl)->desc = LANG_DECL_FUNC;
/* Initialize the static initializer test table. */
hash_table_init (&DECL_FUNCTION_INIT_TEST_TABLE (fndecl),
Index: java/decl.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/java/decl.c,v
retrieving revision 1.116.6.3
diff -p -u -p -r1.116.6.3 decl.c
--- java/decl.c 6 Apr 2002 00:08:52 -0000 1.116.6.3
+++ java/decl.c 25 Apr 2002 22:52:44 -0000
@@ -1551,10 +1551,7 @@ java_dup_lang_specific_decl (node)
if (!DECL_LANG_SPECIFIC (node))
return;
- if (TREE_CODE (node) == VAR_DECL)
- lang_decl_size = sizeof (struct lang_decl_var);
- else
- lang_decl_size = sizeof (struct lang_decl);
+ lang_decl_size = sizeof (struct lang_decl);
x = (struct lang_decl *) ggc_alloc (lang_decl_size);
memcpy (x, DECL_LANG_SPECIFIC (node), lang_decl_size);
DECL_LANG_SPECIFIC (node) = x;
@@ -1851,51 +1848,29 @@ lang_mark_tree (t)
ggc_mark_tree (li->local_value);
ggc_mark_tree (li->utf8_ref);
}
- else if (TREE_CODE (t) == VAR_DECL
- || TREE_CODE (t) == PARM_DECL
- || TREE_CODE (t) == FIELD_DECL)
- {
- struct lang_decl_var *ldv =
- ((struct lang_decl_var *) DECL_LANG_SPECIFIC (t));
- if (ldv)
- {
- ggc_mark (ldv);
- ggc_mark_tree (ldv->slot_chain);
- ggc_mark_tree (ldv->am);
- ggc_mark_tree (ldv->wfl);
- }
- }
- else if (TREE_CODE (t) == FUNCTION_DECL)
- {
- struct lang_decl *ld = DECL_LANG_SPECIFIC (t);
-
- if (ld)
- {
- ggc_mark (ld);
- ggc_mark_tree (ld->wfl);
- ggc_mark_tree (ld->throws_list);
- ggc_mark_tree (ld->function_decl_body);
- ggc_mark_tree (ld->called_constructor);
- ggc_mark_tree (ld->inner_access);
- ggc_mark_tree_hash_table (&ld->init_test_table);
- ggc_mark_tree_hash_table (&ld->ict);
- ggc_mark_tree (ld->smic);
- }
- }
else if (TYPE_P (t))
+ gt_ggc_m_lang_type (TYPE_LANG_SPECIFIC (t));
+ else if (DECL_P (t))
{
- struct lang_type *lt = TYPE_LANG_SPECIFIC (t);
-
- if (lt)
+ struct lang_decl * const x = DECL_LANG_SPECIFIC (t);
+ if (ggc_test_and_set_mark (x))
{
- ggc_mark (lt);
- ggc_mark_tree (lt->signature);
- ggc_mark_tree (lt->cpool_data_ref);
- ggc_mark_tree (lt->finit_stmt_list);
- ggc_mark_tree (lt->clinit_stmt_list);
- ggc_mark_tree (lt->ii_block);
- ggc_mark_tree (lt->dot_class);
- ggc_mark_tree (lt->package_list);
+ unsigned int tag3 = ((*x).desc);
+ if (tag3 == (LANG_DECL_FUNC)) {
+ gt_ggc_m_tree_node ((*x).u.f.wfl);
+ gt_ggc_m_tree_node ((*x).u.f.throws_list);
+ gt_ggc_m_tree_node ((*x).u.f.function_decl_body);
+ gt_ggc_m_tree_node ((*x).u.f.called_constructor);
+ gt_ggc_m_tree_node ((*x).u.f.smic);
+ gt_ggc_m_tree_node ((*x).u.f.inner_access);
+ ggc_mark_tree_hash_table (&(*x).u.f.init_test_table);
+ ggc_mark_tree_hash_table (&(*x).u.f.ict);
+ }
+ if (tag3 == (LANG_DECL_VAR)) {
+ gt_ggc_m_tree_node ((*x).u.v.slot_chain);
+ gt_ggc_m_tree_node ((*x).u.v.am);
+ gt_ggc_m_tree_node ((*x).u.v.wfl);
+ }
}
}
}
Index: java/java-tree.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/java/java-tree.h,v
retrieving revision 1.133.6.3
diff -p -u -p -r1.133.6.3 java-tree.h
--- java/java-tree.h 6 Apr 2002 00:08:52 -0000 1.133.6.3
+++ java/java-tree.h 25 Apr 2002 22:52:44 -0000
@@ -727,41 +727,43 @@ struct lang_identifier
/* For a FUNCTION_DECL, if we are compiling a .class file, then this is
the position in the .class file of the method code.
Specifically, this is the code itself, not the code attribute. */
-#define DECL_CODE_OFFSET(DECL) (DECL_LANG_SPECIFIC(DECL)->code_offset)
+#define DECL_CODE_OFFSET(DECL) (DECL_LANG_SPECIFIC(DECL)->u.f.code_offset)
/* Similarly, the length of the bytecode. */
-#define DECL_CODE_LENGTH(DECL) (DECL_LANG_SPECIFIC(DECL)->code_length)
+#define DECL_CODE_LENGTH(DECL) (DECL_LANG_SPECIFIC(DECL)->u.f.code_length)
/* Similarly, the position of the LineNumberTable attribute. */
#define DECL_LINENUMBERS_OFFSET(DECL) \
- (DECL_LANG_SPECIFIC(DECL)->linenumbers_offset)
+ (DECL_LANG_SPECIFIC(DECL)->u.f.linenumbers_offset)
/* Similarly, the position of the LocalVariableTable attribute
(following the standard attribute header). */
#define DECL_LOCALVARIABLES_OFFSET(DECL) \
- (DECL_LANG_SPECIFIC(DECL)->localvariables_offset)
+ (DECL_LANG_SPECIFIC(DECL)->u.f.localvariables_offset)
-#define DECL_MAX_LOCALS(DECL) (DECL_LANG_SPECIFIC(DECL)->max_locals)
-#define DECL_MAX_STACK(DECL) (DECL_LANG_SPECIFIC(DECL)->max_stack)
+#define DECL_MAX_LOCALS(DECL) (DECL_LANG_SPECIFIC(DECL)->u.f.max_locals)
+#define DECL_MAX_STACK(DECL) (DECL_LANG_SPECIFIC(DECL)->u.f.max_stack)
/* Number of local variable slots needed for the arguments of this function. */
-#define DECL_ARG_SLOT_COUNT(DECL) (DECL_LANG_SPECIFIC(DECL)->arg_slot_count)
+#define DECL_ARG_SLOT_COUNT(DECL) \
+ (DECL_LANG_SPECIFIC(DECL)->u.f.arg_slot_count)
/* Information on declaration location */
-#define DECL_FUNCTION_WFL(DECL) (DECL_LANG_SPECIFIC(DECL)->wfl)
+#define DECL_FUNCTION_WFL(DECL) (DECL_LANG_SPECIFIC(DECL)->u.f.wfl)
/* List of checked thrown exceptions, as specified with the `throws'
keyword */
-#define DECL_FUNCTION_THROWS(DECL) (DECL_LANG_SPECIFIC(DECL)->throws_list)
+#define DECL_FUNCTION_THROWS(DECL) (DECL_LANG_SPECIFIC(DECL)->u.f.throws_list)
/* List of other constructors of the same class that this constructor
calls */
#define DECL_CONSTRUCTOR_CALLS(DECL) \
- (DECL_LANG_SPECIFIC(DECL)->called_constructor)
+ (DECL_LANG_SPECIFIC(DECL)->u.f.called_constructor)
/* When the function is an access function, the DECL it was trying to
access */
#define DECL_FUNCTION_ACCESS_DECL(DECL) \
- (DECL_LANG_SPECIFIC(DECL)->called_constructor)
+ (DECL_LANG_SPECIFIC(DECL)->u.f.called_constructor)
/* The identifier of the access method used to invoke this method from
an inner class. */
#define DECL_FUNCTION_INNER_ACCESS(DECL) \
- (DECL_LANG_SPECIFIC(DECL)->inner_access)
+ (DECL_LANG_SPECIFIC(DECL)->u.f.inner_access)
/* Pointer to the function's current's COMPOUND_EXPR tree (while
completing its body) or the function's block */
-#define DECL_FUNCTION_BODY(DECL) (DECL_LANG_SPECIFIC(DECL)->function_decl_body)
+#define DECL_FUNCTION_BODY(DECL) \
+ (DECL_LANG_SPECIFIC(DECL)->u.f.function_decl_body)
/* How specific the function is (for method selection - Java source
code front-end */
#define DECL_SPECIFIC_COUNT(DECL) DECL_ARG_SLOT_COUNT(DECL)
@@ -770,31 +772,33 @@ struct lang_identifier
boolean decls. The variables are intended to be TRUE when the
class has been initialized in this function, and FALSE otherwise. */
#define DECL_FUNCTION_INIT_TEST_TABLE(DECL) \
- (DECL_LANG_SPECIFIC(DECL)->init_test_table)
+ (DECL_LANG_SPECIFIC(DECL)->u.f.init_test_table)
/* If LOCAL_CLASS_INITIALIZATION_FLAG_P(decl), give class it initializes. */
#define DECL_FUNCTION_INIT_TEST_CLASS(DECL) \
- (((struct lang_decl_var*)DECL_LANG_SPECIFIC(DECL))->slot_chain)
+ (DECL_LANG_SPECIFIC(DECL)->u.v.slot_chain)
/* For each static function decl, itc contains a hash table whose
entries are keyed on class named that are definitively initialized
in DECL. */
#define DECL_FUNCTION_INITIALIZED_CLASS_TABLE(DECL) \
- (DECL_LANG_SPECIFIC(DECL)->ict)
+ (DECL_LANG_SPECIFIC(DECL)->u.f.ict)
/* A list of all the static method calls in the method DECL (if optimizing).
Actually each TREE_VALUE points to a COMPONT_EXPR that wraps the
invoation so we can later patch it. */
#define DECL_FUNCTION_STATIC_METHOD_INVOCATION_COMPOUND(DECL) \
- (DECL_LANG_SPECIFIC(DECL)->smic)
+ (DECL_LANG_SPECIFIC(DECL)->u.f.smic)
/* The Number of Artificial Parameters (NAP) DECL contains. this$<n>
is excluded, because sometimes created as a parameter before the
function decl exists. */
-#define DECL_FUNCTION_NAP(DECL) (DECL_LANG_SPECIFIC(DECL)->nap)
+#define DECL_FUNCTION_NAP(DECL) (DECL_LANG_SPECIFIC(DECL)->u.f.nap)
/* True if DECL is a synthetic ctor. */
#define DECL_FUNCTION_SYNTHETIC_CTOR(DECL) \
- (DECL_LANG_SPECIFIC(DECL)->synthetic_ctor)
-#define DECL_FIXED_CONSTRUCTOR_P(DECL) (DECL_LANG_SPECIFIC(DECL)->fixed_ctor)
+ (DECL_LANG_SPECIFIC(DECL)->u.f.synthetic_ctor)
+#define DECL_FIXED_CONSTRUCTOR_P(DECL) \
+ (DECL_LANG_SPECIFIC(DECL)->u.f.fixed_ctor)
/* A constructor that calls this. */
-#define DECL_INIT_CALLS_THIS(DECL) (DECL_LANG_SPECIFIC(DECL)->init_calls_this)
+#define DECL_INIT_CALLS_THIS(DECL) \
+ (DECL_LANG_SPECIFIC(DECL)->u.f.init_calls_this)
/* True when DECL aliases an outer context local variable. */
#define FIELD_LOCAL_ALIAS(DECL) DECL_LANG_FLAG_6 (DECL)
@@ -857,31 +861,31 @@ struct lang_identifier
/* The slot number for this local variable. */
#define DECL_LOCAL_SLOT_NUMBER(NODE) \
- (((struct lang_decl_var*)DECL_LANG_SPECIFIC(NODE))->slot_number)
+ (DECL_LANG_SPECIFIC(NODE)->u.v.slot_number)
/* The start (bytecode) pc for the valid range of this local variable. */
#define DECL_LOCAL_START_PC(NODE) \
- (((struct lang_decl_var*)DECL_LANG_SPECIFIC(NODE))->start_pc)
+ (DECL_LANG_SPECIFIC(NODE)->u.v.start_pc)
/* The end (bytecode) pc for the valid range of this local variable. */
#define DECL_LOCAL_END_PC(NODE) \
- (((struct lang_decl_var*)DECL_LANG_SPECIFIC(NODE))->end_pc)
+ (DECL_LANG_SPECIFIC(NODE)->u.v.end_pc)
/* For a VAR_DECLor PARM_DECL, used to chain decls with the same
slot_number in decl_map. */
#define DECL_LOCAL_SLOT_CHAIN(NODE) \
- (((struct lang_decl_var*)DECL_LANG_SPECIFIC(NODE))->slot_chain)
+ (DECL_LANG_SPECIFIC(NODE)->u.v.slot_chain)
/* For a FIELD_DECL, holds the name of the access method. Used to
read/write the content of the field from an inner class. */
#define FIELD_INNER_ACCESS(DECL) \
- (((struct lang_decl_var*)DECL_LANG_SPECIFIC(DECL))->am)
+ (DECL_LANG_SPECIFIC(DECL)->u.v.am)
/* Safely tests whether FIELD_INNER_ACCESS exists or not. */
#define FIELD_INNER_ACCESS_P(DECL) \
DECL_LANG_SPECIFIC (DECL) && FIELD_INNER_ACCESS (DECL)
/* True if a final variable was initialized upon its declaration,
or (if a field) in an initializer. Set after definite assignment. */
#define DECL_FIELD_FINAL_IUD(NODE) \
- (((struct lang_decl_var*)DECL_LANG_SPECIFIC(NODE))->final_iud)
+ (DECL_LANG_SPECIFIC(NODE)->u.v.final_iud)
/* The original WFL of a final variable. */
#define DECL_FIELD_FINAL_WFL(NODE) \
- (((struct lang_decl_var*)DECL_LANG_SPECIFIC(NODE))->wfl)
+ (DECL_LANG_SPECIFIC(NODE)->u.v.wfl)
/* True if NODE is a local variable final. */
#define LOCAL_FINAL_P(NODE) (DECL_LANG_SPECIFIC (NODE) && DECL_FINAL (NODE))
/* True if NODE is a final field. */
@@ -892,7 +896,7 @@ struct lang_identifier
/* True if NODE is a class initialization flag. This macro accesses
the flag to read or set it. */
#define LOCAL_CLASS_INITIALIZATION_FLAG(NODE) \
- (((struct lang_decl_var*)DECL_LANG_SPECIFIC(NODE))->cif)
+ (DECL_LANG_SPECIFIC(NODE)->u.v.cif)
/* True if NODE is a class initialization flag. */
#define LOCAL_CLASS_INITIALIZATION_FLAG_P(NODE) \
(DECL_LANG_SPECIFIC (NODE) && LOCAL_CLASS_INITIALIZATION_FLAG(NODE))
@@ -902,7 +906,8 @@ struct lang_identifier
{ \
DECL_LANG_SPECIFIC ((T)) \
= ((struct lang_decl *) \
- ggc_alloc_cleared (sizeof (struct lang_decl_var))); \
+ ggc_alloc_cleared (sizeof (struct lang_decl))); \
+ DECL_LANG_SPECIFIC (T)->desc = LANG_DECL_VAR; \
}
/* A ConstantExpression, after folding and name resolution. */
@@ -919,7 +924,7 @@ struct lang_identifier
#define DECL_BIT_INDEX(DECL) (DECL_CHECK (DECL)->decl.pointer_alias_set)
/* DECL_LANG_SPECIFIC for FUNCTION_DECLs. */
-struct lang_decl
+struct lang_decl_func
{
/* tree chain; not yet used. */
long code_offset;
@@ -927,7 +932,9 @@ struct lang_decl
long linenumbers_offset;
long localvariables_offset;
int arg_slots;
- int max_locals, max_stack, arg_slot_count;
+ int max_locals;
+ int max_stack;
+ int arg_slot_count;
tree wfl; /* Information on the original location */
tree throws_list; /* Exception specified by `throws' */
tree function_decl_body; /* Hold all function's statements */
@@ -969,6 +976,22 @@ struct lang_decl_var
unsigned int cif : 1; /* True: decl is a class initialization flag */
};
+/* This is what 'lang_decl' really points to. */
+
+enum lang_decl_desc {
+ LANG_DECL_FUNC,
+ LANG_DECL_VAR
+};
+
+struct lang_decl
+{
+ enum lang_decl_desc desc;
+ union lang_decl_u {
+ struct lang_decl_func f;
+ struct lang_decl_var v;
+ } u;
+};
+
/* Macro to access fields in `struct lang_type'. */
#define TYPE_SIGNATURE(T) (TYPE_LANG_SPECIFIC(T)->signature)
@@ -996,11 +1019,11 @@ struct lang_decl_var
#define TYPE_PROTECTED_INNER_CLASS(T) (TYPE_LANG_SPECIFIC(T)->poic)
#define TYPE_STRICTFP(T) (TYPE_LANG_SPECIFIC(T)->strictfp)
-struct lang_type
+struct lang_type GTY(())
{
tree signature;
- struct JCF *jcf;
- struct CPool *cpool;
+ struct JCF * GTY ((skip (""))) jcf;
+ struct CPool * GTY ((skip (""))) cpool;
tree cpool_data_ref; /* Cached */
tree finit_stmt_list; /* List of statements finit$ will use */
tree clinit_stmt_list; /* List of statements <clinit> will use */
@@ -1254,10 +1277,10 @@ struct rtx_def * java_lang_expand_expr P
#define METHOD_STATIC(DECL) DECL_LANG_FLAG_2 (DECL)
#define METHOD_FINAL(DECL) DECL_FINAL (DECL)
#define METHOD_SYNCHRONIZED(DECL) DECL_LANG_FLAG_4 (DECL)
-#define METHOD_NATIVE(DECL) (DECL_LANG_SPECIFIC(DECL)->native)
+#define METHOD_NATIVE(DECL) (DECL_LANG_SPECIFIC(DECL)->u.f.native)
#define METHOD_ABSTRACT(DECL) DECL_LANG_FLAG_5 (DECL)
#define METHOD_TRANSIENT(DECL) DECL_LANG_FLAG_6 (DECL)
-#define METHOD_STRICTFP(DECL) (DECL_LANG_SPECIFIC (DECL)->strictfp)
+#define METHOD_STRICTFP(DECL) (DECL_LANG_SPECIFIC (DECL)->u.f.strictfp)
#define JAVA_FILE_P(NODE) TREE_LANG_FLAG_2 (NODE)
#define CLASS_FILE_P(NODE) TREE_LANG_FLAG_3 (NODE)
============================================================
More information about the Gcc-patches
mailing list