@@ -13,17 +13,16 @@ fn simd_ops_f32() {
13
13
assert_eq ! ( a % b, f32x4:: from_array( [ 0.0 , 0.0 , 1.0 , 2.0 ] ) ) ;
14
14
assert_eq ! ( b. abs( ) , f32x4:: from_array( [ 1.0 , 2.0 , 3.0 , 4.0 ] ) ) ;
15
15
16
- // FIXME use Mask::from_array once simd_cast is implemented.
17
- assert_eq ! ( a. lanes_eq( f32x4:: splat( 5.0 ) * b) , Mask :: from_int( i32x4:: from_array( [ 0 , -1 , 0 , 0 ] ) ) ) ;
18
- assert_eq ! ( a. lanes_ne( f32x4:: splat( 5.0 ) * b) , Mask :: from_int( i32x4:: from_array( [ -1 , 0 , -1 , -1 ] ) ) ) ;
19
- assert_eq ! ( a. lanes_le( f32x4:: splat( 5.0 ) * b) , Mask :: from_int( i32x4:: from_array( [ 0 , -1 , -1 , 0 ] ) ) ) ;
20
- assert_eq ! ( a. lanes_lt( f32x4:: splat( 5.0 ) * b) , Mask :: from_int( i32x4:: from_array( [ 0 , 0 , -1 , 0 ] ) ) ) ;
21
- assert_eq ! ( a. lanes_ge( f32x4:: splat( 5.0 ) * b) , Mask :: from_int( i32x4:: from_array( [ -1 , -1 , 0 , -1 ] ) ) ) ;
22
- assert_eq ! ( a. lanes_gt( f32x4:: splat( 5.0 ) * b) , Mask :: from_int( i32x4:: from_array( [ -1 , 0 , 0 , -1 ] ) ) ) ;
16
+ assert_eq ! ( a. lanes_eq( f32x4:: splat( 5.0 ) * b) , Mask :: from_array( [ false , true , false , false ] ) ) ;
17
+ assert_eq ! ( a. lanes_ne( f32x4:: splat( 5.0 ) * b) , Mask :: from_array( [ true , false , true , true ] ) ) ;
18
+ assert_eq ! ( a. lanes_le( f32x4:: splat( 5.0 ) * b) , Mask :: from_array( [ false , true , true , false ] ) ) ;
19
+ assert_eq ! ( a. lanes_lt( f32x4:: splat( 5.0 ) * b) , Mask :: from_array( [ false , false , true , false ] ) ) ;
20
+ assert_eq ! ( a. lanes_ge( f32x4:: splat( 5.0 ) * b) , Mask :: from_array( [ true , true , false , true ] ) ) ;
21
+ assert_eq ! ( a. lanes_gt( f32x4:: splat( 5.0 ) * b) , Mask :: from_array( [ true , false , false , true ] ) ) ;
23
22
24
23
assert_eq ! ( a. horizontal_sum( ) , 40.0 ) ;
25
24
assert_eq ! ( b. horizontal_sum( ) , 2.0 ) ;
26
- assert_eq ! ( a. horizontal_product( ) , 100.0 * 100.0 ) ;
25
+ assert_eq ! ( a. horizontal_product( ) , 100.0 * 100.0 ) ;
27
26
assert_eq ! ( b. horizontal_product( ) , -24.0 ) ;
28
27
}
29
28
@@ -39,17 +38,16 @@ fn simd_ops_f64() {
39
38
assert_eq ! ( a % b, f64x4:: from_array( [ 0.0 , 0.0 , 1.0 , 2.0 ] ) ) ;
40
39
assert_eq ! ( b. abs( ) , f64x4:: from_array( [ 1.0 , 2.0 , 3.0 , 4.0 ] ) ) ;
41
40
42
- // FIXME use Mask::from_array once simd_cast is implemented.
43
- assert_eq ! ( a. lanes_eq( f64x4:: splat( 5.0 ) * b) , Mask :: from_int( i64x4:: from_array( [ 0 , -1 , 0 , 0 ] ) ) ) ;
44
- assert_eq ! ( a. lanes_ne( f64x4:: splat( 5.0 ) * b) , Mask :: from_int( i64x4:: from_array( [ -1 , 0 , -1 , -1 ] ) ) ) ;
45
- assert_eq ! ( a. lanes_le( f64x4:: splat( 5.0 ) * b) , Mask :: from_int( i64x4:: from_array( [ 0 , -1 , -1 , 0 ] ) ) ) ;
46
- assert_eq ! ( a. lanes_lt( f64x4:: splat( 5.0 ) * b) , Mask :: from_int( i64x4:: from_array( [ 0 , 0 , -1 , 0 ] ) ) ) ;
47
- assert_eq ! ( a. lanes_ge( f64x4:: splat( 5.0 ) * b) , Mask :: from_int( i64x4:: from_array( [ -1 , -1 , 0 , -1 ] ) ) ) ;
48
- assert_eq ! ( a. lanes_gt( f64x4:: splat( 5.0 ) * b) , Mask :: from_int( i64x4:: from_array( [ -1 , 0 , 0 , -1 ] ) ) ) ;
41
+ assert_eq ! ( a. lanes_eq( f64x4:: splat( 5.0 ) * b) , Mask :: from_array( [ false , true , false , false ] ) ) ;
42
+ assert_eq ! ( a. lanes_ne( f64x4:: splat( 5.0 ) * b) , Mask :: from_array( [ true , false , true , true ] ) ) ;
43
+ assert_eq ! ( a. lanes_le( f64x4:: splat( 5.0 ) * b) , Mask :: from_array( [ false , true , true , false ] ) ) ;
44
+ assert_eq ! ( a. lanes_lt( f64x4:: splat( 5.0 ) * b) , Mask :: from_array( [ false , false , true , false ] ) ) ;
45
+ assert_eq ! ( a. lanes_ge( f64x4:: splat( 5.0 ) * b) , Mask :: from_array( [ true , true , false , true ] ) ) ;
46
+ assert_eq ! ( a. lanes_gt( f64x4:: splat( 5.0 ) * b) , Mask :: from_array( [ true , false , false , true ] ) ) ;
49
47
50
48
assert_eq ! ( a. horizontal_sum( ) , 40.0 ) ;
51
49
assert_eq ! ( b. horizontal_sum( ) , 2.0 ) ;
52
- assert_eq ! ( a. horizontal_product( ) , 100.0 * 100.0 ) ;
50
+ assert_eq ! ( a. horizontal_product( ) , 100.0 * 100.0 ) ;
53
51
assert_eq ! ( b. horizontal_product( ) , -24.0 ) ;
54
52
}
55
53
@@ -71,13 +69,12 @@ fn simd_ops_i32() {
71
69
assert_eq ! ( b | i32x4:: splat( 2 ) , i32x4:: from_array( [ 3 , 2 , 3 , -2 ] ) ) ;
72
70
assert_eq ! ( b ^ i32x4:: splat( 2 ) , i32x4:: from_array( [ 3 , 0 , 1 , -2 ] ) ) ;
73
71
74
- // FIXME use Mask::from_array once simd_cast is implemented.
75
- assert_eq ! ( a. lanes_eq( i32x4:: splat( 5 ) * b) , Mask :: from_int( i32x4:: from_array( [ 0 , -1 , 0 , 0 ] ) ) ) ;
76
- assert_eq ! ( a. lanes_ne( i32x4:: splat( 5 ) * b) , Mask :: from_int( i32x4:: from_array( [ -1 , 0 , -1 , -1 ] ) ) ) ;
77
- assert_eq ! ( a. lanes_le( i32x4:: splat( 5 ) * b) , Mask :: from_int( i32x4:: from_array( [ 0 , -1 , -1 , 0 ] ) ) ) ;
78
- assert_eq ! ( a. lanes_lt( i32x4:: splat( 5 ) * b) , Mask :: from_int( i32x4:: from_array( [ 0 , 0 , -1 , 0 ] ) ) ) ;
79
- assert_eq ! ( a. lanes_ge( i32x4:: splat( 5 ) * b) , Mask :: from_int( i32x4:: from_array( [ -1 , -1 , 0 , -1 ] ) ) ) ;
80
- assert_eq ! ( a. lanes_gt( i32x4:: splat( 5 ) * b) , Mask :: from_int( i32x4:: from_array( [ -1 , 0 , 0 , -1 ] ) ) ) ;
72
+ assert_eq ! ( a. lanes_eq( i32x4:: splat( 5 ) * b) , Mask :: from_array( [ false , true , false , false ] ) ) ;
73
+ assert_eq ! ( a. lanes_ne( i32x4:: splat( 5 ) * b) , Mask :: from_array( [ true , false , true , true ] ) ) ;
74
+ assert_eq ! ( a. lanes_le( i32x4:: splat( 5 ) * b) , Mask :: from_array( [ false , true , true , false ] ) ) ;
75
+ assert_eq ! ( a. lanes_lt( i32x4:: splat( 5 ) * b) , Mask :: from_array( [ false , false , true , false ] ) ) ;
76
+ assert_eq ! ( a. lanes_ge( i32x4:: splat( 5 ) * b) , Mask :: from_array( [ true , true , false , true ] ) ) ;
77
+ assert_eq ! ( a. lanes_gt( i32x4:: splat( 5 ) * b) , Mask :: from_array( [ true , false , false , true ] ) ) ;
81
78
82
79
assert_eq ! ( a. horizontal_and( ) , 10 ) ;
83
80
assert_eq ! ( b. horizontal_and( ) , 0 ) ;
@@ -87,10 +84,94 @@ fn simd_ops_i32() {
87
84
assert_eq ! ( b. horizontal_xor( ) , -4 ) ;
88
85
assert_eq ! ( a. horizontal_sum( ) , 40 ) ;
89
86
assert_eq ! ( b. horizontal_sum( ) , 2 ) ;
90
- assert_eq ! ( a. horizontal_product( ) , 100 * 100 ) ;
87
+ assert_eq ! ( a. horizontal_product( ) , 100 * 100 ) ;
91
88
assert_eq ! ( b. horizontal_product( ) , -24 ) ;
92
89
}
93
90
91
+ fn simd_mask ( ) {
92
+ let intmask = Mask :: from_int ( i32x4:: from_array ( [ 0 , -1 , 0 , 0 ] ) ) ;
93
+ assert_eq ! ( intmask, Mask :: from_array( [ false , true , false , false ] ) ) ;
94
+ assert_eq ! ( intmask. to_array( ) , [ false , true , false , false ] ) ;
95
+ }
96
+
97
+ fn simd_cast ( ) {
98
+ // between integer types
99
+ assert_eq ! ( i32x4:: from_array( [ 1 , 2 , 3 , -4 ] ) , i16x4:: from_array( [ 1 , 2 , 3 , -4 ] ) . cast( ) ) ;
100
+ assert_eq ! ( i16x4:: from_array( [ 1 , 2 , 3 , -4 ] ) , i32x4:: from_array( [ 1 , 2 , 3 , -4 ] ) . cast( ) ) ;
101
+ assert_eq ! ( i32x4:: from_array( [ 1 , -1 , 3 , 4 ] ) , u64x4:: from_array( [ 1 , u64 :: MAX , 3 , 4 ] ) . cast( ) ) ;
102
+
103
+ // float -> int
104
+ assert_eq ! (
105
+ i8x4:: from_array( [ 127 , -128 , 127 , -128 ] ) ,
106
+ f32x4:: from_array( [ 127.99 , -128.99 , 999.0 , -999.0 ] ) . cast( )
107
+ ) ;
108
+ assert_eq ! (
109
+ i32x4:: from_array( [ 0 , 1 , -1 , 2147483520 ] ) ,
110
+ f32x4:: from_array( [
111
+ -0.0 ,
112
+ /*0x1.19999ap+0*/ f32 :: from_bits( 0x3f8ccccd ) ,
113
+ /*-0x1.19999ap+0*/ f32 :: from_bits( 0xbf8ccccd ) ,
114
+ 2147483520.0
115
+ ] )
116
+ . cast( )
117
+ ) ;
118
+ assert_eq ! (
119
+ i32x8:: from_array( [ i32 :: MAX , i32 :: MIN , i32 :: MAX , i32 :: MIN , i32 :: MAX , i32 :: MIN , 0 , 0 ] ) ,
120
+ f32x8:: from_array( [
121
+ 2147483648.0f32 ,
122
+ -2147483904.0f32 ,
123
+ f32 :: MAX ,
124
+ f32 :: MIN ,
125
+ f32 :: INFINITY ,
126
+ f32 :: NEG_INFINITY ,
127
+ f32 :: NAN ,
128
+ -f32 :: NAN ,
129
+ ] )
130
+ . cast( )
131
+ ) ;
132
+
133
+ // int -> float
134
+ assert_eq ! (
135
+ f32x4:: from_array( [
136
+ -2147483648.0 ,
137
+ /*0x1.26580cp+30*/ f32 :: from_bits( 0x4e932c06 ) ,
138
+ 16777220.0 ,
139
+ -16777220.0 ,
140
+ ] ) ,
141
+ i32x4:: from_array( [ -2147483647i32 , 1234567890i32 , 16777219i32 , -16777219i32 ] ) . cast( )
142
+ ) ;
143
+
144
+ // float -> float
145
+ assert_eq ! (
146
+ f32x4:: from_array( [ f32 :: INFINITY , f32 :: INFINITY , f32 :: NEG_INFINITY , f32 :: NEG_INFINITY ] ) ,
147
+ f64x4:: from_array( [ f64 :: MAX , f64 :: INFINITY , f64 :: MIN , f64 :: NEG_INFINITY ] ) . cast( )
148
+ ) ;
149
+
150
+ // unchecked casts
151
+ unsafe {
152
+ assert_eq ! (
153
+ i32x4:: from_array( [ 0 , 1 , -1 , 2147483520 ] ) ,
154
+ f32x4:: from_array( [
155
+ -0.0 ,
156
+ /*0x1.19999ap+0*/ f32 :: from_bits( 0x3f8ccccd ) ,
157
+ /*-0x1.19999ap+0*/ f32 :: from_bits( 0xbf8ccccd ) ,
158
+ 2147483520.0
159
+ ] )
160
+ . to_int_unchecked( )
161
+ ) ;
162
+ assert_eq ! (
163
+ u64x4:: from_array( [ 0 , 10000000000000000 , u64 :: MAX - 2047 , 9223372036854775808 ] ) ,
164
+ f64x4:: from_array( [
165
+ -0.99999999999 ,
166
+ 1e16 ,
167
+ ( u64 :: MAX - 1024 ) as f64 ,
168
+ 9223372036854775808.0
169
+ ] )
170
+ . to_int_unchecked( )
171
+ ) ;
172
+ }
173
+ }
174
+
94
175
fn simd_intrinsics ( ) {
95
176
extern "platform-intrinsic" {
96
177
fn simd_eq < T , U > ( x : T , y : T ) -> U ;
@@ -112,14 +193,22 @@ fn simd_intrinsics() {
112
193
assert ! ( simd_reduce_all( i32x4:: splat( -1 ) ) ) ;
113
194
assert ! ( !simd_reduce_all( i32x2:: from_array( [ 0 , -1 ] ) ) ) ;
114
195
115
- assert_eq ! ( simd_select( i8x4:: from_array( [ 0 , -1 , -1 , 0 ] ) , a, b) , i32x4:: from_array( [ 1 , 10 , 10 , 4 ] ) ) ;
116
- assert_eq ! ( simd_select( i8x4:: from_array( [ 0 , -1 , -1 , 0 ] ) , b, a) , i32x4:: from_array( [ 10 , 2 , 10 , 10 ] ) ) ;
196
+ assert_eq ! (
197
+ simd_select( i8x4:: from_array( [ 0 , -1 , -1 , 0 ] ) , a, b) ,
198
+ i32x4:: from_array( [ 1 , 10 , 10 , 4 ] )
199
+ ) ;
200
+ assert_eq ! (
201
+ simd_select( i8x4:: from_array( [ 0 , -1 , -1 , 0 ] ) , b, a) ,
202
+ i32x4:: from_array( [ 10 , 2 , 10 , 10 ] )
203
+ ) ;
117
204
}
118
205
}
119
206
120
207
fn main ( ) {
208
+ simd_mask ( ) ;
121
209
simd_ops_f32 ( ) ;
122
210
simd_ops_f64 ( ) ;
123
211
simd_ops_i32 ( ) ;
212
+ simd_cast ( ) ;
124
213
simd_intrinsics ( ) ;
125
214
}
0 commit comments