[cfe-commits] r84962 - in /cfe/trunk: include/clang/AST/ lib/AST/ lib/Analysis/ lib/CodeGen/ lib/Frontend/ lib/Sema/

Douglas Gregor dgregor at apple.com
Fri Oct 23 11:54:35 PDT 2009


Author: dgregor
Date: Fri Oct 23 13:54:35 2009
New Revision: 84962

URL: http://llvm.org/viewvc/llvm-project?rev=84962&view=rev
Log:
Eliminate QualifiedDeclRefExpr, which captured the notion of a
qualified reference to a declaration that is not a non-static data
member or non-static member function, e.g., 

  namespace N { int i; }
  int j = N::i;

Instead, extend DeclRefExpr to optionally store the qualifier. Most
clients won't see or care about the difference (since
QualifierDeclRefExpr inherited DeclRefExpr). However, this reduces the
number of top-level expression types that clients need to cope with,
brings the implementation of DeclRefExpr into line with MemberExpr,
and simplifies and unifies our handling of declaration references.

Extended DeclRefExpr to (optionally) store explicitly-specified
template arguments. This occurs when naming a declaration via a
template-id (which will be stored in a TemplateIdRefExpr) that,
following template argument deduction and (possibly) overload
resolution, is replaced with a DeclRefExpr that refers to a template
specialization but maintains the template arguments as written.




Modified:
    cfe/trunk/include/clang/AST/Expr.h
    cfe/trunk/include/clang/AST/ExprCXX.h
    cfe/trunk/include/clang/AST/StmtNodes.def
    cfe/trunk/lib/AST/Expr.cpp
    cfe/trunk/lib/AST/StmtPrinter.cpp
    cfe/trunk/lib/AST/StmtProfile.cpp
    cfe/trunk/lib/Analysis/GRExprEngine.cpp
    cfe/trunk/lib/CodeGen/CGExpr.cpp
    cfe/trunk/lib/CodeGen/CGExprAgg.cpp
    cfe/trunk/lib/CodeGen/CGExprConstant.cpp
    cfe/trunk/lib/CodeGen/CodeGenFunction.h
    cfe/trunk/lib/Frontend/PCHReaderStmt.cpp
    cfe/trunk/lib/Frontend/PCHWriterStmt.cpp
    cfe/trunk/lib/Sema/SemaChecking.cpp
    cfe/trunk/lib/Sema/SemaCodeComplete.cpp
    cfe/trunk/lib/Sema/SemaExpr.cpp
    cfe/trunk/lib/Sema/SemaOverload.cpp
    cfe/trunk/lib/Sema/SemaTemplate.cpp
    cfe/trunk/lib/Sema/SemaTemplateInstantiate.cpp
    cfe/trunk/lib/Sema/TreeTransform.h

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

==============================================================================
--- cfe/trunk/include/clang/AST/Expr.h (original)
+++ cfe/trunk/include/clang/AST/Expr.h Fri Oct 23 13:54:35 2009
@@ -322,47 +322,221 @@
 // Primary Expressions.
 //===----------------------------------------------------------------------===//
 
