From: Richard Smith Date: Fri, 1 Feb 2019 21:58:17 +0000 (+0000) Subject: Factor out duplication between ExprIterator and ConstExprIterator. X-Git-Url: https://granicus.if.org/sourcecode?a=commitdiff_plain;h=bda04e052c4b14818d140f2a8f6e063f36c1552e;p=clang Factor out duplication between ExprIterator and ConstExprIterator. This also exposes a more general iterator cast mechanism suitable for use in http://reviews.llvm.org/D56571. git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@352925 91177308-0d34-0410-b5e6-96231b3b80d8 --- diff --git a/include/clang/AST/Stmt.h b/include/clang/AST/Stmt.h index 27d4f506a4..66b53c0881 100644 --- a/include/clang/AST/Stmt.h +++ b/include/clang/AST/Stmt.h @@ -986,38 +986,31 @@ public: struct EmptyShell {}; protected: - /// Iterator for iterating over Stmt * arrays that contain only Expr * + /// Iterator for iterating over Stmt * arrays that contain only T *. /// /// This is needed because AST nodes use Stmt* arrays to store /// references to children (to be compatible with StmtIterator). - struct ExprIterator - : llvm::iterator_adaptor_base { - ExprIterator() : iterator_adaptor_base(nullptr) {} - ExprIterator(Stmt **I) : iterator_adaptor_base(I) {} - - reference operator*() const { - assert((*I)->getStmtClass() >= firstExprConstant && - (*I)->getStmtClass() <= lastExprConstant); - return *reinterpret_cast(I); - } - }; + template + struct CastIterator + : llvm::iterator_adaptor_base, StmtPtr *, + std::random_access_iterator_tag, TPtr> { + using Base = typename CastIterator::iterator_adaptor_base; + + CastIterator() : Base(nullptr) {} + CastIterator(StmtPtr *I) : Base(I) {} - /// Const iterator for iterating over Stmt * arrays that contain only Expr * - struct ConstExprIterator - : llvm::iterator_adaptor_base { - ConstExprIterator() : iterator_adaptor_base(nullptr) {} - ConstExprIterator(const Stmt *const *I) : iterator_adaptor_base(I) {} - - reference operator*() const { - assert((*I)->getStmtClass() >= firstExprConstant && - (*I)->getStmtClass() <= lastExprConstant); - return *reinterpret_cast(I); + typename Base::value_type operator*() const { + return cast(*this->I); } }; + /// Const iterator for iterating over Stmt * arrays that contain only T *. + template + using ConstCastIterator = CastIterator; + + using ExprIterator = CastIterator; + using ConstExprIterator = ConstCastIterator; + private: /// Whether statistic collection is enabled. static bool StatisticsEnabled; diff --git a/lib/CodeGen/CGCoroutine.cpp b/lib/CodeGen/CGCoroutine.cpp index a0668ea4ac..8ac9b5b534 100644 --- a/lib/CodeGen/CGCoroutine.cpp +++ b/lib/CodeGen/CGCoroutine.cpp @@ -732,7 +732,7 @@ RValue CodeGenFunction::EmitCoroutineIntrinsic(const CallExpr *E, Args.push_back(llvm::ConstantTokenNone::get(getLLVMContext())); break; } - for (auto &Arg : E->arguments()) + for (const Expr *Arg : E->arguments()) Args.push_back(EmitScalarExpr(Arg)); llvm::Value *F = CGM.getIntrinsic(IID);