[multiple changes]

Tue Nov 24 17:06:38 1998  Per Bothner  <bothner@cygnus.com>
	* (generate_classfile): Always write class access flag with
 	ACC_SUPER set.
Tue Nov 24 16:34:33 1998  Alexandre Petit-Bianco  <apbianco@cygnus.com>
	* class.c (maybe_layout_super_class): New function.
	(layout_class): Reorganized. Loop on class methods dispatched into
 	a new function. Call maybe_layout_super_class.
	(layout_class_methods, layout_class_method): New functions.
	* expr.c (expand_java_NEW): Call layout_class_methods on loaded
 	class.
	(expand_invoke): Likewise.
	* java-tree.h (all_class_list): New global variable declared.
	(layout_class_methods, layout_class_method): New function
 	prototypes.
	(LAYOUT_SEEN_CLASS_METHODS): New macro.
	* jcf-parse.c (all_class_list): New global variable.
	(load_class): Extended what class_or_name can be. Use parser
 	context mechanism to save globals before calling jcf_parse.
	(jcf_parse_source): Don't parse twice if HAS_BEEN_ALREADY_PARSED_P
 	is set on the file name.
	(jcf_parse): Layout class methods when Object is loaded, otherwise
 	record class in all_class_list for delayed method layout.
	(parse_class_file): Use LAYOUT_SEEN_CLASS_METHODS.
	* lang.c (put_decl_node): Decode <init> into the decl context
 	class name.
	* lex.c (java_allocate_new_line): Use xmalloc.
	* parse.h (INCOMPLETE_TYPE_P): Redefined to work with incomplete
 	pointers, not TREE_LIST elements.
	(struct parser_ctxt): Fixed comment indentations, added comments
 	and reordered some fields.
	(java_check_methods): Function prototype removed.
	* parse.y (java_push_parser_context): Use xmalloc.
	(java_parser_context_restore_global): Pop extra pushed ctxp only
 	when there's nothing next.
	(maybe_create_class_interface_decl): Fixed comment, add new
 	created class decl to all_class_list.
	(method_header): Use GET_REAL_TYPE on argument's types.
	(method_declarator): Use GET_REAL_TYPE, change type to the real
 	type in TREE_LIST dependency node. Build argument list with the
 	real type.
	(create_jdep_list): Use xmalloc. Removed allocation error message.
	(obtain_incomplete_type): Fixed leading comment. Broadened
 	incoming argument meaning.
	(register_incomplete_type): Use xmalloc. Removed allocation error
 	message.
	(safe_layout_class): Fixed leading comment.
	(jdep_resolve_class): Reversed if statement condition and switch
 	if and else bodies.
	(resolve_and_layout): Fixed leading comment. Broadened incoming
 	argument meaning.
	(complete_class_report_errors): New local variable name, for
 	clarity. purify_type_name used for all error cases.
	(java_get_real_method_name): Stricter check on constructors.
	(java_check_regular_methods): Reverse methods list only if not
 	already laid out. Layout artificial constructor.
	(java_check_methods): Deleted.
	(source_start_java_method): Obtain incomplete type for patchable
 	method arguments.
	(java_layout_classes): Fixed leading comment. Use
 	LAYOUT_SEEN_CLASS_METHODS, use a loop to check methods. Added else
 	statement to layout operation, reuse LAYOUT_SEEN_CLASS_METHODS
 	before returning. Fixed comments.
	(java_expand_classes): Check for errors up front.
	(patch_method_invocation): Class to search is resolved and laid
 	out.
A step forward truly mixing .class and .java during package
compilation. Includes a Per's patch.

