<div dir="ltr">I'd sort of rather have a simple "empty(range)" function that could be applied to any range (equality between iterators should be constant time - it seems unlikely it's ever going to be substantially more expensive to test range.begin() == range.end() than some custom empty implementation for any given sequence) & have more range accessors anywhere they're not already available.<br><br>Not sure what other people think.<br><br>- David</div><div class="gmail_extra"><br><div class="gmail_quote">On Mon, Jan 12, 2015 at 7:46 PM, Ramkumar Ramachandra <span dir="ltr"><<a href="mailto:artagnon@gmail.com" target="_blank">artagnon@gmail.com</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: artagnon<br>
Date: Mon Jan 12 21:46:47 2015<br>
New Revision: 225760<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=225760&view=rev" target="_blank">http://llvm.org/viewvc/llvm-project?rev=225760&view=rev</a><br>
Log:<br>
Standardize {pred,succ,use,user}_empty()<br>
<br>
The functions {pred,succ,use,user}_{begin,end} exist, but many users<br>
have to check *_begin() with *_end() by hand to determine if the<br>
BasicBlock or User is empty. Fix this with a standard *_empty(),<br>
demonstrating a few usecases.<br>
<br>
Modified:<br>
    llvm/trunk/include/llvm/IR/CFG.h<br>
    llvm/trunk/include/llvm/IR/Value.h<br>
    llvm/trunk/lib/Analysis/CFG.cpp<br>
    llvm/trunk/lib/IR/Verifier.cpp<br>
    llvm/trunk/lib/Transforms/IPO/PruneEH.cpp<br>
    llvm/trunk/lib/Transforms/Scalar/JumpThreading.cpp<br>
    llvm/trunk/lib/Transforms/Scalar/Reg2Mem.cpp<br>
    llvm/trunk/lib/Transforms/Utils/SimplifyCFG.cpp<br>
