<div dir="ltr"><div dir="ltr" class="gmail_msg">Seeing some failures - missed negation I guess so I added some '!' in r294357.<br class="gmail_msg"><br class="gmail_msg"><div class="gmail_msg"><font face="monospace" class="gmail_msg">IListIteratorTest.cpp:162:3: error: static_assert failed "unexpected implicit conversion"</font></div></div><div dir="ltr" class="gmail_msg"><div class="gmail_msg"><font face="monospace" class="gmail_msg"> static_assert(std::is_convertible<iterator, reverse_iterator>::value,</font></div></div><div dir="ltr" class="gmail_msg"><div class="gmail_msg"><font face="monospace" class="gmail_msg"> ^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~</font></div><div class="gmail_msg"><font face="monospace" class="gmail_msg">IListIteratorTest.cpp:164:3: error: static_assert failed "unexpected implicit conversion"</font></div></div><div dir="ltr" class="gmail_msg"><div class="gmail_msg"><font face="monospace" class="gmail_msg"> static_assert(std::is_convertible<reverse_iterator, iterator>::value,</font></div></div><div dir="ltr" class="gmail_msg"><div class="gmail_msg"><font face="monospace" class="gmail_msg"> ^ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~</font></div><div class="gmail_msg"><font face="monospace" class="gmail_msg">IListIteratorTest.cpp:166:3: error: static_assert failed "unexpected implicit conversion"</font></div><div class="gmail_msg"><font face="monospace" class="gmail_msg"> static_assert(</font></div><div class="gmail_msg"><font face="monospace" class="gmail_msg"> ^</font></div><div class="gmail_msg"><font face="monospace" class="gmail_msg">IListIteratorTest.cpp:169:3: error: static_assert failed "unexpected implicit conversion"</font></div><div class="gmail_msg"><font face="monospace" class="gmail_msg"> static_assert(</font></div><div class="gmail_msg"><font face="monospace" class="gmail_msg"> ^</font></div></div><br class="gmail_msg"><div class="gmail_quote gmail_msg"><div dir="ltr" class="gmail_msg">On Tue, Feb 7, 2017 at 1:15 PM Duncan P. N. Exon Smith via llvm-commits <<a href="mailto:llvm-commits@lists.llvm.org" class="gmail_msg" target="_blank">llvm-commits@lists.llvm.org</a>> wrote:<br class="gmail_msg"></div><blockquote class="gmail_quote gmail_msg" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: dexonsmith<br class="gmail_msg">
Date: Tue Feb 7 15:03:50 2017<br class="gmail_msg">
New Revision: 294349<br class="gmail_msg">
<br class="gmail_msg">
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=294349&view=rev" rel="noreferrer" class="gmail_msg" target="_blank">http://llvm.org/viewvc/llvm-project?rev=294349&view=rev</a><br class="gmail_msg">
Log:<br class="gmail_msg">
ADT: Add explicit conversions for reverse ilist iterators<br class="gmail_msg">
<br class="gmail_msg">
Add explicit conversions between forward and reverse ilist iterators.<br class="gmail_msg">
These follow the conversion conventions of std::reverse_iterator, which<br class="gmail_msg">
are off-by-one: the newly-constructed "reverse" iterator dereferences to<br class="gmail_msg">
the previous node of the one sent in. This has the benefit of<br class="gmail_msg">
converting reverse ranges in place:<br class="gmail_msg">
- If [I, E) is a valid range,<br class="gmail_msg">
- then [reverse(E), reverse(I)) gives the same range in reverse order.<br class="gmail_msg">
<br class="gmail_msg">
ilist_iterator::getReverse() is unchanged: it returns a reverse iterator<br class="gmail_msg">
to the *same* node.<br class="gmail_msg">
<br class="gmail_msg">
Modified:<br class="gmail_msg">
llvm/trunk/include/llvm/ADT/ilist_iterator.h<br class="gmail_msg">
llvm/trunk/include/llvm/CodeGen/MachineInstrBundleIterator.h<br class="gmail_msg">
llvm/trunk/unittests/ADT/IListIteratorTest.cpp<br class="gmail_msg">
llvm/trunk/unittests/CodeGen/MachineInstrBundleIteratorTest.cpp<br class="gmail_msg">
<br class="gmail_msg">
Modified: llvm/trunk/include/llvm/ADT/ilist_iterator.h<br class="gmail_msg">
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ADT/ilist_iterator.h?rev=294349&r1=294348&r2=294349&view=diff" rel="noreferrer" class="gmail_msg" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/ADT/ilist_iterator.h?rev=294349&r1=294348&r2=294349&view=diff</a><br class="gmail_msg">
==============================================================================<br class="gmail_msg">
--- llvm/trunk/include/llvm/ADT/ilist_iterator.h (original)<br class="gmail_msg">
+++ llvm/trunk/include/llvm/ADT/ilist_iterator.h Tue Feb 7 15:03:50 2017<br class="gmail_msg">
@@ -102,10 +102,23 @@ public:<br class="gmail_msg">
return *this;<br class="gmail_msg">
}<br class="gmail_msg">
<br class="gmail_msg">
- /// Convert from an iterator to its reverse.<br class="gmail_msg">
+ /// Explicit conversion between forward/reverse iterators.<br class="gmail_msg">
///<br class="gmail_msg">
- /// TODO: Roll this into the implicit constructor once we're sure that no one<br class="gmail_msg">
- /// is relying on the std::reverse_iterator off-by-one semantics.<br class="gmail_msg">
+ /// Translate between forward and reverse iterators without changing range<br class="gmail_msg">
+ /// boundaries. The resulting iterator will dereference (and have a handle)<br class="gmail_msg">
+ /// to the previous node, which is somewhat unexpected; but converting the<br class="gmail_msg">
+ /// two endpoints in a range will give the same range in reverse.<br class="gmail_msg">
+ ///<br class="gmail_msg">
+ /// This matches std::reverse_iterator conversions.<br class="gmail_msg">
+ explicit ilist_iterator(<br class="gmail_msg">
+ const ilist_iterator<OptionsT, !IsReverse, IsConst> &RHS)<br class="gmail_msg">
+ : ilist_iterator(++RHS.getReverse()) {}<br class="gmail_msg">
+<br class="gmail_msg">
+ /// Get a reverse iterator to the same node.<br class="gmail_msg">
+ ///<br class="gmail_msg">
+ /// Gives a reverse iterator that will dereference (and have a handle) to the<br class="gmail_msg">
+ /// same node. Converting the endpoint iterators in a range will give a<br class="gmail_msg">
+ /// different range; for range operations, use the explicit conversions.<br class="gmail_msg">
ilist_iterator<OptionsT, !IsReverse, IsConst> getReverse() const {<br class="gmail_msg">
if (NodePtr)<br class="gmail_msg">
return ilist_iterator<OptionsT, !IsReverse, IsConst>(*NodePtr);<br class="gmail_msg">
<br class="gmail_msg">
Modified: llvm/trunk/include/llvm/CodeGen/MachineInstrBundleIterator.h<br class="gmail_msg">
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/CodeGen/MachineInstrBundleIterator.h?rev=294349&r1=294348&r2=294349&view=diff" rel="noreferrer" class="gmail_msg" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/CodeGen/MachineInstrBundleIterator.h?rev=294349&r1=294348&r2=294349&view=diff</a><br class="gmail_msg">
==============================================================================<br class="gmail_msg">
--- llvm/trunk/include/llvm/CodeGen/MachineInstrBundleIterator.h (original)<br class="gmail_msg">
+++ llvm/trunk/include/llvm/CodeGen/MachineInstrBundleIterator.h Tue Feb 7 15:03:50 2017<br class="gmail_msg">
@@ -153,6 +153,18 @@ public:<br class="gmail_msg">
: MII(I.getInstrIterator()) {}<br class="gmail_msg">
MachineInstrBundleIterator() : MII(nullptr) {}<br class="gmail_msg">
<br class="gmail_msg">
+ /// Explicit conversion between forward/reverse iterators.<br class="gmail_msg">
+ ///<br class="gmail_msg">
+ /// Translate between forward and reverse iterators without changing range<br class="gmail_msg">
+ /// boundaries. The resulting iterator will dereference (and have a handle)<br class="gmail_msg">
+ /// to the previous node, which is somewhat unexpected; but converting the<br class="gmail_msg">
+ /// two endpoints in a range will give the same range in reverse.<br class="gmail_msg">
+ ///<br class="gmail_msg">
+ /// This matches std::reverse_iterator conversions.<br class="gmail_msg">
+ explicit MachineInstrBundleIterator(<br class="gmail_msg">
+ const MachineInstrBundleIterator<Ty, !IsReverse> &I)<br class="gmail_msg">
+ : MachineInstrBundleIterator(++I.getReverse()) {}<br class="gmail_msg">
+<br class="gmail_msg">
/// Get the bundle iterator for the given instruction's bundle.<br class="gmail_msg">
static MachineInstrBundleIterator getAtBundleBegin(instr_iterator MI) {<br class="gmail_msg">
return MachineInstrBundleIteratorHelper<IsReverse>::getBundleBegin(MI);<br class="gmail_msg">
@@ -258,6 +270,11 @@ public:<br class="gmail_msg">
<br class="gmail_msg">
nonconst_iterator getNonConstIterator() const { return MII.getNonConst(); }<br class="gmail_msg">
<br class="gmail_msg">
+ /// Get a reverse iterator to the same node.<br class="gmail_msg">
+ ///<br class="gmail_msg">
+ /// Gives a reverse iterator that will dereference (and have a handle) to the<br class="gmail_msg">
+ /// same node. Converting the endpoint iterators in a range will give a<br class="gmail_msg">
+ /// different range; for range operations, use the explicit conversions.<br class="gmail_msg">
reverse_iterator getReverse() const { return MII.getReverse(); }<br class="gmail_msg">
};<br class="gmail_msg">
<br class="gmail_msg">
<br class="gmail_msg">
Modified: llvm/trunk/unittests/ADT/IListIteratorTest.cpp<br class="gmail_msg">
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/ADT/IListIteratorTest.cpp?rev=294349&r1=294348&r2=294349&view=diff" rel="noreferrer" class="gmail_msg" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/ADT/IListIteratorTest.cpp?rev=294349&r1=294348&r2=294349&view=diff</a><br class="gmail_msg">
==============================================================================<br class="gmail_msg">
--- llvm/trunk/unittests/ADT/IListIteratorTest.cpp (original)<br class="gmail_msg">
+++ llvm/trunk/unittests/ADT/IListIteratorTest.cpp Tue Feb 7 15:03:50 2017<br class="gmail_msg">
@@ -131,4 +131,44 @@ TEST(IListIteratorTest, CheckEraseRevers<br class="gmail_msg">
EXPECT_EQ(L.rend(), RI);<br class="gmail_msg">
}<br class="gmail_msg">
<br class="gmail_msg">
+TEST(IListIteratorTest, ReverseConstructor) {<br class="gmail_msg">
+ simple_ilist<Node> L;<br class="gmail_msg">
+ const simple_ilist<Node> &CL = L;<br class="gmail_msg">
+ Node A, B;<br class="gmail_msg">
+ L.insert(L.end(), A);<br class="gmail_msg">
+ L.insert(L.end(), B);<br class="gmail_msg">
+<br class="gmail_msg">
+ // Save typing.<br class="gmail_msg">
+ typedef simple_ilist<Node>::iterator iterator;<br class="gmail_msg">
+ typedef simple_ilist<Node>::reverse_iterator reverse_iterator;<br class="gmail_msg">
+ typedef simple_ilist<Node>::const_iterator const_iterator;<br class="gmail_msg">
+ typedef simple_ilist<Node>::const_reverse_iterator const_reverse_iterator;<br class="gmail_msg">
+<br class="gmail_msg">
+ // Check conversion values.<br class="gmail_msg">
+ EXPECT_EQ(L.begin(), iterator(L.rend()));<br class="gmail_msg">
+ EXPECT_EQ(++L.begin(), iterator(++L.rbegin()));<br class="gmail_msg">
+ EXPECT_EQ(L.end(), iterator(L.rbegin()));<br class="gmail_msg">
+ EXPECT_EQ(L.rbegin(), reverse_iterator(L.end()));<br class="gmail_msg">
+ EXPECT_EQ(++L.rbegin(), reverse_iterator(++L.begin()));<br class="gmail_msg">
+ EXPECT_EQ(L.rend(), reverse_iterator(L.begin()));<br class="gmail_msg">
+<br class="gmail_msg">
+ // Check const iterator constructors.<br class="gmail_msg">
+ EXPECT_EQ(CL.begin(), const_iterator(L.rend()));<br class="gmail_msg">
+ EXPECT_EQ(CL.begin(), const_iterator(CL.rend()));<br class="gmail_msg">
+ EXPECT_EQ(CL.rbegin(), const_reverse_iterator(L.end()));<br class="gmail_msg">
+ EXPECT_EQ(CL.rbegin(), const_reverse_iterator(CL.end()));<br class="gmail_msg">
+<br class="gmail_msg">
+ // Confirm lack of implicit conversions.<br class="gmail_msg">
+ static_assert(std::is_convertible<iterator, reverse_iterator>::value,<br class="gmail_msg">
+ "unexpected implicit conversion");<br class="gmail_msg">
+ static_assert(std::is_convertible<reverse_iterator, iterator>::value,<br class="gmail_msg">
+ "unexpected implicit conversion");<br class="gmail_msg">
+ static_assert(<br class="gmail_msg">
+ std::is_convertible<const_iterator, const_reverse_iterator>::value,<br class="gmail_msg">
+ "unexpected implicit conversion");<br class="gmail_msg">
+ static_assert(<br class="gmail_msg">
+ std::is_convertible<const_reverse_iterator, const_iterator>::value,<br class="gmail_msg">
+ "unexpected implicit conversion");<br class="gmail_msg">
+}<br class="gmail_msg">
+<br class="gmail_msg">
} // end namespace<br class="gmail_msg">
<br class="gmail_msg">
Modified: llvm/trunk/unittests/CodeGen/MachineInstrBundleIteratorTest.cpp<br class="gmail_msg">
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/CodeGen/MachineInstrBundleIteratorTest.cpp?rev=294349&r1=294348&r2=294349&view=diff" rel="noreferrer" class="gmail_msg" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/unittests/CodeGen/MachineInstrBundleIteratorTest.cpp?rev=294349&r1=294348&r2=294349&view=diff</a><br class="gmail_msg">
==============================================================================<br class="gmail_msg">
--- llvm/trunk/unittests/CodeGen/MachineInstrBundleIteratorTest.cpp (original)<br class="gmail_msg">
+++ llvm/trunk/unittests/CodeGen/MachineInstrBundleIteratorTest.cpp Tue Feb 7 15:03:50 2017<br class="gmail_msg">
@@ -130,4 +130,68 @@ TEST(MachineInstrBundleIteratorTest, Com<br class="gmail_msg">
ASSERT_TRUE(CI != CMBI.getIterator());<br class="gmail_msg">
}<br class="gmail_msg">
<br class="gmail_msg">
+struct MyUnbundledInstr<br class="gmail_msg">
+ : ilist_node<MyUnbundledInstr, ilist_sentinel_tracking<true>> {<br class="gmail_msg">
+ bool isBundledWithPred() const { return false; }<br class="gmail_msg">
+ bool isBundledWithSucc() const { return false; }<br class="gmail_msg">
+};<br class="gmail_msg">
+typedef MachineInstrBundleIterator<MyUnbundledInstr> unbundled_iterator;<br class="gmail_msg">
+typedef MachineInstrBundleIterator<const MyUnbundledInstr><br class="gmail_msg">
+ const_unbundled_iterator;<br class="gmail_msg">
+typedef MachineInstrBundleIterator<MyUnbundledInstr, true><br class="gmail_msg">
+ reverse_unbundled_iterator;<br class="gmail_msg">
+typedef MachineInstrBundleIterator<const MyUnbundledInstr, true><br class="gmail_msg">
+ const_reverse_unbundled_iterator;<br class="gmail_msg">
+<br class="gmail_msg">
+TEST(MachineInstrBundleIteratorTest, ReverseConstructor) {<br class="gmail_msg">
+ simple_ilist<MyUnbundledInstr, ilist_sentinel_tracking<true>> L;<br class="gmail_msg">
+ const auto &CL = L;<br class="gmail_msg">
+ MyUnbundledInstr A, B;<br class="gmail_msg">
+ L.insert(L.end(), A);<br class="gmail_msg">
+ L.insert(L.end(), B);<br class="gmail_msg">
+<br class="gmail_msg">
+ // Save typing.<br class="gmail_msg">
+ typedef MachineInstrBundleIterator<MyUnbundledInstr> iterator;<br class="gmail_msg">
+ typedef MachineInstrBundleIterator<MyUnbundledInstr, true> reverse_iterator;<br class="gmail_msg">
+ typedef MachineInstrBundleIterator<const MyUnbundledInstr> const_iterator;<br class="gmail_msg">
+ typedef MachineInstrBundleIterator<const MyUnbundledInstr, true><br class="gmail_msg">
+ const_reverse_iterator;<br class="gmail_msg">
+<br class="gmail_msg">
+ // Convert to bundle iterators.<br class="gmail_msg">
+ auto begin = [&]() -> iterator { return L.begin(); };<br class="gmail_msg">
+ auto end = [&]() -> iterator { return L.end(); };<br class="gmail_msg">
+ auto rbegin = [&]() -> reverse_iterator { return L.rbegin(); };<br class="gmail_msg">
+ auto rend = [&]() -> reverse_iterator { return L.rend(); };<br class="gmail_msg">
+ auto cbegin = [&]() -> const_iterator { return CL.begin(); };<br class="gmail_msg">
+ auto cend = [&]() -> const_iterator { return CL.end(); };<br class="gmail_msg">
+ auto crbegin = [&]() -> const_reverse_iterator { return CL.rbegin(); };<br class="gmail_msg">
+ auto crend = [&]() -> const_reverse_iterator { return CL.rend(); };<br class="gmail_msg">
+<br class="gmail_msg">
+ // Check conversion values.<br class="gmail_msg">
+ EXPECT_EQ(begin(), iterator(rend()));<br class="gmail_msg">
+ EXPECT_EQ(++begin(), iterator(++rbegin()));<br class="gmail_msg">
+ EXPECT_EQ(end(), iterator(rbegin()));<br class="gmail_msg">
+ EXPECT_EQ(rbegin(), reverse_iterator(end()));<br class="gmail_msg">
+ EXPECT_EQ(++rbegin(), reverse_iterator(++begin()));<br class="gmail_msg">
+ EXPECT_EQ(rend(), reverse_iterator(begin()));<br class="gmail_msg">
+<br class="gmail_msg">
+ // Check const iterator constructors.<br class="gmail_msg">
+ EXPECT_EQ(cbegin(), const_iterator(rend()));<br class="gmail_msg">
+ EXPECT_EQ(cbegin(), const_iterator(crend()));<br class="gmail_msg">
+ EXPECT_EQ(crbegin(), const_reverse_iterator(end()));<br class="gmail_msg">
+ EXPECT_EQ(crbegin(), const_reverse_iterator(cend()));<br class="gmail_msg">
+<br class="gmail_msg">
+ // Confirm lack of implicit conversions.<br class="gmail_msg">
+ static_assert(!std::is_convertible<iterator, reverse_iterator>::value,<br class="gmail_msg">
+ "unexpected implicit conversion");<br class="gmail_msg">
+ static_assert(!std::is_convertible<reverse_iterator, iterator>::value,<br class="gmail_msg">
+ "unexpected implicit conversion");<br class="gmail_msg">
+ static_assert(<br class="gmail_msg">
+ !std::is_convertible<const_iterator, const_reverse_iterator>::value,<br class="gmail_msg">
+ "unexpected implicit conversion");<br class="gmail_msg">
+ static_assert(<br class="gmail_msg">
+ !std::is_convertible<const_reverse_iterator, const_iterator>::value,<br class="gmail_msg">
+ "unexpected implicit conversion");<br class="gmail_msg">
+}<br class="gmail_msg">
+<br class="gmail_msg">
} // end namespace<br class="gmail_msg">
<br class="gmail_msg">
<br class="gmail_msg">
_______________________________________________<br class="gmail_msg">
llvm-commits mailing list<br class="gmail_msg">
<a href="mailto:llvm-commits@lists.llvm.org" class="gmail_msg" target="_blank">llvm-commits@lists.llvm.org</a><br class="gmail_msg">
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits" rel="noreferrer" class="gmail_msg" target="_blank">http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits</a><br class="gmail_msg">
</blockquote></div></div>