1
1
use core:: mem;
2
2
3
+ use super :: int:: Int ;
4
+
3
5
pub mod conv;
4
6
pub mod add;
5
7
pub mod pow;
@@ -8,39 +10,34 @@ pub mod sub;
8
10
/// Trait for some basic operations on floats
9
11
pub trait Float : Sized + Copy {
10
12
/// A uint of the same with as the float
11
- type Int ;
13
+ type Int : Int ;
12
14
13
- /// Returns the bitwidth of the float type
14
- fn bits ( ) -> u32 ;
15
+ /// The bitwidth of the float type
16
+ const BITS : u32 ;
15
17
16
- /// Returns the bitwidth of the significand
17
- fn significand_bits ( ) -> u32 ;
18
+ /// The bitwidth of the significand
19
+ const SIGNIFICAND_BITS : u32 ;
18
20
19
- /// Returns the bitwidth of the exponent
20
- fn exponent_bits ( ) -> u32 {
21
- Self :: bits ( ) - Self :: significand_bits ( ) - 1
22
- }
23
- /// Returns the maximum value of the exponent
24
- fn exponent_max ( ) -> u32 {
25
- ( 1 << Self :: exponent_bits ( ) ) - 1
26
- }
21
+ /// The bitwidth of the exponent
22
+ const EXPONENT_BITS : u32 = Self :: BITS - Self :: SIGNIFICAND_BITS - 1 ;
27
23
28
- /// Returns the exponent bias value
29
- fn exponent_bias ( ) -> u32 {
30
- Self :: exponent_max ( ) >> 1
31
- }
24
+ /// The maximum value of the exponent
25
+ const EXPONENT_MAX : u32 = ( 1 << Self :: EXPONENT_BITS ) - 1 ;
32
26
33
- /// Returns a mask for the sign bit
34
- fn sign_mask ( ) -> Self :: Int ;
27
+ /// The exponent bias value
28
+ const EXPONENT_BIAS : u32 = Self :: EXPONENT_MAX >> 1 ;
35
29
36
- /// Returns a mask for the significand
37
- fn significand_mask ( ) -> Self :: Int ;
30
+ /// A mask for the sign bit
31
+ const SIGN_MASK : Self :: Int ;
38
32
39
- // Returns the implicit bit of the float format
40
- fn implicit_bit ( ) -> Self :: Int ;
33
+ /// A mask for the significand
34
+ const SIGNIFICAND_MASK : Self :: Int ;
41
35
42
- /// Returns a mask for the exponent
43
- fn exponent_mask ( ) -> Self :: Int ;
36
+ // The implicit bit of the float format
37
+ const IMPLICIT_BIT : Self :: Int ;
38
+
39
+ /// A mask for the exponent
40
+ const EXPONENT_MASK : Self :: Int ;
44
41
45
42
/// Returns `self` transmuted to `Self::Int`
46
43
fn repr ( self ) -> Self :: Int ;
@@ -63,94 +60,45 @@ pub trait Float: Sized + Copy {
63
60
64
61
// FIXME: Some of this can be removed if RFC Issue #1424 is resolved
65
62
// https://github.com/rust-lang/rfcs/issues/1424
66
- impl Float for f32 {
67
- type Int = u32 ;
68
- fn bits ( ) -> u32 {
69
- 32
70
- }
71
- fn significand_bits ( ) -> u32 {
72
- 23
73
- }
74
- fn implicit_bit ( ) -> Self :: Int {
75
- 1 << Self :: significand_bits ( )
76
- }
77
- fn sign_mask ( ) -> Self :: Int {
78
- 1 << ( Self :: bits ( ) - 1 )
79
- }
80
- fn significand_mask ( ) -> Self :: Int {
81
- ( 1 << Self :: significand_bits ( ) ) - 1
82
- }
83
- fn exponent_mask ( ) -> Self :: Int {
84
- !( Self :: sign_mask ( ) | Self :: significand_mask ( ) )
85
- }
86
- fn repr ( self ) -> Self :: Int {
87
- unsafe { mem:: transmute ( self ) }
88
- }
89
- #[ cfg( test) ]
90
- fn eq_repr ( self , rhs : Self ) -> bool {
91
- if self . is_nan ( ) && rhs. is_nan ( ) {
92
- true
93
- } else {
94
- self . repr ( ) == rhs. repr ( )
63
+ macro_rules! float_impl {
64
+ ( $ty: ident, $ity: ident, $bits: expr, $significand_bits: expr) => {
65
+ impl Float for $ty {
66
+ type Int = $ity;
67
+ const BITS : u32 = $bits;
68
+ const SIGNIFICAND_BITS : u32 = $significand_bits;
69
+
70
+ const SIGN_MASK : Self :: Int = 1 << ( Self :: BITS - 1 ) ;
71
+ const SIGNIFICAND_MASK : Self :: Int = ( 1 << Self :: SIGNIFICAND_BITS ) - 1 ;
72
+ const IMPLICIT_BIT : Self :: Int = 1 << Self :: SIGNIFICAND_BITS ;
73
+ const EXPONENT_MASK : Self :: Int = !( Self :: SIGN_MASK | Self :: SIGNIFICAND_MASK ) ;
74
+
75
+ fn repr( self ) -> Self :: Int {
76
+ unsafe { mem:: transmute( self ) }
77
+ }
78
+ #[ cfg( test) ]
79
+ fn eq_repr( self , rhs: Self ) -> bool {
80
+ if self . is_nan( ) && rhs. is_nan( ) {
81
+ true
82
+ } else {
83
+ self . repr( ) == rhs. repr( )
84
+ }
85
+ }
86
+ fn from_repr( a: Self :: Int ) -> Self {
87
+ unsafe { mem:: transmute( a) }
88
+ }
89
+ fn from_parts( sign: bool , exponent: Self :: Int , significand: Self :: Int ) -> Self {
90
+ Self :: from_repr( ( ( sign as Self :: Int ) << ( Self :: BITS - 1 ) ) |
91
+ ( ( exponent << Self :: SIGNIFICAND_BITS ) & Self :: EXPONENT_MASK ) |
92
+ ( significand & Self :: SIGNIFICAND_MASK ) )
93
+ }
94
+ fn normalize( significand: Self :: Int ) -> ( i32 , Self :: Int ) {
95
+ let shift = significand. leading_zeros( )
96
+ . wrapping_sub( ( Self :: Int :: ONE << Self :: SIGNIFICAND_BITS ) . leading_zeros( ) ) ;
97
+ ( 1i32 . wrapping_sub( shift as i32 ) , significand << shift as Self :: Int )
98
+ }
95
99
}
96
100
}
97
- fn from_repr ( a : Self :: Int ) -> Self {
98
- unsafe { mem:: transmute ( a) }
99
- }
100
- fn from_parts ( sign : bool , exponent : Self :: Int , significand : Self :: Int ) -> Self {
101
- Self :: from_repr ( ( ( sign as Self :: Int ) << ( Self :: bits ( ) - 1 ) ) |
102
- ( ( exponent << Self :: significand_bits ( ) ) & Self :: exponent_mask ( ) ) |
103
- ( significand & Self :: significand_mask ( ) ) )
104
- }
105
- fn normalize ( significand : Self :: Int ) -> ( i32 , Self :: Int ) {
106
- let shift = significand. leading_zeros ( )
107
- . wrapping_sub ( ( 1u32 << Self :: significand_bits ( ) ) . leading_zeros ( ) ) ;
108
- ( 1i32 . wrapping_sub ( shift as i32 ) , significand << shift as Self :: Int )
109
- }
110
- }
111
- impl Float for f64 {
112
- type Int = u64 ;
113
- fn bits ( ) -> u32 {
114
- 64
115
- }
116
- fn significand_bits ( ) -> u32 {
117
- 52
118
- }
119
- // Returns the implicit bit of the float format
120
- fn implicit_bit ( ) -> Self :: Int {
121
- 1 << Self :: significand_bits ( )
122
- }
123
- fn sign_mask ( ) -> Self :: Int {
124
- 1 << ( Self :: bits ( ) - 1 )
125
- }
126
- fn significand_mask ( ) -> Self :: Int {
127
- ( 1 << Self :: significand_bits ( ) ) - 1
128
- }
129
- fn exponent_mask ( ) -> Self :: Int {
130
- !( Self :: sign_mask ( ) | Self :: significand_mask ( ) )
131
- }
132
- fn repr ( self ) -> Self :: Int {
133
- unsafe { mem:: transmute ( self ) }
134
- }
135
- #[ cfg( test) ]
136
- fn eq_repr ( self , rhs : Self ) -> bool {
137
- if self . is_nan ( ) && rhs. is_nan ( ) {
138
- true
139
- } else {
140
- self . repr ( ) == rhs. repr ( )
141
- }
142
- }
143
- fn from_repr ( a : Self :: Int ) -> Self {
144
- unsafe { mem:: transmute ( a) }
145
- }
146
- fn from_parts ( sign : bool , exponent : Self :: Int , significand : Self :: Int ) -> Self {
147
- Self :: from_repr ( ( ( sign as Self :: Int ) << ( Self :: bits ( ) - 1 ) ) |
148
- ( ( exponent << Self :: significand_bits ( ) ) & Self :: exponent_mask ( ) ) |
149
- ( significand & Self :: significand_mask ( ) ) )
150
- }
151
- fn normalize ( significand : Self :: Int ) -> ( i32 , Self :: Int ) {
152
- let shift = significand. leading_zeros ( )
153
- . wrapping_sub ( ( 1u64 << Self :: significand_bits ( ) ) . leading_zeros ( ) ) ;
154
- ( 1i32 . wrapping_sub ( shift as i32 ) , significand << shift as Self :: Int )
155
- }
156
101
}
102
+
103
+ float_impl ! ( f32 , u32 , 32 , 23 ) ;
104
+ float_impl ! ( f64 , u64 , 64 , 52 ) ;
0 commit comments