summaryrefslogtreecommitdiff
path: root/include/llvm/IR
diff options
context:
space:
mode:
authorChandler Carruth <chandlerc@gmail.com>2014-03-05 01:50:35 +0000
committerChandler Carruth <chandlerc@gmail.com>2014-03-05 01:50:35 +0000
commitd1fe495464e4abc384565813cbf1cb8b130e5a6d (patch)
tree6e1222dc004b8b8d75d99d363c4536a1dc0a59c9 /include/llvm/IR
parent8b3fad9343111eec5931492fbd812ad578c71089 (diff)
downloadllvm-d1fe495464e4abc384565813cbf1cb8b130e5a6d.tar.gz
llvm-d1fe495464e4abc384565813cbf1cb8b130e5a6d.tar.bz2
llvm-d1fe495464e4abc384565813cbf1cb8b130e5a6d.tar.xz
[C++11] Sink the iterator over a Value's users into the Value type
itself and teach it to convert between the non-const and const variants. De-templatetize its usage in APIs to just use the const variant which always works for those use cases. Also, rename its implementation to reflect that it is an iterator over *users* not over *uses*. This is a step toward providing both iterator and range support for walking the *uses* distinct from the *users*. In a subsequent patch this will get renamed to make it clear that this is an adaptor over the fundamental use iterator. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@202923 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'include/llvm/IR')
-rw-r--r--include/llvm/IR/CallSite.h4
-rw-r--r--include/llvm/IR/Instructions.h3
-rw-r--r--include/llvm/IR/Use.h50
-rw-r--r--include/llvm/IR/Value.h62
4 files changed, 60 insertions, 59 deletions
diff --git a/include/llvm/IR/CallSite.h b/include/llvm/IR/CallSite.h
index 8c64099d57..393bb9a5bb 100644
--- a/include/llvm/IR/CallSite.h
+++ b/include/llvm/IR/CallSite.h
@@ -104,7 +104,7 @@ public:
/// isCallee - Determine whether the passed iterator points to the
/// callee operand's Use.
///
- bool isCallee(value_use_iterator<UserTy> UI) const {
+ bool isCallee(Value::const_use_iterator UI) const {
return getCallee() == &UI.getUse();
}
@@ -121,7 +121,7 @@ public:
/// Given a value use iterator, returns the argument that corresponds to it.
/// Iterator must actually correspond to an argument.
- unsigned getArgumentNo(value_use_iterator<UserTy> I) const {
+ unsigned getArgumentNo(Value::const_use_iterator I) const {
assert(getInstruction() && "Not a call or invoke instruction!");
assert(arg_begin() <= &I.getUse() && &I.getUse() < arg_end()
&& "Argument # out of range!");
diff --git a/include/llvm/IR/Instructions.h b/include/llvm/IR/Instructions.h
index 2a2c4c69d3..24912d7d5c 100644
--- a/include/llvm/IR/Instructions.h
+++ b/include/llvm/IR/Instructions.h
@@ -2100,8 +2100,7 @@ public:
/// getIncomingBlock - Return incoming basic block corresponding
/// to value use iterator.
///
- template <typename U>
- BasicBlock *getIncomingBlock(value_use_iterator<U> I) const {
+ BasicBlock *getIncomingBlock(Value::const_use_iterator I) const {
return getIncomingBlock(I.getUse());
}
diff --git a/include/llvm/IR/Use.h b/include/llvm/IR/Use.h
index 37967f8c02..340572a20b 100644
--- a/include/llvm/IR/Use.h
+++ b/include/llvm/IR/Use.h
@@ -165,56 +165,6 @@ template <> struct simplify_type<const Use> {
static SimpleType getSimplifiedValue(const Use &Val) { return Val.get(); }
};
-template<typename UserTy> // UserTy == 'User' or 'const User'
-class value_use_iterator : public std::iterator<std::forward_iterator_tag,
- UserTy*, ptrdiff_t> {
- typedef std::iterator<std::forward_iterator_tag, UserTy*, ptrdiff_t> super;
- typedef value_use_iterator<UserTy> _Self;
-
- Use *U;
- explicit value_use_iterator(Use *u) : U(u) {}
- friend class Value;
-public:
- typedef typename super::reference reference;
- typedef typename super::pointer pointer;
-
- value_use_iterator() {}
-
- bool operator==(const _Self &x) const {
- return U == x.U;
- }
- bool operator!=(const _Self &x) const {
- return !operator==(x);
- }
-
- /// \brief Returns true if this iterator is equal to use_end() on the value.
- bool atEnd() const { return U == 0; }
-
- // Iterator traversal: forward iteration only
- _Self &operator++() { // Preincrement
- assert(U && "Cannot increment end iterator!");
- U = U->getNext();
- return *this;
- }
- _Self operator++(int) { // Postincrement
- _Self tmp = *this; ++*this; return tmp;
- }
-
- // Retrieve a pointer to the current User.
- UserTy *operator*() const {
- assert(U && "Cannot dereference end iterator!");
- return U->getUser();
- }
-
- UserTy *operator->() const { return operator*(); }
-
- Use &getUse() const { return *U; }
-
- /// \brief Return the operand # of this use in its User.
- /// FIXME: Replace all callers with a direct call to Use::getOperandNo.
- unsigned getOperandNo() const { return U->getOperandNo(); }
-};
-
// Create wrappers for C Binding types (see CBindingWrapping.h).
DEFINE_SIMPLE_CONVERSION_FUNCTIONS(Use, LLVMUseRef)
diff --git a/include/llvm/IR/Value.h b/include/llvm/IR/Value.h
index f1945020d5..b2ed39e917 100644
--- a/include/llvm/IR/Value.h
+++ b/include/llvm/IR/Value.h
@@ -75,6 +75,58 @@ protected:
unsigned char SubclassOptionalData : 7;
private:
+ template <typename UserTy> // UserTy == 'User' or 'const User'
+ class user_iterator_impl
+ : public std::iterator<std::forward_iterator_tag, UserTy *, ptrdiff_t> {
+ typedef std::iterator<std::forward_iterator_tag, UserTy *, ptrdiff_t> super;
+
+ Use *U;
+ explicit user_iterator_impl(Use *u) : U(u) {}
+ friend class Value;
+
+ public:
+ typedef typename super::reference reference;
+ typedef typename super::pointer pointer;
+
+ user_iterator_impl() {}
+
+ bool operator==(const user_iterator_impl &x) const { return U == x.U; }
+ bool operator!=(const user_iterator_impl &x) const { return !operator==(x); }
+
+ /// \brief Returns true if this iterator is equal to use_end() on the value.
+ bool atEnd() const { return U == 0; }
+
+ // Iterator traversal: forward iteration only
+ user_iterator_impl &operator++() { // Preincrement
+ assert(U && "Cannot increment end iterator!");
+ U = U->getNext();
+ return *this;
+ }
+ user_iterator_impl operator++(int) { // Postincrement
+ auto tmp = *this;
+ ++*this;
+ return tmp;
+ }
+
+ // Retrieve a pointer to the current User.
+ UserTy *operator*() const {
+ assert(U && "Cannot dereference end iterator!");
+ return U->getUser();
+ }
+
+ UserTy *operator->() const { return operator*(); }
+
+ operator user_iterator_impl<const UserTy>() const {
+ return user_iterator_impl<const UserTy>(U);
+ }
+
+ Use &getUse() const { return *U; }
+
+ /// \brief Return the operand # of this use in its User.
+ /// FIXME: Replace all callers with a direct call to Use::getOperandNo.
+ unsigned getOperandNo() const { return U->getOperandNo(); }
+ };
+
/// SubclassData - This member is defined by this class, but is not used for
/// anything. Subclasses can use it to hold whatever state they find useful.
/// This field is initialized to zero by the ctor.
@@ -151,16 +203,16 @@ public:
//----------------------------------------------------------------------
// Methods for handling the chain of uses of this Value.
//
- typedef value_use_iterator<User> use_iterator;
- typedef value_use_iterator<const User> const_use_iterator;
-
bool use_empty() const { return UseList == 0; }
+
+ typedef user_iterator_impl<User> use_iterator;
+ typedef user_iterator_impl<const User> const_use_iterator;
use_iterator use_begin() { return use_iterator(UseList); }
const_use_iterator use_begin() const { return const_use_iterator(UseList); }
use_iterator use_end() { return use_iterator(0); }
const_use_iterator use_end() const { return const_use_iterator(0); }
- User *use_back() { return *use_begin(); }
- const User *use_back() const { return *use_begin(); }
+ User *use_back() { return *use_begin(); }
+ const User *use_back() const { return *use_begin(); }
/// hasOneUse - Return true if there is exactly one user of this value. This
/// is specialized because it is a common request and does not require