<div dir="ltr">FWIW, now that postdom is fixed, all the possible "returns/exits" of the function should be direct children of the virtual exit node in the post-dom tree.<div><br></div><div>Thus, the following would work to detect whether each block is a real return or not:</div><div><br></div><div><div>  for (auto &PDTChild : children<DomTreeNode *>(PDT.getRootNode())) {</div><div>    auto *BB = PDTChild->getBlock();</div><div>    auto &Info = BlockInfo[BB];</div><div>    // Real function return</div><div>    if (isa<ReturnInst>(Info.Terminator)) {</div><div>      DEBUG(dbgs() << "post-dom root child is a return: " << BB->getName()</div><div>                   << '\n';);</div><div>      continue;</div><div>    }</div><div>    // PDTChild is something else, like a no-return or infinite loop</div><div>  }<br></div></div><div><br></div><div><br></div><div>You could also just  insert a br i1 false <merged function return>, <existing infinite loop branch> to have a single exit.</div><div>Until you simplify the cfg, it would work.</div><div><br></div></div><div class="gmail_extra"><br><div class="gmail_quote">On Thu, Mar 2, 2017 at 8:08 AM, Christian König via llvm-dev <span dir="ltr"><<a href="mailto:llvm-dev@lists.llvm.org" target="_blank">llvm-dev@lists.llvm.org</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Hi Matt,<br>
<br>
one prerequisite for the algorithm is that each function has exactly one entry and one exit node.<br>
<br>
If I remember correctly there was a LLVM pass called mergereturn or something like that which made sure that you have at most one ret instruction for each function.<br>
<br>
Using that used to be a prerequisite for running the transformation, but that obviously won't work for unreachable instructions.<br>
<br>
The only doable approach I can see is to make the annotator able to handle those. Otherwise you could also have a BB existing a function using ret and another one running into an unreachable.<br>
<br>
Regards,<br>
Christian.<div><div class="h5"><br>
<br>
Am 02.03.2017 um 02:39 schrieb Matt Arsenault:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
Hi,<br>
<br>
I'm trying to solve a problem from StructurizeCFG not actually handling regions with multiple exits. Sample IR attached.<br>
<br>
StructurizeCFG doesn't touch this function, exiting early on the isTopLevelRegion check. SIAnnotateControlFlow then gets confused and ends up inserting an if into one of the blocks, and the matching <a href="http://end.cf" rel="noreferrer" target="_blank">end.cf</a> into one of the return/unreachable blocks. The input to the <a href="http://end.cf" rel="noreferrer" target="_blank">end.cf</a> is then not dominated by the condition which fails the verifier.<br>
<br>
I'm not sure exactly about how to go about fixing this. I see a few options:<br>
<br>
- Try to make the annotator aware of multi exit regions and insert the necessary phis for the input mask values for the <a href="http://end.cf" rel="noreferrer" target="_blank">end.cf</a> calls. This seems undesirable and I'm not sure works in all cases.<br>
<br>
- Make StructurizeCFG duplicate blocks to get simple regions. Is there already code to do this somewhere? CodeExtractor seems to do something similar, but not quite the same. Can this be done in the region pass, or does StructurizeCFG need to be converted to a function pass? RegionInfo mentions support for "extended" regions with multiple exits, but I don't think this helps any here.<br>
<br>
-Matt<br>
<br>
</blockquote>
<br></div></div>
______________________________<wbr>_________________<br>
LLVM Developers mailing list<br>
<a href="mailto:llvm-dev@lists.llvm.org" target="_blank">llvm-dev@lists.llvm.org</a><br>
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/<wbr>mailman/listinfo/llvm-dev</a><br>
</blockquote></div><br></div>