floating point bitwise and/or

199 views
Skip to first unread message

Simon Byrne

unread,
Jan 20, 2015, 7:47:48 AM1/20/15
to juli...@googlegroups.com
In certain algorithms (particularly double-double style arithmetic) it is necessary to and/or individual bits of a floating point number. At the moment, the easiest way to do this in Julia is to reinterpret to the appropriately sized UInt and reinterpret back when done. The code_native of this seems to indicate that this is basically what the compiler ends up doing as well.

However x86 offers native bitwise instructions for floats (ANDPD, etc.): is there any way to access these through Julia? LLVM does seems to make this available through FAND, FOR, etc:

simon

Erik Schnetter

unread,
Jan 20, 2015, 11:28:33 AM1/20/15
to juli...@googlegroups.com
Wow, I would have expected LLVM to handle this kind of low-level detail.

Here is `fabs`, implemented manually:

julia> f(x::Float64) = reinterpret(Float64, reinterpret(UInt64,x) & ~reinterpret(UIn64, -0.0))

Here is the resulting code:

julia> code_native(f, (Float64,))
.section __TEXT,__text,regular,pure_instructions
Filename: none
Source line: 1
push RBP
mov RBP, RSP
Source line: 1
vmovq RAX, XMM0
movabs RCX, 9223372036854775807
and RCX, RAX
vmovq XMM0, RCX
pop RBP
ret

Why doesn't LLVM use vandpd???

This is LLVM 3.3. Did you check LLVM 3.5?

I'd rather have LLVM handle this, as it has all the information it needs. But if it doesn't, then we definitely have to do this manually in Julia. If only to improve the performance of `abs` and `copysign`!

Did you raise this on the LLVM developers' list? Maybe there is a reason for this?

-erik
--
Erik Schnetter <schn...@gmail.com>
http://www.perimeterinstitute.ca/personal/eschnetter/

My email is as private as my paper mail. I therefore support encrypting
and signing email messages. Get my PGP key from https://sks-keyservers.net.

signature.asc

Stefan Karpinski

unread,
Jan 20, 2015, 12:05:35 PM1/20/15
to Julia Dev
LLVM is not great about this sort of thing. The flavor of LLVM instruction you use tends to force the kinds of registers and x86 instructions it uses, even when there are alternative ways to express the operation that would have allowed keeping the data in a single register instead of shuttling it back and forth. So it may be worth it for us to expose the floating-point bitwise operations somehow just so that we can work around that. Of course, the better long-term fix is making LLVM smarter about this, but I'm not sure we should be spearheading that effort.

Erik Schnetter

unread,
Jan 20, 2015, 5:44:36 PM1/20/15
to juli...@googlegroups.com
Should we expose them as intrinsics only, as functions private to Base, or should we just overload & | ~ for some of the floating-point types?

-erik
signature.asc

Stefan Karpinski

unread,
Jan 20, 2015, 6:25:22 PM1/20/15
to Julia Dev
Overloading operators for floating-point types seems reasonable to me, but you need intrinsics first in any case, so that's a safe starting point if someone wants to do this.

Erik Schnetter

unread,
Jan 20, 2015, 6:57:04 PM1/20/15
to juli...@googlegroups.com
Okay, I'll do this.

-erik
signature.asc

Erik Schnetter

unread,
Jan 20, 2015, 7:29:56 PM1/20/15
to juli...@googlegroups.com
Nope, can't do this. Not enough llvm-fu. The FADD etc. instructions are specific to the X86 back-end, and I don't know how to access them from IRBuilder.

-erik
signature.asc

Stefan Karpinski

unread,
Jan 21, 2015, 1:14:23 AM1/21/15
to Julia Dev
Ok, can you or Simon open an issue about this? It should be done but seems somewhat difficult. Accessing x86-specific LLVM intrinsics is a bit tricky, but certainly doable.

Simon Byrne

unread,
Jan 21, 2015, 4:16:15 AM1/21/15
to juli...@googlegroups.com
Reply all
Reply to author
Forward
0 new messages