зеркало из https://github.com/microsoft/clang-1.git
PR1893: Fix up the type of tentative definitions of incomplete array
types so that they end up the correct size. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@51787 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Родитель
a04a1538ee
Коммит
cd5f4aaf0c
|
@ -411,7 +411,18 @@ void CodeGenModule::EmitGlobalVarInit(const VarDecl *D) {
|
|||
llvm::PointerType::get(VarTy, ASTTy.getAddressSpace());
|
||||
|
||||
if (D->getInit() == 0) {
|
||||
Init = llvm::Constant::getNullValue(VarTy);
|
||||
// This is a tentative definition; tentative definitions are
|
||||
// implicitly initialized with { 0 }
|
||||
const llvm::Type* InitTy;
|
||||
if (ASTTy->isIncompleteArrayType()) {
|
||||
// An incomplete array is normally [ TYPE x 0 ], but we need
|
||||
// to fix it to [ TYPE x 1 ].
|
||||
const llvm::ArrayType* ATy = cast<llvm::ArrayType>(VarTy);
|
||||
InitTy = llvm::ArrayType::get(ATy->getElementType(), 1);
|
||||
} else {
|
||||
InitTy = VarTy;
|
||||
}
|
||||
Init = llvm::Constant::getNullValue(InitTy);
|
||||
} else {
|
||||
Init = EmitGlobalInit(D->getInit());
|
||||
}
|
||||
|
@ -435,6 +446,10 @@ void CodeGenModule::EmitGlobalVarInit(const VarDecl *D) {
|
|||
// and then a definition of a different type (e.g. "int x[10];"). This also
|
||||
// happens when an initializer has a different type from the type of the
|
||||
// global (this happens with unions).
|
||||
//
|
||||
// FIXME: This also ends up happening if there's a definition followed by
|
||||
// a tentative definition! (Although Sema rejects that construct
|
||||
// at the moment.)
|
||||
|
||||
// Save the old global
|
||||
llvm::GlobalVariable *OldGV = GV;
|
||||
|
@ -470,7 +485,12 @@ void CodeGenModule::EmitGlobalVarInit(const VarDecl *D) {
|
|||
|
||||
GV->setInitializer(Init);
|
||||
|
||||
unsigned Align = Context.getTypeAlign(D->getType());
|
||||
// FIXME: This is silly; getTypeAlign should just work for incomplete arrays
|
||||
unsigned Align;
|
||||
if (const IncompleteArrayType* IAT = D->getType()->getAsIncompleteArrayType())
|
||||
Align = Context.getTypeAlign(IAT->getElementType());
|
||||
else
|
||||
Align = Context.getTypeAlign(D->getType());
|
||||
if (const AlignedAttr* AA = D->getAttr<AlignedAttr>()) {
|
||||
Align = std::max(Align, AA->getAlignment());
|
||||
}
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
// RUN: clang -emit-llvm < %s -triple=i686-apple-darwin9 | grep "global \[1 x i32\]"
|
||||
|
||||
int r[];
|
||||
int (*a)[] = &r;
|
Загрузка…
Ссылка в новой задаче