[llvm-dev] fptosi undefined behaviour
Simon Byrne via llvm-dev
llvm-dev at lists.llvm.org
Fri Jan 22 11:45:30 PST 2016
Hi all,
Consider the following snippet, the aim of which is to convert a
double to a signed i16, returning 0 if not exactly representable:
define i16 @foo(double) {
top:
%1 = fptosi double %0 to i16
%2 = sitofp i16 %1 to double
%3 = fcmp une double %2, %0
%4 = select i1 %3, i16 0, i16 %1
ret i16 %4
}
Of course, if the value is out-of-range, the result of fptosi is
undefined. Nevertheless, the snippet works on x86 & x86_64, generating
what to me seems to be fairly efficient code for the task.
However it breaks on ARM, with foo(200000.0) => 3392. From what I can
tell (given my very limited knowledge of LLVM IR, assembler and ARM
architecture), the first line is returning a value out-of-range of the
i16 type.
1) I realise this is a somewhat silly question, but is this still
acceptable "undefined behaviour"?
2) If so, is there a way to do this in an efficient manner without
relying on undefined behaviour? (i.e. I can introduce a range check
before the fptosi call, but this would add further overhead).
(for further context, this problem originally arose in the Julia issue
https://github.com/JuliaLang/julia/issues/14549)
Thanks,
Simon
More information about the llvm-dev
mailing list