aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEli Friedman <eli.friedman@gmail.com>2010-08-10 03:13:15 +0000
committerEli Friedman <eli.friedman@gmail.com>2010-08-10 03:13:15 +0000
commitbf87f2c1c6e2d8cb50902a6d79e8b170c19570d2 (patch)
tree6ff621933fea30d81eb9f6e74910bff4f72de52c
parent4a5496bdd50f6cec5f8eb252665503e5431708d9 (diff)
Fix redefinition of typedefs of fixable variably-modified array types; should
fix an issue compiling <windows.h>. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@110651 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--lib/Sema/SemaDecl.cpp18
-rw-r--r--test/Sema/typedef-variable-type.c7
2 files changed, 16 insertions, 9 deletions
diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp
index e6c5170357..d94b8dd304 100644
--- a/lib/Sema/SemaDecl.cpp
+++ b/lib/Sema/SemaDecl.cpp
@@ -2332,16 +2332,10 @@ Sema::ActOnTypedefDeclarator(Scope* S, Declarator& D, DeclContext* DC,
// Handle attributes prior to checking for duplicates in MergeVarDecl
ProcessDeclAttributes(S, NewTD, D);
- // Merge the decl with the existing one if appropriate. If the decl is
- // in an outer scope, it isn't the same thing.
- FilterLookupForScope(*this, Previous, DC, S, /*ConsiderLinkage*/ false);
- if (!Previous.empty()) {
- Redeclaration = true;
- MergeTypeDefDecl(NewTD, Previous);
- }
-
// C99 6.7.7p2: If a typedef name specifies a variably modified type
// then it shall have block scope.
+ // Note that variably modified types must be fixed before merging the decl so
+ // that redeclarations will match.
QualType T = NewTD->getUnderlyingType();
if (T->isVariablyModifiedType()) {
setFunctionHasBranchProtectedScope();
@@ -2365,6 +2359,14 @@ Sema::ActOnTypedefDeclarator(Scope* S, Declarator& D, DeclContext* DC,
}
}
+ // Merge the decl with the existing one if appropriate. If the decl is
+ // in an outer scope, it isn't the same thing.
+ FilterLookupForScope(*this, Previous, DC, S, /*ConsiderLinkage*/ false);
+ if (!Previous.empty()) {
+ Redeclaration = true;
+ MergeTypeDefDecl(NewTD, Previous);
+ }
+
// If this is the C FILE type, notify the AST context.
if (IdentifierInfo *II = NewTD->getIdentifier())
if (!NewTD->isInvalidDecl() &&
diff --git a/test/Sema/typedef-variable-type.c b/test/Sema/typedef-variable-type.c
index f29896850b..b805b1e057 100644
--- a/test/Sema/typedef-variable-type.c
+++ b/test/Sema/typedef-variable-type.c
@@ -1,3 +1,8 @@
-// RUN: %clang_cc1 %s -verify -fsyntax-only -pedantic
+// RUN: %clang_cc1 %s -verify -fsyntax-only -pedantic -Wno-typedef-redefinition
+// Make sure we accept a single typedef
+typedef int (*a)[!.0]; // expected-warning{{size of static array must be an integer constant expression}}
+
+// And make sure we accept identical redefinitions in system headers
+// (The test uses -Wno-typedef-redefinition to simulate this.)
typedef int (*a)[!.0]; // expected-warning{{size of static array must be an integer constant expression}}