re PR c++/27508 (ICE on invalid destructor name)
authorVolker Reichelt <reichelt@igpm.rwth-aachen.de>
Thu, 3 Aug 2006 02:49:07 +0000 (02:49 +0000)
committerVolker Reichelt <reichelt@gcc.gnu.org>
Thu, 3 Aug 2006 02:49:07 +0000 (02:49 +0000)
PR c++/27508
* parser.c (cp_parser_unqualified_id): Check for invalid scopes
when parsing destructor names.

* g++.dg/parse/dtor9.C: New test.
* g++.dg/parse/dtor10.C: New test.
* g++.dg/other/error7.C: Adjust error-marker.

From-SVN: r115896

gcc/cp/ChangeLog
gcc/cp/parser.c
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/other/error7.C
gcc/testsuite/g++.dg/parse/dtor10.C [new file with mode: 0644]
gcc/testsuite/g++.dg/parse/dtor9.C [new file with mode: 0644]

index 93d4d23..47513ef 100644 (file)
@@ -1,5 +1,9 @@
 2006-08-03  Volker Reichelt  <reichelt@igpm.rwth-aachen.de>
 
+       PR c++/27508
+       * parser.c (cp_parser_unqualified_id): Check for invalid scopes
+       when parsing destructor names.
+
        PR c++/28274
        * decl.c (duplicate_decls): Call check_default_args here.
        (start_preparsed_function): Do not call check_default_args.
index c422401..aa29787 100644 (file)
@@ -3416,9 +3416,24 @@ cp_parser_unqualified_id (cp_parser* parser,
        object_scope = parser->object_scope;
        qualifying_scope = parser->qualifying_scope;
 
+       /* Check for invalid scopes.  */
+       if (scope == error_mark_node)
+         {
+           cp_parser_skip_to_end_of_statement (parser);
+           return error_mark_node;
+         }
+       if (scope && TREE_CODE (scope) == NAMESPACE_DECL)
+         {
+           if (!cp_parser_uncommitted_to_tentative_parse_p (parser))
+             error ("scope %qT before %<~%> is not a class-name", scope);
+           cp_parser_skip_to_end_of_statement (parser);
+           return error_mark_node;
+         }
+       gcc_assert (!scope || TYPE_P (scope));
+
        /* If the name is of the form "X::~X" it's OK.  */
        token = cp_lexer_peek_token (parser->lexer);
-       if (scope && TYPE_P (scope)
+       if (scope
            && token->type == CPP_NAME
            && (cp_lexer_peek_nth_token (parser->lexer, 2)->type
                == CPP_OPEN_PAREN)
@@ -3500,7 +3515,7 @@ cp_parser_unqualified_id (cp_parser* parser,
           destructor is the same as the name of the qualifying
           class.  That allows us to keep parsing after running
           into ill-formed destructor names.  */
-       if (type_decl == error_mark_node && scope && TYPE_P (scope))
+       if (type_decl == error_mark_node && scope)
          return build_nt (BIT_NOT_EXPR, scope);
        else if (type_decl == error_mark_node)
          return error_mark_node;
index 8f17cab..dfe0f98 100644 (file)
@@ -1,5 +1,10 @@
 2006-08-03  Volker Reichelt  <reichelt@igpm.rwth-aachen.de>
 
+       PR c++/27508
+       * g++.dg/parse/dtor9.C: New test.
+       * g++.dg/parse/dtor10.C: New test.
+       * g++.dg/other/error7.C: Adjust error-marker.
+
        PR c++/28274
        * g++.dg/other/default5.C: New test.
 
index eadb7b5..9845b41 100644 (file)
@@ -8,5 +8,5 @@ namespace N {}
 
 void foo(void)
 {
-  N::~A();    // { dg-error "not a member" }
+  N::~A();    // { dg-error "not a class-name" }
 }
diff --git a/gcc/testsuite/g++.dg/parse/dtor10.C b/gcc/testsuite/g++.dg/parse/dtor10.C
new file mode 100644 (file)
index 0000000..a6e9054
--- /dev/null
@@ -0,0 +1,9 @@
+// PR c++/27508
+// { dg-do compile }
+
+namespace N
+{
+    struct A { ~A(); };
+}
+
+N::~A () {}  // { dg-error "not a class-name" }
diff --git a/gcc/testsuite/g++.dg/parse/dtor9.C b/gcc/testsuite/g++.dg/parse/dtor9.C
new file mode 100644 (file)
index 0000000..64c82ce
--- /dev/null
@@ -0,0 +1,5 @@
+// PR c++/27508
+// { dg-do compile }
+
+struct A;
+using ::~A;  // { dg-error "not a class-name" }