+/// \brief Represents the qualifier that may precede a C++ name, e.g., the
+/// "std::" in "std::sort".
+struct NameQualifier {
+  /// \brief The nested name specifier.
+  NestedNameSpecifier *NNS;
+  
+  /// \brief The source range covered by the nested name specifier.
+  SourceRange Range;
+};
+
+/// \brief Represents an explicit template argument list in C++, e.g.,
+/// the "<int>" in "sort<int>".
+struct ExplicitTemplateArgumentList {
+  /// \brief The source location of the left angle bracket ('<');
+  SourceLocation LAngleLoc;
+  
+  /// \brief The source location of the right angle bracket ('>');
+  SourceLocation RAngleLoc;
+  
+  /// \brief The number of template arguments in TemplateArgs.
+  /// The actual template arguments (if any) are stored after the
+  /// ExplicitTemplateArgumentList structure.
+  unsigned NumTemplateArgs;
+  
+  /// \brief Retrieve the template arguments
+  TemplateArgument *getTemplateArgs() {
+    return reinterpret_cast<TemplateArgument *> (this + 1);
+  }
+  
+  /// \brief Retrieve the template arguments
+  const TemplateArgument *getTemplateArgs() const {
+    return reinterpret_cast<const TemplateArgument *> (this + 1);
+  }
+};
+  
 /// DeclRefExpr - [C99 6.5.1p2] - A reference to a declared variable, function,
 /// enum, etc.
 class DeclRefExpr : public Expr {
-  NamedDecl *D;
+  enum {
+    // Flag on DecoratedD that specifies when this declaration reference 
+    // expression has a C++ nested-name-specifier.
+    HasQualifierFlag = 0x01,
+    // Flag on DecoratedD that specifies when this declaration reference 
+    // expression has an explicit C++ template argument list.
+    HasExplicitTemplateArgumentListFlag = 0x02
+  };
+  
+  // DecoratedD - The declaration that we are referencing, plus two bits to 
+  // indicate whether (1) the declaration's name was explicitly qualified and
+  // (2) the declaration's name was followed by an explicit template 
+  // argument list.
+  llvm::PointerIntPair<NamedDecl *, 2> DecoratedD;
+  
+  // Loc - The location of the declaration name itself.
   SourceLocation Loc;
 
+  /// \brief Retrieve the qualifier that preceded the declaration name, if any.
+  NameQualifier *getNameQualifier() {
+    if (DecoratedD.getInt() & HasQualifierFlag == 0)
+      return 0;
+    
+    return reinterpret_cast<NameQualifier *> (this + 1);
+  }
+  
+  /// \brief Retrieve the qualifier that preceded the member name, if any.
+  const NameQualifier *getNameQualifier() const {
+    return const_cast<DeclRefExpr *>(this)->getNameQualifier();
+  }
+  
+  /// \brief Retrieve the explicit template argument list that followed the
+  /// member template name, if any.
+  ExplicitTemplateArgumentList *getExplicitTemplateArgumentList() {
+    if (DecoratedD.getInt() & HasExplicitTemplateArgumentListFlag == 0)
+      return 0;
+    
+    if (DecoratedD.getInt() & HasQualifierFlag == 0)
+      return reinterpret_cast<ExplicitTemplateArgumentList *>(this + 1);
+    
+    return reinterpret_cast<ExplicitTemplateArgumentList *>(
+                                                      getNameQualifier() + 1);
+  }
+  
+  /// \brief Retrieve the explicit template argument list that followed the
+  /// member template name, if any.
+  const ExplicitTemplateArgumentList *getExplicitTemplateArgumentList() const {
+    return const_cast<DeclRefExpr *>(this)->getExplicitTemplateArgumentList();
+  }
+  
+  DeclRefExpr(NestedNameSpecifier *Qualifier, SourceRange QualifierRange,
+              NamedDecl *D, SourceLocation NameLoc,
+              bool HasExplicitTemplateArgumentList,
+              SourceLocation LAngleLoc,
+              const TemplateArgument *ExplicitTemplateArgs,
+              unsigned NumExplicitTemplateArgs,
+              SourceLocation RAngleLoc,
+              QualType T, bool TD, bool VD);
+  
 protected:
   // FIXME: Eventually, this constructor will go away and all subclasses
   // will have to provide the type- and value-dependent flags.
   DeclRefExpr(StmtClass SC, NamedDecl *d, QualType t, SourceLocation l) :
-    Expr(SC, t), D(d), Loc(l) {}
+    Expr(SC, t), DecoratedD(d, 0), Loc(l) {}
 
   DeclRefExpr(StmtClass SC, NamedDecl *d, QualType t, SourceLocation l, bool TD,
               bool VD) :
-    Expr(SC, t, TD, VD), D(d), Loc(l) {}
+    Expr(SC, t, TD, VD), DecoratedD(d, 0), Loc(l) {}
 
 public:
   // FIXME: Eventually, this constructor will go away and all clients
   // will have to provide the type- and value-dependent flags.
   DeclRefExpr(NamedDecl *d, QualType t, SourceLocation l) :
-    Expr(DeclRefExprClass, t), D(d), Loc(l) {}
+    Expr(DeclRefExprClass, t), DecoratedD(d, 0), Loc(l) {}
 
   DeclRefExpr(NamedDecl *d, QualType t, SourceLocation l, bool TD, bool VD) :
-    Expr(DeclRefExprClass, t, TD, VD), D(d), Loc(l) {}
+    Expr(DeclRefExprClass, t, TD, VD), DecoratedD(d, 0), Loc(l) {}
 
   /// \brief Construct an empty declaration reference expression.
   explicit DeclRefExpr(EmptyShell Empty)
     : Expr(DeclRefExprClass, Empty) { }
 
-  NamedDecl *getDecl() { return D; }
-  const NamedDecl *getDecl() const { return D; }
-  void setDecl(NamedDecl *NewD) { D = NewD; }
+  static DeclRefExpr *Create(ASTContext &Context,
+                             NestedNameSpecifier *Qualifier,
+                             SourceRange QualifierRange,
+                             NamedDecl *D,
+                             SourceLocation NameLoc,
+                             QualType T, bool TD, bool VD);
+  
+  static DeclRefExpr *Create(ASTContext &Context,
+                             NestedNameSpecifier *Qualifier,
+                             SourceRange QualifierRange,
+                             NamedDecl *D,
+                             SourceLocation NameLoc,
+                             bool HasExplicitTemplateArgumentList,
+                             SourceLocation LAngleLoc,
+                             const TemplateArgument *ExplicitTemplateArgs,
+                             unsigned NumExplicitTemplateArgs,
+                             SourceLocation RAngleLoc,
+                             QualType T, bool TD, bool VD);
+  
+  NamedDecl *getDecl() { return DecoratedD.getPointer(); }
+  const NamedDecl *getDecl() const { return DecoratedD.getPointer(); }
+  void setDecl(NamedDecl *NewD) { DecoratedD.setPointer(NewD); }
 
   SourceLocation getLocation() const { return Loc; }
   void setLocation(SourceLocation L) { Loc = L; }
-  virtual SourceRange getSourceRange() const { return SourceRange(Loc); }
+  virtual SourceRange getSourceRange() const;
 
+  /// \brief Determine whether this declaration reference was preceded by a
+  /// C++ nested-name-specifier, e.g., \c N::foo.
+  bool hasQualifier() const { return DecoratedD.getInt() & HasQualifierFlag; }
+  
+  /// \brief If the name was qualified, retrieves the source range of
+  /// the nested-name-specifier that precedes the name. Otherwise,
+  /// returns an empty source range.
+  SourceRange getQualifierRange() const {
+    if (!hasQualifier())
+      return SourceRange();
+    
+    return getNameQualifier()->Range;
+  }
+  
+  /// \brief If the name was qualified, retrieves the nested-name-specifier 
+  /// that precedes the name. Otherwise, returns NULL.
+  NestedNameSpecifier *getQualifier() const {
+    if (!hasQualifier())
+      return 0;
+    
+    return getNameQualifier()->NNS;
+  }
+  
+  /// \brief Determines whether this member expression actually had a C++
+  /// template argument list explicitly specified, e.g., x.f<int>.
+  bool hasExplicitTemplateArgumentList() const {
+    return DecoratedD.getInt() & HasExplicitTemplateArgumentListFlag;
+  }
+  
+  /// \brief Retrieve the location of the left angle bracket following the
+  /// member name ('<'), if any.
+  SourceLocation getLAngleLoc() const {
+    if (!hasExplicitTemplateArgumentList())
+      return SourceLocation();
+    
+    return getExplicitTemplateArgumentList()->LAngleLoc;
+  }
+  
+  /// \brief Retrieve the template arguments provided as part of this
+  /// template-id.
+  const TemplateArgument *getTemplateArgs() const {
+    if (!hasExplicitTemplateArgumentList())
+      return 0;
+    
+    return getExplicitTemplateArgumentList()->getTemplateArgs();
+  }
+  
+  /// \brief Retrieve the number of template arguments provided as part of this
+  /// template-id.
+  unsigned getNumTemplateArgs() const {
+    if (!hasExplicitTemplateArgumentList())
+      return 0;
+    
+    return getExplicitTemplateArgumentList()->NumTemplateArgs;
+  }
+  
+  /// \brief Retrieve the location of the right angle bracket following the
+  /// template arguments ('>').
+  SourceLocation getRAngleLoc() const {
+    if (!hasExplicitTemplateArgumentList())
+      return SourceLocation();
+    
+    return getExplicitTemplateArgumentList()->RAngleLoc;
+  }
+  
   static bool classof(const Stmt *T) {
     return T->getStmtClass() == DeclRefExprClass ||
-           T->getStmtClass() == CXXConditionDeclExprClass ||
-           T->getStmtClass() == QualifiedDeclRefExprClass;
+           T->getStmtClass() == CXXConditionDeclExprClass;
   }
   static bool classof(const DeclRefExpr *) { return true; }
 
@@ -1062,41 +1236,6 @@
   virtual child_iterator child_end();
 };
 
