]> granicus.if.org Git - clang/commitdiff
Add the initial TypoExpr AST node for delayed typo correction.
authorKaelyn Takata <rikka@google.com>
Mon, 27 Oct 2014 18:07:20 +0000 (18:07 +0000)
committerKaelyn Takata <rikka@google.com>
Mon, 27 Oct 2014 18:07:20 +0000 (18:07 +0000)
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@220692 91177308-0d34-0410-b5e6-96231b3b80d8

17 files changed:
include/clang/AST/DataRecursiveASTVisitor.h
include/clang/AST/Expr.h
include/clang/AST/RecursiveASTVisitor.h
include/clang/Basic/StmtNodes.td
include/clang/Sema/SemaInternal.h
lib/AST/Expr.cpp
lib/AST/ExprClassification.cpp
lib/AST/ExprConstant.cpp
lib/AST/ItaniumMangle.cpp
lib/AST/StmtPrinter.cpp
lib/AST/StmtProfile.cpp
lib/Sema/SemaExceptionSpec.cpp
lib/Sema/TreeTransform.h
lib/Serialization/ASTReaderStmt.cpp
lib/Serialization/ASTWriterStmt.cpp
lib/StaticAnalyzer/Core/ExprEngine.cpp
tools/libclang/CXCursor.cpp

index 54c22fbda3efe768881b9fc60aa68e876d0e0e43..f528e1cabb8ad25f5dd1be4ea5b8ec7b4fd49713 100644 (file)
@@ -2240,6 +2240,7 @@ DEF_TRAVERSE_STMT(CapturedStmt, { TRY_TO(TraverseDecl(S->getCapturedDecl())); })
 
 DEF_TRAVERSE_STMT(CXXOperatorCallExpr, {})
 DEF_TRAVERSE_STMT(OpaqueValueExpr, {})
+DEF_TRAVERSE_STMT(TypoExpr, {})
 DEF_TRAVERSE_STMT(CUDAKernelCallExpr, {})
 
 // These operators (all of them) do not need any action except
index 2b2adc810afdd88690bce3ff05320306734cf0fd..b838204b5d92fac0dcb3fe76bfec85646bb46800 100644 (file)
@@ -4846,6 +4846,24 @@ public:
     return child_range(SubExprs, SubExprs+NumSubExprs);
   }
 };
+
+/// TypoExpr - Internal placeholder for expressions where typo correction
+/// still needs to be performed and/or an error diagnostic emitted.
+class TypoExpr : public Expr {
+public:
+  TypoExpr(QualType T)
+      : Expr(TypoExprClass, T, VK_LValue, OK_Ordinary,
+             /*isTypeDependent*/ true,
+             /*isValueDependent*/ true,
+             /*isInstantiationDependent*/ true,
+             /*containsUnexpandedParameterPack*/ false) {
+    assert(T->isDependentType() && "TypoExpr given a non-dependent type");
+  }
+
+  child_range children() { return child_range(); }
+  SourceLocation getLocStart() const LLVM_READONLY { return SourceLocation(); }
+  SourceLocation getLocEnd() const LLVM_READONLY { return SourceLocation(); }
+};
 }  // end namespace clang
 
 #endif
index bda4916201add76b1fe3a3cd75d039cc913b2eac..4688beae8bfb136a0131bfb0c834bafb94045f28 100644 (file)
@@ -2262,6 +2262,7 @@ DEF_TRAVERSE_STMT(CapturedStmt, { TRY_TO(TraverseDecl(S->getCapturedDecl())); })
 
 DEF_TRAVERSE_STMT(CXXOperatorCallExpr, {})
 DEF_TRAVERSE_STMT(OpaqueValueExpr, {})
+DEF_TRAVERSE_STMT(TypoExpr, {})
 DEF_TRAVERSE_STMT(CUDAKernelCallExpr, {})
 
 // These operators (all of them) do not need any action except
index be025e344a0cea86574712c9d9f3d3e093ce7285..ea2f931c1ab35dfd1e4689318ee47bda6bf0b305 100644 (file)
@@ -163,6 +163,7 @@ def ShuffleVectorExpr : DStmt<Expr>;
 def ConvertVectorExpr : DStmt<Expr>;
 def BlockExpr : DStmt<Expr>;
 def OpaqueValueExpr : DStmt<Expr>;
