Update Parser::ParseTypeName to return a TypeResult, which also tells
us whether there was an error in trying to parse a type-name (type-id
in C++). This allows propagation of errors further in the compiler,
suppressing more bogus error messages.


git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@64922 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Parse/ParseDecl.cpp b/lib/Parse/ParseDecl.cpp
index 9974aea..6e68b20 100644
--- a/lib/Parse/ParseDecl.cpp
+++ b/lib/Parse/ParseDecl.cpp
@@ -28,7 +28,7 @@
 ///         specifier-qualifier-list abstract-declarator[opt]
 ///
 /// Called type-id in C++.
-Parser::TypeTy *Parser::ParseTypeName() {
+Action::TypeResult Parser::ParseTypeName() {
   // Parse the common declaration-specifiers piece.
   DeclSpec DS;
   ParseSpecifierQualifierList(DS);
@@ -37,7 +37,10 @@
   Declarator DeclaratorInfo(DS, Declarator::TypeNameContext);
   ParseDeclarator(DeclaratorInfo);
   
-  return Actions.ActOnTypeName(CurScope, DeclaratorInfo).get();
+  if (DeclaratorInfo.getInvalidType())
+    return true;
+
+  return Actions.ActOnTypeName(CurScope, DeclaratorInfo);
 }
 
 /// ParseAttributes - Parse a non-empty attributes list.
@@ -2383,8 +2386,10 @@
     }
 
     OwningExprResult Result(ParseCastExpression(true/*isUnaryExpression*/));
-    if (Result.isInvalid())
+    if (Result.isInvalid()) {
+      DS.SetTypeSpecError();
       return;
+    }
 
     const char *PrevSpec = 0;
     // Check for duplicate type specifiers.
@@ -2400,24 +2405,32 @@
   SourceLocation LParenLoc = ConsumeParen(), RParenLoc;
   
   if (isTypeIdInParens()) {
-    TypeTy *Ty = ParseTypeName();
+    Action::TypeResult Ty = ParseTypeName();
 
-    assert(Ty && "Parser::ParseTypeofSpecifier(): missing type");
+    assert((Ty.isInvalid() || Ty.get()) && 
+           "Parser::ParseTypeofSpecifier(): missing type");
 
     if (Tok.isNot(tok::r_paren)) {
       MatchRHSPunctuation(tok::r_paren, LParenLoc);
       return;
     }
     RParenLoc = ConsumeParen();
-    const char *PrevSpec = 0;
-    // Check for duplicate type specifiers (e.g. "int typeof(int)").
-    if (DS.SetTypeSpecType(DeclSpec::TST_typeofType, StartLoc, PrevSpec, Ty))
-      Diag(StartLoc, diag::err_invalid_decl_spec_combination) << PrevSpec;
+
+    if (Ty.isInvalid())
+      DS.SetTypeSpecError();
+    else {
+      const char *PrevSpec = 0;
+      // Check for duplicate type specifiers (e.g. "int typeof(int)").
+      if (DS.SetTypeSpecType(DeclSpec::TST_typeofType, StartLoc, PrevSpec, 
+                             Ty.get()))
+        Diag(StartLoc, diag::err_invalid_decl_spec_combination) << PrevSpec;
+    }
   } else { // we have an expression.
     OwningExprResult Result(ParseExpression());
 
     if (Result.isInvalid() || Tok.isNot(tok::r_paren)) {
       MatchRHSPunctuation(tok::r_paren, LParenLoc);
+      DS.SetTypeSpecError();
       return;
     }
     RParenLoc = ConsumeParen();