<div dir="ltr"><br><div class="gmail_extra"><br><div class="gmail_quote">On Wed, Feb 4, 2015 at 5:47 PM, Sanjoy Das <span dir="ltr"><<a href="mailto:sanjoy@playingwithpointers.com" target="_blank">sanjoy@playingwithpointers.com</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"><span class="">> Turns out that undef + fast math flags is enough to cause LLVM to become<br>
> inconsistent:<br>
> define i1 @f(i1 %a.is_nan, float %a, float %b) {<br>
>   %add = fadd nnan float %a, %b<br>
>   %sel = select i1 %a.is_nan, float undef, float %add<br>
>   %cmp = fcmp ord float %b, %sel<br>
>   ret i1 %cmp<br>
> }<br>
><br>
> When 'b' is NaN, the following occurs:<br>
> %add = float undef<br>
> %sel = float undef<br>
> %cmp = i1 false<br>
><br>
> However, the 'select i1 %A, %B, undef' -> 'undef' optimization permits us to<br>
<br>
</span>How can you transform 'select X, Y, undef' to undef?  What if X is<br>
true?  Did you mean 'select X, undef, undef' -> undef?<br></blockquote><div><br></div><div>Sorry, I meant 'select X, Y, undef' to 'Y'</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">
<span class=""><br>
> transform @f to:<br>
> define i1 @f(i1 %a.is_nan, float %a, float %b) {<br>
>   %add = fadd nnan float %a, %b<br>
>   %cmp = fcmp ord float %add, 0.000000e+00<br>
<br>
</span>I don't see how you got here -- %cmp was "fcmp ord float %b, %sel".<br>
Now %b is NaN so %add is undef, making %cmp = "fcmp ord NaN, undef"<br>
which is false for any value of undef.<br></blockquote><div><br></div><div>Just to be clear, I agree. This is why I said that %cmp = i1 false in the untransformed @f.</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>
Maybe I'm being thick, but I think it will help if you break down the<br>
second half of your argument into smaller steps. :)<br></blockquote><div><br></div><div>We start with:</div><div><div>define i1 @f(i1 %a.is_nan, float %a, float %b) {</div><div>  %add = fadd nnan float %a, %b</div><div>  %sel = select i1 %a.is_nan, float undef, float %add</div><div>  %cmp = fcmp ord float %b, %sel</div><div>  ret i1 %cmp</div><div>}</div></div><div><br></div><div>LLVM (currently) permits 'select i1 %a.is_nan, float undef, float %add' to turn into '%add', this leaves us with:</div><div><div>define i1 @f(i1 %a.is_nan, float %a, float %b) {</div><div>  %add = fadd nnan float %a, %b</div><div>  %cmp = fcmp ord float %b, %add<br></div><div>  ret i1 %cmp</div><div>}</div></div><div><br></div><div>'fadd nnan' claims that it is allowed to assume that its operands can't be NaN and that those which value depend on the value will not get NaN.  I believe this would let 'fcmp' assume that it only needs to look at the result of '%add':</div><div><div>define i1 @f(i1 %a.is_nan, float %a, float %b) {</div><div>  %add = fadd nnan float %a, %b</div><div>  %cmp = fcmp ord float 0., %add</div><div>  ret i1 %cmp</div><div>}</div></div><div><br></div><div><br></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>
Having said that I won't be surprised if fast-math flags suffer from<br>
issues similar to poison -- "Allow algebraically equivalent<br>
transformations that may dramatically change results in floating<br>
point" sounds somewhat vague to me.<br>
<br>
-- Sanjoy<br>
<span class=""><br>
>   ret i1 %cmp<br>
> }<br>
><br>
> Now we will have:<br>
> %add = float undef<br>
> %cmp = i1 undef<br>
><br>
><br>
>><br>
>><br>
>><br>
>> John<br>
><br>
><br>
><br>
</span>> _______________________________________________<br>
> LLVM Developers mailing list<br>
> <a href="mailto:LLVMdev@cs.uiuc.edu">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/mailman/listinfo/llvmdev</a><br>
><br>
</blockquote></div><br></div></div>