LEFT | RIGHT |
1 // Copyright 2012 The Go Authors. All rights reserved. | 1 // Copyright 2012 The Go Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style | 2 // Use of this source code is governed by a BSD-style |
3 // license that can be found in the LICENSE file. | 3 // license that can be found in the LICENSE file. |
4 | 4 |
5 package runtime_test | 5 package runtime_test |
6 | 6 |
7 import ( | 7 import ( |
8 . "runtime" | 8 . "runtime" |
9 "testing" | 9 "testing" |
10 "unsafe" | 10 "unsafe" |
11 ) | 11 ) |
12 | 12 |
13 // Simple serial sanity test for parallelfor. | 13 // Simple serial sanity test for parallelfor. |
14 func TestParfor(t *testing.T) { | 14 func TestParFor(t *testing.T) { |
15 const P = 1 | 15 const P = 1 |
16 const N = 20 | 16 const N = 20 |
17 data := make([]uint64, N) | 17 data := make([]uint64, N) |
18 for i := uint64(0); i < N; i++ { | 18 for i := uint64(0); i < N; i++ { |
19 data[i] = i | 19 data[i] = i |
20 } | 20 } |
21 » desc := NewParfor(P) | 21 » desc := NewParFor(P) |
22 » ParforSetup(desc, P, N, nil, true, func(desc *Parfor, i uint32) { | 22 » ParForSetup(desc, P, N, nil, true, func(desc *ParFor, i uint32) { |
23 data[i] = data[i]*data[i] + 1 | 23 data[i] = data[i]*data[i] + 1 |
24 }) | 24 }) |
25 » ParforDo(desc) | 25 » ParForDo(desc) |
26 for i := uint64(0); i < N; i++ { | 26 for i := uint64(0); i < N; i++ { |
27 if data[i] != i*i+1 { | 27 if data[i] != i*i+1 { |
28 » » » t.Errorf("Wrong element %d: %d", i, data[i]) | 28 » » » t.Fatalf("Wrong element %d: %d", i, data[i]) |
29 } | 29 } |
30 } | 30 } |
31 } | 31 } |
32 | 32 |
33 // Test that nonblocking parallelfor does not block. | 33 // Test that nonblocking parallelfor does not block. |
34 func TestParfor2(t *testing.T) { | 34 func TestParFor2(t *testing.T) { |
35 const P = 7 | 35 const P = 7 |
36 const N = 1003 | 36 const N = 1003 |
37 data := make([]uint64, N) | 37 data := make([]uint64, N) |
38 for i := uint64(0); i < N; i++ { | 38 for i := uint64(0); i < N; i++ { |
39 data[i] = i | 39 data[i] = i |
40 } | 40 } |
41 » desc := NewParfor(P) | 41 » desc := NewParFor(P) |
42 » ParforSetup(desc, P, N, (*byte)(unsafe.Pointer(&data)), false, func(desc
*Parfor, i uint32) { | 42 » ParForSetup(desc, P, N, (*byte)(unsafe.Pointer(&data)), false, func(desc
*ParFor, i uint32) { |
43 » » d := (*[]uint64)(unsafe.Pointer(desc.Ctx)) | 43 » » d := *(*[]uint64)(unsafe.Pointer(desc.Ctx)) |
44 » » (*d)[i] = (*d)[i]*(*d)[i] + 1 | 44 » » d[i] = d[i]*d[i] + 1 |
45 }) | 45 }) |
46 for p := 0; p < P; p++ { | 46 for p := 0; p < P; p++ { |
47 » » ParforDo(desc) | 47 » » ParForDo(desc) |
48 } | 48 } |
49 for i := uint64(0); i < N; i++ { | 49 for i := uint64(0); i < N; i++ { |
50 if data[i] != i*i+1 { | 50 if data[i] != i*i+1 { |
51 » » » t.Errorf("Wrong element %d: %d", i, data[i]) | 51 » » » t.Fatalf("Wrong element %d: %d", i, data[i]) |
52 } | 52 } |
53 } | 53 } |
54 } | 54 } |
55 | 55 |
56 // Test that iterations are properly distributed. | 56 // Test that iterations are properly distributed. |
57 func TestParforSetup(t *testing.T) { | 57 func TestParForSetup(t *testing.T) { |
58 const P = 11 | 58 const P = 11 |
59 const N = 101 | 59 const N = 101 |
60 » desc := NewParfor(P) | 60 » desc := NewParFor(P) |
61 for n := uint32(0); n < N; n++ { | 61 for n := uint32(0); n < N; n++ { |
62 for p := uint32(1); p <= P; p++ { | 62 for p := uint32(1); p <= P; p++ { |
63 » » » ParforSetup(desc, p, n, nil, true, func(desc *Parfor, i
uint32) {}) | 63 » » » ParForSetup(desc, p, n, nil, true, func(desc *ParFor, i
uint32) {}) |
64 sum := uint32(0) | 64 sum := uint32(0) |
65 size0 := uint32(0) | 65 size0 := uint32(0) |
66 end0 := uint32(0) | 66 end0 := uint32(0) |
67 for i := uint32(0); i < p; i++ { | 67 for i := uint32(0); i < p; i++ { |
68 » » » » begin, end := ParforGetIters(desc, i) | 68 » » » » begin, end := ParForIters(desc, i) |
69 size := end - begin | 69 size := end - begin |
70 sum += size | 70 sum += size |
71 if i == 0 { | 71 if i == 0 { |
72 size0 = size | 72 size0 = size |
73 if begin != 0 { | 73 if begin != 0 { |
74 » » » » » » t.Fatalf("incorrect begin: %d",
begin) | 74 » » » » » » t.Fatalf("incorrect begin: %d (n
=%d, p=%d)", begin, n, p) |
75 } | 75 } |
76 } else { | 76 } else { |
77 » » » » » if size != size0 && size != size0-1 { | 77 » » » » » if size != size0 && size != size0+1 { |
78 » » » » » » t.Fatalf("incorrect size: %d/%d"
, size, size0) | 78 » » » » » » t.Fatalf("incorrect size: %d/%d
(n=%d, p=%d)", size, size0, n, p) |
79 } | 79 } |
80 if begin != end0 { | 80 if begin != end0 { |
81 » » » » » » t.Fatalf("incorrect begin/end: %
d/%d", begin, end0) | 81 » » » » » » t.Fatalf("incorrect begin/end: %
d/%d (n=%d, p=%d)", begin, end0, n, p) |
82 } | 82 } |
83 } | 83 } |
84 end0 = end | 84 end0 = end |
85 } | 85 } |
86 if sum != n { | 86 if sum != n { |
87 » » » » t.Fatalf("incorrect sum: %d/%d", sum, n) | 87 » » » » t.Fatalf("incorrect sum: %d/%d (p=%d)", sum, n,
p) |
88 } | 88 } |
89 } | 89 } |
90 } | 90 } |
91 } | 91 } |
92 | 92 |
93 // Test parallel parallelfor. | 93 // Test parallel parallelfor. |
94 func TestParforParallel(t *testing.T) { | 94 func TestParForParallel(t *testing.T) { |
95 N := uint64(1e7) | 95 N := uint64(1e7) |
96 if testing.Short() { | 96 if testing.Short() { |
97 N /= 10 | 97 N /= 10 |
98 } | 98 } |
99 data := make([]uint64, N) | 99 data := make([]uint64, N) |
100 for i := uint64(0); i < N; i++ { | 100 for i := uint64(0); i < N; i++ { |
101 data[i] = i | 101 data[i] = i |
102 } | 102 } |
103 P := GOMAXPROCS(-1) | 103 P := GOMAXPROCS(-1) |
104 » desc := NewParfor(uint32(P)) | 104 » desc := NewParFor(uint32(P)) |
105 » ParforSetup(desc, uint32(P), uint32(N), nil, true, func(desc *Parfor, i
uint32) { | 105 » ParForSetup(desc, uint32(P), uint32(N), nil, true, func(desc *ParFor, i
uint32) { |
106 data[i] = data[i]*data[i] + 1 | 106 data[i] = data[i]*data[i] + 1 |
107 }) | 107 }) |
108 for p := 1; p < P; p++ { | 108 for p := 1; p < P; p++ { |
109 » » go func() { | 109 » » go ParForDo(desc) |
110 » » » ParforDo(desc) | |
111 » » }() | |
112 } | 110 } |
113 » ParforDo(desc) | 111 » ParForDo(desc) |
114 for i := uint64(0); i < N; i++ { | 112 for i := uint64(0); i < N; i++ { |
115 if data[i] != i*i+1 { | 113 if data[i] != i*i+1 { |
116 » » » t.Errorf("Wrong element %d: %d", i, data[i]) | 114 » » » t.Fatalf("Wrong element %d: %d", i, data[i]) |
117 } | 115 } |
118 } | 116 } |
119 } | 117 } |
LEFT | RIGHT |