-
Notifications
You must be signed in to change notification settings - Fork 42
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Built-in function naming scheme #19
Comments
@topperc I am not family with x86 stuffs, could you share the status/implementation on x86 land? |
Most X86 builtins start with There have been concerns raised with compile time of x86 intrinsics due to the size of the headers. For the last 10 years or more all new ISAs are only available from a single header file |
For those builtin function which used for intrinsic function, I am prefer DO NOT have too much restriction on that:
|
What would be good/canonical examples of the flexibility gained by this layer of indirection? Are there good historical examples we can reference? |
In my understanding that prevent target to corrupts the global name space without two underline prefix, using a indirection layer (intrinsic wrapper -> built-in function). @jim-wilson do you know does here some historical reason for lots of target doing this? |
Ana also mention one thing about that intrinsic might not implement by built-in function, it might implement some compiler extension, ARM Neon is an good example for that, vadd are simply implement by operator+ of GNU vector extension: https://github.com/gcc-mirror/gcc/blob/master/gcc/config/arm/arm_neon.h#L533 /* vadd */
__extension__ extern __inline int8x8_t
__attribute__ ((__always_inline__, __gnu_inline__, __artificial__))
vadd_s8 (int8x8_t __a, int8x8_t __b)
{
return __a + __b;
} |
ISO C says "All identifiers that begin with an underscore and either an uppercase letter or another underscore are always reserved for any use.", so __builtin is clearly safe for the compiler to use. The builtin part of that just makes it clear that it is a compiler builtin and not some libgcc or other library routine. Builtin functions don't have declarations that can be used for type checking and nice error messages. So it is useful to define an inline function with types that then calls the builtin, put the inline function in a header file, and ask the user to call that instead of the builtin. If there is a problem, the user gets an error that points at the header file, which is generally easier to understand than something that just complains about an incorrect call to a builtin but doesn't give you a declaration to look at. If you have good enough error messages, maybe you don't need the inline function in the header file. If you do have the inline functions in a header file, they don't necessarily need to call a builtin if there are other ways to get the correct result. |
Both RISC-V LLVM and GNU folks are fine with no strict rule on those builtin functions, I gonna to write a PR for this recently. |
Preface
This topic is compiler internal implementation specific, here is another issue (#18_ for discuss intrinsic naming scheme.
This issue intend to discus the built-in function naming scheme, generally those functions named with
__builtin_<arch>
prefix, there is an issue is: should we have consistent naming for built-in functions among different compiler, or just keep the intrinsic interface consistent is enough.Scope
This scope are limited to the built-in functions are used for intrinsic function only, because non-intrinsic purposed built-in function like
__builtin_thread_pointer
has no good reason to have different name among different compilerHow Other Target Implement
Most target implement their target specific built-in function and then use that to implement their intrinsic functions, here is an example from ARM:
vsubw_s8
is one of intrinsic function for NEON, but the compiler is implement that as__builtin_neon_vsubwsv8qi
internally. the general motivation is prevent namespace pollution,so we prevent compiler to declare the name of built-in function to same as name of intrinsic function directly.
However not everyone using this scheme, AArch64 SVE using
pragma
trick to declare the intrinsic function without introduce lots of__builtin_
functions, this would be useful if there is lots of intrinsic function, this could be significant reduce the compilation time, and I also intend to use this trick on GCC RVV implementation, since there is almost ~20k intrinsic function, that might increase the compilation time 30 sec ~ 60 sec.https://github.com/gcc-mirror/gcc/blob/master/gcc/config/aarch64/arm_sve.h
#pragma GCC aarch64 "arm_sve.h"
The interested thing is SVE implementation on clang/LLVM didn't using same trick, it just using the most common way, create built-in function with prefix
__builtin_
and then define intrinsic in the header file.Discussion
prama
trick.__builtin_riscv_<asm_mnemonic>
__builtin_riscv_<asm_mnemonic>_<16|32|64|x>
The pros and cons analysis might be very incomplete, feel free to share your thought here.
Any comment are appreciate!
The text was updated successfully, but these errors were encountered: