]> git.ipfire.org Git - thirdparty/gcc.git/blob - gcc/java/class.c
Merge from pch-branch up to tag pch-commit-20020603.
[thirdparty/gcc.git] / gcc / java / class.c
1 /* Functions related to building classes and their related objects.
2 Copyright (C) 1996, 1997, 1998, 1999, 2000, 2001, 2002
3 Free Software Foundation, Inc.
4
5 This file is part of GNU CC.
6
7 GNU CC is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2, or (at your option)
10 any later version.
11
12 GNU CC is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with GNU CC; see the file COPYING. If not, write to
19 the Free Software Foundation, 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA.
21
22 Java and all Java-based marks are trademarks or registered trademarks
23 of Sun Microsystems, Inc. in the United States and other countries.
24 The Free Software Foundation is independent of Sun Microsystems, Inc. */
25
26 /* Written by Per Bothner <bothner@cygnus.com> */
27
28 #include "config.h"
29 #include "system.h"
30 #include "tree.h"
31 #include "rtl.h"
32 #include "flags.h"
33 #include "java-tree.h"
34 #include "jcf.h"
35 #include "obstack.h"
36 #include "toplev.h"
37 #include "output.h"
38 #include "parse.h"
39 #include "function.h"
40 #include "ggc.h"
41 #include "stdio.h"
42 #include "target.h"
43
44 /* DOS brain-damage */
45 #ifndef O_BINARY
46 #define O_BINARY 0 /* MS-DOS brain-damage */
47 #endif
48
49 static tree make_method_value PARAMS ((tree));
50 static tree build_java_method_type PARAMS ((tree, tree, int));
51 static int32 hashUtf8String PARAMS ((const char *, int));
52 static tree make_field_value PARAMS ((tree));
53 static tree get_dispatch_vector PARAMS ((tree));
54 static tree get_dispatch_table PARAMS ((tree, tree));
55 static void add_interface_do PARAMS ((tree, tree, int));
56 static tree maybe_layout_super_class PARAMS ((tree, tree));
57 static int assume_compiled PARAMS ((const char *));
58 static tree build_method_symbols_entry PARAMS ((tree));
59
60 static GTY(()) rtx registerClass_libfunc;
61 static GTY(()) rtx registerResource_libfunc;
62
63 extern struct obstack permanent_obstack;
64 struct obstack temporary_obstack;
65
66 /* The compiler generates different code depending on whether or not
67 it can assume certain classes have been compiled down to native
68 code or not. The compiler options -fassume-compiled= and
69 -fno-assume-compiled= are used to create a tree of
70 assume_compiled_node objects. This tree is queried to determine if
71 a class is assume to be compiled or not. Each node in the tree
72 represents either a package or a specific class. */
73
74 typedef struct assume_compiled_node_struct
75 {
76 /* The class or package name. */
77 const char *ident;
78
79 /* Non-zero if this represents an exclusion. */
80 int excludep;
81
82 /* Pointers to other nodes in the tree. */
83 struct assume_compiled_node_struct *parent;
84 struct assume_compiled_node_struct *sibling;
85 struct assume_compiled_node_struct *child;
86 } assume_compiled_node;
87
88 static assume_compiled_node *find_assume_compiled_node
89 PARAMS ((assume_compiled_node *, const char *));
90
91 /* This is the root of the include/exclude tree. */
92
93 static assume_compiled_node *assume_compiled_tree;
94
95 static GTY(()) tree class_roots[5];
96 #define registered_class class_roots[0]
97 #define fields_ident class_roots[1] /* get_identifier ("fields") */
98 #define info_ident class_roots[2] /* get_identifier ("info") */
99 #define class_list class_roots[3]
100 #define class_dtable_decl class_roots[4]
101
102 /* Return the node that most closely represents the class whose name
103 is IDENT. Start the search from NODE. Return NULL if an
104 appropriate node does not exist. */
105
106 static assume_compiled_node *
107 find_assume_compiled_node (node, ident)
108 assume_compiled_node *node;
109 const char *ident;
110 {
111 while (node)
112 {
113 size_t node_ident_length = strlen (node->ident);
114
115 /* node_ident_length is zero at the root of the tree. If the
116 identifiers are the same length, then we have matching
117 classes. Otherwise check if we've matched an enclosing
118 package name. */
119
120 if (node_ident_length == 0
121 || (strncmp (ident, node->ident, node_ident_length) == 0
122 && (strlen (ident) == node_ident_length
123 || ident[node_ident_length] == '.')))
124 {
125 /* We've found a match, however, there might be a more
126 specific match. */
127
128 assume_compiled_node *found = find_assume_compiled_node (node->child,
129 ident);
130 if (found)
131 return found;
132 else
133 return node;
134 }
135
136 /* No match yet. Continue through the sibling list. */
137 node = node->sibling;
138 }
139
140 /* No match at all in this tree. */
141 return NULL;
142 }
143
144 /* Add a new IDENT to the include/exclude tree. It's an exclusion
145 if EXCLUDEP is non-zero. */
146
147 void
148 add_assume_compiled (ident, excludep)
149 const char *ident;
150 int excludep;
151 {
152 assume_compiled_node *parent;
153 assume_compiled_node *node =
154 (assume_compiled_node *) xmalloc (sizeof (assume_compiled_node));
155
156 node->ident = xstrdup (ident);
157 node->excludep = excludep;
158 node->child = NULL;
159
160 /* Create the root of the tree if it doesn't exist yet. */
161
162 if (NULL == assume_compiled_tree)
163 {
164 assume_compiled_tree =
165 (assume_compiled_node *) xmalloc (sizeof (assume_compiled_node));
166 assume_compiled_tree->ident = "";
167 assume_compiled_tree->excludep = 0;
168 assume_compiled_tree->sibling = NULL;
169 assume_compiled_tree->child = NULL;
170 assume_compiled_tree->parent = NULL;
171 }
172
173 /* Calling the function with the empty string means we're setting
174 excludep for the root of the hierarchy. */
175
176 if (0 == ident[0])
177 {
178 assume_compiled_tree->excludep = excludep;
179 return;
180 }
181
182 /* Find the parent node for this new node. PARENT will either be a
183 class or a package name. Adjust PARENT accordingly. */
184
185 parent = find_assume_compiled_node (assume_compiled_tree, ident);
186 if (ident[strlen (parent->ident)] != '.')
187 parent = parent->parent;
188
189 /* Insert NODE into the tree. */
190
191 node->parent = parent;
192 node->sibling = parent->child;
193 parent->child = node;
194 }
195
196 /* Returns non-zero if IDENT is the name of a class that the compiler
197 should assume has been compiled to FIXME */
198
199 static int
200 assume_compiled (ident)
201 const char *ident;
202 {
203 assume_compiled_node *i;
204 int result;
205
206 if (NULL == assume_compiled_tree)
207 return 1;
208
209 i = find_assume_compiled_node (assume_compiled_tree,
210 ident);
211
212 result = ! i->excludep;
213
214 return (result);
215 }
216
217 /* Return an IDENTIFIER_NODE the same as (OLD_NAME, OLD_LENGTH).
218 except that characters matching OLD_CHAR are substituted by NEW_CHAR.
219 Also, PREFIX is prepended, and SUFFIX is appended. */
220
221 tree
222 ident_subst (old_name, old_length, prefix, old_char, new_char, suffix)
223 const char* old_name;
224 int old_length;
225 const char *prefix;
226 int old_char;
227 int new_char;
228 const char *suffix;
229 {
230 int prefix_len = strlen (prefix);
231 int suffix_len = strlen (suffix);
232 int i = prefix_len + old_length + suffix_len + 1;
233 #ifdef __GNUC__
234 char buffer[i];
235 #else
236 char *buffer = (char *)alloca (i);
237 #endif
238 strcpy (buffer, prefix);
239 for (i = 0; i < old_length; i++)
240 {
241 char ch = old_name[i];
242 if (ch == old_char)
243 ch = new_char;
244 buffer[prefix_len + i] = ch;
245 }
246 strcpy (buffer + prefix_len + old_length, suffix);
247 return get_identifier (buffer);
248 }
249
250 /* Return an IDENTIFIER_NODE the same as OLD_ID,
251 except that characters matching OLD_CHAR are substituted by NEW_CHAR.
252 Also, PREFIX is prepended, and SUFFIX is appended. */
253
254 tree
255 identifier_subst (old_id, prefix, old_char, new_char, suffix)
256 const tree old_id;
257 const char *prefix;
258 int old_char;
259 int new_char;
260 const char *suffix;
261 {
262 return ident_subst (IDENTIFIER_POINTER (old_id), IDENTIFIER_LENGTH (old_id),
263 prefix, old_char, new_char, suffix);
264 }
265
266 /* Generate a valid C identifier from the name of the class TYPE,
267 prefixed by PREFIX. */
268
269 tree
270 mangled_classname (prefix, type)
271 const char *prefix;
272 tree type;
273 {
274 tree ident = TYPE_NAME (type);
275 if (TREE_CODE (ident) != IDENTIFIER_NODE)
276 ident = DECL_NAME (ident);
277 return identifier_subst (ident, prefix, '.', '_', "");
278 }
279
280 tree
281 make_class ()
282 {
283 tree type;
284 type = make_node (RECORD_TYPE);
285 #ifdef JAVA_USE_HANDLES
286 tree field1 = build_decl (FIELD_DECL, get_identifier ("obj"),
287 build_pointer_type (type));
288 tree field2 = build_decl (FIELD_DECL, get_identifier ("methods"),
289 methodtable_ptr_type);
290 tree handle_type = make_node (RECORD_TYPE);
291 TREE_CHAIN (field1) = field2;
292 TYPE_FIELDS (handle_type) = field1;
293 TYPE_BINFO (type) = make_tree_vec (7);
294 TYPE_BINFO (handle_type) = make_tree_vec (7);
295 BINFO_HANDLE (TYPE_BINFO (handle_type)) = type;
296 BINFO_HANDLE (TYPE_BINFO (type)) = handle_type;
297 #else
298 TYPE_BINFO (type) = make_tree_vec (6);
299 #endif
300 MAYBE_CREATE_TYPE_TYPE_LANG_SPECIFIC (type);
301
302 return type;
303 }
304
305 /* Given a fully-qualified classname in NAME (whose length is NAME_LENGTH),
306 and where each of the constituents is separated by '/',
307 return a corresponding IDENTIFIER_NODE, except using '.' as separator. */
308
309 tree
310 unmangle_classname (name, name_length)
311 const char *name; int name_length;
312 {
313 tree to_return = ident_subst (name, name_length, "", '/', '.', "");
314 /* It's not sufficient to compare to_return and get_identifier
315 (name) to determine whether to_return is qualified. There are
316 cases in signature analysis where name will be stripped of a
317 trailing ';'. */
318 name = IDENTIFIER_POINTER (to_return);
319 while (*name)
320 if (*name++ == '.')
321 {
322 QUALIFIED_P (to_return) = 1;
323 break;
324 }
325
326 return to_return;
327 }
328
329 tree
330 push_class (class_type, class_name)
331 tree class_type, class_name;
332 {
333 tree decl, signature;
334 const char *save_input_filename = input_filename;
335 int save_lineno = lineno;
336 tree source_name = identifier_subst (class_name, "", '.', '/', ".java");
337 CLASS_P (class_type) = 1;
338 input_filename = IDENTIFIER_POINTER (source_name);
339 lineno = 0;
340 decl = build_decl (TYPE_DECL, class_name, class_type);
341
342 /* dbxout needs a DECL_SIZE if in gstabs mode */
343 DECL_SIZE (decl) = integer_zero_node;
344
345 input_filename = save_input_filename;
346 lineno = save_lineno;
347 signature = identifier_subst (class_name, "L", '.', '/', ";");
348 IDENTIFIER_SIGNATURE_TYPE (signature) = build_pointer_type (class_type);
349
350 /* Setting DECL_ARTIFICIAL forces dbxout.c to specific the type is
351 both a typedef and in the struct name-space. We may want to re-visit
352 this later, but for now it reduces the changes needed for gdb. */
353 DECL_ARTIFICIAL (decl) = 1;
354
355 pushdecl_top_level (decl);
356 #ifdef JAVA_USE_HANDLES
357 {
358 tree handle_name = identifier_subst (class_name,
359 "Handle$", '.', '.', "");
360 tree handle_decl = build_decl (TYPE_DECL, handle_name,
361 CLASS_TO_HANDLE_TYPE (class_type));
362 pushdecl (handle_decl);
363 }
364 #endif
365
366 return decl;
367 }
368
369 /* Finds the (global) class named NAME. Creates the class if not found.
370 Also creates associated TYPE_DECL.
371 Does not check if the class actually exists, load the class,
372 fill in field or methods, or do layout_type. */
373
374 tree
375 lookup_class (name)
376 tree name;
377 {
378 tree decl = IDENTIFIER_CLASS_VALUE (name);
379 if (decl == NULL_TREE)
380 decl = push_class (make_class (), name);
381 return TREE_TYPE (decl);
382 }
383
384 void
385 set_super_info (access_flags, this_class, super_class, interfaces_count)
386 int access_flags;
387 tree this_class;
388 tree super_class;
389 int interfaces_count;
390 {
391 int total_supers = interfaces_count;
392 tree class_decl = TYPE_NAME (this_class);
393 if (super_class)
394 total_supers++;
395
396 TYPE_BINFO_BASETYPES (this_class) = make_tree_vec (total_supers);
397 if (super_class)
398 {
399 tree super_binfo = make_tree_vec (6);
400 BINFO_TYPE (super_binfo) = super_class;
401 BINFO_OFFSET (super_binfo) = integer_zero_node;
402 TREE_VIA_PUBLIC (super_binfo) = 1;
403 TREE_VEC_ELT (BINFO_BASETYPES (TYPE_BINFO (this_class)), 0)
404 = super_binfo;
405 CLASS_HAS_SUPER (this_class) = 1;
406 }
407
408 set_class_decl_access_flags (access_flags, class_decl);
409 }
410
411 void
412 set_class_decl_access_flags (access_flags, class_decl)
413 int access_flags;
414 tree class_decl;
415 {
416 if (access_flags & ACC_PUBLIC) CLASS_PUBLIC (class_decl) = 1;
417 if (access_flags & ACC_FINAL) CLASS_FINAL (class_decl) = 1;
418 if (access_flags & ACC_SUPER) CLASS_SUPER (class_decl) = 1;
419 if (access_flags & ACC_INTERFACE) CLASS_INTERFACE (class_decl) = 1;
420 if (access_flags & ACC_ABSTRACT) CLASS_ABSTRACT (class_decl) = 1;
421 if (access_flags & ACC_STATIC) CLASS_STATIC (class_decl) = 1;
422 if (access_flags & ACC_PRIVATE) CLASS_PRIVATE (class_decl) = 1;
423 if (access_flags & ACC_PROTECTED) CLASS_PROTECTED (class_decl) = 1;
424 if (access_flags & ACC_STRICT) CLASS_STRICTFP (class_decl) = 1;
425 }
426
427 /* Return length of inheritance chain of CLAS, where java.lang.Object is 0,
428 direct sub-classes of Object are 1, and so on. */
429
430 int
431 class_depth (clas)
432 tree clas;
433 {
434 int depth = 0;
435 if (! CLASS_LOADED_P (clas))
436 load_class (clas, 1);
437 if (TYPE_SIZE (clas) == error_mark_node)
438 return -1;
439 while (clas != object_type_node)
440 {
441 depth++;
442 clas = TYPE_BINFO_BASETYPE (clas, 0);
443 }
444 return depth;
445 }
446
447 /* Return true iff TYPE2 is an interface that extends interface TYPE1 */
448
449 int
450 interface_of_p (type1, type2)
451 tree type1, type2;
452 {
453 int n, i;
454 tree basetype_vec;
455
456 if (!(basetype_vec = TYPE_BINFO_BASETYPES (type2)))
457 return 0;
458 n = TREE_VEC_LENGTH (basetype_vec);
459 for (i = 0; i < n; i++)
460 {
461 tree vec_elt = TREE_VEC_ELT (basetype_vec, i);
462 if (vec_elt && BINFO_TYPE (vec_elt) == type1)
463 return 1;
464 }
465 for (i = 0; i < n; i++)
466 {
467 tree vec_elt = TREE_VEC_ELT (basetype_vec, i);
468 if (vec_elt && BINFO_TYPE (vec_elt)
469 && interface_of_p (type1, BINFO_TYPE (vec_elt)))
470 return 1;
471 }
472 return 0;
473 }
474
475 /* Return true iff TYPE1 inherits from TYPE2. */
476
477 int
478 inherits_from_p (type1, type2)
479 tree type1, type2;
480 {
481 while (type1 != NULL_TREE && TREE_CODE (type1) == RECORD_TYPE)
482 {
483 if (type1 == type2)
484 return 1;
485 type1 = CLASSTYPE_SUPER (type1);
486 }
487 return 0;
488 }
489
490 /* Return a 1 iff TYPE1 is an enclosing context for TYPE2 */
491
492 int
493 enclosing_context_p (type1, type2)
494 tree type1, type2;
495 {
496 if (!INNER_CLASS_TYPE_P (type2))
497 return 0;
498
499 for (type2 = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (type2)));
500 type2;
501 type2 = (INNER_CLASS_TYPE_P (type2) ?
502 TREE_TYPE (DECL_CONTEXT (TYPE_NAME (type2))) : NULL_TREE))
503 {
504 if (type2 == type1)
505 return 1;
506 }
507
508 return 0;
509 }
510
511 /* Return 1 iff there exists a common enclosing context between TYPE1
512 and TYPE2. */
513
514 int common_enclosing_context_p (type1, type2)
515 tree type1, type2;
516 {
517 if (!PURE_INNER_CLASS_TYPE_P (type1) || !PURE_INNER_CLASS_TYPE_P (type2))
518 return 0;
519
520 for (type1 = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (type1))); type1;
521 type1 = (PURE_INNER_CLASS_TYPE_P (type1) ?
522 TREE_TYPE (DECL_CONTEXT (TYPE_NAME (type1))) : NULL_TREE))
523 {
524 tree current;
525 for (current = TREE_TYPE (DECL_CONTEXT (TYPE_NAME (type2))); current;
526 current = (PURE_INNER_CLASS_TYPE_P (current) ?
527 TREE_TYPE (DECL_CONTEXT (TYPE_NAME (current))) :
528 NULL_TREE))
529 if (type1 == current)
530 return 1;
531 }
532 return 0;
533 }
534
535 static void
536 add_interface_do (basetype_vec, interface_class, i)
537 tree basetype_vec, interface_class;
538 int i;
539 {
540 tree interface_binfo = make_tree_vec (6);
541 BINFO_TYPE (interface_binfo) = interface_class;
542 BINFO_OFFSET (interface_binfo) = integer_zero_node;
543 BINFO_VPTR_FIELD (interface_binfo) = integer_zero_node;
544 TREE_VIA_VIRTUAL (interface_binfo) = 1;
545 TREE_VIA_PUBLIC (interface_binfo) = 1;
546 TREE_VEC_ELT (basetype_vec, i) = interface_binfo;
547 }
548
549 /* Add INTERFACE_CLASS to THIS_CLASS iff INTERFACE_CLASS can't be
550 found in THIS_CLASS. Returns NULL_TREE upon success, INTERFACE_CLASS
551 if attempt is made to add it twice. */
552
553 tree
554 maybe_add_interface (this_class, interface_class)
555 tree this_class, interface_class;
556 {
557 tree basetype_vec = TYPE_BINFO_BASETYPES (this_class);
558 int i;
559 int n = TREE_VEC_LENGTH (basetype_vec);
560 for (i = 0; ; i++)
561 {
562 if (i >= n)
563 {
564 error ("internal error - too many interface type");
565 return NULL_TREE;
566 }
567 else if (TREE_VEC_ELT (basetype_vec, i) == NULL_TREE)
568 break;
569 else if (BINFO_TYPE (TREE_VEC_ELT (basetype_vec, i)) == interface_class)
570 return interface_class;
571 }
572 add_interface_do (basetype_vec, interface_class, i);
573 return NULL_TREE;
574 }
575
576 /* Add the INTERFACE_CLASS as one of the interfaces of THIS_CLASS. */
577
578 void
579 add_interface (this_class, interface_class)
580 tree this_class, interface_class;
581 {
582 tree basetype_vec = TYPE_BINFO_BASETYPES (this_class);
583 int i;
584 int n = TREE_VEC_LENGTH (basetype_vec);
585 for (i = 0; ; i++)
586 {
587 if (i >= n)
588 {
589 error ("internal error - too many interface type");
590 return;
591 }
592 else if (TREE_VEC_ELT (basetype_vec, i) == NULL_TREE)
593 break;
594 }
595 add_interface_do (basetype_vec, interface_class, i);
596 }
597
598 #if 0
599 /* Return the address of a pointer to the first FUNCTION_DECL
600 in the list (*LIST) whose DECL_NAME is NAME. */
601
602 static tree *
603 find_named_method (list, name)
604 tree *list;
605 tree name;
606 {
607 while (*list && DECL_NAME (*list) != name)
608 list = &TREE_CHAIN (*list);
609 return list;
610 }
611 #endif
612
613 static tree
614 build_java_method_type (fntype, this_class, access_flags)
615 tree fntype;
616 tree this_class;
617 int access_flags;
618 {
619 if (access_flags & ACC_STATIC)
620 return fntype;
621 return build_method_type (CLASS_TO_HANDLE_TYPE (this_class), fntype);
622 }
623
624 tree
625 add_method_1 (handle_class, access_flags, name, function_type)
626 tree handle_class;
627 int access_flags;
628 tree name;
629 tree function_type;
630 {
631 tree method_type, fndecl;
632
633 method_type = build_java_method_type (function_type,
634 handle_class, access_flags);
635
636 fndecl = build_decl (FUNCTION_DECL, name, method_type);
637 DECL_CONTEXT (fndecl) = handle_class;
638
639 DECL_LANG_SPECIFIC (fndecl)
640 = (struct lang_decl *) ggc_alloc_cleared (sizeof (struct lang_decl));
641 DECL_LANG_SPECIFIC (fndecl)->desc = LANG_DECL_FUNC;
642
643 /* Initialize the static initializer test table. */
644
645 DECL_FUNCTION_INIT_TEST_TABLE (fndecl) =
646 java_treetreehash_create (10, 1);
647
648 /* Initialize the initialized (static) class table. */
649 if (access_flags & ACC_STATIC)
650 DECL_FUNCTION_INITIALIZED_CLASS_TABLE (fndecl) =
651 htab_create_ggc (50, htab_hash_pointer, htab_eq_pointer, NULL);
652
653 /* Initialize the static method invocation compound list */
654 DECL_FUNCTION_STATIC_METHOD_INVOCATION_COMPOUND (fndecl) = NULL_TREE;
655
656 TREE_CHAIN (fndecl) = TYPE_METHODS (handle_class);
657 TYPE_METHODS (handle_class) = fndecl;
658
659 /* Notice that this is a finalizer and update the class type
660 accordingly. This is used to optimize instance allocation. */
661 if (name == finalize_identifier_node
662 && TREE_TYPE (function_type) == void_type_node
663 && TREE_VALUE (TYPE_ARG_TYPES (function_type)) == void_type_node)
664 HAS_FINALIZER_P (handle_class) = 1;
665
666 if (access_flags & ACC_PUBLIC) METHOD_PUBLIC (fndecl) = 1;
667 if (access_flags & ACC_PROTECTED) METHOD_PROTECTED (fndecl) = 1;
668 if (access_flags & ACC_PRIVATE)
669 METHOD_PRIVATE (fndecl) = DECL_INLINE (fndecl) = 1;
670 if (access_flags & ACC_NATIVE)
671 {
672 METHOD_NATIVE (fndecl) = 1;
673 DECL_EXTERNAL (fndecl) = 1;
674 }
675 if (access_flags & ACC_STATIC)
676 METHOD_STATIC (fndecl) = DECL_INLINE (fndecl) = 1;
677 if (access_flags & ACC_FINAL)
678 METHOD_FINAL (fndecl) = DECL_INLINE (fndecl) = 1;
679 if (access_flags & ACC_SYNCHRONIZED) METHOD_SYNCHRONIZED (fndecl) = 1;
680 if (access_flags & ACC_ABSTRACT) METHOD_ABSTRACT (fndecl) = 1;
681 if (access_flags & ACC_TRANSIENT) METHOD_TRANSIENT (fndecl) = 1;
682 if (access_flags & ACC_STRICT) METHOD_STRICTFP (fndecl) = 1;
683 return fndecl;
684 }
685
686 /* Add a method to THIS_CLASS.
687 The method's name is NAME.
688 Its signature (mangled type) is METHOD_SIG (an IDENTIFIER_NODE). */
689
690 tree
691 add_method (this_class, access_flags, name, method_sig)
692 tree this_class;
693 int access_flags;
694 tree name;
695 tree method_sig;
696 {
697 tree handle_class = CLASS_TO_HANDLE_TYPE (this_class);
698 tree function_type, fndecl;
699 const unsigned char *sig
700 = (const unsigned char *) IDENTIFIER_POINTER (method_sig);
701
702 if (sig[0] != '(')
703 fatal_error ("bad method signature");
704
705 function_type = get_type_from_signature (method_sig);
706 fndecl = add_method_1 (handle_class, access_flags, name, function_type);
707 set_java_signature (TREE_TYPE (fndecl), method_sig);
708 return fndecl;
709 }
710
711 tree
712 add_field (class, name, field_type, flags)
713 tree class;
714 tree name;
715 tree field_type;
716 int flags;
717 {
718 int is_static = (flags & ACC_STATIC) != 0;
719 tree field;
720 field = build_decl (is_static ? VAR_DECL : FIELD_DECL, name, field_type);
721 TREE_CHAIN (field) = TYPE_FIELDS (class);
722 TYPE_FIELDS (class) = field;
723 DECL_CONTEXT (field) = class;
724
725 if (flags & ACC_PUBLIC) FIELD_PUBLIC (field) = 1;
726 if (flags & ACC_PROTECTED) FIELD_PROTECTED (field) = 1;
727 if (flags & ACC_PRIVATE) FIELD_PRIVATE (field) = 1;
728 if (flags & ACC_FINAL) FIELD_FINAL (field) = 1;
729 if (flags & ACC_VOLATILE) FIELD_VOLATILE (field) = 1;
730 if (flags & ACC_TRANSIENT) FIELD_TRANSIENT (field) = 1;
731 if (is_static)
732 {
733 FIELD_STATIC (field) = 1;
734 /* Always make field externally visible. This is required so
735 that native methods can always access the field. */
736 TREE_PUBLIC (field) = 1;
737 /* Considered external until we know what classes are being
738 compiled into this object file. */
739 DECL_EXTERNAL (field) = 1;
740 }
741
742 return field;
743 }
744
745 /* Associate a constant value CONSTANT with VAR_DECL FIELD. */
746
747 void
748 set_constant_value (field, constant)
749 tree field, constant;
750 {
751 if (field == NULL_TREE)
752 warning ("misplaced ConstantValue attribute (not in any field)");
753 else if (DECL_INITIAL (field) != NULL_TREE)
754 warning ("duplicate ConstantValue attribute for field '%s'",
755 IDENTIFIER_POINTER (DECL_NAME (field)));
756 else
757 {
758 DECL_INITIAL (field) = constant;
759 if (TREE_TYPE (constant) != TREE_TYPE (field)
760 && ! (TREE_TYPE (constant) == int_type_node
761 && INTEGRAL_TYPE_P (TREE_TYPE (field))
762 && TYPE_PRECISION (TREE_TYPE (field)) <= 32)
763 && ! (TREE_TYPE (constant) == utf8const_ptr_type
764 && TREE_TYPE (field) == string_ptr_type_node))
765 error ("ConstantValue attribute of field '%s' has wrong type",
766 IDENTIFIER_POINTER (DECL_NAME (field)));
767 if (FIELD_FINAL (field))
768 DECL_FIELD_FINAL_IUD (field) = 1;
769 }
770 }
771
772 /* Count the number of Unicode chars encoded in a given Ut8 string. */
773
774 #if 0
775 int
776 strLengthUtf8 (str, len)
777 char *str;
778 int len;
779 {
780 register unsigned char* ptr = (unsigned char*) str;
781 register unsigned char *limit = ptr + len;
782 int str_length = 0;
783 for (; ptr < limit; str_length++) {
784 if (UTF8_GET (ptr, limit) < 0)
785 return -1;
786 }
787 return str_length;
788 }
789 #endif
790
791
792 /* Calculate a hash value for a string encoded in Utf8 format.
793 * This returns the same hash value as specified for java.lang.String.hashCode.
794 */
795
796 static int32
797 hashUtf8String (str, len)
798 const char *str;
799 int len;
800 {
801 register const unsigned char* ptr = (const unsigned char*) str;
802 register const unsigned char *limit = ptr + len;
803 int32 hash = 0;
804 for (; ptr < limit;)
805 {
806 int ch = UTF8_GET (ptr, limit);
807 /* Updated specification from
808 http://www.javasoft.com/docs/books/jls/clarify.html. */
809 hash = (31 * hash) + ch;
810 }
811 return hash;
812 }
813
814 /* Generate a byte array representing the contents of FILENAME. The
815 array is assigned a unique local symbol. The array represents a
816 compiled Java resource, which is accessed by the runtime using
817 NAME. */
818 void
819 compile_resource_file (name, filename)
820 char *name;
821 const char *filename;
822 {
823 struct stat stat_buf;
824 int fd;
825 char *buffer;
826 char buf[60];
827 tree rtype, field = NULL_TREE, data_type, rinit, data, decl;
828 static int Jr_count = 0;
829
830 fd = open (filename, O_RDONLY | O_BINARY);
831 if (fd < 0)
832 {
833 perror ("Failed to read resource file");
834 return;
835 }
836 if (fstat (fd, &stat_buf) != 0
837 || ! S_ISREG (stat_buf.st_mode))
838 {
839 perror ("Could not figure length of resource file");
840 return;
841 }
842 buffer = xmalloc (strlen (name) + stat_buf.st_size);
843 strcpy (buffer, name);
844 read (fd, buffer + strlen (name), stat_buf.st_size);
845 close (fd);
846 data_type = build_prim_array_type (unsigned_byte_type_node,
847 strlen (name) + stat_buf.st_size);
848 rtype = make_node (RECORD_TYPE);
849 PUSH_FIELD (rtype, field, "name_length", unsigned_int_type_node);
850 PUSH_FIELD (rtype, field, "resource_length", unsigned_int_type_node);
851 PUSH_FIELD (rtype, field, "data", data_type);
852 FINISH_RECORD (rtype);
853 START_RECORD_CONSTRUCTOR (rinit, rtype);
854 PUSH_FIELD_VALUE (rinit, "name_length",
855 build_int_2 (strlen (name), 0));
856 PUSH_FIELD_VALUE (rinit, "resource_length",
857 build_int_2 (stat_buf.st_size, 0));
858 data = build_string (strlen(name) + stat_buf.st_size, buffer);
859 TREE_TYPE (data) = data_type;
860 PUSH_FIELD_VALUE (rinit, "data", data);
861 FINISH_RECORD_CONSTRUCTOR (rinit);
862 TREE_CONSTANT (rinit) = 1;
863
864 /* Generate a unique-enough identifier. */
865 sprintf(buf, "_Jr%d", ++Jr_count);
866
867 decl = build_decl (VAR_DECL, get_identifier (buf), rtype);
868 TREE_STATIC (decl) = 1;
869 DECL_ARTIFICIAL (decl) = 1;
870 DECL_IGNORED_P (decl) = 1;
871 TREE_READONLY (decl) = 1;
872 TREE_THIS_VOLATILE (decl) = 0;
873 DECL_INITIAL (decl) = rinit;
874 layout_decl (decl, 0);
875 pushdecl (decl);
876 rest_of_decl_compilation (decl, (char*) 0, global_bindings_p (), 0);
877 make_decl_rtl (decl, (char*) 0);
878 assemble_variable (decl, 1, 0, 0);
879
880 {
881 tree init_name = get_file_function_name ('I');
882 tree init_type = build_function_type (void_type_node, end_params_node);
883 tree init_decl;
884
885 init_decl = build_decl (FUNCTION_DECL, init_name, init_type);
886 SET_DECL_ASSEMBLER_NAME (init_decl, init_name);
887 TREE_STATIC (init_decl) = 1;
888 current_function_decl = init_decl;
889 DECL_RESULT (init_decl) = build_decl (RESULT_DECL,
890 NULL_TREE, void_type_node);
891
892 /* It can be a static function as long as collect2 does not have
893 to scan the object file to find its ctor/dtor routine. */
894 TREE_PUBLIC (init_decl) = ! targetm.have_ctors_dtors;
895
896 pushlevel (0);
897 make_decl_rtl (init_decl, NULL);
898 init_function_start (init_decl, input_filename, 0);
899 expand_function_start (init_decl, 0);
900
901 emit_library_call (registerResource_libfunc, 0, VOIDmode, 1,
902 gen_rtx (SYMBOL_REF, Pmode, buf),
903 Pmode);
904
905 expand_function_end (input_filename, 0, 0);
906 poplevel (1, 0, 1);
907 {
908 /* Force generation, even with -O3 or deeper. Gross hack. FIXME */
909 int saved_flag = flag_inline_functions;
910 flag_inline_functions = 0;
911 rest_of_compilation (init_decl);
912 flag_inline_functions = saved_flag;
913 }
914 current_function_decl = NULL_TREE;
915 (* targetm.asm_out.constructor) (XEXP (DECL_RTL (init_decl), 0),
916 DEFAULT_INIT_PRIORITY);
917 }
918 }
919
920 tree utf8_decl_list = NULL_TREE;
921
922 tree
923 build_utf8_ref (name)
924 tree name;
925 {
926 const char * name_ptr = IDENTIFIER_POINTER(name);
927 int name_len = IDENTIFIER_LENGTH(name);
928 char buf[60];
929 tree ctype, field = NULL_TREE, str_type, cinit, string;
930 static int utf8_count = 0;
931 int name_hash;
932 tree ref = IDENTIFIER_UTF8_REF (name);
933 tree decl;
934 if (ref != NULL_TREE)
935 return ref;
936
937 ctype = make_node (RECORD_TYPE);
938 str_type = build_prim_array_type (unsigned_byte_type_node,
939 name_len + 1); /* Allow for final '\0'. */
940 PUSH_FIELD (ctype, field, "hash", unsigned_short_type_node);
941 PUSH_FIELD (ctype, field, "length", unsigned_short_type_node);
942 PUSH_FIELD (ctype, field, "data", str_type);
943 FINISH_RECORD (ctype);
944 START_RECORD_CONSTRUCTOR (cinit, ctype);
945 name_hash = hashUtf8String (name_ptr, name_len) & 0xFFFF;
946 PUSH_FIELD_VALUE (cinit, "hash", build_int_2 (name_hash, 0));
947 PUSH_FIELD_VALUE (cinit, "length", build_int_2 (name_len, 0));
948 string = build_string (name_len, name_ptr);
949 TREE_TYPE (string) = str_type;
950 PUSH_FIELD_VALUE (cinit, "data", string);
951 FINISH_RECORD_CONSTRUCTOR (cinit);
952 TREE_CONSTANT (cinit) = 1;
953
954 /* Generate a unique-enough identifier. */
955 sprintf(buf, "_Utf%d", ++utf8_count);
956
957 decl = build_decl (VAR_DECL, get_identifier (buf), utf8const_type);
958 TREE_STATIC (decl) = 1;
959 DECL_ARTIFICIAL (decl) = 1;
960 DECL_IGNORED_P (decl) = 1;
961 TREE_READONLY (decl) = 1;
962 TREE_THIS_VOLATILE (decl) = 0;
963 DECL_INITIAL (decl) = cinit;
964 #ifdef HAVE_GAS_SHF_MERGE
965 {
966 int decl_size;
967 /* Ensure decl_size is a multiple of utf8const_type's alignment. */
968 decl_size = (name_len + 5 + TYPE_ALIGN_UNIT (utf8const_type) - 1)
969 & ~(TYPE_ALIGN_UNIT (utf8const_type) - 1);
970 if (flag_merge_constants && decl_size < 256)
971 {
972 char buf[32];
973 int flags = (SECTION_OVERRIDE
974 | SECTION_MERGE | (SECTION_ENTSIZE & decl_size));
975 sprintf (buf, ".rodata.jutf8.%d", decl_size);
976 named_section_flags (buf, flags);
977 DECL_SECTION_NAME (decl) = build_string (strlen (buf), buf);
978 }
979 }
980 #endif
981 TREE_CHAIN (decl) = utf8_decl_list;
982 layout_decl (decl, 0);
983 pushdecl (decl);
984 rest_of_decl_compilation (decl, (char*) 0, global_bindings_p (), 0);
985 utf8_decl_list = decl;
986 make_decl_rtl (decl, (char*) 0);
987 ref = build1 (ADDR_EXPR, utf8const_ptr_type, decl);
988 IDENTIFIER_UTF8_REF (name) = ref;
989 return ref;
990 }
991
992 /* Build a reference to the class TYPE.
993 Also handles primitive types and array types. */
994
995 tree
996 build_class_ref (type)
997 tree type;
998 {
999 int is_compiled = is_compiled_class (type);
1000 if (is_compiled)
1001 {
1002 tree ref, decl_name, decl;
1003 if (TREE_CODE (type) == POINTER_TYPE)
1004 type = TREE_TYPE (type);
1005 if (TREE_CODE (type) == RECORD_TYPE)
1006 {
1007 if (TYPE_SIZE (type) == error_mark_node)
1008 return null_pointer_node;
1009 decl_name = identifier_subst (DECL_NAME (TYPE_NAME (type)),
1010 "", '/', '/', ".class");
1011 decl = IDENTIFIER_GLOBAL_VALUE (decl_name);
1012 if (decl == NULL_TREE)
1013 {
1014 decl = build_decl (VAR_DECL, decl_name, class_type_node);
1015 DECL_SIZE (decl) = TYPE_SIZE (class_type_node);
1016 DECL_SIZE_UNIT (decl) = TYPE_SIZE_UNIT (class_type_node);
1017 TREE_STATIC (decl) = 1;
1018 TREE_PUBLIC (decl) = 1;
1019 DECL_IGNORED_P (decl) = 1;
1020 DECL_ARTIFICIAL (decl) = 1;
1021 if (is_compiled == 1)
1022 DECL_EXTERNAL (decl) = 1;
1023 SET_DECL_ASSEMBLER_NAME (decl,
1024 java_mangle_class_field
1025 (&temporary_obstack, type));
1026 make_decl_rtl (decl, NULL);
1027 pushdecl_top_level (decl);
1028 }
1029 }
1030 else
1031 {
1032 const char *name;
1033 char buffer[25];
1034 if (flag_emit_class_files)
1035 {
1036 const char *prim_class_name;
1037 tree prim_class;
1038 if (type == char_type_node)
1039 prim_class_name = "java.lang.Character";
1040 else if (type == boolean_type_node)
1041 prim_class_name = "java.lang.Boolean";
1042 else if (type == byte_type_node)
1043 prim_class_name = "java.lang.Byte";
1044 else if (type == short_type_node)
1045 prim_class_name = "java.lang.Short";
1046 else if (type == int_type_node)
1047 prim_class_name = "java.lang.Integer";
1048 else if (type == long_type_node)
1049 prim_class_name = "java.lang.Long";
1050 else if (type == float_type_node)
1051 prim_class_name = "java.lang.Float";
1052 else if (type == double_type_node)
1053 prim_class_name = "java.lang.Double";
1054 else if (type == void_type_node)
1055 prim_class_name = "java.lang.Void";
1056 else
1057 abort ();
1058
1059 prim_class = lookup_class (get_identifier (prim_class_name));
1060 return build (COMPONENT_REF, NULL_TREE,
1061 prim_class, TYPE_identifier_node);
1062 }
1063 decl_name = TYPE_NAME (type);
1064 if (TREE_CODE (decl_name) == TYPE_DECL)
1065 decl_name = DECL_NAME (decl_name);
1066 name = IDENTIFIER_POINTER (decl_name);
1067 if (strncmp (name, "promoted_", 9) == 0)
1068 name += 9;
1069 sprintf (buffer, "_Jv_%sClass", name);
1070 decl_name = get_identifier (buffer);
1071 decl = IDENTIFIER_GLOBAL_VALUE (decl_name);
1072 if (decl == NULL_TREE)
1073 {
1074 decl = build_decl (VAR_DECL, decl_name, class_type_node);
1075 TREE_STATIC (decl) = 1;
1076 TREE_PUBLIC (decl) = 1;
1077 DECL_EXTERNAL (decl) = 1;
1078 make_decl_rtl (decl, NULL);
1079 pushdecl_top_level (decl);
1080 }
1081 }
1082
1083 ref = build1 (ADDR_EXPR, class_ptr_type, decl);
1084 return ref;
1085 }
1086 else
1087 {
1088 int index;
1089 tree cl;
1090 index = alloc_class_constant (type);
1091 cl = build_ref_from_constant_pool (index);
1092 TREE_TYPE (cl) = promote_type (class_ptr_type);
1093 return cl;
1094 }
1095 }
1096
1097 tree
1098 build_static_field_ref (fdecl)
1099 tree fdecl;
1100 {
1101 tree fclass = DECL_CONTEXT (fdecl);
1102 int is_compiled = is_compiled_class (fclass);
1103 if (is_compiled)
1104 {
1105 if (!DECL_RTL_SET_P (fdecl))
1106 {
1107 if (is_compiled == 1)
1108 DECL_EXTERNAL (fdecl) = 1;
1109 make_decl_rtl (fdecl, NULL);
1110 }
1111 return fdecl;
1112 }
1113 else
1114 {
1115 /* Compile as:
1116 * *(FTYPE*)build_class_ref(FCLASS)->fields[INDEX].info.addr */
1117 tree ref = build_class_ref (fclass);
1118 tree fld;
1119 int field_index = 0;
1120 ref = build1 (INDIRECT_REF, class_type_node, ref);
1121 ref = build (COMPONENT_REF, field_ptr_type_node, ref,
1122 lookup_field (&class_type_node, fields_ident));
1123
1124 for (fld = TYPE_FIELDS (fclass); ; fld = TREE_CHAIN (fld))
1125 {
1126 if (fld == fdecl)
1127 break;
1128 if (fld == NULL_TREE)
1129 fatal_error ("field '%s' not found in class",
1130 IDENTIFIER_POINTER (DECL_NAME (fdecl)));
1131 if (FIELD_STATIC (fld))
1132 field_index++;
1133 }
1134 field_index *= int_size_in_bytes (field_type_node);
1135 ref = fold (build (PLUS_EXPR, field_ptr_type_node,
1136 ref, build_int_2 (field_index, 0)));
1137 ref = build1 (INDIRECT_REF, field_type_node, ref);
1138 ref = build (COMPONENT_REF, field_info_union_node,
1139 ref, lookup_field (&field_type_node, info_ident));
1140 ref = build (COMPONENT_REF, ptr_type_node,
1141 ref, TREE_CHAIN (TYPE_FIELDS (field_info_union_node)));
1142 return fold (build1 (INDIRECT_REF, TREE_TYPE(fdecl), ref));
1143 }
1144 }
1145
1146 int
1147 get_access_flags_from_decl (decl)
1148 tree decl;
1149 {
1150 int access_flags = 0;
1151 if (TREE_CODE (decl) == FIELD_DECL || TREE_CODE (decl) == VAR_DECL)
1152 {
1153 if (FIELD_STATIC (decl))
1154 access_flags |= ACC_STATIC;
1155 if (FIELD_PUBLIC (decl))
1156 access_flags |= ACC_PUBLIC;
1157 if (FIELD_PROTECTED (decl))
1158 access_flags |= ACC_PROTECTED;
1159 if (FIELD_PRIVATE (decl))
1160 access_flags |= ACC_PRIVATE;
1161 if (FIELD_FINAL (decl))
1162 access_flags |= ACC_FINAL;
1163 if (FIELD_VOLATILE (decl))
1164 access_flags |= ACC_VOLATILE;
1165 if (FIELD_TRANSIENT (decl))
1166 access_flags |= ACC_TRANSIENT;
1167 return access_flags;
1168 }
1169 if (TREE_CODE (decl) == TYPE_DECL)
1170 {
1171 if (CLASS_PUBLIC (decl))
1172 access_flags |= ACC_PUBLIC;
1173 if (CLASS_FINAL (decl))
1174 access_flags |= ACC_FINAL;
1175 if (CLASS_SUPER (decl))
1176 access_flags |= ACC_SUPER;
1177 if (CLASS_INTERFACE (decl))
1178 access_flags |= ACC_INTERFACE;
1179 if (CLASS_ABSTRACT (decl))
1180 access_flags |= ACC_ABSTRACT;
1181 if (CLASS_STATIC (decl))
1182 access_flags |= ACC_STATIC;
1183 if (CLASS_PRIVATE (decl))
1184 access_flags |= ACC_PRIVATE;
1185 if (CLASS_PROTECTED (decl))
1186 access_flags |= ACC_PROTECTED;
1187 if (CLASS_STRICTFP (decl))
1188 access_flags |= ACC_STRICT;
1189 return access_flags;
1190 }
1191 if (TREE_CODE (decl) == FUNCTION_DECL)
1192 {
1193 if (METHOD_PUBLIC (decl))
1194 access_flags |= ACC_PUBLIC;
1195 if (METHOD_PRIVATE (decl))
1196 access_flags |= ACC_PRIVATE;
1197 if (METHOD_PROTECTED (decl))
1198 access_flags |= ACC_PROTECTED;
1199 if (METHOD_STATIC (decl))
1200 access_flags |= ACC_STATIC;
1201 if (METHOD_FINAL (decl))
1202 access_flags |= ACC_FINAL;
1203 if (METHOD_SYNCHRONIZED (decl))
1204 access_flags |= ACC_SYNCHRONIZED;
1205 if (METHOD_NATIVE (decl))
1206 access_flags |= ACC_NATIVE;
1207 if (METHOD_ABSTRACT (decl))
1208 access_flags |= ACC_ABSTRACT;
1209 if (METHOD_TRANSIENT (decl))
1210 access_flags |= ACC_TRANSIENT;
1211 if (METHOD_STRICTFP (decl))
1212 access_flags |= ACC_STRICT;
1213 return access_flags;
1214 }
1215 abort ();
1216 }
1217
1218 static tree
1219 make_field_value (fdecl)
1220 tree fdecl;
1221 {
1222 tree finit;
1223 int flags;
1224 tree type = TREE_TYPE (fdecl);
1225 int resolved = is_compiled_class (type);
1226
1227 START_RECORD_CONSTRUCTOR (finit, field_type_node);
1228 PUSH_FIELD_VALUE (finit, "name", build_utf8_ref (DECL_NAME (fdecl)));
1229 if (resolved)
1230 type = build_class_ref (type);
1231 else
1232 {
1233 tree signature = build_java_signature (type);
1234
1235 type = build_utf8_ref (unmangle_classname
1236 (IDENTIFIER_POINTER (signature),
1237 IDENTIFIER_LENGTH (signature)));
1238 }
1239 PUSH_FIELD_VALUE (finit, "type", type);
1240
1241 flags = get_access_flags_from_decl (fdecl);
1242 if (! resolved)
1243 flags |= 0x8000 /* FIELD_UNRESOLVED_FLAG */;
1244
1245 PUSH_FIELD_VALUE (finit, "accflags", build_int_2 (flags, 0));
1246 PUSH_FIELD_VALUE (finit, "bsize", TYPE_SIZE_UNIT (TREE_TYPE (fdecl)));
1247
1248 PUSH_FIELD_VALUE
1249 (finit, "info",
1250 build (CONSTRUCTOR, field_info_union_node, NULL_TREE,
1251 build_tree_list
1252 ((FIELD_STATIC (fdecl)
1253 ? TREE_CHAIN (TYPE_FIELDS (field_info_union_node))
1254 : TYPE_FIELDS (field_info_union_node)),
1255 (FIELD_STATIC (fdecl)
1256 ? build_address_of (build_static_field_ref (fdecl))
1257 : byte_position (fdecl)))));
1258
1259 FINISH_RECORD_CONSTRUCTOR (finit);
1260 return finit;
1261 }
1262
1263 static tree
1264 make_method_value (mdecl)
1265 tree mdecl;
1266 {
1267 static int method_name_count = 0;
1268 tree minit;
1269 tree index;
1270 tree code;
1271 #define ACC_TRANSLATED 0x4000
1272 int accflags = get_access_flags_from_decl (mdecl) | ACC_TRANSLATED;
1273
1274 if (!flag_indirect_dispatch && DECL_VINDEX (mdecl) != NULL_TREE)
1275 index = DECL_VINDEX (mdecl);
1276 else
1277 index = integer_minus_one_node;
1278
1279 code = null_pointer_node;
1280 if (DECL_RTL_SET_P (mdecl))
1281 code = build1 (ADDR_EXPR, nativecode_ptr_type_node, mdecl);
1282 START_RECORD_CONSTRUCTOR (minit, method_type_node);
1283 PUSH_FIELD_VALUE (minit, "name",
1284 build_utf8_ref (DECL_CONSTRUCTOR_P (mdecl) ?
1285 init_identifier_node
1286 : DECL_NAME (mdecl)));
1287 {
1288 tree signature = build_java_signature (TREE_TYPE (mdecl));
1289 PUSH_FIELD_VALUE (minit, "signature",
1290 (build_utf8_ref
1291 (unmangle_classname
1292 (IDENTIFIER_POINTER(signature),
1293 IDENTIFIER_LENGTH(signature)))));
1294 }
1295 PUSH_FIELD_VALUE (minit, "accflags", build_int_2 (accflags, 0));
1296 PUSH_FIELD_VALUE (minit, "index", index);
1297 PUSH_FIELD_VALUE (minit, "ncode", code);
1298
1299 {
1300 /* Compute the `throws' information for the method. */
1301 tree table = null_pointer_node;
1302 if (DECL_FUNCTION_THROWS (mdecl) != NULL_TREE)
1303 {
1304 int length = 1 + list_length (DECL_FUNCTION_THROWS (mdecl));
1305 tree iter, type, array;
1306 char buf[60];
1307
1308 table = tree_cons (NULL_TREE, table, NULL_TREE);
1309 for (iter = DECL_FUNCTION_THROWS (mdecl);
1310 iter != NULL_TREE;
1311 iter = TREE_CHAIN (iter))
1312 {
1313 tree sig = build_java_signature (TREE_VALUE (iter));
1314 tree utf8
1315 = build_utf8_ref (unmangle_classname (IDENTIFIER_POINTER (sig),
1316 IDENTIFIER_LENGTH (sig)));
1317 table = tree_cons (NULL_TREE, utf8, table);
1318 }
1319 type = build_prim_array_type (ptr_type_node, length);
1320 table = build (CONSTRUCTOR, type, NULL_TREE, table);
1321 /* Compute something unique enough. */
1322 sprintf (buf, "_methods%d", method_name_count++);
1323 array = build_decl (VAR_DECL, get_identifier (buf), type);
1324 DECL_INITIAL (array) = table;
1325 TREE_STATIC (array) = 1;
1326 DECL_ARTIFICIAL (array) = 1;
1327 DECL_IGNORED_P (array) = 1;
1328 rest_of_decl_compilation (array, (char*) 0, 1, 0);
1329
1330 table = build1 (ADDR_EXPR, ptr_type_node, array);
1331 }
1332
1333 PUSH_FIELD_VALUE (minit, "throws", table);
1334 }
1335
1336 FINISH_RECORD_CONSTRUCTOR (minit);
1337 return minit;
1338 }
1339
1340 static tree
1341 get_dispatch_vector (type)
1342 tree type;
1343 {
1344 tree vtable = TYPE_VTABLE (type);
1345 if (vtable == NULL)
1346 {
1347 HOST_WIDE_INT i;
1348 tree method;
1349 tree super = CLASSTYPE_SUPER (type);
1350 HOST_WIDE_INT nvirtuals = tree_low_cst (TYPE_NVIRTUALS (type), 0);
1351 vtable = make_tree_vec (nvirtuals);
1352 TYPE_VTABLE (type) = vtable;
1353 if (super != NULL_TREE)
1354 {
1355 tree super_vtable = get_dispatch_vector (super);
1356
1357 for (i = tree_low_cst (TYPE_NVIRTUALS (super), 0); --i >= 0; )
1358 TREE_VEC_ELT (vtable, i) = TREE_VEC_ELT (super_vtable, i);
1359 }
1360
1361 for (method = TYPE_METHODS (type); method != NULL_TREE;
1362 method = TREE_CHAIN (method))
1363 if (DECL_VINDEX (method) != NULL_TREE
1364 && host_integerp (DECL_VINDEX (method), 0))
1365 TREE_VEC_ELT (vtable, tree_low_cst (DECL_VINDEX (method), 0))
1366 = method;
1367 }
1368
1369 return vtable;
1370 }
1371
1372 static tree
1373 get_dispatch_table (type, this_class_addr)
1374 tree type, this_class_addr;
1375 {
1376 int abstract_p = CLASS_ABSTRACT (TYPE_NAME (type));
1377 tree vtable = get_dispatch_vector (type);
1378 int i, j;
1379 tree list = NULL_TREE;
1380 int nvirtuals = TREE_VEC_LENGTH (vtable);
1381 int arraysize;
1382 tree gc_descr;
1383
1384 for (i = nvirtuals; --i >= 0; )
1385 {
1386 tree method = TREE_VEC_ELT (vtable, i);
1387 if (METHOD_ABSTRACT (method))
1388 {
1389 if (! abstract_p)
1390 warning_with_decl (method,
1391 "abstract method in non-abstract class");
1392
1393 if (TARGET_VTABLE_USES_DESCRIPTORS)
1394 for (j = 0; j < TARGET_VTABLE_USES_DESCRIPTORS; ++j)
1395 list = tree_cons (NULL_TREE, null_pointer_node, list);
1396 else
1397 list = tree_cons (NULL_TREE, null_pointer_node, list);
1398 }
1399 else
1400 {
1401 if (!DECL_RTL_SET_P (method))
1402 make_decl_rtl (method, NULL);
1403
1404 if (TARGET_VTABLE_USES_DESCRIPTORS)
1405 for (j = 0; j < TARGET_VTABLE_USES_DESCRIPTORS; ++j)
1406 {
1407 tree fdesc = build (FDESC_EXPR, nativecode_ptr_type_node,
1408 method, build_int_2 (j, 0));
1409 TREE_CONSTANT (fdesc) = 1;
1410 list = tree_cons (NULL_TREE, fdesc, list);
1411 }
1412 else
1413 list = tree_cons (NULL_TREE,
1414 build1 (ADDR_EXPR, nativecode_ptr_type_node,
1415 method),
1416 list);
1417 }
1418 }
1419
1420 /* Dummy entry for compatibility with G++ -fvtable-thunks. When
1421 using the Boehm GC we sometimes stash a GC type descriptor
1422 there. We set the PURPOSE to NULL_TREE not to interfere (reset)
1423 the emitted byte count during the output to the assembly file. */
1424 /* With TARGET_VTABLE_USES_DESCRIPTORS, we only add one extra
1425 fake "function descriptor". It's first word is the is the class
1426 pointer, and subsequent words (usually one) contain the GC descriptor.
1427 In all other cases, we reserve two extra vtable slots. */
1428 gc_descr = get_boehm_type_descriptor (type);
1429 list = tree_cons (NULL_TREE, gc_descr, list);
1430 for (j = 1; j < TARGET_VTABLE_USES_DESCRIPTORS-1; ++j)
1431 list = tree_cons (NULL_TREE, gc_descr, list);
1432 list = tree_cons (NULL_TREE, this_class_addr, list);
1433
1434 /** Pointer to type_info object (to be implemented), according to g++ ABI. */
1435 list = tree_cons (NULL_TREE, null_pointer_node, list);
1436 /** Offset to start of whole object. Always (ptrdiff_t)0 for Java. */
1437 list = tree_cons (integer_zero_node, null_pointer_node, list);
1438
1439 arraysize = (TARGET_VTABLE_USES_DESCRIPTORS? nvirtuals + 1 : nvirtuals + 2);
1440 if (TARGET_VTABLE_USES_DESCRIPTORS)
1441 arraysize *= TARGET_VTABLE_USES_DESCRIPTORS;
1442 arraysize += 2;
1443 return build (CONSTRUCTOR,
1444 build_prim_array_type (nativecode_ptr_type_node, arraysize),
1445 NULL_TREE, list);
1446 }
1447
1448 void
1449 make_class_data (type)
1450 tree type;
1451 {
1452 tree decl, cons, temp;
1453 tree field, fields_decl;
1454 tree static_fields = NULL_TREE;
1455 tree instance_fields = NULL_TREE;
1456 HOST_WIDE_INT static_field_count = 0;
1457 HOST_WIDE_INT instance_field_count = 0;
1458 HOST_WIDE_INT field_count;
1459 tree field_array_type;
1460 tree method;
1461 tree methods = NULL_TREE;
1462 tree dtable_decl = NULL_TREE;
1463 HOST_WIDE_INT method_count = 0;
1464 tree method_array_type;
1465 tree methods_decl;
1466 tree super;
1467 tree this_class_addr;
1468 tree constant_pool_constructor;
1469 tree interfaces = null_pointer_node;
1470 int interface_len = 0;
1471 tree type_decl = TYPE_NAME (type);
1472 /** Offset from start of virtual function table declaration
1473 to where objects actually point at, following new g++ ABI. */
1474 tree dtable_start_offset = build_int_2 (2 * POINTER_SIZE / BITS_PER_UNIT, 0);
1475
1476 this_class_addr = build_class_ref (type);
1477 decl = TREE_OPERAND (this_class_addr, 0);
1478
1479 /* Build Field array. */
1480 field = TYPE_FIELDS (type);
1481 if (DECL_NAME (field) == NULL_TREE)
1482 field = TREE_CHAIN (field); /* Skip dummy field for inherited data. */
1483 for ( ; field != NULL_TREE; field = TREE_CHAIN (field))
1484 {
1485 if (! DECL_ARTIFICIAL (field))
1486 {
1487 tree init = make_field_value (field);
1488 if (FIELD_STATIC (field))
1489 {
1490 tree initial = DECL_INITIAL (field);
1491 static_field_count++;
1492 static_fields = tree_cons (NULL_TREE, init, static_fields);
1493 /* If the initial value is a string constant,
1494 prevent output_constant from trying to assemble the value. */
1495 if (initial != NULL_TREE
1496 && TREE_TYPE (initial) == string_ptr_type_node)
1497 DECL_INITIAL (field) = NULL_TREE;
1498 rest_of_decl_compilation (field, (char*) 0, 1, 1);
1499 DECL_INITIAL (field) = initial;
1500 }
1501 else
1502 {
1503 instance_field_count++;
1504 instance_fields = tree_cons (NULL_TREE, init, instance_fields);
1505 }
1506 }
1507 }
1508 field_count = static_field_count + instance_field_count;
1509 if (field_count > 0)
1510 {
1511 static_fields = nreverse (static_fields);
1512 instance_fields = nreverse (instance_fields);
1513 static_fields = chainon (static_fields, instance_fields);
1514 field_array_type = build_prim_array_type (field_type_node, field_count);
1515 fields_decl = build_decl (VAR_DECL, mangled_classname ("_FL_", type),
1516 field_array_type);
1517 DECL_INITIAL (fields_decl) = build (CONSTRUCTOR, field_array_type,
1518 NULL_TREE, static_fields);
1519 TREE_STATIC (fields_decl) = 1;
1520 DECL_ARTIFICIAL (fields_decl) = 1;
1521 DECL_IGNORED_P (fields_decl) = 1;
1522 rest_of_decl_compilation (fields_decl, (char*) 0, 1, 0);
1523 }
1524 else
1525 fields_decl = NULL_TREE;
1526
1527 /* Build Method array. */
1528 for (method = TYPE_METHODS (CLASS_TO_HANDLE_TYPE (type));
1529 method != NULL_TREE; method = TREE_CHAIN (method))
1530 {
1531 tree init;
1532 if (METHOD_PRIVATE (method)
1533 && ! flag_keep_inline_functions
1534 && (flag_inline_functions || optimize))
1535 continue;
1536 init = make_method_value (method);
1537 method_count++;
1538 methods = tree_cons (NULL_TREE, init, methods);
1539 }
1540 method_array_type = build_prim_array_type (method_type_node, method_count);
1541 methods_decl = build_decl (VAR_DECL, mangled_classname ("_MT_", type),
1542 method_array_type);
1543 DECL_INITIAL (methods_decl) = build (CONSTRUCTOR, method_array_type,
1544 NULL_TREE, nreverse (methods));
1545 TREE_STATIC (methods_decl) = 1;
1546 DECL_ARTIFICIAL (methods_decl) = 1;
1547 DECL_IGNORED_P (methods_decl) = 1;
1548 rest_of_decl_compilation (methods_decl, (char*) 0, 1, 0);
1549
1550 if (assume_compiled (IDENTIFIER_POINTER (DECL_NAME (type_decl)))
1551 && ! CLASS_INTERFACE (type_decl) && !flag_indirect_dispatch)
1552 {
1553 tree dtable = get_dispatch_table (type, this_class_addr);
1554 dtable_decl = build_dtable_decl (type);
1555 DECL_INITIAL (dtable_decl) = dtable;
1556 TREE_STATIC (dtable_decl) = 1;
1557 DECL_ARTIFICIAL (dtable_decl) = 1;
1558 DECL_IGNORED_P (dtable_decl) = 1;
1559 TREE_PUBLIC (dtable_decl) = 1;
1560 rest_of_decl_compilation (dtable_decl, (char*) 0, 1, 0);
1561 if (type == class_type_node)
1562 class_dtable_decl = dtable_decl;
1563 }
1564
1565 if (class_dtable_decl == NULL_TREE)
1566 {
1567 class_dtable_decl = build_dtable_decl (class_type_node);
1568 TREE_STATIC (class_dtable_decl) = 1;
1569 DECL_ARTIFICIAL (class_dtable_decl) = 1;
1570 DECL_IGNORED_P (class_dtable_decl) = 1;
1571 if (is_compiled_class (class_type_node) != 2)
1572 DECL_EXTERNAL (class_dtable_decl) = 1;
1573 rest_of_decl_compilation (class_dtable_decl, (char*) 0, 1, 0);
1574 }
1575
1576 super = CLASSTYPE_SUPER (type);
1577 if (super == NULL_TREE)
1578 super = null_pointer_node;
1579 else if (assume_compiled (IDENTIFIER_POINTER (DECL_NAME (type_decl))))
1580 super = build_class_ref (super);
1581 else
1582 {
1583 int super_index = alloc_class_constant (super);
1584 super = build_int_2 (super_index, 0);
1585 TREE_TYPE (super) = ptr_type_node;
1586 }
1587
1588 /* Build and emit the array of implemented interfaces. */
1589 if (type != object_type_node)
1590 interface_len = TREE_VEC_LENGTH (TYPE_BINFO_BASETYPES (type)) - 1;
1591 if (interface_len > 0)
1592 {
1593 tree init = NULL_TREE;
1594 int i;
1595 tree interface_array_type, idecl;
1596 interface_array_type
1597 = build_prim_array_type (class_ptr_type, interface_len);
1598 idecl = build_decl (VAR_DECL, mangled_classname ("_IF_", type),
1599 interface_array_type);
1600 for (i = interface_len; i > 0; i--)
1601 {
1602 tree child = TREE_VEC_ELT (TYPE_BINFO_BASETYPES (type), i);
1603 tree iclass = BINFO_TYPE (child);
1604 tree index;
1605 if (assume_compiled (IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (iclass)))))
1606 index = build_class_ref (iclass);
1607 else
1608 {
1609 int int_index = alloc_class_constant (iclass);
1610 index = build_int_2 (int_index, 0);
1611 TREE_TYPE (index) = ptr_type_node;
1612 }
1613 init = tree_cons (NULL_TREE, index, init);
1614 }
1615 DECL_INITIAL (idecl) = build (CONSTRUCTOR, interface_array_type,
1616 NULL_TREE, init);
1617 TREE_STATIC (idecl) = 1;
1618 DECL_ARTIFICIAL (idecl) = 1;
1619 DECL_IGNORED_P (idecl) = 1;
1620 interfaces = build1 (ADDR_EXPR, ptr_type_node, idecl);
1621 rest_of_decl_compilation (idecl, (char*) 0, 1, 0);
1622 }
1623
1624 constant_pool_constructor = build_constants_constructor ();
1625
1626 START_RECORD_CONSTRUCTOR (temp, object_type_node);
1627 PUSH_FIELD_VALUE (temp, "vtable",
1628 build (PLUS_EXPR, dtable_ptr_type,
1629 build1 (ADDR_EXPR, dtable_ptr_type, class_dtable_decl),
1630 dtable_start_offset));
1631 if (! flag_hash_synchronization)
1632 PUSH_FIELD_VALUE (temp, "sync_info", null_pointer_node);
1633 FINISH_RECORD_CONSTRUCTOR (temp);
1634 START_RECORD_CONSTRUCTOR (cons, class_type_node);
1635 PUSH_SUPER_VALUE (cons, temp);
1636 PUSH_FIELD_VALUE (cons, "next", null_pointer_node);
1637 PUSH_FIELD_VALUE (cons, "name", build_utf8_ref (DECL_NAME (type_decl)));
1638 PUSH_FIELD_VALUE (cons, "accflags",
1639 build_int_2 (get_access_flags_from_decl (type_decl), 0));
1640
1641 PUSH_FIELD_VALUE (cons, "superclass",
1642 CLASS_INTERFACE (type_decl) ? null_pointer_node : super);
1643 PUSH_FIELD_VALUE (cons, "constants", constant_pool_constructor);
1644 PUSH_FIELD_VALUE (cons, "methods",
1645 build1 (ADDR_EXPR, method_ptr_type_node, methods_decl));
1646 PUSH_FIELD_VALUE (cons, "method_count", build_int_2 (method_count, 0));
1647
1648 if (flag_indirect_dispatch)
1649 PUSH_FIELD_VALUE (cons, "vtable_method_count", integer_minus_one_node)
1650 else
1651 PUSH_FIELD_VALUE (cons, "vtable_method_count", TYPE_NVIRTUALS (type));
1652
1653 PUSH_FIELD_VALUE (cons, "fields",
1654 fields_decl == NULL_TREE ? null_pointer_node
1655 : build1 (ADDR_EXPR, field_ptr_type_node, fields_decl));
1656 PUSH_FIELD_VALUE (cons, "size_in_bytes", size_in_bytes (type));
1657 PUSH_FIELD_VALUE (cons, "field_count", build_int_2 (field_count, 0));
1658 PUSH_FIELD_VALUE (cons, "static_field_count",
1659 build_int_2 (static_field_count, 0));
1660
1661 if (flag_indirect_dispatch)
1662 PUSH_FIELD_VALUE (cons, "vtable", null_pointer_node)
1663 else
1664 PUSH_FIELD_VALUE (cons, "vtable",
1665 dtable_decl == NULL_TREE ? null_pointer_node
1666 : build (PLUS_EXPR, dtable_ptr_type,
1667 build1 (ADDR_EXPR, dtable_ptr_type, dtable_decl),
1668 dtable_start_offset));
1669
1670 if (otable_methods == NULL_TREE)
1671 {
1672 PUSH_FIELD_VALUE (cons, "otable", null_pointer_node);
1673 PUSH_FIELD_VALUE (cons, "otable_syms", null_pointer_node);
1674 }
1675 else
1676 {
1677 PUSH_FIELD_VALUE (cons, "otable",
1678 build1 (ADDR_EXPR, otable_ptr_type, otable_decl));
1679 PUSH_FIELD_VALUE (cons, "otable_syms",
1680 build1 (ADDR_EXPR, method_symbols_array_ptr_type,
1681 otable_syms_decl));
1682 }
1683 PUSH_FIELD_VALUE (cons, "interfaces", interfaces);
1684 PUSH_FIELD_VALUE (cons, "loader", null_pointer_node);
1685 PUSH_FIELD_VALUE (cons, "interface_count", build_int_2 (interface_len, 0));
1686 PUSH_FIELD_VALUE (cons, "state", integer_zero_node);
1687
1688 PUSH_FIELD_VALUE (cons, "thread", null_pointer_node);
1689 PUSH_FIELD_VALUE (cons, "depth", integer_zero_node);
1690 PUSH_FIELD_VALUE (cons, "ancestors", null_pointer_node);
1691 PUSH_FIELD_VALUE (cons, "idt", null_pointer_node);
1692 PUSH_FIELD_VALUE (cons, "arrayclass", null_pointer_node);
1693 PUSH_FIELD_VALUE (cons, "protectionDomain", null_pointer_node);
1694
1695 FINISH_RECORD_CONSTRUCTOR (cons);
1696
1697 DECL_INITIAL (decl) = cons;
1698
1699 /* Hash synchronization requires at least 64-bit alignment. */
1700 if (flag_hash_synchronization && POINTER_SIZE < 64)
1701 DECL_ALIGN (decl) = 64;
1702
1703 rest_of_decl_compilation (decl, (char*) 0, 1, 0);
1704 }
1705
1706 void
1707 finish_class ()
1708 {
1709 tree method;
1710 tree type_methods = TYPE_METHODS (CLASS_TO_HANDLE_TYPE (current_class));
1711 int saw_native_method = 0;
1712
1713 /* Find out if we have any native methods. We use this information
1714 later. */
1715 for (method = type_methods;
1716 method != NULL_TREE;
1717 method = TREE_CHAIN (method))
1718 {
1719 if (METHOD_NATIVE (method))
1720 {
1721 saw_native_method = 1;
1722 break;
1723 }
1724 }
1725
1726 /* Emit deferred inline methods. */
1727 for (method = type_methods; method != NULL_TREE; )
1728 {
1729 if (! TREE_ASM_WRITTEN (method) && DECL_SAVED_INSNS (method) != 0)
1730 {
1731 output_inline_function (method);
1732 /* Scan the list again to see if there are any earlier
1733 methods to emit. */
1734 method = type_methods;
1735 continue;
1736 }
1737 method = TREE_CHAIN (method);
1738 }
1739
1740 current_function_decl = NULL_TREE;
1741 make_class_data (current_class);
1742 register_class ();
1743 rest_of_decl_compilation (TYPE_NAME (current_class), (char*) 0, 1, 0);
1744 }
1745
1746 /* Return 2 if CLASS is compiled by this compilation job;
1747 return 1 if CLASS can otherwise be assumed to be compiled;
1748 return 0 if we cannot assume that CLASS is compiled.
1749 Returns 1 for primitive and 0 for array types. */
1750 int
1751 is_compiled_class (class)
1752 tree class;
1753 {
1754 int seen_in_zip;
1755 if (TREE_CODE (class) == POINTER_TYPE)
1756 class = TREE_TYPE (class);
1757 if (TREE_CODE (class) != RECORD_TYPE) /* Primitive types are static. */
1758 return 1;
1759 if (TYPE_ARRAY_P (class))
1760 return 0;
1761 if (class == current_class)
1762 return 2;
1763
1764 seen_in_zip = (TYPE_JCF (class) && JCF_SEEN_IN_ZIP (TYPE_JCF (class)));
1765 if (CLASS_FROM_CURRENTLY_COMPILED_P (class) || seen_in_zip)
1766 {
1767 /* The class was seen in the current ZIP file and will be
1768 available as a compiled class in the future but may not have
1769 been loaded already. Load it if necessary. This prevent
1770 build_class_ref () from crashing. */
1771
1772 if (seen_in_zip && !CLASS_LOADED_P (class))
1773 load_class (class, 1);
1774
1775 /* We return 2 for class seen in ZIP and class from files
1776 belonging to the same compilation unit */
1777 return 2;
1778 }
1779
1780 if (assume_compiled (IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (class)))))
1781 {
1782 if (!CLASS_LOADED_P (class))
1783 {
1784 if (CLASS_FROM_SOURCE_P (class))
1785 safe_layout_class (class);
1786 else
1787 load_class (class, 1);
1788 }
1789 return 1;
1790 }
1791
1792 return 0;
1793 }
1794
1795 /* Build a VAR_DECL for the dispatch table (vtable) for class TYPE. */
1796
1797 tree
1798 build_dtable_decl (type)
1799 tree type;
1800 {
1801 tree dtype;
1802
1803 /* We need to build a new dtable type so that its size is uniquely
1804 computed when we're dealing with the class for real and not just
1805 faking it (like java.lang.Class during the initialization of the
1806 compiler.) We know we're not faking a class when CURRENT_CLASS is
1807 TYPE. */
1808 if (current_class == type)
1809 {
1810 tree dummy = NULL_TREE;
1811 int n;
1812
1813 dtype = make_node (RECORD_TYPE);
1814
1815 PUSH_FIELD (dtype, dummy, "top_offset", ptr_type_node);
1816 PUSH_FIELD (dtype, dummy, "type_info", ptr_type_node);
1817
1818 PUSH_FIELD (dtype, dummy, "class", class_ptr_type);
1819 for (n = 1; n < TARGET_VTABLE_USES_DESCRIPTORS; ++n)
1820 {
1821 tree tmp_field = build_decl (FIELD_DECL, NULL_TREE, ptr_type_node);
1822 TREE_CHAIN (dummy) = tmp_field;
1823 DECL_CONTEXT (tmp_field) = dtype;
1824 DECL_ARTIFICIAL (tmp_field) = 1;
1825 dummy = tmp_field;
1826 }
1827
1828 PUSH_FIELD (dtype, dummy, "gc_descr", ptr_type_node);
1829 for (n = 1; n < TARGET_VTABLE_USES_DESCRIPTORS; ++n)
1830 {
1831 tree tmp_field = build_decl (FIELD_DECL, NULL_TREE, ptr_type_node);
1832 TREE_CHAIN (dummy) = tmp_field;
1833 DECL_CONTEXT (tmp_field) = dtype;
1834 DECL_ARTIFICIAL (tmp_field) = 1;
1835 dummy = tmp_field;
1836 }
1837
1838 n = TREE_VEC_LENGTH (get_dispatch_vector (type));
1839 if (TARGET_VTABLE_USES_DESCRIPTORS)
1840 n *= TARGET_VTABLE_USES_DESCRIPTORS;
1841
1842 PUSH_FIELD (dtype, dummy, "methods",
1843 build_prim_array_type (nativecode_ptr_type_node, n));
1844 layout_type (dtype);
1845 }
1846 else
1847 dtype = dtable_type;
1848
1849 return build_decl (VAR_DECL,
1850 java_mangle_vtable (&temporary_obstack, type), dtype);
1851 }
1852
1853 /* Pre-pend the TYPE_FIELDS of THIS_CLASS with a dummy FIELD_DECL for the
1854 fields inherited from SUPER_CLASS. */
1855
1856 void
1857 push_super_field (this_class, super_class)
1858 tree this_class, super_class;
1859 {
1860 tree base_decl;
1861 /* Don't insert the field if we're just re-laying the class out. */
1862 if (TYPE_FIELDS (this_class) && !DECL_NAME (TYPE_FIELDS (this_class)))
1863 return;
1864 base_decl = build_decl (FIELD_DECL, NULL_TREE, super_class);
1865 DECL_IGNORED_P (base_decl) = 1;
1866 TREE_CHAIN (base_decl) = TYPE_FIELDS (this_class);
1867 TYPE_FIELDS (this_class) = base_decl;
1868 DECL_SIZE (base_decl) = TYPE_SIZE (super_class);
1869 DECL_SIZE_UNIT (base_decl) = TYPE_SIZE_UNIT (super_class);
1870 }
1871
1872 /* Handle the different manners we may have to lay out a super class. */
1873
1874 static tree
1875 maybe_layout_super_class (super_class, this_class)
1876 tree super_class;
1877 tree this_class;
1878 {
1879 if (TREE_CODE (super_class) == RECORD_TYPE)
1880 {
1881 if (!CLASS_LOADED_P (super_class) && CLASS_FROM_SOURCE_P (super_class))
1882 safe_layout_class (super_class);
1883 if (!CLASS_LOADED_P (super_class))
1884 load_class (super_class, 1);
1885 }
1886 /* We might have to layout the class before its dependency on
1887 the super class gets resolved by java_complete_class */
1888 else if (TREE_CODE (super_class) == POINTER_TYPE)
1889 {
1890 if (TREE_TYPE (super_class) != NULL_TREE)
1891 super_class = TREE_TYPE (super_class);
1892 else
1893 {
1894 super_class = do_resolve_class (NULL_TREE, /* FIXME? */
1895 super_class, NULL_TREE, this_class);
1896 if (!super_class)
1897 return NULL_TREE; /* FIXME, NULL_TREE not checked by caller. */
1898 super_class = TREE_TYPE (super_class);
1899 }
1900 }
1901 if (!TYPE_SIZE (super_class))
1902 safe_layout_class (super_class);
1903
1904 return super_class;
1905 }
1906
1907 void
1908 layout_class (this_class)
1909 tree this_class;
1910 {
1911 tree super_class = CLASSTYPE_SUPER (this_class);
1912 tree field;
1913
1914 class_list = tree_cons (this_class, NULL_TREE, class_list);
1915 if (CLASS_BEING_LAIDOUT (this_class))
1916 {
1917 char buffer [1024];
1918 char *report;
1919 tree current;
1920
1921 sprintf (buffer, " with `%s'",
1922 IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (this_class))));
1923 obstack_grow (&temporary_obstack, buffer, strlen (buffer));
1924
1925 for (current = TREE_CHAIN (class_list); current;
1926 current = TREE_CHAIN (current))
1927 {
1928 tree decl = TYPE_NAME (TREE_PURPOSE (current));
1929 sprintf (buffer, "\n which inherits from `%s' (%s:%d)",
1930 IDENTIFIER_POINTER (DECL_NAME (decl)),
1931 DECL_SOURCE_FILE (decl),
1932 DECL_SOURCE_LINE (decl));
1933 obstack_grow (&temporary_obstack, buffer, strlen (buffer));
1934 }
1935 obstack_1grow (&temporary_obstack, '\0');
1936 report = obstack_finish (&temporary_obstack);
1937 cyclic_inheritance_report = ggc_strdup (report);
1938 obstack_free (&temporary_obstack, report);
1939 TYPE_SIZE (this_class) = error_mark_node;
1940 return;
1941 }
1942 CLASS_BEING_LAIDOUT (this_class) = 1;
1943
1944 if (super_class && !CLASS_BEING_LAIDOUT (super_class))
1945 {
1946 tree maybe_super_class
1947 = maybe_layout_super_class (super_class, this_class);
1948 if (maybe_super_class == NULL
1949 || TREE_CODE (TYPE_SIZE (maybe_super_class)) == ERROR_MARK)
1950 {
1951 TYPE_SIZE (this_class) = error_mark_node;
1952 CLASS_BEING_LAIDOUT (this_class) = 0;
1953 class_list = TREE_CHAIN (class_list);
1954 return;
1955 }
1956 if (TYPE_SIZE (this_class) == NULL_TREE)
1957 push_super_field (this_class, maybe_super_class);
1958 }
1959
1960 for (field = TYPE_FIELDS (this_class);
1961 field != NULL_TREE; field = TREE_CHAIN (field))
1962 {
1963 if (FIELD_STATIC (field))
1964 {
1965 /* Set DECL_ASSEMBLER_NAME to something suitably mangled. */
1966 SET_DECL_ASSEMBLER_NAME (field,
1967 java_mangle_decl
1968 (&temporary_obstack, field));
1969 }
1970 }
1971
1972 layout_type (this_class);
1973
1974 /* Also recursively load/layout any superinterfaces, but only if class was
1975 loaded from bytecode. The source parser will take care of this itself. */
1976 if (!CLASS_FROM_SOURCE_P (this_class))
1977 {
1978 tree basetype_vec = TYPE_BINFO_BASETYPES (this_class);
1979
1980 if (basetype_vec)
1981 {
1982 int n = TREE_VEC_LENGTH (basetype_vec) - 1;
1983 int i;
1984 for (i = n; i > 0; i--)
1985 {
1986 tree vec_elt = TREE_VEC_ELT (basetype_vec, i);
1987 tree super_interface = BINFO_TYPE (vec_elt);
1988
1989 tree maybe_super_interface
1990 = maybe_layout_super_class (super_interface, NULL_TREE);
1991 if (maybe_super_interface == NULL
1992 || TREE_CODE (TYPE_SIZE (maybe_super_interface)) == ERROR_MARK)
1993 {
1994 TYPE_SIZE (this_class) = error_mark_node;
1995 CLASS_BEING_LAIDOUT (this_class) = 0;
1996 class_list = TREE_CHAIN (class_list);
1997 return;
1998 }
1999 }
2000 }
2001 }
2002
2003 /* Convert the size back to an SI integer value */
2004 TYPE_SIZE_UNIT (this_class) =
2005 fold (convert (int_type_node, TYPE_SIZE_UNIT (this_class)));
2006
2007 CLASS_BEING_LAIDOUT (this_class) = 0;
2008 class_list = TREE_CHAIN (class_list);
2009 }
2010
2011 void
2012 layout_class_methods (this_class)
2013 tree this_class;
2014 {
2015 tree method_decl, dtable_count;
2016 tree super_class, handle_type;
2017
2018 if (TYPE_NVIRTUALS (this_class))
2019 return;
2020
2021 super_class = CLASSTYPE_SUPER (this_class);
2022 handle_type = CLASS_TO_HANDLE_TYPE (this_class);
2023
2024 if (super_class)
2025 {
2026 super_class = maybe_layout_super_class (super_class, this_class);
2027 if (!TYPE_NVIRTUALS (super_class))
2028 layout_class_methods (super_class);
2029 dtable_count = TYPE_NVIRTUALS (super_class);
2030 }
2031 else
2032 dtable_count = integer_zero_node;
2033
2034 TYPE_METHODS (handle_type) = nreverse (TYPE_METHODS (handle_type));
2035
2036 for (method_decl = TYPE_METHODS (handle_type);
2037 method_decl; method_decl = TREE_CHAIN (method_decl))
2038 dtable_count = layout_class_method (this_class, super_class,
2039 method_decl, dtable_count);
2040
2041 TYPE_NVIRTUALS (this_class) = dtable_count;
2042
2043 #ifdef JAVA_USE_HANDLES
2044 layout_type (handle_type);
2045 #endif
2046 }
2047
2048 /* Return 0 if NAME is equal to STR, -1 if STR is "less" than NAME,
2049 and 1 if STR is "greater" than NAME. */
2050
2051 /* Lay METHOD_DECL out, returning a possibly new value of
2052 DTABLE_COUNT. Also mangle the method's name. */
2053
2054 tree
2055 layout_class_method (this_class, super_class, method_decl, dtable_count)
2056 tree this_class, super_class, method_decl, dtable_count;
2057 {
2058 tree method_name = DECL_NAME (method_decl);
2059
2060 TREE_PUBLIC (method_decl) = 1;
2061
2062 /* This is a good occasion to mangle the method's name */
2063 SET_DECL_ASSEMBLER_NAME (method_decl,
2064 java_mangle_decl (&temporary_obstack,
2065 method_decl));
2066 /* We don't generate a RTL for the method if it's abstract, or if
2067 it's an interface method that isn't clinit. */
2068 if (! METHOD_ABSTRACT (method_decl)
2069 || (CLASS_INTERFACE (TYPE_NAME (this_class))
2070 && (DECL_CLINIT_P (method_decl))))
2071 make_decl_rtl (method_decl, NULL);
2072
2073 if (ID_INIT_P (method_name))
2074 {
2075 const char *p = IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME (this_class)));
2076 const char *ptr;
2077 for (ptr = p; *ptr; )
2078 {
2079 if (*ptr++ == '.')
2080 p = ptr;
2081 }
2082 DECL_CONSTRUCTOR_P (method_decl) = 1;
2083 build_java_argument_signature (TREE_TYPE (method_decl));
2084 }
2085 else if (! METHOD_STATIC (method_decl) && !DECL_ARTIFICIAL (method_decl))
2086 {
2087 tree method_sig =
2088 build_java_argument_signature (TREE_TYPE (method_decl));
2089 tree super_method = lookup_argument_method (super_class, method_name,
2090 method_sig);
2091 if (super_method != NULL_TREE && ! METHOD_PRIVATE (super_method))
2092 {
2093 DECL_VINDEX (method_decl) = DECL_VINDEX (super_method);
2094 if (DECL_VINDEX (method_decl) == NULL_TREE
2095 && !CLASS_FROM_SOURCE_P (this_class))
2096 error_with_decl (method_decl,
2097 "non-static method '%s' overrides static method");
2098 }
2099 else if (! METHOD_FINAL (method_decl)
2100 && ! METHOD_PRIVATE (method_decl)
2101 && ! CLASS_FINAL (TYPE_NAME (this_class))
2102 && dtable_count)
2103 {
2104 DECL_VINDEX (method_decl) = dtable_count;
2105 dtable_count = fold (build (PLUS_EXPR, integer_type_node,
2106 dtable_count, integer_one_node));
2107 }
2108 }
2109
2110 return dtable_count;
2111 }
2112
2113 void
2114 register_class ()
2115 {
2116 /* END does not need to be registered with the garbage collector
2117 because it always points into the list given by REGISTERED_CLASS,
2118 and that variable is registered with the collector. */
2119 static tree end;
2120 tree node = TREE_OPERAND (build_class_ref (current_class), 0);
2121 tree current = copy_node (node);
2122
2123 XEXP (DECL_RTL (current), 0) = copy_rtx (XEXP (DECL_RTL(node), 0));
2124 if (!registered_class)
2125 registered_class = current;
2126 else
2127 TREE_CHAIN (end) = current;
2128
2129 end = current;
2130 }
2131
2132 /* Emit something to register classes at start-up time.
2133
2134 The preferred mechanism is through the .jcr section, which contain
2135 a list of pointers to classes which get registered during
2136 constructor invoction time. The fallback mechanism is to generate
2137 a `constructor' function which calls _Jv_RegisterClass for each
2138 class in this file. */
2139
2140 void
2141 emit_register_classes ()
2142 {
2143 /* ??? This isn't quite the correct test. We also have to know
2144 that the target is using gcc's crtbegin/crtend objects rather
2145 than the ones that come with the operating system. */
2146 if (SUPPORTS_WEAK && targetm.have_named_sections)
2147 {
2148 #ifdef JCR_SECTION_NAME
2149 tree t;
2150 named_section_flags (JCR_SECTION_NAME, SECTION_WRITE);
2151 assemble_align (POINTER_SIZE);
2152 for (t = registered_class; t; t = TREE_CHAIN (t))
2153 assemble_integer (XEXP (DECL_RTL (t), 0),
2154 POINTER_SIZE / BITS_PER_UNIT, POINTER_SIZE, 1);
2155 #else
2156 abort ();
2157 #endif
2158 }
2159 else
2160 {
2161 extern tree get_file_function_name PARAMS ((int));
2162 tree init_name = get_file_function_name ('I');
2163 tree init_type = build_function_type (void_type_node, end_params_node);
2164 tree init_decl;
2165 tree t;
2166
2167 init_decl = build_decl (FUNCTION_DECL, init_name, init_type);
2168 SET_DECL_ASSEMBLER_NAME (init_decl, init_name);
2169 TREE_STATIC (init_decl) = 1;
2170 current_function_decl = init_decl;
2171 DECL_RESULT (init_decl) = build_decl (RESULT_DECL, NULL_TREE,
2172 void_type_node);
2173
2174 /* It can be a static function as long as collect2 does not have
2175 to scan the object file to find its ctor/dtor routine. */
2176 TREE_PUBLIC (init_decl) = ! targetm.have_ctors_dtors;
2177
2178 /* Suppress spurious warnings. */
2179 TREE_USED (init_decl) = 1;
2180
2181 pushlevel (0);
2182 make_decl_rtl (init_decl, NULL);
2183 init_function_start (init_decl, input_filename, 0);
2184 expand_function_start (init_decl, 0);
2185
2186 /* Do not allow the function to be deferred. */
2187 current_function_cannot_inline
2188 = "static constructors and destructors cannot be inlined";
2189
2190 for ( t = registered_class; t; t = TREE_CHAIN (t))
2191 emit_library_call (registerClass_libfunc, 0, VOIDmode, 1,
2192 XEXP (DECL_RTL (t), 0), Pmode);
2193
2194 expand_function_end (input_filename, 0, 0);
2195 poplevel (1, 0, 1);
2196 rest_of_compilation (init_decl);
2197 current_function_decl = NULL_TREE;
2198
2199 if (targetm.have_ctors_dtors)
2200 (* targetm.asm_out.constructor) (XEXP (DECL_RTL (init_decl), 0),
2201 DEFAULT_INIT_PRIORITY);
2202 }
2203 }
2204
2205 /* Make a method_symbol_type (_Jv_MethodSymbol) node for METHOD. */
2206
2207 tree
2208 build_method_symbols_entry (tree method)
2209 {
2210 tree clname, name, signature, method_symbol;
2211
2212 clname = build_utf8_ref (DECL_NAME (TYPE_NAME (DECL_CONTEXT (method))));
2213 name = build_utf8_ref (DECL_NAME (method));
2214 signature = build_java_signature (TREE_TYPE (method));
2215 signature = build_utf8_ref (unmangle_classname
2216 (IDENTIFIER_POINTER (signature),
2217 IDENTIFIER_LENGTH (signature)));
2218
2219 START_RECORD_CONSTRUCTOR (method_symbol, method_symbol_type);
2220 PUSH_FIELD_VALUE (method_symbol, "clname", clname);
2221 PUSH_FIELD_VALUE (method_symbol, "name", name);
2222 PUSH_FIELD_VALUE (method_symbol, "signature", signature);
2223 FINISH_RECORD_CONSTRUCTOR (method_symbol);
2224 TREE_CONSTANT (method_symbol) = 1;
2225
2226 return method_symbol;
2227 }
2228
2229 /* Emit the offset symbols table for indirect virtual dispatch. */
2230
2231 void
2232 emit_offset_symbol_table ()
2233 {
2234 tree method_list, method, table, list, null_symbol;
2235 tree otable_bound, otable_array_type;
2236 int index;
2237
2238 /* Only emit an offset table if this translation unit actually made virtual
2239 calls. */
2240 if (otable_methods == NULL_TREE)
2241 return;
2242
2243 /* Build a list of _Jv_MethodSymbols for each entry in otable_methods. */
2244 index = 0;
2245 method_list = otable_methods;
2246 list = NULL_TREE;
2247 while (method_list != NULL_TREE)
2248 {
2249 method = TREE_VALUE (method_list);
2250 list = tree_cons (NULL_TREE, build_method_symbols_entry (method), list);
2251 method_list = TREE_CHAIN (method_list);
2252 index++;
2253 }
2254
2255 /* Terminate the list with a "null" entry. */
2256 START_RECORD_CONSTRUCTOR (null_symbol, method_symbol_type);
2257 PUSH_FIELD_VALUE (null_symbol, "clname", null_pointer_node);
2258 PUSH_FIELD_VALUE (null_symbol, "name", null_pointer_node);
2259 PUSH_FIELD_VALUE (null_symbol, "signature", null_pointer_node);
2260 FINISH_RECORD_CONSTRUCTOR (null_symbol);
2261 TREE_CONSTANT (null_symbol) = 1;
2262 list = tree_cons (NULL_TREE, null_symbol, list);
2263
2264 /* Put the list in the right order and make it a constructor. */
2265 list = nreverse (list);
2266 table = build (CONSTRUCTOR, method_symbols_array_type, NULL_TREE, list);
2267
2268 /* Make it the initial value for otable_syms and emit the decl. */
2269 DECL_INITIAL (otable_syms_decl) = table;
2270 DECL_ARTIFICIAL (otable_syms_decl) = 1;
2271 DECL_IGNORED_P (otable_syms_decl) = 1;
2272 rest_of_decl_compilation (otable_syms_decl, NULL, 1, 0);
2273
2274 /* Now that its size is known, redefine otable as an uninitialized static
2275 array of INDEX + 1 integers. The extra entry is used by the runtime
2276 to track whether the otable has been initialized. */
2277 otable_bound = build_index_type (build_int_2 (index, 0));
2278 otable_array_type = build_array_type (integer_type_node, otable_bound);
2279 otable_decl = build_decl (VAR_DECL, get_identifier ("otable"),
2280 otable_array_type);
2281 TREE_STATIC (otable_decl) = 1;
2282 TREE_READONLY (otable_decl) = 1;
2283 rest_of_decl_compilation (otable_decl, NULL, 1, 0);
2284 }
2285
2286 void
2287 init_class_processing ()
2288 {
2289 registerClass_libfunc = gen_rtx_SYMBOL_REF (Pmode, "_Jv_RegisterClass");
2290 registerResource_libfunc =
2291 gen_rtx_SYMBOL_REF (Pmode, "_Jv_RegisterResource");
2292 fields_ident = get_identifier ("fields");
2293 info_ident = get_identifier ("info");
2294 gcc_obstack_init (&temporary_obstack);
2295 }
2296 \f
2297 static hashval_t java_treetreehash_hash PARAMS ((const void *));
2298 static int java_treetreehash_compare PARAMS ((const void *, const void *));
2299
2300 /* A hash table mapping trees to trees. Used generally. */
2301
2302 #define JAVA_TREEHASHHASH_H(t) ((hashval_t) (t))
2303
2304 static hashval_t
2305 java_treetreehash_hash (k_p)
2306 const void *k_p;
2307 {
2308 struct treetreehash_entry *k = (struct treetreehash_entry *) k_p;
2309 return JAVA_TREEHASHHASH_H (k->key);
2310 }
2311
2312 static int
2313 java_treetreehash_compare (k1_p, k2_p)
2314 const void * k1_p;
2315 const void * k2_p;
2316 {
2317 struct treetreehash_entry * k1 = (struct treetreehash_entry *) k1_p;
2318 tree k2 = (tree) k2_p;
2319 return (k1->key == k2);
2320 }
2321
2322 tree
2323 java_treetreehash_find (ht, t)
2324 htab_t ht;
2325 tree t;
2326 {
2327 struct treetreehash_entry *e;
2328 hashval_t hv = JAVA_TREEHASHHASH_H (t);
2329 e = (struct treetreehash_entry *) htab_find_with_hash (ht, t, hv);
2330 if (e == NULL)
2331 return NULL;
2332 else
2333 return e->value;
2334 }
2335
2336 tree *
2337 java_treetreehash_new (ht, t)
2338 htab_t ht;
2339 tree t;
2340 {
2341 PTR *e;
2342 struct treetreehash_entry *tthe;
2343 hashval_t hv = JAVA_TREEHASHHASH_H (t);
2344
2345 e = htab_find_slot_with_hash (ht, t, hv, INSERT);
2346 if (*e == NULL)
2347 {
2348 tthe = (*ht->alloc_f) (1, sizeof (*tthe));
2349 tthe->key = t;
2350 *e = (PTR) tthe;
2351 }
2352 else
2353 tthe = (struct treetreehash_entry *) *e;
2354 return &tthe->value;
2355 }
2356
2357 htab_t
2358 java_treetreehash_create (size, gc)
2359 size_t size;
2360 int gc;
2361 {
2362 if (gc)
2363 return htab_create_ggc (size, java_treetreehash_hash,
2364 java_treetreehash_compare, NULL);
2365 else
2366 return htab_create_alloc (size, java_treetreehash_hash,
2367 java_treetreehash_compare, free, xcalloc, free);
2368 }
2369
2370 #include "gt-java-class.h"