<br>
Modified: llvm/trunk/include/llvm/IR/CFG.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/IR/CFG.h?rev=225760&r1=225759&r2=225760&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/IR/CFG.h?rev=225760&r1=225759&r2=225760&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/IR/CFG.h (original)<br>
+++ llvm/trunk/include/llvm/IR/CFG.h Mon Jan 12 21:46:47 2015<br>
@@ -93,6 +93,9 @@ inline pred_iterator pred_end(BasicBlock<br>
 inline const_pred_iterator pred_end(const BasicBlock *BB) {<br>
   return const_pred_iterator(BB, true);<br>
 }<br>
+inline bool pred_empty(const BasicBlock *BB) {<br>
+  return pred_begin(BB) == pred_end(BB);<br>
+}<br>
<br>
<br>
<br>
@@ -257,6 +260,9 @@ inline succ_iterator succ_end(BasicBlock<br>
 inline succ_const_iterator succ_end(const BasicBlock *BB) {<br>
   return succ_const_iterator(BB->getTerminator(), true);<br>
 }<br>
+inline bool succ_empty(const BasicBlock *BB) {<br>
+  return succ_begin(BB) == succ_end(BB);<br>
+}<br>
<br>
 template <typename T, typename U> struct isPodLike<SuccIterator<T, U> > {<br>
   static const bool value = isPodLike<T>::value;<br>
<br>
Modified: llvm/trunk/include/llvm/IR/Value.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/IR/Value.h?rev=225760&r1=225759&r2=225760&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/IR/Value.h?rev=225760&r1=225759&r2=225760&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/IR/Value.h (original)<br>
+++ llvm/trunk/include/llvm/IR/Value.h Mon Jan 12 21:46:47 2015<br>
@@ -286,6 +286,8 @@ public:<br>
     return iterator_range<const_use_iterator>(use_begin(), use_end());<br>
   }<br>
<br>
+  bool               user_empty() const { return UseList == nullptr; }<br>
+<br>
   typedef user_iterator_impl<User>       user_iterator;<br>
   typedef user_iterator_impl<const User> const_user_iterator;<br>
   user_iterator       user_begin()       { return user_iterator(UseList); }<br>
<br>
Modified: llvm/trunk/lib/Analysis/CFG.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Analysis/CFG.cpp?rev=225760&r1=225759&r2=225760&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Analysis/CFG.cpp?rev=225760&r1=225759&r2=225760&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/Analysis/CFG.cpp (original)<br>
+++ llvm/trunk/lib/Analysis/CFG.cpp Mon Jan 12 21:46:47 2015<br>
@@ -27,7 +27,7 @@ using namespace llvm;<br>
 void llvm::FindFunctionBackedges(const Function &F,<br>
      SmallVectorImpl<std::pair<const BasicBlock*,const BasicBlock*> > &Result) {<br>
   const BasicBlock *BB = &F.getEntryBlock();<br>
-  if (succ_begin(BB) == succ_end(BB))<br>
+  if (succ_empty(BB))<br>
     return;<br>
<br>
   SmallPtrSet<const BasicBlock*, 8> Visited;<br>
<br>
Modified: llvm/trunk/lib/IR/Verifier.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/IR/Verifier.cpp?rev=225760&r1=225759&r2=225760&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/IR/Verifier.cpp?rev=225760&r1=225759&r2=225760&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/IR/Verifier.cpp (original)<br>
+++ llvm/trunk/lib/IR/Verifier.cpp Mon Jan 12 21:46:47 2015<br>
@@ -1128,7 +1128,7 @@ void Verifier::visitFunction(const Funct<br>
<br>
     // Check the entry node<br>
     const BasicBlock *Entry = &F.getEntryBlock();<br>
-    Assert1(pred_begin(Entry) == pred_end(Entry),<br>
+    Assert1(pred_empty(Entry),<br>
             "Entry block to function must not have predecessors!", Entry);<br>
<br>
     // The address of the entry block cannot be taken, unless it is dead.<br>
<br>
Modified: llvm/trunk/lib/Transforms/IPO/PruneEH.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/IPO/PruneEH.cpp?rev=225760&r1=225759&r2=225760&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/IPO/PruneEH.cpp?rev=225760&r1=225759&r2=225760&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/Transforms/IPO/PruneEH.cpp (original)<br>
+++ llvm/trunk/lib/Transforms/IPO/PruneEH.cpp Mon Jan 12 21:46:47 2015<br>
@@ -200,7 +200,7 @@ bool PruneEH::SimplifyFunction(Function<br>
         BB->getInstList().pop_back();<br>
<br>
         // If the unwind block is now dead, nuke it.<br>
-        if (pred_begin(UnwindBlock) == pred_end(UnwindBlock))<br>
+        if (pred_empty(UnwindBlock))<br>
           DeleteBasicBlock(UnwindBlock);  // Delete the new BB.<br>
<br>
         ++NumRemoved;<br>
@@ -234,7 +234,7 @@ bool PruneEH::SimplifyFunction(Function<br>
 /// updating the callgraph to reflect any now-obsolete edges due to calls that<br>
 /// exist in the BB.<br>
 void PruneEH::DeleteBasicBlock(BasicBlock *BB) {<br>
-  assert(pred_begin(BB) == pred_end(BB) && "BB is not dead!");<br>
+  assert(pred_empty(BB) && "BB is not dead!");<br>
   CallGraph &CG = getAnalysis<CallGraphWrapperPass>().getCallGraph();<br>
<br>
   CallGraphNode *CGN = CG[BB->getParent()];<br>
<br>
Modified: llvm/trunk/lib/Transforms/Scalar/JumpThreading.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/JumpThreading.cpp?rev=225760&r1=225759&r2=225760&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/JumpThreading.cpp?rev=225760&r1=225759&r2=225760&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/Transforms/Scalar/JumpThreading.cpp (original)<br>
+++ llvm/trunk/lib/Transforms/Scalar/JumpThreading.cpp Mon Jan 12 21:46:47 2015<br>
@@ -188,7 +188,7 @@ bool JumpThreading::runOnFunction(Functi<br>
<br>
       // If the block is trivially dead, zap it.  This eliminates the successor<br>
       // edges which simplifies the CFG.<br>
-      if (pred_begin(BB) == pred_end(BB) &&<br>
+      if (pred_empty(BB) &&<br>
           BB != &BB->getParent()->getEntryBlock()) {<br>
         DEBUG(dbgs() << "  JT: Deleting dead block '" << BB->getName()<br>
               << "' with terminator: " << *BB->getTerminator() << '\n');<br>
@@ -662,7 +662,7 @@ static bool hasAddressTakenAndUsed(Basic<br>
 bool JumpThreading::ProcessBlock(BasicBlock *BB) {<br>
   // If the block is trivially dead, just return and let the caller nuke it.<br>
   // This simplifies other transformations.<br>
-  if (pred_begin(BB) == pred_end(BB) &&<br>
+  if (pred_empty(BB) &&<br>
       BB != &BB->getParent()->getEntryBlock())<br>
     return false;<br>
<br>
<br>
Modified: llvm/trunk/lib/Transforms/Scalar/Reg2Mem.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/Reg2Mem.cpp?rev=225760&r1=225759&r2=225760&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Scalar/Reg2Mem.cpp?rev=225760&r1=225759&r2=225760&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/Transforms/Scalar/Reg2Mem.cpp (original)<br>
+++ llvm/trunk/lib/Transforms/Scalar/Reg2Mem.cpp Mon Jan 12 21:46:47 2015<br>
@@ -73,7 +73,7 @@ bool RegToMem::runOnFunction(Function &F<br>
<br>
   // Insert all new allocas into entry block.<br>
   BasicBlock *BBEntry = &F.getEntryBlock();<br>
-  assert(pred_begin(BBEntry) == pred_end(BBEntry) &&<br>
+  assert(pred_empty(BBEntry) &&<br>
          "Entry block to function must not have predecessors!");<br>
<br>
   // Find first non-alloca instruction and create insertion point. This is<br>
<br>
Modified: llvm/trunk/lib/Transforms/Utils/SimplifyCFG.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Utils/SimplifyCFG.cpp?rev=225760&r1=225759&r2=225760&view=diff" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/Utils/SimplifyCFG.cpp?rev=225760&r1=225759&r2=225760&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/Transforms/Utils/SimplifyCFG.cpp (original)<br>
+++ llvm/trunk/lib/Transforms/Utils/SimplifyCFG.cpp Mon Jan 12 21:46:47 2015<br>
@@ -3020,7 +3020,7 @@ bool SimplifyCFGOpt::SimplifyReturn(Retu<br>
     }<br>
<br>
     // If we eliminated all predecessors of the block, delete the block now.<br>
-    if (pred_begin(BB) == pred_end(BB))<br>
+    if (pred_empty(BB))<br>
       // We know there are no successors, so just nuke the block.<br>
       BB->eraseFromParent();<br>
<br>
@@ -3193,7 +3193,7 @@ bool SimplifyCFGOpt::SimplifyUnreachable<br>
   }<br>
<br>
   // If this block is now dead, remove it.<br>
-  if (pred_begin(BB) == pred_end(BB) &&<br>
+  if (pred_empty(BB) &&<br>
       BB != &BB->getParent()->getEntryBlock()) {<br>
     // We know there are no successors, so just nuke the block.<br>
     BB->eraseFromParent();<br>
@@ -4587,7 +4587,7 @@ bool SimplifyCFGOpt::run(BasicBlock *BB)<br>
<br>
   // Remove basic blocks that have no predecessors (except the entry block)...<br>
   // or that just have themself as a predecessor.  These are unreachable.<br>
-  if ((pred_begin(BB) == pred_end(BB) &&<br>
+  if ((pred_emtpy(BB) &&<br>
        BB != &BB->getParent()->getEntryBlock()) ||<br>
       BB->getSinglePredecessor() == BB) {<br>
     DEBUG(dbgs() << "Removing BB: \n" << *BB);<br>
<br>
<br>
_______________________________________________<br>
llvm-commits mailing list<br>
<a href="mailto:llvm-commits@cs.uiuc.edu">llvm-commits@cs.uiuc.edu</a><br>
<a href="http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits" target="_blank">http://lists.cs.uiuc.edu/mailman/listinfo/llvm-commits</a><br>
</blockquote></div><br></div>