diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index 6e44c4fcf62d731d42ba10538bc6ef1bda8714f4..443cdd5e9315d8c3a22cfca9d5e814b0dad5c192 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,13 @@ +1999-08-19 Mark Mitchell <mark@codesourcery.com> + + * cp-tree.def (PSEUDO_DTOR_EXPR): New tree code. + * decl2.c (build_expr_from_tree): Handle it. + * error.c (dump_expr): Likewise. + * pt.c (for_each_template_parm): Likewise. + (tsubst_copy): Likewise. + * tree.c (search_tree): Likewise. + * semantics.c (finish_pseudo_destructor_call): Create it. + 1999-08-18 Mark Mitchell <mark@codesourcery.com> * search.c (setup_class_bindings): Robustify. diff --git a/gcc/cp/cp-tree.def b/gcc/cp/cp-tree.def index 19709222e469b620f9735e6749cad56974c2a399..d31d33ea85e416448a16bf0e7946bf962aa6c099 100644 --- a/gcc/cp/cp-tree.def +++ b/gcc/cp/cp-tree.def @@ -214,6 +214,7 @@ DEFTREECODE (ALIGNOF_EXPR, "alignof_expr", '1', 1) DEFTREECODE (ARROW_EXPR, "arrow_expr", 'e', 1) DEFTREECODE (DOTSTAR_EXPR, "dotstar_expr", 'e', 2) DEFTREECODE (TYPEID_EXPR, "typeid_expr", 'e', 1) +DEFTREECODE (PSEUDO_DTOR_EXPR, "pseudo_dtor_expr", 'e', 3) DEFTREECODE (EXPR_STMT, "expr_stmt", 'e', 1) DEFTREECODE (COMPOUND_STMT, "compound_stmt", 'e', 1) diff --git a/gcc/cp/decl2.c b/gcc/cp/decl2.c index a0a7e6c367fada6f5d7a8310f5d0bca3e44b6c20..ecfdd61e695f8dcec77be82001adfe8b441e4061 100644 --- a/gcc/cp/decl2.c +++ b/gcc/cp/decl2.c @@ -3992,6 +3992,12 @@ build_expr_from_tree (t) build_expr_from_tree (TREE_OPERAND (t, 1)), build_expr_from_tree (TREE_OPERAND (t, 2))); + case PSEUDO_DTOR_EXPR: + return (finish_pseudo_destructor_call_expr + (build_expr_from_tree (TREE_OPERAND (t, 0)), + build_expr_from_tree (TREE_OPERAND (t, 1)), + build_expr_from_tree (TREE_OPERAND (t, 2)))); + case TREE_LIST: { tree purpose, value, chain; diff --git a/gcc/cp/error.c b/gcc/cp/error.c index ce0ffbf11b66e1f4eee57ea71d3480277b19f1b9..b6598ff30a4bece6c0b8d5173681f85dea5fc362 100644 --- a/gcc/cp/error.c +++ b/gcc/cp/error.c @@ -1776,6 +1776,14 @@ dump_expr (t, nop) dump_expr (TREE_OPERAND (t, 0), nop); break; + case PSEUDO_DTOR_EXPR: + dump_expr (TREE_OPERAND (t, 2), nop); + OB_PUTS ("."); + dump_type (TREE_OPERAND (t, 0), nop); + OB_PUTS ("::~"); + dump_type (TREE_OPERAND (t, 1), nop); + break; + case TEMPLATE_ID_EXPR: dump_decl (t, 0); break; diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c index 9a31d60699ddb701475e0f8b4208927b47bb959a..e1e8ab435cc6b3e9a6852c2119ed959ea63312d2 100644 --- a/gcc/cp/pt.c +++ b/gcc/cp/pt.c @@ -4300,6 +4300,7 @@ for_each_template_parm (t, fn, data) case DOTSTAR_EXPR: case TYPEID_EXPR: case LOOKUP_EXPR: + case PSEUDO_DTOR_EXPR: if (!fn) return 1; /* Fall through. */ @@ -7078,6 +7079,7 @@ tsubst_copy (t, args, complain, in_decl) case COND_EXPR: case MODOP_EXPR: + case PSEUDO_DTOR_EXPR: { r = build_nt (code, tsubst_copy (TREE_OPERAND (t, 0), args, complain, in_decl), diff --git a/gcc/cp/semantics.c b/gcc/cp/semantics.c index dc6b54144b0c255d1139499067db8472631560bf..def1276bffc489927ae05b062df8f67bca88106b 100644 --- a/gcc/cp/semantics.c +++ b/gcc/cp/semantics.c @@ -1229,6 +1229,9 @@ finish_pseudo_destructor_call_expr (object, scope, destructor) tree scope; tree destructor; { + if (processing_template_decl) + return build_min_nt (PSEUDO_DTOR_EXPR, object, scope, destructor); + if (scope && scope != destructor) cp_error ("destructor specifier `%T::~%T()' must have matching names", scope, destructor); diff --git a/gcc/cp/tree.c b/gcc/cp/tree.c index d159ac143b37a894b2c6d59db40850ffdde56bea..8d367535ba06e67be42c8361c493094f4112fc11 100644 --- a/gcc/cp/tree.c +++ b/gcc/cp/tree.c @@ -1675,6 +1675,7 @@ search_tree (t, func) case ARROW_EXPR: case DOTSTAR_EXPR: case TYPEID_EXPR: + case PSEUDO_DTOR_EXPR: break; case COMPLEX_CST: diff --git a/gcc/testsuite/g++.old-deja/g++.pt/crash48.C b/gcc/testsuite/g++.old-deja/g++.pt/crash48.C new file mode 100644 index 0000000000000000000000000000000000000000..907360bf78e1a891ac2f53168fdb6c616d67e4f8 --- /dev/null +++ b/gcc/testsuite/g++.old-deja/g++.pt/crash48.C @@ -0,0 +1,8 @@ +// Build don't link: +// Origin: Jean-Francois Panisset <panisset@discreet.com> + +template<class T> +void foo(T *data) +{ + ((char *)data)->~T(); +}