зеркало из https://github.com/microsoft/clang-1.git
Add SourceLocations to ObjCClassDecl for the class identifiers referenced by @class.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@89170 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Родитель
f74a419b72
Коммит
321c22f1c4
|
@ -718,10 +718,22 @@ public:
|
|||
/// @class NSCursor, NSImage, NSPasteboard, NSWindow;
|
||||
///
|
||||
class ObjCClassDecl : public Decl {
|
||||
ObjCList<ObjCInterfaceDecl> ForwardDecls;
|
||||
public:
|
||||
class ObjCClassRef {
|
||||
ObjCInterfaceDecl *ID;
|
||||
SourceLocation L;
|
||||
public:
|
||||
ObjCClassRef(ObjCInterfaceDecl *d, SourceLocation l) : ID(d), L(l) {}
|
||||
SourceLocation getLocation() const { return L; }
|
||||
ObjCInterfaceDecl *getInterface() const { return ID; }
|
||||
};
|
||||
private:
|
||||
ObjCClassRef *ForwardDecls;
|
||||
unsigned NumDecls;
|
||||
|
||||
ObjCClassDecl(DeclContext *DC, SourceLocation L,
|
||||
ObjCInterfaceDecl *const *Elts, unsigned nElts, ASTContext &C);
|
||||
ObjCInterfaceDecl *const *Elts, const SourceLocation *Locs,
|
||||
unsigned nElts, ASTContext &C);
|
||||
virtual ~ObjCClassDecl() {}
|
||||
public:
|
||||
|
||||
|
@ -730,17 +742,17 @@ public:
|
|||
|
||||
static ObjCClassDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation L,
|
||||
ObjCInterfaceDecl *const *Elts = 0,
|
||||
const SourceLocation *Locs = 0,
|
||||
unsigned nElts = 0);
|
||||
|
||||
typedef ObjCList<ObjCInterfaceDecl>::iterator iterator;
|
||||
iterator begin() const { return ForwardDecls.begin(); }
|
||||
iterator end() const { return ForwardDecls.end(); }
|
||||
unsigned size() const { return ForwardDecls.size(); }
|
||||
typedef const ObjCClassRef* iterator;
|
||||
iterator begin() const { return ForwardDecls; }
|
||||
iterator end() const { return ForwardDecls + NumDecls; }
|
||||
unsigned size() const { return NumDecls; }
|
||||
|
||||
/// setClassList - Set the list of forward classes.
|
||||
void setClassList(ASTContext &C, ObjCInterfaceDecl*const*List, unsigned Num) {
|
||||
ForwardDecls.set(List, Num, C);
|
||||
}
|
||||
void setClassList(ASTContext &C, ObjCInterfaceDecl*const*List,
|
||||
const SourceLocation *Locs, unsigned Num);
|
||||
|
||||
static bool classof(const Decl *D) { return D->getKind() == ObjCClass; }
|
||||
static bool classof(const ObjCClassDecl *D) { return true; }
|
||||
|
|
|
@ -678,7 +678,7 @@ void DeclContext::buildLookup(DeclContext *DCtx) {
|
|||
if (ObjCClassDecl *Class = dyn_cast<ObjCClassDecl>(*D))
|
||||
for (ObjCClassDecl::iterator I = Class->begin(), IEnd = Class->end();
|
||||
I != IEnd; ++I)
|
||||
makeDeclVisibleInContextImpl(*I);
|
||||
makeDeclVisibleInContextImpl(I->getInterface());
|
||||
|
||||
// If this declaration is itself a transparent declaration context,
|
||||
// add its members (recursively).
|
||||
|
|
|
@ -571,31 +571,46 @@ ObjCMethodDecl *ObjCProtocolDecl::lookupMethod(Selector Sel,
|
|||
//===----------------------------------------------------------------------===//
|
||||
|
||||
ObjCClassDecl::ObjCClassDecl(DeclContext *DC, SourceLocation L,
|
||||
ObjCInterfaceDecl *const *Elts, unsigned nElts,
|
||||
ObjCInterfaceDecl *const *Elts,
|
||||
const SourceLocation *Locs,
|
||||
unsigned nElts,
|
||||
ASTContext &C)
|
||||
: Decl(ObjCClass, DC, L) {
|
||||
ForwardDecls.set(Elts, nElts, C);
|
||||
setClassList(C, Elts, Locs, nElts);
|
||||
}
|
||||
|
||||
void ObjCClassDecl::setClassList(ASTContext &C, ObjCInterfaceDecl*const*List,
|
||||
const SourceLocation *Locs, unsigned Num) {
|
||||
ForwardDecls = (ObjCClassRef*) C.Allocate(sizeof(ObjCClassRef)*Num,
|
||||
llvm::alignof<ObjCClassRef>());
|
||||
for (unsigned i = 0; i < Num; ++i)
|
||||
new (&ForwardDecls[i]) ObjCClassRef(List[i], Locs[i]);
|
||||
|
||||
NumDecls = Num;
|
||||
}
|
||||
|
||||
ObjCClassDecl *ObjCClassDecl::Create(ASTContext &C, DeclContext *DC,
|
||||
SourceLocation L,
|
||||
ObjCInterfaceDecl *const *Elts,
|
||||
const SourceLocation *Locs,
|
||||
unsigned nElts) {
|
||||
return new (C) ObjCClassDecl(DC, L, Elts, nElts, C);
|
||||
return new (C) ObjCClassDecl(DC, L, Elts, Locs, nElts, C);
|
||||
}
|
||||
|
||||
void ObjCClassDecl::Destroy(ASTContext &C) {
|
||||
|
||||
// FIXME: There is no clear ownership policy now for referenced
|
||||
// ObjCInterfaceDecls. Some of them can be forward declarations that
|
||||
// are never later defined (in which case the ObjCClassDecl owns them)
|
||||
// or the ObjCInterfaceDecl later becomes a real definition later. Ideally
|
||||
// we should have separate objects for forward declarations and definitions,
|
||||
// obviating this problem. Because of this situation, referenced
|
||||
// ObjCInterfaceDecls are destroyed in ~TranslationUnit.
|
||||
|
||||
ForwardDecls.Destroy(C);
|
||||
// ObjCInterfaceDecls registered with a DeclContext will get destroyed
|
||||
// when the DeclContext is destroyed. For those created only by a forward
|
||||
// declaration, the first @class that created the ObjCInterfaceDecl gets
|
||||
// to destroy it.
|
||||
// FIXME: Note that this ownership role is very brittle; a better
|
||||
// polict is surely need in the future.
|
||||
for (iterator I = begin(), E = end(); I !=E ; ++I) {
|
||||
ObjCInterfaceDecl *ID = I->getInterface();
|
||||
if (ID->isForwardDecl() && ID->getLocStart() == getLocStart())
|
||||
ID->Destroy(C);
|
||||
}
|
||||
|
||||
C.Deallocate(ForwardDecls);
|
||||
Decl::Destroy(C);
|
||||
}
|
||||
|
||||
|
|
|
@ -624,7 +624,7 @@ void DeclPrinter::VisitObjCClassDecl(ObjCClassDecl *D) {
|
|||
for (ObjCClassDecl::iterator I = D->begin(), E = D->end();
|
||||
I != E; ++I) {
|
||||
if (I != D->begin()) Out << ", ";
|
||||
Out << (*I)->getNameAsString();
|
||||
Out << I->getInterface()->getNameAsString();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -264,7 +264,12 @@ void PCHDeclReader::VisitObjCClassDecl(ObjCClassDecl *CD) {
|
|||
ClassRefs.reserve(NumClassRefs);
|
||||
for (unsigned I = 0; I != NumClassRefs; ++I)
|
||||
ClassRefs.push_back(cast<ObjCInterfaceDecl>(Reader.GetDecl(Record[Idx++])));
|
||||
CD->setClassList(*Reader.getContext(), ClassRefs.data(), NumClassRefs);
|
||||
llvm::SmallVector<SourceLocation, 16> SLocs;
|
||||
SLocs.reserve(NumClassRefs);
|
||||
for (unsigned I = 0; I != NumClassRefs; ++I)
|
||||
SLocs.push_back(SourceLocation::getFromRawEncoding(Record[Idx++]));
|
||||
CD->setClassList(*Reader.getContext(), ClassRefs.data(), SLocs.data(),
|
||||
NumClassRefs);
|
||||
}
|
||||
|
||||
void PCHDeclReader::VisitObjCForwardProtocolDecl(ObjCForwardProtocolDecl *FPD) {
|
||||
|
|
|
@ -260,7 +260,9 @@ void PCHDeclWriter::VisitObjCClassDecl(ObjCClassDecl *D) {
|
|||
VisitDecl(D);
|
||||
Record.push_back(D->size());
|
||||
for (ObjCClassDecl::iterator I = D->begin(), IEnd = D->end(); I != IEnd; ++I)
|
||||
Writer.AddDeclRef(*I, Record);
|
||||
Writer.AddDeclRef(I->getInterface(), Record);
|
||||
for (ObjCClassDecl::iterator I = D->begin(), IEnd = D->end(); I != IEnd; ++I)
|
||||
Writer.AddSourceLocation(I->getLocation(), Record);
|
||||
Code = pch::DECL_OBJC_CLASS;
|
||||
}
|
||||
|
||||
|
|
|
@ -744,7 +744,7 @@ void RewriteObjC::RewriteForwardClassDecl(ObjCClassDecl *ClassDecl) {
|
|||
typedefString += "\n";
|
||||
for (ObjCClassDecl::iterator I = ClassDecl->begin(), E = ClassDecl->end();
|
||||
I != E; ++I) {
|
||||
ObjCInterfaceDecl *ForwardDecl = *I;
|
||||
ObjCInterfaceDecl *ForwardDecl = I->getInterface();
|
||||
typedefString += "#ifndef _REWRITER_typedef_";
|
||||
typedefString += ForwardDecl->getNameAsString();
|
||||
typedefString += "\n";
|
||||
|
|
|
@ -1197,10 +1197,7 @@ Sema::ActOnForwardClassDeclaration(SourceLocation AtClassLoc,
|
|||
ObjCInterfaceDecl *IDecl = dyn_cast_or_null<ObjCInterfaceDecl>(PrevDecl);
|
||||
if (!IDecl) { // Not already seen? Make a forward decl.
|
||||
IDecl = ObjCInterfaceDecl::Create(Context, CurContext, AtClassLoc,
|
||||
IdentList[i],
|
||||
// FIXME: need to get the 'real'
|
||||
// identifier loc from the parser.
|
||||
AtClassLoc, true);
|
||||
IdentList[i], IdentLocs[i], true);
|
||||
|
||||
// Push the ObjCInterfaceDecl on the scope chain but do *not* add it to
|
||||
// the current DeclContext. This prevents clients that walk DeclContext
|
||||
|
@ -1214,8 +1211,9 @@ Sema::ActOnForwardClassDeclaration(SourceLocation AtClassLoc,
|
|||
Interfaces.push_back(IDecl);
|
||||
}
|
||||
|
||||
assert(Interfaces.size() == NumElts);
|
||||
ObjCClassDecl *CDecl = ObjCClassDecl::Create(Context, CurContext, AtClassLoc,
|
||||
&Interfaces[0],
|
||||
Interfaces.data(), IdentLocs,
|
||||
Interfaces.size());
|
||||
CurContext->addDecl(CDecl);
|
||||
CheckObjCDeclScope(CDecl);
|
||||
|
|
Загрузка…
Ссылка в новой задаче