]> granicus.if.org Git - clang/commitdiff
When dealing with an anonymous enumeration declared in function
authorDouglas Gregor <dgregor@apple.com>
Thu, 16 Sep 2010 23:58:57 +0000 (23:58 +0000)
committerDouglas Gregor <dgregor@apple.com>
Thu, 16 Sep 2010 23:58:57 +0000 (23:58 +0000)
prototype scope, temporarily set the context of the enumeration
declaration to the translation unit. We do the same thing for
parameters, until we have an actual function declaration on which to
hang them. Fixes <rdar://problem/8435682>.

There is more work to do in this area, since we have existing bugs
with tags being declared/defined in function parameter lists. This fix
is correct, and we'll end up extending it when we deal with those
existing bugs.

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

lib/Sema/SemaDecl.cpp
test/CXX/dcl.decl/dcl.meaning/dcl.fct/p8.cpp [new file with mode: 0644]

index e314c1acfe4954f37ddb9e424d7eba66fb293d44..51b5ae91d6aed75ad5f3aa2cff1cb2203dbc683b 100644 (file)
@@ -5326,11 +5326,11 @@ bool Sema::isAcceptableTagRedeclaration(const TagDecl *Previous,
 /// TagSpec indicates what kind of tag this is. TUK indicates whether this is a
 /// reference/declaration/definition of a tag.
 Decl *Sema::ActOnTag(Scope *S, unsigned TagSpec, TagUseKind TUK,
-                               SourceLocation KWLoc, CXXScopeSpec &SS,
-                               IdentifierInfo *Name, SourceLocation NameLoc,
-                               AttributeList *Attr, AccessSpecifier AS,
-                               MultiTemplateParamsArg TemplateParameterLists,
-                               bool &OwnedDecl, bool &IsDependent) {
+                     SourceLocation KWLoc, CXXScopeSpec &SS,
+                     IdentifierInfo *Name, SourceLocation NameLoc,
+                     AttributeList *Attr, AccessSpecifier AS,
+                     MultiTemplateParamsArg TemplateParameterLists,
+                     bool &OwnedDecl, bool &IsDependent) {
   // If this is not a definition, it must have a name.
   assert((Name != 0 || TUK == TUK_Definition) &&
          "Nameless record must be a definition!");
@@ -5459,6 +5459,10 @@ Decl *Sema::ActOnTag(Scope *S, unsigned TagSpec, TagUseKind TUK,
       while (isa<RecordDecl>(SearchDC) || isa<EnumDecl>(SearchDC))
         SearchDC = SearchDC->getParent();
     }
+  } else if (S->isFunctionPrototypeScope()) {
+    // If this is an enum declaration in function prototype scope, set its
+    // initial context to the translation unit.
+    SearchDC = Context.getTranslationUnitDecl();
   }
 
   if (Previous.isSingleResult() &&
diff --git a/test/CXX/dcl.decl/dcl.meaning/dcl.fct/p8.cpp b/test/CXX/dcl.decl/dcl.meaning/dcl.fct/p8.cpp
new file mode 100644 (file)
index 0000000..34a8c85
--- /dev/null
@@ -0,0 +1,10 @@
+// RUN: %clang_cc1 -fsyntax-only -verify %s
+
+struct A { };
+A::A (enum { e1 }) {} // expected-error{{can not be defined in a parameter}} \
+// expected-error{{out-of-line definition}}
+void A::f(enum { e2 }) {} // expected-error{{can not be defined in a parameter}} \
+// expected-error{{out-of-line definition}}
+
+enum { e3 } A::g() { } // expected-error{{can not be defined in the result type}} \
+// expected-error{{out-of-line definition}}