[cfe-commits] r64889 - in /cfe/trunk: include/clang/AST/ASTContext.h include/clang/AST/Type.h lib/AST/ASTContext.cpp lib/AST/Type.cpp lib/Sema/SemaType.cpp

Fariborz Jahanian fjahanian at apple.com
Tue Feb 17 21:09:50 PST 2009


Author: fjahanian
Date: Tue Feb 17 23:09:49 2009
New Revision: 64889

URL: http://llvm.org/viewvc/llvm-project?rev=64889&view=rev
Log:
Representation of objc gc's attribute using ExtQualType.
Note that one test attr-objc-gc.m fails. I will fix this
after removing these attributes from the Decl nodes.


Modified:
    cfe/trunk/include/clang/AST/ASTContext.h
    cfe/trunk/include/clang/AST/Type.h
    cfe/trunk/lib/AST/ASTContext.cpp
    cfe/trunk/lib/AST/Type.cpp
    cfe/trunk/lib/Sema/SemaType.cpp

Modified: cfe/trunk/include/clang/AST/ASTContext.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/ASTContext.h?rev=64889&r1=64888&r2=64889&view=diff

==============================================================================
--- cfe/trunk/include/clang/AST/ASTContext.h (original)
+++ cfe/trunk/include/clang/AST/ASTContext.h Tue Feb 17 23:09:49 2009
@@ -190,6 +190,11 @@
   /// replaced.
   QualType getAddrSpaceQualType(QualType T, unsigned AddressSpace);
   
+  /// getObjCGCQualType - Returns the uniqued reference to the type for an
+  /// objc gc qualified type. The retulting type has a union of the qualifiers
+  /// from T and the gc attribute.
+  QualType getObjCGCQualType(QualType T, QualType::GCAttrTypes gcAttr);
+  
   /// getComplexType - Return the uniqued reference to the type for a complex
   /// number with the specified element type.
   QualType getComplexType(QualType T);

Modified: cfe/trunk/include/clang/AST/Type.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/Type.h?rev=64889&r1=64888&r2=64889&view=diff

==============================================================================
--- cfe/trunk/include/clang/AST/Type.h (original)
+++ cfe/trunk/include/clang/AST/Type.h Tue Feb 17 23:09:49 2009
@@ -93,6 +93,12 @@
     CVRFlags = Const|Restrict|Volatile
   };
   
+  enum GCAttrTypes {
+    GCNone = 0,
+    Weak,
+    Strong
+  };
+  
   QualType() {}
   
   QualType(const Type *Ptr, unsigned Quals)
@@ -188,6 +194,9 @@
   /// getAddressSpace - Return the address space of this type.
   inline unsigned getAddressSpace() const;
   
+  /// GCAttrTypesAttr - Returns gc attribute of this type.
+  inline QualType::GCAttrTypes getObjCGCAttr() const;
+  
   /// Emit - Serialize a QualType to Bitcode.
   void Emit(llvm::Serializer& S) const;
   
@@ -255,6 +264,7 @@
     BlockPointer,          // C extension
     FixedWidthInt
   };
+  
 private:
   QualType CanonicalType;
 
@@ -461,14 +471,6 @@
 /// __strong attributes.
 ///
 class ExtQualType : public Type, public llvm::FoldingSetNode {
-public:
-  enum GCAttrTypes {
-    GCNone = 0,
-    Weak,
-    Strong
-  };
-  
-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.
@@ -477,16 +479,16 @@
   /// Address Space ID - The address space ID this type is qualified with.
   unsigned AddressSpace;
   /// GC __weak/__strong attributes
-  GCAttrTypes GCAttrType;
+  QualType::GCAttrTypes GCAttrType;
   
   ExtQualType(Type *Base, QualType CanonicalPtr, unsigned AddrSpace,
-              GCAttrTypes gcAttr) :
+              QualType::GCAttrTypes gcAttr) :
     Type(ExtQual, CanonicalPtr, Base->isDependentType()), BaseType(Base),
     AddressSpace(AddrSpace), GCAttrType(gcAttr) { }
   friend class ASTContext;  // ASTContext creates these.
 public:
   Type *getBaseType() const { return BaseType; }
