]> granicus.if.org Git - clang/commitdiff
pch'ify typeid.
authorChris Lattner <sabre@nondot.org>
Sun, 9 May 2010 06:03:39 +0000 (06:03 +0000)
committerChris Lattner <sabre@nondot.org>
Sun, 9 May 2010 06:03:39 +0000 (06:03 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@103374 91177308-0d34-0410-b5e6-96231b3b80d8

include/clang/AST/ExprCXX.h
include/clang/Frontend/PCHBitCodes.h
lib/Frontend/PCHReaderStmt.cpp
lib/Frontend/PCHWriterStmt.cpp
test/Makefile
test/PCH/cxx_exprs.cpp
test/PCH/cxx_exprs.h

index c11f55b95bd6cfebfc9a6233b05a82d13ce8cde6..e6bc39419eb381bbbc1e107195c5762fc7ec93bd 100644 (file)
@@ -321,6 +321,14 @@ public:
         Operand->isTypeDependent() || Operand->isValueDependent()),
       Operand(Operand), Range(R) { }
 
+  CXXTypeidExpr(EmptyShell Empty, bool isExpr)
+    : Expr(CXXTypeidExprClass, Empty) {
+    if (isExpr)
+      Operand = (Expr*)0;
+    else
+      Operand = (TypeSourceInfo*)0;
+  }
+  
   bool isTypeOperand() const { return Operand.is<TypeSourceInfo *>(); }
   
   /// \brief Retrieves the type operand of this typeid() expression after
@@ -332,15 +340,20 @@ public:
     assert(isTypeOperand() && "Cannot call getTypeOperand for typeid(expr)");
     return Operand.get<TypeSourceInfo *>();
   }
+
+  void setTypeOperandSourceInfo(TypeSourceInfo *TSI) {
+    assert(isTypeOperand() && "Cannot call getTypeOperand for typeid(expr)");
+    Operand = TSI;
+  }
   
-  ExprgetExprOperand() const {
+  Expr *getExprOperand() const {
     assert(!isTypeOperand() && "Cannot call getExprOperand for typeid(type)");
     return static_cast<Expr*>(Operand.get<Stmt *>());
   }
-
-  virtual SourceRange getSourceRange() const {
-    return Range;
-  }
+  
+  virtual SourceRange getSourceRange() const { return Range; }
+  void setSourceRange(SourceRange R) { Range = R; }
+  
   static bool classof(const Stmt *T) {
     return T->getStmtClass() == CXXTypeidExprClass;
   }
index 5d9b02788fd138574c5d9eff4ea2d955a516f7ad..575881ad59689d52f1b99b91effc77ebab3326ec 100644 (file)
@@ -746,8 +746,9 @@ namespace clang {
       EXPR_CXX_FUNCTIONAL_CAST,
       // \brief A CXXBoolLiteralExpr record.
       EXPR_CXX_BOOL_LITERAL,
-      // \brief A CXXNullPtrLiteralExpr record.
-      EXPR_CXX_NULL_PTR_LITERAL
+      EXPR_CXX_NULL_PTR_LITERAL,  // CXXNullPtrLiteralExpr
+      EXPR_CXX_TYPEID_EXPR,       // CXXTypeidExpr (of expr).
+      EXPR_CXX_TYPEID_TYPE        // CXXTypeidExpr (of type).
     };
 
     /// \brief The kinds of designators that can occur in a
index 394a894e4e4c2e7882504952c219b35285f1d830..cce2e262deee38fda616b2d4c64dcf88c87c21c7 100644 (file)
@@ -126,6 +126,7 @@ namespace {
     unsigned VisitCXXFunctionalCastExpr(CXXFunctionalCastExpr *E);
     unsigned VisitCXXBoolLiteralExpr(CXXBoolLiteralExpr *E);
     unsigned VisitCXXNullPtrLiteralExpr(CXXNullPtrLiteralExpr *E);
+    unsigned VisitCXXTypeidExpr(CXXTypeidExpr *E);
   };
 }
 
@@ -992,6 +993,19 @@ unsigned PCHStmtReader::VisitCXXNullPtrLiteralExpr(CXXNullPtrLiteralExpr *E) {
   return 0;
 }
 
