diff options
author | Fariborz Jahanian <fjahanian@apple.com> | 2010-08-20 21:21:08 +0000 |
---|---|---|
committer | Fariborz Jahanian <fjahanian@apple.com> | 2010-08-20 21:21:08 +0000 |
commit | 2c18bb7c9fca66c30b6eabbdcbc6399d24a54fa9 (patch) | |
tree | 6ffe7fcf0b582777655da4fddf91842e14a83ba4 /lib/AST/DeclObjC.cpp | |
parent | d9ca4ab3ed3637e97a19d716aa9fbd54c6a5f698 (diff) |
objective-c ivar refactoring patch. Iterations
over ivars for a varienty of puposes is now
consolidated into two small routines; DeepCollectObjCIvars
and ShallowCollectObjCIvars.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@111679 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/AST/DeclObjC.cpp')
-rw-r--r-- | lib/AST/DeclObjC.cpp | 56 |
1 files changed, 55 insertions, 1 deletions
diff --git a/lib/AST/DeclObjC.cpp b/lib/AST/DeclObjC.cpp index 32f9433d9a..4167841838 100644 --- a/lib/AST/DeclObjC.cpp +++ b/lib/AST/DeclObjC.cpp @@ -442,7 +442,8 @@ ObjCInterfaceDecl(DeclContext *DC, SourceLocation atLoc, IdentifierInfo *Id, SourceLocation CLoc, bool FD, bool isInternal) : ObjCContainerDecl(ObjCInterface, DC, atLoc, Id), TypeForDecl(0), SuperClass(0), - CategoryList(0), ForwardDecl(FD), InternalInterface(isInternal), + CategoryList(0), IvarList(0), + ForwardDecl(FD), InternalInterface(isInternal), ClassLoc(CLoc) { } @@ -455,6 +456,49 @@ void ObjCInterfaceDecl::setImplementation(ObjCImplementationDecl *ImplD) { getASTContext().setObjCImplementation(this, ImplD); } +/// all_declared_ivar_begin - return first ivar declared in this class, +/// its extensions and its implementation. Lazily build the list on first +/// access. +ObjCIvarDecl *ObjCInterfaceDecl::all_declared_ivar_begin() { + if (IvarList) + return IvarList; + + ObjCIvarDecl *curIvar = 0; + if (!ivar_empty()) { + ObjCInterfaceDecl::ivar_iterator I = ivar_begin(), E = ivar_end(); + IvarList = (*I); ++I; + for (curIvar = IvarList; I != E; curIvar = *I, ++I) + curIvar->setNextIvar(*I); + } + + for (const ObjCCategoryDecl *CDecl = getFirstClassExtension(); CDecl; + CDecl = CDecl->getNextClassExtension()) { + if (!CDecl->ivar_empty()) { + ObjCCategoryDecl::ivar_iterator I = CDecl->ivar_begin(), + E = CDecl->ivar_end(); + if (!IvarList) { + IvarList = (*I); ++I; + curIvar = IvarList; + } + for ( ;I != E; curIvar = *I, ++I) + curIvar->setNextIvar(*I); + } + } + + if (ObjCImplementationDecl *ImplDecl = getImplementation()) { + if (!ImplDecl->ivar_empty()) { + ObjCImplementationDecl::ivar_iterator I = ImplDecl->ivar_begin(), + E = ImplDecl->ivar_end(); + if (!IvarList) { + IvarList = (*I); ++I; + curIvar = IvarList; + } + for ( ;I != E; curIvar = *I, ++I) + curIvar->setNextIvar(*I); + } + } + return IvarList; +} /// FindCategoryDeclaration - Finds category declaration in the list of /// categories for this class and returns it. Name of the category is passed @@ -556,6 +600,16 @@ ObjCIvarDecl *ObjCIvarDecl::Create(ASTContext &C, ObjCContainerDecl *DC, assert((isa<ObjCInterfaceDecl>(DC) || isa<ObjCImplementationDecl>(DC) || isa<ObjCCategoryDecl>(DC)) && "Invalid ivar decl context!"); + // Once a new ivar is created in any of class/class-extension/implementation + // decl contexts, the previously built IvarList must be rebuilt. + ObjCInterfaceDecl *ID = dyn_cast<ObjCInterfaceDecl>(DC); + if (!ID) { + if (ObjCImplementationDecl *IM = dyn_cast<ObjCImplementationDecl>(DC)) + ID = IM->getClassInterface(); + else + ID = (cast<ObjCCategoryDecl>(DC))->getClassInterface(); + } + ID->setIvarList(0); } return new (C) ObjCIvarDecl(DC, L, Id, T, TInfo, ac, BW, synthesized); |