diff --git a/clang/lib/Sema/SemaOverload.cpp b/clang/lib/Sema/SemaOverload.cpp --- a/clang/lib/Sema/SemaOverload.cpp +++ b/clang/lib/Sema/SemaOverload.cpp @@ -14328,8 +14328,12 @@ // Convert the rest of the arguments if (ConvertArgumentsForCall(TheCall, MemExpr, Method, Proto, Args, - RParenLoc)) - return ExprError(); + RParenLoc)) { + std::vector SubExprs = {MemExprE}; + llvm::for_each(Args, [&SubExprs](Expr *E) { SubExprs.push_back(E); }); + return CreateRecoveryExpr(MemExprE->getBeginLoc(), RParenLoc, SubExprs, + ResultType); + } DiagnoseSentinelCalls(Method, LParenLoc, Args); diff --git a/clang/test/AST/ast-dump-recovery.cpp b/clang/test/AST/ast-dump-recovery.cpp --- a/clang/test/AST/ast-dump-recovery.cpp +++ b/clang/test/AST/ast-dump-recovery.cpp @@ -121,6 +121,20 @@ foo->func(x); } +// CHECK: FunctionDecl {{.*}} test2 +// CHECK-NEXT: |-ParmVarDecl {{.*}} f +// CHECK-NEXT: `-CompoundStmt +// CHECK-NEXT: `-RecoveryExpr {{.*}} 'double' +// CHECK-NEXT: |-MemberExpr {{.*}} '' +// CHECK-NEXT: | `-DeclRefExpr {{.*}} +// CHECK-NEXT: `-IntegerLiteral {{.*}} 'int' 1 +struct Foo2 { + double func(); +}; +void test2(Foo2 f) { + f.func(1); +} + // CHECK: |-AlignedAttr {{.*}} alignas // CHECK-NEXT:| `-RecoveryExpr {{.*}} contains-errors // CHECK-NEXT:| `-UnresolvedLookupExpr {{.*}} 'invalid' diff --git a/clang/test/SemaCXX/ms-property-error.cpp b/clang/test/SemaCXX/ms-property-error.cpp --- a/clang/test/SemaCXX/ms-property-error.cpp +++ b/clang/test/SemaCXX/ms-property-error.cpp @@ -13,7 +13,7 @@ public: __declspec(property(get=GetX,put=PutX)) T x[]; T GetX(T i, T j) { return i+j; } // expected-note 3 {{'GetX' declared here}} - T PutX(T i, T j, T k) { return j = i = k; } // expected-note 2 {{'PutX' declared here}} + T PutX(T i, T j, T k) { return j = i = k; } // expected-note 3 {{'PutX' declared here}} ~St() { x[1] = 0; // expected-error {{too few arguments to function call, expected 3, have 2}} x[2][3] = 4; @@ -33,5 +33,6 @@ float j1 = (p2->x); // expected-error {{too few arguments to function call, expected 2, have 0}} ((p2->x)[23])[1][2] = *argv; // expected-error {{too many arguments to function call, expected 3, have 4}} argv = p2->x[11][22] = argc; // expected-error {{assigning to 'char **' from incompatible type 'float'}} - return ++(((p2->x)[23])); // expected-error {{too few arguments to function call, expected 2, have 1}} + return ++(((p2->x)[23])); // expected-error {{too few arguments to function call, expected 2, have 1}} \ + expected-error {{too few arguments to function call, expected 3, have 2}} }