-  GCAttrTypes getType() const { return GCAttrType; }
+  QualType::GCAttrTypes getObjCGCAttr() const { return GCAttrType; }
   unsigned getAddressSpace() const { return AddressSpace; }
   
   virtual void getAsStringInternal(std::string &InnerString) const;
@@ -495,7 +497,7 @@
     Profile(ID, getBaseType(), AddressSpace, GCAttrType);
   }
   static void Profile(llvm::FoldingSetNodeID &ID, Type *Base, 
-                      unsigned AddrSpace, GCAttrTypes gcAttr) {
+                      unsigned AddrSpace, QualType::GCAttrTypes gcAttr) {
     ID.AddPointer(Base);
     ID.AddInteger(AddrSpace);
     ID.AddInteger(gcAttr);
@@ -1741,6 +1743,16 @@
   return 0;
 }
 
+/// getObjCGCAttr - Return the gc attribute of this type.
+inline QualType::GCAttrTypes QualType::getObjCGCAttr() const {
+  QualType CT = getTypePtr()->getCanonicalTypeInternal();
+  if (const ArrayType *AT = dyn_cast<ArrayType>(CT))
+      return AT->getElementType().getObjCGCAttr();
+  if (const ExtQualType *EXTQT = dyn_cast<ExtQualType>(CT))
+    return EXTQT->getObjCGCAttr();
+    return GCNone;
+}
+  
 /// isMoreQualifiedThan - Determine whether this type is more
 /// qualified than the Other type. For example, "const volatile int"
 /// is more qualified than "const int", "volatile int", and

Modified: cfe/trunk/lib/AST/ASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/ASTContext.cpp?rev=64889&r1=64888&r2=64889&view=diff

==============================================================================
--- cfe/trunk/lib/AST/ASTContext.cpp (original)
+++ cfe/trunk/lib/AST/ASTContext.cpp Tue Feb 17 23:09:49 2009
@@ -725,7 +725,7 @@
   // 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::GCNone);      
+  ExtQualType::Profile(ID, T.getTypePtr(), AddressSpace, T.getObjCGCAttr());      
   void *InsertPos = 0;
   if (ExtQualType *EXTQy = ExtQualTypes.FindNodeOrInsertPos(ID, InsertPos))
     return QualType(EXTQy, 0);
@@ -741,12 +741,47 @@
     assert(NewIP == 0 && "Shouldn't be in the map!"); NewIP = NewIP;
   }
   ExtQualType *New = new (*this, 8) ExtQualType(T.getTypePtr(), Canonical, 
-                                                AddressSpace, ExtQualType::GCNone);
+                                                AddressSpace, 
+                                                QualType::GCNone);
   ExtQualTypes.InsertNode(New, InsertPos);
   Types.push_back(New);
   return QualType(New, T.getCVRQualifiers());
 }
 
+QualType ASTContext::getObjCGCQualType(QualType T, 
+                                       QualType::GCAttrTypes attr) {
+  QualType CanT = getCanonicalType(T);
+  if (CanT.getObjCGCAttr() == attr)
+    return T;
+  
+  // Type's cannot have multiple ExtQuals, therefore we know we only have to deal
+  // with CVR qualifiers from here on out.
+  assert(CanT.getObjCGCAttr() == QualType::GCNone && 
+         "Type is already gc qualified");
+  
+  // Check if we've already instantiated an gc qual'd type of this type.
+  llvm::FoldingSetNodeID ID;
+  ExtQualType::Profile(ID, T.getTypePtr(), T.getAddressSpace(), attr);      
+  void *InsertPos = 0;
+  if (ExtQualType *EXTQy = ExtQualTypes.FindNodeOrInsertPos(ID, InsertPos))
+    return QualType(EXTQy, 0);
+  
+  // If the base type isn't canonical, this won't be a canonical type either,
+  // so fill in the canonical type field.
+  QualType Canonical;
+  if (!T->isCanonical()) {
+    Canonical = getObjCGCQualType(CanT, attr);
+    
+    // Get the new insert position for the node we care about.
+    ExtQualType *NewIP = ExtQualTypes.FindNodeOrInsertPos(ID, InsertPos);
+    assert(NewIP == 0 && "Shouldn't be in the map!"); NewIP = NewIP;
+  }
+  ExtQualType *New = new (*this, 8) ExtQualType(T.getTypePtr(), Canonical, 
+                                                0, attr);
+  ExtQualTypes.InsertNode(New, InsertPos);
+  Types.push_back(New);
+  return QualType(New, T.getCVRQualifiers());
+}
 
 /// getComplexType - Return the uniqued reference to the type for a complex
 /// number with the specified element type.