From-SVN: r23834
parent 333a9f0a
Tue Nov 24 17:06:38 1998 Per Bothner <bothner@cygnus.com>
* (generate_classfile): Always write class access flag with
ACC_SUPER set.
Tue Nov 24 16:34:33 1998 Alexandre Petit-Bianco <apbianco@cygnus.com>
* class.c (maybe_layout_super_class): New function.
(layout_class): Reorganized. Loop on class methods dispatched into
a new function. Call maybe_layout_super_class.
(layout_class_methods, layout_class_method): New functions.
* expr.c (expand_java_NEW): Call layout_class_methods on loaded
class.
(expand_invoke): Likewise.
* java-tree.h (all_class_list): New global variable declared.
(layout_class_methods, layout_class_method): New function
prototypes.
(LAYOUT_SEEN_CLASS_METHODS): New macro.
* jcf-parse.c (all_class_list): New global variable.
(load_class): Extended what class_or_name can be. Use parser
context mechanism to save globals before calling jcf_parse.
(jcf_parse_source): Don't parse twice if HAS_BEEN_ALREADY_PARSED_P
is set on the file name.
(jcf_parse): Layout class methods when Object is loaded, otherwise
record class in all_class_list for delayed method layout.
(parse_class_file): Use LAYOUT_SEEN_CLASS_METHODS.
* lang.c (put_decl_node): Decode <init> into the decl context
class name.
* lex.c (java_allocate_new_line): Use xmalloc.
* parse.h (INCOMPLETE_TYPE_P): Redefined to work with incomplete
pointers, not TREE_LIST elements.
(struct parser_ctxt): Fixed comment indentations, added comments
and reordered some fields.
(java_check_methods): Function prototype removed.
* parse.y (java_push_parser_context): Use xmalloc.
(java_parser_context_restore_global): Pop extra pushed ctxp only
when there's nothing next.
(maybe_create_class_interface_decl): Fixed comment, add new
created class decl to all_class_list.
(method_header): Use GET_REAL_TYPE on argument's types.
(method_declarator): Use GET_REAL_TYPE, change type to the real
type in TREE_LIST dependency node. Build argument list with the
real type.
(create_jdep_list): Use xmalloc. Removed allocation error message.
(obtain_incomplete_type): Fixed leading comment. Broadened
incoming argument meaning.
(register_incomplete_type): Use xmalloc. Removed allocation error
message.
(safe_layout_class): Fixed leading comment.
(jdep_resolve_class): Reversed if statement condition and switch
if and else bodies.
(resolve_and_layout): Fixed leading comment. Broadened incoming
argument meaning.
(complete_class_report_errors): New local variable name, for
clarity. purify_type_name used for all error cases.
(java_get_real_method_name): Stricter check on constructors.
(java_check_regular_methods): Reverse methods list only if not
already laid out. Layout artificial constructor.
(java_check_methods): Deleted.
(source_start_java_method): Obtain incomplete type for patchable
method arguments.
(java_layout_classes): Fixed leading comment. Use
LAYOUT_SEEN_CLASS_METHODS, use a loop to check methods. Added else
statement to layout operation, reuse LAYOUT_SEEN_CLASS_METHODS
before returning. Fixed comments.
(java_expand_classes): Check for errors up front.
(patch_method_invocation): Class to search is resolved and laid
out.
Tue Nov 24 12:57:13 1998 Per Bothner <bothner@cygnus.com> Tue Nov 24 12:57:13 1998 Per Bothner <bothner@cygnus.com>
* expr.c (java_lang_expand_expr): Add missing emit_queue. * expr.c (java_lang_expand_expr): Add missing emit_queue.
......
...@@ -910,6 +910,7 @@ expand_java_NEW (type) ...@@ -910,6 +910,7 @@ expand_java_NEW (type)
{ {
if (! CLASS_LOADED_P (type)) if (! CLASS_LOADED_P (type))
load_class (type, 1); load_class (type, 1);
layout_class_methods (type);
push_value (build (CALL_EXPR, promote_type (type), push_value (build (CALL_EXPR, promote_type (type),
build_address_of (alloc_object_node), build_address_of (alloc_object_node),
tree_cons (NULL_TREE, build_class_ref (type), tree_cons (NULL_TREE, build_class_ref (type),
...@@ -1485,6 +1486,7 @@ expand_invoke (opcode, method_ref_index, nargs) ...@@ -1485,6 +1486,7 @@ expand_invoke (opcode, method_ref_index, nargs)
if (TREE_CODE (TYPE_SIZE (self_type)) == ERROR_MARK) if (TREE_CODE (TYPE_SIZE (self_type)) == ERROR_MARK)
fatal ("failed to find class '%s'", self_name); fatal ("failed to find class '%s'", self_name);
} }
layout_class_methods (self_type);
if (method_name == init_identifier_node) if (method_name == init_identifier_node)
method = lookup_java_constructor (CLASS_TO_HANDLE_TYPE (self_type), method = lookup_java_constructor (CLASS_TO_HANDLE_TYPE (self_type),
......
...@@ -112,6 +112,9 @@ extern tree main_class; ...@@ -112,6 +112,9 @@ extern tree main_class;
/* The class we are currently processing. */ /* The class we are currently processing. */
extern tree current_class; extern tree current_class;
/* List of all class DECLs seen so far. */
extern tree all_class_list;
/* Nonzero if we want to automatically do array bounds checking; /* Nonzero if we want to automatically do array bounds checking;
on by default. Use -fno-bounds-check to disable. */ on by default. Use -fno-bounds-check to disable. */
...@@ -483,6 +486,8 @@ extern tree unmangle_classname PROTO ((const char *name, int name_length)); ...@@ -483,6 +486,8 @@ extern tree unmangle_classname PROTO ((const char *name, int name_length));
extern tree parse_signature_string PROTO ((const unsigned char *, int)); extern tree parse_signature_string PROTO ((const unsigned char *, int));
extern tree get_type_from_signature PROTO ((tree)); extern tree get_type_from_signature PROTO ((tree));
extern void layout_class PROTO ((tree)); extern void layout_class PROTO ((tree));
extern tree layout_class_method PROTO ((tree, tree, tree, tree));
extern void layout_class_methods PROTO ((tree));
extern tree make_class (); extern tree make_class ();
extern tree build_class_ref PROTO ((tree)); extern tree build_class_ref PROTO ((tree));
extern tree build_dtable_decl PROTO ((tree)); extern tree build_dtable_decl PROTO ((tree));
...@@ -835,3 +840,10 @@ extern tree *type_map; ...@@ -835,3 +840,10 @@ extern tree *type_map;
if (java_error_count) \ if (java_error_count) \
return; \ return; \
} }
#define LAYOUT_SEEN_CLASS_METHODS() \
{ \
tree current; \
for (current = all_class_list; current; current = TREE_CHAIN (current)) \
layout_class_methods (TREE_TYPE (TREE_VALUE (current))); \
}
...@@ -61,7 +61,10 @@ tree current_class = NULL_TREE; ...@@ -61,7 +61,10 @@ tree current_class = NULL_TREE;
/* The class we started with. */ /* The class we started with. */
tree main_class = NULL_TREE; tree main_class = NULL_TREE;
/* The FIELD_DECL for the current field. */ /* List of all class DECL seen so far. */
tree all_class_list = NULL_TREE;
/* The FIELD_DECL for the current field. */
static tree current_field = NULL_TREE; static tree current_field = NULL_TREE;
/* The METHOD_DECL for the current method. */ /* The METHOD_DECL for the current method. */
...@@ -450,8 +453,7 @@ load_class (class_or_name, verbose) ...@@ -450,8 +453,7 @@ load_class (class_or_name, verbose)
int verbose; int verbose;
{ {
JCF this_jcf, *jcf; JCF this_jcf, *jcf;
tree name = (TREE_CODE (class_or_name) == IDENTIFIER_NODE ? tree name;
class_or_name : DECL_NAME (TYPE_NAME (class_or_name)));
tree save_current_class = current_class; tree save_current_class = current_class;
char *save_input_filename = input_filename; char *save_input_filename = input_filename;
JCF *save_current_jcf = current_jcf; JCF *save_current_jcf = current_jcf;
...@@ -459,6 +461,17 @@ load_class (class_or_name, verbose) ...@@ -459,6 +461,17 @@ load_class (class_or_name, verbose)
if (current_jcf->read_state) if (current_jcf->read_state)
saved_pos = ftell (current_jcf->read_state); saved_pos = ftell (current_jcf->read_state);
/* class_or_name can be the name of the class we want to load */
if (TREE_CODE (class_or_name) == IDENTIFIER_NODE)
name = class_or_name;
/* In some cases, it's a dependency that we process earlier that
we though */
else if (TREE_CODE (class_or_name) == TREE_LIST)
name = TYPE_NAME (TREE_PURPOSE (class_or_name));
/* Or it's a type in the making */
else
name = DECL_NAME (TYPE_NAME (class_or_name));
push_obstacks (&permanent_obstack, &permanent_obstack); push_obstacks (&permanent_obstack, &permanent_obstack);
/* Search in current zip first. */ /* Search in current zip first. */
...@@ -494,10 +507,12 @@ load_class (class_or_name, verbose) ...@@ -494,10 +507,12 @@ load_class (class_or_name, verbose)
if (current_jcf->java_source) if (current_jcf->java_source)
jcf_parse_source (current_jcf); jcf_parse_source (current_jcf);
else { else {
int saved_lineno = lineno; java_parser_context_save_global ();
java_push_parser_context ();
input_filename = current_jcf->filename; input_filename = current_jcf->filename;
jcf_parse (current_jcf); jcf_parse (current_jcf);
lineno = saved_lineno; java_pop_parser_context (0);
java_parser_context_restore_global ();
} }
if (!current_jcf->seen_in_zip) if (!current_jcf->seen_in_zip)
...@@ -524,13 +539,16 @@ jcf_parse_source (jcf) ...@@ -524,13 +539,16 @@ jcf_parse_source (jcf)
java_push_parser_context (); java_push_parser_context ();
input_filename = current_jcf->filename; input_filename = current_jcf->filename;
file = get_identifier (input_filename); file = get_identifier (input_filename);
if (!(finput = fopen (input_filename, "r"))) if (!HAS_BEEN_ALREADY_PARSED_P (file))
fatal ("input file `%s' just disappeared - jcf_parse_source", {
input_filename); if (!(finput = fopen (input_filename, "r")))
parse_source_file (file); fatal ("input file `%s' just disappeared - jcf_parse_source",
if (fclose (finput)) input_filename);
fatal ("can't close input file `%s' stream - jcf_parse_source", parse_source_file (file);
input_filename); if (fclose (finput))
fatal ("can't close input file `%s' stream - jcf_parse_source",
input_filename);
}
java_pop_parser_context (IS_A_COMMAND_LINE_FILENAME_P (file)); java_pop_parser_context (IS_A_COMMAND_LINE_FILENAME_P (file));
java_parser_context_restore_global (); java_parser_context_restore_global ();
} }
...@@ -586,6 +604,11 @@ jcf_parse (jcf) ...@@ -586,6 +604,11 @@ jcf_parse (jcf)
push_obstacks (&permanent_obstack, &permanent_obstack); push_obstacks (&permanent_obstack, &permanent_obstack);
layout_class (current_class); layout_class (current_class);
if (current_class == object_type_node)
layout_class_methods (object_type_node);
else
all_class_list = tree_cons (NULL_TREE,
TYPE_NAME (current_class), all_class_list );
pop_obstacks (); pop_obstacks ();
} }
...@@ -612,6 +635,8 @@ parse_class_file () ...@@ -612,6 +635,8 @@ parse_class_file ()
char *save_input_filename = input_filename; char *save_input_filename = input_filename;
int save_lineno = lineno; int save_lineno = lineno;
LAYOUT_SEEN_CLASS_METHODS ();
input_filename = DECL_SOURCE_FILE (TYPE_NAME (current_class)); input_filename = DECL_SOURCE_FILE (TYPE_NAME (current_class));
lineno = 0; lineno = 0;
debug_start_source_file (input_filename); debug_start_source_file (input_filename);
......
...@@ -2342,7 +2342,8 @@ generate_classfile (clas, state) ...@@ -2342,7 +2342,8 @@ generate_classfile (clas, state)
else else
i = 8 + 2 * total_supers; i = 8 + 2 * total_supers;
ptr = append_chunk (NULL, i, state); ptr = append_chunk (NULL, i, state);
i = get_access_flags (TYPE_NAME (clas)); PUT2 (i); /* acces_flags */ i = get_access_flags (TYPE_NAME (clas)) | ACC_SUPER;
PUT2 (i); /* acces_flags */
i = find_class_constant (&state->cpool, clas); PUT2 (i); /* this_class */ i = find_class_constant (&state->cpool, clas); PUT2 (i); /* this_class */
if (clas == object_type_node) if (clas == object_type_node)
{ {
......
...@@ -358,7 +358,12 @@ put_decl_node (node) ...@@ -358,7 +358,12 @@ put_decl_node (node)
put_decl_string (".", 1); put_decl_string (".", 1);
} }
#endif #endif
put_decl_node (DECL_NAME (node)); if (TREE_CODE (node) == FUNCTION_DECL
&& DECL_NAME (node) == init_identifier_node
&& !DECL_ARTIFICIAL (node) && current_class)
put_decl_node (TYPE_NAME (current_class));
else
put_decl_node (DECL_NAME (node));
if (TREE_CODE (node) == FUNCTION_DECL && TREE_TYPE (node) != NULL_TREE) if (TREE_CODE (node) == FUNCTION_DECL && TREE_TYPE (node) != NULL_TREE)
{ {
int i = 0; int i = 0;
......
...@@ -153,12 +153,12 @@ java_allocate_new_line () ...@@ -153,12 +153,12 @@ java_allocate_new_line ()
if (!ctxp->c_line) if (!ctxp->c_line)
{ {
ctxp->c_line = (struct java_line *)malloc (sizeof (struct java_line)); ctxp->c_line = (struct java_line *)xmalloc (sizeof (struct java_line));
ctxp->c_line->max = JAVA_LINE_MAX; ctxp->c_line->max = JAVA_LINE_MAX;
ctxp->c_line->line = (unicode_t *)malloc ctxp->c_line->line = (unicode_t *)xmalloc
(sizeof (unicode_t)*ctxp->c_line->max); (sizeof (unicode_t)*ctxp->c_line->max);
ctxp->c_line->unicode_escape_p = ctxp->c_line->unicode_escape_p =
(char *)malloc (sizeof (char)*ctxp->c_line->max); (char *)xmalloc (sizeof (char)*ctxp->c_line->max);
ctxp->c_line->white_space_only = 0; ctxp->c_line->white_space_only = 0;
} }
......
...@@ -147,10 +147,10 @@ extern tree stabilize_reference PROTO ((tree)); ...@@ -147,10 +147,10 @@ extern tree stabilize_reference PROTO ((tree));
TYPE_NAME (ptr) = name; \ TYPE_NAME (ptr) = name; \
} }
#define INCOMPLETE_TYPE_P(NODE) \ #define INCOMPLETE_TYPE_P(NODE) \
((TREE_CODE (NODE) == TREE_LIST) \ ((TREE_CODE (NODE) == POINTER_TYPE) \
&& (TREE_CODE (TREE_PURPOSE (NODE)) == POINTER_TYPE) \ && !TREE_TYPE (NODE) \
&& (TREE_TYPE (TREE_PURPOSE (NODE)) == NULL_TREE)) && TREE_CODE (TYPE_NAME (NODE)) == IDENTIFIER_NODE)
/* Set the EMIT_LINE_NOTE flag of a EXPR_WLF to 1 if debug information /* Set the EMIT_LINE_NOTE flag of a EXPR_WLF to 1 if debug information
are requested. Works in the context of a parser rule. */ are requested. Works in the context of a parser rule. */
...@@ -589,13 +589,13 @@ struct parser_ctxt { ...@@ -589,13 +589,13 @@ struct parser_ctxt {
int parser_ccb_indent; /* Keep track of {} indent, parser */ int parser_ccb_indent; /* Keep track of {} indent, parser */
int osb_number; /* Keep track of ['s */ int osb_number; /* Keep track of ['s */
int minus_seen; /* Integral literal overflow */ int minus_seen; /* Integral literal overflow */
int lineno; /* Current lineno */ int lineno; /* Current lineno */
int java_error_flag; /* Report error when true */ int java_error_flag; /* Report error when true */
int deprecated; /* @deprecated tag seen */ int deprecated; /* @deprecated tag seen */
/* This section is defined only if we compile jc1 */ /* This section is defined only if we compile jc1 */
#ifndef JC1_LITE #ifndef JC1_LITE
tree modifier_ctx [11]; /* WFL of modifiers */ tree modifier_ctx [11]; /* WFL of modifiers */
tree current_class; /* Current class */ tree current_class; /* Current class */
tree current_function_decl; /* Current function decl, save/restore */ tree current_function_decl; /* Current function decl, save/restore */
...@@ -609,30 +609,34 @@ struct parser_ctxt { ...@@ -609,30 +609,34 @@ struct parser_ctxt {
tree package; /* Defined package ID */ tree package; /* Defined package ID */
/* Those tow list are saved accross file traversal */
tree incomplete_class; /* List of non-complete classes */ tree incomplete_class; /* List of non-complete classes */
tree current_parsed_class; /* Class currently parsed */ tree gclass_list; /* All classes seen from source code */
tree current_parsed_class_un; /* Curr. parsed class unqualified name */
/* These two lists won't survive file traversal */
tree class_list; /* List of classes in a CU */ tree class_list; /* List of classes in a CU */
tree gclass_list; /* All classes seen so far. */
jdeplist *classd_list; /* Classe dependencies in a CU */ jdeplist *classd_list; /* Classe dependencies in a CU */
tree current_parsed_class; /* Class currently parsed */
tree current_parsed_class_un; /* Curr. parsed class unqualified name */
tree non_static_initialized; /* List of non static initialized fields */ tree non_static_initialized; /* List of non static initialized fields */
tree static_initialized; /* List of static non final initialized */ tree static_initialized; /* List of static non final initialized */
tree import_list; /* List of import */ tree import_list; /* List of import */
tree import_demand_list; /* List of import on demand */ tree import_demand_list; /* List of import on demand */
tree current_loop; /* List of the currently nested loops/switches */ tree current_loop; /* List of the currently nested
tree current_labeled_block; /* List of currently nested loops/switches */
labeled blocks. */ tree current_labeled_block; /* List of currently nested
labeled blocks. */
int pending_block; /* Pending block to close */ int pending_block; /* Pending block to close */
int explicit_constructor_p; /* True when processing an int explicit_constructor_p; /* True when processing an explicit
explicit constructor. This flag is constructor. This flag is used to trap
used to trap illegal argument usage illegal argument usage during an
during an explicit constructor explicit constructor invocation. */
invocation. */
#endif /* JC1_LITE */ #endif /* JC1_LITE */
}; };
...@@ -803,7 +807,6 @@ void safe_layout_class PROTO ((tree)); ...@@ -803,7 +807,6 @@ void safe_layout_class PROTO ((tree));
void java_complete_class PROTO ((void)); void java_complete_class PROTO ((void));
void java_check_circular_reference PROTO ((void)); void java_check_circular_reference PROTO ((void));
void java_check_final PROTO ((void)); void java_check_final PROTO ((void));
void java_check_methods PROTO ((void));
void java_layout_classes PROTO ((void)); void java_layout_classes PROTO ((void));
tree java_method_add_stmt PROTO ((tree, tree)); tree java_method_add_stmt PROTO ((tree, tree));
char *java_get_line_col PROTO ((char *, int, int)); char *java_get_line_col PROTO ((char *, int, int));
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment