]> git.proxmox.com Git - rustc.git/blob - vendor/compiler_builtins/src/float/mod.rs
New upstream version 1.54.0+dfsg1
[rustc.git] / vendor / compiler_builtins / src / float / mod.rs
1 use core::ops;
2
3 use super::int::Int;
4
5 pub mod add;
6 pub mod cmp;
7 pub mod conv;
8 pub mod div;
9 pub mod extend;
10 pub mod mul;
11 pub mod pow;
12 pub mod sub;
13
14 public_test_dep! {
15 /// Trait for some basic operations on floats
16 pub(crate) trait Float:
17 Copy
18 + core::fmt::Debug
19 + PartialEq
20 + PartialOrd
21 + ops::AddAssign
22 + ops::MulAssign
23 + ops::Add<Output = Self>
24 + ops::Sub<Output = Self>
25 + ops::Div<Output = Self>
26 + ops::Rem<Output = Self>
27 {
28 /// A uint of the same with as the float
29 type Int: Int;
30
31 /// A int of the same with as the float
32 type SignedInt: Int;
33
34 /// An int capable of containing the exponent bits plus a sign bit. This is signed.
35 type ExpInt: Int;
36
37 const ZERO: Self;
38 const ONE: Self;
39
40 /// The bitwidth of the float type
41 const BITS: u32;
42
43 /// The bitwidth of the significand
44 const SIGNIFICAND_BITS: u32;
45
46 /// The bitwidth of the exponent
47 const EXPONENT_BITS: u32 = Self::BITS - Self::SIGNIFICAND_BITS - 1;
48
49 /// The maximum value of the exponent
50 const EXPONENT_MAX: u32 = (1 << Self::EXPONENT_BITS) - 1;
51
52 /// The exponent bias value
53 const EXPONENT_BIAS: u32 = Self::EXPONENT_MAX >> 1;
54
55 /// A mask for the sign bit
56 const SIGN_MASK: Self::Int;
57
58 /// A mask for the significand
59 const SIGNIFICAND_MASK: Self::Int;
60
61 // The implicit bit of the float format
62 const IMPLICIT_BIT: Self::Int;
63
64 /// A mask for the exponent
65 const EXPONENT_MASK: Self::Int;
66
67 /// Returns `self` transmuted to `Self::Int`
68 fn repr(self) -> Self::Int;
69
70 /// Returns `self` transmuted to `Self::SignedInt`
71 fn signed_repr(self) -> Self::SignedInt;
72
73 /// Checks if two floats have the same bit representation. *Except* for NaNs! NaN can be
74 /// represented in multiple different ways. This method returns `true` if two NaNs are
75 /// compared.
76 fn eq_repr(self, rhs: Self) -> bool;
77
78 /// Returns the sign bit
79 fn sign(self) -> bool;
80
81 /// Returns the exponent with bias
82 fn exp(self) -> Self::ExpInt;
83
84 /// Returns the significand with no implicit bit (or the "fractional" part)
85 fn frac(self) -> Self::Int;
86
87 /// Returns the significand with implicit bit
88 fn imp_frac(self) -> Self::Int;
89
90 /// Returns a `Self::Int` transmuted back to `Self`
91 fn from_repr(a: Self::Int) -> Self;
92
93 /// Constructs a `Self` from its parts. Inputs are treated as bits and shifted into position.
94 fn from_parts(sign: bool, exponent: Self::Int, significand: Self::Int) -> Self;
95
96 /// Returns (normalized exponent, normalized significand)
97 fn normalize(significand: Self::Int) -> (i32, Self::Int);
98
99 /// Returns if `self` is subnormal
100 fn is_subnormal(self) -> bool;
101 }
102 }
103
104 macro_rules! float_impl {
105 ($ty:ident, $ity:ident, $sity:ident, $expty:ident, $bits:expr, $significand_bits:expr) => {
106 impl Float for $ty {
107 type Int = $ity;
108 type SignedInt = $sity;
109 type ExpInt = $expty;
110
111 const ZERO: Self = 0.0;
112 const ONE: Self = 1.0;
113
114 const BITS: u32 = $bits;
115 const SIGNIFICAND_BITS: u32 = $significand_bits;
116
117 const SIGN_MASK: Self::Int = 1 << (Self::BITS - 1);
118 const SIGNIFICAND_MASK: Self::Int = (1 << Self::SIGNIFICAND_BITS) - 1;
119 const IMPLICIT_BIT: Self::Int = 1 << Self::SIGNIFICAND_BITS;
120 const EXPONENT_MASK: Self::Int = !(Self::SIGN_MASK | Self::SIGNIFICAND_MASK);
121
122 fn repr(self) -> Self::Int {
123 self.to_bits()
124 }
125 fn signed_repr(self) -> Self::SignedInt {
126 self.to_bits() as Self::SignedInt
127 }
128 fn eq_repr(self, rhs: Self) -> bool {
129 if self.is_nan() && rhs.is_nan() {
130 true
131 } else {
132 self.repr() == rhs.repr()
133 }
134 }
135 fn sign(self) -> bool {
136 self.signed_repr() < Self::SignedInt::ZERO
137 }
138 fn exp(self) -> Self::ExpInt {
139 ((self.to_bits() & Self::EXPONENT_MASK) >> Self::SIGNIFICAND_BITS) as Self::ExpInt
140 }
141 fn frac(self) -> Self::Int {
142 self.to_bits() & Self::SIGNIFICAND_MASK
143 }
144 fn imp_frac(self) -> Self::Int {
145 self.frac() | Self::IMPLICIT_BIT
146 }
147 fn from_repr(a: Self::Int) -> Self {
148 Self::from_bits(a)
149 }
150 fn from_parts(sign: bool, exponent: Self::Int, significand: Self::Int) -> Self {
151 Self::from_repr(
152 ((sign as Self::Int) << (Self::BITS - 1))
153 | ((exponent << Self::SIGNIFICAND_BITS) & Self::EXPONENT_MASK)
154 | (significand & Self::SIGNIFICAND_MASK),
155 )
156 }
157 fn normalize(significand: Self::Int) -> (i32, Self::Int) {
158 let shift = significand
159 .leading_zeros()
160 .wrapping_sub((Self::Int::ONE << Self::SIGNIFICAND_BITS).leading_zeros());
161 (
162 1i32.wrapping_sub(shift as i32),
163 significand << shift as Self::Int,
164 )
165 }
166 fn is_subnormal(self) -> bool {
167 (self.repr() & Self::EXPONENT_MASK) == Self::Int::ZERO
168 }
169 }
170 };
171 }
172
173 float_impl!(f32, u32, i32, i16, 32, 23);
174 float_impl!(f64, u64, i64, i16, 64, 52);