<div dir="ltr"><div class="gmail_extra"><div class="gmail_quote">On Tue, Sep 9, 2014 at 9:50 AM, John Regehr <span dir="ltr"><<a href="mailto:regehr@cs.utah.edu" target="_blank">regehr@cs.utah.edu</a>></span> wrote:<br><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">In the section about poison values, the LLVM language reference manual says:<br>
<br>
  "Values other than phi nodes depend on their operands."<br>
<br>
This implies that a select instruction's output can be poisoned by its not-selected argument value. If select were poisoned only by its selected argument, we would expect this fact to be mentioned specifically, as it is for phi.<br>
<br>
Next I'll show how poisoning by the not-selected value can introduce a problem. Take this C program:<br>
<br>
int printf(const char *, ...);<br>
int foo(int x0) {<br>
  int x3 = x0 >> 27;<br>
  int x4 = x3 - 27;<br>
  int x2 = x4 ? x4 : (1 >> x4);<br>
  int x1 = x2 != 0;<br>
  return x1;<br>
}<br>
int arg;<br>
int main (void) {<br>
  int x1 = foo(arg);<br>
  printf("%x\n", x1);<br>
  return 0;<br>
}<br>
<br>
This program has no UB and it should print "1'.<br>
<br>
Clang at -O2 turns foo() into this:<br>
<br>
define i32 @foo(i32 %x0) #0 {<br>
entry:<br>
  %shr = ashr i32 %x0, 27<br>
  %sub = add nsw i32 %shr, -27<br>
  %tobool = icmp ne i32 %sub, 0<br>
  %shr1 = lshr i32 1, %sub<br>
  %cond = select i1 %tobool, i32 %sub, i32 %shr1<br>
  %cmp = icmp ne i32 %cond, 0<br>
  %conv = zext i1 %cmp to i32<br>
  ret i32 %conv<br>
}<br>
<br>
Although the translation is very straightforward, there's a problem: %shr1 is a poison value and although it is not selected, it propagates through the rest of the function and poisons the return value.<br>
<br>
Obviously things are not going well if the source program contains no UB and the emitted code returns a poison value. Either there has been a miscompilation or else the LLVM documentation should be changed to make it clear that the select instruction only has a value dependence on the value that is selected.<br></blockquote><div><br></div><div>While the documentation may not match the facts on the ground, InstructionSimplify does (in my opinion) the right thing; an undef operand doesn't mean the entire SelectInst folds away to undef:</div><div><a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Analysis/InstructionSimplify.cpp?revision=217342&view=markup#l2880">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Analysis/InstructionSimplify.cpp?revision=217342&view=markup#l2880</a></div><div> </div><blockquote class="gmail_quote" style="margin:0px 0px 0px 0.8ex;border-left-width:1px;border-left-color:rgb(204,204,204);border-left-style:solid;padding-left:1ex">
<br>
The immediate problem here is that both Souper and Alive are happy for foo() to return 0 instead of 1. Souper actually does this optimization -- legally, of course, according to the reference manual.<br>
<br>
Anyway this issue seemed tricky enough to bring up here instead of just filing a PR.<br>
<br>
Thanks,<br>
<br>
John<br>
______________________________<u></u>_________________<br>
LLVM Developers mailing list<br>
<a href="mailto:LLVMdev@cs.uiuc.edu" target="_blank">LLVMdev@cs.uiuc.edu</a>         <a href="http://llvm.cs.uiuc.edu" target="_blank">http://llvm.cs.uiuc.edu</a><br>
<a href="http://lists.cs.uiuc.edu/mailman/listinfo/llvmdev" target="_blank">http://lists.cs.uiuc.edu/<u></u>mailman/listinfo/llvmdev</a><br>
</blockquote></div><br></div></div>