tree.h (struct tree_common): Rename raises_flag to nothrow_flag.
[gcc.git] / gcc / cp / rtti.c
1 /* RunTime Type Identification
2 Copyright (C) 1995, 1996, 1997, 1998, 1999, 2000
3 Free Software Foundation, Inc.
4 Mostly written by Jason Merrill (jason@cygnus.com).
5
6 This file is part of GNU CC.
7
8 GNU CC is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2, or (at your option)
11 any later version.
12
13 GNU CC is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GNU CC; see the file COPYING. If not, write to
20 the Free Software Foundation, 59 Temple Place - Suite 330,
21 Boston, MA 02111-1307, USA. */
22
23
24 #include "config.h"
25 #include "system.h"
26 #include "tree.h"
27 #include "cp-tree.h"
28 #include "flags.h"
29 #include "output.h"
30 #include "assert.h"
31 #include "toplev.h"
32
33 #ifndef INT_TYPE_SIZE
34 #define INT_TYPE_SIZE BITS_PER_WORD
35 #endif
36
37 /* Accessors for the type_info objects. We need to remember several things
38 about each of the type_info types. The global tree nodes such as
39 bltn_desc_type_node are TREE_LISTs, and these macros are used to access
40 the required information. */
41 /* The RECORD_TYPE of a type_info derived class. */
42 #define TINFO_PSEUDO_TYPE(NODE) TREE_TYPE (NODE)
43 /* The VAR_DECL of the vtable for the type_info derived class. */
44 #define TINFO_VTABLE_DECL(NODE) TREE_VALUE (NODE)
45
46 extern struct obstack permanent_obstack;
47
48 static tree build_runtime_decl PARAMS((const char *, tree));
49 static tree build_headof_sub PARAMS((tree));
50 static tree build_headof PARAMS((tree));
51 static tree get_tinfo_var PARAMS((tree));
52 static tree ifnonnull PARAMS((tree, tree));
53 static tree tinfo_name PARAMS((tree));
54 static tree get_base_offset PARAMS((tree, tree));
55 static tree build_dynamic_cast_1 PARAMS((tree, tree));
56 static void expand_si_desc PARAMS((tree, tree));
57 static void expand_class_desc PARAMS((tree, tree));
58 static void expand_attr_desc PARAMS((tree, tree));
59 static void expand_ptr_desc PARAMS((tree, tree));
60 static void expand_generic_desc PARAMS((tree, tree, const char *));
61 static tree throw_bad_cast PARAMS((void));
62 static tree throw_bad_typeid PARAMS((void));
63 static tree get_tinfo_decl_dynamic PARAMS((tree));
64 static tree tinfo_from_decl PARAMS((tree));
65 static int qualifier_flags PARAMS((tree));
66 static tree tinfo_base_init PARAMS((tree, tree));
67 static tree generic_initializer PARAMS((tree, tree));
68 static tree ptr_ref_initializer PARAMS((tree, tree));
69 static tree ptmd_initializer PARAMS((tree, tree));
70 static int class_hint_flags PARAMS((tree));
71 static tree class_initializer PARAMS((tree, tree, tree));
72 static tree synthesize_tinfo_var PARAMS((tree, tree));
73 static tree create_real_tinfo_var PARAMS((tree, tree, tree));
74 static tree create_pseudo_type_info PARAMS((const char *, int, ...));
75 static tree get_vmi_pseudo_type_info PARAMS((int));
76 static void create_tinfo_types PARAMS((void));
77
78 static int doing_runtime = 0;
79 \f
80 void
81 init_rtti_processing ()
82 {
83 if (flag_honor_std)
84 push_namespace (get_identifier ("std"));
85 type_info_type_node = xref_tag
86 (class_type_node, get_identifier ("type_info"), 1);
87 if (flag_honor_std)
88 pop_namespace ();
89 if (!new_abi_rtti_p ())
90 {
91 tinfo_decl_id = get_identifier ("__tf");
92 tinfo_decl_type = build_function_type
93 (build_reference_type
94 (build_qualified_type
95 (type_info_type_node, TYPE_QUAL_CONST)),
96 void_list_node);
97 }
98 else
99 {
100 tinfo_decl_id = get_identifier ("__ti");
101 tinfo_decl_type = build_qualified_type
102 (type_info_type_node, TYPE_QUAL_CONST);
103 }
104 tinfo_var_id = get_identifier ("__ti");
105 }
106
107 /* Given a pointer to an object with at least one virtual table
108 pointer somewhere, return a pointer to a possible sub-object that
109 has a virtual table pointer in it that is the vtable parent for
110 that sub-object. */
111
112 static tree
113 build_headof_sub (exp)
114 tree exp;
115 {
116 tree type = TREE_TYPE (TREE_TYPE (exp));
117 tree basetype = CLASSTYPE_RTTI (type);
118 tree binfo = get_binfo (basetype, type, 0);
119
120 exp = convert_pointer_to_real (binfo, exp);
121 return exp;
122 }
123
124 /* Given the expression EXP of type `class *', return the head of the
125 object pointed to by EXP with type cv void*, if the class has any
126 virtual functions (TYPE_POLYMORPHIC_P), else just return the
127 expression. */
128
129 static tree
130 build_headof (exp)
131 tree exp;
132 {
133 tree type = TREE_TYPE (exp);
134 tree aref;
135 tree offset;
136
137 my_friendly_assert (TREE_CODE (type) == POINTER_TYPE, 20000112);
138 type = TREE_TYPE (type);
139
140 if (!TYPE_POLYMORPHIC_P (type))
141 return exp;
142 if (CLASSTYPE_COM_INTERFACE (type))
143 {
144 cp_error ("RTTI not supported for COM interface type `%T'", type);
145 return error_mark_node;
146 }
147
148 /* If we don't have rtti stuff, get to a sub-object that does. */
149 if (!CLASSTYPE_VFIELDS (TREE_TYPE (TREE_TYPE (exp))))
150 exp = build_headof_sub (exp);
151
152 /* We use this a couple of times below, protect it. */
153 exp = save_expr (exp);
154
155 aref = build_vtbl_ref (build_indirect_ref (exp, NULL_PTR), integer_zero_node);
156
157 if (flag_vtable_thunks)
158 offset = aref;
159 else
160 offset = build_component_ref (aref, delta_identifier, NULL_TREE, 0);
161
162 type = build_qualified_type (ptr_type_node,
163 CP_TYPE_QUALS (TREE_TYPE (exp)));
164 return build (PLUS_EXPR, type, exp,
165 cp_convert (ptrdiff_type_node, offset));
166 }
167
168 /* Build a decl to a runtime entry point taking void and returning TYPE.
169 Although the entry point may never return, making its return type
170 consistent is necessary. */
171
172 static tree
173 build_runtime_decl (name, type)
174 const char *name;
175 tree type;
176 {
177 tree d = get_identifier (name);
178
179 if (IDENTIFIER_GLOBAL_VALUE (d))
180 d = IDENTIFIER_GLOBAL_VALUE (d);
181 else
182 {
183 type = build_function_type (type, void_list_node);
184 d = build_lang_decl (FUNCTION_DECL, d, type);
185 DECL_EXTERNAL (d) = 1;
186 TREE_PUBLIC (d) = 1;
187 DECL_ARTIFICIAL (d) = 1;
188 TREE_THIS_VOLATILE (d) = 1;
189 pushdecl_top_level (d);
190 make_function_rtl (d);
191 }
192
193 mark_used (d);
194 return d;
195 }
196
197 /* Get a bad_cast node for the program to throw...
198
199 See libstdc++/exception.cc for __throw_bad_cast */
200
201 static tree
202 throw_bad_cast ()
203 {
204 if (!throw_bad_cast_node)
205 throw_bad_cast_node = build_runtime_decl
206 ("__throw_bad_cast", ptr_type_node);
207
208 return build_call (throw_bad_cast_node,
209 TREE_TYPE (TREE_TYPE (throw_bad_cast_node)),
210 NULL_TREE);
211 }
212
213 static tree
214 throw_bad_typeid ()
215 {
216 if (!throw_bad_typeid_node)
217 throw_bad_typeid_node = build_runtime_decl
218 ("__throw_bad_typeid",
219 build_reference_type
220 (build_qualified_type
221 (type_info_type_node, TYPE_QUAL_CONST)));
222
223 return build_call (throw_bad_typeid_node,
224 TREE_TYPE (TREE_TYPE (throw_bad_typeid_node)),
225 NULL_TREE);
226 }
227 \f
228 /* Return a pointer to type_info function associated with the expression EXP.
229 If EXP is a reference to a polymorphic class, return the dynamic type;
230 otherwise return the static type of the expression. */
231
232 static tree
233 get_tinfo_decl_dynamic (exp)
234 tree exp;
235 {
236 tree type;
237
238 if (exp == error_mark_node)
239 return error_mark_node;
240
241 type = TREE_TYPE (exp);
242
243 /* peel back references, so they match. */
244 if (TREE_CODE (type) == REFERENCE_TYPE)
245 type = TREE_TYPE (type);
246
247 /* Peel off cv qualifiers. */
248 type = TYPE_MAIN_VARIANT (type);
249
250 if (type != void_type_node)
251 type = complete_type_or_else (type, exp);
252
253 if (!type)
254 return error_mark_node;
255
256 /* If exp is a reference to polymorphic type, get the real type_info. */
257 if (TYPE_POLYMORPHIC_P (type) && ! resolves_to_fixed_type_p (exp, 0))
258 {
259 /* build reference to type_info from vtable. */
260 tree t;
261
262 if (! flag_rtti)
263 error ("taking dynamic typeid of object with -fno-rtti");
264 if (CLASSTYPE_COM_INTERFACE (type))
265 {
266 cp_error ("RTTI not supported for COM interface type `%T'", type);
267 return error_mark_node;
268 }
269
270 /* If we don't have rtti stuff, get to a sub-object that does. */
271 if (! CLASSTYPE_VFIELDS (type))
272 {
273 exp = build_unary_op (ADDR_EXPR, exp, 0);
274 exp = build_headof_sub (exp);
275 exp = build_indirect_ref (exp, NULL_PTR);
276 }
277
278 if (flag_vtable_thunks)
279 t = build_vfn_ref ((tree *) 0, exp, integer_one_node);
280 else
281 t = build_vfn_ref ((tree *) 0, exp, integer_zero_node);
282 TREE_TYPE (t) = build_pointer_type (tinfo_decl_type);
283 return t;
284 }
285
286 /* otherwise return the type_info for the static type of the expr. */
287 exp = get_tinfo_decl (TYPE_MAIN_VARIANT (type));
288 return build_unary_op (ADDR_EXPR, exp, 0);
289 }
290
291 tree
292 build_typeid (exp)
293 tree exp;
294 {
295 tree cond = NULL_TREE;
296 int nonnull = 0;
297
298 if (! flag_rtti)
299 {
300 error ("cannot use typeid with -fno-rtti");
301 return error_mark_node;
302 }
303
304 if (TYPE_SIZE (type_info_type_node) == NULL_TREE)
305 {
306 error ("must #include <typeinfo> before using typeid");
307 return error_mark_node;
308 }
309
310 if (processing_template_decl)
311 return build_min_nt (TYPEID_EXPR, exp);
312
313 if (TREE_CODE (exp) == INDIRECT_REF
314 && TREE_CODE (TREE_TYPE (TREE_OPERAND (exp, 0))) == POINTER_TYPE
315 && TYPE_POLYMORPHIC_P (TREE_TYPE (exp))
316 && ! resolves_to_fixed_type_p (exp, &nonnull)
317 && ! nonnull)
318 {
319 exp = stabilize_reference (exp);
320 cond = cp_convert (boolean_type_node, TREE_OPERAND (exp, 0));
321 }
322
323 exp = get_tinfo_decl_dynamic (exp);
324
325 if (exp == error_mark_node)
326 return error_mark_node;
327
328 exp = tinfo_from_decl (exp);
329
330 if (cond)
331 {
332 tree bad = throw_bad_typeid ();
333
334 exp = build (COND_EXPR, TREE_TYPE (exp), cond, exp, bad);
335 }
336
337 return convert_from_reference (exp);
338 }
339
340 static tree
341 get_tinfo_var (type)
342 tree type;
343 {
344 tree tname = build_overload_with_type (tinfo_var_id, type);
345 tree arrtype;
346 int size;
347
348 my_friendly_assert (!new_abi_rtti_p (), 20000118);
349 if (IDENTIFIER_GLOBAL_VALUE (tname))
350 return IDENTIFIER_GLOBAL_VALUE (tname);
351
352 /* Figure out how much space we need to allocate for the type_info object.
353 If our struct layout or the type_info classes are changed, this will
354 need to be modified. */
355 if (TYPE_QUALS (type) != TYPE_UNQUALIFIED)
356 size = 3 * POINTER_SIZE + INT_TYPE_SIZE;
357 else if (TREE_CODE (type) == POINTER_TYPE
358 && ! (TREE_CODE (TREE_TYPE (type)) == OFFSET_TYPE
359 || TREE_CODE (TREE_TYPE (type)) == METHOD_TYPE))
360 size = 3 * POINTER_SIZE;
361 else if (IS_AGGR_TYPE (type))
362 {
363 if (CLASSTYPE_N_BASECLASSES (type) == 0)
364 size = 2 * POINTER_SIZE;
365 else if (! TYPE_BASE_CONVS_MAY_REQUIRE_CODE_P (type)
366 && (TREE_VIA_PUBLIC
367 (TREE_VEC_ELT (TYPE_BINFO_BASETYPES (type), 0))))
368 size = 3 * POINTER_SIZE;
369 else
370 size = 3 * POINTER_SIZE + TYPE_PRECISION (sizetype);
371 }
372 else
373 size = 2 * POINTER_SIZE;
374
375 /* The type for a character array of the appropriate size. */
376 arrtype = build_cplus_array_type
377 (unsigned_char_type_node,
378 build_index_type (size_int (size / BITS_PER_UNIT - 1)));
379
380 return declare_global_var (tname, arrtype);
381 }
382
383 /* Generate the NTBS name of a type. */
384 static tree
385 tinfo_name (type)
386 tree type;
387 {
388 const char *name = build_overload_name (type, 1, 1);
389 tree name_string = combine_strings (build_string (strlen (name) + 1, name));
390 return name_string;
391 }
392
393 /* Returns a decl for a function or variable which can be used to obtain a
394 type_info object for TYPE. The old-abi uses functions, the new-abi
395 uses the type_info object directly. You can take the address of the
396 returned decl, to save the decl. To use the decl call
397 tinfo_from_decl. You must arrange that the decl is mark_used, if
398 actually use it --- decls in vtables are only used if the vtable is
399 output. */
400
401 tree
402 get_tinfo_decl (type)
403 tree type;
404 {
405 tree name;
406 tree d;
407
408 if (TREE_CODE (type) == OFFSET_TYPE)
409 type = TREE_TYPE (type);
410 if (TREE_CODE (type) == METHOD_TYPE)
411 type = build_function_type (TREE_TYPE (type),
412 TREE_CHAIN (TYPE_ARG_TYPES (type)));
413
414 name = build_overload_with_type (tinfo_decl_id, type);
415
416 d = IDENTIFIER_GLOBAL_VALUE (name);
417 if (d)
418 /* OK */;
419 else if (!new_abi_rtti_p ())
420 {
421 /* The tinfo decl is a function returning a reference to the type_info
422 object. */
423 d = build_lang_decl (FUNCTION_DECL, name, tinfo_decl_type);
424 DECL_EXTERNAL (d) = 1;
425 TREE_PUBLIC (d) = 1;
426 DECL_ARTIFICIAL (d) = 1;
427 TREE_NOTHROW (d) = 1;
428 DECL_NOT_REALLY_EXTERN (d) = 1;
429 SET_DECL_TINFO_FN_P (d);
430 TREE_TYPE (name) = type;
431
432 pushdecl_top_level (d);
433 make_function_rtl (d);
434 mark_inline_for_output (d);
435 }
436 else
437 {
438 /* The tinfo decl is the type_info object itself. We make all
439 tinfo objects look as type_info, even though they will end up
440 being a subclass of that when emitted. This means the we'll
441 erroneously think we know the dynamic type -- be careful in the
442 runtime. */
443 d = build_lang_decl (VAR_DECL, name, tinfo_decl_type);
444
445 DECL_ARTIFICIAL (d) = 1;
446 DECL_ALIGN (d) = TYPE_ALIGN (ptr_type_node);
447 TREE_READONLY (d) = 1;
448 TREE_STATIC (d) = 1;
449 DECL_EXTERNAL (d) = 1;
450 TREE_PUBLIC (d) = 1;
451 DECL_ASSEMBLER_NAME (d) = DECL_NAME (d);
452 cp_finish_decl (d, NULL_TREE, NULL_TREE, 0);
453
454 pushdecl_top_level (d);
455 /* Remember the type it is for. */
456 TREE_TYPE (name) = type;
457 }
458 return d;
459 }
460
461 /* Given an expr produced by get_tinfo_decl, return an expr which
462 produces a reference to the type_info object. */
463
464 static tree
465 tinfo_from_decl (expr)
466 tree expr;
467 {
468 tree t;
469
470 if (!new_abi_rtti_p ())
471 t = build_call (expr, TREE_TYPE (tinfo_decl_type), NULL_TREE);
472 else if (TREE_CODE (TREE_TYPE (expr)) == POINTER_TYPE)
473 t = build_indirect_ref (expr, NULL);
474 else
475 t = expr;
476
477 return t;
478 }
479
480 tree
481 get_typeid_1 (type)
482 tree type;
483 {
484 tree t;
485
486 t = get_tinfo_decl (type);
487 t = tinfo_from_decl (t);
488 return convert_from_reference (t);
489 }
490
491 /* Return the type_info object for TYPE. */
492
493 tree
494 get_typeid (type)
495 tree type;
496 {
497 if (type == error_mark_node)
498 return error_mark_node;
499
500 if (TYPE_SIZE (type_info_type_node) == NULL_TREE)
501 {
502 error ("must #include <typeinfo> before using typeid");
503 return error_mark_node;
504 }
505
506 if (processing_template_decl)
507 return build_min_nt (TYPEID_EXPR, type);
508
509 /* If the type of the type-id is a reference type, the result of the
510 typeid expression refers to a type_info object representing the
511 referenced type. */
512 if (TREE_CODE (type) == REFERENCE_TYPE)
513 type = TREE_TYPE (type);
514
515 /* The top-level cv-qualifiers of the lvalue expression or the type-id
516 that is the operand of typeid are always ignored. */
517 type = TYPE_MAIN_VARIANT (type);
518
519 if (type != void_type_node)
520 type = complete_type_or_else (type, NULL_TREE);
521
522 if (!type)
523 return error_mark_node;
524
525 return get_typeid_1 (type);
526 }
527
528 /* Check whether TEST is null before returning RESULT. If TEST is used in
529 RESULT, it must have previously had a save_expr applied to it. */
530
531 static tree
532 ifnonnull (test, result)
533 tree test, result;
534 {
535 return build (COND_EXPR, TREE_TYPE (result),
536 build (EQ_EXPR, boolean_type_node, test, integer_zero_node),
537 cp_convert (TREE_TYPE (result), integer_zero_node),
538 result);
539 }
540
541 /* Generate the constant expression describing where direct base BINFO
542 appears within the PARENT. How to interpret this expression depends on
543 details of the ABI, which the runtime must be aware of. */
544
545 static tree
546 get_base_offset (binfo, parent)
547 tree binfo;
548 tree parent;
549 {
550 tree offset;
551
552 if (!TREE_VIA_VIRTUAL (binfo))
553 offset = BINFO_OFFSET (binfo);
554 else if (!vbase_offsets_in_vtable_p ())
555 {
556 tree t = BINFO_TYPE (binfo);
557 const char *name;
558 tree field;
559
560 FORMAT_VBASE_NAME (name, t);
561 field = lookup_field (parent, get_identifier (name), 0, 0);
562 offset = size_binop (FLOOR_DIV_EXPR,
563 DECL_FIELD_BITPOS (field),
564 bitsize_int (BITS_PER_UNIT));
565 offset = convert (sizetype, offset);
566 }
567 else
568 {
569 /* Under the new ABI, we store the vtable offset at which
570 the virtual base offset can be found. */
571 tree vbase = BINFO_FOR_VBASE (BINFO_TYPE (binfo), parent);
572 offset = convert (sizetype, BINFO_VPTR_FIELD (vbase));
573 }
574 return offset;
575 }
576
577 /* Execute a dynamic cast, as described in section 5.2.6 of the 9/93 working
578 paper. */
579
580 static tree
581 build_dynamic_cast_1 (type, expr)
582 tree type, expr;
583 {
584 enum tree_code tc = TREE_CODE (type);
585 tree exprtype;
586 enum tree_code ec;
587 tree dcast_fn;
588 tree old_expr = expr;
589
590 if (TREE_CODE (expr) == OFFSET_REF)
591 expr = resolve_offset_ref (expr);
592
593 exprtype = TREE_TYPE (expr);
594 assert (exprtype != NULL_TREE);
595 ec = TREE_CODE (exprtype);
596
597 switch (tc)
598 {
599 case POINTER_TYPE:
600 if (ec == REFERENCE_TYPE)
601 {
602 expr = convert_from_reference (expr);
603 exprtype = TREE_TYPE (expr);
604 ec = TREE_CODE (exprtype);
605 }
606 if (ec != POINTER_TYPE)
607 goto fail;
608 if (TREE_CODE (TREE_TYPE (exprtype)) != RECORD_TYPE)
609 goto fail;
610 if (TYPE_SIZE (complete_type (TREE_TYPE (exprtype))) == NULL_TREE)
611 goto fail;
612 if (!at_least_as_qualified_p (TREE_TYPE (type),
613 TREE_TYPE (exprtype)))
614 goto fail;
615 if (TYPE_MAIN_VARIANT (TREE_TYPE (type)) == void_type_node)
616 break;
617 /* else fall through */
618 case REFERENCE_TYPE:
619 if (TREE_CODE (TREE_TYPE (type)) != RECORD_TYPE)
620 goto fail;
621 if (TYPE_SIZE (complete_type (TREE_TYPE (type))) == NULL_TREE)
622 goto fail;
623 break;
624 /* else fall through */
625 default:
626 goto fail;
627 }
628
629 /* Apply trivial conversion T -> T& for dereferenced ptrs. */
630 if (ec == RECORD_TYPE)
631 {
632 exprtype = build_reference_type (exprtype);
633 expr = convert_to_reference (exprtype, expr, CONV_IMPLICIT,
634 LOOKUP_NORMAL, NULL_TREE);
635 ec = REFERENCE_TYPE;
636 }
637
638 if (tc == REFERENCE_TYPE)
639 {
640 if (ec != REFERENCE_TYPE)
641 goto fail;
642 if (TREE_CODE (TREE_TYPE (exprtype)) != RECORD_TYPE)
643 goto fail;
644 if (TYPE_SIZE (complete_type (TREE_TYPE (exprtype))) == NULL_TREE)
645 goto fail;
646 if (!at_least_as_qualified_p (TREE_TYPE (type),
647 TREE_TYPE (exprtype)))
648 goto fail;
649 }
650
651 /* If *type is an unambiguous accessible base class of *exprtype,
652 convert statically. */
653 {
654 int distance;
655 tree path;
656
657 distance = get_base_distance (TREE_TYPE (type), TREE_TYPE (exprtype), 1,
658 &path);
659
660 if (distance == -2)
661 {
662 cp_error ("dynamic_cast from `%T' to ambiguous base class `%T'",
663 TREE_TYPE (exprtype), TREE_TYPE (type));
664 return error_mark_node;
665 }
666 if (distance == -3)
667 {
668 cp_error ("dynamic_cast from `%T' to private base class `%T'",
669 TREE_TYPE (exprtype), TREE_TYPE (type));
670 return error_mark_node;
671 }
672
673 if (distance >= 0)
674 return build_vbase_path (PLUS_EXPR, type, expr, path, 0);
675 }
676
677 /* Otherwise *exprtype must be a polymorphic class (have a vtbl). */
678 if (TYPE_POLYMORPHIC_P (TREE_TYPE (exprtype)))
679 {
680 tree expr1;
681 /* if TYPE is `void *', return pointer to complete object. */
682 if (tc == POINTER_TYPE
683 && TYPE_MAIN_VARIANT (TREE_TYPE (type)) == void_type_node)
684 {
685 /* if b is an object, dynamic_cast<void *>(&b) == (void *)&b. */
686 if (TREE_CODE (expr) == ADDR_EXPR
687 && TREE_CODE (TREE_OPERAND (expr, 0)) == VAR_DECL
688 && TREE_CODE (TREE_TYPE (TREE_OPERAND (expr, 0))) == RECORD_TYPE)
689 return build1 (NOP_EXPR, type, expr);
690
691 /* Since expr is used twice below, save it. */
692 expr = save_expr (expr);
693
694 expr1 = build_headof (expr);
695 if (TREE_TYPE (expr1) != type)
696 expr1 = build1 (NOP_EXPR, type, expr1);
697 return ifnonnull (expr, expr1);
698 }
699 else
700 {
701 tree retval;
702 tree result, td2, td3, elems;
703 tree static_type, target_type, boff;
704
705 /* If we got here, we can't convert statically. Therefore,
706 dynamic_cast<D&>(b) (b an object) cannot succeed. */
707 if (ec == REFERENCE_TYPE)
708 {
709 if (TREE_CODE (old_expr) == VAR_DECL
710 && TREE_CODE (TREE_TYPE (old_expr)) == RECORD_TYPE)
711 {
712 tree expr = throw_bad_cast ();
713 cp_warning ("dynamic_cast of `%#D' to `%#T' can never succeed",
714 old_expr, type);
715 /* Bash it to the expected type. */
716 TREE_TYPE (expr) = type;
717 return expr;
718 }
719 }
720 /* Ditto for dynamic_cast<D*>(&b). */
721 else if (TREE_CODE (expr) == ADDR_EXPR)
722 {
723 tree op = TREE_OPERAND (expr, 0);
724 if (TREE_CODE (op) == VAR_DECL
725 && TREE_CODE (TREE_TYPE (op)) == RECORD_TYPE)
726 {
727 cp_warning ("dynamic_cast of `%#D' to `%#T' can never succeed",
728 op, type);
729 retval = build_int_2 (0, 0);
730 TREE_TYPE (retval) = type;
731 return retval;
732 }
733 }
734
735 target_type = TYPE_MAIN_VARIANT (TREE_TYPE (type));
736 static_type = TYPE_MAIN_VARIANT (TREE_TYPE (exprtype));
737 td2 = build_unary_op (ADDR_EXPR, get_tinfo_decl (target_type), 0);
738 td3 = build_unary_op (ADDR_EXPR, get_tinfo_decl (static_type), 0);
739
740 /* Determine how T and V are related. */
741 boff = get_dynamic_cast_base_type (static_type, target_type);
742
743 /* Since expr is used twice below, save it. */
744 expr = save_expr (expr);
745
746 expr1 = expr;
747 if (tc == REFERENCE_TYPE)
748 expr1 = build_unary_op (ADDR_EXPR, expr1, 0);
749
750 if (!new_abi_rtti_p ())
751 {
752 tree expr2 = build_headof (expr1);
753 tree td1 = expr;
754
755 if (ec == POINTER_TYPE)
756 td1 = build_indirect_ref (td1, NULL_PTR);
757 td1 = get_tinfo_decl_dynamic (td1);
758
759 elems = tree_cons
760 (NULL_TREE, td1, tree_cons
761 (NULL_TREE, td2, tree_cons
762 (NULL_TREE, boff, tree_cons
763 (NULL_TREE, expr2, tree_cons
764 (NULL_TREE, td3, tree_cons
765 (NULL_TREE, expr1, NULL_TREE))))));
766 }
767 else
768 elems = tree_cons
769 (NULL_TREE, expr1, tree_cons
770 (NULL_TREE, td3, tree_cons
771 (NULL_TREE, td2, tree_cons
772 (NULL_TREE, boff, NULL_TREE))));
773
774 dcast_fn = dynamic_cast_node;
775 if (!dcast_fn)
776 {
777 tree tmp;
778 tree tinfo_ptr;
779 tree ns = global_namespace;
780 const char *name;
781
782 push_nested_namespace (ns);
783 if (!new_abi_rtti_p ())
784 {
785 tinfo_ptr = build_pointer_type (tinfo_decl_type);
786 name = "__dynamic_cast_2";
787 tmp = tree_cons
788 (NULL_TREE, tinfo_ptr, tree_cons
789 (NULL_TREE, tinfo_ptr, tree_cons
790 (NULL_TREE, integer_type_node, tree_cons
791 (NULL_TREE, ptr_type_node, tree_cons
792 (NULL_TREE, tinfo_ptr, tree_cons
793 (NULL_TREE, ptr_type_node, void_list_node))))));
794 }
795 else
796 {
797 if (flag_honor_std)
798 {
799 push_namespace (get_identifier ("std"));
800 ns = current_namespace;
801 }
802 tinfo_ptr = xref_tag (class_type_node,
803 get_identifier ("__class_type_info"),
804 1);
805
806 tinfo_ptr = build_pointer_type
807 (build_qualified_type
808 (tinfo_ptr, TYPE_QUAL_CONST));
809 name = "__dynamic_cast";
810 tmp = tree_cons
811 (NULL_TREE, const_ptr_type_node, tree_cons
812 (NULL_TREE, tinfo_ptr, tree_cons
813 (NULL_TREE, tinfo_ptr, tree_cons
814 (NULL_TREE, ptrdiff_type_node, void_list_node))));
815 }
816 tmp = build_function_type (ptr_type_node, tmp);
817 dcast_fn = build_lang_decl (FUNCTION_DECL,
818 get_identifier (name),
819 tmp);
820 DECL_EXTERNAL (dcast_fn) = 1;
821 TREE_PUBLIC (dcast_fn) = 1;
822 DECL_ARTIFICIAL (dcast_fn) = 1;
823 TREE_NOTHROW (dcast_fn) = 1;
824 pushdecl (dcast_fn);
825 if (new_abi_rtti_p ())
826 /* We want its name mangling. */
827 set_mangled_name_for_decl (dcast_fn);
828 make_function_rtl (dcast_fn);
829 pop_nested_namespace (ns);
830 dynamic_cast_node = dcast_fn;
831 }
832 mark_used (dcast_fn);
833 result = build_call
834 (dcast_fn, TREE_TYPE (TREE_TYPE (dcast_fn)), elems);
835
836 if (tc == REFERENCE_TYPE)
837 {
838 tree bad = throw_bad_cast ();
839
840 result = save_expr (result);
841 return build (COND_EXPR, type, result, result, bad);
842 }
843
844 /* Now back to the type we want from a void*. */
845 result = cp_convert (type, result);
846 return ifnonnull (expr, result);
847 }
848 }
849
850 cp_error ("dynamic_cast from non-polymorphic type `%#T'", exprtype);
851 return error_mark_node;
852
853 fail:
854 cp_error ("cannot dynamic_cast `%E' (of type `%#T') to type `%#T'",
855 expr, exprtype, type);
856 return error_mark_node;
857 }
858
859 tree
860 build_dynamic_cast (type, expr)
861 tree type, expr;
862 {
863 if (type == error_mark_node || expr == error_mark_node)
864 return error_mark_node;
865
866 if (processing_template_decl)
867 return build_min (DYNAMIC_CAST_EXPR, type, expr);
868
869 return convert_from_reference (build_dynamic_cast_1 (type, expr));
870 }
871 \f
872 /* Build and initialize various sorts of descriptors. Every descriptor
873 node has a name associated with it (the name created by mangling).
874 For this reason, we use the identifier as our access to the __*_desc
875 nodes, instead of sticking them directly in the types. Otherwise we
876 would burden all built-in types (and pointer types) with slots that
877 we don't necessarily want to use.
878
879 For each descriptor we build, we build a variable that contains
880 the descriptor's information. When we need this info at runtime,
881 all we need is access to these variables.
882
883 Note: these constructors always return the address of the descriptor
884 info, since that is simplest for their mutual interaction. */
885
886 /* Build an initializer for a __si_type_info node. */
887
888 static void
889 expand_si_desc (tdecl, type)
890 tree tdecl;
891 tree type;
892 {
893 tree t, elems, fn;
894 tree name_string = tinfo_name (type);
895
896 type = BINFO_TYPE (TREE_VEC_ELT (TYPE_BINFO_BASETYPES (type), 0));
897 finish_expr_stmt (get_typeid_1 (type));
898 t = decay_conversion (get_tinfo_var (type));
899 elems = tree_cons
900 (NULL_TREE, decay_conversion (tdecl), tree_cons
901 (NULL_TREE, decay_conversion (name_string), tree_cons
902 (NULL_TREE, t, NULL_TREE)));
903
904 fn = get_identifier ("__rtti_si");
905 if (IDENTIFIER_GLOBAL_VALUE (fn))
906 fn = IDENTIFIER_GLOBAL_VALUE (fn);
907 else
908 {
909 tree tmp;
910 tmp = tree_cons
911 (NULL_TREE, ptr_type_node, tree_cons
912 (NULL_TREE, const_string_type_node, tree_cons
913 (NULL_TREE, build_pointer_type (type_info_type_node),
914 void_list_node)));
915 tmp = build_function_type (void_type_node, tmp);
916
917 fn = build_lang_decl (FUNCTION_DECL, fn, tmp);
918 DECL_EXTERNAL (fn) = 1;
919 TREE_PUBLIC (fn) = 1;
920 DECL_ARTIFICIAL (fn) = 1;
921 TREE_NOTHROW (fn) = 1;
922 pushdecl_top_level (fn);
923 make_function_rtl (fn);
924 }
925
926 mark_used (fn);
927 fn = build_call (fn, TREE_TYPE (TREE_TYPE (fn)), elems);
928 finish_expr_stmt (fn);
929 }
930
931 /* Build an initializer for a __class_type_info node. */
932
933 static void
934 expand_class_desc (tdecl, type)
935 tree tdecl;
936 tree type;
937 {
938 tree name_string;
939 tree fn, tmp;
940
941 int i = CLASSTYPE_N_BASECLASSES (type);
942 int base_cnt = 0;
943 tree binfos = TYPE_BINFO_BASETYPES (type);
944 #if 0
945 /* See code below that used these. */
946 tree vb = CLASSTYPE_VBASECLASSES (type);
947 int n_base = i;
948 #endif
949 tree base, elems, access, offset, isvir;
950 tree elt, elts = NULL_TREE;
951
952 if (base_desc_type_node == NULL_TREE)
953 {
954 tree fields [4];
955
956 /* A reasonably close approximation of __class_type_info::base_info */
957
958 base_desc_type_node = make_aggr_type (RECORD_TYPE);
959
960 /* Actually const __user_type_info * */
961 fields [0] = build_lang_decl
962 (FIELD_DECL, NULL_TREE,
963 build_pointer_type (build_qualified_type
964 (type_info_type_node,
965 TYPE_QUAL_CONST)));
966 fields [1] = build_lang_decl
967 (FIELD_DECL, NULL_TREE,
968 flag_new_abi ? intSI_type_node : unsigned_intSI_type_node);
969 DECL_BIT_FIELD (fields[1]) = 1;
970 DECL_SIZE (fields[1]) = bitsize_int (29);
971
972 fields [2] = build_lang_decl (FIELD_DECL, NULL_TREE, boolean_type_node);
973 DECL_BIT_FIELD (fields[2]) = 1;
974 DECL_SIZE (fields[2]) = bitsize_int (1);
975
976 /* Actually enum access */
977 fields [3] = build_lang_decl (FIELD_DECL, NULL_TREE, integer_type_node);
978 DECL_BIT_FIELD (fields[3]) = 1;
979 DECL_SIZE (fields[3]) = bitsize_int (2);
980
981 finish_builtin_type (base_desc_type_node, "__base_info", fields,
982 3, ptr_type_node);
983 }
984
985 while (--i >= 0)
986 {
987 tree binfo = TREE_VEC_ELT (binfos, i);
988
989 finish_expr_stmt (get_typeid_1 (BINFO_TYPE (binfo)));
990 base = decay_conversion (get_tinfo_var (BINFO_TYPE (binfo)));
991 offset = get_base_offset (binfo, type);
992
993 if (TREE_VIA_PUBLIC (binfo))
994 access = access_public_node;
995 else if (TREE_VIA_PROTECTED (binfo))
996 access = access_protected_node;
997 else
998 access = access_private_node;
999 if (TREE_VIA_VIRTUAL (binfo))
1000 isvir = boolean_true_node;
1001 else
1002 isvir = boolean_false_node;
1003
1004 elt = build
1005 (CONSTRUCTOR, base_desc_type_node, NULL_TREE, tree_cons
1006 (NULL_TREE, base, tree_cons
1007 (NULL_TREE, offset, tree_cons
1008 (NULL_TREE, isvir, tree_cons
1009 (NULL_TREE, access, NULL_TREE)))));
1010 TREE_HAS_CONSTRUCTOR (elt) = TREE_CONSTANT (elt) = TREE_STATIC (elt) = 1;
1011 elts = tree_cons (NULL_TREE, elt, elts);
1012 base_cnt++;
1013 }
1014 #if 0
1015 i = n_base;
1016 while (vb)
1017 {
1018 tree b;
1019 access = access_public_node;
1020 while (--i >= 0)
1021 {
1022 b = TREE_VEC_ELT (binfos, i);
1023 if (BINFO_TYPE (vb) == BINFO_TYPE (b) && TREE_VIA_VIRTUAL (b))
1024 {
1025 if (TREE_VIA_PUBLIC (b))
1026 access = access_public_node;
1027 else if (TREE_VIA_PROTECTED (b))
1028 access = access_protected_node;
1029 else
1030 access = access_private_node;
1031 break;
1032 }
1033 }
1034 base = build_t_desc (BINFO_TYPE (vb), 1);
1035 offset = BINFO_OFFSET (vb);
1036 isvir = build_int_2 (1, 0);
1037
1038 base_list = tree_cons (NULL_TREE, base, base_list);
1039 isvir_list = tree_cons (NULL_TREE, isvir, isvir_list);
1040 acc_list = tree_cons (NULL_TREE, access, acc_list);
1041 off_list = tree_cons (NULL_TREE, offset, off_list);
1042
1043 base_cnt++;
1044 vb = TREE_CHAIN (vb);
1045 }
1046 #endif
1047
1048 name_string = tinfo_name (type);
1049
1050 {
1051 tree arrtype = build_array_type (base_desc_type_node, NULL_TREE);
1052 elts = build (CONSTRUCTOR, arrtype, NULL_TREE, elts);
1053 TREE_HAS_CONSTRUCTOR (elts) = TREE_CONSTANT (elts)
1054 = TREE_STATIC (elts) = 1;
1055 complete_array_type (arrtype, elts, 1);
1056 }
1057
1058 elems = tree_cons
1059 (NULL_TREE, decay_conversion (tdecl), tree_cons
1060 (NULL_TREE, decay_conversion (name_string), tree_cons
1061 (NULL_TREE, decay_conversion (elts), tree_cons
1062 (NULL_TREE, cp_convert (sizetype, build_int_2 (base_cnt, 0)),
1063 NULL_TREE))));
1064
1065 fn = get_identifier ("__rtti_class");
1066 if (IDENTIFIER_GLOBAL_VALUE (fn))
1067 fn = IDENTIFIER_GLOBAL_VALUE (fn);
1068 else
1069 {
1070 tmp = tree_cons
1071 (NULL_TREE, ptr_type_node, tree_cons
1072 (NULL_TREE, const_string_type_node, tree_cons
1073 (NULL_TREE, build_pointer_type (base_desc_type_node), tree_cons
1074 (NULL_TREE, sizetype, void_list_node))));
1075 tmp = build_function_type (void_type_node, tmp);
1076
1077 fn = build_lang_decl (FUNCTION_DECL, fn, tmp);
1078 DECL_EXTERNAL (fn) = 1;
1079 TREE_PUBLIC (fn) = 1;
1080 DECL_ARTIFICIAL (fn) = 1;
1081 TREE_NOTHROW (fn) = 1;
1082 pushdecl_top_level (fn);
1083 make_function_rtl (fn);
1084 }
1085
1086 mark_used (fn);
1087 fn = build_call (fn, TREE_TYPE (TREE_TYPE (fn)), elems);
1088 finish_expr_stmt (fn);
1089 }
1090
1091 /* Build an initializer for a __pointer_type_info node. */
1092
1093 static void
1094 expand_ptr_desc (tdecl, type)
1095 tree tdecl;
1096 tree type;
1097 {
1098 tree t, elems, fn;
1099 tree name_string = tinfo_name (type);
1100
1101 type = TREE_TYPE (type);
1102 finish_expr_stmt (get_typeid_1 (type));
1103 t = decay_conversion (get_tinfo_var (type));
1104 elems = tree_cons
1105 (NULL_TREE, decay_conversion (tdecl), tree_cons
1106 (NULL_TREE, decay_conversion (name_string), tree_cons
1107 (NULL_TREE, t, NULL_TREE)));
1108
1109 fn = get_identifier ("__rtti_ptr");
1110 if (IDENTIFIER_GLOBAL_VALUE (fn))
1111 fn = IDENTIFIER_GLOBAL_VALUE (fn);
1112 else
1113 {
1114 tree tmp;
1115 tmp = tree_cons
1116 (NULL_TREE, ptr_type_node, tree_cons
1117 (NULL_TREE, const_string_type_node, tree_cons
1118 (NULL_TREE, build_pointer_type (type_info_type_node),
1119 void_list_node)));
1120 tmp = build_function_type (void_type_node, tmp);
1121
1122 fn = build_lang_decl (FUNCTION_DECL, fn, tmp);
1123 DECL_EXTERNAL (fn) = 1;
1124 TREE_PUBLIC (fn) = 1;
1125 DECL_ARTIFICIAL (fn) = 1;
1126 TREE_NOTHROW (fn) = 1;
1127 pushdecl_top_level (fn);
1128 make_function_rtl (fn);
1129 }
1130
1131 mark_used (fn);
1132 fn = build_call (fn, TREE_TYPE (TREE_TYPE (fn)), elems);
1133 finish_expr_stmt (fn);
1134 }
1135
1136 /* Build an initializer for a __attr_type_info node. */
1137
1138 static void
1139 expand_attr_desc (tdecl, type)
1140 tree tdecl;
1141 tree type;
1142 {
1143 tree elems, t, fn;
1144 tree name_string = tinfo_name (type);
1145 tree attrval = build_int_2 (TYPE_QUALS (type), 0);
1146
1147 finish_expr_stmt (get_typeid_1 (TYPE_MAIN_VARIANT (type)));
1148 t = decay_conversion (get_tinfo_var (TYPE_MAIN_VARIANT (type)));
1149 elems = tree_cons
1150 (NULL_TREE, decay_conversion (tdecl), tree_cons
1151 (NULL_TREE, decay_conversion (name_string), tree_cons
1152 (NULL_TREE, attrval, tree_cons (NULL_TREE, t, NULL_TREE))));
1153
1154 fn = get_identifier ("__rtti_attr");
1155 if (IDENTIFIER_GLOBAL_VALUE (fn))
1156 fn = IDENTIFIER_GLOBAL_VALUE (fn);
1157 else
1158 {
1159 tree tmp;
1160 tmp = tree_cons
1161 (NULL_TREE, ptr_type_node, tree_cons
1162 (NULL_TREE, const_string_type_node, tree_cons
1163 (NULL_TREE, integer_type_node, tree_cons
1164 (NULL_TREE, build_pointer_type (type_info_type_node),
1165 void_list_node))));
1166 tmp = build_function_type (void_type_node, tmp);
1167
1168 fn = build_lang_decl (FUNCTION_DECL, fn, tmp);
1169 DECL_EXTERNAL (fn) = 1;
1170 TREE_PUBLIC (fn) = 1;
1171 DECL_ARTIFICIAL (fn) = 1;
1172 TREE_NOTHROW (fn) = 1;
1173 pushdecl_top_level (fn);
1174 make_function_rtl (fn);
1175 }
1176
1177 mark_used (fn);
1178 fn = build_call (fn, TREE_TYPE (TREE_TYPE (fn)), elems);
1179 finish_expr_stmt (fn);
1180 }
1181
1182 /* Build an initializer for a type_info node that just has a name. */
1183
1184 static void
1185 expand_generic_desc (tdecl, type, fnname)
1186 tree tdecl;
1187 tree type;
1188 const char *fnname;
1189 {
1190 tree name_string = tinfo_name (type);
1191 tree elems = tree_cons
1192 (NULL_TREE, decay_conversion (tdecl), tree_cons
1193 (NULL_TREE, decay_conversion (name_string), NULL_TREE));
1194
1195 tree fn = get_identifier (fnname);
1196 if (IDENTIFIER_GLOBAL_VALUE (fn))
1197 fn = IDENTIFIER_GLOBAL_VALUE (fn);
1198 else
1199 {
1200 tree tmp;
1201 tmp = tree_cons
1202 (NULL_TREE, ptr_type_node, tree_cons
1203 (NULL_TREE, const_string_type_node, void_list_node));
1204 tmp = build_function_type (void_type_node, tmp);
1205
1206 fn = build_lang_decl (FUNCTION_DECL, fn, tmp);
1207 DECL_EXTERNAL (fn) = 1;
1208 TREE_PUBLIC (fn) = 1;
1209 DECL_ARTIFICIAL (fn) = 1;
1210 TREE_NOTHROW (fn) = 1;
1211 pushdecl_top_level (fn);
1212 make_function_rtl (fn);
1213 }
1214
1215 mark_used (fn);
1216 fn = build_call (fn, TREE_TYPE (TREE_TYPE (fn)), elems);
1217 finish_expr_stmt (fn);
1218 }
1219
1220 /* Generate the code for a type_info initialization function.
1221 Note that we take advantage of the passage
1222
1223 5.2.7 Type identification [expr.typeid]
1224
1225 Whether or not the destructor is called for the type_info object at the
1226 end of the program is unspecified.
1227
1228 and don't bother to arrange for these objects to be destroyed. It
1229 doesn't matter, anyway, since the destructors don't do anything.
1230
1231 This must only be called from toplevel (i.e. from finish_file)! */
1232
1233 void
1234 synthesize_tinfo_fn (fndecl)
1235 tree fndecl;
1236 {
1237 tree type = TREE_TYPE (DECL_NAME (fndecl));
1238 tree tmp, addr, tdecl;
1239 tree compound_stmt;
1240 tree if_stmt;
1241 tree then_clause;
1242
1243 my_friendly_assert (!new_abi_rtti_p (), 20000118);
1244 if (at_eof)
1245 {
1246 import_export_decl (fndecl);
1247 if (DECL_REALLY_EXTERN (fndecl))
1248 return;
1249 }
1250
1251 /* Declare the static typeinfo variable. */
1252 tdecl = get_tinfo_var (type);
1253 DECL_EXTERNAL (tdecl) = 0;
1254 TREE_STATIC (tdecl) = 1;
1255 DECL_COMMON (tdecl) = 1;
1256 TREE_USED (tdecl) = 1;
1257 DECL_ALIGN (tdecl) = TYPE_ALIGN (ptr_type_node);
1258 cp_finish_decl (tdecl, NULL_TREE, NULL_TREE, 0);
1259
1260 /* Begin processing the function. */
1261 start_function (NULL_TREE, fndecl, NULL_TREE,
1262 SF_DEFAULT | SF_PRE_PARSED);
1263 DECL_DEFER_OUTPUT (fndecl) = 1;
1264 store_parm_decls ();
1265 clear_last_expr ();
1266
1267 /* Begin the body of the function. */
1268 compound_stmt = begin_compound_stmt (/*has_no_scope=*/0);
1269
1270 /* For convenience, we save away the address of the static
1271 variable. */
1272 addr = decay_conversion (tdecl);
1273
1274 /* If the first word of the array (the vtable) is non-zero, we've already
1275 initialized the object, so don't do it again. */
1276 if_stmt = begin_if_stmt ();
1277 tmp = cp_convert (build_pointer_type (ptr_type_node), addr);
1278 tmp = build_indirect_ref (tmp, 0);
1279 tmp = build_binary_op (EQ_EXPR, tmp, integer_zero_node);
1280 finish_if_stmt_cond (tmp, if_stmt);
1281 then_clause = begin_compound_stmt (/*has_no_scope=*/0);
1282
1283 if (TREE_CODE (type) == FUNCTION_TYPE)
1284 expand_generic_desc (tdecl, type, "__rtti_func");
1285 else if (TREE_CODE (type) == ARRAY_TYPE)
1286 expand_generic_desc (tdecl, type, "__rtti_array");
1287 else if (TYPE_QUALS (type) != TYPE_UNQUALIFIED)
1288 expand_attr_desc (tdecl, type);
1289 else if (TREE_CODE (type) == POINTER_TYPE)
1290 {
1291 if (TREE_CODE (TREE_TYPE (type)) == OFFSET_TYPE)
1292 expand_generic_desc (tdecl, type, "__rtti_ptmd");
1293 else if (TREE_CODE (TREE_TYPE (type)) == METHOD_TYPE)
1294 expand_generic_desc (tdecl, type, "__rtti_ptmf");
1295 else
1296 expand_ptr_desc (tdecl, type);
1297 }
1298 else if (TYPE_PTRMEMFUNC_P (type))
1299 expand_generic_desc (tdecl, type, "__rtti_ptmf");
1300 else if (IS_AGGR_TYPE (type))
1301 {
1302 if (CLASSTYPE_N_BASECLASSES (type) == 0)
1303 expand_generic_desc (tdecl, type, "__rtti_user");
1304 else if (! TYPE_BASE_CONVS_MAY_REQUIRE_CODE_P (type)
1305 && (TREE_VIA_PUBLIC
1306 (TREE_VEC_ELT (TYPE_BINFO_BASETYPES (type), 0))))
1307 expand_si_desc (tdecl, type);
1308 else
1309 expand_class_desc (tdecl, type);
1310 }
1311 else if (TREE_CODE (type) == ENUMERAL_TYPE)
1312 expand_generic_desc (tdecl, type, "__rtti_user");
1313 else
1314 my_friendly_abort (252);
1315
1316 finish_compound_stmt (/*has_no_scope=*/0, then_clause);
1317 finish_then_clause (if_stmt);
1318 finish_if_stmt ();
1319
1320 /* OK, now return the type_info object. */
1321 tmp = cp_convert (build_pointer_type (type_info_type_node), addr);
1322 tmp = build_indirect_ref (tmp, 0);
1323 finish_return_stmt (tmp);
1324 /* Finish the function body. */
1325 finish_compound_stmt (/*has_no_scope=*/0, compound_stmt);
1326 expand_body (finish_function (lineno, 0));
1327 }
1328
1329 /* Return the runtime bit mask encoding the qualifiers of TYPE. */
1330
1331 static int
1332 qualifier_flags (type)
1333 tree type;
1334 {
1335 int flags = 0;
1336 /* we want the qualifiers on this type, not any array core, it might have */
1337 int quals = TYPE_QUALS (type);
1338
1339 if (quals & TYPE_QUAL_CONST)
1340 flags |= 1;
1341 if (quals & TYPE_QUAL_VOLATILE)
1342 flags |= 2;
1343 return flags;
1344 }
1345
1346 /* Return a CONSTRUCTOR for the common part of the type_info objects. This
1347 is the vtable pointer and NTBS name. */
1348
1349 static tree
1350 tinfo_base_init (desc, target)
1351 tree desc;
1352 tree target;
1353 {
1354 tree name_string = tinfo_name (target);
1355 tree init = NULL_TREE;
1356
1357 if (TINFO_VTABLE_DECL (desc))
1358 {
1359 tree vtbl_ptr = build_unary_op (ADDR_EXPR, TINFO_VTABLE_DECL (desc), 0);
1360
1361 init = tree_cons (NULL_TREE, vtbl_ptr, init);
1362 }
1363
1364 init = tree_cons (NULL_TREE, decay_conversion (name_string), init);
1365
1366 init = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, nreverse(init));
1367 TREE_HAS_CONSTRUCTOR (init) = TREE_CONSTANT (init) = TREE_STATIC (init) = 1;
1368 init = tree_cons (NULL_TREE, init, NULL_TREE);
1369
1370 return init;
1371 }
1372
1373 /* Return the CONSTRUCTOR expr for a type_info of TYPE. DESC provides the
1374 information about the particular type_info derivation, which adds no
1375 additional fields to the type_info base. */
1376
1377 static tree
1378 generic_initializer (desc, target)
1379 tree desc;
1380 tree target;
1381 {
1382 tree init = tinfo_base_init (desc, target);
1383
1384 init = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, init);
1385 TREE_HAS_CONSTRUCTOR (init) = TREE_CONSTANT (init) = TREE_STATIC (init) = 1;
1386 return init;
1387 }
1388
1389 /* Return the CONSTRUCTOR expr for a type_info of pointer or reference TYPE.
1390 DESC provides information about the particular type_info derivation,
1391 which adds target type and qualifier flags members to the type_info base. */
1392
1393 static tree
1394 ptr_ref_initializer (desc, target)
1395 tree desc;
1396 tree target;
1397 {
1398 tree init = tinfo_base_init (desc, target);
1399 tree to = TREE_TYPE (target);
1400 int flags = qualifier_flags (to);
1401
1402 init = tree_cons (NULL_TREE, build_int_2 (flags, 0), init);
1403 init = tree_cons (NULL_TREE,
1404 build_unary_op (ADDR_EXPR,
1405 get_tinfo_decl (TYPE_MAIN_VARIANT (to)), 0),
1406 init);
1407
1408 init = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, nreverse (init));
1409 TREE_HAS_CONSTRUCTOR (init) = TREE_CONSTANT (init) = TREE_STATIC (init) = 1;
1410 return init;
1411 }
1412
1413 /* Return the CONSTRUCTOR expr for a type_info of pointer or reference TYPE.
1414 DESC provides information about the particular type_info derivation,
1415 which adds target type and qualifier flags members to the type_info base. */
1416
1417 static tree
1418 ptmd_initializer (desc, target)
1419 tree desc;
1420 tree target;
1421 {
1422 tree init = tinfo_base_init (desc, target);
1423 tree to = TYPE_PTRMEM_POINTED_TO_TYPE (target);
1424 tree klass = TYPE_PTRMEM_CLASS_TYPE (target);
1425 int flags = qualifier_flags (to);
1426
1427 init = tree_cons (NULL_TREE,
1428 build_unary_op (ADDR_EXPR, get_tinfo_decl (klass), 0),
1429 init);
1430 init = tree_cons (NULL_TREE,
1431 build_unary_op (ADDR_EXPR,
1432 get_tinfo_decl (TYPE_MAIN_VARIANT (to)), 0),
1433 init);
1434 init = tree_cons (NULL_TREE, build_int_2 (flags, 0), init);
1435
1436 init = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, nreverse (init));
1437 TREE_HAS_CONSTRUCTOR (init) = TREE_CONSTANT (init) = TREE_STATIC (init) = 1;
1438 return init;
1439 }
1440
1441 /* Determine the hint flags describing the features of a class's heirarchy.
1442 FIXME: better set the hint_flags here! For now set them
1443 to safe 'don't know' values. The specification is under
1444 review. Don't forget to check the runtime dynamic_cast and
1445 catch machinery if these change. */
1446
1447 static int
1448 class_hint_flags (type)
1449 tree type;
1450 {
1451 int hint_flags = 0;
1452 hint_flags |= 0x1; /* contains multiply inherited sub object */
1453 hint_flags |= 0x4; /* has virtual bases */
1454 hint_flags |= 0x8; /* has private base */
1455 if (TYPE_POLYMORPHIC_P (type))
1456 hint_flags |= 0x2;
1457
1458 return hint_flags;
1459 }
1460
1461 /* Return the CONSTRUCTOR expr for a type_info of class TYPE.
1462 DESC provides information about the particular __class_type_info derivation,
1463 which adds hint flags and TRAIL initializers to the type_info base. */
1464
1465 static tree
1466 class_initializer (desc, target, trail)
1467 tree desc;
1468 tree target;
1469 tree trail;
1470 {
1471 tree init = tinfo_base_init (desc, target);
1472 int flags = class_hint_flags (target);
1473
1474 trail = tree_cons (NULL_TREE, build_int_2 (flags, 0), trail);
1475 TREE_CHAIN (init) = trail;
1476 init = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, init);
1477 TREE_HAS_CONSTRUCTOR (init) = TREE_CONSTANT (init) = TREE_STATIC (init) = 1;
1478 return init;
1479 }
1480
1481 /* Generate a pseudo_type_info VAR_DECL suitable for the supplied
1482 TARGET_TYPE and given the REAL_NAME. This is the structure expected by
1483 the runtime, and therefore has additional fields. If we need not emit a
1484 definition (because the runtime must contain it), return NULL_TREE,
1485 otherwise return the VAR_DECL. */
1486
1487 static tree
1488 synthesize_tinfo_var (target_type, real_name)
1489 tree target_type;
1490 tree real_name;
1491 {
1492 tree var_init = NULL_TREE;
1493 tree var_type = NULL_TREE;
1494
1495 my_friendly_assert (new_abi_rtti_p (), 20000118);
1496
1497 switch (TREE_CODE (target_type))
1498 {
1499 case POINTER_TYPE:
1500 if (TYPE_PTRMEM_P (target_type))
1501 {
1502 var_type = ptmd_desc_type_node;
1503 var_init = ptmd_initializer (var_type, target_type);
1504 }
1505 else
1506 {
1507 int code = TREE_CODE (TREE_TYPE (target_type));
1508
1509 if ((CP_TYPE_QUALS (TREE_TYPE (target_type)) | TYPE_QUAL_CONST)
1510 == TYPE_QUAL_CONST
1511 && (code == INTEGER_TYPE || code == BOOLEAN_TYPE
1512 || code == CHAR_TYPE || code == REAL_TYPE
1513 || code == VOID_TYPE)
1514 && !doing_runtime)
1515 /* These are in the runtime. */
1516 return NULL_TREE;
1517 var_type = ptr_desc_type_node;
1518 var_init = ptr_ref_initializer (var_type, target_type);
1519 }
1520 break;
1521 case REFERENCE_TYPE:
1522 var_type = ref_desc_type_node;
1523 var_init = ptr_ref_initializer (var_type, target_type);
1524 break;
1525 case ENUMERAL_TYPE:
1526 var_type = enum_desc_type_node;
1527 var_init = generic_initializer (var_type, target_type);
1528 break;
1529 case FUNCTION_TYPE:
1530 var_type = func_desc_type_node;
1531 var_init = generic_initializer (var_type, target_type);
1532 break;
1533 case ARRAY_TYPE:
1534 var_type = ary_desc_type_node;
1535 var_init = generic_initializer (var_type, target_type);
1536 break;
1537 case UNION_TYPE:
1538 case RECORD_TYPE:
1539 if (!TYPE_SIZE (target_type))
1540 {
1541 /* FIXME: incomplete type. Awaiting specification. */
1542 return NULL_TREE;
1543 }
1544 else if (!CLASSTYPE_N_BASECLASSES (target_type))
1545 {
1546 var_type = class_desc_type_node;
1547 var_init = class_initializer (var_type, target_type, NULL_TREE);
1548 }
1549 else
1550 {
1551 /* if this has a single public non-virtual base, it's easier */
1552 tree binfo = TYPE_BINFO (target_type);
1553 int nbases = BINFO_N_BASETYPES (binfo);
1554 tree base_binfos = BINFO_BASETYPES (binfo);
1555 tree base_inits = NULL_TREE;
1556 int is_simple = nbases == 1;
1557 int ix;
1558
1559 /* Generate the base information initializer. */
1560 for (ix = nbases; ix--;)
1561 {
1562 tree base_binfo = TREE_VEC_ELT (base_binfos, ix);
1563 tree base_init = NULL_TREE;
1564 int flags = 0;
1565 tree tinfo;
1566 tree offset;
1567
1568 if (TREE_VIA_VIRTUAL (base_binfo))
1569 flags |= 1;
1570 if (TREE_PUBLIC (base_binfo))
1571 flags |= 2;
1572 tinfo = get_tinfo_decl (BINFO_TYPE (base_binfo));
1573 tinfo = build_unary_op (ADDR_EXPR, tinfo, 0);
1574 offset = get_base_offset (base_binfo, target_type);
1575
1576 /* is it a single public inheritance? */
1577 if (is_simple && flags == 2 && integer_zerop (offset))
1578 {
1579 base_inits = tree_cons (NULL_TREE, tinfo, NULL_TREE);
1580 break;
1581 }
1582 is_simple = 0;
1583
1584 base_init = tree_cons
1585 (NULL_TREE, build_int_2 (flags, 0), base_init);
1586 base_init = tree_cons (NULL_TREE, offset, base_init);
1587 base_init = tree_cons (NULL_TREE, tinfo, base_init);
1588 base_init = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, base_init);
1589 base_inits = tree_cons (NULL_TREE, base_init, base_inits);
1590 }
1591
1592 if (is_simple)
1593 var_type = si_class_desc_type_node;
1594 else
1595 {
1596 /* Prepend the number of bases. */
1597 base_inits = build (CONSTRUCTOR, NULL_TREE, NULL_TREE, base_inits);
1598 base_inits = tree_cons (NULL_TREE, base_inits, NULL_TREE);
1599 base_inits = tree_cons (NULL_TREE,
1600 build_int_2 (nbases, 0), base_inits);
1601
1602 var_type = get_vmi_pseudo_type_info (nbases);
1603 }
1604 var_init = class_initializer (var_type, target_type, base_inits);
1605 }
1606 break;
1607 case INTEGER_TYPE:
1608 case BOOLEAN_TYPE:
1609 case CHAR_TYPE:
1610 case REAL_TYPE:
1611 case VOID_TYPE:
1612 if (!doing_runtime)
1613 /* These are guaranteed to be in the runtime. */
1614 return NULL_TREE;
1615 var_type = bltn_desc_type_node;
1616 var_init = generic_initializer (var_type, target_type);
1617 break;
1618 default:
1619 my_friendly_abort (20000117);
1620 }
1621
1622 return create_real_tinfo_var (real_name, TINFO_PSEUDO_TYPE (var_type), var_init);
1623 }
1624
1625 /* Create the real typeinfo variable. */
1626
1627 static tree
1628 create_real_tinfo_var (name, type, init)
1629 tree name;
1630 tree type;
1631 tree init;
1632 {
1633 tree decl;
1634
1635 decl = build_lang_decl (VAR_DECL, name,
1636 build_qualified_type (type, TYPE_QUAL_CONST));
1637 DECL_ARTIFICIAL (decl) = 1;
1638 TREE_READONLY (decl) = 1;
1639 TREE_STATIC (decl) = 1;
1640 TREE_PUBLIC (decl) = 1;
1641 DECL_EXTERNAL (decl) = 0;
1642
1643 comdat_linkage (decl);
1644 DECL_ASSEMBLER_NAME (decl) = name;
1645 DECL_INITIAL (decl) = init;
1646 cp_finish_decl (decl, init, NULL_TREE, 0);
1647
1648 return decl;
1649 }
1650
1651 /* Generate the RECORD_TYPE containing the data layout of a type_info
1652 derivative as used by the runtime. This layout must be consistent with
1653 that defined in the runtime support. Also generate the VAR_DECL for the
1654 type's vtable. We explicitly manage the vtable member, and name it for
1655 real type as used in the runtime. The RECORD type has a different name,
1656 to avoid collisions. Return a TREE_LIST who's TINFO_PSEUDO_TYPE
1657 is the generated type and TINFO_VTABLE_DECL is the vtable decl.
1658
1659 REAL_NAME is the runtime's name of the type. Trailing arguments are
1660 additional FIELD_DECL's for the structure. The final argument must be
1661 NULL. */
1662
1663 static tree
1664 create_pseudo_type_info VPARAMS((const char *real_name, int ident, ...))
1665 {
1666 #ifndef ANSI_PROTOTYPES
1667 char const *real_name;
1668 int ident;
1669 #endif
1670 va_list ap;
1671 tree real_type, pseudo_type;
1672 char *pseudo_name;
1673 tree vtable_decl;
1674 int ix;
1675 tree fields[10];
1676 tree field_decl;
1677 tree result;
1678
1679 VA_START (ap, ident);
1680 #ifndef ANSI_PROTOTYPES
1681 real_name = va_arg (ap, char const *);
1682 ident = va_arg (app, int);
1683 #endif
1684
1685 /* Generate the pseudo type name. */
1686 pseudo_name = (char *)alloca (strlen (real_name) + 30);
1687 strcpy (pseudo_name, real_name);
1688 strcat (pseudo_name, "_pseudo");
1689 if (ident)
1690 sprintf (pseudo_name + strlen (pseudo_name), "%d", ident);
1691
1692 /* Get the vtable decl. */
1693 real_type = xref_tag (class_type_node, get_identifier (real_name), 1);
1694 vtable_decl = get_vtable_decl (real_type, /*complete=*/1);
1695
1696 /* First field is the pseudo type_info base class. */
1697 fields[0] = build_lang_decl (FIELD_DECL, NULL_TREE, ti_desc_type_node);
1698
1699 /* Now add the derived fields. */
1700 for (ix = 0; (field_decl = va_arg (ap, tree));)
1701 fields[++ix] = field_decl;
1702
1703 /* Create the pseudo type. */
1704 pseudo_type = make_aggr_type (RECORD_TYPE);
1705 finish_builtin_type (pseudo_type, pseudo_name, fields, ix, ptr_type_node);
1706 TYPE_HAS_CONSTRUCTOR (pseudo_type) = 1;
1707 va_end (ap);
1708
1709 result = tree_cons (NULL_TREE, NULL_TREE, NULL_TREE);
1710 TINFO_VTABLE_DECL (result) = vtable_decl;
1711 TINFO_PSEUDO_TYPE (result) = pseudo_type;
1712
1713 return result;
1714 }
1715
1716 /* Return a descriptor for a vmi type with NUM_BASES bases. */
1717
1718 static tree
1719 get_vmi_pseudo_type_info (num_bases)
1720 int num_bases;
1721 {
1722 tree desc;
1723 tree array_domain, base_array;
1724
1725 if (TREE_VEC_LENGTH (vmi_class_desc_type_node) <= num_bases)
1726 {
1727 int ix;
1728 tree extend = make_tree_vec (num_bases + 5);
1729
1730 for (ix = TREE_VEC_LENGTH (vmi_class_desc_type_node); ix--;)
1731 TREE_VEC_ELT (extend, ix) = TREE_VEC_ELT (vmi_class_desc_type_node, ix);
1732 vmi_class_desc_type_node = extend;
1733 }
1734 desc = TREE_VEC_ELT (vmi_class_desc_type_node, num_bases);
1735
1736 if (desc)
1737 return desc;
1738
1739 /* Add number of bases and trailing array of base_class_type_info. */
1740 array_domain = build_index_type (build_int_2 (num_bases, 0));
1741 base_array = build_array_type (base_desc_type_node, array_domain);
1742
1743 if (flag_honor_std)
1744 push_namespace (get_identifier ("std"));
1745
1746 desc = create_pseudo_type_info
1747 ("__vmi_class_type_info", num_bases,
1748 build_lang_decl (FIELD_DECL, NULL_TREE, integer_type_node),
1749 build_lang_decl (FIELD_DECL, NULL_TREE, integer_type_node),
1750 build_lang_decl (FIELD_DECL, NULL_TREE, base_array),
1751 NULL);
1752
1753 if (flag_honor_std)
1754 pop_namespace ();
1755
1756 TREE_VEC_ELT (vmi_class_desc_type_node, num_bases) = desc;
1757 return desc;
1758 }
1759
1760 /* Make sure the required builtin types exist for generating the type_info
1761 varable definitions. */
1762
1763 static void
1764 create_tinfo_types ()
1765 {
1766 tree ptr_type_info;
1767
1768 if (bltn_desc_type_node)
1769 return;
1770 if (flag_honor_std)
1771 push_namespace (get_identifier ("std"));
1772
1773 ptr_type_info = build_pointer_type
1774 (build_qualified_type
1775 (type_info_type_node, TYPE_QUAL_CONST));
1776
1777 /* Create the internal type_info structure. This is used as a base for
1778 the other structures. */
1779 {
1780 tree fields[2];
1781
1782 ti_desc_type_node = make_aggr_type (RECORD_TYPE);
1783 fields[0] = build_lang_decl (FIELD_DECL, NULL_TREE, const_ptr_type_node);
1784 fields[1] = build_lang_decl (FIELD_DECL, NULL_TREE, const_string_type_node);
1785 finish_builtin_type (ti_desc_type_node, "__type_info_pseudo",
1786 fields, 1, ptr_type_node);
1787 TYPE_HAS_CONSTRUCTOR (ti_desc_type_node) = 1;
1788 }
1789
1790 /* Fundamental type_info */
1791 bltn_desc_type_node = create_pseudo_type_info
1792 ("__fundamental_type_info", 0,
1793 NULL);
1794
1795 /* Pointer and reference type_info. These two fields, qualification mask
1796 and pointer to the pointed to (referenced) type. */
1797 ptr_desc_type_node = create_pseudo_type_info
1798 ("__pointer_type_info", 0,
1799 build_lang_decl (FIELD_DECL, NULL_TREE, integer_type_node),
1800 build_lang_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
1801 NULL);
1802 ref_desc_type_node = create_pseudo_type_info
1803 ("__reference_type_info", 0,
1804 build_lang_decl (FIELD_DECL, NULL_TREE, integer_type_node),
1805 build_lang_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
1806 NULL);
1807
1808 /* Array, function and enum type_info. No additional fields. */
1809 ary_desc_type_node = create_pseudo_type_info
1810 ("__array_type_info", 0,
1811 NULL);
1812 func_desc_type_node = create_pseudo_type_info
1813 ("__function_type_info", 0,
1814 NULL);
1815 enum_desc_type_node = create_pseudo_type_info
1816 ("__enum_type_info", 0,
1817 NULL);
1818
1819 /* Class type_info. Add a flags field. */
1820 class_desc_type_node = create_pseudo_type_info
1821 ("__class_type_info", 0,
1822 build_lang_decl (FIELD_DECL, NULL_TREE, integer_type_node),
1823 NULL);
1824
1825 /* Single public non-virtual base class. Add pointer to base class. */
1826 si_class_desc_type_node = create_pseudo_type_info
1827 ("__si_class_type_info", 0,
1828 build_lang_decl (FIELD_DECL, NULL_TREE, integer_type_node),
1829 build_lang_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
1830 NULL);
1831
1832 /* Base class internal helper. Pointer to base type, offset to base,
1833 flags. */
1834 {
1835 tree fields[3];
1836
1837 fields[0] = build_lang_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
1838 fields[1] = build_lang_decl (FIELD_DECL, NULL_TREE, ptrdiff_type_node),
1839 fields[2] = build_lang_decl (FIELD_DECL, NULL_TREE, integer_type_node),
1840 base_desc_type_node = make_aggr_type (RECORD_TYPE);
1841 finish_builtin_type (base_desc_type_node, "__base_class_type_info_pseudo",
1842 fields, 2, ptr_type_node);
1843 TYPE_HAS_CONSTRUCTOR (base_desc_type_node) = 1;
1844 }
1845
1846 /* General heirarchy is created as necessary in this vector. */
1847 vmi_class_desc_type_node = make_tree_vec (10);
1848
1849 /* Pointer to member data type_info. Add pointer to the class, pointer
1850 to the member's type info and qualifications flags. */
1851 ptmd_desc_type_node = create_pseudo_type_info
1852 ("__ptr_to_member_type_info", 0,
1853 build_lang_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
1854 build_lang_decl (FIELD_DECL, NULL_TREE, ptr_type_info),
1855 build_lang_decl (FIELD_DECL, NULL_TREE, integer_type_node),
1856 NULL);
1857
1858 if (flag_honor_std)
1859 pop_namespace ();
1860 }
1861
1862 /* Emit the type_info descriptors which are guaranteed to be in the runtime
1863 support. Generating them here guarantees consistency with the other
1864 structures. We use the following heuristic to determine when the runtime
1865 is being generated. If std::__fundamental_type_info is defined, and it's
1866 destructor is defined, then the runtime is being built. */
1867
1868 void
1869 emit_support_tinfos ()
1870 {
1871 static tree *const fundamentals[] =
1872 {
1873 &void_type_node,
1874 &boolean_type_node,
1875 &wchar_type_node,
1876 #if 0
1877 &signed_wchar_type_node, &unsigned_wchar_type_node,
1878 #endif
1879 &char_type_node, &signed_char_type_node, &unsigned_char_type_node,
1880 &short_integer_type_node, &short_unsigned_type_node,
1881 &integer_type_node, &unsigned_type_node,
1882 &long_integer_type_node, &long_unsigned_type_node,
1883 &long_long_integer_type_node, &long_long_unsigned_type_node,
1884 &float_type_node, &double_type_node, &long_double_type_node,
1885
1886 /* GCC extension types */
1887 #if 0
1888 &complex_integer_type_node,
1889 &complex_float_type_node, &complex_double_type_node,
1890 &complex_long_double_type_node,
1891 #endif
1892
1893 0
1894 };
1895 int ix;
1896 tree bltn_type, dtor;
1897
1898 if (flag_honor_std)
1899 push_namespace (get_identifier ("std"));
1900 bltn_type = xref_tag (class_type_node,
1901 get_identifier ("__fundamental_type_info"), 1);
1902 if (flag_honor_std)
1903 pop_namespace ();
1904 if (!TYPE_SIZE (bltn_type))
1905 return;
1906 dtor = TREE_VEC_ELT (CLASSTYPE_METHOD_VEC (bltn_type), 1);
1907 if (DECL_EXTERNAL (dtor))
1908 return;
1909 doing_runtime = 1;
1910 for (ix = 0; fundamentals[ix]; ix++)
1911 {
1912 tree bltn = *fundamentals[ix];
1913 tree bltn_ptr = build_pointer_type (bltn);
1914 tree bltn_const_ptr = build_pointer_type
1915 (build_qualified_type (bltn, TYPE_QUAL_CONST));
1916 tree tinfo;
1917
1918 tinfo = get_tinfo_decl (bltn);
1919 TREE_USED (tinfo) = 1;
1920 TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (tinfo)) = 1;
1921
1922 tinfo = get_tinfo_decl (bltn_ptr);
1923 TREE_USED (tinfo) = 1;
1924 TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (tinfo)) = 1;
1925
1926 tinfo = get_tinfo_decl (bltn_const_ptr);
1927 TREE_USED (tinfo) = 1;
1928 TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (tinfo)) = 1;
1929 }
1930 }
1931
1932 /* Return non-zero, iff T is a type_info variable which has not had a
1933 definition emitted for it. */
1934
1935 int
1936 tinfo_decl_p (t, data)
1937 tree t;
1938 void *data ATTRIBUTE_UNUSED;
1939 {
1940 return TREE_CODE (t) == VAR_DECL
1941 && IDENTIFIER_GLOBAL_VALUE (DECL_NAME (t)) == (t)
1942 && TREE_TYPE (t) == tinfo_decl_type
1943 && TREE_TYPE (DECL_NAME (t));
1944 }
1945
1946 /* Emit a suitable type_info definition for the type_info decl pointed to by
1947 DECL_PTR. We emit a completely new variable, of the correct type for the
1948 actual type this is describing. The DECL_ASSEMBLER_NAME of the generated
1949 definition is set to that of the supplied decl, so that they can be tied
1950 up. Mark the supplied decl as having been dealt with. Emitting one
1951 definitions might cause other declarations to be emitted.
1952
1953 We need to do things this way, because we're trying to do something like
1954
1955 struct B : A {
1956 ...
1957 };
1958
1959 extern const A tinfo_var;
1960
1961 const B tinfo_var = {...};
1962
1963 which is not permitted. Also, we've not necessarily seen the definition of B.
1964 So we do something like the following,
1965
1966 extern const A tinfo_var;
1967
1968 struct pseudo_A {
1969 const void *vtable_ptr;
1970 const char *name;
1971 };
1972 struct pseudo_B {
1973 pseudo_A base;
1974 ...
1975 };
1976
1977 const pseudo_B proxy_tinfo_var attribute((assembler_name="tinfo_var")) =
1978 {
1979 {&B::vtable, "..."},
1980 ...
1981 };
1982
1983 pseudo_A and pseudo_B must be layout equivalent to the real definitions in
1984 the runtime. */
1985
1986 int
1987 emit_tinfo_decl (decl_ptr, data)
1988 tree *decl_ptr;
1989 void *data ATTRIBUTE_UNUSED;
1990 {
1991 tree tinfo_decl = *decl_ptr;
1992 tree tinfo_type, decl;
1993
1994 my_friendly_assert (TREE_TYPE (tinfo_decl) == tinfo_decl_type, 20000121);
1995 tinfo_type = TREE_TYPE (DECL_NAME (tinfo_decl));
1996 my_friendly_assert (tinfo_type != NULL_TREE, 20000120);
1997
1998 /* Say we've dealt with it. */
1999 TREE_TYPE (DECL_NAME (tinfo_decl)) = NULL_TREE;
2000
2001 if (!DECL_NEEDED_P (tinfo_decl))
2002 return 0;
2003 create_tinfo_types ();
2004 decl = synthesize_tinfo_var (tinfo_type, DECL_ASSEMBLER_NAME (tinfo_decl));
2005
2006 return decl != 0;
2007 }