]> granicus.if.org Git - clang/commitdiff
Improve error recovery in C++: when we hit 'implicit int' cases in C++,
authorChris Lattner <sabre@nondot.org>
Fri, 26 Jun 2009 04:45:06 +0000 (04:45 +0000)
committerChris Lattner <sabre@nondot.org>
Fri, 26 Jun 2009 04:45:06 +0000 (04:45 +0000)
these are usually because the parser was thoroughly confused.  In addition
to typing the value being declared as an int and hoping for the best, we
mark the value as invalid so we don't get chains of errors when it is
used downstream.  In C, implicit int actually is valid, so typing the thing
as int is good and marking it invalid is bad. :)

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

lib/Sema/SemaInit.cpp
lib/Sema/SemaType.cpp
test/SemaCXX/nested-name-spec.cpp

index 45085962d488a6e588d28d6cd20ebfb2c0f70da6..6b812e1968de2e0af5a2c1ac7b629f8f7b39e9c3 100644 (file)
@@ -200,10 +200,9 @@ bool Sema::CheckInitializerTypes(Expr *&Init, QualType &DeclType,
       
       if (InitEntity)
         return Diag(InitLoc, diag::err_cannot_initialize_decl)
-        << InitEntity << (int)(Init->isLvalue(Context) == Expr::LV_Valid)
-        << Init->getType() << Init->getSourceRange();
-      else
-        return Diag(InitLoc, diag::err_cannot_initialize_decl_noname)
+          << InitEntity << (int)(Init->isLvalue(Context) == Expr::LV_Valid)
+          << Init->getType() << Init->getSourceRange();
+      return Diag(InitLoc, diag::err_cannot_initialize_decl_noname)
         << DeclType << (int)(Init->isLvalue(Context) == Expr::LV_Valid)
         << Init->getType() << Init->getSourceRange();
     }
@@ -211,7 +210,7 @@ bool Sema::CheckInitializerTypes(Expr *&Init, QualType &DeclType,
     // C99 6.7.8p16.
     if (DeclType->isArrayType())
       return Diag(Init->getLocStart(), diag::err_array_init_list_required)
-      << Init->getSourceRange();
+        << Init->getSourceRange();
     
     return CheckSingleInitializer(Init, DeclType, DirectInit, *this);
   } 
index 12077b0671356c619eef848c4f8b8a2c00ae74d0..8a0ad089b68f62d65a5c23b3d62f324248d21d43 100644 (file)
@@ -121,16 +121,18 @@ QualType Sema::ConvertDeclSpecToType(const DeclSpec &DS,
       if (DeclLoc.isInvalid())
         DeclLoc = DS.getSourceRange().getBegin();
 
-      if (getLangOptions().CPlusPlus && !getLangOptions().Microsoft)
+      if (getLangOptions().CPlusPlus && !getLangOptions().Microsoft) {
         Diag(DeclLoc, diag::err_missing_type_specifier)
           << DS.getSourceRange();
-      else
+        
+        // When this occurs in C++ code, often something is very broken with the
+        // value being declared, poison it as invalid so we don't get chains of
+        // errors.
+        isInvalid = true;
+      } else {
         Diag(DeclLoc, diag::ext_missing_type_specifier)
           << DS.getSourceRange();
-
-      // FIXME: If we could guarantee that the result would be well-formed, it
-      // would be useful to have a code insertion hint here. However, after
-      // emitting this warning/error, we often emit other errors.
+      }
     }
       
     // FALL THROUGH.  
index c3e4eb18e2223abef8a23ae55938d94bc28eac46..8fff8a2b2cbc443322386143ed6a1009cd380f3d 100644 (file)
@@ -189,8 +189,7 @@ class foo {
 foo<somens:a> a2;  // expected-error {{unexpected namespace name 'somens': expected expression}} \
 expected-error {{C++ requires a type specifier for all declarations}}
 
-// FIXME: This is bogus, there is no int here!
-somens::a a3 = a2; // expected-error {{cannot initialize 'a3' with an lvalue of type 'int'}}
+somens::a a3 = a2;