From 59d16d1402d76a298ab7fc5f362e9d3dfd744aa5 Mon Sep 17 00:00:00 2001 From: Fariborz Jahanian Date: Tue, 17 Feb 2009 20:16:45 +0000 Subject: [PATCH] Added support for objc's gc attribute in ExtQualType. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@64800 91177308-0d34-0410-b5e6-96231b3b80d8 --- include/clang/AST/Type.h | 39 +++++++++++++++++++++++++++++++++------ lib/AST/ASTContext.cpp | 5 +++-- lib/AST/Type.cpp | 18 +++++++++++++++++- 3 files changed, 53 insertions(+), 9 deletions(-) diff --git a/include/clang/AST/Type.h b/include/clang/AST/Type.h index 3ab40d9820..f5e13c235c 100644 --- a/include/clang/AST/Type.h +++ b/include/clang/AST/Type.h @@ -29,6 +29,7 @@ using llvm::dyn_cast_or_null; namespace clang { class ASTContext; class Type; + class ObjCGCAttr; class TypedefDecl; class TemplateDecl; class TemplateTypeParmDecl; @@ -460,29 +461,55 @@ protected: /// __strong attributes. /// class ExtQualType : public Type, public llvm::FoldingSetNode { +public: + enum EQT { + EXTNONE = 0x0, + ASQUAL = 0x01, + GCQUAL = 0x10 + }; +private: /// BaseType - This is the underlying type that this qualifies. All CVR /// qualifiers are stored on the QualType that references this type, so we /// can't have any here. Type *BaseType; + unsigned ExtQualTypeKind : 2; + /// Address Space ID - The address space ID this type is qualified with. unsigned AddressSpace; - ExtQualType(Type *Base, QualType CanonicalPtr, unsigned AddrSpace) : - Type(ExtQual, CanonicalPtr, Base->isDependentType()), BaseType(Base), - AddressSpace(AddrSpace) { + /// GC __weak/__strong attributes + ObjCGCAttr *GCAttr; + + ExtQualType(Type *Base, QualType CanonicalPtr, unsigned AddrSpace, + ObjCGCAttr *gcAttr, + unsigned ExtKind) : + Type(ExtQual, CanonicalPtr, Base->isDependentType()), BaseType(Base), + ExtQualTypeKind(ExtKind), AddressSpace(0), GCAttr(0) { + if (ExtKind & ASQUAL) + AddressSpace = AddrSpace; + if (ExtKind & GCQUAL) + GCAttr = gcAttr; } friend class ASTContext; // ASTContext creates these. public: Type *getBaseType() const { return BaseType; } - unsigned getAddressSpace() const { return AddressSpace; } + ObjCGCAttr *getGCAttr() const { + assert((ExtQualTypeKind & GCQUAL) && "Bad ExtQualType Kind - not GCQUAL"); + return GCAttr; + } + unsigned getAddressSpace() const { + assert((ExtQualTypeKind & ASQUAL) && "Bad ExtQualType Kind - not ASQUAL"); + return AddressSpace; + } virtual void getAsStringInternal(std::string &InnerString) const; void Profile(llvm::FoldingSetNodeID &ID) { - Profile(ID, getBaseType(), AddressSpace); + Profile(ID, getBaseType(), AddressSpace, GCAttr); } static void Profile(llvm::FoldingSetNodeID &ID, Type *Base, - unsigned AddrSpace) { + unsigned AddrSpace, ObjCGCAttr *gcAttr) { ID.AddPointer(Base); + ID.AddPointer(gcAttr); ID.AddInteger(AddrSpace); } diff --git a/lib/AST/ASTContext.cpp b/lib/AST/ASTContext.cpp index 32a6c7d4c6..dec73182b8 100644 --- a/lib/AST/ASTContext.cpp +++ b/lib/AST/ASTContext.cpp @@ -725,7 +725,7 @@ QualType ASTContext::getAddrSpaceQualType(QualType T, unsigned AddressSpace) { // Check if we've already instantiated an address space qual'd type of this // type. llvm::FoldingSetNodeID ID; - ExtQualType::Profile(ID, T.getTypePtr(), AddressSpace); + ExtQualType::Profile(ID, T.getTypePtr(), AddressSpace, 0); void *InsertPos = 0; if (ExtQualType *EXTQy = ExtQualTypes.FindNodeOrInsertPos(ID, InsertPos)) return QualType(EXTQy, 0); @@ -741,7 +741,8 @@ QualType ASTContext::getAddrSpaceQualType(QualType T, unsigned AddressSpace) { assert(NewIP == 0 && "Shouldn't be in the map!"); NewIP = NewIP; } ExtQualType *New = new (*this, 8) ExtQualType(T.getTypePtr(), Canonical, - AddressSpace); + AddressSpace, 0, + ExtQualType::ASQUAL); ExtQualTypes.InsertNode(New, InsertPos); Types.push_back(New); return QualType(New, T.getCVRQualifiers()); diff --git a/lib/AST/Type.cpp b/lib/AST/Type.cpp index 0edc6ee7f7..6aec24fddd 100644 --- a/lib/AST/Type.cpp +++ b/lib/AST/Type.cpp @@ -1053,7 +1053,23 @@ void ComplexType::getAsStringInternal(std::string &S) const { } void ExtQualType::getAsStringInternal(std::string &S) const { - S = "__attribute__((address_space("+llvm::utostr_32(AddressSpace)+")))" + S; + bool space = false; + if (ExtQualTypeKind & ASQUAL) { + S = "__attribute__((address_space("+llvm::utostr_32(AddressSpace)+")))" + S; + space = true; + } + if (ExtQualTypeKind & GCQUAL) { + if (space) + S += ' '; + S += "__attribute__((objc_gc("; + ObjCGCAttr *gcattr = getGCAttr(); + ObjCGCAttr::GCAttrTypes attr = gcattr->getType(); + if (attr & ObjCGCAttr::Weak) + S += "weak"; + else + S += "strong"; + S += ")))"; + } BaseType->getAsStringInternal(S); } -- 2.50.1