[cfe-commits] r84907 - in /cfe/trunk: include/clang/AST/ASTContext.h include/clang/AST/Type.h include/clang/AST/TypeLoc.h include/clang/AST/TypeNodes.def include/clang/Frontend/PCHBitCodes.h lib/AST/ASTContext.cpp lib/AST/Type.cpp lib/CodeGen/Mangle.cpp lib/Frontend/PCHReader.cpp lib/Frontend/PCHWriter.cpp lib/Index/ResolveLocation.cpp lib/Sema/Sema.h lib/Sema/SemaDeclCXX.cpp lib/Sema/SemaType.cpp lib/Sema/TreeTransform.h test/SemaCXX/overloaded-operator.cpp

John McCall rjmccall at apple.com
Thu Oct 22 15:37:12 PDT 2009


Author: rjmccall
Date: Thu Oct 22 17:37:11 2009
New Revision: 84907

URL: http://llvm.org/viewvc/llvm-project?rev=84907&view=rev
Log:
When building types from declarators, instead of building two types (one for
the DeclaratorInfo, one for semantic analysis), just build a single type whose
canonical type will reflect the semantic analysis (assuming the type is
well-formed, of course).

To make that work, make a few changes to the type system:
* allow the nominal pointee type of a reference type to be a (possibly sugared)
  reference type.  Also, preserve the original spelling of the reference type.
  Both of these can be ignored on canonical reference types.
* Remove ObjCProtocolListType and preserve the associated source information on
  the various ObjC TypeLocs.  Preserve the spelling of protocol lists except in
  the canonical form.
* Preserve some level of source type structure on parameter types, but
  canonicalize on the canonical function type.  This is still a WIP.

Drops code size, makes strides towards accurate source location representation,
slight (~1.7%) progression on Cocoa.h because of complexity drop.


Modified:
    cfe/trunk/include/clang/AST/ASTContext.h
    cfe/trunk/include/clang/AST/Type.h
    cfe/trunk/include/clang/AST/TypeLoc.h
    cfe/trunk/include/clang/AST/TypeNodes.def
    cfe/trunk/include/clang/Frontend/PCHBitCodes.h
    cfe/trunk/lib/AST/ASTContext.cpp
    cfe/trunk/lib/AST/Type.cpp
    cfe/trunk/lib/CodeGen/Mangle.cpp
    cfe/trunk/lib/Frontend/PCHReader.cpp
    cfe/trunk/lib/Frontend/PCHWriter.cpp
    cfe/trunk/lib/Index/ResolveLocation.cpp
    cfe/trunk/lib/Sema/Sema.h
    cfe/trunk/lib/Sema/SemaDeclCXX.cpp
    cfe/trunk/lib/Sema/SemaType.cpp
    cfe/trunk/lib/Sema/TreeTransform.h
    cfe/trunk/test/SemaCXX/overloaded-operator.cpp

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

==============================================================================
--- cfe/trunk/include/clang/AST/ASTContext.h (original)
+++ cfe/trunk/include/clang/AST/ASTContext.h Thu Oct 22 17:37:11 2009
@@ -87,7 +87,6 @@
   llvm::FoldingSet<TypenameType> TypenameTypes;
   llvm::FoldingSet<ObjCInterfaceType> ObjCInterfaceTypes;
   llvm::FoldingSet<ObjCObjectPointerType> ObjCObjectPointerTypes;
-  llvm::FoldingSet<ObjCProtocolListType> ObjCProtocolListTypes;
   llvm::FoldingSet<ElaboratedType> ElaboratedTypes;
 
   llvm::FoldingSet<QualifiedTemplateName> QualifiedTemplateNames;
@@ -437,7 +436,7 @@
 
   /// getLValueReferenceType - Return the uniqued reference to the type for an
   /// lvalue reference to the specified type.
-  QualType getLValueReferenceType(QualType T);
+  QualType getLValueReferenceType(QualType T, bool SpelledAsLValue = true);
 
   /// getRValueReferenceType - Return the uniqued reference to the type for an
   /// rvalue reference to the specified type.
@@ -547,10 +546,6 @@
                                     ObjCProtocolDecl **ProtocolList = 0,
                                     unsigned NumProtocols = 0);
 
-  QualType getObjCProtocolListType(QualType T,
-                                   ObjCProtocolDecl **Protocols,
-                                   unsigned NumProtocols);
-
   /// getTypeOfType - GCC extension.
   QualType getTypeOfExprType(Expr *e);
   QualType getTypeOfType(QualType t);
@@ -847,6 +842,12 @@
     return T->getCanonicalTypeInternal().getTypePtr();
   }
 
+  /// getCanonicalParamType - Return the canonical parameter type
+  /// corresponding to the specific potentially non-canonical one.
+  /// Qualifiers are stripped off, functions are turned into function
+  /// pointers, and arrays decay one level into pointers.
+  CanQualType getCanonicalParamType(QualType T);
+
   /// \brief Determine whether the given types are equivalent.
   bool hasSameType(QualType T1, QualType T2) {
     return getCanonicalType(T1) == getCanonicalType(T2);

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

==============================================================================
--- cfe/trunk/include/clang/AST/Type.h (original)
+++ cfe/trunk/include/clang/AST/Type.h Thu Oct 22 17:37:11 2009
@@ -444,6 +444,7 @@
   }
 
   bool isCanonical() const;
