const_fixed_from_int implementation that works on rustc 1.44
This commit is contained in:
parent
c6ea032292
commit
be0fd36bf5
29
src/lib.rs
29
src/lib.rs
|
@ -590,27 +590,14 @@ fixed! {
|
||||||
#[macro_export]
|
#[macro_export]
|
||||||
macro_rules! const_fixed_from_int {
|
macro_rules! const_fixed_from_int {
|
||||||
($(const $NAME:ident: $Fixed:ty = $int:expr;)*) => { $(
|
($(const $NAME:ident: $Fixed:ty = $int:expr;)*) => { $(
|
||||||
const $NAME: $Fixed = <$Fixed>::from_bits({
|
const $NAME: $Fixed = {
|
||||||
let int = $int;
|
const FRAC: u32 = <$Fixed>::FRAC_NBITS;
|
||||||
// 0 should work even for no integer bits.
|
// Divide shift into two parts for cases where $Fixed cannot represent 1.
|
||||||
if int == 0 {
|
// Use $Fixed as type because there isn't a const way to get the inner type.
|
||||||
// Use int here to clearly ensure that the type of int is the inner type.
|
const ONE_A: $Fixed = <$Fixed>::from_bits(1 << FRAC / 2);
|
||||||
int
|
const ONE_B: $Fixed = <$Fixed>::from_bits(1 << FRAC - FRAC / 2);
|
||||||
} else {
|
<$Fixed>::from_bits($int * ONE_A.to_bits() * ONE_B.to_bits())
|
||||||
// Fails to compile if int is not zero and there are no integer bits.
|
};
|
||||||
let one_bits = <$Fixed>::from_bits(1).to_bits() << <$Fixed>::FRAC_NBITS;
|
|
||||||
if one_bits > 0 {
|
|
||||||
// one_bits is positive: multiplication overflows if int does not fit.
|
|
||||||
int * one_bits
|
|
||||||
} else if !int == 0 {
|
|
||||||
// one_bits is negative minimum for signed inner type and int is -1.
|
|
||||||
one_bits
|
|
||||||
} else {
|
|
||||||
// one_bits is negative minimum and int is not 0 or -1: overflow.
|
|
||||||
1 / 0
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
)* };
|
)* };
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue