1
2
3
4
5 package ssacompile
6
7 import (
8 "testing"
9 "unsafe"
10 )
11
12
13
14
15 func justReturn0() int {
16 var x, y, z int
17 xp := &x
18 yp := &y
19 zp := &z
20 *xp = 0
21 *yp = 1
22 *zp = 2
23 *yp = 3
24 *zp = 4
25 *yp = 5
26 valX1 := *xp
27 *zp = valX1 - 1
28 *xp = 1
29 *yp = 2
30 *xp = 3
31 *yp = 4
32 *xp = 5
33 valZ1 := *zp
34 *yp = valZ1 + 1
35 *zp = 1
36 *xp = 2
37 *zp = 3
38 *xp = 4
39 *zp = 5
40 valY1 := *yp
41 return valY1
42 }
43
44
45
46
47 func ifElseAddr(c bool) int {
48 x := 1
49 p := &x
50 if c {
51 *p = 2
52 } else {
53 *p = 3
54 }
55 return *p
56 }
57
58
59 func ifElseReg(c bool) int {
60 if c {
61 return 2
62 }
63 return 3
64 }
65
66
67
68
69 func loopAddr() int {
70 sum := 0
71 p := &sum
72 for i := 0; i < 10; i++ {
73 *p += i
74 }
75 return *p
76 }
77
78
79 func loopReg() int {
80 sum := 0
81 for i := 0; i < 10; i++ {
82 sum += i
83 }
84 return sum
85 }
86
87
88
89
90 func nestedLoopAddr() int {
91 sum := 0
92 p := &sum
93 for i := 0; i < 10; i++ {
94 for j := 0; j < 10; j++ {
95 *p += i + j
96 }
97 }
98 return *p
99 }
100
101
102 func nestedLoopReg() int {
103 sum := 0
104 for i := 0; i < 10; i++ {
105 for j := 0; j < 10; j++ {
106 sum += i + j
107 }
108 }
109 return sum
110 }
111
112
113
114
115 func switchCaseAddr(x int) int {
116 res := 0
117 p := &res
118 switch x {
119 case 0:
120 *p = 10
121 case 1:
122 *p = 20
123 default:
124 *p = 30
125 }
126 return *p
127 }
128
129
130 func switchCaseReg(x int) int {
131 switch x {
132 case 0:
133 return 10
134 case 1:
135 return 20
136 default:
137 return 30
138 }
139 }
140
141
142
143
144 func gotoAddr(n int) int {
145 sum := 0
146 p := &sum
147 i := 0
148 loop:
149 if i >= n {
150 goto end
151 }
152 *p += i
153 i++
154 goto loop
155 end:
156 return *p
157 }
158
159
160 func gotoReg(n int) int {
161 sum := 0
162 i := 0
163 loop:
164 if i >= n {
165 goto end
166 }
167 sum += i
168 i++
169 goto loop
170 end:
171 return sum
172 }
173
174
175
176
177 func complexAddr(n int) int {
178 res := 0
179 p := &res
180
181
182 inc := func(val int) {
183 *p += val
184 }
185
186 for i := 0; i < n; i++ {
187
188 switch i % 3 {
189 case 0:
190 *p += i
191 case 1:
192 if i > 5 {
193 *p -= i
194 } else {
195 inc(i)
196 }
197 default:
198
199 for j := 0; j < 2; j++ {
200 *p += j
201 }
202 }
203 }
204 return *p
205 }
206
207
208 func complexReg(n int) int {
209 res := 0
210
211 inc := func(val int) {
212 res += val
213 }
214
215 for i := 0; i < n; i++ {
216 switch i % 3 {
217 case 0:
218 res += i
219 case 1:
220 if i > 5 {
221 res -= i
222 } else {
223 inc(i)
224 }
225 default:
226 for j := 0; j < 2; j++ {
227 res += j
228 }
229 }
230 }
231 return res
232 }
233
234
235 func unsafeTypedStoreAddr(c bool) int64 {
236
237
238
239 var x int64 = 7
240 if c {
241 *(*float64)(unsafe.Pointer(&x)) = 1.5
242 }
243 return x
244 }
245
246
247 func unsafeTypedStoreReg(c bool) int64 {
248 x := int64(7)
249 if c {
250 x = int64(0x3ff8000000000000)
251 }
252 return x
253 }
254
255 func TestMem2Reg(t *testing.T) {
256 if r := justReturn0(); r != 0 {
257 t.Errorf("justReturn0() = %d, want 0", r)
258 }
259 if got, want := ifElseAddr(true), ifElseReg(true); got != want {
260 t.Errorf("ifElse(true): got %d, want %d", got, want)
261 }
262 if got, want := ifElseAddr(false), ifElseReg(false); got != want {
263 t.Errorf("ifElse(false): got %d, want %d", got, want)
264 }
265
266 if got, want := loopAddr(), loopReg(); got != want {
267 t.Errorf("loop: got %d, want %d", got, want)
268 }
269 if got, want := nestedLoopAddr(), nestedLoopReg(); got != want {
270 t.Errorf("nestedLoop: got %d, want %d", got, want)
271 }
272 for _, x := range []int{0, 1, 2} {
273 if got, want := switchCaseAddr(x), switchCaseReg(x); got != want {
274 t.Errorf("switchCase(%d): got %d, want %d", x, got, want)
275 }
276 }
277 if got, want := gotoAddr(10), gotoReg(10); got != want {
278 t.Errorf("goto: got %d, want %d", got, want)
279 }
280 if got, want := complexAddr(20), complexReg(20); got != want {
281 t.Errorf("complex: got %d, want %d", got, want)
282 }
283 for _, c := range []bool{true, false} {
284 if got, want := unsafeTypedStoreAddr(c), unsafeTypedStoreReg(c); got != want {
285 t.Errorf("unsafeTypedStore(%v): got %#x, want %#x", c, got, want)
286 }
287 }
288 }
289
View as plain text