1
2
3
4
5 package test
6
7 import (
8 "math"
9 "testing"
10 )
11
12
13 func compare1(a, b float64) bool {
14 return a < b
15 }
16
17
18 func compare2(a, b float32) bool {
19 return a < b
20 }
21
22 func TestFloatCompare(t *testing.T) {
23 if !compare1(3, 5) {
24 t.Errorf("compare1 returned false")
25 }
26 if !compare2(3, 5) {
27 t.Errorf("compare2 returned false")
28 }
29 }
30
31 func TestFloatCompareFolded(t *testing.T) {
32
33 d1, d3, d5, d9 := float64(1), float64(3), float64(5), float64(9)
34 if d3 == d5 {
35 t.Errorf("d3 == d5 returned true")
36 }
37 if d3 != d3 {
38 t.Errorf("d3 != d3 returned true")
39 }
40 if d3 > d5 {
41 t.Errorf("d3 > d5 returned true")
42 }
43 if d3 >= d9 {
44 t.Errorf("d3 >= d9 returned true")
45 }
46 if d5 < d1 {
47 t.Errorf("d5 < d1 returned true")
48 }
49 if d9 <= d1 {
50 t.Errorf("d9 <= d1 returned true")
51 }
52 if math.NaN() == math.NaN() {
53 t.Errorf("math.NaN() == math.NaN() returned true")
54 }
55 if math.NaN() >= math.NaN() {
56 t.Errorf("math.NaN() >= math.NaN() returned true")
57 }
58 if math.NaN() <= math.NaN() {
59 t.Errorf("math.NaN() <= math.NaN() returned true")
60 }
61 if math.Copysign(math.NaN(), -1) < math.NaN() {
62 t.Errorf("math.Copysign(math.NaN(), -1) < math.NaN() returned true")
63 }
64 if math.Inf(1) != math.Inf(1) {
65 t.Errorf("math.Inf(1) != math.Inf(1) returned true")
66 }
67 if math.Inf(-1) != math.Inf(-1) {
68 t.Errorf("math.Inf(-1) != math.Inf(-1) returned true")
69 }
70 if math.Copysign(0, -1) != 0 {
71 t.Errorf("math.Copysign(0, -1) != 0 returned true")
72 }
73 if math.Copysign(0, -1) < 0 {
74 t.Errorf("math.Copysign(0, -1) < 0 returned true")
75 }
76 if 0 > math.Copysign(0, -1) {
77 t.Errorf("0 > math.Copysign(0, -1) returned true")
78 }
79
80
81 s1, s3, s5, s9 := float32(1), float32(3), float32(5), float32(9)
82 if s3 == s5 {
83 t.Errorf("s3 == s5 returned true")
84 }
85 if s3 != s3 {
86 t.Errorf("s3 != s3 returned true")
87 }
88 if s3 > s5 {
89 t.Errorf("s3 > s5 returned true")
90 }
91 if s3 >= s9 {
92 t.Errorf("s3 >= s9 returned true")
93 }
94 if s5 < s1 {
95 t.Errorf("s5 < s1 returned true")
96 }
97 if s9 <= s1 {
98 t.Errorf("s9 <= s1 returned true")
99 }
100 sPosNaN, sNegNaN := float32(math.NaN()), float32(math.Copysign(math.NaN(), -1))
101 if sPosNaN == sPosNaN {
102 t.Errorf("sPosNaN == sPosNaN returned true")
103 }
104 if sPosNaN >= sPosNaN {
105 t.Errorf("sPosNaN >= sPosNaN returned true")
106 }
107 if sPosNaN <= sPosNaN {
108 t.Errorf("sPosNaN <= sPosNaN returned true")
109 }
110 if sNegNaN < sPosNaN {
111 t.Errorf("sNegNaN < sPosNaN returned true")
112 }
113 sPosInf, sNegInf := float32(math.Inf(1)), float32(math.Inf(-1))
114 if sPosInf != sPosInf {
115 t.Errorf("sPosInf != sPosInf returned true")
116 }
117 if sNegInf != sNegInf {
118 t.Errorf("sNegInf != sNegInf returned true")
119 }
120 sNegZero := float32(math.Copysign(0, -1))
121 if sNegZero != 0 {
122 t.Errorf("sNegZero != 0 returned true")
123 }
124 if sNegZero < 0 {
125 t.Errorf("sNegZero < 0 returned true")
126 }
127 if 0 > sNegZero {
128 t.Errorf("0 > sNegZero returned true")
129 }
130 }
131
132
133 func cvt1(a float64) uint64 {
134 return uint64(a)
135 }
136
137
138 func cvt2(a float64) uint32 {
139 return uint32(a)
140 }
141
142
143 func cvt3(a float32) uint64 {
144 return uint64(a)
145 }
146
147
148 func cvt4(a float32) uint32 {
149 return uint32(a)
150 }
151
152
153 func cvt5(a float64) int64 {
154 return int64(a)
155 }
156
157
158 func cvt6(a float64) int32 {
159 return int32(a)
160 }
161
162
163 func cvt7(a float32) int64 {
164 return int64(a)
165 }
166
167
168 func cvt8(a float32) int32 {
169 return int32(a)
170 }
171
172
173
174
175 func cvt9(a float64) int {
176 return int(a)
177 }
178
179
180 func cvt10(a float64) uint {
181 return uint(a)
182 }
183
184
185 func cvt11(a float32) int {
186 return int(a)
187 }
188
189
190 func cvt12(a float32) uint {
191 return uint(a)
192 }
193
194
195 func f2i64p(v float64) *int64 {
196 return ip64(int64(v / 0.1))
197 }
198
199
200 func ip64(v int64) *int64 {
201 return &v
202 }
203
204 func TestFloatConvert(t *testing.T) {
205 if got := cvt1(3.5); got != 3 {
206 t.Errorf("cvt1 got %d, wanted 3", got)
207 }
208 if got := cvt2(3.5); got != 3 {
209 t.Errorf("cvt2 got %d, wanted 3", got)
210 }
211 if got := cvt3(3.5); got != 3 {
212 t.Errorf("cvt3 got %d, wanted 3", got)
213 }
214 if got := cvt4(3.5); got != 3 {
215 t.Errorf("cvt4 got %d, wanted 3", got)
216 }
217 if got := cvt5(3.5); got != 3 {
218 t.Errorf("cvt5 got %d, wanted 3", got)
219 }
220 if got := cvt6(3.5); got != 3 {
221 t.Errorf("cvt6 got %d, wanted 3", got)
222 }
223 if got := cvt7(3.5); got != 3 {
224 t.Errorf("cvt7 got %d, wanted 3", got)
225 }
226 if got := cvt8(3.5); got != 3 {
227 t.Errorf("cvt8 got %d, wanted 3", got)
228 }
229 if got := cvt9(3.5); got != 3 {
230 t.Errorf("cvt9 got %d, wanted 3", got)
231 }
232 if got := cvt10(3.5); got != 3 {
233 t.Errorf("cvt10 got %d, wanted 3", got)
234 }
235 if got := cvt11(3.5); got != 3 {
236 t.Errorf("cvt11 got %d, wanted 3", got)
237 }
238 if got := cvt12(3.5); got != 3 {
239 t.Errorf("cvt12 got %d, wanted 3", got)
240 }
241 if got := *f2i64p(10); got != 100 {
242 t.Errorf("f2i64p got %d, wanted 100", got)
243 }
244 }
245
246 func TestFloatConvertFolded(t *testing.T) {
247
248
249 u64, u32, u16, u8 := uint64(1<<63), uint32(1<<31), uint16(1<<15), uint8(1<<7)
250 i64, i32, i16, i8 := int64(-1<<63), int32(-1<<31), int16(-1<<15), int8(-1<<7)
251 du64, du32, du16, du8 := float64(1<<63), float64(1<<31), float64(1<<15), float64(1<<7)
252 di64, di32, di16, di8 := float64(-1<<63), float64(-1<<31), float64(-1<<15), float64(-1<<7)
253 su64, su32, su16, su8 := float32(1<<63), float32(1<<31), float32(1<<15), float32(1<<7)
254 si64, si32, si16, si8 := float32(-1<<63), float32(-1<<31), float32(-1<<15), float32(-1<<7)
255
256
257 if float64(u64) != du64 {
258 t.Errorf("float64(u64) != du64")
259 }
260 if float64(u32) != du32 {
261 t.Errorf("float64(u32) != du32")
262 }
263 if float64(u16) != du16 {
264 t.Errorf("float64(u16) != du16")
265 }
266 if float64(u8) != du8 {
267 t.Errorf("float64(u8) != du8")
268 }
269 if float64(i64) != di64 {
270 t.Errorf("float64(i64) != di64")
271 }
272 if float64(i32) != di32 {
273 t.Errorf("float64(i32) != di32")
274 }
275 if float64(i16) != di16 {
276 t.Errorf("float64(i16) != di16")
277 }
278 if float64(i8) != di8 {
279 t.Errorf("float64(i8) != di8")
280 }
281 if float32(u64) != su64 {
282 t.Errorf("float32(u64) != su64")
283 }
284 if float32(u32) != su32 {
285 t.Errorf("float32(u32) != su32")
286 }
287 if float32(u16) != su16 {
288 t.Errorf("float32(u16) != su16")
289 }
290 if float32(u8) != su8 {
291 t.Errorf("float32(u8) != su8")
292 }
293 if float32(i64) != si64 {
294 t.Errorf("float32(i64) != si64")
295 }
296 if float32(i32) != si32 {
297 t.Errorf("float32(i32) != si32")
298 }
299 if float32(i16) != si16 {
300 t.Errorf("float32(i16) != si16")
301 }
302 if float32(i8) != si8 {
303 t.Errorf("float32(i8) != si8")
304 }
305
306
307 if uint64(du64) != u64 {
308 t.Errorf("uint64(du64) != u64")
309 }
310 if uint32(du32) != u32 {
311 t.Errorf("uint32(du32) != u32")
312 }
313 if uint16(du16) != u16 {
314 t.Errorf("uint16(du16) != u16")
315 }
316 if uint8(du8) != u8 {
317 t.Errorf("uint8(du8) != u8")
318 }
319 if int64(di64) != i64 {
320 t.Errorf("int64(di64) != i64")
321 }
322 if int32(di32) != i32 {
323 t.Errorf("int32(di32) != i32")
324 }
325 if int16(di16) != i16 {
326 t.Errorf("int16(di16) != i16")
327 }
328 if int8(di8) != i8 {
329 t.Errorf("int8(di8) != i8")
330 }
331 if uint64(su64) != u64 {
332 t.Errorf("uint64(su64) != u64")
333 }
334 if uint32(su32) != u32 {
335 t.Errorf("uint32(su32) != u32")
336 }
337 if uint16(su16) != u16 {
338 t.Errorf("uint16(su16) != u16")
339 }
340 if uint8(su8) != u8 {
341 t.Errorf("uint8(su8) != u8")
342 }
343 if int64(si64) != i64 {
344 t.Errorf("int64(si64) != i64")
345 }
346 if int32(si32) != i32 {
347 t.Errorf("int32(si32) != i32")
348 }
349 if int16(si16) != i16 {
350 t.Errorf("int16(si16) != i16")
351 }
352 if int8(si8) != i8 {
353 t.Errorf("int8(si8) != i8")
354 }
355 }
356
357 func TestFloat32StoreToLoadConstantFold(t *testing.T) {
358
359
360
361
362
363
364 {
365 const nan = uint32(0x7f800001)
366 if x := math.Float32bits(math.Float32frombits(nan)); x != nan {
367 t.Errorf("got %#x, want %#x", x, nan)
368 }
369 }
370 {
371 const nan = uint32(0x7fbfffff)
372 if x := math.Float32bits(math.Float32frombits(nan)); x != nan {
373 t.Errorf("got %#x, want %#x", x, nan)
374 }
375 }
376 {
377 const nan = uint32(0xff800001)
378 if x := math.Float32bits(math.Float32frombits(nan)); x != nan {
379 t.Errorf("got %#x, want %#x", x, nan)
380 }
381 }
382 {
383 const nan = uint32(0xffbfffff)
384 if x := math.Float32bits(math.Float32frombits(nan)); x != nan {
385 t.Errorf("got %#x, want %#x", x, nan)
386 }
387 }
388
389
390 {
391 const nan = uint32(0x7fc00000)
392 if x := math.Float32bits(math.Float32frombits(nan)); x != nan {
393 t.Errorf("got %#x, want %#x", x, nan)
394 }
395 }
396 {
397 const nan = uint32(0x7fffffff)
398 if x := math.Float32bits(math.Float32frombits(nan)); x != nan {
399 t.Errorf("got %#x, want %#x", x, nan)
400 }
401 }
402 {
403 const nan = uint32(0x8fc00000)
404 if x := math.Float32bits(math.Float32frombits(nan)); x != nan {
405 t.Errorf("got %#x, want %#x", x, nan)
406 }
407 }
408 {
409 const nan = uint32(0x8fffffff)
410 if x := math.Float32bits(math.Float32frombits(nan)); x != nan {
411 t.Errorf("got %#x, want %#x", x, nan)
412 }
413 }
414
415
416 {
417 const inf = uint32(0x7f800000)
418 if x := math.Float32bits(math.Float32frombits(inf)); x != inf {
419 t.Errorf("got %#x, want %#x", x, inf)
420 }
421 }
422 {
423 const negInf = uint32(0xff800000)
424 if x := math.Float32bits(math.Float32frombits(negInf)); x != negInf {
425 t.Errorf("got %#x, want %#x", x, negInf)
426 }
427 }
428
429
430 {
431 const zero = uint32(0)
432 if x := math.Float32bits(math.Float32frombits(zero)); x != zero {
433 t.Errorf("got %#x, want %#x", x, zero)
434 }
435 }
436 {
437 const negZero = uint32(1 << 31)
438 if x := math.Float32bits(math.Float32frombits(negZero)); x != negZero {
439 t.Errorf("got %#x, want %#x", x, negZero)
440 }
441 }
442 {
443 const one = uint32(0x3f800000)
444 if x := math.Float32bits(math.Float32frombits(one)); x != one {
445 t.Errorf("got %#x, want %#x", x, one)
446 }
447 }
448 {
449 const negOne = uint32(0xbf800000)
450 if x := math.Float32bits(math.Float32frombits(negOne)); x != negOne {
451 t.Errorf("got %#x, want %#x", x, negOne)
452 }
453 }
454 {
455 const frac = uint32(0x3fc00000)
456 if x := math.Float32bits(math.Float32frombits(frac)); x != frac {
457 t.Errorf("got %#x, want %#x", x, frac)
458 }
459 }
460 {
461 const negFrac = uint32(0xbfc00000)
462 if x := math.Float32bits(math.Float32frombits(negFrac)); x != negFrac {
463 t.Errorf("got %#x, want %#x", x, negFrac)
464 }
465 }
466 }
467
468
469 const (
470 snan32bits uint32 = 0x7f800001
471 snan64bits uint64 = 0x7ff0000000000001
472 )
473
474
475 var snan32bitsVar uint32 = snan32bits
476 var snan64bitsVar uint64 = snan64bits
477
478 func TestFloatSignalingNaN(t *testing.T) {
479
480
481 f32 := math.Float32frombits(snan32bits)
482 g32 := math.Float32frombits(snan32bitsVar)
483 x32 := math.Float32bits(f32)
484 y32 := math.Float32bits(g32)
485 if x32 != y32 {
486 t.Errorf("got %x, want %x (diff=%x)", x32, y32, x32^y32)
487 }
488
489 f64 := math.Float64frombits(snan64bits)
490 g64 := math.Float64frombits(snan64bitsVar)
491 x64 := math.Float64bits(f64)
492 y64 := math.Float64bits(g64)
493 if x64 != y64 {
494 t.Errorf("got %x, want %x (diff=%x)", x64, y64, x64^y64)
495 }
496 }
497
498 func TestFloatSignalingNaNConversion(t *testing.T) {
499
500
501
502 s32 := math.Float32frombits(snan32bitsVar)
503 if s32 == s32 {
504 t.Errorf("converting a NaN did not result in a NaN")
505 }
506 s64 := math.Float64frombits(snan64bitsVar)
507 if s64 == s64 {
508 t.Errorf("converting a NaN did not result in a NaN")
509 }
510 }
511
512 func TestFloatSignalingNaNConversionConst(t *testing.T) {
513
514
515
516 s32 := math.Float32frombits(snan32bits)
517 if s32 == s32 {
518 t.Errorf("converting a NaN did not result in a NaN")
519 }
520 s64 := math.Float64frombits(snan64bits)
521 if s64 == s64 {
522 t.Errorf("converting a NaN did not result in a NaN")
523 }
524 }
525
526 var sinkFloat float64
527
528 func BenchmarkMul2(b *testing.B) {
529 for i := 0; i < b.N; i++ {
530 var m float64 = 1
531 for j := 0; j < 500; j++ {
532 m *= 2
533 }
534 sinkFloat = m
535 }
536 }
537 func BenchmarkMulNeg2(b *testing.B) {
538 for i := 0; i < b.N; i++ {
539 var m float64 = 1
540 for j := 0; j < 500; j++ {
541 m *= -2
542 }
543 sinkFloat = m
544 }
545 }
546
View as plain text