+unsigned PCHStmtReader::VisitCXXTypeidExpr(CXXTypeidExpr *E) {
+  VisitExpr(E);
+  E->setSourceRange(Reader.ReadSourceRange(Record, Idx));
+  if (E->isTypeOperand()) { // typeid(int)
+    E->setTypeOperandSourceInfo(Reader.GetTypeSourceInfo(Record, Idx));
+    return 0;
+  }
+  
+  // typeid(42+2)
+  return 1;
+}
+
+
 // Within the bitstream, expressions are stored in Reverse Polish
 // Notation, with each of the subexpressions preceding the
 // expression they are stored in. To evaluate expressions, we
@@ -1341,6 +1355,12 @@ Stmt *PCHReader::ReadStmt(llvm::BitstreamCursor &Cursor) {
     case pch::EXPR_CXX_NULL_PTR_LITERAL:
       S = new (Context) CXXNullPtrLiteralExpr(Empty);
       break;
+    case pch::EXPR_CXX_TYPEID_EXPR:
+      S = new (Context) CXXTypeidExpr(Empty, true);
+      break;
+    case pch::EXPR_CXX_TYPEID_TYPE:
+      S = new (Context) CXXTypeidExpr(Empty, false);
+      break;
     }
 
     // We hit a STMT_STOP, so we're done with this expression.
index 3c2022ea99832c2f37273ddebfcccd6d795d20e4..1e272c3c66f4a41e83028805090b666732f73fcb 100644 (file)
@@ -122,6 +122,7 @@ namespace {
     void VisitCXXFunctionalCastExpr(CXXFunctionalCastExpr *E);
     void VisitCXXBoolLiteralExpr(CXXBoolLiteralExpr *E);
     void VisitCXXNullPtrLiteralExpr(CXXNullPtrLiteralExpr *E);
+    void VisitCXXTypeidExpr(CXXTypeidExpr *E);
   };
 }
 
@@ -911,6 +912,18 @@ void PCHStmtWriter::VisitCXXNullPtrLiteralExpr(CXXNullPtrLiteralExpr *E) {
   Code = pch::EXPR_CXX_NULL_PTR_LITERAL;
 }
 
+void PCHStmtWriter::VisitCXXTypeidExpr(CXXTypeidExpr *E) {
+  VisitExpr(E);
+  Writer.AddSourceRange(E->getSourceRange(), Record);
+  if (E->isTypeOperand()) {
+    Writer.AddTypeSourceInfo(E->getTypeOperandSourceInfo(), Record);
+    Code = pch::EXPR_CXX_TYPEID_TYPE;
+  } else {
+    Writer.WriteSubStmt(E->getExprOperand());
+    Code = pch::EXPR_CXX_TYPEID_EXPR;
+  }
+}
+
 //===----------------------------------------------------------------------===//
 // PCHWriter Implementation
 //===----------------------------------------------------------------------===//
index e9d89454b898a707174a71159c703366844e349c..40170e42ff9f834f97eea3db32cd1a01c0e8e1fa 100644 (file)
@@ -16,9 +16,9 @@ TESTDIRS += $(EXTRA_TESTDIRS)
 
 ifndef TESTARGS
 ifdef VERBOSE
-TESTARGS = -v
+TESTARGS = -v -j16
 else
-TESTARGS = -s -v
+TESTARGS = -s -v -j16
 endif
 endif
 
index 0f0fe88dc54aa83a9509c05662699d89cbdfa5d6..ec7041b9843a6f02027674422e5b533deaa29561 100644 (file)
@@ -33,3 +33,7 @@ static_assert(!false_value, "false_value is false");
 
 // CXXNullPtrLiteralExpr
 cxx_null_ptr_result null_ptr = nullptr;
+
+// CXXTypeidExpr
+typeid_result1 typeid_1 = 0;
+typeid_result2 typeid_2 = 0;
\ No newline at end of file
index 6766842f0a2dc778b1245619495d04890665ee29..4f01b3aff630a96299a8ff2d18ce4a9f16e982d5 100644 (file)
@@ -1,5 +1,6 @@
 // Header for PCH test cxx_exprs.cpp
 
+
 // CXXStaticCastExpr
 typedef __typeof__(static_cast<void *>(0)) static_cast_result;
 
@@ -31,4 +32,14 @@ typedef __typeof__(nullptr) cxx_null_ptr_result;
 void foo(Derived *P) {
   // CXXMemberCallExpr
   P->f();
-}
\ No newline at end of file
+}
+
+
+// FIXME: This is a hack until <typeinfo> works completely.
+namespace std {
+  class type_info {};
+}
+
+// CXXTypeidExpr - Both expr and type forms.
+typedef __typeof__(typeid(int))* typeid_result1;
+typedef __typeof__(typeid(2))*   typeid_result2;