From c291f8b146078790ba0bec3ce3cc5a86c8d8c187 Mon Sep 17 00:00:00 2001 From: Volker Reichelt Date: Wed, 7 Jun 2006 16:08:30 +0000 Subject: [PATCH] re PR c++/27601 (ICE (in fold_offsetof_1, at c-common.c:5998) on strange offsetof) PR c++/27601 * cp-tree.h (finish_offsetof): Add prototype. * semantics.c (finish_offsetof): New function. * parser.c (cp_parser_builtin_offsetof): Call it instead of fold_offsetof. * pt.c (tsubst_copy_and_build): Likewise. * g++.dg/ext/offsetof1.C: Test member functions. From-SVN: r114469 --- gcc/cp/ChangeLog | 9 +++++++++ gcc/cp/cp-tree.h | 1 + gcc/cp/parser.c | 2 +- gcc/cp/pt.c | 2 +- gcc/cp/semantics.c | 17 +++++++++++++++++ gcc/testsuite/ChangeLog | 5 +++++ gcc/testsuite/g++.dg/ext/offsetof1.C | 3 +++ 7 files changed, 37 insertions(+), 2 deletions(-) diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index c63ad8390ef..d401f88d79f 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,12 @@ +2006-06-07 Volker Reichelt + + PR c++/27601 + * cp-tree.h (finish_offsetof): Add prototype. + * semantics.c (finish_offsetof): New function. + * parser.c (cp_parser_builtin_offsetof): Call it instead of + fold_offsetof. + * pt.c (tsubst_copy_and_build): Likewise. + 2006-06-06 Mark Mitchell PR c++/27177 diff --git a/gcc/cp/cp-tree.h b/gcc/cp/cp-tree.h index 4e83852a304..77b906729eb 100644 --- a/gcc/cp/cp-tree.h +++ b/gcc/cp/cp-tree.h @@ -4252,6 +4252,7 @@ extern tree finish_id_expression (tree, tree, tree, bool, bool, bool, bool, const char **); extern tree finish_typeof (tree); +extern tree finish_offsetof (tree); extern void finish_decl_cleanup (tree, tree); extern void finish_eh_cleanup (tree); extern void expand_body (tree); diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index ee807295e6b..eaebe191c54 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -6036,7 +6036,7 @@ cp_parser_builtin_offsetof (cp_parser *parser) if (processing_template_decl) expr = build1 (OFFSETOF_EXPR, size_type_node, expr); else - expr = fold_offsetof (expr); + expr = finish_offsetof (expr); failure: parser->integral_constant_expression_p = save_ice_p; diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c index 8b2f0d3054e..07963d6b370 100644 --- a/gcc/cp/pt.c +++ b/gcc/cp/pt.c @@ -9126,7 +9126,7 @@ tsubst_copy_and_build (tree t, in_decl)); case OFFSETOF_EXPR: - return fold_offsetof (RECUR (TREE_OPERAND (t, 0))); + return finish_offsetof (RECUR (TREE_OPERAND (t, 0))); case STMT_EXPR: { diff --git a/gcc/cp/semantics.c b/gcc/cp/semantics.c index b4e9505b75b..8b414231666 100644 --- a/gcc/cp/semantics.c +++ b/gcc/cp/semantics.c @@ -2881,6 +2881,23 @@ finish_typeof (tree expr) return type; } +/* Perform C++-specific checks for __builtin_offsetof before calling + fold_offsetof. */ + +tree +finish_offsetof (tree expr) +{ + if (TREE_CODE (TREE_TYPE (expr)) == FUNCTION_TYPE + || TREE_CODE (TREE_TYPE (expr)) == METHOD_TYPE + || TREE_CODE (TREE_TYPE (expr)) == UNKNOWN_TYPE) + { + error ("cannot apply % to member function %qD", + TREE_OPERAND (expr, 1)); + return error_mark_node; + } + return fold_offsetof (expr); +} + /* Called from expand_body via walk_tree. Replace all AGGR_INIT_EXPRs with equivalent CALL_EXPRs. */ diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 0e870df741b..3e0314552d9 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2006-06-07 Volker Reichelt + + PR c++/27601 + * g++.dg/ext/offsetof1.C: Test member functions. + 2006-06-07 Steve Ellcey * gcc.dg/pr27095.c: Improve scanning. diff --git a/gcc/testsuite/g++.dg/ext/offsetof1.C b/gcc/testsuite/g++.dg/ext/offsetof1.C index 5d6552f7878..0cfabf8033c 100644 --- a/gcc/testsuite/g++.dg/ext/offsetof1.C +++ b/gcc/testsuite/g++.dg/ext/offsetof1.C @@ -4,6 +4,9 @@ struct bar { static int foo; + static int baz(); }; int a = __builtin_offsetof(bar, foo); // { dg-error "static data member" } +int b = __builtin_offsetof(bar, baz); // { dg-error "member function" } +int c = __builtin_offsetof(bar, ~bar); // { dg-error "member function" } -- 2.30.2