1193323Sed//===- llvm/Support/InstIterator.h - Classes for inst iteration -*- C++ -*-===// 2193323Sed// 3193323Sed// The LLVM Compiler Infrastructure 4193323Sed// 5193323Sed// This file is distributed under the University of Illinois Open Source 6193323Sed// License. See LICENSE.TXT for details. 7193323Sed// 8193323Sed//===----------------------------------------------------------------------===// 9193323Sed// 10193323Sed// This file contains definitions of two iterators for iterating over the 11193323Sed// instructions in a function. This is effectively a wrapper around a two level 12193323Sed// iterator that can probably be genericized later. 13193323Sed// 14193323Sed// Note that this iterator gets invalidated any time that basic blocks or 15193323Sed// instructions are moved around. 16193323Sed// 17193323Sed//===----------------------------------------------------------------------===// 18193323Sed 19193323Sed#ifndef LLVM_SUPPORT_INSTITERATOR_H 20193323Sed#define LLVM_SUPPORT_INSTITERATOR_H 21193323Sed 22249423Sdim#include "llvm/IR/BasicBlock.h" 23249423Sdim#include "llvm/IR/Function.h" 24193323Sed 25193323Sednamespace llvm { 26193323Sed 27193323Sed// This class implements inst_begin() & inst_end() for 28193323Sed// inst_iterator and const_inst_iterator's. 29193323Sed// 30193323Sedtemplate <class _BB_t, class _BB_i_t, class _BI_t, class _II_t> 31193323Sedclass InstIterator { 32193323Sed typedef _BB_t BBty; 33193323Sed typedef _BB_i_t BBIty; 34193323Sed typedef _BI_t BIty; 35193323Sed typedef _II_t IIty; 36193323Sed _BB_t *BBs; // BasicBlocksType 37193323Sed _BB_i_t BB; // BasicBlocksType::iterator 38193323Sed _BI_t BI; // BasicBlock::iterator 39193323Sedpublic: 40193323Sed typedef std::bidirectional_iterator_tag iterator_category; 41193323Sed typedef IIty value_type; 42193323Sed typedef signed difference_type; 43193323Sed typedef IIty* pointer; 44193323Sed typedef IIty& reference; 45193323Sed 46193323Sed // Default constructor 47193323Sed InstIterator() {} 48193323Sed 49193323Sed // Copy constructor... 50193323Sed template<typename A, typename B, typename C, typename D> 51193323Sed InstIterator(const InstIterator<A,B,C,D> &II) 52193323Sed : BBs(II.BBs), BB(II.BB), BI(II.BI) {} 53193323Sed 54193323Sed template<typename A, typename B, typename C, typename D> 55193323Sed InstIterator(InstIterator<A,B,C,D> &II) 56193323Sed : BBs(II.BBs), BB(II.BB), BI(II.BI) {} 57193323Sed 58193323Sed template<class M> InstIterator(M &m) 59193323Sed : BBs(&m.getBasicBlockList()), BB(BBs->begin()) { // begin ctor 60193323Sed if (BB != BBs->end()) { 61193323Sed BI = BB->begin(); 62193323Sed advanceToNextBB(); 63193323Sed } 64193323Sed } 65193323Sed 66193323Sed template<class M> InstIterator(M &m, bool) 67193323Sed : BBs(&m.getBasicBlockList()), BB(BBs->end()) { // end ctor 68193323Sed } 69193323Sed 70193323Sed // Accessors to get at the underlying iterators... 71193323Sed inline BBIty &getBasicBlockIterator() { return BB; } 72193323Sed inline BIty &getInstructionIterator() { return BI; } 73193323Sed 74193323Sed inline reference operator*() const { return *BI; } 75193323Sed inline pointer operator->() const { return &operator*(); } 76193323Sed 77193323Sed inline bool operator==(const InstIterator &y) const { 78193323Sed return BB == y.BB && (BB == BBs->end() || BI == y.BI); 79193323Sed } 80193323Sed inline bool operator!=(const InstIterator& y) const { 81193323Sed return !operator==(y); 82193323Sed } 83193323Sed 84193323Sed InstIterator& operator++() { 85193323Sed ++BI; 86193323Sed advanceToNextBB(); 87193323Sed return *this; 88193323Sed } 89193323Sed inline InstIterator operator++(int) { 90193323Sed InstIterator tmp = *this; ++*this; return tmp; 91193323Sed } 92193323Sed 93193323Sed InstIterator& operator--() { 94193323Sed while (BB == BBs->end() || BI == BB->begin()) { 95193323Sed --BB; 96193323Sed BI = BB->end(); 97193323Sed } 98193323Sed --BI; 99193323Sed return *this; 100193323Sed } 101193323Sed inline InstIterator operator--(int) { 102193323Sed InstIterator tmp = *this; --*this; return tmp; 103193323Sed } 104193323Sed 105193323Sed inline bool atEnd() const { return BB == BBs->end(); } 106193323Sed 107193323Sedprivate: 108193323Sed inline void advanceToNextBB() { 109193323Sed // The only way that the II could be broken is if it is now pointing to 110193323Sed // the end() of the current BasicBlock and there are successor BBs. 111193323Sed while (BI == BB->end()) { 112193323Sed ++BB; 113193323Sed if (BB == BBs->end()) break; 114193323Sed BI = BB->begin(); 115193323Sed } 116193323Sed } 117193323Sed}; 118193323Sed 119193323Sed 120193323Sedtypedef InstIterator<iplist<BasicBlock>, 121193323Sed Function::iterator, BasicBlock::iterator, 122193323Sed Instruction> inst_iterator; 123193323Sedtypedef InstIterator<const iplist<BasicBlock>, 124193323Sed Function::const_iterator, 125193323Sed BasicBlock::const_iterator, 126193323Sed const Instruction> const_inst_iterator; 127193323Sed 128193323Sedinline inst_iterator inst_begin(Function *F) { return inst_iterator(*F); } 129193323Sedinline inst_iterator inst_end(Function *F) { return inst_iterator(*F, true); } 130193323Sedinline const_inst_iterator inst_begin(const Function *F) { 131193323Sed return const_inst_iterator(*F); 132193323Sed} 133193323Sedinline const_inst_iterator inst_end(const Function *F) { 134193323Sed return const_inst_iterator(*F, true); 135193323Sed} 136193323Sedinline inst_iterator inst_begin(Function &F) { return inst_iterator(F); } 137193323Sedinline inst_iterator inst_end(Function &F) { return inst_iterator(F, true); } 138193323Sedinline const_inst_iterator inst_begin(const Function &F) { 139193323Sed return const_inst_iterator(F); 140193323Sed} 141193323Sedinline const_inst_iterator inst_end(const Function &F) { 142193323Sed return const_inst_iterator(F, true); 143193323Sed} 144193323Sed 145193323Sed} // End llvm namespace 146193323Sed 147193323Sed#endif 148