mirror of
git://gcc.gnu.org/git/gcc.git
synced 2024-12-19 04:08:59 +08:00
cp-tree.h (get_tinfo_fn_dynamic): Remove prototype.
* cp-tree.h (get_tinfo_fn_dynamic): Remove prototype. (build_x_typeid): Likewise. (get_tinfo_fn): Likewise. (get_tinfo_fn_unused): Rename to ... (get_tinfo_decl): ... here. * rtti.c (build_headof): Replace logic error with assertion. (get_tinfo_fn_dynamic): Rename to ... (get_tinfo_decl_dynamic): ... here. Make static. Use complete_type_or_else. (build_x_typeid): Move into ... (build_typeid): ... here. Adjust call to get_tinfo_decl_dynamic. Use tinfo_from_decl. Simplify throw_bad_typeid expression. (get_tinfo_fn_unused): Rename to ... (get_tinfo_decl): ... here. Adjust comment. (get_tinfo_fn): Delete. (tinfo_from_decl): New static function. (get_typeid_1): Call get_tinfo_decl and tinfo_from_decl. (get_typeid): Use complete_type_or_else. (build_dynamic_cast_1): Adjust calls to get_tinfo_decl_dynamic. Simplify throw_bad_cast expression. * parse.y (primary): Adjust call to build_typeid. * except.c (build_eh_type_type_ref): Adjust call to get_tinfo_decl. Mark as used. * class.c (set_rtti_entry): Adjust call to get_tinfo_decl. * decl2.c (build_expr_from_tree): Adjust call to build_typeid. * parse.c: Regenerated. From-SVN: r31485
This commit is contained in:
parent
c399e76da6
commit
e5f614d777
@ -1,3 +1,33 @@
|
||||
2000-01-18 Nathan Sidwell <sidwell@codesourcery.com>
|
||||
|
||||
* cp-tree.h (get_tinfo_fn_dynamic): Remove prototype.
|
||||
(build_x_typeid): Likewise.
|
||||
(get_tinfo_fn): Likewise.
|
||||
(get_tinfo_fn_unused): Rename to ...
|
||||
(get_tinfo_decl): ... here.
|
||||
* rtti.c (build_headof): Replace logic error with assertion.
|
||||
(get_tinfo_fn_dynamic): Rename to ...
|
||||
(get_tinfo_decl_dynamic): ... here. Make static. Use
|
||||
complete_type_or_else.
|
||||
(build_x_typeid): Move into ...
|
||||
(build_typeid): ... here. Adjust call to
|
||||
get_tinfo_decl_dynamic. Use tinfo_from_decl. Simplify
|
||||
throw_bad_typeid expression.
|
||||
(get_tinfo_fn_unused): Rename to ...
|
||||
(get_tinfo_decl): ... here. Adjust comment.
|
||||
(get_tinfo_fn): Delete.
|
||||
(tinfo_from_decl): New static function.
|
||||
(get_typeid_1): Call get_tinfo_decl and tinfo_from_decl.
|
||||
(get_typeid): Use complete_type_or_else.
|
||||
(build_dynamic_cast_1): Adjust calls to
|
||||
get_tinfo_decl_dynamic. Simplify throw_bad_cast expression.
|
||||
* parse.y (primary): Adjust call to build_typeid.
|
||||
* except.c (build_eh_type_type_ref): Adjust call to
|
||||
get_tinfo_decl. Mark as used.
|
||||
* class.c (set_rtti_entry): Adjust call to get_tinfo_decl.
|
||||
* decl2.c (build_expr_from_tree): Adjust call to build_typeid.
|
||||
* parse.c: Regenerated.
|
||||
|
||||
2000-01-17 Mark Mitchell <mark@codesourcery.com>
|
||||
|
||||
* class.c (fixed_type_or_null): Don't clear NONNULL. Document
|
||||
|
@ -829,7 +829,7 @@ set_rtti_entry (virtuals, offset, type)
|
||||
return;
|
||||
|
||||
if (flag_rtti)
|
||||
fn = get_tinfo_fn_unused (type);
|
||||
fn = get_tinfo_decl (type);
|
||||
else
|
||||
/* If someone tries to get RTTI information for a type compiled
|
||||
without RTTI, they're out of luck. By calling __pure_virtual
|
||||
|
@ -3961,11 +3961,8 @@ extern void finish_repo PROTO((void));
|
||||
|
||||
/* in rtti.c */
|
||||
extern void init_rtti_processing PROTO((void));
|
||||
extern tree get_tinfo_fn_dynamic PROTO((tree));
|
||||
extern tree build_typeid PROTO((tree));
|
||||
extern tree build_x_typeid PROTO((tree));
|
||||
extern tree get_tinfo_fn PROTO((tree));
|
||||
extern tree get_tinfo_fn_unused PROTO((tree));
|
||||
extern tree get_tinfo_decl PROTO((tree));
|
||||
extern tree get_typeid PROTO((tree));
|
||||
extern tree get_typeid_1 PROTO((tree));
|
||||
extern tree build_dynamic_cast PROTO((tree, tree));
|
||||
|
@ -3999,7 +3999,7 @@ build_expr_from_tree (t)
|
||||
case TYPEID_EXPR:
|
||||
if (TREE_CODE_CLASS (TREE_CODE (TREE_OPERAND (t, 0))) == 't')
|
||||
return get_typeid (TREE_OPERAND (t, 0));
|
||||
return build_x_typeid (build_expr_from_tree (TREE_OPERAND (t, 0)));
|
||||
return build_typeid (build_expr_from_tree (TREE_OPERAND (t, 0)));
|
||||
|
||||
case VAR_DECL:
|
||||
return convert_from_reference (t);
|
||||
|
@ -343,7 +343,7 @@ build_eh_type_type (type)
|
||||
return build1 (ADDR_EXPR, ptr_type_node, get_typeid_1 (type));
|
||||
}
|
||||
|
||||
/* Build the address of a typeinfo function for use in the runtime
|
||||
/* Build the address of a typeinfo decl for use in the runtime
|
||||
matching field of the new exception model */
|
||||
|
||||
static tree
|
||||
@ -362,7 +362,8 @@ build_eh_type_type_ref (type)
|
||||
/* Peel off cv qualifiers. */
|
||||
type = TYPE_MAIN_VARIANT (type);
|
||||
|
||||
exp = get_tinfo_fn (type);
|
||||
exp = get_tinfo_decl (type);
|
||||
mark_used (exp);
|
||||
exp = build1 (ADDR_EXPR, ptr_type_node, exp);
|
||||
|
||||
return (exp);
|
||||
|
@ -5748,7 +5748,7 @@ case 327:
|
||||
break;}
|
||||
case 328:
|
||||
#line 1460 "parse.y"
|
||||
{ yyval.ttype = build_x_typeid (yyvsp[-1].ttype); ;
|
||||
{ yyval.ttype = build_typeid (yyvsp[-1].ttype); ;
|
||||
break;}
|
||||
case 329:
|
||||
#line 1462 "parse.y"
|
||||
|
@ -1457,7 +1457,7 @@ primary:
|
||||
check_for_new_type ("const_cast", $3);
|
||||
$$ = build_const_cast (type, $6); }
|
||||
| TYPEID '(' expr ')'
|
||||
{ $$ = build_x_typeid ($3); }
|
||||
{ $$ = build_typeid ($3); }
|
||||
| TYPEID '(' type_id ')'
|
||||
{ tree type = groktypename ($3.t);
|
||||
check_for_new_type ("typeid", $3);
|
||||
|
124
gcc/cp/rtti.c
124
gcc/cp/rtti.c
@ -48,6 +48,8 @@ static void expand_ptr_desc PROTO((tree, tree));
|
||||
static void expand_generic_desc PROTO((tree, tree, const char *));
|
||||
static tree throw_bad_cast PROTO((void));
|
||||
static tree throw_bad_typeid PROTO((void));
|
||||
static tree get_tinfo_decl_dynamic PROTO((tree));
|
||||
static tree tinfo_from_decl PROTO((tree));
|
||||
|
||||
void
|
||||
init_rtti_processing ()
|
||||
@ -95,11 +97,7 @@ build_headof (exp)
|
||||
tree aref;
|
||||
tree offset;
|
||||
|
||||
if (TREE_CODE (type) != POINTER_TYPE)
|
||||
{
|
||||
error ("`headof' applied to non-pointer type");
|
||||
return error_mark_node;
|
||||
}
|
||||
my_friendly_assert (TREE_CODE (type) == POINTER_TYPE, 20000112);
|
||||
type = TREE_TYPE (type);
|
||||
|
||||
if (!TYPE_POLYMORPHIC_P (type))
|
||||
@ -172,25 +170,19 @@ throw_bad_typeid ()
|
||||
return call_void_fn ("__throw_bad_typeid");
|
||||
}
|
||||
|
||||
/* Return the type_info function associated with the expression EXP. If
|
||||
EXP is a reference to a polymorphic class, return the dynamic type;
|
||||
/* Return a pointer to type_info function associated with the expression EXP.
|
||||
If EXP is a reference to a polymorphic class, return the dynamic type;
|
||||
otherwise return the static type of the expression. */
|
||||
|
||||
tree
|
||||
get_tinfo_fn_dynamic (exp)
|
||||
static tree
|
||||
get_tinfo_decl_dynamic (exp)
|
||||
tree exp;
|
||||
{
|
||||
tree type;
|
||||
|
||||
|
||||
if (exp == error_mark_node)
|
||||
return error_mark_node;
|
||||
|
||||
if (type_unknown_p (exp))
|
||||
{
|
||||
error ("typeid of overloaded function");
|
||||
return error_mark_node;
|
||||
}
|
||||
|
||||
type = TREE_TYPE (exp);
|
||||
|
||||
/* peel back references, so they match. */
|
||||
@ -199,12 +191,12 @@ get_tinfo_fn_dynamic (exp)
|
||||
|
||||
/* Peel off cv qualifiers. */
|
||||
type = TYPE_MAIN_VARIANT (type);
|
||||
|
||||
if (TYPE_SIZE (complete_type (type)) == NULL_TREE)
|
||||
{
|
||||
cp_error ("taking typeid of incomplete type `%T'", type);
|
||||
return error_mark_node;
|
||||
}
|
||||
|
||||
if (type != void_type_node)
|
||||
type = complete_type_or_else (type, exp);
|
||||
|
||||
if (!type)
|
||||
return error_mark_node;
|
||||
|
||||
/* If exp is a reference to polymorphic type, get the real type_info. */
|
||||
if (TYPE_POLYMORPHIC_P (type) && ! resolves_to_fixed_type_p (exp, 0))
|
||||
@ -223,7 +215,7 @@ get_tinfo_fn_dynamic (exp)
|
||||
/* If we don't have rtti stuff, get to a sub-object that does. */
|
||||
if (! CLASSTYPE_VFIELDS (type))
|
||||
{
|
||||
exp = build_unary_op (ADDR_EXPR, exp, 0);
|
||||
exp = build_unary_op (ADDR_EXPR, exp, 0);
|
||||
exp = build_headof_sub (exp);
|
||||
exp = build_indirect_ref (exp, NULL_PTR);
|
||||
}
|
||||
@ -237,21 +229,13 @@ get_tinfo_fn_dynamic (exp)
|
||||
}
|
||||
|
||||
/* otherwise return the type_info for the static type of the expr. */
|
||||
return get_tinfo_fn (TYPE_MAIN_VARIANT (type));
|
||||
exp = get_tinfo_decl (TYPE_MAIN_VARIANT (type));
|
||||
return build_unary_op (ADDR_EXPR, exp, 0);
|
||||
}
|
||||
|
||||
tree
|
||||
build_typeid (exp)
|
||||
tree exp;
|
||||
{
|
||||
exp = get_tinfo_fn_dynamic (exp);
|
||||
exp = build_call (exp, TREE_TYPE (tinfo_fn_type), NULL_TREE);
|
||||
return convert_from_reference (exp);
|
||||
}
|
||||
|
||||
tree
|
||||
build_x_typeid (exp)
|
||||
tree exp;
|
||||
{
|
||||
tree cond = NULL_TREE;
|
||||
tree type;
|
||||
@ -282,22 +266,18 @@ build_x_typeid (exp)
|
||||
cond = cp_convert (boolean_type_node, TREE_OPERAND (exp, 0));
|
||||
}
|
||||
|
||||
exp = get_tinfo_fn_dynamic (exp);
|
||||
exp = get_tinfo_decl_dynamic (exp);
|
||||
|
||||
if (exp == error_mark_node)
|
||||
return error_mark_node;
|
||||
|
||||
type = TREE_TYPE (tinfo_fn_type);
|
||||
exp = build_call (exp, type, NULL_TREE);
|
||||
exp = tinfo_from_decl (exp);
|
||||
|
||||
if (cond)
|
||||
{
|
||||
tree bad = throw_bad_typeid ();
|
||||
|
||||
bad = build_compound_expr
|
||||
(tree_cons (NULL_TREE, bad, build_tree_list
|
||||
(NULL_TREE, cp_convert (type, integer_zero_node))));
|
||||
exp = build (COND_EXPR, type, cond, exp, bad);
|
||||
exp = build (COND_EXPR, TREE_TYPE (exp), cond, exp, bad);
|
||||
}
|
||||
|
||||
return convert_from_reference (exp);
|
||||
@ -345,19 +325,16 @@ get_tinfo_var (type)
|
||||
return declare_global_var (tname, arrtype);
|
||||
}
|
||||
|
||||
/* Returns the decl for a function which will return a type_info node for
|
||||
TYPE. This version does not mark the function used, for use in
|
||||
set_rtti_entry; for the vtable case, we'll get marked in
|
||||
finish_vtable_vardecl, when we know that we want to be emitted.
|
||||
|
||||
We do this to avoid emitting the tinfo node itself, since we don't
|
||||
currently support DECL_DEFER_OUTPUT for variables. Also, we don't
|
||||
associate constant pools with their functions properly, so we would
|
||||
emit string constants and such even though we don't emit the actual
|
||||
function. When those bugs are fixed, this function should go away. */
|
||||
/* Returns a decl for a function or variable which can be used to obtain a
|
||||
type_info object for TYPE. The old-abi uses functions, the new-abi will
|
||||
use the type_info object directly. You can take the address of the
|
||||
returned decl, to save the decl. To use the generator call
|
||||
tinfo_from_generator. You must arrange that the decl is mark_used, if
|
||||
actually use it --- decls in vtables are only used if the vtable is
|
||||
output. */
|
||||
|
||||
tree
|
||||
get_tinfo_fn_unused (type)
|
||||
get_tinfo_decl (type)
|
||||
tree type;
|
||||
{
|
||||
tree name;
|
||||
@ -385,19 +362,20 @@ get_tinfo_fn_unused (type)
|
||||
pushdecl_top_level (d);
|
||||
make_function_rtl (d);
|
||||
mark_inline_for_output (d);
|
||||
|
||||
|
||||
return d;
|
||||
}
|
||||
|
||||
/* Likewise, but also mark it used. Called by various EH and RTTI code. */
|
||||
/* Given an expr produced by get_tinfo_decl, return an expr which
|
||||
produces a reference to the type_info object. */
|
||||
|
||||
tree
|
||||
get_tinfo_fn (type)
|
||||
tree type;
|
||||
static tree
|
||||
tinfo_from_decl (expr)
|
||||
tree expr;
|
||||
{
|
||||
tree d = get_tinfo_fn_unused (type);
|
||||
mark_used (d);
|
||||
return d;
|
||||
tree t = build_call (expr, TREE_TYPE (tinfo_fn_type), NULL_TREE);
|
||||
|
||||
return t;
|
||||
}
|
||||
|
||||
tree
|
||||
@ -406,12 +384,12 @@ get_typeid_1 (type)
|
||||
{
|
||||
tree t;
|
||||
|
||||
t = build_call
|
||||
(get_tinfo_fn (type), TREE_TYPE (tinfo_fn_type), NULL_TREE);
|
||||
t = get_tinfo_decl (type);
|
||||
t = tinfo_from_decl (t);
|
||||
return convert_from_reference (t);
|
||||
}
|
||||
|
||||
/* Return the type_info object for TYPE, creating it if necessary. */
|
||||
/* Return the type_info object for TYPE. */
|
||||
|
||||
tree
|
||||
get_typeid (type)
|
||||
@ -439,11 +417,11 @@ get_typeid (type)
|
||||
that is the operand of typeid are always ignored. */
|
||||
type = TYPE_MAIN_VARIANT (type);
|
||||
|
||||
if (TYPE_SIZE (complete_type (type)) == NULL_TREE)
|
||||
{
|
||||
cp_error ("taking typeid of incomplete type `%T'", type);
|
||||
return error_mark_node;
|
||||
}
|
||||
if (type != void_type_node)
|
||||
type = complete_type_or_else (type, NULL_TREE);
|
||||
|
||||
if (!type)
|
||||
return error_mark_node;
|
||||
|
||||
return get_typeid_1 (type);
|
||||
}
|
||||
@ -627,15 +605,15 @@ build_dynamic_cast_1 (type, expr)
|
||||
expr2 = build_headof (expr1);
|
||||
|
||||
if (ec == POINTER_TYPE)
|
||||
td1 = get_tinfo_fn_dynamic (build_indirect_ref (expr, NULL_PTR));
|
||||
td1 = get_tinfo_decl_dynamic (build_indirect_ref (expr, NULL_PTR));
|
||||
else
|
||||
td1 = get_tinfo_fn_dynamic (expr);
|
||||
td1 = get_tinfo_decl_dynamic (expr);
|
||||
td1 = decay_conversion (td1);
|
||||
|
||||
target_type = TYPE_MAIN_VARIANT (TREE_TYPE (type));
|
||||
static_type = TYPE_MAIN_VARIANT (TREE_TYPE (exprtype));
|
||||
td2 = decay_conversion (get_tinfo_fn (target_type));
|
||||
td3 = decay_conversion (get_tinfo_fn (static_type));
|
||||
td2 = decay_conversion (get_tinfo_decl (target_type));
|
||||
td3 = decay_conversion (get_tinfo_decl (static_type));
|
||||
|
||||
/* Determine how T and V are related. */
|
||||
boff = get_dynamic_cast_base_type (static_type, target_type);
|
||||
@ -678,10 +656,6 @@ build_dynamic_cast_1 (type, expr)
|
||||
if (tc == REFERENCE_TYPE)
|
||||
{
|
||||
expr1 = throw_bad_cast ();
|
||||
expr1 = build_compound_expr
|
||||
(tree_cons (NULL_TREE, expr1,
|
||||
build_tree_list (NULL_TREE, cp_convert (type, integer_zero_node))));
|
||||
TREE_TYPE (expr1) = type;
|
||||
result = save_expr (result);
|
||||
return build (COND_EXPR, type, result, result, expr1);
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user