[llvm-dev] llvm intrinsics/libc/libm question

Anton Korobeynikov via llvm-dev llvm-dev at lists.llvm.org
Tue Jun 14 16:20:05 PDT 2016


Mostly because there are fabs / fcopysign instructions in many ISAs.
But nothing like this for floor / trunc.

On Tue, Jun 14, 2016 at 8:15 PM, Ryan Taylor via llvm-dev
<llvm-dev at lists.llvm.org> wrote:
> If I do
>
> T.getArch() == xxx
>    TLI.setUnavailable(LibFunc::copysign)
>
> then this works at generating a call instead of not being able to select the
> ISD::FCOPYSIGN, but I don't know why I don't need to do this for other
> LibFunc functions (such as floor, etc... these generate call just fine)?
>
> Thanks,
> Ryan
>
>
>
> On Tue, Jun 14, 2016 at 11:58 AM, Ryan Taylor <ryta1203 at gmail.com> wrote:
>>
>> I'm still not sure why copysign and fabs have to be lowered to a call when
>> they are represented as a call in the IR?
>>
>> Looks like the DAG makes them into SDNodes.
>>
>>
>> On Thu, Jun 9, 2016 at 2:35 PM, Ahmed Bougacha <ahmed.bougacha at gmail.com>
>> wrote:
>>>
>>> On Thu, Jun 9, 2016 at 11:28 AM, Ryan Taylor <ryta1203 at gmail.com> wrote:
>>> > I'm assuming that "__builtin_" is a keyword in LLVM. If I have code
>>> > like:
>>> >
>>> > #define acos __builtin_acos
>>> >
>>> > extern double acos(double, double);
>>> >
>>> > double a;
>>> > void foo(float b) {
>>> >   a = acos(b);
>>> > }
>>> >
>>> > I never see a call to "__builtin_acos", is LLVM removing the prefix
>>> > __builtin_ ?
>>>
>>> Oh, that's a clang thing, not LLVM:  yes, I think clang has special
>>> handling for __builtin_*, and for libm functions, just turns them into
>>> a regular function call to the function.  That happens in clang
>>> CGBuiltin.cpp, getBuiltinLibFunction.
>>>
>>> By the time LLVM sees the call, yes, it's just a call to "@acos".
>>> There's no such thing as "__builtin_" from LLVM's standpoint, it's
>>> purely a C thing.
>>>
>>> -Ahmed
>>>
>>> > Thanks,
>>> >
>>> > Ryan
>>> >
>>> > On Thu, Jun 9, 2016 at 2:10 PM, Ahmed Bougacha
>>> > <ahmed.bougacha at gmail.com>
>>> > wrote:
>>> >>
>>> >> On Wed, Jun 8, 2016 at 10:43 AM, Ryan Taylor <ryta1203 at gmail.com>
>>> >> wrote:
>>> >> > Correct, it does check based on OS and triple, what I meant was that
>>> >> > it
>>> >> > might be better to have this info in the target specific files and
>>> >> > have
>>> >> > the
>>> >> > LibraryInfo do a look up of that (like most other sections of the
>>> >> > core
>>> >> > code
>>> >> > do, ie have the tablegen or ISelLowering specify the libs etc..)
>>> >>
>>> >> I agree it's not the best place, but one difference is that
>>> >> TargetLibraryInfo is much more about OSes than architectures.
>>> >>
>>> >> > I'm not sure I follow about the RTLIB, I'm able to use an intrinsic
>>> >> > for
>>> >> > floor (def int_floor::Intrinsic in IntrinsicsXXX.td) and still use
>>> >> > RTLIB
>>> >> > to
>>> >> > generate the appropriate name for the function (ie __xxx_floor). It
>>> >> > sounds
>>> >> > like you're implying either/or, not both?
>>> >>
>>> >> No, I'm just saying that RTLIB only solves the codegen problem; you'll
>>> >> need something else (like your intrinsic?) to have better IR
>>> >> optimizations.
>>> >>
>>> >> > I agree, it doesn't seem supported. It looks like I might just need
>>> >> > to
>>> >> > change 'TLI.has' and 'TLI.getName' in order to make this happen
>>> >> > (potentially
>>> >> > removing the prefix here). This goes back to my first point, the TLI
>>> >> > should
>>> >> > be changed to simply get this info generically from the target
>>> >> > information,
>>> >> > you seem to agree with that.
>>> >>
>>> >> Hmm, what are you really trying to do?  If you want LLVM to recognize
>>> >> your __xxx functions: yes, the cleanest solution is probably to teach
>>> >> TLI and its users to recognize the "custom" names, and mark the
>>> >> functions as available with your custom __xxx names.
>>> >>
>>> >> HTH,
>>> >> -Ahmed
>>> >>
>>> >> > Thanks,
>>> >> >
>>> >> > Ryan
>>> >> >
>>> >> > On Tue, Jun 7, 2016 at 7:06 PM, Ahmed Bougacha
>>> >> > <ahmed.bougacha at gmail.com>
>>> >> > wrote:
>>> >> >>
>>> >> >> On Tue, Jun 7, 2016 at 1:57 PM, Ryan Taylor <ryta1203 at gmail.com>
>>> >> >> wrote:
>>> >> >> > Tim,
>>> >> >> >
>>> >> >> > Currently, I have to do multiple things:
>>> >> >> >
>>> >> >> > 1) create some setLibcallNames in XXXISelLowering.cpp to generate
>>> >> >> > correct
>>> >> >> > naming for RTLIBS.
>>> >> >> > 2) lower ISD down to an RTLIB for some calls (and then do
>>> >> >> > solution 1
>>> >> >> > on
>>> >> >> > those to get correct names)
>>> >> >>
>>> >> >> These solve a related but different - CodeGen - problem.
>>> >> >>
>>> >> >> RTLIB libcalls are used when we're not able to select some IR
>>> >> >> instruction/intrinsic so have to rely on a runtime library helper
>>> >> >> function (e.g., the stuff in compiler-rt/lib/builtins/).
>>> >> >>
>>> >> >> So, #1 and #2 would make LLVM able to emit calls to __xxx_acos when
>>> >> >> it sees "@llvm.acos.f32", but it won't let LLVM optimize (constant
>>> >> >> fold, transform into the intrinsic, ...) "__xx_acos()" when it sees
>>> >> >> it.
>>> >> >>
>>> >> >> It sounds like you also want to recognize and optimize these calls.
>>> >> >> That involves (pre-CodeGen) IR-level optimizations.
>>> >> >> No, I don't think that's supported today without changing LLVM (see
>>> >> >> the list in my first email).
>>> >> >>
>>> >> >> > 3) change TargetLibraryInfo for functions that aren't covered in
>>> >> >> > solutions 1
>>> >> >> > and 2 (so that they can also be optimized)
>>> >> >> >
>>> >> >> > I must be missing something, I'm just not sure what it is.
>>> >> >> >
>>> >> >> > Thanks,
>>> >> >> >
>>> >> >> > Ryan
>>> >> >> >
>>> >> >> >
>>> >> >> > On Tue, Jun 7, 2016 at 4:45 PM, Ryan Taylor <ryta1203 at gmail.com>
>>> >> >> > wrote:
>>> >> >> >>
>>> >> >> >> Tim,
>>> >> >> >>
>>> >> >> >>  Are you referring to setLibcallName? That is target specific
>>> >> >> >> yes
>>> >> >> >> but
>>> >> >> >> there isn't RTLIB for most of the libm functions, for example,
>>> >> >> >> for
>>> >> >> >> acos
>>> >> >> >> this
>>> >> >> >> doesn't apply.
>>> >> >> >>
>>> >> >> >>  Ideally what I would like is to create a libc with functions
>>> >> >> >> like
>>> >> >> >> acos
>>> >> >> >> called something like __xxx_acos that can still be recognized to
>>> >> >> >> be
>>> >> >> >> optimized.
>>> >> >> >>
>>> >> >> >>  RTLIB is pretty limited but it works fine, I can just use
>>> >> >> >> setLibcallName(RTLIB::floor, "__xxx_floor")... but again, the
>>> >> >> >> functions
>>> >> >> >> that
>>> >> >> >> are RTLIB are limited. Using intrinsics make it more difficult
>>> >> >> >> because
>>> >> >> >> then
>>> >> >> >> you have to match the intrinsic (rather than it automatically
>>> >> >> >> generating a
>>> >> >> >> lib call). ISD is just as bad (FCOPYSIGN, FABS for example)
>>> >> >> >> because
>>> >> >> >> then
>>> >> >> >> they need to be manually lowered.
>>> >> >> >> Thanks,
>>> >> >> >>
>>> >> >> >> Ryan
>>> >> >> >>
>>> >> >> >>
>>> >> >> >>
>>> >> >> >> On Tue, Jun 7, 2016 at 4:38 PM, Tim Northover
>>> >> >> >> <t.p.northover at gmail.com>
>>> >> >> >> wrote:
>>> >> >> >>>
>>> >> >> >>> On 7 June 2016 at 13:24, Ryan Taylor via llvm-dev
>>> >> >> >>> <llvm-dev at lists.llvm.org> wrote:
>>> >> >> >>> > Not sure why it's called TargetLibraryInfo if it's not in
>>> >> >> >>> > target
>>> >> >> >>> > specific
>>> >> >> >>> > code? It seems that ALL targets use this code, making it
>>> >> >> >>> > generic.
>>> >> >> >>> > Am
>>> >> >> >>> > I
>>> >> >> >>> > missing something here?
>>> >> >>
>>> >> >> I agree the name "Target" is a bit awkward, but it's not generic in
>>> >> >> that it behaves differently depending on the target triple, which
>>> >> >> is
>>> >> >> usually not OK in a "generic" analysis.
>>> >> >>
>>> >> >> If you look in TargetLibraryInfo.cpp, there are various checks for
>>> >> >> function availability, usually predicated on OS versions.
>>> >> >>
>>> >> >> -Ahmed
>>> >> >>
>>> >> >> >>> Some of the names can vary by platform, for example ARM
>>> >> >> >>> sometimes
>>> >> >> >>> has
>>> >> >> >>> __aeabi_memcpy instead of memcpy
>>> >> >> >>>
>>> >> >> >>> > ps. The spec also states (albeit unclearly) that you can use
>>> >> >> >>> > "#undef"
>>> >> >> >>> > to
>>> >> >> >>> > omit a library function so that a user defined function of
>>> >> >> >>> > the
>>> >> >> >>> > same
>>> >> >> >>> > name can
>>> >> >> >>> > be used but LLVM doesn't seem to support that.
>>> >> >> >>>
>>> >> >> >>> I think it says exactly the opposite: (7.1.2p3):
>>> >> >> >>>
>>> >> >> >>>     "If the program removes (with #undef) any macro definition
>>> >> >> >>> of
>>> >> >> >>> an
>>> >> >> >>> identifier in the first group listed above, the behavior is
>>> >> >> >>> undefined."
>>> >> >> >>>
>>> >> >> >>> Incidentally, I don't think anyone's mentioned that
>>> >> >> >>> "-ffreestanding"
>>> >> >> >>> will probably inhibit the intrinsics substantially if that's
>>> >> >> >>> what
>>> >> >> >>> you're after (technically, it's probably a compiler extension
>>> >> >> >>> that
>>> >> >> >>> it
>>> >> >> >>> gives them back to the user, but everyone does it as far as I
>>> >> >> >>> know).
>>> >> >> >>>
>>> >> >> >>> Cheers.
>>> >> >> >>>
>>> >> >> >>> Tim.
>>> >> >> >>
>>> >> >> >>
>>> >> >> >
>>> >> >
>>> >> >
>>> >
>>> >
>>
>>
>
>
> _______________________________________________
> LLVM Developers mailing list
> llvm-dev at lists.llvm.org
> http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-dev
>



-- 
With best regards, Anton Korobeynikov
Department of Statistical Modelling, Saint Petersburg State University


More information about the llvm-dev mailing list