builtin.bi exposes a selected set of GCC and clang
__builtin_* entry points to FreeBASIC code.
It is a low-level include for code that is already depending on the C backend. It is not a general replacement for normal FreeBASIC statements, the runtime library, or the C runtime headers.
Backend requirement
builtin.bi requires the GCC or clang backend:
#include once "builtin.bi"
Compile with one of the C backends:
fbc -gen gcc program.bas
fbc -gen clang program.bas
If the active backend is not
gcc or
clang, the include stops with an error. That is intentional. The declarations name compiler builtins, not portable runtime functions, and non-C backends do not have the same builtin lowering rules.
Why this header exists
GCC and clang recognize many
__builtin_* names specially. Some behave like C library calls that can be optimized or inlined. Others expose compiler knowledge such as object size, checked arithmetic, branch prediction hints, byte swapping, or bit counting.
FreeBASIC can call those entry points through normal
DECLARE statements, but the declarations must match the target C ABI. That is the main job of
builtin.bi.
The header defines private helper types such as
__fb_builtin_size_t,
__fb_builtin_clong, and
__fb_builtin_culong so declarations follow the target C data model. For example, LP64 Unix targets use C
long for
size_t-related declarations, while Win64 keeps C
long at 32 bits.
What is included
The header intentionally exposes a core useful set, not every builtin supported by GCC or clang.
Currently included families:
- Memory and string builtins: __builtin_memcpy, __builtin_memmove, __builtin_memset, __builtin_strlen, __builtin_strcmp, and related routines.
- Bit operations: __builtin_ffs, __builtin_clz, __builtin_ctz, __builtin_clrsb, __builtin_popcount, and __builtin_parity with int, long, and long long variants.
- Byte swaps: __builtin_bswap16, __builtin_bswap32, and __builtin_bswap64.
- Object-size queries: __builtin_object_size and, on targets where it lowers correctly, __builtin_dynamic_object_size.
- Checked arithmetic: fixed-type signed and unsigned add, subtract, and multiply overflow helpers.
- Code-generation hints: __builtin_expect, __builtin_expect_with_probability, __builtin_prefetch, __builtin_trap, and __builtin_unreachable.
The header intentionally does not include target-specific builtins, language-specific builtins, broad SIMD families, every C library builtin, or portable fallback implementations.
Examples
Checked addition:
#include once "builtin.bi"
dim as long a = &h7fffffff
dim as long b = 1
dim as long result
if __builtin_sadd_overflow( a, b, @result ) then
print "overflow"
else
print result
end if
Byte swapping:
#include once "builtin.bi"
dim as ulong value = &h12345678
print hex( __builtin_bswap32( value ) )
Using an unlikely branch hint:
#include once "builtin.bi"
dim as long failed = any
failed = 0
if __builtin_expect( failed, 0 ) then
print "rare failure path"
end if
Important caveats
These calls follow the C compiler builtin semantics. That means some familiar-looking routines still carry C rules:
- __builtin_memcpy requires non-overlapping source and destination ranges. Use __builtin_memmove when overlap is possible.
- __builtin_clz and __builtin_ctz families have undefined results when the input is zero.
- __builtin_unreachable tells the optimizer that execution cannot reach that point. If execution does reach it, program behavior is undefined.
- __builtin_trap is an intentional abnormal stop, not normal error handling.
- Object-size builtins report what the compiler can prove, not a general run-time allocation size.
- Builtins may be optimized away, lowered inline, or emitted as calls depending on target, optimization level, and compiler version.
When to use it
Use
builtin.bi when the program or library is intentionally tied to the GCC/clang backend and needs a specific compiler builtin.
Good uses include low-level runtime code, checked arithmetic helpers, fortify-style buffer checks, endian conversion helpers, and small hot paths where the C compiler builtin is exactly the interface desired.
For ordinary application code, prefer normal FreeBASIC features, the runtime library, or documented C runtime declarations unless a builtin is specifically needed.
See also