+def TypoExpr : DStmt<Expr>;
 
 // Microsoft Extensions.
 def MSPropertyRefExpr : DStmt<Expr>;
index 59920d20dcd9b21c4c7d905c0dc44d81f2817ab5..9f0d39a11dd35dd0ada79a9aeeaa8f05d8293075 100644 (file)
@@ -149,6 +149,9 @@ public:
   /// in the consumer.
   TypoCorrection getNextCorrection();
 
+  ASTContext &getContext() const { return SemaRef.Context; }
+  const LookupResult &getLookupResult() const { return Result; }
+
 private:
   class NamespaceSpecifierSet {
     struct SpecifierInfo {
index 5020d5a9e2930840b7734f5ad7d115132ca4fbe5..ec679f0669a9223573d9d2f29c7625bae6b2bf55 100644 (file)
@@ -2886,6 +2886,7 @@ bool Expr::HasSideEffects(const ASTContext &Ctx) const {
   case PackExpansionExprClass:
   case SubstNonTypeTemplateParmPackExprClass:
   case FunctionParmPackExprClass:
+  case TypoExprClass:
     llvm_unreachable("shouldn't see dependent / unresolved nodes here");
 
   case DeclRefExprClass:
index d3d25308a38680e25dc827281cec47d78c85f0ae..4e2e3ea2ee89dfb86dbb35c39d33c21fc0bbc648 100644 (file)
@@ -124,10 +124,11 @@ static Cl::Kinds ClassifyInternal(ASTContext &Ctx, const Expr *E) {
   case Expr::ObjCPropertyRefExprClass:
     // C++ [expr.typeid]p1: The result of a typeid expression is an lvalue of...
   case Expr::CXXTypeidExprClass:
-    // Unresolved lookups get classified as lvalues.
+    // Unresolved lookups and uncorrected typos get classified as lvalues.
     // FIXME: Is this wise? Should they get their own kind?
   case Expr::UnresolvedLookupExprClass:
   case Expr::UnresolvedMemberExprClass:
+  case Expr::TypoExprClass:
   case Expr::CXXDependentScopeMemberExprClass:
   case Expr::DependentScopeDeclRefExprClass:
     // ObjC instance variables are lvalues
index 78de2578bee1f7e59c737c980c80eb4235c4a2e9..d49d9b2c27c42b32e9e712fbc1da6905f9684229 100644 (file)
@@ -8625,6 +8625,7 @@ static ICEDiag CheckICE(const Expr* E, const ASTContext &Ctx) {
   case Expr::CXXDeleteExprClass:
   case Expr::CXXPseudoDestructorExprClass:
   case Expr::UnresolvedLookupExprClass:
+  case Expr::TypoExprClass:
   case Expr::DependentScopeDeclRefExprClass:
   case Expr::CXXConstructExprClass:
   case Expr::CXXStdInitializerListExprClass:
index 76664673d53c29f33f03bbf07e3ca32ec6c75b1b..e41c664c8f23b70ba2d2b3160198caa340de9f7e 100644 (file)
@@ -2627,6 +2627,7 @@ recurse:
   case Expr::ParenListExprClass:
   case Expr::LambdaExprClass:
   case Expr::MSPropertyRefExprClass:
+  case Expr::TypoExprClass:  // This should no longer exist in the AST by now.
     llvm_unreachable("unexpected statement kind");
 
   // FIXME: invent manglings for all these.
index c84875c09fb08ece04dbed323424a56bf10d2468..b5441c830de0742db441d29baf75091e8aa368dc 100644 (file)
@@ -2166,6 +2166,11 @@ void StmtPrinter::VisitOpaqueValueExpr(OpaqueValueExpr *Node) {
   PrintExpr(Node->getSourceExpr());
 }
 
+void StmtPrinter::VisitTypoExpr(TypoExpr *Node) {
+  // TODO: Print something reasonable for a TypoExpr, if necessary.
+  assert(false && "Cannot print TypoExpr nodes");
+}
+
 void StmtPrinter::VisitAsTypeExpr(AsTypeExpr *Node) {
   OS << "__builtin_astype(";
   PrintExpr(Node->getSrcExpr());
index 87e30bb3e357a9ecc0bffdaa9f5881978e69a180..15a867698620a3a355bbce21074b5fd474cf0d44 100644 (file)
@@ -1242,6 +1242,10 @@ void StmtProfiler::VisitOpaqueValueExpr(const OpaqueValueExpr *E) {
   VisitExpr(E);  
 }
 
+void StmtProfiler::VisitTypoExpr(const TypoExpr *E) {
+  VisitExpr(E);
+}
+
 void StmtProfiler::VisitObjCStringLiteral(const ObjCStringLiteral *S) {
   VisitExpr(S);
 }
index e4963b13d641da6c4e7a1d8a91ebe2a387c855cf..ac0616df74082a6e69f34b623044563c4180a971 100644 (file)
@@ -1068,6 +1068,7 @@ CanThrowResult Sema::canThrow(const Expr *E) {
   case Expr::UnaryExprOrTypeTraitExprClass:
   case Expr::UnresolvedLookupExprClass:
   case Expr::UnresolvedMemberExprClass:
+  case Expr::TypoExprClass:
     // FIXME: Can any of the above throw?  If so, when?
     return CT_Cannot;
 
index 28890f59ce2f1268f11d7cf0d205b9653e8c2675..c569d31f7e30944bbcc89ebf80d446162475fedb 100644 (file)
@@ -7321,6 +7321,12 @@ TreeTransform<Derived>::TransformOpaqueValueExpr(OpaqueValueExpr *E) {
   return E;
 }
 
+template<typename Derived>
+ExprResult
+TreeTransform<Derived>::TransformTypoExpr(TypoExpr *E) {
+  return E;
+}
+
 template<typename Derived>
 ExprResult
 TreeTransform<Derived>::TransformPseudoObjectExpr(PseudoObjectExpr *E) {
index d2b7568dfac4b9a10d74af8182171bfcb358a945..5b4e12cbb45d8c4fd606f68b7ca0a725809e54d3 100644 (file)
@@ -1588,6 +1588,10 @@ void ASTStmtReader::VisitOpaqueValueExpr(OpaqueValueExpr *E) {
   E->Loc = ReadSourceLocation(Record, Idx);
 }
 
+void ASTStmtReader::VisitTypoExpr(TypoExpr *E) {
+  llvm_unreachable("Cannot read TypoExpr nodes");
+}
+
 //===----------------------------------------------------------------------===//
 // Microsoft Expressions and Statements
 //===----------------------------------------------------------------------===//
index 6891f56e2d4ecd3a697e8c02c74621d8a3562c06..18aad2ffe8bd315c3478b06f572785322d97e88f 100644 (file)
@@ -1588,6 +1588,12 @@ void ASTStmtWriter::VisitOpaqueValueExpr(OpaqueValueExpr *E) {
   Code = serialization::EXPR_OPAQUE_VALUE;
 }
 
+void ASTStmtWriter::VisitTypoExpr(TypoExpr *E) {
+  VisitExpr(E);
+  // TODO: Figure out sane writer behavior for a TypoExpr, if necessary
+  assert(false && "Cannot write TypoExpr nodes");
+}
+
 //===----------------------------------------------------------------------===//
 // CUDA Expressions and Statements.
 //===----------------------------------------------------------------------===//
index c844147e35cdbe30e16716a84625a4d0adbae93e..7464b84c4a0133603150b07578e6acdda2ce734d 100644 (file)
@@ -760,6 +760,7 @@ void ExprEngine::Visit(const Stmt *S, ExplodedNode *Pred,
     case Stmt::ExpressionTraitExprClass:
     case Stmt::UnresolvedLookupExprClass:
     case Stmt::UnresolvedMemberExprClass:
+    case Stmt::TypoExprClass:
     case Stmt::CXXNoexceptExprClass:
     case Stmt::PackExpansionExprClass:
     case Stmt::SubstNonTypeTemplateParmPackExprClass:
index 6590b158e5c3c0b2ea0cab648225415337298807..2c83236ca914409d04bbe237e6544d03bcb5caa5 100644 (file)
@@ -469,6 +469,7 @@ CXCursor cxcursor::MakeCXCursor(const Stmt *S, const Decl *Parent,
   case Stmt::SubstNonTypeTemplateParmPackExprClass:
   case Stmt::FunctionParmPackExprClass:
   case Stmt::UnresolvedLookupExprClass:
+  case Stmt::TypoExprClass: // A typo could actually be a DeclRef or a MemberRef
     K = CXCursor_DeclRefExpr;
     break;