Source file
src/runtime/memmove_test.go
Documentation: runtime
1
2
3
4
5 package runtime_test
6
7 import (
8 "crypto/rand"
9 "encoding/binary"
10 "fmt"
11 "internal/race"
12 "internal/testenv"
13 . "runtime"
14 "sync/atomic"
15 "testing"
16 "unsafe"
17 )
18
19 func TestMemmove(t *testing.T) {
20 if *flagQuick {
21 t.Skip("-quick")
22 }
23 t.Parallel()
24 size := 256
25 if testing.Short() {
26 size = 128 + 16
27 }
28 src := make([]byte, size)
29 dst := make([]byte, size)
30 for i := 0; i < size; i++ {
31 src[i] = byte(128 + (i & 127))
32 }
33 for i := 0; i < size; i++ {
34 dst[i] = byte(i & 127)
35 }
36 for n := 0; n <= size; n++ {
37 for x := 0; x <= size-n; x++ {
38 for y := 0; y <= size-n; y++ {
39 copy(dst[y:y+n], src[x:x+n])
40 for i := 0; i < y; i++ {
41 if dst[i] != byte(i&127) {
42 t.Fatalf("prefix dst[%d] = %d", i, dst[i])
43 }
44 }
45 for i := y; i < y+n; i++ {
46 if dst[i] != byte(128+((i-y+x)&127)) {
47 t.Fatalf("copied dst[%d] = %d", i, dst[i])
48 }
49 dst[i] = byte(i & 127)
50 }
51 for i := y + n; i < size; i++ {
52 if dst[i] != byte(i&127) {
53 t.Fatalf("suffix dst[%d] = %d", i, dst[i])
54 }
55 }
56 }
57 }
58 }
59 }
60
61 func TestMemmoveAlias(t *testing.T) {
62 if *flagQuick {
63 t.Skip("-quick")
64 }
65 t.Parallel()
66 size := 256
67 if testing.Short() {
68 size = 128 + 16
69 }
70 buf := make([]byte, size)
71 for i := 0; i < size; i++ {
72 buf[i] = byte(i)
73 }
74 for n := 0; n <= size; n++ {
75 for x := 0; x <= size-n; x++ {
76 for y := 0; y <= size-n; y++ {
77 copy(buf[y:y+n], buf[x:x+n])
78 for i := 0; i < y; i++ {
79 if buf[i] != byte(i) {
80 t.Fatalf("prefix buf[%d] = %d", i, buf[i])
81 }
82 }
83 for i := y; i < y+n; i++ {
84 if buf[i] != byte(i-y+x) {
85 t.Fatalf("copied buf[%d] = %d", i, buf[i])
86 }
87 buf[i] = byte(i)
88 }
89 for i := y + n; i < size; i++ {
90 if buf[i] != byte(i) {
91 t.Fatalf("suffix buf[%d] = %d", i, buf[i])
92 }
93 }
94 }
95 }
96 }
97 }
98
99 func TestMemmoveLarge0x180000(t *testing.T) {
100 if testing.Short() && testenv.Builder() == "" {
101 t.Skip("-short")
102 }
103
104 t.Parallel()
105 if race.Enabled {
106 t.Skip("skipping large memmove test under race detector")
107 }
108 testSize(t, 0x180000)
109 }
110
111 func TestMemmoveOverlapLarge0x120000(t *testing.T) {
112 if testing.Short() && testenv.Builder() == "" {
113 t.Skip("-short")
114 }
115
116 t.Parallel()
117 if race.Enabled {
118 t.Skip("skipping large memmove test under race detector")
119 }
120 testOverlap(t, 0x120000)
121 }
122
123 func testSize(t *testing.T, size int) {
124 src := make([]byte, size)
125 dst := make([]byte, size)
126 _, _ = rand.Read(src)
127 _, _ = rand.Read(dst)
128
129 ref := make([]byte, size)
130 copyref(ref, dst)
131
132 for n := size - 50; n > 1; n >>= 1 {
133 for x := 0; x <= size-n; x = x*7 + 1 {
134 for y := 0; y <= size-n; y = y*9 + 1 {
135 copy(dst[y:y+n], src[x:x+n])
136 copyref(ref[y:y+n], src[x:x+n])
137 p := cmpb(dst, ref)
138 if p >= 0 {
139 t.Fatalf("Copy failed, copying from src[%d:%d] to dst[%d:%d].\nOffset %d is different, %v != %v", x, x+n, y, y+n, p, dst[p], ref[p])
140 }
141 }
142 }
143 }
144 }
145
146 func testOverlap(t *testing.T, size int) {
147 src := make([]byte, size)
148 test := make([]byte, size)
149 ref := make([]byte, size)
150 _, _ = rand.Read(src)
151
152 for n := size - 50; n > 1; n >>= 1 {
153 for x := 0; x <= size-n; x = x*7 + 1 {
154 for y := 0; y <= size-n; y = y*9 + 1 {
155
156 copyref(test, src)
157 copyref(ref, src)
158 copy(test[y:y+n], test[x:x+n])
159 if y <= x {
160 copyref(ref[y:y+n], ref[x:x+n])
161 } else {
162 copybw(ref[y:y+n], ref[x:x+n])
163 }
164 p := cmpb(test, ref)
165 if p >= 0 {
166 t.Fatalf("Copy failed, copying from src[%d:%d] to dst[%d:%d].\nOffset %d is different, %v != %v", x, x+n, y, y+n, p, test[p], ref[p])
167 }
168 }
169 }
170 }
171
172 }
173
174
175 func copyref(dst, src []byte) {
176 for i, v := range src {
177 dst[i] = v
178 }
179 }
180
181
182 func copybw(dst, src []byte) {
183 if len(src) == 0 {
184 return
185 }
186 for i := len(src) - 1; i >= 0; i-- {
187 dst[i] = src[i]
188 }
189 }
190
191
192 func matchLen(a, b []byte, max int) int {
193 a = a[:max]
194 b = b[:max]
195 for i, av := range a {
196 if b[i] != av {
197 return i
198 }
199 }
200 return max
201 }
202
203 func cmpb(a, b []byte) int {
204 l := matchLen(a, b, len(a))
205 if l == len(a) {
206 return -1
207 }
208 return l
209 }
210
211
212
213 func TestMemmoveAtomicity(t *testing.T) {
214 if race.Enabled {
215 t.Skip("skip under the race detector -- this test is intentionally racy")
216 }
217
218 var x int
219
220 for _, backward := range []bool{true, false} {
221 for _, n := range []int{3, 4, 5, 6, 7, 8, 9, 10, 15, 25, 49} {
222 n := n
223
224
225 sz := uintptr(n * PtrSize)
226 name := fmt.Sprint(sz)
227 if backward {
228 name += "-backward"
229 } else {
230 name += "-forward"
231 }
232 t.Run(name, func(t *testing.T) {
233
234 var s [100]*int
235 src := s[n-1 : 2*n-1]
236 dst := s[:n]
237 if backward {
238 src, dst = dst, src
239 }
240 for i := range src {
241 src[i] = &x
242 }
243 for i := range dst {
244 dst[i] = nil
245 }
246
247 var ready atomic.Uint32
248 go func() {
249 sp := unsafe.Pointer(&src[0])
250 dp := unsafe.Pointer(&dst[0])
251 ready.Store(1)
252 for i := 0; i < 10000; i++ {
253 Memmove(dp, sp, sz)
254 MemclrNoHeapPointers(dp, sz)
255 }
256 ready.Store(2)
257 }()
258
259 for ready.Load() == 0 {
260 Gosched()
261 }
262
263 for ready.Load() != 2 {
264 for i := range dst {
265 p := dst[i]
266 if p != nil && p != &x {
267 t.Fatalf("got partially updated pointer %p at dst[%d], want either nil or %p", p, i, &x)
268 }
269 }
270 }
271 })
272 }
273 }
274 }
275
276 func benchmarkSizes(b *testing.B, sizes []int, fn func(b *testing.B, n int)) {
277 for _, n := range sizes {
278 b.Run(fmt.Sprint(n), func(b *testing.B) {
279 b.SetBytes(int64(n))
280 fn(b, n)
281 })
282 }
283 }
284
285 var bufSizes = []int{
286 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16,
287 32, 64, 128, 256, 512, 1024, 2048, 4096,
288 }
289 var bufSizesOverlap = []int{
290 32, 64, 128, 256, 512, 1024, 2048, 4096,
291 }
292
293 func BenchmarkMemmove(b *testing.B) {
294 benchmarkSizes(b, bufSizes, func(b *testing.B, n int) {
295 x := make([]byte, n)
296 y := make([]byte, n)
297 for i := 0; i < b.N; i++ {
298 copy(x, y)
299 }
300 })
301 }
302
303 func BenchmarkMemmoveOverlap(b *testing.B) {
304 benchmarkSizes(b, bufSizesOverlap, func(b *testing.B, n int) {
305 x := make([]byte, n+16)
306 for i := 0; i < b.N; i++ {
307 copy(x[16:n+16], x[:n])
308 }
309 })
310 }
311
312 func BenchmarkMemmoveUnalignedDst(b *testing.B) {
313 benchmarkSizes(b, bufSizes, func(b *testing.B, n int) {
314 x := make([]byte, n+1)
315 y := make([]byte, n)
316 for i := 0; i < b.N; i++ {
317 copy(x[1:], y)
318 }
319 })
320 }
321
322 func BenchmarkMemmoveUnalignedDstOverlap(b *testing.B) {
323 benchmarkSizes(b, bufSizesOverlap, func(b *testing.B, n int) {
324 x := make([]byte, n+16)
325 for i := 0; i < b.N; i++ {
326 copy(x[16:n+16], x[1:n+1])
327 }
328 })
329 }
330
331 func BenchmarkMemmoveUnalignedSrc(b *testing.B) {
332 benchmarkSizes(b, bufSizes, func(b *testing.B, n int) {
333 x := make([]byte, n)
334 y := make([]byte, n+1)
335 for i := 0; i < b.N; i++ {
336 copy(x, y[1:])
337 }
338 })
339 }
340
341 func BenchmarkMemmoveUnalignedSrcDst(b *testing.B) {
342 for _, n := range []int{16, 64, 256, 4096, 65536} {
343 buf := make([]byte, (n+8)*2)
344 x := buf[:len(buf)/2]
345 y := buf[len(buf)/2:]
346 for _, off := range []int{0, 1, 4, 7} {
347 b.Run(fmt.Sprint("f_", n, off), func(b *testing.B) {
348 b.SetBytes(int64(n))
349 for i := 0; i < b.N; i++ {
350 copy(x[off:n+off], y[off:n+off])
351 }
352 })
353
354 b.Run(fmt.Sprint("b_", n, off), func(b *testing.B) {
355 b.SetBytes(int64(n))
356 for i := 0; i < b.N; i++ {
357 copy(y[off:n+off], x[off:n+off])
358 }
359 })
360 }
361 }
362 }
363
364 func BenchmarkMemmoveUnalignedSrcOverlap(b *testing.B) {
365 benchmarkSizes(b, bufSizesOverlap, func(b *testing.B, n int) {
366 x := make([]byte, n+1)
367 for i := 0; i < b.N; i++ {
368 copy(x[1:n+1], x[:n])
369 }
370 })
371 }
372
373 func TestMemclr(t *testing.T) {
374 size := 512
375 if testing.Short() {
376 size = 128 + 16
377 }
378 mem := make([]byte, size)
379 for i := 0; i < size; i++ {
380 mem[i] = 0xee
381 }
382 for n := 0; n < size; n++ {
383 for x := 0; x <= size-n; x++ {
384 MemclrBytes(mem[x : x+n])
385 for i := 0; i < x; i++ {
386 if mem[i] != 0xee {
387 t.Fatalf("overwrite prefix mem[%d] = %d", i, mem[i])
388 }
389 }
390 for i := x; i < x+n; i++ {
391 if mem[i] != 0 {
392 t.Fatalf("failed clear mem[%d] = %d", i, mem[i])
393 }
394 mem[i] = 0xee
395 }
396 for i := x + n; i < size; i++ {
397 if mem[i] != 0xee {
398 t.Fatalf("overwrite suffix mem[%d] = %d", i, mem[i])
399 }
400 }
401 }
402 }
403 }
404
405 func BenchmarkMemclr(b *testing.B) {
406 for _, n := range []int{5, 16, 64, 256, 4096, 65536} {
407 x := make([]byte, n)
408 b.Run(fmt.Sprint(n), func(b *testing.B) {
409 b.SetBytes(int64(n))
410 for i := 0; i < b.N; i++ {
411 MemclrBytes(x)
412 }
413 })
414 }
415 for _, m := range []int{1, 4, 8, 16, 64} {
416 x := make([]byte, m<<20)
417 b.Run(fmt.Sprint(m, "M"), func(b *testing.B) {
418 b.SetBytes(int64(m << 20))
419 for i := 0; i < b.N; i++ {
420 MemclrBytes(x)
421 }
422 })
423 }
424 }
425
426 func BenchmarkMemclrUnaligned(b *testing.B) {
427 for _, off := range []int{0, 1, 4, 7} {
428 for _, n := range []int{5, 16, 64, 256, 4096, 65536} {
429 x := make([]byte, n+off)
430 b.Run(fmt.Sprint(off, n), func(b *testing.B) {
431 b.SetBytes(int64(n))
432 for i := 0; i < b.N; i++ {
433 MemclrBytes(x[off:])
434 }
435 })
436 }
437 }
438
439 for _, off := range []int{0, 1, 4, 7} {
440 for _, m := range []int{1, 4, 8, 16, 64} {
441 x := make([]byte, (m<<20)+off)
442 b.Run(fmt.Sprint(off, m, "M"), func(b *testing.B) {
443 b.SetBytes(int64(m << 20))
444 for i := 0; i < b.N; i++ {
445 MemclrBytes(x[off:])
446 }
447 })
448 }
449 }
450 }
451
452 func BenchmarkGoMemclr(b *testing.B) {
453 benchmarkSizes(b, []int{5, 16, 64, 256}, func(b *testing.B, n int) {
454 x := make([]byte, n)
455 for i := 0; i < b.N; i++ {
456 for j := range x {
457 x[j] = 0
458 }
459 }
460 })
461 }
462
463 func BenchmarkMemclrRange(b *testing.B) {
464 type RunData struct {
465 data []int
466 }
467
468 benchSizes := []RunData{
469 {[]int{1043, 1078, 1894, 1582, 1044, 1165, 1467, 1100, 1919, 1562, 1932, 1645,
470 1412, 1038, 1576, 1200, 1029, 1336, 1095, 1494, 1350, 1025, 1502, 1548, 1316, 1296,
471 1868, 1639, 1546, 1626, 1642, 1308, 1726, 1665, 1678, 1187, 1515, 1598, 1353, 1237,
472 1977, 1452, 2012, 1914, 1514, 1136, 1975, 1618, 1536, 1695, 1600, 1733, 1392, 1099,
473 1358, 1996, 1224, 1783, 1197, 1838, 1460, 1556, 1554, 2020}},
474 {[]int{3964, 5139, 6573, 7775, 6553, 2413, 3466, 5394, 2469, 7336, 7091, 6745,
475 4028, 5643, 6164, 3475, 4138, 6908, 7559, 3335, 5660, 4122, 3945, 2082, 7564, 6584,
476 5111, 2288, 6789, 2797, 4928, 7986, 5163, 5447, 2999, 4968, 3174, 3202, 7908, 8137,
477 4735, 6161, 4646, 7592, 3083, 5329, 3687, 2754, 3599, 7231, 6455, 2549, 8063, 2189,
478 7121, 5048, 4277, 6626, 6306, 2815, 7473, 3963, 7549, 7255}},
479 {[]int{16304, 15936, 15760, 4736, 9136, 11184, 10160, 5952, 14560, 15744,
480 6624, 5872, 13088, 14656, 14192, 10304, 4112, 10384, 9344, 4496, 11392, 7024,
481 5200, 10064, 14784, 5808, 13504, 10480, 8512, 4896, 13264, 5600}},
482 {[]int{164576, 233136, 220224, 183280, 214112, 217248, 228560, 201728}},
483 }
484
485 for _, t := range benchSizes {
486 total := 0
487 minLen := 0
488 maxLen := 0
489
490 for _, clrLen := range t.data {
491 maxLen = max(maxLen, clrLen)
492 if clrLen < minLen || minLen == 0 {
493 minLen = clrLen
494 }
495 total += clrLen
496 }
497 buffer := make([]byte, maxLen)
498
499 text := ""
500 if minLen >= (1 << 20) {
501 text = fmt.Sprint(minLen>>20, "M ", (maxLen+(1<<20-1))>>20, "M")
502 } else if minLen >= (1 << 10) {
503 text = fmt.Sprint(minLen>>10, "K ", (maxLen+(1<<10-1))>>10, "K")
504 } else {
505 text = fmt.Sprint(minLen, " ", maxLen)
506 }
507 b.Run(text, func(b *testing.B) {
508 b.SetBytes(int64(total))
509 for i := 0; i < b.N; i++ {
510 for _, clrLen := range t.data {
511 MemclrBytes(buffer[:clrLen])
512 }
513 }
514 })
515 }
516 }
517
518 func BenchmarkClearFat7(b *testing.B) {
519 p := new([7]byte)
520 Escape(p)
521 b.ResetTimer()
522 for i := 0; i < b.N; i++ {
523 *p = [7]byte{}
524 }
525 }
526
527 func BenchmarkClearFat8(b *testing.B) {
528 p := new([8 / 4]uint32)
529 Escape(p)
530 b.ResetTimer()
531 for i := 0; i < b.N; i++ {
532 *p = [8 / 4]uint32{}
533 }
534 }
535
536 func BenchmarkClearFat11(b *testing.B) {
537 p := new([11]byte)
538 Escape(p)
539 b.ResetTimer()
540 for i := 0; i < b.N; i++ {
541 *p = [11]byte{}
542 }
543 }
544
545 func BenchmarkClearFat12(b *testing.B) {
546 p := new([12 / 4]uint32)
547 Escape(p)
548 b.ResetTimer()
549 for i := 0; i < b.N; i++ {
550 *p = [12 / 4]uint32{}
551 }
552 }
553
554 func BenchmarkClearFat13(b *testing.B) {
555 p := new([13]byte)
556 Escape(p)
557 b.ResetTimer()
558 for i := 0; i < b.N; i++ {
559 *p = [13]byte{}
560 }
561 }
562
563 func BenchmarkClearFat14(b *testing.B) {
564 p := new([14]byte)
565 Escape(p)
566 b.ResetTimer()
567 for i := 0; i < b.N; i++ {
568 *p = [14]byte{}
569 }
570 }
571
572 func BenchmarkClearFat15(b *testing.B) {
573 p := new([15]byte)
574 Escape(p)
575 b.ResetTimer()
576 for i := 0; i < b.N; i++ {
577 *p = [15]byte{}
578 }
579 }
580
581 func BenchmarkClearFat16(b *testing.B) {
582 p := new([16 / 4]uint32)
583 Escape(p)
584 b.ResetTimer()
585 for i := 0; i < b.N; i++ {
586 *p = [16 / 4]uint32{}
587 }
588 }
589
590 func BenchmarkClearFat24(b *testing.B) {
591 p := new([24 / 4]uint32)
592 Escape(p)
593 b.ResetTimer()
594 for i := 0; i < b.N; i++ {
595 *p = [24 / 4]uint32{}
596 }
597 }
598
599 func BenchmarkClearFat32(b *testing.B) {
600 p := new([32 / 4]uint32)
601 Escape(p)
602 b.ResetTimer()
603 for i := 0; i < b.N; i++ {
604 *p = [32 / 4]uint32{}
605 }
606 }
607
608 func BenchmarkClearFat40(b *testing.B) {
609 p := new([40 / 4]uint32)
610 Escape(p)
611 b.ResetTimer()
612 for i := 0; i < b.N; i++ {
613 *p = [40 / 4]uint32{}
614 }
615 }
616
617 func BenchmarkClearFat48(b *testing.B) {
618 p := new([48 / 4]uint32)
619 Escape(p)
620 b.ResetTimer()
621 for i := 0; i < b.N; i++ {
622 *p = [48 / 4]uint32{}
623 }
624 }
625
626 func BenchmarkClearFat56(b *testing.B) {
627 p := new([56 / 4]uint32)
628 Escape(p)
629 b.ResetTimer()
630 for i := 0; i < b.N; i++ {
631 *p = [56 / 4]uint32{}
632 }
633 }
634
635 func BenchmarkClearFat64(b *testing.B) {
636 p := new([64 / 4]uint32)
637 Escape(p)
638 b.ResetTimer()
639 for i := 0; i < b.N; i++ {
640 *p = [64 / 4]uint32{}
641 }
642 }
643
644 func BenchmarkClearFat72(b *testing.B) {
645 p := new([72 / 4]uint32)
646 Escape(p)
647 b.ResetTimer()
648 for i := 0; i < b.N; i++ {
649 *p = [72 / 4]uint32{}
650 }
651 }
652
653 func BenchmarkClearFat128(b *testing.B) {
654 p := new([128 / 4]uint32)
655 Escape(p)
656 b.ResetTimer()
657 for i := 0; i < b.N; i++ {
658 *p = [128 / 4]uint32{}
659 }
660 }
661
662 func BenchmarkClearFat256(b *testing.B) {
663 p := new([256 / 4]uint32)
664 Escape(p)
665 b.ResetTimer()
666 for i := 0; i < b.N; i++ {
667 *p = [256 / 4]uint32{}
668 }
669 }
670
671 func BenchmarkClearFat512(b *testing.B) {
672 p := new([512 / 4]uint32)
673 Escape(p)
674 b.ResetTimer()
675 for i := 0; i < b.N; i++ {
676 *p = [512 / 4]uint32{}
677 }
678 }
679
680 func BenchmarkClearFat1024(b *testing.B) {
681 p := new([1024 / 4]uint32)
682 Escape(p)
683 b.ResetTimer()
684 for i := 0; i < b.N; i++ {
685 *p = [1024 / 4]uint32{}
686 }
687 }
688
689 func BenchmarkClearFat1032(b *testing.B) {
690 p := new([1032 / 4]uint32)
691 Escape(p)
692 b.ResetTimer()
693 for i := 0; i < b.N; i++ {
694 *p = [1032 / 4]uint32{}
695 }
696 }
697
698 func BenchmarkClearFat1040(b *testing.B) {
699 p := new([1040 / 4]uint32)
700 Escape(p)
701 b.ResetTimer()
702 for i := 0; i < b.N; i++ {
703 *p = [1040 / 4]uint32{}
704 }
705 }
706
707 func BenchmarkCopyFat7(b *testing.B) {
708 var x [7]byte
709 p := new([7]byte)
710 Escape(p)
711 b.ResetTimer()
712 for i := 0; i < b.N; i++ {
713 *p = x
714 }
715 }
716
717 func BenchmarkCopyFat8(b *testing.B) {
718 var x [8 / 4]uint32
719 p := new([8 / 4]uint32)
720 Escape(p)
721 b.ResetTimer()
722 for i := 0; i < b.N; i++ {
723 *p = x
724 }
725 }
726
727 func BenchmarkCopyFat11(b *testing.B) {
728 var x [11]byte
729 p := new([11]byte)
730 Escape(p)
731 b.ResetTimer()
732 for i := 0; i < b.N; i++ {
733 *p = x
734 }
735 }
736
737 func BenchmarkCopyFat12(b *testing.B) {
738 var x [12 / 4]uint32
739 p := new([12 / 4]uint32)
740 Escape(p)
741 b.ResetTimer()
742 for i := 0; i < b.N; i++ {
743 *p = x
744 }
745 }
746
747 func BenchmarkCopyFat13(b *testing.B) {
748 var x [13]byte
749 p := new([13]byte)
750 Escape(p)
751 b.ResetTimer()
752 for i := 0; i < b.N; i++ {
753 *p = x
754 }
755 }
756
757 func BenchmarkCopyFat14(b *testing.B) {
758 var x [14]byte
759 p := new([14]byte)
760 Escape(p)
761 b.ResetTimer()
762 for i := 0; i < b.N; i++ {
763 *p = x
764 }
765 }
766
767 func BenchmarkCopyFat15(b *testing.B) {
768 var x [15]byte
769 p := new([15]byte)
770 Escape(p)
771 b.ResetTimer()
772 for i := 0; i < b.N; i++ {
773 *p = x
774 }
775 }
776
777 func BenchmarkCopyFat16(b *testing.B) {
778 var x [16 / 4]uint32
779 p := new([16 / 4]uint32)
780 Escape(p)
781 b.ResetTimer()
782 for i := 0; i < b.N; i++ {
783 *p = x
784 }
785 }
786
787 func BenchmarkCopyFat24(b *testing.B) {
788 var x [24 / 4]uint32
789 p := new([24 / 4]uint32)
790 Escape(p)
791 b.ResetTimer()
792 for i := 0; i < b.N; i++ {
793 *p = x
794 }
795 }
796
797 func BenchmarkCopyFat32(b *testing.B) {
798 var x [32 / 4]uint32
799 p := new([32 / 4]uint32)
800 Escape(p)
801 b.ResetTimer()
802 for i := 0; i < b.N; i++ {
803 *p = x
804 }
805 }
806
807 func BenchmarkCopyFat64(b *testing.B) {
808 var x [64 / 4]uint32
809 p := new([64 / 4]uint32)
810 Escape(p)
811 b.ResetTimer()
812 for i := 0; i < b.N; i++ {
813 *p = x
814 }
815 }
816
817 func BenchmarkCopyFat72(b *testing.B) {
818 var x [72 / 4]uint32
819 p := new([72 / 4]uint32)
820 Escape(p)
821 b.ResetTimer()
822 for i := 0; i < b.N; i++ {
823 *p = x
824 }
825 }
826
827 func BenchmarkCopyFat128(b *testing.B) {
828 var x [128 / 4]uint32
829 p := new([128 / 4]uint32)
830 Escape(p)
831 b.ResetTimer()
832 for i := 0; i < b.N; i++ {
833 *p = x
834 }
835 }
836
837 func BenchmarkCopyFat256(b *testing.B) {
838 var x [256 / 4]uint32
839 p := new([256 / 4]uint32)
840 Escape(p)
841 b.ResetTimer()
842 for i := 0; i < b.N; i++ {
843 *p = x
844 }
845 }
846
847 func BenchmarkCopyFat512(b *testing.B) {
848 var x [512 / 4]uint32
849 p := new([512 / 4]uint32)
850 Escape(p)
851 b.ResetTimer()
852 for i := 0; i < b.N; i++ {
853 *p = x
854 }
855 }
856
857 func BenchmarkCopyFat520(b *testing.B) {
858 var x [520 / 4]uint32
859 p := new([520 / 4]uint32)
860 Escape(p)
861 b.ResetTimer()
862 for i := 0; i < b.N; i++ {
863 *p = x
864 }
865 }
866
867 func BenchmarkCopyFat1024(b *testing.B) {
868 var x [1024 / 4]uint32
869 p := new([1024 / 4]uint32)
870 Escape(p)
871 b.ResetTimer()
872 for i := 0; i < b.N; i++ {
873 *p = x
874 }
875 }
876
877 func BenchmarkCopyFat1032(b *testing.B) {
878 var x [1032 / 4]uint32
879 p := new([1032 / 4]uint32)
880 Escape(p)
881 b.ResetTimer()
882 for i := 0; i < b.N; i++ {
883 *p = x
884 }
885 }
886
887 func BenchmarkCopyFat1040(b *testing.B) {
888 var x [1040 / 4]uint32
889 p := new([1040 / 4]uint32)
890 Escape(p)
891 b.ResetTimer()
892 for i := 0; i < b.N; i++ {
893 *p = x
894 }
895 }
896
897
898
899
900 func BenchmarkIssue18740(b *testing.B) {
901 benchmarks := []struct {
902 name string
903 nbyte int
904 f func([]byte) uint64
905 }{
906 {"2byte", 2, func(buf []byte) uint64 { return uint64(binary.LittleEndian.Uint16(buf)) }},
907 {"4byte", 4, func(buf []byte) uint64 { return uint64(binary.LittleEndian.Uint32(buf)) }},
908 {"8byte", 8, func(buf []byte) uint64 { return binary.LittleEndian.Uint64(buf) }},
909 }
910
911 var g [4096]byte
912 for _, bm := range benchmarks {
913 buf := make([]byte, bm.nbyte)
914 b.Run(bm.name, func(b *testing.B) {
915 for j := 0; j < b.N; j++ {
916 for i := 0; i < 4096; i += bm.nbyte {
917 copy(buf[:], g[i:])
918 sink += bm.f(buf[:])
919 }
920 }
921 })
922 }
923 }
924
925 var memclrSink []int8
926
927 func BenchmarkMemclrKnownSize1(b *testing.B) {
928 var x [1]int8
929
930 b.SetBytes(1)
931 for i := 0; i < b.N; i++ {
932 for a := range x {
933 x[a] = 0
934 }
935 }
936
937 memclrSink = x[:]
938 }
939 func BenchmarkMemclrKnownSize2(b *testing.B) {
940 var x [2]int8
941
942 b.SetBytes(2)
943 for i := 0; i < b.N; i++ {
944 for a := range x {
945 x[a] = 0
946 }
947 }
948
949 memclrSink = x[:]
950 }
951 func BenchmarkMemclrKnownSize4(b *testing.B) {
952 var x [4]int8
953
954 b.SetBytes(4)
955 for i := 0; i < b.N; i++ {
956 for a := range x {
957 x[a] = 0
958 }
959 }
960
961 memclrSink = x[:]
962 }
963 func BenchmarkMemclrKnownSize8(b *testing.B) {
964 var x [8]int8
965
966 b.SetBytes(8)
967 for i := 0; i < b.N; i++ {
968 for a := range x {
969 x[a] = 0
970 }
971 }
972
973 memclrSink = x[:]
974 }
975 func BenchmarkMemclrKnownSize16(b *testing.B) {
976 var x [16]int8
977
978 b.SetBytes(16)
979 for i := 0; i < b.N; i++ {
980 for a := range x {
981 x[a] = 0
982 }
983 }
984
985 memclrSink = x[:]
986 }
987 func BenchmarkMemclrKnownSize32(b *testing.B) {
988 var x [32]int8
989
990 b.SetBytes(32)
991 for i := 0; i < b.N; i++ {
992 for a := range x {
993 x[a] = 0
994 }
995 }
996
997 memclrSink = x[:]
998 }
999 func BenchmarkMemclrKnownSize64(b *testing.B) {
1000 var x [64]int8
1001
1002 b.SetBytes(64)
1003 for i := 0; i < b.N; i++ {
1004 for a := range x {
1005 x[a] = 0
1006 }
1007 }
1008
1009 memclrSink = x[:]
1010 }
1011 func BenchmarkMemclrKnownSize112(b *testing.B) {
1012 var x [112]int8
1013
1014 b.SetBytes(112)
1015 for i := 0; i < b.N; i++ {
1016 for a := range x {
1017 x[a] = 0
1018 }
1019 }
1020
1021 memclrSink = x[:]
1022 }
1023
1024 func BenchmarkMemclrKnownSize128(b *testing.B) {
1025 var x [128]int8
1026
1027 b.SetBytes(128)
1028 for i := 0; i < b.N; i++ {
1029 for a := range x {
1030 x[a] = 0
1031 }
1032 }
1033
1034 memclrSink = x[:]
1035 }
1036
1037 func BenchmarkMemclrKnownSize192(b *testing.B) {
1038 var x [192]int8
1039
1040 b.SetBytes(192)
1041 for i := 0; i < b.N; i++ {
1042 for a := range x {
1043 x[a] = 0
1044 }
1045 }
1046
1047 memclrSink = x[:]
1048 }
1049
1050 func BenchmarkMemclrKnownSize248(b *testing.B) {
1051 var x [248]int8
1052
1053 b.SetBytes(248)
1054 for i := 0; i < b.N; i++ {
1055 for a := range x {
1056 x[a] = 0
1057 }
1058 }
1059
1060 memclrSink = x[:]
1061 }
1062
1063 func BenchmarkMemclrKnownSize256(b *testing.B) {
1064 var x [256]int8
1065
1066 b.SetBytes(256)
1067 for i := 0; i < b.N; i++ {
1068 for a := range x {
1069 x[a] = 0
1070 }
1071 }
1072
1073 memclrSink = x[:]
1074 }
1075 func BenchmarkMemclrKnownSize512(b *testing.B) {
1076 var x [512]int8
1077
1078 b.SetBytes(512)
1079 for i := 0; i < b.N; i++ {
1080 for a := range x {
1081 x[a] = 0
1082 }
1083 }
1084
1085 memclrSink = x[:]
1086 }
1087 func BenchmarkMemclrKnownSize1024(b *testing.B) {
1088 var x [1024]int8
1089
1090 b.SetBytes(1024)
1091 for i := 0; i < b.N; i++ {
1092 for a := range x {
1093 x[a] = 0
1094 }
1095 }
1096
1097 memclrSink = x[:]
1098 }
1099 func BenchmarkMemclrKnownSize4096(b *testing.B) {
1100 var x [4096]int8
1101
1102 b.SetBytes(4096)
1103 for i := 0; i < b.N; i++ {
1104 for a := range x {
1105 x[a] = 0
1106 }
1107 }
1108
1109 memclrSink = x[:]
1110 }
1111 func BenchmarkMemclrKnownSize512KiB(b *testing.B) {
1112 var x [524288]int8
1113
1114 b.SetBytes(524288)
1115 for i := 0; i < b.N; i++ {
1116 for a := range x {
1117 x[a] = 0
1118 }
1119 }
1120
1121 memclrSink = x[:]
1122 }
1123
View as plain text