-/// \brief Represents the qualifier that may precede a C++ name, e.g., the
-/// "std::" in "std::sort".
-struct NameQualifier {
-  /// \brief The nested name specifier.
-  NestedNameSpecifier *NNS;
-
-  /// \brief The source range covered by the nested name specifier.
-  SourceRange Range;
-};
-
-/// \brief Represents an explicit template argument list in C++, e.g.,
-/// the "<int>" in "sort<int>".
-struct ExplicitTemplateArgumentList {
-  /// \brief The source location of the left angle bracket ('<');
-  SourceLocation LAngleLoc;
-
-  /// \brief The source location of the right angle bracket ('>');
-  SourceLocation RAngleLoc;
-
-  /// \brief The number of template arguments in TemplateArgs.
-  /// The actual template arguments (if any) are stored after the
-  /// ExplicitTemplateArgumentList structure.
-  unsigned NumTemplateArgs;
-
-  /// \brief Retrieve the template arguments
-  TemplateArgument *getTemplateArgs() {
-    return reinterpret_cast<TemplateArgument *> (this + 1);
-  }
-
-  /// \brief Retrieve the template arguments
-  const TemplateArgument *getTemplateArgs() const {
-    return reinterpret_cast<const TemplateArgument *> (this + 1);
-  }
-};
-
 /// MemberExpr - [C99 6.5.2.3] Structure and Union Members.  X->F and X.F.
 ///
 class MemberExpr : public Expr {

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

==============================================================================
--- cfe/trunk/include/clang/AST/ExprCXX.h (original)
+++ cfe/trunk/include/clang/AST/ExprCXX.h Fri Oct 23 13:54:35 2009
@@ -1061,46 +1061,11 @@
   virtual child_iterator child_end();
 };
 
-/// QualifiedDeclRefExpr - A reference to a declared variable,
-/// function, enum, etc., that includes a qualification, e.g.,
-/// "N::foo".
-class QualifiedDeclRefExpr : public DeclRefExpr {
-  /// QualifierRange - The source range that covers the
-  /// nested-name-specifier.
-  SourceRange QualifierRange;
-
-  /// \brief The nested-name-specifier that qualifies this declaration
-  /// name.
-  NestedNameSpecifier *NNS;
-
-public:
-  QualifiedDeclRefExpr(NamedDecl *d, QualType t, SourceLocation l, bool TD,
-                       bool VD, SourceRange R, NestedNameSpecifier *NNS)
-    : DeclRefExpr(QualifiedDeclRefExprClass, d, t, l, TD, VD),
-      QualifierRange(R), NNS(NNS) { }
-
-  /// \brief Retrieve the source range of the nested-name-specifier.
-  SourceRange getQualifierRange() const { return QualifierRange; }
-
-  /// \brief Retrieve the nested-name-specifier that qualifies this
-  /// declaration.
-  NestedNameSpecifier *getQualifier() const { return NNS; }
-
-  virtual SourceRange getSourceRange() const {
-    return SourceRange(QualifierRange.getBegin(), getLocation());
-  }
-
-  static bool classof(const Stmt *T) {
-    return T->getStmtClass() == QualifiedDeclRefExprClass;
-  }
-  static bool classof(const QualifiedDeclRefExpr *) { return true; }
-};
-
 /// \brief A qualified reference to a name whose declaration cannot
 /// yet be resolved.
 ///
-/// UnresolvedDeclRefExpr is similar to QualifiedDeclRefExpr in that
-/// it expresses a qualified reference to a declaration such as
+/// UnresolvedDeclRefExpr is similar to eclRefExpr in that
+/// it expresses a reference to a declaration such as
 /// X<T>::value. The difference, however, is that an
 /// UnresolvedDeclRefExpr node is used only within C++ templates when
 /// the qualification (e.g., X<T>::) refers to a dependent type. In
@@ -1108,8 +1073,8 @@
 /// declaration will differ from on instantiation of X<T> to the
 /// next. Therefore, UnresolvedDeclRefExpr keeps track of the
 /// qualifier (X<T>::) and the name of the entity being referenced
