aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAdrian Prantl <aprantl@apple.com>2013-02-27 01:31:55 +0000
committerAdrian Prantl <aprantl@apple.com>2013-02-27 01:31:55 +0000
commit10b4df7ff21076c21ca764f8ca38ccaff7888f25 (patch)
tree24ab636cfafd0221097c00478c22607dc3e36a22
parentb7a3f74bbb02788ad1b597fe3897db2d8a4fed43 (diff)
Temporarily revert r176116 for compile-time performance regression.
This reverts commit ea95e4587fd13606fbf63b10a07a7d02026aa39c. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@176151 91177308-0d34-0410-b5e6-96231b3b80d8
-rw-r--r--include/clang/AST/DeclObjC.h7
-rw-r--r--lib/AST/DeclObjC.cpp53
-rw-r--r--lib/CodeGen/CGDebugInfo.cpp30
-rw-r--r--lib/CodeGen/CGDebugInfo.h4
-rw-r--r--test/CodeGenObjC/debug-info-ivars-2.m28
-rw-r--r--test/CodeGenObjC/debug-info-ivars-3.m31
-rw-r--r--test/CodeGenObjC/debug-info-ivars-private.m36
7 files changed, 23 insertions, 166 deletions
diff --git a/include/clang/AST/DeclObjC.h b/include/clang/AST/DeclObjC.h
index 43f255fd04..1c5588f926 100644
--- a/include/clang/AST/DeclObjC.h
+++ b/include/clang/AST/DeclObjC.h
@@ -651,10 +651,6 @@ class ObjCInterfaceDecl : public ObjCContainerDecl
/// completed by the external AST source when required.
mutable bool ExternallyCompleted : 1;
- /// \brief Indicates that the ivar cache does not yet include ivars
- /// declared in the implementation.
- mutable bool IvarListMissingImplementation : 1;
-
/// \brief The location of the superclass, if any.
SourceLocation SuperClassLoc;
@@ -664,8 +660,7 @@ class ObjCInterfaceDecl : public ObjCContainerDecl
SourceLocation EndLoc;
DefinitionData() : Definition(), SuperClass(), CategoryList(), IvarList(),
- ExternallyCompleted(),
- IvarListMissingImplementation(true) { }
+ ExternallyCompleted() { }
};
ObjCInterfaceDecl(DeclContext *DC, SourceLocation atLoc, IdentifierInfo *Id,
diff --git a/lib/AST/DeclObjC.cpp b/lib/AST/DeclObjC.cpp
index d1bf9a9e45..d539e0098f 100644
--- a/lib/AST/DeclObjC.cpp
+++ b/lib/AST/DeclObjC.cpp
@@ -1093,51 +1093,38 @@ namespace {
/// all_declared_ivar_begin - return first ivar declared in this class,
/// its extensions and its implementation. Lazily build the list on first
/// access.
-///
-/// Caveat: The list returned by this method reflects the current
-/// state of the parser. The cache will be updated for every ivar
-/// added by an extension or the implementation when they are
-/// encountered.
-/// See also ObjCIvarDecl::Create().
ObjCIvarDecl *ObjCInterfaceDecl::all_declared_ivar_begin() {
// FIXME: Should make sure no callers ever do this.
if (!hasDefinition())
return 0;
+ if (data().IvarList)
+ return data().IvarList;
+
ObjCIvarDecl *curIvar = 0;
- if (!data().IvarList) {
- if (!ivar_empty()) {
- ObjCInterfaceDecl::ivar_iterator I = ivar_begin(), E = ivar_end();
- data().IvarList = *I; ++I;
- for (curIvar = data().IvarList; I != E; curIvar = *I, ++I)
- curIvar->setNextIvar(*I);
- }
+ if (!ivar_empty()) {
+ ObjCInterfaceDecl::ivar_iterator I = ivar_begin(), E = ivar_end();
+ data().IvarList = *I; ++I;
+ for (curIvar = data().IvarList; I != E; curIvar = *I, ++I)
+ curIvar->setNextIvar(*I);
+ }
- for (ObjCInterfaceDecl::known_extensions_iterator
- Ext = known_extensions_begin(),
- ExtEnd = known_extensions_end();
- Ext != ExtEnd; ++Ext) {
- if (!Ext->ivar_empty()) {
- ObjCCategoryDecl::ivar_iterator
- I = Ext->ivar_begin(),
- E = Ext->ivar_end();
- if (!data().IvarList) {
- data().IvarList = *I; ++I;
- curIvar = data().IvarList;
- }
- for ( ;I != E; curIvar = *I, ++I)
- curIvar->setNextIvar(*I);
+ for (ObjCInterfaceDecl::known_extensions_iterator
+ Ext = known_extensions_begin(),
+ ExtEnd = known_extensions_end();
+ Ext != ExtEnd; ++Ext) {
+ if (!Ext->ivar_empty()) {
+ ObjCCategoryDecl::ivar_iterator I = Ext->ivar_begin(),E = Ext->ivar_end();
+ if (!data().IvarList) {
+ data().IvarList = *I; ++I;
+ curIvar = data().IvarList;
}
+ for ( ;I != E; curIvar = *I, ++I)
+ curIvar->setNextIvar(*I);
}
- data().IvarListMissingImplementation = true;
}
-
- // cached and complete!
- if (!data().IvarListMissingImplementation)
- return data().IvarList;
if (ObjCImplementationDecl *ImplDecl = getImplementation()) {
- data().IvarListMissingImplementation = false;
if (!ImplDecl->ivar_empty()) {
SmallVector<SynthesizeIvarChunk, 16> layout;
for (ObjCImplementationDecl::ivar_iterator I = ImplDecl->ivar_begin(),
diff --git a/lib/CodeGen/CGDebugInfo.cpp b/lib/CodeGen/CGDebugInfo.cpp
index 2d0d2b8377..970ba50b71 100644
--- a/lib/CodeGen/CGDebugInfo.cpp
+++ b/lib/CodeGen/CGDebugInfo.cpp
@@ -1343,7 +1343,7 @@ llvm::DIType CGDebugInfo::CreateType(const RecordType *Ty) {
LexicalBlockStack.push_back(FwdDeclNode);
RegionMap[Ty->getDecl()] = llvm::WeakVH(FwdDecl);
- // Add this to the completed-type cache while we're completing it recursively.
+ // Add this to the completed types cache since we're completing it.
CompletedTypeCache[QualType(Ty, 0).getAsOpaquePtr()] = FwdDecl;
// Convert all the elements.
@@ -1436,8 +1436,7 @@ llvm::DIType CGDebugInfo::CreateType(const ObjCInterfaceType *Ty,
// Otherwise, insert it into the CompletedTypeCache so that recursive uses
// will find it and we're emitting the complete type.
- QualType QualTy = QualType(Ty, 0);
- CompletedTypeCache[QualTy.getAsOpaquePtr()] = RealDecl;
+ CompletedTypeCache[QualType(Ty, 0).getAsOpaquePtr()] = RealDecl;
// Push the struct on region stack.
llvm::TrackingVH<llvm::MDNode> FwdDeclNode(RealDecl);
@@ -1562,12 +1561,6 @@ llvm::DIType CGDebugInfo::CreateType(const ObjCInterfaceType *Ty,
llvm::DIArray Elements = DBuilder.getOrCreateArray(EltTys);
FwdDeclNode->replaceOperandWith(10, Elements);
-
- // If the implementation is not yet set, we do not want to mark it
- // as complete. An implementation may declare additional
- // private ivars that we would miss otherwise.
- if (ID->getImplementation() == 0)
- CompletedTypeCache.erase(QualTy.getAsOpaquePtr());
LexicalBlockStack.pop_back();
return llvm::DIType(FwdDeclNode);
@@ -1831,10 +1824,6 @@ llvm::DIType CGDebugInfo::getOrCreateType(QualType Ty, llvm::DIFile Unit) {
ReplaceMap.push_back(std::make_pair(Ty.getAsOpaquePtr(),
static_cast<llvm::Value*>(TC)));
- // Do not cache the type if it may be incomplete.
- if (maybeIncompleteInterface(Ty))
- return Res;
-
// And update the type cache.
TypeCache[Ty.getAsOpaquePtr()] = Res;
@@ -1844,21 +1833,6 @@ llvm::DIType CGDebugInfo::getOrCreateType(QualType Ty, llvm::DIFile Unit) {
return Res;
}
-/// clang::ParseAST handles each TopLevelDecl immediately after it was parsed.
-/// A subsequent implementation may add more ivars to an interface, which is
-/// why we cannot cache it yet.
-bool CGDebugInfo::maybeIncompleteInterface(QualType Ty) {
- switch (Ty->getTypeClass()) {
- case Type::ObjCObjectPointer:
- return maybeIncompleteInterface(cast<ObjCObjectPointerType>(Ty)->getPointeeType());
- case Type::ObjCInterface:
- if (ObjCInterfaceDecl *Decl = cast<ObjCInterfaceType>(Ty)->getDecl())
- return (Decl->getImplementation() == 0);
- default:
- return false;
- }
-}
-
/// CreateTypeNode - Create a new debug type node.
llvm::DIType CGDebugInfo::CreateTypeNode(QualType Ty, llvm::DIFile Unit) {
// Handle qualifiers, which recursively handles what they refer to.
diff --git a/lib/CodeGen/CGDebugInfo.h b/lib/CodeGen/CGDebugInfo.h
index 81b5c71327..fbbee0b3d2 100644
--- a/lib/CodeGen/CGDebugInfo.h
+++ b/lib/CodeGen/CGDebugInfo.h
@@ -299,10 +299,6 @@ private:
/// CreateTypeNode - Create type metadata for a source language type.
llvm::DIType CreateTypeNode(QualType Ty, llvm::DIFile F);
- /// maybeIncompleteInterface - Determine if Ty may contain an
- /// interface without an implementation
- bool maybeIncompleteInterface(QualType Ty);
-
/// CreateLimitedTypeNode - Create type metadata for a source language
/// type, but only partial types for records.
llvm::DIType CreateLimitedTypeNode(QualType Ty, llvm::DIFile F);
diff --git a/test/CodeGenObjC/debug-info-ivars-2.m b/test/CodeGenObjC/debug-info-ivars-2.m
deleted file mode 100644
index ac47ad1c08..0000000000
--- a/test/CodeGenObjC/debug-info-ivars-2.m
+++ /dev/null
@@ -1,28 +0,0 @@
-// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -emit-llvm -g %s -o - | FileCheck %s
-
-// Debug symbols for private IVars
-
-@interface I
-{
- @public int a;
-}
-@end
-
-void foo(I* pi) {
- // poking into pi for primary class ivars.
- int _a = pi->a;
-}
-
-@interface I()
-{
- @public int b;
-}
-@end
-
-void gorf (I* pg) {
- // poking into pg for ivars for class extension
- int _b = pg->b;
-}
-
-// CHECK: metadata !{i32 {{[0-9]*}}, metadata !{{[0-9]*}}, metadata !"a", metadata !{{[0-9]*}}, i32 7, i64 32, i64 32, i64 0, i32 0, metadata !{{[0-9]*}}, null} ; [ DW_TAG_member ] [a] [line 7, size 32, align 32, offset 0] [from int]
-// CHECK: metadata !{i32 {{[0-9]*}}, metadata !{{[0-9]*}}, metadata !"b", metadata !{{[0-9]*}}, i32 18, i64 32, i64 32, i64 0, i32 0, metadata !{{[0-9]*}}, null} ; [ DW_TAG_member ] [b] [line 18, size 32, align 32, offset 0] [from int]
diff --git a/test/CodeGenObjC/debug-info-ivars-3.m b/test/CodeGenObjC/debug-info-ivars-3.m
deleted file mode 100644
index 9fc3f59bdf..0000000000
--- a/test/CodeGenObjC/debug-info-ivars-3.m
+++ /dev/null
@@ -1,31 +0,0 @@
-// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -emit-llvm -g %s -o - | FileCheck %s
-
-// Debug symbols for private IVars
-
-@interface I
-{
- @public int a;
-}
-@end
-
-void foo(I* pi) {
- int _a = pi->a;
-}
-
-// another layer of indirection
-struct S
-{
- I* i;
-};
-
-@interface I()
-{
- @public int b;
-}
-@end
-
-void gorf (struct S* s) {
- int _b = s->i->b;
-}
-
-// CHECK: metadata !{i32 {{[0-9]*}}, metadata !{{[0-9]*}}, metadata !"b", metadata !{{[0-9]*}}, i32 23, i64 32, i64 32, i64 0, i32 0, metadata !{{[0-9]*}}, null} ; [ DW_TAG_member ] [b] [line 23, size 32, align 32, offset 0] [from int]
diff --git a/test/CodeGenObjC/debug-info-ivars-private.m b/test/CodeGenObjC/debug-info-ivars-private.m
deleted file mode 100644
index eb109f1b89..0000000000
--- a/test/CodeGenObjC/debug-info-ivars-private.m
+++ /dev/null
@@ -1,36 +0,0 @@
-// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -emit-llvm -g %s -o - | FileCheck %s
-
-// Debug symbols for private IVars. This test ensures that we are generating
-// DI for ivars added ny the implementation.
-__attribute((objc_root_class)) @interface NSObject {
- id isa;
-}
-@end
-
-@protocol Protocol
-@end
-
-@interface Delegate : NSObject<Protocol> {
- @protected int foo;
-}
-@end
-
-@interface Delegate(NSObject)
- - (void)f;
-@end
-
-@implementation Delegate(NSObject)
-- (void)f { return; }
-@end
-
-@implementation Delegate {
- int bar;
-}
-
-- (void)g:(NSObject*) anObject {
- bar = foo;
-}
-@end
-
-// CHECK: metadata !{i32 {{[0-9]*}}, metadata !{{[0-9]*}}, metadata !"foo", metadata !{{[0-9]*}}, i32 14, i64 32, i64 32, i64 0, i32 2, metadata !{{[0-9]*}}, null} ; [ DW_TAG_member ] [foo] [line 14, size 32, align 32, offset 0] [protected] [from int]
-// CHECK: metadata !{i32 {{[0-9]*}}, metadata !{{[0-9]*}}, metadata !"bar", metadata !{{[0-9]*}}, i32 27, i64 32, i64 32, i64 0, i32 1, metadata !{{[0-9]*}}, null} ; [ DW_TAG_member ] [bar] [line 27, size 32, align 32, offset 0] [private] [from int]