When a class contains a non-empty anonymous union or struct, mark is

as non-empty. Fixes PR7021.

llvm-svn: 102913
This commit is contained in:
Douglas Gregor 2010-05-03 15:18:25 +00:00
parent d040e6b25a
commit 456ad1a817
2 changed files with 30 additions and 3 deletions

View File

@ -1773,8 +1773,11 @@ Sema::DeclPtrTy Sema::BuildAnonymousStructOrUnion(Scope *S, DeclSpec &DS,
TInfo,
/*BitWidth=*/0, /*Mutable=*/false);
Anon->setAccess(AS_public);
if (getLangOptions().CPlusPlus)
if (getLangOptions().CPlusPlus) {
FieldCollector->Add(cast<FieldDecl>(Anon));
if (!cast<CXXRecordDecl>(Record)->isEmpty())
cast<CXXRecordDecl>(OwningClass)->setEmpty(false);
}
} else {
DeclSpec::SCS SCSpec = DS.getStorageClassSpec();
assert(SCSpec != DeclSpec::SCS_typedef &&
@ -1802,7 +1805,7 @@ Sema::DeclPtrTy Sema::BuildAnonymousStructOrUnion(Scope *S, DeclSpec &DS,
// context. We'll be referencing this object when we refer to one of
// its members.
Owner->addDecl(Anon);
// Inject the members of the anonymous struct/union into the owning
// context and into the identifier resolver chain for name lookup
// purposes.

View File

@ -1,4 +1,4 @@
// RUN: %clang_cc1 -emit-llvm -o - %s
// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -emit-llvm -o - %s
struct A {
union {
@ -10,3 +10,27 @@ struct A {
};
A a;
namespace PR7021 {
struct X
{
union { long l; };
};
// CHECK: define void @_ZN6PR70211fENS_1XES0_
void f(X x, X z) {
X x1;
// CHECK: store i64 1, i64
x1.l = 1;
// CHECK: call void @llvm.memcpy.p0i8.p0i8.i64
X x2(x1);
X x3;
// CHECK: call void @llvm.memcpy.p0i8.p0i8.i64
x3 = x1;
// CHECK: ret void
}
}