+  bool isCanonicalAsParam() const;
 
   /// isNull - Return true if this QualType doesn't point to a type yet.
   bool isNull() const {
@@ -1093,19 +1094,50 @@
 class ReferenceType : public Type, public llvm::FoldingSetNode {
   QualType PointeeType;
 
+  /// True if the type was originally spelled with an lvalue sigil.
+  /// This is never true of rvalue references but can also be false
+  /// on lvalue references because of C++0x [dcl.typedef]p9,
+  /// as follows:
+  ///
+  ///   typedef int &ref;    // lvalue, spelled lvalue
+  ///   typedef int &&rvref; // rvalue
+  ///   ref &a;              // lvalue, inner ref, spelled lvalue
+  ///   ref &&a;             // lvalue, inner ref
+  ///   rvref &a;            // lvalue, inner ref, spelled lvalue
+  ///   rvref &&a;           // rvalue, inner ref
+  bool SpelledAsLValue;
+
+  /// True if the inner type is a reference type.  This only happens
+  /// in non-canonical forms.
+  bool InnerRef;
+
 protected:
-  ReferenceType(TypeClass tc, QualType Referencee, QualType CanonicalRef) :
+  ReferenceType(TypeClass tc, QualType Referencee, QualType CanonicalRef,
+                bool SpelledAsLValue) :
     Type(tc, CanonicalRef, Referencee->isDependentType()),
-    PointeeType(Referencee) {
+    PointeeType(Referencee), SpelledAsLValue(SpelledAsLValue),
+    InnerRef(Referencee->isReferenceType()) {
   }
 public:
-  QualType getPointeeType() const { return PointeeType; }
+  bool isSpelledAsLValue() const { return SpelledAsLValue; }
+
+  QualType getPointeeTypeAsWritten() const { return PointeeType; }
+  QualType getPointeeType() const {
+    // FIXME: this might strip inner qualifiers; okay?
+    const ReferenceType *T = this;
+    while (T->InnerRef)
+      T = T->PointeeType->getAs<ReferenceType>();
+    return T->PointeeType;
+  }
 
   void Profile(llvm::FoldingSetNodeID &ID) {
-    Profile(ID, getPointeeType());
+    Profile(ID, PointeeType, SpelledAsLValue);
   }
-  static void Profile(llvm::FoldingSetNodeID &ID, QualType Referencee) {
+  static void Profile(llvm::FoldingSetNodeID &ID,
+                      QualType Referencee,
+                      bool SpelledAsLValue) {
     ID.AddPointer(Referencee.getAsOpaquePtr());
+    ID.AddBoolean(SpelledAsLValue);
   }
 
   static bool classof(const Type *T) {
@@ -1118,9 +1150,10 @@
 /// LValueReferenceType - C++ [dcl.ref] - Lvalue reference
 ///
 class LValueReferenceType : public ReferenceType {
-  LValueReferenceType(QualType Referencee, QualType CanonicalRef) :
-    ReferenceType(LValueReference, Referencee, CanonicalRef) {
-  }
+  LValueReferenceType(QualType Referencee, QualType CanonicalRef,
+                      bool SpelledAsLValue) :
+    ReferenceType(LValueReference, Referencee, CanonicalRef, SpelledAsLValue)
+  {}
   friend class ASTContext; // ASTContext creates these
 public:
   virtual void getAsStringInternal(std::string &InnerString,
@@ -1139,7 +1172,7 @@
 ///
 class RValueReferenceType : public ReferenceType {
   RValueReferenceType(QualType Referencee, QualType CanonicalRef) :
-    ReferenceType(RValueReference, Referencee, CanonicalRef) {
+    ReferenceType(RValueReference, Referencee, CanonicalRef, false) {
   }
   friend class ASTContext; // ASTContext creates these
 public:
@@ -2433,9 +2466,9 @@
   // List is sorted on protocol name. No protocol is enterred more than once.
   llvm::SmallVector<ObjCProtocolDecl*, 4> Protocols;
 
-  ObjCInterfaceType(ObjCInterfaceDecl *D,
+  ObjCInterfaceType(QualType Canonical, ObjCInterfaceDecl *D,
                     ObjCProtocolDecl **Protos, unsigned NumP) :
-    Type(ObjCInterface, QualType(), /*Dependent=*/false),
+    Type(ObjCInterface, Canonical, /*Dependent=*/false),
     Decl(D), Protocols(Protos, Protos+NumP) { }
   friend class ASTContext;  // ASTContext creates these.
 public:
@@ -2481,8 +2514,9 @@
   // List is sorted on protocol name. No protocol is entered more than once.
   llvm::SmallVector<ObjCProtocolDecl*, 8> Protocols;
 
-  ObjCObjectPointerType(QualType T, ObjCProtocolDecl **Protos, unsigned NumP) :
-    Type(ObjCObjectPointer, QualType(), /*Dependent=*/false),
+  ObjCObjectPointerType(QualType Canonical, QualType T,
+                        ObjCProtocolDecl **Protos, unsigned NumP) :
+    Type(ObjCObjectPointer, Canonical, /*Dependent=*/false),
     PointeeType(T), Protocols(Protos, Protos+NumP) { }
   friend class ASTContext;  // ASTContext creates these.
 
@@ -2547,49 +2581,6 @@
   static bool classof(const ObjCObjectPointerType *) { return true; }
 };
 
-/// \brief An ObjC Protocol list that qualifies a type.
-///
-/// This is used only for keeping detailed type source information, it should
-/// not participate in the semantics of the type system.
-/// The protocol list is not canonicalized.
-class ObjCProtocolListType : public Type, public llvm::FoldingSetNode {
-  QualType BaseType;
-
-  // List of protocols for this protocol conforming object type.
-  llvm::SmallVector<ObjCProtocolDecl*, 4> Protocols;
-
-  ObjCProtocolListType(QualType T, ObjCProtocolDecl **Protos, unsigned NumP) :
-    Type(ObjCProtocolList, QualType(), /*Dependent=*/false),
-    BaseType(T), Protocols(Protos, Protos+NumP) { }
-  friend class ASTContext;  // ASTContext creates these.
-
-public:
-  QualType getBaseType() const { return BaseType; }
-
-  /// \brief Provides access to the list of protocols qualifying the base type.
-  typedef llvm::SmallVector<ObjCProtocolDecl*, 4>::const_iterator qual_iterator;
-
-  qual_iterator qual_begin() const { return Protocols.begin(); }
-  qual_iterator qual_end() const   { return Protocols.end(); }
-  bool qual_empty() const { return Protocols.size() == 0; }
-
-  /// \brief Return the number of qualifying protocols.
-  unsigned getNumProtocols() const { return Protocols.size(); }
-
-  bool isSugared() const { return false; }
-  QualType desugar() const { return QualType(this, 0); }
-
-  void Profile(llvm::FoldingSetNodeID &ID);
-  static void Profile(llvm::FoldingSetNodeID &ID, QualType T,
-                      ObjCProtocolDecl **protocols, unsigned NumProtocols);
-  virtual void getAsStringInternal(std::string &InnerString,
-                                   const PrintingPolicy &Policy) const;
-  static bool classof(const Type *T) {
-    return T->getTypeClass() == ObjCProtocolList;
-  }
-  static bool classof(const ObjCProtocolListType *) { return true; }
-};
-
 /// A qualifier set is used to build a set of qualifiers.
 class QualifierCollector : public Qualifiers {
   ASTContext *Context;
@@ -2633,6 +2624,13 @@
   return T->isCanonicalUnqualified();
 }
 
+inline bool QualType::isCanonicalAsParam() const {
+  if (hasQualifiers()) return false;
+  const Type *T = getTypePtr();
+  return T->isCanonicalUnqualified() &&
+           !isa<FunctionType>(T) && !isa<ArrayType>(T);
+}
+
 inline void QualType::removeConst() {
   removeFastQualifiers(Qualifiers::Const);
 }

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

==============================================================================
--- cfe/trunk/include/clang/AST/TypeLoc.h (original)
+++ cfe/trunk/include/clang/AST/TypeLoc.h Thu Oct 22 17:37:11 2009
@@ -375,48 +375,52 @@
                            SubstTemplateTypeParmType> {
 };
 
-/// \brief Wrapper for source info for ObjC interfaces.
-class ObjCInterfaceTypeLoc : public TypeSpecTypeLoc<ObjCInterfaceTypeLoc,
-                                                    ObjCInterfaceType> {
-public:
-  ObjCInterfaceDecl *getIFaceDecl() const {
-    return getTypePtr()->getDecl();
-  }
-};
-
 
 struct ObjCProtocolListLocInfo {
-  SourceLocation LAngleLoc, RAngleLoc;
+  SourceLocation LAngleLoc;
+  SourceLocation RAngleLoc;
 };
 
-/// \brief Wrapper for source info for ObjC protocol lists.
-class ObjCProtocolListTypeLoc
-  : public ConcreteTypeLoc<UnqualTypeLoc,
-                           ObjCProtocolListTypeLoc,
-                           ObjCProtocolListType,
-                           ObjCProtocolListLocInfo> {
+// A helper class for defining ObjC TypeLocs that can qualified with
+// protocols.
+//
+// TypeClass basically has to be either ObjCInterfaceType or
+// ObjCObjectPointerType.
+template <class Derived, class TypeClass, class LocalData>
+class ObjCProtocolListTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
+                                                       Derived,
+                                                       TypeClass,
+                                                       LocalData> {
   // SourceLocations are stored after Info, one for each Protocol.
   SourceLocation *getProtocolLocArray() const {
-    return (SourceLocation*) getExtraLocalData();
+    return (SourceLocation*) this->getExtraLocalData();
+  }
+
+protected:
+  void initializeLocalBase(SourceLocation Loc) {
+    setLAngleLoc(Loc);
+    setRAngleLoc(Loc);
+    for (unsigned i = 0, e = getNumProtocols(); i != e; ++i)
+      setProtocolLoc(i, Loc);
   }
 
 public:
   SourceLocation getLAngleLoc() const {
-    return getLocalData()->LAngleLoc;
+    return this->getLocalData()->LAngleLoc;
   }
   void setLAngleLoc(SourceLocation Loc) {
-    getLocalData()->LAngleLoc = Loc;
+    this->getLocalData()->LAngleLoc = Loc;
   }
 
   SourceLocation getRAngleLoc() const {
-    return getLocalData()->RAngleLoc;
+    return this->getLocalData()->RAngleLoc;
   }
   void setRAngleLoc(SourceLocation Loc) {
-    getLocalData()->RAngleLoc = Loc;
+    this->getLocalData()->RAngleLoc = Loc;
   }
 
   unsigned getNumProtocols() const {
-    return getTypePtr()->getNumProtocols();
+    return this->getTypePtr()->getNumProtocols();
   }
 
   SourceLocation getProtocolLoc(unsigned i) const {
@@ -430,33 +434,122 @@
 
   ObjCProtocolDecl *getProtocol(unsigned i) const {
     assert(i < getNumProtocols() && "Index is out of bounds!");
-    return *(getTypePtr()->qual_begin() + i);
+    return *(this->getTypePtr()->qual_begin() + i);
   }
   
-  TypeLoc getBaseTypeLoc() const {
-    return getInnerTypeLoc();
-  }
-
   SourceRange getSourceRange() const {
     return SourceRange(getLAngleLoc(), getRAngleLoc());
   }
 
   void initializeLocal(SourceLocation Loc) {
-    setLAngleLoc(Loc);
-    setRAngleLoc(Loc);
-    for (unsigned i = 0, e = getNumProtocols(); i != e; ++i)
-      setProtocolLoc(i, Loc);
+    initializeLocalBase(Loc);
   }
 
-  /// \brief Returns the size of the type source info data block that is
-  /// specific to this type.
   unsigned getExtraLocalDataSize() const {
-    return getNumProtocols() * sizeof(SourceLocation);
+    return this->getNumProtocols() * sizeof(SourceLocation);
   }
+};
+
+
+struct ObjCInterfaceLocInfo : ObjCProtocolListLocInfo {
+  SourceLocation NameLoc;
+};
+
+/// \brief Wrapper for source info for ObjC interfaces.
+class ObjCInterfaceTypeLoc :
+    public ObjCProtocolListTypeLoc<ObjCInterfaceTypeLoc,
+                                   ObjCInterfaceType,
+                                   ObjCInterfaceLocInfo> {
+public:
+  ObjCInterfaceDecl *getIFaceDecl() const {
+    return getTypePtr()->getDecl();
+  }
+
+  SourceLocation getNameLoc() const {
+    return getLocalData()->NameLoc;
+  }
+
+  void setNameLoc(SourceLocation Loc) {
+    getLocalData()->NameLoc = Loc;
+  }
+
+  SourceRange getSourceRange() const {
+    if (getNumProtocols()) 
+      return SourceRange(getNameLoc(), getRAngleLoc());
+    else
+      return SourceRange(getNameLoc(), getNameLoc());
+  }
+
+  void initializeLocal(SourceLocation Loc) {
+    initializeLocalBase(Loc);
+    setNameLoc(Loc);
+  }
+};
+
 
-  QualType getInnerType() const { return getTypePtr()->getBaseType(); }
+struct ObjCObjectPointerLocInfo : ObjCProtocolListLocInfo {
+  SourceLocation StarLoc;
+  bool HasProtocols;
+  bool HasBaseType;
 };
 
+/// Wraps an ObjCPointerType with source location information.  Note
+/// that not all ObjCPointerTypes actually have a star location; nor
+/// are protocol locations necessarily written in the source just
+/// because they're present on the type.
+class ObjCObjectPointerTypeLoc :
+    public ObjCProtocolListTypeLoc<ObjCObjectPointerTypeLoc,
+                                   ObjCObjectPointerType,
+                                   ObjCObjectPointerLocInfo> {
+public:
+  bool hasProtocolsAsWritten() const {
+    return getLocalData()->HasProtocols;
+  }
+
+  void setHasProtocolsAsWritten(bool HasProtocols) {
+    getLocalData()->HasProtocols = HasProtocols;
+  }
+
+  bool hasBaseTypeAsWritten() const {
+    return getLocalData()->HasBaseType;
+  }
+
+  void setHasBaseTypeAsWritten(bool HasBaseType) {
+    getLocalData()->HasBaseType = HasBaseType;
+  }
+
+  SourceLocation getStarLoc() const {
+    return getLocalData()->StarLoc;
+  }
+
+  void setStarLoc(SourceLocation Loc) {
+    getLocalData()->StarLoc = Loc;
+  }
+
+  SourceRange getSourceRange() const {
+    // Being written with protocols is incompatible with being written
+    // with a star.
+    if (hasProtocolsAsWritten())
+      return SourceRange(getLAngleLoc(), getRAngleLoc());
+    else
+      return SourceRange(getStarLoc(), getStarLoc());
+  }
+
+  void initializeLocal(SourceLocation Loc) {
+    initializeLocalBase(Loc);
+    setHasProtocolsAsWritten(false);
+    setHasBaseTypeAsWritten(false);
+    setStarLoc(Loc);
+  }
+
+  TypeLoc getBaseTypeLoc() const {
+    return getInnerTypeLoc();
+  }
+
+  QualType getInnerType() const {
+    return getTypePtr()->getPointeeType();
+  }
+};
 
 
 struct PointerLikeLocInfo {
@@ -534,6 +627,10 @@
 
 class ReferenceTypeLoc : public PointerLikeTypeLoc<ReferenceTypeLoc,
                                                    ReferenceType> {
+public:
+  QualType getInnerType() const {
+    return getTypePtr()->getPointeeTypeAsWritten();
+  }
 };
 
 class LValueReferenceTypeLoc :
@@ -562,20 +659,6 @@
   }
 };
 
-/// Wraps an ObjCPointerType with source location information.  Note
-/// that not all ObjCPointerTypes actually have a star location.
-class ObjCObjectPointerTypeLoc :
-    public PointerLikeTypeLoc<ObjCObjectPointerTypeLoc,
-                              ObjCObjectPointerType> {
-public:
-  SourceLocation getStarLoc() const {
-    return getSigilLoc();
-  }
-  void setStarLoc(SourceLocation Loc) {
-    setSigilLoc(Loc);
-  }
-};
-
 
 struct FunctionLocInfo {
   SourceLocation LParenLoc, RParenLoc;

Modified: cfe/trunk/include/clang/AST/TypeNodes.def
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/TypeNodes.def?rev=84907&r1=84906&r2=84907&view=diff

==============================================================================
--- cfe/trunk/include/clang/AST/TypeNodes.def (original)
+++ cfe/trunk/include/clang/AST/TypeNodes.def Thu Oct 22 17:37:11 2009
@@ -86,7 +86,6 @@
 DEPENDENT_TYPE(Typename, Type)
 TYPE(ObjCInterface, Type)
 TYPE(ObjCObjectPointer, Type)
-NON_CANONICAL_TYPE(ObjCProtocolList, Type)
 
 // These types are always leaves in the type hierarchy.
 #ifdef LEAF_TYPE
@@ -94,7 +93,6 @@
 LEAF_TYPE(Builtin)
 LEAF_TYPE(FixedWidthInt)
 LEAF_TYPE(ObjCInterface)
-LEAF_TYPE(ObjCObjectPointer)
 LEAF_TYPE(TemplateTypeParm)
 #undef LEAF_TYPE
 #endif

Modified: cfe/trunk/include/clang/Frontend/PCHBitCodes.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Frontend/PCHBitCodes.h?rev=84907&r1=84906&r2=84907&view=diff

==============================================================================
--- cfe/trunk/include/clang/Frontend/PCHBitCodes.h (original)
+++ cfe/trunk/include/clang/Frontend/PCHBitCodes.h Thu Oct 22 17:37:11 2009
@@ -397,14 +397,12 @@
       TYPE_OBJC_INTERFACE           = 21,
       /// \brief An ObjCObjectPointerType record.
       TYPE_OBJC_OBJECT_POINTER      = 22,
-      /// \brief An ObjCProtocolListType record.
-      TYPE_OBJC_PROTOCOL_LIST       = 23,
       /// \brief a DecltypeType record.
-      TYPE_DECLTYPE                 = 24,
+      TYPE_DECLTYPE                 = 23,
       /// \brief An ElaboratedType record.
-      TYPE_ELABORATED               = 25,
+      TYPE_ELABORATED               = 24,
       /// \brief A SubstTemplateTypeParmType record.
-      TYPE_SUBST_TEMPLATE_TYPE_PARM = 26
+      TYPE_SUBST_TEMPLATE_TYPE_PARM = 25
     };
 
     /// \brief The type IDs for special types constructed by semantic

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

==============================================================================
--- cfe/trunk/lib/AST/ASTContext.cpp (original)
+++ cfe/trunk/lib/AST/ASTContext.cpp Thu Oct 22 17:37:11 2009
@@ -555,10 +555,6 @@
     assert(false && "Should not see dependent types");
     break;
 
-  case Type::ObjCProtocolList:
-    assert(false && "Should not see protocol list types");
-    break;
-
   case Type::FunctionNoProto:
   case Type::FunctionProto:
     // GCC extension: alignof(function) = 32 bits
@@ -1235,22 +1231,25 @@
 
 /// getLValueReferenceType - Return the uniqued reference to the type for an
 /// lvalue reference to the specified type.
-QualType ASTContext::getLValueReferenceType(QualType T) {
+QualType ASTContext::getLValueReferenceType(QualType T, bool SpelledAsLValue) {
   // Unique pointers, to guarantee there is only one pointer of a particular
   // structure.
   llvm::FoldingSetNodeID ID;
-  ReferenceType::Profile(ID, T);
+  ReferenceType::Profile(ID, T, SpelledAsLValue);
 
   void *InsertPos = 0;
   if (LValueReferenceType *RT =
         LValueReferenceTypes.FindNodeOrInsertPos(ID, InsertPos))
     return QualType(RT, 0);
 
+  const ReferenceType *InnerRef = T->getAs<ReferenceType>();
+
   // If the referencee 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 = getLValueReferenceType(getCanonicalType(T));
+  if (!SpelledAsLValue || InnerRef || !T.isCanonical()) {
+    QualType PointeeType = (InnerRef ? InnerRef->getPointeeType() : T);
+    Canonical = getLValueReferenceType(getCanonicalType(PointeeType));
 
     // Get the new insert position for the node we care about.
     LValueReferenceType *NewIP =
@@ -1259,9 +1258,11 @@
   }
 
   LValueReferenceType *New
-    = new (*this, TypeAlignment) LValueReferenceType(T, Canonical);
+    = new (*this, TypeAlignment) LValueReferenceType(T, Canonical,
+                                                     SpelledAsLValue);
   Types.push_back(New);
   LValueReferenceTypes.InsertNode(New, InsertPos);
+
   return QualType(New, 0);
 }
 
@@ -1271,18 +1272,21 @@
   // Unique pointers, to guarantee there is only one pointer of a particular
   // structure.
   llvm::FoldingSetNodeID ID;
-  ReferenceType::Profile(ID, T);
+  ReferenceType::Profile(ID, T, false);
 
   void *InsertPos = 0;
   if (RValueReferenceType *RT =
         RValueReferenceTypes.FindNodeOrInsertPos(ID, InsertPos))
     return QualType(RT, 0);
 
+  const ReferenceType *InnerRef = T->getAs<ReferenceType>();
+
   // If the referencee 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 = getRValueReferenceType(getCanonicalType(T));
+  if (InnerRef || !T.isCanonical()) {
+    QualType PointeeType = (InnerRef ? InnerRef->getPointeeType() : T);
+    Canonical = getRValueReferenceType(getCanonicalType(PointeeType));
 
     // Get the new insert position for the node we care about.
     RValueReferenceType *NewIP =
@@ -1603,12 +1607,6 @@
                                      unsigned TypeQuals, bool hasExceptionSpec,
                                      bool hasAnyExceptionSpec, unsigned NumExs,
                                      const QualType *ExArray, bool NoReturn) {
-  if (LangOpts.CPlusPlus) {
-    for (unsigned i = 0; i != NumArgs; ++i)
-      assert(!ArgArray[i].hasQualifiers() && 
-             "C++ arguments can't have toplevel qualifiers!");
-  }
-  
   // Unique functions, to guarantee there is only one function of a particular
   // structure.
   llvm::FoldingSetNodeID ID;
@@ -1622,11 +1620,9 @@
     return QualType(FTP, 0);
 
   // Determine whether the type being created is already canonical or not.
-  bool isCanonical = ResultTy.isCanonical();
-  if (hasExceptionSpec)
-    isCanonical = false;
+  bool isCanonical = !hasExceptionSpec && ResultTy.isCanonical();
   for (unsigned i = 0; i != NumArgs && isCanonical; ++i)
-    if (!ArgArray[i].isCanonical())
+    if (!ArgArray[i].isCanonicalAsParam())
       isCanonical = false;
 
   // If this type isn't canonical, get the canonical version of it.
@@ -1636,7 +1632,7 @@
     llvm::SmallVector<QualType, 16> CanonicalArgs;
     CanonicalArgs.reserve(NumArgs);
     for (unsigned i = 0; i != NumArgs; ++i)
-      CanonicalArgs.push_back(getCanonicalType(ArgArray[i]));
+      CanonicalArgs.push_back(getCanonicalParamType(ArgArray[i]));
 
     Canonical = getFunctionType(getCanonicalType(ResultTy),
                                 CanonicalArgs.data(), NumArgs,
@@ -1920,7 +1916,17 @@
   return LHS->getDeclName() < RHS->getDeclName();
 }
 
-static void SortAndUniqueProtocols(ObjCProtocolDecl **&Protocols,
+static bool areSortedAndUniqued(ObjCProtocolDecl **Protocols,
+                                unsigned NumProtocols) {
+  if (NumProtocols == 0) return true;
+
+  for (unsigned i = 1; i != NumProtocols; ++i)
+    if (!CmpProtocolNames(Protocols[i-1], Protocols[i]))
+      return false;
+  return true;
+}
+
+static void SortAndUniqueProtocols(ObjCProtocolDecl **Protocols,
                                    unsigned &NumProtocols) {
   ObjCProtocolDecl **ProtocolsEnd = Protocols+NumProtocols;
 
@@ -1937,10 +1943,6 @@
 QualType ASTContext::getObjCObjectPointerType(QualType InterfaceT,
                                               ObjCProtocolDecl **Protocols,
                                               unsigned NumProtocols) {
-  // Sort the protocol list alphabetically to canonicalize it.
-  if (NumProtocols)
-    SortAndUniqueProtocols(Protocols, NumProtocols);
-
   llvm::FoldingSetNodeID ID;
   ObjCObjectPointerType::Profile(ID, InterfaceT, Protocols, NumProtocols);
 
@@ -1949,9 +1951,31 @@
               ObjCObjectPointerTypes.FindNodeOrInsertPos(ID, InsertPos))
     return QualType(QT, 0);
 
+  // Sort the protocol list alphabetically to canonicalize it.
+  QualType Canonical;
+  if (!InterfaceT.isCanonical() || 
+      !areSortedAndUniqued(Protocols, NumProtocols)) {
+    if (!areSortedAndUniqued(Protocols, NumProtocols)) {
+      llvm::SmallVector<ObjCProtocolDecl*, 8> Sorted(NumProtocols);
+      unsigned UniqueCount = NumProtocols;
+
+      std::copy(Protocols, Protocols + NumProtocols, Sorted.begin());
+      SortAndUniqueProtocols(&Sorted[0], UniqueCount);
+
+      Canonical = getObjCObjectPointerType(getCanonicalType(InterfaceT),
+                                           &Sorted[0], UniqueCount);
+    } else {
+      Canonical = getObjCObjectPointerType(getCanonicalType(InterfaceT),
+                                           Protocols, NumProtocols);
+    }
+
+    // Regenerate InsertPos.
+    ObjCObjectPointerTypes.FindNodeOrInsertPos(ID, InsertPos);
+  }
+
   // No Match;
   ObjCObjectPointerType *QType = new (*this, TypeAlignment)
-    ObjCObjectPointerType(InterfaceT, Protocols, NumProtocols);
+    ObjCObjectPointerType(Canonical, InterfaceT, Protocols, NumProtocols);
 
   Types.push_back(QType);
   ObjCObjectPointerTypes.InsertNode(QType, InsertPos);
@@ -1962,10 +1986,6 @@
 /// specified ObjC interface decl. The list of protocols is optional.
 QualType ASTContext::getObjCInterfaceType(const ObjCInterfaceDecl *Decl,
                        ObjCProtocolDecl **Protocols, unsigned NumProtocols) {
-  if (NumProtocols)
-    // Sort the protocol list alphabetically to canonicalize it.
-    SortAndUniqueProtocols(Protocols, NumProtocols);
-
   llvm::FoldingSetNodeID ID;
   ObjCInterfaceType::Profile(ID, Decl, Protocols, NumProtocols);
 
@@ -1974,31 +1994,26 @@
       ObjCInterfaceTypes.FindNodeOrInsertPos(ID, InsertPos))
     return QualType(QT, 0);
 
-  // No Match;
-  ObjCInterfaceType *QType = new (*this, TypeAlignment)
-    ObjCInterfaceType(const_cast<ObjCInterfaceDecl*>(Decl),
-                      Protocols, NumProtocols);
-  Types.push_back(QType);
-  ObjCInterfaceTypes.InsertNode(QType, InsertPos);
-  return QualType(QType, 0);
-}
+  // Sort the protocol list alphabetically to canonicalize it.
+  QualType Canonical;
+  if (NumProtocols && !areSortedAndUniqued(Protocols, NumProtocols)) {
+    llvm::SmallVector<ObjCProtocolDecl*, 8> Sorted(NumProtocols);
+    std::copy(Protocols, Protocols + NumProtocols, Sorted.begin());
 
-QualType ASTContext::getObjCProtocolListType(QualType T,
-                                             ObjCProtocolDecl **Protocols,
-                                             unsigned NumProtocols) {
-  llvm::FoldingSetNodeID ID;
-  ObjCProtocolListType::Profile(ID, T, Protocols, NumProtocols);
+    unsigned UniqueCount = NumProtocols;
+    SortAndUniqueProtocols(&Sorted[0], UniqueCount);
 
-  void *InsertPos = 0;
-  if (ObjCProtocolListType *QT =
-      ObjCProtocolListTypes.FindNodeOrInsertPos(ID, InsertPos))
-    return QualType(QT, 0);
+    Canonical = getObjCInterfaceType(Decl, &Sorted[0], UniqueCount);
+
+    ObjCInterfaceTypes.FindNodeOrInsertPos(ID, InsertPos);
+  }
+
+  ObjCInterfaceType *QType = new (*this, TypeAlignment)
+    ObjCInterfaceType(Canonical, const_cast<ObjCInterfaceDecl*>(Decl),
+                      Protocols, NumProtocols);
 
-  // No Match;
-  ObjCProtocolListType *QType = new (*this, TypeAlignment)
-    ObjCProtocolListType(T, Protocols, NumProtocols);
   Types.push_back(QType);
-  ObjCProtocolListTypes.InsertNode(QType, InsertPos);
+  ObjCInterfaceTypes.InsertNode(QType, InsertPos);
   return QualType(QType, 0);
 }
 
@@ -2155,6 +2170,24 @@
 //                              Type Operators
 //===----------------------------------------------------------------------===//
 
+CanQualType ASTContext::getCanonicalParamType(QualType T) {
+  // Push qualifiers into arrays, and then discard any remaining
+  // qualifiers.
+  T = getCanonicalType(T);
+  const Type *Ty = T.getTypePtr();
+
+  QualType Result;
+  if (isa<ArrayType>(Ty)) {
+    Result = getArrayDecayedType(QualType(Ty,0));
+  } else if (isa<FunctionType>(Ty)) {
+    Result = getPointerType(QualType(Ty, 0));
+  } else {
+    Result = QualType(Ty, 0);
+  }
+
+  return CanQualType::CreateUnsafe(Result);
+}
+
 /// getCanonicalType - Return the canonical (structural) type corresponding to
 /// the specified potentially non-canonical type.  The non-canonical version
 /// of a type may have many "decorated" versions of types.  Decorators can

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

==============================================================================
--- cfe/trunk/lib/AST/Type.cpp (original)
+++ cfe/trunk/lib/AST/Type.cpp Thu Oct 22 17:37:11 2009
@@ -724,18 +724,6 @@
     Profile(ID, getPointeeType(), 0, 0);
 }
 
-void ObjCProtocolListType::Profile(llvm::FoldingSetNodeID &ID,
-                                   QualType OIT, ObjCProtocolDecl **protocols,
-                                   unsigned NumProtocols) {
-  ID.AddPointer(OIT.getAsOpaquePtr());
-  for (unsigned i = 0; i != NumProtocols; i++)
-    ID.AddPointer(protocols[i]);
-}
-
-void ObjCProtocolListType::Profile(llvm::FoldingSetNodeID &ID) {
-    Profile(ID, getBaseType(), &Protocols[0], getNumProtocols());
-}
-
 /// LookThroughTypedefs - Return the ultimate type this typedef corresponds to
 /// potentially looking through *all* consequtive typedefs.  This returns the
 /// sum of the type qualifiers, so if you have:
@@ -1059,10 +1047,10 @@
 
   // Handle things like 'int (&A)[4];' correctly.
   // FIXME: this should include vectors, but vectors use attributes I guess.
-  if (isa<ArrayType>(getPointeeType()))
+  if (isa<ArrayType>(getPointeeTypeAsWritten()))
     S = '(' + S + ')';
 
-  getPointeeType().getAsStringInternal(S, Policy);
+  getPointeeTypeAsWritten().getAsStringInternal(S, Policy);
 }
 
 void RValueReferenceType::getAsStringInternal(std::string &S, const PrintingPolicy &Policy) const {
@@ -1070,10 +1058,10 @@
 
   // Handle things like 'int (&&A)[4];' correctly.
   // FIXME: this should include vectors, but vectors use attributes I guess.
-  if (isa<ArrayType>(getPointeeType()))
+  if (isa<ArrayType>(getPointeeTypeAsWritten()))
     S = '(' + S + ')';
 
-  getPointeeType().getAsStringInternal(S, Policy);
+  getPointeeTypeAsWritten().getAsStringInternal(S, Policy);
 }
 
 void MemberPointerType::getAsStringInternal(std::string &S, const PrintingPolicy &Policy) const {
@@ -1463,25 +1451,6 @@
   InnerString = ObjCQIString + InnerString;
 }
 
-void ObjCProtocolListType::getAsStringInternal(std::string &InnerString,
-                                           const PrintingPolicy &Policy) const {
-  if (!InnerString.empty())    // Prefix the basic type, e.g. 'typedefname X'.
-    InnerString = ' ' + InnerString;
-
-  std::string ObjCQIString = getBaseType().getAsString(Policy);
-  ObjCQIString += '<';
-  bool isFirst = true;
-  for (qual_iterator I = qual_begin(), E = qual_end(); I != E; ++I) {
-    if (isFirst)
-      isFirst = false;
-    else
-      ObjCQIString += ',';
-    ObjCQIString += (*I)->getNameAsString();
-  }
-  ObjCQIString += '>';
-  InnerString = ObjCQIString + InnerString;
-}
-
 void ElaboratedType::getAsStringInternal(std::string &InnerString,
                                          const PrintingPolicy &Policy) const {
   std::string TypeStr;

Modified: cfe/trunk/lib/CodeGen/Mangle.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/Mangle.cpp?rev=84907&r1=84906&r2=84907&view=diff

==============================================================================
--- cfe/trunk/lib/CodeGen/Mangle.cpp (original)
+++ cfe/trunk/lib/CodeGen/Mangle.cpp Thu Oct 22 17:37:11 2009
@@ -248,7 +248,12 @@
     FD = PrimaryTemplate->getTemplatedDecl();
   }
 
-  mangleBareFunctionType(FD->getType()->getAs<FunctionType>(), MangleReturnType);
+  // Do the canonicalization out here because parameter types can
+  // undergo additional canonicalization (e.g. array decay).
+  FunctionType *FT = cast<FunctionType>(Context.getASTContext()
+                                          .getCanonicalType(FD->getType()));
+
+  mangleBareFunctionType(FT, MangleReturnType);
 }
 
 static bool isStdNamespace(const DeclContext *DC) {

Modified: cfe/trunk/lib/Frontend/PCHReader.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Frontend/PCHReader.cpp?rev=84907&r1=84906&r2=84907&view=diff

==============================================================================
--- cfe/trunk/lib/Frontend/PCHReader.cpp (original)
+++ cfe/trunk/lib/Frontend/PCHReader.cpp Thu Oct 22 17:37:11 2009
@@ -1964,16 +1964,6 @@
     return Context->getObjCObjectPointerType(OIT, Protos.data(), NumProtos);
   }
 
-  case pch::TYPE_OBJC_PROTOCOL_LIST: {
-    unsigned Idx = 0;
-    QualType OIT = GetType(Record[Idx++]);
-    unsigned NumProtos = Record[Idx++];
-    llvm::SmallVector<ObjCProtocolDecl*, 4> Protos;
-    for (unsigned I = 0; I != NumProtos; ++I)
-      Protos.push_back(cast<ObjCProtocolDecl>(GetDecl(Record[Idx++])));
-    return Context->getObjCProtocolListType(OIT, Protos.data(), NumProtos);
-  }
-
   case pch::TYPE_SUBST_TEMPLATE_TYPE_PARM: {
     unsigned Idx = 0;
     QualType Parm = GetType(Record[Idx++]);
@@ -2124,15 +2114,20 @@
 }
 void TypeLocReader::VisitObjCInterfaceTypeLoc(ObjCInterfaceTypeLoc TL) {
   TL.setNameLoc(SourceLocation::getFromRawEncoding(Record[Idx++]));
+  TL.setLAngleLoc(SourceLocation::getFromRawEncoding(Record[Idx++]));
+  TL.setRAngleLoc(SourceLocation::getFromRawEncoding(Record[Idx++]));
+  for (unsigned i = 0, e = TL.getNumProtocols(); i != e; ++i)
+    TL.setProtocolLoc(i, SourceLocation::getFromRawEncoding(Record[Idx++]));
 }
 void TypeLocReader::VisitObjCObjectPointerTypeLoc(ObjCObjectPointerTypeLoc TL) {
   TL.setStarLoc(SourceLocation::getFromRawEncoding(Record[Idx++]));
-}
-void TypeLocReader::VisitObjCProtocolListTypeLoc(ObjCProtocolListTypeLoc TL) {
   TL.setLAngleLoc(SourceLocation::getFromRawEncoding(Record[Idx++]));
   TL.setRAngleLoc(SourceLocation::getFromRawEncoding(Record[Idx++]));
-  for (unsigned i = 0, e = TL.getNumProtocols(); i != e; ++i)
-    TL.setProtocolLoc(i, SourceLocation::getFromRawEncoding(Record[Idx++]));
+  TL.setHasBaseTypeAsWritten(Record[Idx++]);
+  TL.setHasProtocolsAsWritten(Record[Idx++]);
+  if (TL.hasProtocolsAsWritten())
+    for (unsigned i = 0, e = TL.getNumProtocols(); i != e; ++i)
+      TL.setProtocolLoc(i, SourceLocation::getFromRawEncoding(Record[Idx++]));
 }
 
 DeclaratorInfo *PCHReader::GetDeclaratorInfo(const RecordData &Record,

Modified: cfe/trunk/lib/Frontend/PCHWriter.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Frontend/PCHWriter.cpp?rev=84907&r1=84906&r2=84907&view=diff

==============================================================================
--- cfe/trunk/lib/Frontend/PCHWriter.cpp (original)
+++ cfe/trunk/lib/Frontend/PCHWriter.cpp Thu Oct 22 17:37:11 2009
@@ -248,15 +248,6 @@
   Code = pch::TYPE_OBJC_OBJECT_POINTER;
 }
 
-void PCHTypeWriter::VisitObjCProtocolListType(const ObjCProtocolListType *T) {
-  Writer.AddTypeRef(T->getBaseType(), Record);
-  Record.push_back(T->getNumProtocols());
-  for (ObjCProtocolListType::qual_iterator I = T->qual_begin(),
-       E = T->qual_end(); I != E; ++I)
-    Writer.AddDeclRef(*I, Record);
-  Code = pch::TYPE_OBJC_PROTOCOL_LIST;
-}
-
 namespace {
 
 class TypeLocWriter : public TypeLocVisitor<TypeLocWriter> {
@@ -387,15 +378,20 @@
 }
 void TypeLocWriter::VisitObjCInterfaceTypeLoc(ObjCInterfaceTypeLoc TL) {
   Writer.AddSourceLocation(TL.getNameLoc(), Record);
+  Writer.AddSourceLocation(TL.getLAngleLoc(), Record);
+  Writer.AddSourceLocation(TL.getRAngleLoc(), Record);
+  for (unsigned i = 0, e = TL.getNumProtocols(); i != e; ++i)
+    Writer.AddSourceLocation(TL.getProtocolLoc(i), Record);
 }
 void TypeLocWriter::VisitObjCObjectPointerTypeLoc(ObjCObjectPointerTypeLoc TL) {
   Writer.AddSourceLocation(TL.getStarLoc(), Record);
-}
-void TypeLocWriter::VisitObjCProtocolListTypeLoc(ObjCProtocolListTypeLoc TL) {
   Writer.AddSourceLocation(TL.getLAngleLoc(), Record);
   Writer.AddSourceLocation(TL.getRAngleLoc(), Record);
-  for (unsigned i = 0, e = TL.getNumProtocols(); i != e; ++i)
-    Writer.AddSourceLocation(TL.getProtocolLoc(i), Record);
+  Record.push_back(TL.hasBaseTypeAsWritten());
+  Record.push_back(TL.hasProtocolsAsWritten());
+  if (TL.hasProtocolsAsWritten())
+    for (unsigned i = 0, e = TL.getNumProtocols(); i != e; ++i)
+      Writer.AddSourceLocation(TL.getProtocolLoc(i), Record);
 }
 
 //===----------------------------------------------------------------------===//
@@ -569,7 +565,6 @@
   RECORD(TYPE_ENUM);
   RECORD(TYPE_OBJC_INTERFACE);
   RECORD(TYPE_OBJC_OBJECT_POINTER);
-  RECORD(TYPE_OBJC_PROTOCOL_LIST);
   RECORD(DECL_ATTR);
   RECORD(DECL_TRANSLATION_UNIT);
   RECORD(DECL_TYPEDEF);

Modified: cfe/trunk/lib/Index/ResolveLocation.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Index/ResolveLocation.cpp?rev=84907&r1=84906&r2=84907&view=diff

==============================================================================
--- cfe/trunk/lib/Index/ResolveLocation.cpp (original)
+++ cfe/trunk/lib/Index/ResolveLocation.cpp Thu Oct 22 17:37:11 2009
@@ -120,11 +120,12 @@
   TypeLocResolver(ASTContext &ctx, SourceLocation loc, Decl *pd)
     : LocResolverBase(ctx, loc), ParentDecl(pd) { }
 
+  ASTLocation VisitBuiltinTypeLoc(BuiltinTypeLoc TL);
   ASTLocation VisitTypedefTypeLoc(TypedefTypeLoc TL);
   ASTLocation VisitFunctionTypeLoc(FunctionTypeLoc TL);
   ASTLocation VisitArrayTypeLoc(ArrayTypeLoc TL);
   ASTLocation VisitObjCInterfaceTypeLoc(ObjCInterfaceTypeLoc TL);
-  ASTLocation VisitObjCProtocolListTypeLoc(ObjCProtocolListTypeLoc TL);
+  ASTLocation VisitObjCObjectPointerTypeLoc(ObjCObjectPointerTypeLoc TL);
   ASTLocation VisitTypeLoc(TypeLoc TL);
 };
 
@@ -349,6 +350,24 @@
   return ASTLocation(D);
 }
 
+ASTLocation TypeLocResolver::VisitBuiltinTypeLoc(BuiltinTypeLoc TL) {
+  // Continue the 'id' magic by making the builtin type (which cannot
+  // actually be spelled) map to the typedef.
+  BuiltinType *T = TL.getTypePtr();
+  if (T->getKind() == BuiltinType::ObjCId) {
+    TypedefDecl *D = Ctx.getObjCIdType()->getAs<TypedefType>()->getDecl();
+    return ASTLocation(ParentDecl, D, TL.getNameLoc());
+  }
+
+  // Same thing with 'Class'.
+  if (T->getKind() == BuiltinType::ObjCClass) {
+    TypedefDecl *D = Ctx.getObjCClassType()->getAs<TypedefType>()->getDecl();
+    return ASTLocation(ParentDecl, D, TL.getNameLoc());
+  }
+
+  return ASTLocation(ParentDecl, TL);
+}
+
 ASTLocation TypeLocResolver::VisitTypedefTypeLoc(TypedefTypeLoc TL) {
   assert(ContainsLocation(TL) &&
          "Should visit only after verifying that loc is in range");
@@ -389,12 +408,6 @@
          "Should visit only after verifying that loc is in range");
   if (ContainsLocation(TL.getNameLoc()))
     return ASTLocation(ParentDecl, TL.getIFaceDecl(), TL.getNameLoc());
-  return ASTLocation(ParentDecl, TL);
-}
-
-ASTLocation TypeLocResolver::VisitObjCProtocolListTypeLoc(ObjCProtocolListTypeLoc TL) {
-  assert(ContainsLocation(TL) &&
-         "Should visit only after verifying that loc is in range");
 
   for (unsigned i = 0; i != TL.getNumProtocols(); ++i) {
     SourceLocation L = TL.getProtocolLoc(i);
@@ -408,6 +421,24 @@
   return ASTLocation(ParentDecl, TL);
 }
 
+ASTLocation TypeLocResolver::VisitObjCObjectPointerTypeLoc(ObjCObjectPointerTypeLoc TL) {
+  assert(ContainsLocation(TL) &&
+         "Should visit only after verifying that loc is in range");
+
+  if (TL.hasProtocolsAsWritten()) {
+    for (unsigned i = 0; i != TL.getNumProtocols(); ++i) {
+      SourceLocation L = TL.getProtocolLoc(i);
+      RangePos RP = CheckRange(L);
+      if (RP == AfterLoc)
+        break;
+      if (RP == ContainsLoc)
+        return ASTLocation(ParentDecl, TL.getProtocol(i), L);
+    }
+  }
+
+  return ASTLocation(ParentDecl, TL);
+}
+
 ASTLocation TypeLocResolver::VisitTypeLoc(TypeLoc TL) {
   assert(ContainsLocation(TL) &&
          "Should visit only after verifying that loc is in range");

Modified: cfe/trunk/lib/Sema/Sema.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/Sema.h?rev=84907&r1=84906&r2=84907&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/Sema.h (original)
+++ cfe/trunk/lib/Sema/Sema.h Thu Oct 22 17:37:11 2009
@@ -448,7 +448,7 @@
   //
   QualType adjustParameterType(QualType T);
   QualType ConvertDeclSpecToType(const DeclSpec &DS, SourceLocation DeclLoc,
-                                 bool &IsInvalid, QualType &SourceTy);
+                                 bool &IsInvalid);
   void ProcessTypeAttributeList(QualType &Result, const AttributeList *AL);
   QualType BuildPointerType(QualType T, unsigned Quals,
                             SourceLocation Loc, DeclarationName Entity);
@@ -3755,22 +3755,6 @@
                       QualType FieldTy, const Expr *BitWidth,
                       bool *ZeroWidth = 0);
 
-  /// adjustFunctionParamType - Converts the type of a function parameter to a
-  // type that can be passed as an argument type to
-  /// ASTContext::getFunctionType.
-  ///
-  /// C++ [dcl.fct]p3: "...Any cv-qualifier modifying a parameter type is
-  /// deleted. Such cv-qualifiers affect only the definition of the parameter 
-  /// within the body of the function; they do not affect the function type. 
-  QualType adjustFunctionParamType(QualType T) const {
-    if (!Context.getLangOptions().CPlusPlus)
-      return T;
-    return 
-      T->isDependentType() ? T.getUnqualifiedType()
-                            : T.getDesugaredType().getUnqualifiedType();
-    
-  }
-
   /// \name Code completion
   //@{
   void setCodeCompleteConsumer(CodeCompleteConsumer *CCC);

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

==============================================================================
--- cfe/trunk/lib/Sema/SemaDeclCXX.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDeclCXX.cpp Thu Oct 22 17:37:11 2009
@@ -4281,8 +4281,7 @@
   // friend templates because ActOnTag never produces a ClassTemplateDecl
   // for a TUK_Friend.
   bool invalid = false;
-  QualType SourceTy;
-  QualType T = ConvertDeclSpecToType(DS, Loc, invalid, SourceTy);
+  QualType T = ConvertDeclSpecToType(DS, Loc, invalid);
   if (invalid) return DeclPtrTy();
 
   // This is definitely an error in C++98.  It's probably meant to

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

==============================================================================
--- cfe/trunk/lib/Sema/SemaType.cpp (original)
+++ cfe/trunk/lib/Sema/SemaType.cpp Thu Oct 22 17:37:11 2009
@@ -52,16 +52,14 @@
 /// object.
 /// \param DS  the declaration specifiers
 /// \param DeclLoc The location of the declarator identifier or invalid if none.
-/// \param SourceTy QualType representing the type as written in source form.
 /// \returns The type described by the declaration specifiers.  This function
 /// never returns null.
 QualType Sema::ConvertDeclSpecToType(const DeclSpec &DS,
                                      SourceLocation DeclLoc,
-                                     bool &isInvalid, QualType &SourceTy) {
+                                     bool &isInvalid) {
   // FIXME: Should move the logic from DeclSpec::Finish to here for validity
   // checking.
   QualType Result;
-  SourceTy = Result;
 
   switch (DS.getTypeSpecType()) {
   case DeclSpec::TST_void:
@@ -106,9 +104,6 @@
   case DeclSpec::TST_unspecified:
     // "<proto1,proto2>" is an objc qualified ID with a missing id.
     if (DeclSpec::ProtocolQualifierListTy PQ = DS.getProtocolQualifiers()) {
-      SourceTy = Context.getObjCProtocolListType(QualType(),
-                                                 (ObjCProtocolDecl**)PQ,
-                                                 DS.getNumProtocolQualifiers());
       Result = Context.getObjCObjectPointerType(Context.ObjCBuiltinIdTy,
                                                 (ObjCProtocolDecl**)PQ,
                                                 DS.getNumProtocolQualifiers());
@@ -226,9 +221,6 @@
     Result = GetTypeFromParser(DS.getTypeRep());
 
     if (DeclSpec::ProtocolQualifierListTy PQ = DS.getProtocolQualifiers()) {
-      SourceTy = Context.getObjCProtocolListType(Result,
-                                                 (ObjCProtocolDecl**)PQ,
-                                                 DS.getNumProtocolQualifiers());
       if (const ObjCInterfaceType *
             Interface = Result->getAs<ObjCInterfaceType>()) {
         // It would be nice if protocol qualifiers were only stored with the
@@ -385,8 +377,6 @@
     Result = Context.getQualifiedType(Result, Quals);
   }
 
-  if (SourceTy.isNull())
-    SourceTy = Result;
   return Result;
 }
 
@@ -450,36 +440,32 @@
 ///
 /// \returns A suitable reference type, if there are no
 /// errors. Otherwise, returns a NULL type.
-QualType Sema::BuildReferenceType(QualType T, bool LValueRef, unsigned CVR,
-                                  SourceLocation Loc, DeclarationName Entity) {
+QualType Sema::BuildReferenceType(QualType T, bool SpelledAsLValue,
+                                  unsigned CVR, SourceLocation Loc,
+                                  DeclarationName Entity) {
   Qualifiers Quals = Qualifiers::fromCVRMask(CVR);
-  if (LValueRef) {
-    if (const RValueReferenceType *R = T->getAs<RValueReferenceType>()) {
-      // C++0x [dcl.typedef]p9: If a typedef TD names a type that is a
-      //   reference to a type T, and attempt to create the type "lvalue
-      //   reference to cv TD" creates the type "lvalue reference to T".
-      // We use the qualifiers (restrict or none) of the original reference,
-      // not the new ones. This is consistent with GCC.
-      QualType LVRT = Context.getLValueReferenceType(R->getPointeeType());
-      return Context.getQualifiedType(LVRT, T.getQualifiers());
-    }
-  }
-  if (T->isReferenceType()) {
-    // C++ [dcl.ref]p4: There shall be no references to references.
-    //
-    // According to C++ DR 106, references to references are only
-    // diagnosed when they are written directly (e.g., "int & &"),
-    // but not when they happen via a typedef:
-    //
-    //   typedef int& intref;
-    //   typedef intref& intref2;
-    //
-    // Parser::ParseDeclaratorInternal diagnoses the case where
-    // references are written directly; here, we handle the
-    // collapsing of references-to-references as described in C++
-    // DR 106 and amended by C++ DR 540.
-    return T;
-  }
+
+  bool LValueRef = SpelledAsLValue || T->getAs<LValueReferenceType>();
+
+  // C++0x [dcl.typedef]p9: If a typedef TD names a type that is a
+  //   reference to a type T, and attempt to create the type "lvalue
+  //   reference to cv TD" creates the type "lvalue reference to T".
+  // We use the qualifiers (restrict or none) of the original reference,
+  // not the new ones. This is consistent with GCC.
+
+  // C++ [dcl.ref]p4: There shall be no references to references.
+  //
+  // According to C++ DR 106, references to references are only
+  // diagnosed when they are written directly (e.g., "int & &"),
+  // but not when they happen via a typedef:
+  //
+  //   typedef int& intref;
+  //   typedef intref& intref2;
+  //
+  // Parser::ParseDeclaratorInternal diagnoses the case where
+  // references are written directly; here, we handle the
+  // collapsing of references-to-references as described in C++
+  // DR 106 and amended by C++ DR 540.
 
   // C++ [dcl.ref]p1:
   //   A declarator that specifies the type "reference to cv void"
@@ -511,7 +497,8 @@
 
   // Handle restrict on references.
   if (LValueRef)
-    return Context.getQualifiedType(Context.getLValueReferenceType(T), Quals);
+    return Context.getQualifiedType(
+               Context.getLValueReferenceType(T, SpelledAsLValue), Quals);
   return Context.getQualifiedType(Context.getRValueReferenceType(T), Quals);
 }
 
@@ -717,7 +704,7 @@
       Invalid = true;
     }
 
-    ParamTypes[Idx] = adjustFunctionParamType(ParamType);
+    ParamTypes[Idx] = ParamType;
   }
 
   if (Invalid)
@@ -856,9 +843,6 @@
   // Determine the type of the declarator. Not all forms of declarator
   // have a type.
   QualType T;
-  // The QualType referring to the type as written in source code. We can't use
-  // T because it can change due to semantic analysis.
-  QualType SourceTy;
 
   switch (D.getKind()) {
   case Declarator::DK_Abstract:
@@ -872,7 +856,7 @@
       T = Context.DependentTy;
     } else {
       bool isInvalid = false;
-      T = ConvertDeclSpecToType(DS, D.getIdentifierLoc(), isInvalid, SourceTy);
+      T = ConvertDeclSpecToType(DS, D.getIdentifierLoc(), isInvalid);
       if (isInvalid)
         D.setInvalidType(true);
       else if (OwnedDecl && DS.isTypeSpecOwned())
@@ -891,9 +875,6 @@
     break;
   }
   
-  if (SourceTy.isNull())
-    SourceTy = T;
-
   if (T == Context.UndeducedAutoTy) {
     int Error = -1;
 
@@ -942,8 +923,6 @@
   if (D.getIdentifier())
     Name = D.getIdentifier();
 
-  bool ShouldBuildInfo = DInfo != 0;
-
   // Walk the DeclTypeInfo, building the recursive type as we go.
   // DeclTypeInfos are ordered from the identifier out, which is
   // opposite of what we want :).
@@ -952,17 +931,6 @@
     switch (DeclType.Kind) {
     default: assert(0 && "Unknown decltype!");
     case DeclaratorChunk::BlockPointer:
-      if (ShouldBuildInfo) {
-        if (SourceTy->isFunctionType())
-          SourceTy
-            = Context.getQualifiedType(Context.getBlockPointerType(SourceTy),
-                             Qualifiers::fromCVRMask(DeclType.Cls.TypeQuals));
-        else
-          // If not function type Context::getBlockPointerType asserts,
-          // so just give up.
-          ShouldBuildInfo = false;
-      }
-
       // If blocks are disabled, emit an error.
       if (!LangOpts.Blocks)
         Diag(DeclType.Loc, diag::err_blocks_disable);
@@ -971,10 +939,6 @@
                                 Name);
       break;
     case DeclaratorChunk::Pointer:
-      //FIXME: Use ObjCObjectPointer for info when appropriate.
-      if (ShouldBuildInfo)
-        SourceTy = Context.getQualifiedType(Context.getPointerType(SourceTy),
-                             Qualifiers::fromCVRMask(DeclType.Ptr.TypeQuals));
       // Verify that we're not building a pointer to pointer to function with
       // exception specification.
       if (getLangOptions().CPlusPlus && CheckDistantExceptionSpec(T)) {
@@ -995,14 +959,6 @@
       Qualifiers Quals;
       if (DeclType.Ref.HasRestrict) Quals.addRestrict();
 
-      if (ShouldBuildInfo) {
-        if (DeclType.Ref.LValueRef)
-          SourceTy = Context.getLValueReferenceType(SourceTy);
-        else
-          SourceTy = Context.getRValueReferenceType(SourceTy);
-        SourceTy = Context.getQualifiedType(SourceTy, Quals);
-      }
-
       // Verify that we're not building a reference to pointer to function with
       // exception specification.
       if (getLangOptions().CPlusPlus && CheckDistantExceptionSpec(T)) {
@@ -1015,11 +971,6 @@
       break;
     }
     case DeclaratorChunk::Array: {
-      if (ShouldBuildInfo)
-        // We just need to get an array type, the exact type doesn't matter.
-        SourceTy = Context.getIncompleteArrayType(SourceTy, ArrayType::Normal,
-                                                  DeclType.Arr.TypeQuals);
-
       // Verify that we're not building an array of pointers to function with
       // exception specification.
       if (getLangOptions().CPlusPlus && CheckDistantExceptionSpec(T)) {
@@ -1051,24 +1002,6 @@
       break;
     }
     case DeclaratorChunk::Function: {
-      if (ShouldBuildInfo) {
-        const DeclaratorChunk::FunctionTypeInfo &FTI = DeclType.Fun;
-        llvm::SmallVector<QualType, 16> ArgTys;
-
-        for (unsigned i = 0, e = FTI.NumArgs; i != e; ++i) {
-          ParmVarDecl *Param = FTI.ArgInfo[i].Param.getAs<ParmVarDecl>();
-          if (Param) {
-            QualType ArgTy = adjustFunctionParamType(Param->getType());
-
-            ArgTys.push_back(ArgTy);
-          }
-        }
-        SourceTy = Context.getFunctionType(SourceTy, ArgTys.data(),
-                                           ArgTys.size(),
-                                           FTI.isVariadic,
-                                           FTI.TypeQuals);
-      }
-
       // If the function declarator has a prototype (i.e. it is not () and
       // does not have a K&R-style identifier list), then the arguments are part
       // of the type, otherwise the argument list is ().
@@ -1137,6 +1070,7 @@
       } else if (FTI.ArgInfo[0].Param == 0) {
         // C99 6.7.5.3p3: Reject int(x,y,z) when it's not a function definition.
         Diag(FTI.ArgInfo[0].IdentLoc, diag::err_ident_list_in_fn_declaration);
+        D.setInvalidType(true);
       } else {
         // Otherwise, we have a function with an argument list that is
         // potentially variadic.
@@ -1185,7 +1119,7 @@
             }
           }
 
-          ArgTys.push_back(adjustFunctionParamType(ArgTy));
+          ArgTys.push_back(ArgTy);
         }
 
         llvm::SmallVector<QualType, 4> Exceptions;
@@ -1234,13 +1168,6 @@
         D.setInvalidType(true);
       }
 
-      if (ShouldBuildInfo) {
-        QualType cls = !ClsType.isNull() ? ClsType : Context.IntTy;
-        SourceTy = Context.getQualifiedType(
-                      Context.getMemberPointerType(SourceTy, cls.getTypePtr()),
-                      Qualifiers::fromCVRMask(DeclType.Mem.TypeQuals));
-      }
-
       if (!ClsType.isNull())
         T = BuildMemberPointerType(T, ClsType, DeclType.Mem.TypeQuals,
                                    DeclType.Loc, D.getIdentifier());
@@ -1293,8 +1220,12 @@
   if (const AttributeList *Attrs = D.getAttributes())
     ProcessTypeAttributeList(T, Attrs);
 
-  if (ShouldBuildInfo)
-    *DInfo = GetDeclaratorInfoForDeclarator(D, SourceTy, Skip);
+  if (DInfo) {
+    if (D.isInvalidType())
+      *DInfo = 0;
+    else
+      *DInfo = GetDeclaratorInfoForDeclarator(D, T, Skip);
+  }
 
   return T;
 }
@@ -1314,17 +1245,49 @@
     }
     void VisitObjCInterfaceTypeLoc(ObjCInterfaceTypeLoc TL) {
       TL.setNameLoc(DS.getTypeSpecTypeLoc());
+
+      if (DS.getProtocolQualifiers()) {
+        assert(TL.getNumProtocols() > 0);
+        assert(TL.getNumProtocols() == DS.getNumProtocolQualifiers());
+        TL.setLAngleLoc(DS.getProtocolLAngleLoc());
+        TL.setRAngleLoc(DS.getSourceRange().getEnd());
+        for (unsigned i = 0, e = DS.getNumProtocolQualifiers(); i != e; ++i)
+          TL.setProtocolLoc(i, DS.getProtocolLocs()[i]);
+      } else {
+        assert(TL.getNumProtocols() == 0);
+        TL.setLAngleLoc(SourceLocation());
+        TL.setRAngleLoc(SourceLocation());
+      }
     }
-    void VisitObjCProtocolListTypeLoc(ObjCProtocolListTypeLoc TL) {
+    void VisitObjCObjectPointerTypeLoc(ObjCObjectPointerTypeLoc TL) {
       assert(TL.getNumProtocols() == DS.getNumProtocolQualifiers());
-      TL.setLAngleLoc(DS.getProtocolLAngleLoc());
-      TL.setRAngleLoc(DS.getSourceRange().getEnd());
-      for (unsigned i = 0; i != DS.getNumProtocolQualifiers(); ++i)
-        TL.setProtocolLoc(i, DS.getProtocolLocs()[i]);
 
-      TypeLoc BaseLoc = TL.getBaseTypeLoc();
-      if (BaseLoc)
+      TL.setStarLoc(SourceLocation());
+
+      if (DS.getProtocolQualifiers()) {
+        assert(TL.getNumProtocols() > 0);
+        assert(TL.getNumProtocols() == DS.getNumProtocolQualifiers());
+        TL.setHasProtocolsAsWritten(true);
+        TL.setLAngleLoc(DS.getProtocolLAngleLoc());
+        TL.setRAngleLoc(DS.getSourceRange().getEnd());
+        for (unsigned i = 0, e = DS.getNumProtocolQualifiers(); i != e; ++i)
+          TL.setProtocolLoc(i, DS.getProtocolLocs()[i]);
+
+      } else {
+        assert(TL.getNumProtocols() == 0);
+        TL.setHasProtocolsAsWritten(false);
+        TL.setLAngleLoc(SourceLocation());
+        TL.setRAngleLoc(SourceLocation());
+      }
+
+      // This might not have been written with an inner type.
+      if (DS.getTypeSpecType() == DeclSpec::TST_unspecified) {
+        TL.setHasBaseTypeAsWritten(false);
+        TL.getBaseTypeLoc().initialize(SourceLocation());
+      } else {
+        TL.setHasBaseTypeAsWritten(true);
         Visit(TL.getBaseTypeLoc());
+      }
     }
     void VisitTypeLoc(TypeLoc TL) {
       // FIXME: add other typespec types and change this to an assert.
@@ -1353,6 +1316,10 @@
     void VisitObjCObjectPointerTypeLoc(ObjCObjectPointerTypeLoc TL) {
       assert(Chunk.Kind == DeclaratorChunk::Pointer);
       TL.setStarLoc(Chunk.Loc);
+      TL.setHasBaseTypeAsWritten(true);
+      TL.setHasProtocolsAsWritten(false);
+      TL.setLAngleLoc(SourceLocation());
+      TL.setRAngleLoc(SourceLocation());
     }
     void VisitMemberPointerTypeLoc(MemberPointerTypeLoc TL) {
       assert(Chunk.Kind == DeclaratorChunk::MemberPointer);
@@ -1361,7 +1328,8 @@
     }
     void VisitLValueReferenceTypeLoc(LValueReferenceTypeLoc TL) {
       assert(Chunk.Kind == DeclaratorChunk::Reference);
-      assert(Chunk.Ref.LValueRef);
+      // 'Amp' is misleading: this might have been originally
+      /// spelled with AmpAmp.
       TL.setAmpLoc(Chunk.Loc);
     }
     void VisitRValueReferenceTypeLoc(RValueReferenceTypeLoc TL) {
@@ -1381,12 +1349,9 @@
       TL.setRParenLoc(Chunk.EndLoc);
 
       const DeclaratorChunk::FunctionTypeInfo &FTI = Chunk.Fun;
-      for (unsigned i = 0, e = FTI.NumArgs, tpi = 0; i != e; ++i) {
+      for (unsigned i = 0, e = TL.getNumArgs(), tpi = 0; i != e; ++i) {
         ParmVarDecl *Param = FTI.ArgInfo[i].Param.getAs<ParmVarDecl>();
-        if (Param) {
-          assert(tpi < TL.getNumArgs());
-          TL.setArg(tpi++, Param);
-        }
+        TL.setArg(tpi++, Param);
       }
       // FIXME: exception specs
     }

Modified: cfe/trunk/lib/Sema/TreeTransform.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/TreeTransform.h?rev=84907&r1=84906&r2=84907&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/TreeTransform.h (original)
+++ cfe/trunk/lib/Sema/TreeTransform.h Thu Oct 22 17:37:11 2009
@@ -514,14 +514,6 @@
                                   SourceRange(getDerived().getBaseLocation()));
   }
 
-  /// \brief Rebuild an objective C protocol list type.
-  QualType RebuildObjCProtocolListType(QualType BaseType,
-                                       ObjCProtocolDecl **Protocols,
-                                       unsigned NumProtocols) {
-    return SemaRef.Context.getObjCProtocolListType(BaseType, Protocols,
-                                                   NumProtocols);
-  }
-
   /// \brief Build a new nested-name-specifier given the prefix and an
   /// identifier that names the next step in the nested-name-specifier.
   ///
@@ -2808,50 +2800,16 @@
 QualType
 TreeTransform<Derived>::TransformObjCInterfaceType(TypeLocBuilder &TLB,
                                                    ObjCInterfaceTypeLoc TL) {
-  return TransformTypeSpecType(TLB, TL);
+  assert(false && "TransformObjCInterfaceType unimplemented");
+  return QualType();
 }
 
 template<typename Derived>
 QualType
 TreeTransform<Derived>::TransformObjCObjectPointerType(TypeLocBuilder &TLB,
                                                ObjCObjectPointerTypeLoc TL) {
-  TransformPointerLikeType(ObjCObjectPointerType);
-}
-
-template<typename Derived>
-QualType TreeTransform<Derived>::TransformObjCProtocolListType(
-                                                TypeLocBuilder &TLB,
-                                                ObjCProtocolListTypeLoc TL) {
-  ObjCProtocolListType *T = TL.getTypePtr();
-  QualType BaseType = T->getBaseType();
-  if (!BaseType.isNull()) {
-    BaseType = getDerived().TransformType(TLB, TL.getBaseTypeLoc());
-    if (BaseType.isNull())
-      return QualType();
-  } 
-
-  QualType Result = TL.getType();
-  if (getDerived().AlwaysRebuild() ||
-      BaseType != T->getBaseType()) {
-    // TODO: transform these?
-    llvm::SmallVector<ObjCProtocolDecl*,4> Protocols(T->getNumProtocols());
-    std::copy(T->qual_begin(), T->qual_end(), Protocols.begin());
-    Result = getDerived().RebuildObjCProtocolListType(BaseType,
-                                                      &Protocols[0],
-                                                      T->getNumProtocols());
-    if (Result.isNull())
-      return QualType();
-  }
-
-  ObjCProtocolListTypeLoc NewTL = TLB.push<ObjCProtocolListTypeLoc>(Result);
-  NewTL.setLAngleLoc(TL.getLAngleLoc());
-  NewTL.setRAngleLoc(TL.getRAngleLoc());
-
-  assert(NewTL.getNumProtocols() == TL.getNumProtocols());
-  for (unsigned i = 0, e = TL.getNumProtocols(); i != e; ++i)
-    NewTL.setProtocolLoc(i, TL.getProtocolLoc(i));
-
-  return Result;
+  assert(false && "TransformObjCObjectPointerType unimplemented");
+  return QualType();
 }
 
 //===----------------------------------------------------------------------===//

Modified: cfe/trunk/test/SemaCXX/overloaded-operator.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/SemaCXX/overloaded-operator.cpp?rev=84907&r1=84906&r2=84907&view=diff

==============================================================================
--- cfe/trunk/test/SemaCXX/overloaded-operator.cpp (original)
+++ cfe/trunk/test/SemaCXX/overloaded-operator.cpp Thu Oct 22 17:37:11 2009
@@ -155,7 +155,7 @@
 typedef float& Func2(int, double);
 
 struct ConvertToFunc {
-  operator Func1*(); // expected-note{{conversion candidate of type 'INTREF (*)(float, double)'}}
+  operator Func1*(); // expected-note{{conversion candidate of type 'INTREF (*)(FLOAT, double)'}}
   operator Func2&(); // expected-note{{conversion candidate of type 'float &(&)(int, double)'}}
   void operator()();
 };





More information about the cfe-commits mailing list