]> granicus.if.org Git - clang/commitdiff
Diagnose misuse of '.*' and '->*' operators during parse
authorFariborz Jahanian <fjahanian@apple.com>
Fri, 23 Oct 2009 21:01:39 +0000 (21:01 +0000)
committerFariborz Jahanian <fjahanian@apple.com>
Fri, 23 Oct 2009 21:01:39 +0000 (21:01 +0000)
instead of crashing in code gen.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@84968 91177308-0d34-0410-b5e6-96231b3b80d8

include/clang/Basic/DiagnosticParseKinds.td
lib/Parse/ParseExpr.cpp
lib/Sema/SemaExprCXX.cpp
test/Parser/cxx-parse-member-pointer-op.cpp [new file with mode: 0644]

index 19b0ea3932a5e901462530ced82c56fd01f4140d..a7f3441e30160a8be1206410eb6efabb690dd9a1 100644 (file)
@@ -117,6 +117,8 @@ def err_expected_semi_after_static_assert : Error<
   "expected ';' after static_assert">;
 def err_expected_semi_for : Error<"expected ';' in 'for' statement specifier">;
 def err_expected_colon_after : Error<"expected ':' after %0">;
+def err_pointer_to_member_type : Error<
+  "invalid use of pointer to member type after %0">;
 def err_label_end_of_compound_statement : Error<
   "label at end of compound statement: expected statement">;
 def err_expected_string_literal : Error<"expected string literal">;
index 8be89a8916800d6673bc28f65959b6a0fbb6b753..7d056fdebb9165cb4bb59b0e93b1ddee1d76e292 100644 (file)
@@ -340,7 +340,18 @@ Parser::ParseRHSOfBinaryExpression(OwningExprResult LHS, unsigned MinPrec) {
       // Eat the colon.
       ColonLoc = ConsumeToken();
     }
-
+    
+    if ((OpToken.is(tok::periodstar) || OpToken.is(tok::arrowstar))
+         && Tok.is(tok::identifier)) {
+      CXXScopeSpec SS;
+      if (Actions.getTypeName(*Tok.getIdentifierInfo(),
+                                           Tok.getLocation(), CurScope, &SS)) {
+        const char *Opc = OpToken.is(tok::periodstar) ? "'.*'" : "'->*'";
+        Diag(OpToken, diag::err_pointer_to_member_type) << Opc;
+        return ExprError();
+      }
+        
+    }
     // Parse another leaf here for the RHS of the operator.
     // ParseCastExpression works here because all RHS expressions in C have it
     // as a prefix, at least. However, in C++, an assignment-expression could
index ee19ff6b84863f96b85603d1064183357a2b6459..6f26ea1eeef92554bde94cd6138b6b8f70a321d9 100644 (file)
@@ -212,7 +212,7 @@ Sema::ActOnCXXTypeConstructExpr(SourceRange TypeRange, TypeTy *TypeRep,
                           PDiag(diag::err_invalid_incomplete_type_use)
                             << FullRange))
     return ExprError();
-
+  
   if (RequireNonAbstractType(TyBeginLoc, Ty,
                              diag::err_allocation_of_abstract_type))
     return ExprError();
diff --git a/test/Parser/cxx-parse-member-pointer-op.cpp b/test/Parser/cxx-parse-member-pointer-op.cpp
new file mode 100644 (file)
index 0000000..cc2e8b1
--- /dev/null
@@ -0,0 +1,13 @@
+// RUN: clang-cc -fsyntax-only -pedantic -verify %s
+
+struct C {};
+
+typedef void (C::*pmfc)();
+
+void g(pmfc) {
+  C *c;
+  c->*pmfc(); // expected-error {{invalid use of pointer to member type after '->*'}}
+  C c1;
+  c1.*pmfc(); // expected-error {{invalid use of pointer to member type after '.*'}}
+}
+