Modified: cfe/trunk/lib/AST/Type.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/Type.cpp?rev=64889&r1=64888&r2=64889&view=diff

==============================================================================
--- cfe/trunk/lib/AST/Type.cpp (original)
+++ cfe/trunk/lib/AST/Type.cpp Tue Feb 17 23:09:49 2009
@@ -1058,11 +1058,11 @@
     S = "__attribute__((address_space("+llvm::utostr_32(AddressSpace)+")))" + S;
     space = true;
   }
-  if (GCAttrType != GCNone) {
+  if (GCAttrType != QualType::GCNone) {
     if (space)
       S += ' ';
     S += "__attribute__((objc_gc(";
-    if (GCAttrType == Weak)
+    if (GCAttrType == QualType::Weak)
       S += "weak";
     else
       S += "strong";

Modified: cfe/trunk/lib/Sema/SemaType.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaType.cpp?rev=64889&r1=64888&r2=64889&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/SemaType.cpp (original)
+++ cfe/trunk/lib/Sema/SemaType.cpp Tue Feb 17 23:09:49 2009
@@ -758,6 +758,35 @@
   Type = S.Context.getAddrSpaceQualType(Type, ASIdx);
 }
 
+/// HandleObjCGCTypeAttribute - Process an objc's gc attribute on the
+/// specified type.  The attribute contains 1 argument, weak or strong.
+static void HandleObjCGCTypeAttribute(QualType &Type, 
+                                      const AttributeList &Attr, Sema &S){
+  // FIXME. Needs more work for this to make sense.
+  if (Type.getObjCGCAttr() != QualType::GCNone) {
+    S.Diag(Attr.getLoc(), diag::err_attribute_address_multiple_qualifiers);
+    return;
+  }
+  
+  // Check the attribute arguments.
+  QualType::GCAttrTypes attr;
+  if (!Attr.getParameterName() || Attr.getNumArgs() != 0) {
+    S.Diag(Attr.getLoc(), diag::err_attribute_wrong_number_arguments) << 1;
+    return;
+  }
+  if (Attr.getParameterName()->isStr("weak")) 
+    attr = QualType::Weak;
+  else if (Attr.getParameterName()->isStr("strong"))
+    attr = QualType::Strong;
+  else {
+    S.Diag(Attr.getLoc(), diag::warn_attribute_type_not_supported)
+      << "objc_gc" << Attr.getParameterName();
+    return;
+  }
+  
+  Type = S.Context.getObjCGCQualType(Type, attr);
+}
+
 void Sema::ProcessTypeAttributeList(QualType &Result, const AttributeList *AL) {
   // Scan through and apply attributes to this type where it makes sense.  Some
   // attributes (such as __address_space__, __vector_size__, etc) apply to the
@@ -771,6 +800,9 @@
     case AttributeList::AT_address_space:
       HandleAddressSpaceTypeAttribute(Result, *AL, *this);
       break;
+    case AttributeList::AT_objc_gc:
+      HandleObjCGCTypeAttribute(Result, *AL, *this);
+      break;
     }
   }
 }





More information about the cfe-commits mailing list