authorgravatar for jan.hafer@rwth-aachen.deJan Philipp Hafer <jan.hafer@rwth-aachen.de> 2023-01-26 22:44:39+01:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2023-02-02 17:45:38-05:00
log03cdb4fb5853109e46bdc08d8a849a23780093ae
tree2ccf60b8cbbf760d956db7e4d0f81ab7b84fa195
parent7505d19e931893c01cf78760fa31d819ef10e879

compiler_rt: make README visually nice and improve explanations

This commit makes the text more dense with sources, noes the outstanding audit and adds an explanation of the table before converting everything to markdown tables. For the status a checkmark or cross in utf8 encoding are used and the input and output sizes of all operations are given inclusive comments for understanding of the routines. This should document all compiler_rt integer and float routines, but does not include a documentation of existing ieee floating and math routines.

1 files changed, 534 insertions(+), 471 deletions(-)

lib/compiler_rt/README.md+534-471
...@@ -27,482 +27,545 @@ then statically linked and therefore is a transparent dependency for the...@@ -27,482 +27,545 @@ then statically linked and therefore is a transparent dependency for the
27programmer.27programmer.
28For details see `../compiler_rt.zig`.28For details see `../compiler_rt.zig`.
2929
30The routines in this folder are listed below.
31Routines are annotated as `type source routine // description`, with `routine`
32being the name used in aforementioned `compiler_rt.zig`.
33`dev` means deviating from compiler_rt, `port` ported, `source` is the
34information source for the implementation, `none` means unimplemented.
35Some examples for the naming convention are:
36- dev source name_routine, name_routine2 various implementations for performance, simplicity etc
37- port llvm compiler-rt library routines from [LLVM](http://compiler-rt.llvm.org/)
38 * LLVM emits library calls to compiler-rt, if the hardware lacks functionality
39- port musl libc routines from [musl](https://musl.libc.org/)
40If the library or information source is uncommon, use the entry `other` for `source`.
41Please do not break the search by inserting entries in another format than `impl space source`.
42
43Bugs should be solved by trying to duplicate the bug upstream, if possible.30Bugs should be solved by trying to duplicate the bug upstream, if possible.
44 * If the bug exists upstream, get it fixed upstream and port the fix downstream to Zig.31 * If the bug exists upstream, get it fixed upstream and port the fix downstream to Zig.
45 * If the bug only exists in Zig, use the corresponding C code and debug32 * If the bug only exists in Zig, use the corresponding C code and debug
46 both implementations side by side to figure out what is wrong.33 both implementations side by side to figure out what is wrong.
4734
48## Integer library routines35Routines with status are given below. Sources were besides
4936"The Art of Computer Programming" by Donald E. Knuth, "HackersDelight" by Henry S. Warren,
50#### Integer Bit operations37"Bit Twiddling Hacks" collected by Sean Eron Anderson, "Berkeley SoftFloat" by John R. Hauser,
5138LLVM "compiler-rt" as it was MIT-licensed, "musl libc" and thoughts + work of contributors.
52- dev HackersDelight __clzsi2 // count leading zeros39
53- dev HackersDelight __clzdi2 // count leading zeros40The compiler-rt routines have not yet been audited.
54- dev HackersDelight __clzti2 // count leading zeros41See https://github.com/ziglang/zig/issues/1504.
55- dev HackersDelight __ctzsi2 // count trailing zeros42
56- dev HackersDelight __ctzdi2 // count trailing zeros43From left to right the columns mean 1. if the routine is implemented (✗ or ✓),
57- dev HackersDelight __ctzti2 // count trailing zeros442. the name, 3. input (`a`), 4. input (`b`), 5. return value,
58- dev __ctzsi2 __ffssi2 // find least significant 1 bit456. an explanation of the functionality, .. to repeat the comment from the
59- dev __ctzsi2 __ffsdi2 // find least significant 1 bit46column a row above and/or additional return values.
60- dev __ctzsi2 __ffsti2 // find least significant 1 bit47Some routines have more extensive comments supplemented with a reference text.
61- dev BitTwiddlingHacks __paritysi2 // bit parity48
62- dev BitTwiddlingHacks __paritydi2 // bit parity49Integer and Float Operations
63- dev BitTwiddlingHacks __parityti2 // bit parity50
64- dev TAOCP __popcountsi2 // bit population51| Done | Name | a | b | Out | Comment |
65- dev TAOCP __popcountdi2 // bit population52| ------ | ------------- | ---- | ---- | ---- | ------------------------------ |
66- dev TAOCP __popcountti2 // bit population53| | | | | | **Integer Bit Operations** |
67- dev other __bswapsi2 // a byteswapped54| ✓ | __clzsi2 | u32 | ∅ | i32 | count leading zeroes |
68- dev other __bswapdi2 // a byteswapped55| ✓ | __clzdi2 | u64 | ∅ | i32 | count leading zeroes |
69- dev other __bswapti2 // a byteswapped56| ✓ | __clzti2 | u128 | ∅ | i32 | count trailing zeros |
7057| ✓ | __ctzsi2 | u32 | ∅ | i32 | count trailing zeros |
71#### Integer Comparison58| ✓ | __ctzdi2 | u64 | ∅ | i32 | count trailing zeros |
7259| ✓ | __ctzti2 | u128 | ∅ | i32 | count leading zeroes |
73- port llvm __cmpsi2 // a,b: i32, (a<b)-> 0, (a==b) -> 1, (a>b) -> 260| ✓ | __ffssi2 | u32 | ∅ | i32 | count leading zeroes |
74- port llvm __cmpdi2 // a,b: i6461| ✓ | __ffsdi2 | u64 | ∅ | i32 | count leading zeroes |
75- port llvm __cmpti2 // a,b: i12862| ✓ | __ffsti2 | u128 | ∅ | i32 | count leading zeroes |
76- port llvm __ucmpsi2 // a,b: u32, (a<b)-> 0, (a==b) -> 1, (a>b) -> 263| ✓ | __paritysi2 | u32 | ∅ | i32 | find least significant 1 bit |
77- port llvm __ucmpdi2 // a,b: u6464| ✓ | __paritydi2 | u64 | ∅ | i32 | find least significant 1 bit |
78- port llvm __ucmpti2 // a,b: u12865| ✓ | __parityti2 | u128 | ∅ | i32 | find least significant 1 bit |
7966| ✓ | __popcountsi2 | u32 | ∅ | i32 | bit population |
80#### Integer Arithmetic67| ✓ | __popcountdi2 | u64 | ∅ | i32 | bit population |
8168| ✓ | __popcountti2 | u128 | ∅ | i32 | bit population |
82- none none __ashlsi3 // a,b: i32, a << b unused in llvm, TODO (e.g. used by rl78)69| ✓ | __bswapsi2 | u32 | ∅ | i32 | bit parity |
83- port llvm __ashldi3 // a,b: u6470| ✓ | __bswapdi2 | u64 | ∅ | i32 | bit parity |
84- port llvm __ashlti3 // a,b: u12871| ✓ | __bswapti2 | u128 | ∅ | i32 | bit parity |
85- none none __ashrsi3 // a,b: i32, a >> b arithmetic (sign fill) TODO (e.g. used by rl78)72| | | | | | **Integer Comparison** |
86- port llvm __ashrdi3 // ..73| ✓ | __cmpsi2 | i32 | i32 | i32 | `(a<b) -> 0, (a==b) -> 1, (a>b) -> 2` |
87- port llvm __ashrti3 //74| ✓ | __cmpdi2 | i64 | i64 | i32 | .. |
88- none none __lshrsi3 // a,b: i32, a >> b logical (zero fill) TODO (e.g. used by rl78)75| ✓ | __cmpti2 | i128 | i128 | i32 | .. |
89- port llvm __lshrdi3 //76| ✓ | __ucmpsi2 | i32 | i32 | i32 | `(a<b) -> 0, (a==b) -> 1, (a>b) -> 2` |
90- port llvm __lshrti3 //77| ✓ | __ucmpdi2 | i64 | i64 | i32 | .. |
91- port llvm __negdi2 // a: i32, -a, symbol-level compatibility with libgcc78| ✓ | __ucmpti2 | i128 | i128 | i32 | .. |
92- port llvm __negti2 // unnecessary: unused in backends79| | | | | | **Integer Arithmetic** |
93- port llvm __mulsi3 // a,b: i32, a * b80| ✗ | __ashlsi3 | i32 | i32 | i32 | `a << b` [^unused_rl78] |
94- port llvm __muldi3 //81| ✓ | __ashldi3 | i64 | i32 | i64 | .. |
95- port llvm __multi3 //82| ✓ | __ashlti3 | i128 | i32 | i128 | .. |
96- port llvm __divsi3 // a,b: i32, a / b83| ✓ | __aeabi_llsl | i32 | i32 | i32 | .. ARM |
97- port llvm __divdi3 //84| ✗ | __ashrsi3 | i32 | i32 | i32 | `a >> b` arithmetic (sign fill) [^unused_rl78] |
98- port llvm __divti3 //85| ✓ | __ashrdi3 | i64 | i32 | i64 | .. |
99- port llvm __udivsi3 // a,b: u32, a / b86| ✓ | __ashrti3 | i128 | i32 | i128 | .. |
100- port llvm __udivdi3 //87| ✓ | __aeabi_lasr | i64 | i32 | i64 | .. ARM |
101- port llvm __udivti3 //88| ✗ | __lshrsi3 | i32 | i32 | i32 | `a >> b` logical (zero fill) [^unused_rl78] |
102- port llvm __modsi3 // a,b: i32, a % b89| ✓ | __lshrdi3 | i64 | i32 | i64 | .. |
103- port llvm __moddi3 //90| ✓ | __lshrti3 | i128 | i32 | i128 | .. |
104- port llvm __modti3 //91| ✓ | __aeabi_llsr | i64 | i32 | i64 | .. ARM |
105- port llvm __umodsi3 // a,b: u32, a % b92| ✓ | __negsi2 | i32 | i32 | i32 | `-a` [^libgcc_compat] |
106- port llvm __umoddi3 //93| ✓ | __negdi2 | i64 | i64 | i64 | .. |
107- port llvm __umodti3 //94| ✓ | __negti2 | i128 | i128 | i128 | .. |
108- port llvm __udivmoddi4 // a,b: u32, a / b, rem.* = a % b unsigned95| ✓ | __mulsi3 | i32 | i32 | i32 | `a * b` |
109- port llvm __udivmodti4 //96| ✓ | __muldi3 | i64 | i64 | i64 | .. |
110- port llvm __udivmodsi4 //97| ✓ | __multi3 | i128 | i128 | i128 | .. |
111- port llvm __divmodsi4 // a,b: i32, a / b, rem.* = a % b signed, ARM98| ✓ | __divsi3 | i32 | i32 | i32 | `a / b` |
112- port llvm __divmoddi4 //99| ✓ | __divdi3 | i64 | i64 | i64 | .. |
113100| ✓ | __divti3 | i128 | i128 | i128 | .. |
114#### Integer Arithmetic with trapping overflow101| ✓ | __aeabi_idiv | i32 | i32 | i32 | .. ARM |
115102| ✓ | __udivsi3 | u32 | u32 | u32 | `a / b` |
116- dev BitTwiddlingHacks __absvsi2 // abs(a)103| ✓ | __udivdi3 | u64 | u64 | u64 | .. |
117- dev BitTwiddlingHacks __absvdi2 // abs(a)104| ✓ | __udivti3 | u128 | u128 | u128 | .. |
118- dev BitTwiddlingHacks __absvti2 // abs(a)105| ✓ | __aeabi_uidiv | i32 | i32 | i32 | .. ARM |
119- port llvm __negvsi2 // -a symbol-level compatibility: libgcc106| ✓ | __modsi3 | i32 | i32 | i32 | `a % b` |
120- port llvm __negvdi2 // -a unnecessary: unused in backends107| ✓ | __moddi3 | i64 | i64 | i64 | .. |
121- port llvm __negvti2 // -a108| ✓ | __modti3 | i128 | i128 | i128 | .. |
122- TODO upstreaming __addvsi3..__mulvti3 after testing panics works109| ✓ | __umodsi3 | u32 | u32 | u32 | `a % b` |
123- dev HackersDelight __addvsi3 // a + b110| ✓ | __umoddi3 | u64 | u64 | u64 | .. |
124- dev HackersDelight __addvdi3 //111| ✓ | __umodti3 | u128 | u128 | u128 | .. |
125- dev HackersDelight __addvti3 //112| ✓ | __udivmodsi4 | u32 | u32 | u32 | `a / b, rem.* = a % b` |
126- dev HackersDelight __subvsi3 // a - b113| ✓ | __udivmoddi4 | u64 | u64 | u64 | .. |
127- dev HackersDelight __subvdi3 //114| ✓ | __udivmodti4 | u128 | u128 | u128 | .. |
128- dev HackersDelight __subvti3 //115| ✓ | __divmodsi4 | i32 | i32 | i32 | `a / b, rem.* = a % b` |
129- dev HackersDelight __mulvsi3 // a * b116| ✓ | __divmoddi4 | i64 | i64 | i64 | .. |
130- dev HackersDelight __mulvdi3 //117| ✗ | __divmodti4 | i128 | i128 | i128 | .. [^libgcc_compat] |
131- dev HackersDelight __mulvti3 //118| | | | | | **Integer Arithmetic with Trapping Overflow**|
132119| ✓ | __absvsi2 | i32 | i32 | i32 | abs(a) |
133#### Integer Arithmetic which returns if overflow (would be faster without pointer)120| ✓ | __absvdi2 | i64 | i64 | i64 | .. |
134121| ✓ | __absvti2 | i128 | i128 | i128 | .. |
135- dev HackersDelight __addosi4 // a + b, overflow->ov.*=1 else 0122| ✓ | __negvsi2 | i32 | i32 | i32 | `-a` [^libgcc_compat] |
136- dev HackersDelight __addodi4 // (completeness + performance, llvm does not use them)123| ✓ | __negvdi2 | i64 | i64 | i64 | .. |
137- dev HackersDelight __addoti4 //124| ✓ | __negvti2 | i128 | i128 | i128 | .. |
138- dev HackersDelight __subosi4 // a - b, overflow->ov.*=1 else 0125| ✗ | __addvsi3 | i32 | i32 | i32 | `a + b` |
139- dev HackersDelight __subodi4 // (completeness + performance, llvm does not use them)126| ✗ | __addvdi3 | i64 | i64 | i64 | .. |
140- dev HackersDelight __suboti4 //127| ✗ | __addvti3 | i128 | i128 | i128 | .. |
141- dev HackersDelight __mulosi4 // a * b, overflow->ov.*=1 else 0128| ✗ | __subvsi3 | i32 | i32 | i32 | `a - b` |
142- dev HackersDelight __mulodi4 // (required by llvm)129| ✗ | __subvdi3 | i64 | i64 | i64 | .. |
143- dev HackersDelight __muloti4 //130| ✗ | __subvti3 | i128 | i128 | i128 | .. |
144131| ✗ | __mulvsi3 | i32 | i32 | i32 | `a * b` |
145## Float library routines132| ✗ | __mulvdi3 | i64 | i64 | i64 | .. |
146133| ✗ | __mulvti3 | i128 | i128 | i128 | .. |
147TODO: review source of implementation134| | | | | | **Integer Arithmetic which Return on Overflow** [^noptr_faster] |
148135| ✓ | __addosi4 | i32 | i32 | i32 | `a + b`, overflow->ov.*=1 else 0 [^perf_addition] |
149#### Float Conversion136| ✓ | __addodi4 | i64 | i64 | i64 | .. |
150137| ✓ | __addoti4 | i128 | i128 | i128 | .. |
151- dev other __extendsfdf2 // a: f32 -> f64, TODO: missing tests138| ✓ | __subosi4 | i32 | i32 | i32 | `a - b`, overflow->ov.*=1 else 0 [^perf_addition] |
152- dev other __extendsftf2 // a: f32 -> f128139| ✓ | __subodi4 | i64 | i64 | i64 | .. |
153- dev llvm __extendsfxf2 // a: f32 -> f80, TODO: missing tests140| ✓ | __suboti4 | i128 | i128 | i128 | .. |
154- dev other __extenddftf2 // a: f64 -> f128141| ✓ | __mulosi4 | i32 | i32 | i32 | `a * b`, overflow->ov.*=1 else 0 |
155- dev llvm __extenddfxf2 // a: f64 -> f80142| ✓ | __mulodi4 | i64 | i64 | i64 | .. |
156- dev other __truncdfsf2 // a: f64 -> f32, rounding towards zero143| ✓ | __muloti4 | i128 | i128 | i128 | .. |
157- dev other __trunctfdf2 // a: f128-> f64144| | | | | | **Float Conversion** |
158- dev other __trunctfsf2 // a: f128-> f32145| ✓ | __extendsfdf2 | f32 | ∅ | f64 | .. |
159- dev llvm __truncxfsf2 // a: f80 -> f32, TODO: missing tests146| ✓ | __extendsftf2 | f32 | ∅ | f128 | .. |
160- dev llvm __truncxfdf2 // a: f80 -> f64, TODO: missing tests147| ✓ | __extendsfxf2 | f32 | ∅ | f80 | .. |
161148| ✓ | __extenddftf2 | f64 | ∅ | f128 | .. |
162- dev unclear __fixsfsi // a: f32 -> i32, rounding towards zero149| ✓ | __extenddfxf2 | f64 | ∅ | f80 | .. |
163- dev unclear __fixdfsi // a: f64 -> i32150| ✓ | __truncsfhf2 | f32 | ∅ | f16 | rounding towards zero |
164- dev unclear __fixtfsi // a: f128-> i32151| ✓ | __truncdfhf2 | f64 | ∅ | f16 | .. |
165- dev unclear __fixxfsi // a: f80 -> i32, TODO: missing tests152| ✓ | __truncdfsf2 | f64 | ∅ | f32 | .. |
166- dev unclear __fixsfdi // a: f32 -> i64, rounding towards zero153| ✓ | __trunctfhf2 | f128 | ∅ | f16 | .. |
167- dev unclear __fixdfdi // ..154| ✓ | __trunctfsf2 | f128 | ∅ | f32 | .. |
168- dev unclear __fixtfdi //155| ✓ | __trunctfdf2 | f128 | ∅ | f64 | .. |
169- dev unclear __fixxfdi // TODO: missing tests156| ✓ | __trunctfxf2 | f128 | ∅ | f80 | .. |
170- dev unclear __fixsfti // a: f32 -> i128, rounding towards zero157| ✓ | __truncxfhf2 | f80 | ∅ | f16 | .. |
171- dev unclear __fixdfti // ..158| ✓ | __truncxfsf2 | f80 | ∅ | f32 | .. |
172- dev unclear __fixtfdi //159| ✓ | __truncxfdf2 | f80 | ∅ | f64 | .. |
173- dev unclear __fixxfti // TODO: missing tests160| ✓ | __aeabi_f2h | f32 | ∅ | f16 | .. ARM |
174161| ✓ | __gnu_f2h_ieee | f32 | ∅ | f16 | ..GNU naming convention |
175- dev unclear __fixunssfsi // a: f32 -> u32, rounding towards zero. negative values become 0.162| ✓ | __aeabi_d2h | f64 | ∅ | f16 | .. ARM |
176- dev unclear __fixunsdfsi // ..163| ✓ | __aeabi_d2f | f64 | ∅ | f32 | .. ARM |
177- dev unclear __fixunstfsi //164| ✓ | __trunckfsf2 | f128 | ∅ | f32 | .. PPC |
178- dev unclear __fixunsxfsi // TODO: missing tests165| ✓ | _Qp_qtos |*f128 | ∅ | f32 | .. SPARC |
179- dev unclear __fixunssfdi // a: f32 -> u64, rounding towards zero. negative values become 0.166| ✓ | __trunckfdf2 | f128 | ∅ | f64 | .. PPC |
180- dev unclear __fixunsdfdi //167| ✓ | _Qp_qtod |*f128 | ∅ | f64 | .. SPARC |
181- dev unclear __fixunstfdi //168| ✓ | __fixhfsi | f16 | ∅ | i32 | rounding towards zero |
182- dev unclear __fixunsxfdi // TODO: missing tests169| ✓ | __fixsfsi | f32 | ∅ | i32 | .. |
183- dev unclear __fixunssfti // a: f32 -> u128, rounding towards zero. negative values become 0.170| ✓ | __fixdfsi | f64 | ∅ | i32 | .. |
184- dev unclear __fixunsdfti //171| ✓ | __fixtfsi | f128 | ∅ | i32 | .. |
185- dev unclear __fixunstfdi //172| ✓ | __fixxfsi | f80 | ∅ | i32 | .. |
186- dev unclear __fixunsxfti // TODO: some more tests needed for base coverage173| ✓ | __fixhfdi | f16 | ∅ | i64 | .. |
187174| ✓ | __fixsfdi | f32 | ∅ | i64 | .. |
188- dev unclear __floatsisf // a: i32 -> f32175| ✓ | __fixdfdi | f64 | ∅ | i64 | .. |
189- dev unclear __floatsidf // a: i32 -> f64, TODO: missing tests176| ✓ | __fixtfdi | f128 | ∅ | i64 | .. |
190- dev unclear __floatsitf // ..177| ✓ | __fixxfdi | f80 | ∅ | i64 | .. |
191- dev unclear __floatsixf // TODO: missing tests178| ✓ | __fixhfti | f16 | ∅ | i128 | .. |
192- dev unclear __floatdisf // a: i64 -> f32179| ✓ | __fixsfti | f32 | ∅ | i128 | .. |
193- dev unclear __floatdidf //180| ✓ | __fixdfti | f64 | ∅ | i128 | .. |
194- dev unclear __floatditf //181| ✓ | __fixtfti | f128 | ∅ | i128 | .. |
195- dev unclear __floatdixf // TODO: missing tests182| ✓ | __fixxfti | f80 | ∅ | i128 | .. |
196- dev unclear __floattisf // a: i128-> f32183| ✓ | __fixunshfsi | f16 | ∅ | u32 | rounding towards zero. negative values become 0. |
197- dev unclear __floattidf //184| ✓ | __fixunssfsi | f32 | ∅ | u32 | .. |
198- dev unclear __floattitf //185| ✓ | __fixunsdfsi | f64 | ∅ | u32 | .. |
199- dev unclear __floattixf // TODO: missing tests186| ✓ | __fixunstfsi | f128 | ∅ | u32 | .. |
200187| ✓ | __fixunsxfsi | f80 | ∅ | u32 | .. |
201- dev unclear __floatunsisf // a: u32 -> f32188| ✓ | __fixunshfdi | f16 | ∅ | u64 | .. |
202- dev unclear __floatunsidf // TODO: missing tests189| ✓ | __fixunssfdi | f32 | ∅ | u64 | .. |
203- dev unclear __floatunsitf //190| ✓ | __fixunsdfdi | f64 | ∅ | u64 | .. |
204- dev unclear __floatunsixf // TODO: missing tests191| ✓ | __fixunstfdi | f128 | ∅ | u64 | .. |
205- dev unclear __floatundisf // a: u64 -> f32192| ✓ | __fixunsxfdi | f80 | ∅ | u64 | .. |
206- dev unclear __floatundidf //193| ✓ | __fixunshfti | f16 | ∅ | u128 | .. |
207- dev unclear __floatunditf //194| ✓ | __fixunssfti | f32 | ∅ | u128 | .. |
208- dev unclear __floatundixf // TODO: missing tests195| ✓ | __fixunsdfti | f64 | ∅ | u128 | .. |
209- dev unclear __floatuntisf // a: u128-> f32196| ✓ | __fixunstfti | f128 | ∅ | u128 | .. |
210- dev unclear __floatuntidf //197| ✓ | __fixunsxfti | f80 | ∅ | u128 | .. |
211- dev unclear __floatuntitf //198| ✓ | __floatsihf | i32 | ∅ | f16 | int_to_float conversions |
212- dev unclear __floatuntixf // TODO: missing tests199| ✓ | __floatsisf | i32 | ∅ | f32 | .. |
213200| ✓ | __floatsidf | i32 | ∅ | f64 | .. |
214#### Float Comparison201| ✓ | __floatsitf | i32 | ∅ | f128 | .. |
215202| ✓ | __floatsixf | i32 | ∅ | f80 | .. |
216- dev other __cmpsf2 // a,b:f32, (a<b)->-1,(a==b)->0,(a>b)->1,Nan->1203| ✓ | __floatdisf | i64 | ∅ | f32 | .. |
217- dev other __cmpdf2 // exported from __lesf2, __ledf2, __letf2 (below)204| ✓ | __floatdidf | i64 | ∅ | f64 | .. |
218- dev other __cmptf2 // But: if NaN is a possibility, use another routine.205| ✓ | __floatditf | i64 | ∅ | f128 | .. |
219- dev other __unordsf2 // a,b:f32, (a==+-NaN or b==+-NaN) -> !=0, else -> 0206| ✓ | __floatdixf | i64 | ∅ | f80 | .. |
220- dev other __unorddf2 // __only reliable for (input!=NaN)__207| ✓ | __floattihf | i128 | ∅ | f16 | .. |
221- dev other __unordtf2 // TODO: missing tests208| ✓ | __floattisf | i128 | ∅ | f32 | .. |
222- dev other __eqsf2 // (a!=NaN) and (b!=Nan) and (a==b) -> output=0209| ✓ | __floattidf | i128 | ∅ | f64 | .. |
223- dev other __eqdf2 //210| ✓ | __floattitf | i128 | ∅ | f128 | .. |
224- dev other __eqtf2 //211| ✓ | __floattixf | i128 | ∅ | f80 | .. |
225- dev other __nesf2 // (a==NaN) or (b==Nan) or (a!=b) -> output!=0212| ✓ | __floatunsihf | u32 | ∅ | f16 | uint_to_float conversions |
226- dev other __nedf2 //213| ✓ | __floatunsisf | u32 | ∅ | f32 | .. |
227- dev other __netf2 // __eqtf2 and __netf2 have same return value -> tested with __eqsf2214| ✓ | __floatunsidf | u32 | ∅ | f64 | .. |
228- dev other __gesf2 // (a!=Nan) and (b!=Nan) and (a>=b) -> output>=0215| ✓ | __floatunsitf | u32 | ∅ | f128 | .. |
229- dev other __gedf2 //216| ✓ | __floatunsixf | u32 | ∅ | f80 | .. |
230- dev other __getf2 // TODO: missing tests217| ✓ | __floatundihf | u64 | ∅ | f16 | .. |
231- dev other __ltsf2 // (a!=Nan) and (b!=Nan) and (a<b) -> output<0218| ✓ | __floatundisf | u64 | ∅ | f32 | .. |
232- dev other __ltdf2 //219| ✓ | __floatundidf | u64 | ∅ | f64 | .. |
233- dev other __lttf2 // TODO: missing tests220| ✓ | __floatunditf | u64 | ∅ | f128 | .. |
234- dev other __lesf2 // (a!=Nan) and (b!=Nan) and (a<=b) -> output<=0221| ✓ | __floatundixf | u64 | ∅ | f80 | .. |
235- dev other __ledf2 //222| ✓ | __floatuntihf | u128 | ∅ | f16 | .. |
236- dev other __letf2 // TODO: missing tests223| ✓ | __floatuntisf | u128 | ∅ | f32 | .. |
237- dev other __gtsf2 // (a!=Nan) and (b!=Nan) and (a>b) -> output>0224| ✓ | __floatuntidf | u128 | ∅ | f64 | .. |
238- dev other __gtdf2 //225| ✓ | __floatuntitf | u128 | ∅ | f128 | .. |
239- dev other __gttf2 // TODO: missing tests226| ✓ | __floatuntixf | u128 | ∅ | f80 | .. |
240227| | | | | | **Float Comparison** |
241#### Float Arithmetic228| ✓ | __cmphf2 | f16 | f16 | i32 | `(a<b)->-1, (a==b)->0, (a>b)->1, Nan->1` |
242229| ✓ | __cmpsf2 | f32 | f32 | i32 | exported from __lesf2, __ledf2, __letf2 (below) |
243- dev unclear __addsf3 // a + b f32, TODO: missing tests230| ✓ | __cmpdf2 | f64 | f64 | i32 | But: if NaN is a possibility, use another routine. |
244- dev unclear __adddf3 // a + b f64, TODO: missing tests231| ✓ | __cmptf2 | f128 | f128 | i32 | .. |
245- dev unclear __addtf3 // a + b f128232| ✓ | __cmpxf2 | f80 | f80 | i32 | .. |
246- dev unclear __addxf3 // a + b f80233| ✓ | _Qp_cmp |*f128 |*f128 | i32 | .. SPARC |
247- dev unclear __aeabi_fadd // a + b f64 ARM: AAPCS234| ✓ | __unordhf2 | f16 | f16 | i32 | `(a==+-NaN or b==+-NaN) -> !=0, else -> 0` |
248- dev unclear __aeabi_dadd // a + b f64 ARM: AAPCS235| ✓ | __unordsf2 | f32 | f32 | i32 | .. |
249- dev unclear __subsf3 // a - b, TODO: missing tests236| ✓ | __unorddf2 | f64 | f64 | i32 | Note: only reliable for (input!=NaN) |
250- dev unclear __subdf3 // a - b, TODO: missing tests237| ✓ | __unordtf2 | f128 | f128 | i32 | .. |
251- dev unclear __subtf3 // a - b238| ✓ | __unordxf2 | f80 | f80 | i32 | .. |
252- dev unclear __subxf3 // a - b f80, TODO: missing tests239| ✓ | __aeabi_fcmpun | f32 | f32 | i32 | .. ARM |
253- dev unclear __aeabi_fsub // a - b f64 ARM: AAPCS240| ✓ | __aeabi_dcmpun | f32 | f32 | i32 | .. ARM |
254- dev unclear __aeabi_dsub // a - b f64 ARM: AAPCS241| ✓ | __unordkf2 | f128 | f128 | i32 | .. PPC |
255- dev unclear __mulsf3 // a * b, TODO: missing tests242| ✓ | __eqhf2 | f16 | f16 | i32 | `(a!=NaN) and (b!=Nan) and (a==b) -> output=0` |
256- dev unclear __muldf3 // a * b, TODO: missing tests243| ✓ | __eqsf2 | f32 | f32 | i32 | .. |
257- dev unclear __multf3 // a * b244| ✓ | __eqdf2 | f64 | f64 | i32 | .. |
258- dev unclear __mulxf3 // a * b245| ✓ | __eqtf2 | f128 | f128 | i32 | .. |
259- dev unclear __divsf3 // a / b, TODO: review tests246| ✓ | __eqxf2 | f80 | f80 | i32 | .. |
260- dev unclear __divdf3 // a / b, TODO: review tests247| ✓ | __aeabi_fcmpeq | f32 | f32 | i32 | .. ARM |
261- dev unclear __divtf3 // a / b248| ✓ | __aeabi_dcmpeq | f32 | f32 | i32 | .. ARM |
262- dev unclear __divxf3 // a / b249| ✓ | __eqkf2 | f128 | f128 | i32 | .. PPC |
263- dev unclear __negsf2 // -a symbol-level compatibility: libgcc uses this for the rl78250| ✓ | _Qp_feq |*f128 |*f128 | bool | .. SPARC |
264- dev unclear __negdf2 // -a unnecessary: can be lowered directly to a xor251| ✓ | __nehf2 | f16 | f16 | i32 | `(a==NaN) or (b==Nan) or (a!=b) -> output!=0` |
265- dev unclear __negtf2 // -a, TODO: missing tests252| ✓ | __nesf2 | f32 | f32 | i32 | Note: __eqXf2 and __neXf2 have same return value |
266- dev unclear __negxf2 // -a, TODO: missing tests253| ✓ | __nedf2 | f64 | f64 | i32 | .. |
267254| ✓ | __netf2 | f128 | f128 | i32 | .. |
268#### Floating point raised to integer power255| ✓ | __nexf2 | f80 | f80 | i32 | .. |
269- dev unclear __powisf2 // a ^ b, TODO256| ✓ | __nekf2 | f128 | f128 | i32 | .. PPC |
270- dev unclear __powidf2 //257| ✓ | _Qp_fne |*f128 |*f128 | bool | .. SPARC |
271- dev unclear __powitf2 //258| ✓ | __gehf2 | f16 | f16 | i32 | `(a!=Nan) and (b!=Nan) and (a>=b) -> output>=0` |
272- dev unclear __powixf2 //259| ✓ | __gesf2 | f32 | f32 | i32 | .. |
273- dev unclear __mulsc3 // (a+ib) * (c+id)260| ✓ | __gedf2 | f64 | f64 | i32 | .. |
274- dev unclear __muldc3 //261| ✓ | __getf2 | f128 | f128 | i32 | .. |
275- dev unclear __multc3 //262| ✓ | __gexf2 | f80 | f80 | i32 | .. |
276- dev unclear __mulxc3 //263| ✓ | __gekf2 | f128 | f128 | i32 | .. PPC |
277- dev unclear __divsc3 // (a+ib) * / (c+id)264| ✓ | _Qp_fge |*f128 |*f128 | bool | .. SPARC |
278- dev unclear __divdc3 //265| ✓ | __lthf2 | f16 | f16 | i32 | `(a!=Nan) and (b!=Nan) and (a<b) -> output<0` |
279- dev unclear __divtc3 //266| ✓ | __ltsf2 | f32 | f32 | i32 | .. |
280- dev unclear __divxc3 //267| ✓ | __ltdf2 | f64 | f64 | i32 | .. |
281268| ✓ | __lttf2 | f128 | f128 | i32 | .. |
282## Decimal float library routines269| ✓ | __ltxf2 | f80 | f80 | i32 | .. |
270| ✓ | __ltkf2 | f128 | f128 | i32 | .. PPC |
271| ✓ | __aeabi_fcmplt | f32 | f32 | i32 | .. ARM |
272| ✓ | __aeabi_dcmplt | f32 | f32 | i32 | .. ARM |
273| ✓ | _Qp_flt |*f128 |*f128 | bool | .. SPARC |
274| ✓ | __lehf2 | f16 | f16 | i32 | `(a!=Nan) and (b!=Nan) and (a<=b) -> output<=0` |
275| ✓ | __lesf2 | f32 | f32 | i32 | .. |
276| ✓ | __ledf2 | f64 | f64 | i32 | .. |
277| ✓ | __letf2 | f128 | f128 | i32 | .. |
278| ✓ | __lexf2 | f80 | f80 | i32 | .. |
279| ✓ | __aeabi_fcmple | f32 | f32 | i32 | .. ARM |
280| ✓ | __aeabi_dcmple | f32 | f32 | i32 | .. ARM |
281| ✓ | __lekf2 | f128 | f128 | i32 | .. PPC |
282| ✓ | _Qp_fle |*f128 |*f128 | bool | .. SPARC |
283| ✓ | __gthf2 | f16 | f16 | i32 | `(a!=Nan) and (b!=Nan) and (a>b) -> output>0` |
284| ✓ | __gtsf2 | f32 | f32 | i32 | .. |
285| ✓ | __gtdf2 | f64 | f64 | i32 | .. |
286| ✓ | __gttf2 | f128 | f128 | i32 | .. |
287| ✓ | __gtxf2 | f80 | f80 | i32 | .. |
288| ✓ | __gtkf2 | f128 | f128 | i32 | .. PPC |
289| ✓ | _Qp_fgt |*f128 |*f128 | bool | .. SPARC |
290| | | | | | **Float Arithmetic** |
291| ✓ | __addhf3 | f32 | f32 | f32 | `a + b` |
292| ✓ | __addsf3 | f32 | f32 | f32 | .. |
293| ✓ | __adddf3 | f64 | f64 | f64 | .. |
294| ✓ | __addtf3 | f128 | f128 | f128 | .. |
295| ✓ | __addxf3 | f80 | f80 | f80 | .. |
296| ✓ | __aeabi_fadd | f32 | f32 | f32 | .. ARM |
297| ✓ | __aeabi_dadd | f64 | f64 | f64 | .. ARM |
298| ✓ | __addkf3 | f128 | f128 | f128 | .. PPC |
299| ✓ | _Qp_add |*f128 |*f128 | void | .. SPARC args *c,*a,*b c=a+b |
300| ✓ | __subhf3 | f32 | f32 | f32 | `a - b` |
301| ✓ | __subsf3 | f32 | f32 | f32 | .. |
302| ✓ | __subdf3 | f64 | f64 | f64 | .. |
303| ✓ | __subtf3 | f128 | f128 | f128 | .. |
304| ✓ | __subxf3 | f80 | f80 | f80 | .. |
305| ✓ | __aeabi_fsub | f32 | f32 | f32 | .. ARM |
306| ✓ | __aeabi_dsub | f64 | f64 | f64 | .. ARM |
307| ✓ | __subkf3 | f128 | f128 | f128 | .. PPC |
308| ✓ | _Qp_sub |*f128 |*f128 | void | .. SPARC args *c,*a,*b c=a-b |
309| ✓ | __mulhf3 | f32 | f32 | f32 | `a * b` |
310| ✓ | __mulsf3 | f32 | f32 | f32 | .. |
311| ✓ | __muldf3 | f64 | f64 | f64 | .. |
312| ✓ | __multf3 | f128 | f128 | f128 | .. |
313| ✓ | __mulxf3 | f80 | f80 | f80 | .. |
314| ✓ | __aeabi_fmul | f32 | f32 | f32 | .. ARM |
315| ✓ | __aeabi_dmul | f64 | f64 | f64 | .. ARM |
316| ✓ | __mulkf3 | f128 | f128 | f128 | .. PPC |
317| ✓ | _Qp_mul |*f128 |*f128 | void | .. SPARC args *c,*a,*b c=a*b |
318| ✓ | __divsf3 | f32 | f32 | f32 | `a / b` |
319| ✓ | __divdf3 | f64 | f64 | f64 | .. |
320| ✓ | __divtf3 | f128 | f128 | f128 | .. |
321| ✓ | __divxf3 | f80 | f80 | f80 | .. |
322| ✓ | __aeabi_fdiv | f32 | f32 | f32 | .. ARM |
323| ✓ | __aeabi_ddiv | f64 | f64 | f64 | .. ARM |
324| ✓ | __divkf3 | f128 | f128 | f128 | .. PPC |
325| ✓ | _Qp_div |*f128 |*f128 | void | .. SPARC args *c,*a,*b c=a*b |
326| ✓ | __negsf2 | f32 | ∅ | f32[^unused_rl78] | -a (can be lowered directly to a xor) |
327| ✓ | __negdf2 | f64 | ∅ | f64 | .. |
328| ✓ | __negtf2 | f128 | ∅ | f128 | .. |
329| ✓ | __negxf2 | f80 | ∅ | f80 | .. |
330| | | | | | **Floating point raised to integer power** |
331| ✗ | __powihf2 | f16 | f16 | f16 | `a ^ b` |
332| ✗ | __powisf2 | f32 | f32 | f32 | .. |
333| ✗ | __powidf2 | f64 | f64 | f64 | .. |
334| ✗ | __powitf2 | f128 | f128 | f128 | .. |
335| ✗ | __powixf2 | f80 | f80 | f80 | .. |
336| ✓ | __mulhc3 | all4 | f16 | f16 | `(a+ib) * (c+id)` |
337| ✓ | __mulsc3 | all4 | f32 | f32 | .. |
338| ✓ | __muldc3 | all4 | f64 | f64 | .. |
339| ✓ | __multc3 | all4 | f128 | f128 | .. |
340| ✓ | __mulxc3 | all4 | f80 | f80 | .. |
341| ✓ | __divhc3 | all4 | f16 | f16 | `(a+ib) / (c+id)` |
342| ✓ | __divsc3 | all4 | f32 | f32 | .. |
343| ✓ | __divdc3 | all4 | f64 | f64 | .. |
344| ✓ | __divtc3 | all4 | f128 | f128 | .. |
345| ✓ | __divxc3 | all4 | f80 | f80 | .. |
346
347[^unused_rl78]: Unused in LLVM, but used for example by rl78.
348[^libgcc_compat]: Unused in backends and for symbol-level compatibility with libgcc.
349[^noptr_faster]: Operations without pointer and without C struct semantics lead to better optimizations.
350[^perf_addition]: Has better performance than standard method due to 2s complement semantics.
351Not provided by LLVM and libgcc.
352
353Decimal float library routines
283354
284BID means Binary Integer Decimal encoding, DPD means Densely Packed Decimal encoding.355BID means Binary Integer Decimal encoding, DPD means Densely Packed Decimal encoding.
285BID should be only chosen for binary data, DPD for decimal data (ASCII, Unicode etc).356BID should be only chosen for binary data, DPD for decimal data (ASCII, Unicode etc).
286If possible, use BCD instead of DPD to represent numbers not accurately representable357For example the number 0.2 is not accurately representable in binary data.
287in binary like the number 0.2.358
288359| Done | Name | a | b | Out | Comment |
289All routines are TODO.360| ------ | ------------- | --------- | --------- | --------- | ---------------------------- |
290361| | | | | | **Decimal Float Conversion** |
291#### Decimal float Conversion362| ✗ | __dpd_extendsddd2 | dec32 | ∅ | dec64 | conversion |
292363| ✗ | __bid_extendsddd2 | dec32 | ∅ | dec64 | .. |
293- __dpd_extendsddd2 // dec32->dec64364| ✗ | __dpd_extendsdtd2 | dec32 | ∅ | dec128| .. |
294- __bid_extendsddd2 // dec32->dec64365| ✗ | __bid_extendsdtd2 | dec32 | ∅ | dec128| .. |
295- __dpd_extendsdtd2 // dec32->dec128366| ✗ | __dpd_extendddtd2 | dec64 | ∅ | dec128| .. |
296- __bid_extendsdtd2 // dec32->dec128367| ✗ | __bid_extendddtd2 | dec64 | ∅ | dec128| .. |
297- __dpd_extendddtd2 // dec64->dec128368| ✗ | __dpd_truncddsd2 | dec64 | ∅ | dec32 | .. |
298- __bid_extendddtd2 // dec64->dec128369| ✗ | __bid_truncddsd2 | dec64 | ∅ | dec32 | .. |
299- __dpd_truncddsd2 // dec64->dec32370| ✗ | __dpd_trunctdsd2 | dec128 | ∅ | dec32 | .. |
300- __bid_truncddsd2 // dec64->dec32371| ✗ | __bid_trunctdsd2 | dec128 | ∅ | dec32 | .. |
301- __dpd_trunctdsd2 // dec128->dec32372| ✗ | __dpd_trunctddd2 | dec128 | ∅ | dec64 | .. |
302- __bid_trunctdsd2 // dec128->dec32373| ✗ | __bid_trunctddd2 | dec128 | ∅ | dec64 | .. |
303- __dpd_trunctddd2 // dec128->dec64374| ✗ | __dpd_extendsfdd | float | ∅ | dec64 | .. |
304- __bid_trunctddd2 // dec128->dec64375| ✗ | __bid_extendsfdd | float | ∅ | dec64 | .. |
305376| ✗ | __dpd_extendsftd | float | ∅ | dec128| .. |
306- __dpd_extendsfdd // float->dec64377| ✗ | __bid_extendsftd | float | ∅ | dec128| .. |
307- __bid_extendsfdd // float->dec64378| ✗ | __dpd_extenddftd | double | ∅ | dec128| .. |
308- __dpd_extendsftd // float->dec128379| ✗ | __bid_extenddftd | double | ∅ | dec128| .. |
309- __bid_extendsftd // float->dec128380| ✗ | __dpd_extendxftd |long double | ∅ | dec128| .. |
310- __dpd_extenddftd // double->dec128381| ✗ | __bid_extendxftd |long double | ∅ | dec128| .. |
311- __bid_extenddftd // double->dec128382| ✗ | __dpd_truncdfsd | double | ∅ | dec32 | .. |
312- __dpd_extendxftd // long double->dec128383| ✗ | __bid_truncdfsd | double | ∅ | dec32 | .. |
313- __bid_extendxftd // long double->dec128384| ✗ | __dpd_truncxfsd |long double | ∅ | dec32 | .. |
314- __dpd_truncdfsd // double->dec32385| ✗ | __bid_truncxfsd |long double | ∅ | dec32 | .. |
315- __bid_truncdfsd // double->dec32386| ✗ | __dpd_trunctfsd |long double | ∅ | dec32 | .. |
316- __dpd_truncxfsd // long double->dec32387| ✗ | __bid_trunctfsd |long double | ∅ | dec32 | .. |
317- __bid_truncxfsd // long double->dec32388| ✗ | __dpd_truncxfdd |long double | ∅ | dec64 | .. |
318- __dpd_trunctfsd // long double->dec32389| ✗ | __bid_truncxfdd |long double | ∅ | dec64 | .. |
319- __bid_trunctfsd // long double->dec32390| ✗ | __dpd_trunctfdd |long double | ∅ | dec64 | .. |
320- __dpd_truncxfdd // long double->dec64391| ✗ | __bid_trunctfdd |long double | ∅ | dec64 | .. |
321- __bid_truncxfdd // long double->dec64392| ✗ | __dpd_truncddsf | dec64 | ∅ | float | .. |
322- __dpd_trunctfdd // long double->dec64393| ✗ | __bid_truncddsf | dec64 | ∅ | float | .. |
323- __bid_trunctfdd // long double->dec64394| ✗ | __dpd_trunctdsf | dec128 | ∅ | float | .. |
324395| ✗ | __bid_trunctdsf | dec128 | ∅ | float | .. |
325- __dpd_truncddsf // dec64->float396| ✗ | __dpd_extendsddf | dec32 | ∅ | double| .. |
326- __bid_truncddsf // dec64->float397| ✗ | __bid_extendsddf | dec32 | ∅ | double| .. |
327- __dpd_trunctdsf // dec128->float398| ✗ | __dpd_trunctddf | dec128 | ∅ | double| .. |
328- __bid_trunctdsf // dec128->float399| ✗ | __bid_trunctddf | dec128 | ∅ | double| .. |
329- __dpd_extendsddf // dec32->double400| ✗ | __dpd_extendsdxf | dec32 | ∅ |long double| .. |
330- __bid_extendsddf // dec32->double401| ✗ | __bid_extendsdxf | dec32 | ∅ |long double| .. |
331- __dpd_trunctddf // dec128->double402| ✗ | __dpd_extendddxf | dec64 | ∅ |long double| .. |
332- __bid_trunctddf // dec128->double403| ✗ | __bid_extendddxf | dec64 | ∅ |long double| .. |
333- __dpd_extendsdxf // dec32->long double404| ✗ | __dpd_trunctdxf | dec128 | ∅ |long double| .. |
334- __bid_extendsdxf // dec32->long double405| ✗ | __bid_trunctdxf | dec128 | ∅ |long double| .. |
335- __dpd_extendddxf // dec64->long double406| ✗ | __dpd_extendsdtf | dec32 | ∅ |long double| .. |
336- __bid_extendddxf // dec64->long double407| ✗ | __bid_extendsdtf | dec32 | ∅ |long double| .. |
337- __dpd_trunctdxf // dec128->long double408| ✗ | __dpd_extendddtf | dec64 | ∅ |long double| .. |
338- __bid_trunctdxf // dec128->long double409| ✗ | __bid_extendddtf | dec64 | ∅ |long double| .. |
339- __dpd_extendsdtf // dec32->long double410| ✗ | __dpd_extendsfsd | float | ∅ | dec32 | same size conversions |
340- __bid_extendsdtf // dec32->long double411| ✗ | __bid_extendsfsd | float | ∅ | dec32 | .. |
341- __dpd_extendddtf // dec64->long double412| ✗ | __dpd_extenddfdd | double | ∅ | dec64 | .. |
342- __bid_extendddtf // dec64->long double413| ✗ | __bid_extenddfdd | double | ∅ | dec64 | .. |
343414| ✗ | __dpd_extendtftd |long double | ∅ | dec128| .. |
344Same size conversion:415| ✗ | __bid_extendtftd |long double | ∅ | dec128| .. |
345- __dpd_extendsfsd // float->dec32416| ✗ | __dpd_truncsdsf | dec32 | ∅ | float | .. |
346- __bid_extendsfsd // float->dec32417| ✗ | __bid_truncsdsf | dec32 | ∅ | float | .. |
347- __dpd_extenddfdd // double->dec64418| ✗ | __dpd_truncdddf | dec64 | ∅ | float | conversion |
348- __bid_extenddfdd // double->dec64419| ✗ | __bid_truncdddf | dec64 | ∅ | float | .. |
349- __dpd_extendtftd //long double->dec128420| ✗ | __dpd_trunctdtf | dec128 | ∅ |long double| .. |
350- __bid_extendtftd //long double->dec128421| ✗ | __bid_trunctdtf | dec128 | ∅ |long double| .. |
351- __dpd_truncsdsf // dec32->float422| ✗ | __dpd_fixsdsi | dec32 | ∅ | int | .. |
352- __bid_truncsdsf // dec32->float423| ✗ | __bid_fixsdsi | dec32 | ∅ | int | .. |
353- __dpd_truncdddf // dec64->float424| ✗ | __dpd_fixddsi | dec64 | ∅ | int | .. |
354- __bid_truncdddf // dec64->float425| ✗ | __bid_fixddsi | dec64 | ∅ | int | .. |
355- __dpd_trunctdtf // dec128->long double426| ✗ | __dpd_fixtdsi | dec128 | ∅ | int | .. |
356- __bid_trunctdtf // dec128->long double427| ✗ | __bid_fixtdsi | dec128 | ∅ | int | .. |
357428| ✗ | __dpd_fixsddi | dec32 | ∅ | long | .. |
358- __dpd_fixsdsi // dec32->int429| ✗ | __bid_fixsddi | dec32 | ∅ | long | .. |
359- __bid_fixsdsi // dec32->int430| ✗ | __dpd_fixdddi | dec64 | ∅ | long | .. |
360- __dpd_fixddsi // dec64->int431| ✗ | __bid_fixdddi | dec64 | ∅ | long | .. |
361- __bid_fixddsi // dec64->int432| ✗ | __dpd_fixtddi | dec128 | ∅ | long | .. |
362- __dpd_fixtdsi // dec128->int433| ✗ | __bid_fixtddi | dec128 | ∅ | long | .. |
363- __bid_fixtdsi // dec128->int434| ✗ | __dpd_fixunssdsi | dec32 | ∅ |unsigned int | .. All negative values become zero. |
364435| ✗ | __bid_fixunssdsi | dec32 | ∅ |unsigned int | .. |
365- __dpd_fixsddi // dec32->long436| ✗ | __dpd_fixunsddsi | dec64 | ∅ |unsigned int | .. |
366- __bid_fixsddi // dec32->long437| ✗ | __bid_fixunsddsi | dec64 | ∅ |unsigned int | .. |
367- __dpd_fixdddi // dec64->long438| ✗ | __dpd_fixunstdsi | dec128 | ∅ |unsigned int | .. |
368- __bid_fixdddi // dec64->long439| ✗ | __bid_fixunstdsi | dec128 | ∅ |unsigned int | .. |
369- __dpd_fixtddi // dec128->long440| ✗ | __dpd_fixunssddi | dec32 | ∅ |unsigned long| .. |
370- __bid_fixtddi // dec128->long441| ✗ | __bid_fixunssddi | dec32 | ∅ |unsigned long| .. |
371442| ✗ | __dpd_fixunsdddi | dec64 | ∅ |unsigned long| .. |
372- __dpd_fixunssdsi // dec32->unsigned int, All negative values become zero.443| ✗ | __bid_fixunsdddi | dec64 | ∅ |unsigned long| .. |
373- __bid_fixunssdsi // dec32->unsigned int444| ✗ | __dpd_fixunstddi | dec128 | ∅ |unsigned long| .. |
374- __dpd_fixunsddsi // dec64->unsigned int445| ✗ | __bid_fixunstddi | dec128 | ∅ |unsigned long| .. |
375- __bid_fixunsddsi // dec64->unsigned int446| ✗ | __dpd_floatsisd | int | ∅ | dec32 | .. |
376- __dpd_fixunstdsi // dec128->unsigned int447| ✗ | __bid_floatsisd | int | ∅ | dec32 | .. |
377- __bid_fixunstdsi // dec128->unsigned int448| ✗ | __dpd_floatsidd | int | ∅ | dec64 | .. |
378449| ✗ | __bid_floatsidd | int | ∅ | dec64 | .. |
379- __dpd_fixunssddi // dec32->unsigned long, All negative values become zero.450| ✗ | __dpd_floatsitd | int | ∅ | dec128 | .. |
380- __bid_fixunssddi // dec32->unsigned long451| ✗ | __bid_floatsitd | int | ∅ | dec128 | .. |
381- __dpd_fixunsdddi // dec64->unsigned long452| ✗ | __dpd_floatdisd | long | ∅ | dec32 | .. |
382- __bid_fixunsdddi // dec64->unsigned long453| ✗ | __bid_floatdisd | long | ∅ | dec32 | .. |
383- __dpd_fixunstddi // dec128->unsigned long454| ✗ | __dpd_floatdidd | long | ∅ | dec64 | .. |
384- __bid_fixunstddi // dec128->unsigned long455| ✗ | __bid_floatdidd | long | ∅ | dec64 | .. |
385456| ✗ | __dpd_floatditd | long | ∅ | dec128 | .. |
386- __dpd_floatsisd // int->dec32457| ✗ | __bid_floatditd | long | ∅ | dec128 | .. |
387- __bid_floatsisd // int->dec32458| ✗ | __dpd_floatunssisd | unsigned int| ∅ | dec32 | .. |
388- __dpd_floatsidd // int->dec64459| ✗ | __bid_floatunssisd | unsigned int| ∅ | dec32 | .. |
389- __bid_floatsidd // int->dec64460| ✗ | __dpd_floatunssidd | unsigned int| ∅ | dec64 | .. |
390- __dpd_floatsitd // int->dec128461| ✗ | __bid_floatunssidd | unsigned int| ∅ | dec64 | .. |
391- __bid_floatsitd // int->dec128462| ✗ | __dpd_floatunssitd | unsigned int| ∅ | dec128 | .. |
392463| ✗ | __bid_floatunssitd | unsigned int| ∅ | dec128 | .. |
393- __dpd_floatdisd // long->dec32464| ✗ | __dpd_floatunsdisd |unsigned long| ∅ | dec32 | .. |
394- __bid_floatdisd // long->dec32465| ✗ | __bid_floatunsdisd |unsigned long| ∅ | dec32 | .. |
395- __dpd_floatdidd // long->dec64466| ✗ | __dpd_floatunsdidd |unsigned long| ∅ | dec64 | .. |
396- __bid_floatdidd // long->dec64467| ✗ | __bid_floatunsdidd |unsigned long| ∅ | dec64 | .. |
397- __dpd_floatditd // long->dec128468| ✗ | __dpd_floatunsditd |unsigned long| ∅ | dec128 | .. |
398- __bid_floatditd // long->dec128469| ✗ | __bid_floatunsditd |unsigned long| ∅ | dec128 | .. |
399470| | | | | | **Decimal Float Comparison** |
400- __dpd_floatunssisd // unsigned int->dec32471| ✗ | __dpd_unordsd2 | dec32 | dec32 | c_int | `a +-NaN or a +-NaN -> 1(nonzero), else -> 0` |
401- __bid_floatunssisd // unsigned int->dec32472| ✗ | __bid_unordsd2 | dec32 | dec32 | c_int | .. |
402- __dpd_floatunssidd // unsigned int->dec64473| ✗ | __dpd_unorddd2 | dec64 | dec64 | c_int | .. |
403- __bid_floatunssidd // unsigned int->dec64474| ✗ | __bid_unorddd2 | dec64 | dec64 | c_int | .. |
404- __dpd_floatunssitd // unsigned int->dec128475| ✗ | __dpd_unordtd2 | dec128 | dec128 | c_int | .. |
405- __bid_floatunssitd // unsigned int->dec128476| ✗ | __bid_unordtd2 | dec128 | dec128 | c_int | .. |
406477| ✗ | __dpd_eqsd2 | dec32 | dec32 | c_int |`a!=+-NaN and b!=+-Nan and a==b -> 0, else -> 1(nonzero)`|
407- __dpd_floatunsdisd // unsigned long->dec32478| ✗ | __bid_eqsd2 | dec32 | dec32 | c_int | .. |
408- __bid_floatunsdisd // unsigned long->dec32479| ✗ | __dpd_eqdd2 | dec64 | dec64 | c_int | .. |
409- __dpd_floatunsdidd // unsigned long->dec64480| ✗ | __bid_eqdd2 | dec64 | dec64 | c_int | .. |
410- __bid_floatunsdidd // unsigned long->dec64481| ✗ | __dpd_eqtd2 | dec128 | dec128 | c_int | .. |
411- __dpd_floatunsditd // unsigned long->dec128482| ✗ | __bid_eqtd2 | dec128 | dec128 | c_int | .. |
412- __bid_floatunsditd // unsigned long->dec128483| ✗ | __dpd_nesd2 | dec32 | dec32 | c_int | `a==+-NaN or b==+-NaN or a!=b -> 1(nonzero), else -> 0` |
413484| ✗ | __bid_nesd2 | dec32 | dec32 | c_int | .. |
414#### Decimal float Comparison485| ✗ | __dpd_nedd2 | dec64 | dec64 | c_int | .. |
415486| ✗ | __bid_nedd2 | dec64 | dec64 | c_int | .. |
416All decimal float comparison routines return c_int.487| ✗ | __dpd_netd2 | dec128 | dec128 | c_int | .. |
417488| ✗ | __bid_netd2 | dec128 | dec128 | c_int | .. |
418- __dpd_unordsd2 // a,b: dec32, a +-NaN or a +-NaN -> 1(nonzero), else -> 0489| ✗ | __dpd_gesd2 | dec32 | dec32 | c_int | `a!=+-NaN and b!=+-NaN and a>=b -> >=0, else -> <0` |
419- __bid_unordsd2 // a,b: dec32490| ✗ | __bid_gesd2 | dec32 | dec32 | c_int | .. |
420- __dpd_unorddd2 // a,b: dec64491| ✗ | __dpd_gedd2 | dec64 | dec64 | c_int | .. |
421- __bid_unorddd2 // a,b: dec64492| ✗ | __bid_gedd2 | dec64 | dec64 | c_int | .. |
422- __dpd_unordtd2 // a,b: dec128493| ✗ | __dpd_getd2 | dec128 | dec128 | c_int | .. |
423- __bid_unordtd2 // a,b: dec128494| ✗ | __bid_getd2 | dec128 | dec128 | c_int | .. |
424495| ✗ | __dpd_ltsd2 | dec32 | dec32 | c_int | `a!=+-NaN and b!=+-NaN and a<b -> <0, else -> >=0` |
425- __dpd_eqsd2 // a,b: dec32, a!=+-NaN and b!=+-Nan and a==b -> 0, else -> 1(nonzero)496| ✗ | __bid_ltsd2 | dec32 | dec32 | c_int | .. |
426- __bid_eqsd2 // a,b: dec32497| ✗ | __dpd_ltdd2 | dec64 | dec64 | c_int | .. |
427- __dpd_eqdd2 // a,b: dec64498| ✗ | __bid_ltdd2 | dec64 | dec64 | c_int | .. |
428- __bid_eqdd2 // a,b: dec64499| ✗ | __dpd_lttd2 | dec128 | dec128 | c_int | .. |
429- __dpd_eqtd2 // a,b: dec128500| ✗ | __bid_lttd2 | dec128 | dec128 | c_int | .. |
430- __bid_eqtd2 // a,b: dec128501| ✗ | __dpd_lesd2 | dec32 | dec32 | c_int | `a!=+-NaN and b!=+-NaN and a<=b -> <=0, else -> >=0` |
431502| ✗ | __bid_lesd2 | dec32 | dec32 | c_int | .. |
432- __dpd_nesd2 // a,b: dec32, a==+-NaN or b==+-NaN or a!=b -> 1(nonzero), else -> 0503| ✗ | __dpd_ledd2 | dec64 | dec64 | c_int | .. |
433- __bid_nesd2 // a,b: dec32504| ✗ | __bid_ledd2 | dec64 | dec64 | c_int | .. |
434- __dpd_nedd2 // a,b: dec64505| ✗ | __dpd_letd2 | dec128 | dec128 | c_int | .. |
435- __bid_nedd2 // a,b: dec64506| ✗ | __bid_letd2 | dec128 | dec128 | c_int | .. |
436- __dpd_netd2 // a,b: dec128507| ✗ | __dpd_gtsd2 | dec32 | dec32 | c_int | `a!=+-NaN and b!=+-NaN and a>b -> >0, else -> <=0` |
437- __bid_netd2 // a,b: dec128508| ✗ | __bid_gtsd2 | dec32 | dec32 | c_int | .. |
438509| ✗ | __dpd_gtdd2 | dec64 | dec64 | c_int | .. |
439- __dpd_gesd2 // a,b: dec32, a!=+-NaN and b!=+-NaN and a>=b -> >=0, else -> <0510| ✗ | __bid_gtdd2 | dec64 | dec64 | c_int | .. |
440- __bid_gesd2 // a,b: dec32511| ✗ | __dpd_gttd2 | dec128 | dec128 | c_int | .. |
441- __dpd_gedd2 // a,b: dec64512| ✗ | __bid_gttd2 | dec128 | dec128 | c_int | .. |
442- __bid_gedd2 // a,b: dec64513| | | | | | **Decimal Float Arithmetic**[^options] |
443- __dpd_getd2 // a,b: dec128514| ✗ | __dpd_addsd3 | dec32 | dec32 | dec32 |`a + b`|
444- __bid_getd2 // a,b: dec128515| ✗ | __bid_addsd3 | dec32 | dec32 | dec32 | .. |
445516| ✗ | __dpd_adddd3 | dec64 | dec64 | dec64 | .. |
446- __dpd_ltsd2 // a,b: dec32, a!=+-NaN and b!=+-NaN and a<b -> <0, else -> >=0517| ✗ | __bid_adddd3 | dec64 | dec64 | dec64 | .. |
447- __bid_ltsd2 // a,b: dec32518| ✗ | __dpd_addtd3 | dec128 | dec128 | dec128 | .. |
448- __dpd_ltdd2 // a,b: dec64519| ✗ | __bid_addtd3 | dec128 | dec128 | dec128 | .. |
449- __bid_ltdd2 // a,b: dec64520| ✗ | __dpd_subsd3 | dec32 | dec32 | dec32 |`a - b`|
450- __dpd_lttd2 // a,b: dec128521| ✗ | __bid_subsd3 | dec32 | dec32 | dec32 | .. |
451- __bid_lttd2 // a,b: dec128522| ✗ | __dpd_subdd3 | dec64 | dec64 | dec64 | .. |
452523| ✗ | __bid_subdd3 | dec64 | dec64 | dec64 | .. |
453- __dpd_lesd2 // a,b: dec32, a!=+-NaN and b!=+-NaN and a<=b -> <=0, else -> >=0524| ✗ | __dpd_subtd3 | dec128 | dec128 | dec128 | .. |
454- __bid_lesd2 // a,b: dec32525| ✗ | __bid_subtd3 | dec128 | dec128 | dec128 | .. |
455- __dpd_ledd2 // a,b: dec64526| ✗ | __dpd_mulsd3 | dec32 | dec32 | dec32 |`a * b`|
456- __bid_ledd2 // a,b: dec64527| ✗ | __bid_mulsd3 | dec32 | dec32 | dec32 | .. |
457- __dpd_letd2 // a,b: dec128528| ✗ | __dpd_muldd3 | dec64 | dec64 | dec64 | .. |
458- __bid_letd2 // a,b: dec128529| ✗ | __bid_muldd3 | dec64 | dec64 | dec64 | .. |
459530| ✗ | __dpd_multd3 | dec128 | dec128 | dec128 | .. |
460- __dpd_gtsd2 // a,b: dec32, a!=+-NaN and b!=+-NaN and a>b -> >0, else -> <=0531| ✗ | __bid_multd3 | dec128 | dec128 | dec128 | .. |
461- __bid_gtsd2 // a,b: dec32532| ✗ | __dpd_divsd3 | dec32 | dec32 | dec32 |`a / b`|
462- __dpd_gtdd2 // a,b: dec64533| ✗ | __bid_divsd3 | dec32 | dec32 | dec32 | .. |
463- __bid_gtdd2 // a,b: dec64534| ✗ | __dpd_divdd3 | dec64 | dec64 | dec64 | .. |
464- __dpd_gttd2 // a,b: dec128535| ✗ | __bid_divdd3 | dec64 | dec64 | dec64 | .. |
465- __bid_gttd2 // a,b: dec128536| ✗ | __dpd_divtd3 | dec128 | dec128 | dec128 | .. |
466537| ✗ | __bid_divtd3 | dec128 | dec128 | dec128 | .. |
467#### Decimal float Arithmetic538| ✗ | __dpd_negsd2 | dec32 | dec32 | dec32 | `-a` |
468539| ✗ | __bid_negsd2 | dec32 | dec32 | dec32 | .. |
469These numbers include options with routines for +-0 and +-Nan.540| ✗ | __dpd_negdd2 | dec64 | dec64 | dec64 | .. |
470541| ✗ | __bid_negdd2 | dec64 | dec64 | dec64 | .. |
471- __dpd_addsd3 // a,b: dec32 -> dec32, a + b542| ✗ | __dpd_negtd2 | dec128 | dec128 | dec128 | .. |
472- __bid_addsd3 // a,b: dec32 -> dec32543| ✗ | __bid_negtd2 | dec128 | dec128 | dec128 | .. |
473- __dpd_adddd3 // a,b: dec64 -> dec64544
474- __bid_adddd3 // a,b: dec64 -> dec64545[^options]: These numbers include options with routines for +-0 and +-Nan.
475- __dpd_addtd3 // a,b: dec128-> dec128546
476- __bid_addtd3 // a,b: dec128-> dec128547Fixed-point fractional library routines
477- __dpd_subsd3 // a,b: dec32, a - b548
478- __bid_subsd3 // a,b: dec32 -> dec32549TODO brief explanation + implementation
479- __dpd_subdd3 // a,b: dec64 ..550
480- __bid_subdd3 // a,b: dec64551| Done | Name | a | b | Out | Comment |
481- __dpd_subtd3 // a,b: dec128552| ------ | ------------- | --------- | --------- | --------- | -------------------------- |
482- __bid_subtd3 // a,b: dec128553| | | | | | **Fixed-Point Fractional** |
483- __dpd_mulsd3 // a,b: dec32, a * b554
484- __bid_mulsd3 // a,b: dec32 -> dec32555Further content:
485- __dpd_muldd3 // a,b: dec64 ..556- aarch64 outline atomics
486- __bid_muldd3 // a,b: dec64557- atomics
487- __dpd_multd3 // a,b: dec128558- msvc things like _alldiv, _aulldiv, _allrem
488- __bid_multd3 // a,b: dec128559- clear cache
489- __dpd_divsd3 // a,b: dec32, a / b560- tls emulation
490- __bid_divsd3 // a,b: dec32 -> dec32561- math routines (cos, sin, tan, ceil, floor, exp, exp2, fabs, log, log10, log2, sincos, sqrt)
491- __dpd_divdd3 // a,b: dec64 ..562- bcmp
492- __bid_divdd3 // a,b: dec64563- ieee float routines (fma, fmax, fmin, fmod, fabs, float rounding, )
493- __dpd_divtd3 // a,b: dec128564- arm routines (memory routines + memclr [setting to 0], divmod routines and stubs for unwind_cpp)
494- __bid_divtd3 // a,b: dec128565- memory routines (memcmp, memcpy, memset, memmove)
495- __dpd_negsd2 // a,b: dec32, -a566- objective-c __isPlatformVersionAtLeast check
496- __bid_negsd2 // a,b: dec32 -> dec32567- stack probe routines
497- __dpd_negdd2 // a,b: dec64 ..568
498- __bid_negdd2 // a,b: dec64569Future work
499- __dpd_negtd2 // a,b: dec128570
500- __bid_negtd2 // a,b: dec128571Arbitrary length integer library routines
501
502## Fixed-point fractional library routines
503
504TODO
505
506Too unclear for work items:
507- Miscellaneous routines => unclear, if supported (cache control and stack functions)
508- Zig-specific language runtime features, for example "Arbitrary length integer library routines"