Sema::CheckForFileScopedRedefinitions(): Make sure tentative decls of incomplete array types are completed (and diagnosed properly).



git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@54612 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp
index c776a5b..df4add2 100644
--- a/lib/Sema/SemaDecl.cpp
+++ b/lib/Sema/SemaDecl.cpp
@@ -391,6 +391,7 @@
 /// when dealing with C "tentative" external object definitions (C99 6.9.2).
 void Sema::CheckForFileScopedRedefinitions(Scope *S, VarDecl *VD) {
   bool VDIsTentative = isTentativeDefinition(VD);
+  bool VDIsIncompleteArray = VD->getType()->isIncompleteArrayType();
   
   for (IdentifierResolver::iterator
        I = IdResolver.begin(VD->getIdentifier(), 
@@ -399,6 +400,14 @@
     if (*I != VD && IdResolver.isDeclInScope(*I, VD->getDeclContext(), S)) {
       VarDecl *OldDecl = dyn_cast<VarDecl>(*I);
       
+      // Handle the following case:
+      //   int a[10];
+      //   int a[];   - the code below makes sure we set the correct type. 
+      //   int a[11]; - this is an error, size isn't 10.
+      if (OldDecl && VDIsTentative && VDIsIncompleteArray && 
+          OldDecl->getType()->isConstantArrayType())
+        VD->setType(OldDecl->getType());
+      
       // Check for "tentative" definitions. We can't accomplish this in 
       // MergeVarDecl since the initializer hasn't been attached.
       if (!OldDecl || isTentativeDefinition(OldDecl) || VDIsTentative)
diff --git a/test/Sema/tentative-decls.c b/test/Sema/tentative-decls.c
index 7a374e0..288757a 100644
--- a/test/Sema/tentative-decls.c
+++ b/test/Sema/tentative-decls.c
@@ -27,6 +27,10 @@
 int (*pToArray)[];
 int (*pToArray)[8];
 
+int redef[10];
+int redef[];  // expected-error{{previous definition is here}}
+int redef[11]; // expected-error{{redefinition of 'redef'}}
+
 void func() {
   extern int i1; // expected-error{{previous definition is here}}
   static int i1; // expected-error{{static declaration of 'i1' follows non-static declaration}}