-/// ("value"). Such expressions will instantiate to
-/// QualifiedDeclRefExprs.
+/// ("value"). Such expressions will instantiate to a DeclRefExpr once the
+/// declaration can be found.
 class UnresolvedDeclRefExpr : public Expr {
   /// The name of the entity we will be referencing.
   DeclarationName Name;
@@ -1126,6 +1091,7 @@
   NestedNameSpecifier *NNS;
 
   /// \brief Whether this expr is an address of (&) operand.
+  /// FIXME: Stash this bit into NNS!
   bool IsAddressOfOperand;
 
 public:

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

==============================================================================
--- cfe/trunk/include/clang/AST/StmtNodes.def (original)
+++ cfe/trunk/include/clang/AST/StmtNodes.def Fri Oct 23 13:54:35 2009
@@ -127,7 +127,6 @@
 EXPR(CXXPseudoDestructorExpr, Expr)
 EXPR(UnresolvedFunctionNameExpr , Expr)
 EXPR(UnaryTypeTraitExpr     , Expr)
-EXPR(QualifiedDeclRefExpr   , DeclRefExpr)
 EXPR(UnresolvedDeclRefExpr  , Expr)
 EXPR(TemplateIdRefExpr      , Expr)
 EXPR(CXXConstructExpr       , Expr)

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

==============================================================================
--- cfe/trunk/lib/AST/Expr.cpp (original)
+++ cfe/trunk/lib/AST/Expr.cpp Fri Oct 23 13:54:35 2009
@@ -30,6 +30,91 @@
 // Primary Expressions.
 //===----------------------------------------------------------------------===//
 
+DeclRefExpr::DeclRefExpr(NestedNameSpecifier *Qualifier, 
+                         SourceRange QualifierRange,
+                         NamedDecl *D, SourceLocation NameLoc,
+                         bool HasExplicitTemplateArgumentList,
+                         SourceLocation LAngleLoc,
+                         const TemplateArgument *ExplicitTemplateArgs,
+                         unsigned NumExplicitTemplateArgs,
+                         SourceLocation RAngleLoc,
+                         QualType T, bool TD, bool VD)
+  : Expr(DeclRefExprClass, T, TD, VD),
+    DecoratedD(D,
+               (Qualifier? HasQualifierFlag : 0) |
+               (HasExplicitTemplateArgumentList? 
+                                    HasExplicitTemplateArgumentListFlag : 0)),
+    Loc(NameLoc) {
+  if (Qualifier) {
+    NameQualifier *NQ = getNameQualifier();
+    NQ->NNS = Qualifier;
+    NQ->Range = QualifierRange;
+  }
+      
+  if (HasExplicitTemplateArgumentList) {
+    ExplicitTemplateArgumentList *ETemplateArgs
+      = getExplicitTemplateArgumentList();
+    ETemplateArgs->LAngleLoc = LAngleLoc;
+    ETemplateArgs->RAngleLoc = RAngleLoc;
+    ETemplateArgs->NumTemplateArgs = NumExplicitTemplateArgs;
+    
+    TemplateArgument *TemplateArgs = ETemplateArgs->getTemplateArgs();
+    for (unsigned I = 0; I < NumExplicitTemplateArgs; ++I)
+      new (TemplateArgs + I) TemplateArgument(ExplicitTemplateArgs[I]);
+  }
+}
+
+DeclRefExpr *DeclRefExpr::Create(ASTContext &Context,
+                                 NestedNameSpecifier *Qualifier,
+                                 SourceRange QualifierRange,
+                                 NamedDecl *D,
+                                 SourceLocation NameLoc,
+                                 QualType T, bool TD, bool VD) {
+  return Create(Context, Qualifier, QualifierRange, D, NameLoc,
+                false, SourceLocation(), 0, 0, SourceLocation(),
+                T, TD, VD);
+}
+
+DeclRefExpr *DeclRefExpr::Create(ASTContext &Context,
+                                 NestedNameSpecifier *Qualifier,
+                                 SourceRange QualifierRange,
+                                 NamedDecl *D,
+                                 SourceLocation NameLoc,
+                                 bool HasExplicitTemplateArgumentList,
+                                 SourceLocation LAngleLoc,
+                                 const TemplateArgument *ExplicitTemplateArgs,
+                                 unsigned NumExplicitTemplateArgs,
+                                 SourceLocation RAngleLoc,
+                                 QualType T, bool TD, bool VD) {
+  std::size_t Size = sizeof(DeclRefExpr);
+  if (Qualifier != 0)
+    Size += sizeof(NameQualifier);
+  
+  if (HasExplicitTemplateArgumentList)
+    Size += sizeof(ExplicitTemplateArgumentList) +
+            sizeof(TemplateArgument) * NumExplicitTemplateArgs;
+  
+  void *Mem = Context.Allocate(Size, llvm::alignof<DeclRefExpr>());
+  return new (Mem) DeclRefExpr(Qualifier, QualifierRange, D, NameLoc,
+                               HasExplicitTemplateArgumentList,
+                               LAngleLoc, 
+                               ExplicitTemplateArgs, 
+                               NumExplicitTemplateArgs,
+                               RAngleLoc,
+                               T, TD, VD);
+}
+
+SourceRange DeclRefExpr::getSourceRange() const {
+  // FIXME: Does not handle multi-token names well, e.g., operator[].
+  SourceRange R(Loc);
+  
+  if (hasQualifier())
+    R.setBegin(getQualifierRange().getBegin());
+  if (hasExplicitTemplateArgumentList())
+    R.setEnd(getRAngleLoc());
+  return R;
+}
+
 // FIXME: Maybe this should use DeclPrinter with a special "print predefined
 // expr" policy instead.
 std::string PredefinedExpr::ComputeName(ASTContext &Context, IdentType IT,
@@ -855,8 +940,7 @@
     if (cast<ArraySubscriptExpr>(this)->getBase()->getType()->isVectorType())
       return cast<ArraySubscriptExpr>(this)->getBase()->isLvalue(Ctx);
     return LV_Valid;
-  case DeclRefExprClass:
-  case QualifiedDeclRefExprClass: { // C99 6.5.1p2
+  case DeclRefExprClass: { // C99 6.5.1p2
     const NamedDecl *RefdDecl = cast<DeclRefExpr>(this)->getDecl();
     if (DeclCanBeLvalue(RefdDecl, Ctx))
       return LV_Valid;
@@ -1133,8 +1217,7 @@
     return cast<ImplicitCastExpr>(this)->getSubExpr()->isOBJCGCCandidate(Ctx);
   case CStyleCastExprClass:
     return cast<CStyleCastExpr>(this)->getSubExpr()->isOBJCGCCandidate(Ctx);
-  case DeclRefExprClass:
-  case QualifiedDeclRefExprClass: {
+  case DeclRefExprClass: {
     const Decl *D = cast<DeclRefExpr>(this)->getDecl();
     if (const VarDecl *VD = dyn_cast<VarDecl>(D)) {
       if (VD->hasGlobalStorage())
@@ -1432,7 +1515,6 @@
     return ICEDiag(2, E->getLocStart());
   }
   case Expr::DeclRefExprClass:
-  case Expr::QualifiedDeclRefExprClass:
     if (isa<EnumConstantDecl>(cast<DeclRefExpr>(E)->getDecl()))
       return NoDiag();
     if (Ctx.getLangOptions().CPlusPlus &&

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

==============================================================================
--- cfe/trunk/lib/AST/StmtPrinter.cpp (original)
+++ cfe/trunk/lib/AST/StmtPrinter.cpp Fri Oct 23 13:54:35 2009
@@ -473,14 +473,14 @@
 }
 
 void StmtPrinter::VisitDeclRefExpr(DeclRefExpr *Node) {
+  if (NestedNameSpecifier *Qualifier = Node->getQualifier())
+    Qualifier->print(OS, Policy);
   OS << Node->getDecl()->getNameAsString();
-}
-
-void StmtPrinter::VisitQualifiedDeclRefExpr(QualifiedDeclRefExpr *Node) {
-  NamedDecl *D = Node->getDecl();
-
-  Node->getQualifier()->print(OS, Policy);
-  OS << D->getNameAsString();
+  if (Node->hasExplicitTemplateArgumentList())
+    OS << TemplateSpecializationType::PrintTemplateArgumentList(
+                                                    Node->getTemplateArgs(),
+                                                    Node->getNumTemplateArgs(),
+                                                    Policy);  
 }
 
 void StmtPrinter::VisitUnresolvedDeclRefExpr(UnresolvedDeclRefExpr *Node) {

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

==============================================================================
--- cfe/trunk/lib/AST/StmtProfile.cpp (original)
+++ cfe/trunk/lib/AST/StmtProfile.cpp Fri Oct 23 13:54:35 2009
@@ -206,7 +206,9 @@
 
 void StmtProfiler::VisitDeclRefExpr(DeclRefExpr *S) {
   VisitExpr(S);
+  VisitNestedNameSpecifier(S->getQualifier());
   VisitDecl(S->getDecl());
+  VisitTemplateArguments(S->getTemplateArgs(), S->getNumTemplateArgs());
 }
 
 void StmtProfiler::VisitPredefinedExpr(PredefinedExpr *S) {
@@ -521,11 +523,6 @@
   VisitType(S->getQueriedType());
 }
 
-void StmtProfiler::VisitQualifiedDeclRefExpr(QualifiedDeclRefExpr *S) {
-  VisitDeclRefExpr(S);
-  VisitNestedNameSpecifier(S->getQualifier());
-}
-
 void StmtProfiler::VisitUnresolvedDeclRefExpr(UnresolvedDeclRefExpr *S) {
   VisitExpr(S);
   VisitName(S->getDeclName());

Modified: cfe/trunk/lib/Analysis/GRExprEngine.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Analysis/GRExprEngine.cpp?rev=84962&r1=84961&r2=84962&view=diff

==============================================================================
--- cfe/trunk/lib/Analysis/GRExprEngine.cpp (original)
+++ cfe/trunk/lib/Analysis/GRExprEngine.cpp Fri Oct 23 13:54:35 2009
@@ -409,7 +409,6 @@
     }
 
     case Stmt::DeclRefExprClass:
-    case Stmt::QualifiedDeclRefExprClass:
       VisitDeclRefExpr(cast<DeclRefExpr>(S), Pred, Dst, false);
       break;
 
@@ -522,7 +521,6 @@
       return;
 
     case Stmt::DeclRefExprClass:
-    case Stmt::QualifiedDeclRefExprClass:
       VisitDeclRefExpr(cast<DeclRefExpr>(Ex), Pred, Dst, true);
       return;
 

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

==============================================================================
--- cfe/trunk/lib/CodeGen/CGExpr.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGExpr.cpp Fri Oct 23 13:54:35 2009
@@ -245,7 +245,6 @@
   case Expr::VAArgExprClass:
     return EmitVAArgExprLValue(cast<VAArgExpr>(E));
   case Expr::DeclRefExprClass:
-  case Expr::QualifiedDeclRefExprClass:
     return EmitDeclRefLValue(cast<DeclRefExpr>(E));
   case Expr::ParenExprClass:return EmitLValue(cast<ParenExpr>(E)->getSubExpr());
   case Expr::PredefinedExprClass:
@@ -866,9 +865,9 @@
     llvm::Value *V = LocalDeclMap[IPD];
     assert(V && "BlockVarDecl not entered in LocalDeclMap?");
     return LValue::MakeAddr(V, MakeQualifiers(E->getType()));
-  } else if (const QualifiedDeclRefExpr *QDRExpr = 
-             dyn_cast<QualifiedDeclRefExpr>(E)) {
-    return EmitPointerToDataMemberLValue(QDRExpr);
+  } else if (E->getQualifier()) {
+    // FIXME: the qualifier check does not seem sufficient here
+    return EmitPointerToDataMemberLValue(E);
   }
   assert(0 && "Unimp declref");
   //an invalid LValue, but the assert will
@@ -1519,8 +1518,7 @@
 }
 
 
-LValue CodeGenFunction::EmitPointerToDataMemberLValue(
-                                              const QualifiedDeclRefExpr *E) {
+LValue CodeGenFunction::EmitPointerToDataMemberLValue(const DeclRefExpr *E) {
   const FieldDecl *Field = cast<FieldDecl>(E->getDecl());
   const CXXRecordDecl *ClassDecl = cast<CXXRecordDecl>(Field->getDeclContext());
   QualType NNSpecTy = 

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

==============================================================================
--- cfe/trunk/lib/CodeGen/CGExprAgg.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGExprAgg.cpp Fri Oct 23 13:54:35 2009
@@ -297,7 +297,7 @@
   assert(MPT->getPointeeType()->isFunctionProtoType() &&
          "Unexpected member pointer type!");
   
-  const QualifiedDeclRefExpr *DRE = cast<QualifiedDeclRefExpr>(E->getSubExpr());
+  const DeclRefExpr *DRE = cast<DeclRefExpr>(E->getSubExpr());
   const CXXMethodDecl *MD = cast<CXXMethodDecl>(DRE->getDecl());
 
   const llvm::Type *PtrDiffTy = 

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

==============================================================================
--- cfe/trunk/lib/CodeGen/CGExprConstant.cpp (original)
+++ cfe/trunk/lib/CodeGen/CGExprConstant.cpp Fri Oct 23 13:54:35 2009
@@ -434,7 +434,7 @@
         E->getType()->getAs<MemberPointerType>()) {
       QualType T = MPT->getPointeeType();
       if (T->isFunctionProtoType()) {
-        QualifiedDeclRefExpr *DRE = cast<QualifiedDeclRefExpr>(E->getSubExpr());
+        DeclRefExpr *DRE = cast<DeclRefExpr>(E->getSubExpr());
         
         return EmitMemberFunctionPointer(cast<CXXMethodDecl>(DRE->getDecl()));
       }
@@ -739,8 +739,7 @@
                                      E->getType().getAddressSpace());
       return C;
     }
-    case Expr::DeclRefExprClass:
-    case Expr::QualifiedDeclRefExprClass: {
+    case Expr::DeclRefExprClass: {
       NamedDecl *Decl = cast<DeclRefExpr>(E)->getDecl();
       if (const FunctionDecl *FD = dyn_cast<FunctionDecl>(Decl))
         return CGM.GetAddrOfFunction(FD);

Modified: cfe/trunk/lib/CodeGen/CodeGenFunction.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/CodeGen/CodeGenFunction.h?rev=84962&r1=84961&r2=84962&view=diff

==============================================================================
--- cfe/trunk/lib/CodeGen/CodeGenFunction.h (original)
+++ cfe/trunk/lib/CodeGen/CodeGenFunction.h Fri Oct 23 13:54:35 2009
@@ -819,7 +819,7 @@
   LValue EmitConditionalOperatorLValue(const ConditionalOperator *E);
   LValue EmitCastLValue(const CastExpr *E);
   LValue EmitNullInitializationLValue(const CXXZeroInitValueExpr *E);
-  LValue EmitPointerToDataMemberLValue(const QualifiedDeclRefExpr *E);
+  LValue EmitPointerToDataMemberLValue(const DeclRefExpr *E);
   
   llvm::Value *EmitIvarOffset(const ObjCInterfaceDecl *Interface,
                               const ObjCIvarDecl *Ivar);

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

==============================================================================
--- cfe/trunk/lib/Frontend/PCHReaderStmt.cpp (original)
+++ cfe/trunk/lib/Frontend/PCHReaderStmt.cpp Fri Oct 23 13:54:35 2009
@@ -347,6 +347,8 @@
   VisitExpr(E);
   E->setDecl(cast<NamedDecl>(Reader.GetDecl(Record[Idx++])));
   E->setLocation(SourceLocation::getFromRawEncoding(Record[Idx++]));
+  // FIXME: read qualifier
+  // FIXME: read explicit template arguments
   return 0;
 }
 

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

==============================================================================
--- cfe/trunk/lib/Frontend/PCHWriterStmt.cpp (original)
+++ cfe/trunk/lib/Frontend/PCHWriterStmt.cpp Fri Oct 23 13:54:35 2009
@@ -314,6 +314,8 @@
   VisitExpr(E);
   Writer.AddDeclRef(E->getDecl(), Record);
   Writer.AddSourceLocation(E->getLocation(), Record);
+  // FIXME: write qualifier
+  // FIXME: write explicit template arguments
   Code = pch::EXPR_DECL_REF;
 }
 

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

==============================================================================
--- cfe/trunk/lib/Sema/SemaChecking.cpp (original)
+++ cfe/trunk/lib/Sema/SemaChecking.cpp Fri Oct 23 13:54:35 2009
@@ -1420,8 +1420,7 @@
   // viewed AST node.  We then recursively traverse the AST by calling
   // EvalAddr and EvalVal appropriately.
   switch (E->getStmtClass()) {
-  case Stmt::DeclRefExprClass:
-  case Stmt::QualifiedDeclRefExprClass: {
+  case Stmt::DeclRefExprClass: {
     // DeclRefExpr: the base case.  When we hit a DeclRefExpr we are looking
     //  at code that refers to a variable's name.  We check if it has local
     //  storage within the function, and if so, return the expression.

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

==============================================================================
--- cfe/trunk/lib/Sema/SemaCodeComplete.cpp (original)
+++ cfe/trunk/lib/Sema/SemaCodeComplete.cpp Fri Oct 23 13:54:35 2009
@@ -1171,8 +1171,7 @@
         // At the XXX, our completions are TagDecl::TK_union,
         // TagDecl::TK_struct, and TagDecl::TK_class, rather than TK_union,
         // TK_struct, and TK_class.
-        if (QualifiedDeclRefExpr *QDRE = dyn_cast<QualifiedDeclRefExpr>(DRE))
-          Qualifier = QDRE->getQualifier();
+        Qualifier = DRE->getQualifier();
       }
   }
   

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

==============================================================================
--- cfe/trunk/lib/Sema/SemaExpr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExpr.cpp Fri Oct 23 13:54:35 2009
@@ -446,9 +446,7 @@
                                   isAddressOfOperand);
 }
 
-/// BuildDeclRefExpr - Build either a DeclRefExpr or a
-/// QualifiedDeclRefExpr based on whether or not SS is a
-/// nested-name-specifier.
+/// BuildDeclRefExpr - Build a DeclRefExpr.
 Sema::OwningExprResult
 Sema::BuildDeclRefExpr(NamedDecl *D, QualType Ty, SourceLocation Loc,
                        bool TypeDependent, bool ValueDependent,
@@ -476,15 +474,11 @@
 
   MarkDeclarationReferenced(Loc, D);
 
-  Expr *E;
-  if (SS && !SS->isEmpty()) {
-    E = new (Context) QualifiedDeclRefExpr(D, Ty, Loc, TypeDependent,
-                                          ValueDependent, SS->getRange(),
-                  static_cast<NestedNameSpecifier *>(SS->getScopeRep()));
-  } else
-    E = new (Context) DeclRefExpr(D, Ty, Loc, TypeDependent, ValueDependent);
-
-  return Owned(E);
+  return Owned(DeclRefExpr::Create(Context, 
+                              SS? (NestedNameSpecifier *)SS->getScopeRep() : 0, 
+                                   SS? SS->getRange() : SourceRange(), 
+                                   D, Loc, 
+                                   Ty, TypeDependent, ValueDependent));
 }
 
 /// getObjectForAnonymousRecordDecl - Retrieve the (unnamed) field or
@@ -2738,16 +2732,12 @@
                cast<UnaryOperator>(FnExpr)->getOpcode()
                == UnaryOperator::AddrOf) {
       FnExpr = cast<UnaryOperator>(FnExpr)->getSubExpr();
-    } else if (QualifiedDeclRefExpr *QDRExpr 
-                 = dyn_cast<QualifiedDeclRefExpr>(FnExpr)) {
-      // Qualified names disable ADL (C++0x [basic.lookup.argdep]p1).
-      ArgumentDependentLookup = false;
-      Qualifier = QDRExpr->getQualifier();
-      QualifierRange = QDRExpr->getQualifierRange();
-      Function = dyn_cast<NamedDecl>(QDRExpr->getDecl());
-      break;
     } else if (DeclRefExpr *DRExpr = dyn_cast<DeclRefExpr>(FnExpr)) {
       Function = dyn_cast<NamedDecl>(DRExpr->getDecl());
+      if ((Qualifier = DRExpr->getQualifier())) {
+        ArgumentDependentLookup = false;
+        QualifierRange = DRExpr->getQualifierRange();
+      }      
       break;
     } else if (UnresolvedFunctionNameExpr *DepName
                = dyn_cast<UnresolvedFunctionNameExpr>(FnExpr)) {
@@ -2933,16 +2923,10 @@
         return ExprError();
 
       // Update Fn to refer to the actual function selected.
-      Expr *NewFn = 0;
-      if (Qualifier)
-        NewFn = new (Context) QualifiedDeclRefExpr(FDecl, FDecl->getType(),
-                                                   Fn->getLocStart(),
-                                                   false, false,
-                                                   QualifierRange,
-                                                   Qualifier);
-      else
-        NewFn = new (Context) DeclRefExpr(FDecl, FDecl->getType(),
-                                          Fn->getLocStart());
+      // FIXME: Use FixOverloadedFunctionReference?
+      Expr *NewFn = DeclRefExpr::Create(Context, Qualifier, QualifierRange, FDecl, 
+                                        Fn->getLocStart(), FDecl->getType(), false, 
+                                        false);
       Fn->Destroy(Context);
       Fn = NewFn;
     }
@@ -5083,7 +5067,6 @@
 static NamedDecl *getPrimaryDecl(Expr *E) {
   switch (E->getStmtClass()) {
   case Stmt::DeclRefExprClass:
-  case Stmt::QualifiedDeclRefExprClass:
     return cast<DeclRefExpr>(E)->getDecl();
   case Stmt::MemberExprClass:
     // If this is an arrow operator, the address is an offset from
@@ -5199,7 +5182,7 @@
       // Okay: we can take the address of a field.
       // Could be a pointer to member, though, if there is an explicit
       // scope qualifier for the class.
-      if (isa<QualifiedDeclRefExpr>(op)) {
+      if (isa<DeclRefExpr>(op) && cast<DeclRefExpr>(op)->getQualifier()) {
         DeclContext *Ctx = dcl->getDeclContext();
         if (Ctx && Ctx->isRecord()) {
           if (FD->getType()->isReferenceType()) {
@@ -5216,7 +5199,8 @@
     } else if (CXXMethodDecl *MD = dyn_cast<CXXMethodDecl>(dcl)) {
       // Okay: we can take the address of a function.
       // As above.
-      if (isa<QualifiedDeclRefExpr>(op) && MD->isInstance())
+      if (isa<DeclRefExpr>(op) && cast<DeclRefExpr>(op)->getQualifier() &&
+          MD->isInstance())
         return Context.getMemberPointerType(op->getType(),
               Context.getTypeDeclType(MD->getParent()).getTypePtr());
     } else if (!isa<FunctionDecl>(dcl))

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

==============================================================================
--- cfe/trunk/lib/Sema/SemaOverload.cpp (original)
+++ cfe/trunk/lib/Sema/SemaOverload.cpp Fri Oct 23 13:54:35 2009
@@ -5370,18 +5370,19 @@
       if (Method->isStatic()) {
         // Do nothing: static member functions aren't any different
         // from non-member functions.
-      } else if (QualifiedDeclRefExpr *DRE
-                 = dyn_cast<QualifiedDeclRefExpr>(UnOp->getSubExpr())) {
-        // We have taken the address of a pointer to member
-        // function. Perform the computation here so that we get the
-        // appropriate pointer to member type.
-        DRE->setDecl(Fn);
-        DRE->setType(Fn->getType());
-        QualType ClassType
-          = Context.getTypeDeclType(cast<RecordDecl>(Method->getDeclContext()));
-        E->setType(Context.getMemberPointerType(Fn->getType(),
-                                                ClassType.getTypePtr()));
-        return E;
+      } else if (DeclRefExpr *DRE = dyn_cast<DeclRefExpr>(UnOp->getSubExpr())) {
+        if (DRE->getQualifier()) {
+          // We have taken the address of a pointer to member
+          // function. Perform the computation here so that we get the
+          // appropriate pointer to member type.
+          DRE->setDecl(Fn);
+          DRE->setType(Fn->getType());
+          QualType ClassType
+            = Context.getTypeDeclType(cast<RecordDecl>(Method->getDeclContext()));
+          E->setType(Context.getMemberPointerType(Fn->getType(),
+                                                  ClassType.getTypePtr()));
+          return E;
+        }
       }
       // FIXME: TemplateIdRefExpr referring to a member function template
       // specialization!
@@ -5401,18 +5402,20 @@
     MemExpr->setMemberDecl(Fn);
     E->setType(Fn->getType());
   } else if (TemplateIdRefExpr *TID = dyn_cast<TemplateIdRefExpr>(E)) {
-    // FIXME: We should capture the template arguments here.
-    if (NestedNameSpecifier *Qualifier = TID->getQualifier())
-      E = new (Context) QualifiedDeclRefExpr(Fn, Fn->getType(),
-                                             TID->getTemplateNameLoc(),
-                                             /*FIXME?*/false, /*FIXME?*/false,
-                                             TID->getQualifierRange(),
-                                             Qualifier);
-    else
-      E = new (Context) DeclRefExpr(Fn, Fn->getType(), 
-                                    TID->getTemplateNameLoc());
+    E = DeclRefExpr::Create(Context, 
+                            TID->getQualifier(), TID->getQualifierRange(),
+                            Fn, TID->getTemplateNameLoc(), 
+                            true,
+                            TID->getLAngleLoc(),
+                            TID->getTemplateArgs(),
+                            TID->getNumTemplateArgs(),
+                            TID->getRAngleLoc(),
+                            Fn->getType(), 
+                            /*FIXME?*/false, /*FIXME?*/false);
     
-    TID->Destroy(Context);
+    // FIXME: Don't destroy TID here, since we need its template arguments
+    // to survive.
+    // TID->Destroy(Context);
   } else {
     assert(false && "Invalid reference to overloaded function");
   }

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

==============================================================================
--- cfe/trunk/lib/Sema/SemaTemplate.cpp (original)
+++ cfe/trunk/lib/Sema/SemaTemplate.cpp Fri Oct 23 13:54:35 2009
@@ -1845,7 +1845,7 @@
   //   template-parameter shall be one of: [...]
   //
   //     -- a pointer to member expressed as described in 5.3.1.
-  QualifiedDeclRefExpr *DRE = 0;
+  DeclRefExpr *DRE = 0;
 
   // Ignore (and complain about) any excess parentheses.
   while (ParenExpr *Parens = dyn_cast<ParenExpr>(Arg)) {
@@ -1860,8 +1860,11 @@
   }
 
   if (UnaryOperator *UnOp = dyn_cast<UnaryOperator>(Arg))
-    if (UnOp->getOpcode() == UnaryOperator::AddrOf)
-      DRE = dyn_cast<QualifiedDeclRefExpr>(UnOp->getSubExpr());
+    if (UnOp->getOpcode() == UnaryOperator::AddrOf) {
+      DRE = dyn_cast<DeclRefExpr>(UnOp->getSubExpr());
+      if (DRE && !DRE->getQualifier())
+        DRE = 0;
+    }
 
   if (!DRE)
     return Diag(Arg->getSourceRange().getBegin(),

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

==============================================================================
--- cfe/trunk/lib/Sema/SemaTemplateInstantiate.cpp (original)
+++ cfe/trunk/lib/Sema/SemaTemplateInstantiate.cpp Fri Oct 23 13:54:35 2009
@@ -618,10 +618,21 @@
   // FIXME: Is this correct? Maybe FindInstantiatedDecl should do this?
   InstD = InstD->getUnderlyingDecl();
 
-  // FIXME: nested-name-specifier for QualifiedDeclRefExpr
+  CXXScopeSpec SS;
+  NestedNameSpecifier *Qualifier = 0;
+  if (E->getQualifier()) {
+    Qualifier = TransformNestedNameSpecifier(E->getQualifier(),
+                                             E->getQualifierRange());
+    if (!Qualifier)
+      return SemaRef.ExprError();
+    
+    SS.setScopeRep(Qualifier);
+    SS.setRange(E->getQualifierRange());
+  }
+  
   return SemaRef.BuildDeclarationNameExpr(E->getLocation(), InstD,
                                           /*FIXME:*/false,
-                                          /*FIXME:*/0,
+                                          &SS,
                                           /*FIXME:*/false);
 }
 

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

==============================================================================
--- cfe/trunk/lib/Sema/TreeTransform.h (original)
+++ cfe/trunk/lib/Sema/TreeTransform.h Fri Oct 23 13:54:35 2009
@@ -781,10 +781,15 @@
   ///
   /// By default, performs semantic analysis to build the new expression.
   /// Subclasses may override this routine to provide different behavior.
-  OwningExprResult RebuildDeclRefExpr(NamedDecl *ND, SourceLocation Loc) {
+  OwningExprResult RebuildDeclRefExpr(NestedNameSpecifier *Qualifier,
+                                      SourceRange QualifierRange,
+                                      NamedDecl *ND, SourceLocation Loc) {
+    CXXScopeSpec SS;
+    SS.setScopeRep(Qualifier);
+    SS.setRange(QualifierRange);
     return getSema().BuildDeclarationNameExpr(Loc, ND,
                                               /*FIXME:*/false,
-                                              /*SS=*/0,
+                                              &SS,
                                               /*FIXME:*/false);
   }
 
@@ -1392,26 +1397,6 @@
                                          T.getAsOpaquePtr(), RParenLoc);
   }
 
-  /// \brief Build a new qualified declaration reference expression.
-  ///
-  /// By default, performs semantic analysis to build the new expression.
-  /// Subclasses may override this routine to provide different behavior.
-  OwningExprResult RebuildQualifiedDeclRefExpr(NestedNameSpecifier *NNS,
-                                               SourceRange QualifierRange,
-                                               NamedDecl *ND,
-                                               SourceLocation Location,
-                                               bool IsAddressOfOperand) {
-    CXXScopeSpec SS;
-    SS.setRange(QualifierRange);
-    SS.setScopeRep(NNS);
-    return getSema().ActOnDeclarationNameExpr(/*Scope=*/0,
-                                              Location,
-                                              ND->getDeclName(),
-                                              /*Trailing lparen=*/false,
-                                              &SS,
-                                              IsAddressOfOperand);
-  }
-
   /// \brief Build a new (previously unresolved) declaration reference
   /// expression.
   ///
@@ -3276,15 +3261,40 @@
 template<typename Derived>
 Sema::OwningExprResult
 TreeTransform<Derived>::TransformDeclRefExpr(DeclRefExpr *E) {
+  NestedNameSpecifier *Qualifier = 0;
+  if (E->getQualifier()) {
+    Qualifier = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
+                                                       E->getQualifierRange());
+    if (!Qualifier)
+      return SemaRef.ExprError();
+  }
+  
   NamedDecl *ND
     = dyn_cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getDecl()));
   if (!ND)
     return SemaRef.ExprError();
 
-  if (!getDerived().AlwaysRebuild() && ND == E->getDecl())
+  if (!getDerived().AlwaysRebuild() && 
+      Qualifier == E->getQualifier() &&
+      ND == E->getDecl() &&
+      !E->hasExplicitTemplateArgumentList())
     return SemaRef.Owned(E->Retain());
 
-  return getDerived().RebuildDeclRefExpr(ND, E->getLocation());
+  // FIXME: We're losing the explicit template arguments in this transformation.
+
+  llvm::SmallVector<TemplateArgument, 4> TransArgs;
+  for (unsigned I = 0, N = E->getNumTemplateArgs(); I != N; ++I) {
+    TemplateArgument TransArg
+      = getDerived().TransformTemplateArgument(E->getTemplateArgs()[I]);
+    if (TransArg.isNull())
+      return SemaRef.ExprError();
+    
+    TransArgs.push_back(TransArg);
+  }
+  
+  // FIXME: Pass the qualifier/qualifier range along.
+  return getDerived().RebuildDeclRefExpr(Qualifier, E->getQualifierRange(),
+                                         ND, E->getLocation());
 }
 
 template<typename Derived>
@@ -4301,32 +4311,6 @@
 
 template<typename Derived>
 Sema::OwningExprResult
-TreeTransform<Derived>::TransformQualifiedDeclRefExpr(QualifiedDeclRefExpr *E) {
-  NestedNameSpecifier *NNS
-    = getDerived().TransformNestedNameSpecifier(E->getQualifier(),
-                                                E->getQualifierRange());
-  if (!NNS)
-    return SemaRef.ExprError();
-
-  NamedDecl *ND
-    = dyn_cast_or_null<NamedDecl>(getDerived().TransformDecl(E->getDecl()));
-  if (!ND)
-    return SemaRef.ExprError();
-
-  if (!getDerived().AlwaysRebuild() &&
-      NNS == E->getQualifier() &&
-      ND == E->getDecl())
-    return SemaRef.Owned(E->Retain());
-
-  return getDerived().RebuildQualifiedDeclRefExpr(NNS,
-                                                  E->getQualifierRange(),
-                                                  ND,
-                                                  E->getLocation(),
-                                                  /*FIXME:*/false);
-}
-
-template<typename Derived>
-Sema::OwningExprResult
 TreeTransform<Derived>::TransformUnresolvedDeclRefExpr(
                                                     UnresolvedDeclRefExpr *E) {
   NestedNameSpecifier *NNS





More information about the cfe-commits mailing list