blob: ae982f495742b17cf82d149962077e429f40aee1 [file] [log] [blame]
Russ Coxfcb4cab2014-09-11 12:17:45 -04001// errorcheck -0 -l -live -wb=0
Russ Coxca9975a2014-01-16 10:32:30 -05002
3// Copyright 2014 The Go Authors. All rights reserved.
4// Use of this source code is governed by a BSD-style
5// license that can be found in the LICENSE file.
6
Russ Coxeb540792014-06-02 21:26:32 -04007// liveness tests with inlining disabled.
8// see also live2.go.
9
Russ Coxca9975a2014-01-16 10:32:30 -050010package main
11
Russ Cox75d3f622014-11-05 14:42:54 -050012func printnl()
13
14//go:noescape
15func printpointer(**int)
16
17//go:noescape
18func printintpointer(*int)
19
20//go:noescape
21func printstringpointer(*string)
22
23//go:noescape
24func printstring(string)
25
26//go:noescape
27func printbytepointer(*byte)
28
29func printint(int)
30
Russ Coxca9975a2014-01-16 10:32:30 -050031func f1() {
32 var x *int
Russ Cox75d3f622014-11-05 14:42:54 -050033 printpointer(&x) // ERROR "live at call to printpointer: x$"
34 printpointer(&x) // ERROR "live at call to printpointer: x$"
Russ Coxca9975a2014-01-16 10:32:30 -050035}
36
37func f2(b bool) {
38 if b {
Russ Cox75d3f622014-11-05 14:42:54 -050039 printint(0) // nothing live here
Russ Coxca9975a2014-01-16 10:32:30 -050040 return
41 }
42 var x *int
Russ Cox75d3f622014-11-05 14:42:54 -050043 printpointer(&x) // ERROR "live at call to printpointer: x$"
44 printpointer(&x) // ERROR "live at call to printpointer: x$"
Russ Coxca9975a2014-01-16 10:32:30 -050045}
46
47func f3(b bool) {
Russ Cox28f18682014-04-03 20:33:25 -040048 // Because x and y are ambiguously live, they appear
49 // live throughout the function, to avoid being poisoned
50 // in GODEBUG=gcdead=1 mode.
51
Russ Cox75d3f622014-11-05 14:42:54 -050052 printint(0) // ERROR "live at call to printint: x y$"
Russ Coxca9975a2014-01-16 10:32:30 -050053 if b == false {
Russ Cox75d3f622014-11-05 14:42:54 -050054 printint(0) // ERROR "live at call to printint: x y$"
Russ Coxca9975a2014-01-16 10:32:30 -050055 return
56 }
57
58 if b {
59 var x *int
Russ Cox75d3f622014-11-05 14:42:54 -050060 printpointer(&x) // ERROR "live at call to printpointer: x y$"
61 printpointer(&x) // ERROR "live at call to printpointer: x y$"
Russ Coxca9975a2014-01-16 10:32:30 -050062 } else {
63 var y *int
Russ Cox75d3f622014-11-05 14:42:54 -050064 printpointer(&y) // ERROR "live at call to printpointer: x y$"
65 printpointer(&y) // ERROR "live at call to printpointer: x y$"
Russ Coxca9975a2014-01-16 10:32:30 -050066 }
Dmitry Vyukov76477412015-02-19 22:00:11 +030067 printint(0) // ERROR "f3: x \(type \*int\) is ambiguously live$" "f3: y \(type \*int\) is ambiguously live$" "live at call to printint: x y$"
Russ Coxca9975a2014-01-16 10:32:30 -050068}
69
70// The old algorithm treated x as live on all code that
71// could flow to a return statement, so it included the
72// function entry and code above the declaration of x
73// but would not include an indirect use of x in an infinite loop.
74// Check that these cases are handled correctly.
75
76func f4(b1, b2 bool) { // x not live here
77 if b2 {
Russ Cox75d3f622014-11-05 14:42:54 -050078 printint(0) // x not live here
Russ Coxca9975a2014-01-16 10:32:30 -050079 return
80 }
81 var z **int
82 x := new(int)
83 *x = 42
84 z = &x
Russ Cox75d3f622014-11-05 14:42:54 -050085 printint(**z) // ERROR "live at call to printint: x z$"
Russ Coxca9975a2014-01-16 10:32:30 -050086 if b2 {
Russ Cox75d3f622014-11-05 14:42:54 -050087 printint(1) // ERROR "live at call to printint: x$"
Russ Coxca9975a2014-01-16 10:32:30 -050088 return
89 }
90 for {
Russ Cox75d3f622014-11-05 14:42:54 -050091 printint(**z) // ERROR "live at call to printint: x z$"
Russ Coxca9975a2014-01-16 10:32:30 -050092 }
93}
94
95func f5(b1 bool) {
96 var z **int
97 if b1 {
98 x := new(int)
99 *x = 42
100 z = &x
101 } else {
102 y := new(int)
103 *y = 54
104 z = &y
105 }
Dmitry Vyukov76477412015-02-19 22:00:11 +0300106 printint(**z) // ERROR "f5: x \(type \*int\) is ambiguously live$" "f5: y \(type \*int\) is ambiguously live$" "live at call to printint: x y$"
Russ Coxca9975a2014-01-16 10:32:30 -0500107}
Russ Coxa069cf02014-02-13 20:59:39 -0500108
109// confusion about the _ result used to cause spurious "live at entry to f6: _".
110
111func f6() (_, y string) {
112 y = "hello"
113 return
114}
Russ Cox824e9182014-02-13 21:11:50 -0500115
116// confusion about addressed results used to cause "live at entry to f7: x".
117
118func f7() (x string) {
119 _ = &x
120 x = "hello"
121 return
122}
123
Russ Cox91b1f7c2014-02-13 22:45:16 -0500124// ignoring block returns used to cause "live at entry to f8: x, y".
125
126func f8() (x, y string) {
127 return g8()
128}
129
130func g8() (string, string)
131
132// ignoring block assignments used to cause "live at entry to f9: x"
133// issue 7205
134
135var i9 interface{}
136
137func f9() bool {
138 g8()
139 x := i9
Dmitry Vyukov76477412015-02-19 22:00:11 +0300140 return x != interface{}(99.0i) // ERROR "live at call to convT2E: x$"
Russ Cox91b1f7c2014-02-13 22:45:16 -0500141}
Russ Coxab9e8d02014-02-13 23:56:53 -0500142
143// liveness formerly confused by UNDEF followed by RET,
144// leading to "live at entry to f10: ~r1" (unnamed result).
145
146func f10() string {
147 panic(1)
148}
149
Russ Coxaf545662014-02-14 00:38:24 -0500150// liveness formerly confused by select, thinking runtime.selectgo
151// can return to next instruction; it always jumps elsewhere.
152// note that you have to use at least two cases in the select
153// to get a true select; smaller selects compile to optimized helper functions.
154
155var c chan *int
156var b bool
157
158// this used to have a spurious "live at entry to f11a: ~r0"
159func f11a() *int {
Dmitry Vyukov76477412015-02-19 22:00:11 +0300160 select { // ERROR "live at call to newselect: autotmp_[0-9]+$" "live at call to selectgo: autotmp_[0-9]+$"
161 case <-c: // ERROR "live at call to selectrecv: autotmp_[0-9]+$"
Russ Coxaf545662014-02-14 00:38:24 -0500162 return nil
Dmitry Vyukov76477412015-02-19 22:00:11 +0300163 case <-c: // ERROR "live at call to selectrecv: autotmp_[0-9]+$"
Russ Coxaf545662014-02-14 00:38:24 -0500164 return nil
165 }
166}
167
168func f11b() *int {
169 p := new(int)
170 if b {
171 // At this point p is dead: the code here cannot
172 // get to the bottom of the function.
173 // This used to have a spurious "live at call to printint: p".
Russ Cox75d3f622014-11-05 14:42:54 -0500174 printint(1) // nothing live here!
Dmitry Vyukov76477412015-02-19 22:00:11 +0300175 select { // ERROR "live at call to newselect: autotmp_[0-9]+$" "live at call to selectgo: autotmp_[0-9]+$"
176 case <-c: // ERROR "live at call to selectrecv: autotmp_[0-9]+$"
Russ Coxaf545662014-02-14 00:38:24 -0500177 return nil
Dmitry Vyukov76477412015-02-19 22:00:11 +0300178 case <-c: // ERROR "live at call to selectrecv: autotmp_[0-9]+$"
Russ Coxaf545662014-02-14 00:38:24 -0500179 return nil
180 }
181 }
182 println(*p)
183 return nil
184}
185
186func f11c() *int {
187 p := new(int)
188 if b {
189 // Unlike previous, the cases in this select fall through,
190 // so we can get to the println, so p is not dead.
Dmitry Vyukov76477412015-02-19 22:00:11 +0300191 printint(1) // ERROR "live at call to printint: p$"
192 select { // ERROR "live at call to newselect: autotmp_[0-9]+ p$" "live at call to selectgo: autotmp_[0-9]+ p$"
193 case <-c: // ERROR "live at call to selectrecv: autotmp_[0-9]+ p$"
194 case <-c: // ERROR "live at call to selectrecv: autotmp_[0-9]+ p$"
Russ Coxaf545662014-02-14 00:38:24 -0500195 }
196 }
197 println(*p)
198 return nil
199}
200
201// similarly, select{} does not fall through.
202// this used to have a spurious "live at entry to f12: ~r0".
203
204func f12() *int {
205 if b {
Russ Cox1806a572014-08-18 21:13:11 -0400206 select {}
Russ Coxaf545662014-02-14 00:38:24 -0500207 } else {
208 return nil
209 }
210}
Russ Cox7a7c0ff2014-02-15 10:58:55 -0500211
212// incorrectly placed VARDEF annotations can cause missing liveness annotations.
213// this used to be missing the fact that s is live during the call to g13 (because it is
214// needed for the call to h13).
215
216func f13() {
217 s := "hello"
Dmitry Vyukov76477412015-02-19 22:00:11 +0300218 s = h13(s, g13(s)) // ERROR "live at call to g13: s$"
Russ Cox7a7c0ff2014-02-15 10:58:55 -0500219}
220
221func g13(string) string
222func h13(string, string) string
Russ Cox6722d452014-03-27 14:05:57 -0400223
224// more incorrectly placed VARDEF.
225
226func f14() {
227 x := g14()
Dmitry Vyukov76477412015-02-19 22:00:11 +0300228 printstringpointer(&x) // ERROR "live at call to printstringpointer: x$"
Russ Cox6722d452014-03-27 14:05:57 -0400229}
230
231func g14() string
232
233func f15() {
234 var x string
235 _ = &x
Dmitry Vyukov76477412015-02-19 22:00:11 +0300236 x = g15() // ERROR "live at call to g15: x$"
237 printstring(x) // ERROR "live at call to printstring: x$"
Russ Cox6722d452014-03-27 14:05:57 -0400238}
239
240func g15() string
Russ Coxb700cb42014-04-01 13:31:38 -0400241
242// Checking that various temporaries do not persist or cause
243// ambiguously live values that must be zeroed.
244// The exact temporary names are inconsequential but we are
245// trying to check that there is only one at any given site,
246// and also that none show up in "ambiguously live" messages.
247
248var m map[string]int
249
250func f16() {
251 if b {
252 delete(m, "hi") // ERROR "live at call to mapdelete: autotmp_[0-9]+$"
253 }
254 delete(m, "hi") // ERROR "live at call to mapdelete: autotmp_[0-9]+$"
255 delete(m, "hi") // ERROR "live at call to mapdelete: autotmp_[0-9]+$"
256}
257
258var m2s map[string]*byte
259var m2 map[[2]string]*byte
260var x2 [2]string
261var bp *byte
262
263func f17a() {
264 // value temporary only
265 if b {
266 m2[x2] = nil // ERROR "live at call to mapassign1: autotmp_[0-9]+$"
267 }
268 m2[x2] = nil // ERROR "live at call to mapassign1: autotmp_[0-9]+$"
269 m2[x2] = nil // ERROR "live at call to mapassign1: autotmp_[0-9]+$"
270}
271
272func f17b() {
273 // key temporary only
274 if b {
275 m2s["x"] = bp // ERROR "live at call to mapassign1: autotmp_[0-9]+$"
276 }
277 m2s["x"] = bp // ERROR "live at call to mapassign1: autotmp_[0-9]+$"
278 m2s["x"] = bp // ERROR "live at call to mapassign1: autotmp_[0-9]+$"
279}
280
281func f17c() {
282 // key and value temporaries
283 if b {
284 m2s["x"] = nil // ERROR "live at call to mapassign1: autotmp_[0-9]+ autotmp_[0-9]+$"
285 }
286 m2s["x"] = nil // ERROR "live at call to mapassign1: autotmp_[0-9]+ autotmp_[0-9]+$"
287 m2s["x"] = nil // ERROR "live at call to mapassign1: autotmp_[0-9]+ autotmp_[0-9]+$"
288}
289
290func g18() [2]string
291
292func f18() {
293 // key temporary for mapaccess.
294 // temporary introduced by orderexpr.
295 var z *byte
296 if b {
297 z = m2[g18()] // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
298 }
299 z = m2[g18()] // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
300 z = m2[g18()] // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500301 printbytepointer(z)
Russ Coxb700cb42014-04-01 13:31:38 -0400302}
303
304var ch chan *byte
305
306func f19() {
307 // dest temporary for channel receive.
308 var z *byte
Russ Cox1806a572014-08-18 21:13:11 -0400309
Russ Coxb700cb42014-04-01 13:31:38 -0400310 if b {
311 z = <-ch // ERROR "live at call to chanrecv1: autotmp_[0-9]+$"
312 }
313 z = <-ch // ERROR "live at call to chanrecv1: autotmp_[0-9]+$"
314 z = <-ch // ERROR "live at call to chanrecv1: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500315 printbytepointer(z)
Russ Coxb700cb42014-04-01 13:31:38 -0400316}
317
318func f20() {
319 // src temporary for channel send
320 if b {
321 ch <- nil // ERROR "live at call to chansend1: autotmp_[0-9]+$"
322 }
323 ch <- nil // ERROR "live at call to chansend1: autotmp_[0-9]+$"
324 ch <- nil // ERROR "live at call to chansend1: autotmp_[0-9]+$"
325}
326
327func f21() {
328 // key temporary for mapaccess using array literal key.
329 var z *byte
330 if b {
331 z = m2[[2]string{"x", "y"}] // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
332 }
333 z = m2[[2]string{"x", "y"}] // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
334 z = m2[[2]string{"x", "y"}] // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500335 printbytepointer(z)
Russ Coxb700cb42014-04-01 13:31:38 -0400336}
337
338func f23() {
339 // key temporary for two-result map access using array literal key.
340 var z *byte
341 var ok bool
342 if b {
343 z, ok = m2[[2]string{"x", "y"}] // ERROR "live at call to mapaccess2: autotmp_[0-9]+$"
344 }
345 z, ok = m2[[2]string{"x", "y"}] // ERROR "live at call to mapaccess2: autotmp_[0-9]+$"
346 z, ok = m2[[2]string{"x", "y"}] // ERROR "live at call to mapaccess2: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500347 printbytepointer(z)
348 print(ok)
Russ Coxb700cb42014-04-01 13:31:38 -0400349}
350
351func f24() {
352 // key temporary for map access using array literal key.
353 // value temporary too.
354 if b {
355 m2[[2]string{"x", "y"}] = nil // ERROR "live at call to mapassign1: autotmp_[0-9]+ autotmp_[0-9]+$"
356 }
357 m2[[2]string{"x", "y"}] = nil // ERROR "live at call to mapassign1: autotmp_[0-9]+ autotmp_[0-9]+$"
358 m2[[2]string{"x", "y"}] = nil // ERROR "live at call to mapassign1: autotmp_[0-9]+ autotmp_[0-9]+$"
359}
Russ Coxdaca06f2014-04-01 20:02:54 -0400360
361// defer should not cause spurious ambiguously live variables
362
363func f25(b bool) {
364 defer g25()
365 if b {
366 return
367 }
368 var x string
369 _ = &x
Dmitry Vyukov76477412015-02-19 22:00:11 +0300370 x = g15() // ERROR "live at call to g15: x$"
371 printstring(x) // ERROR "live at call to printstring: x$"
372} // ERROR "live at call to deferreturn: x$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400373
374func g25()
Russ Cox1806a572014-08-18 21:13:11 -0400375
Russ Coxdaca06f2014-04-01 20:02:54 -0400376// non-escaping ... slices passed to function call should die on return,
377// so that the temporaries do not stack and do not cause ambiguously
378// live variables.
379
380func f26(b bool) {
381 if b {
Russ Cox1806a572014-08-18 21:13:11 -0400382 print26((*int)(nil), (*int)(nil), (*int)(nil)) // ERROR "live at call to print26: autotmp_[0-9]+$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400383 }
Russ Cox1806a572014-08-18 21:13:11 -0400384 print26((*int)(nil), (*int)(nil), (*int)(nil)) // ERROR "live at call to print26: autotmp_[0-9]+$"
385 print26((*int)(nil), (*int)(nil), (*int)(nil)) // ERROR "live at call to print26: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500386 printnl()
Russ Coxdaca06f2014-04-01 20:02:54 -0400387}
388
389//go:noescape
390func print26(...interface{})
391
392// non-escaping closures passed to function call should die on return
393
394func f27(b bool) {
395 x := 0
396 if b {
Russ Cox1806a572014-08-18 21:13:11 -0400397 call27(func() { x++ }) // ERROR "live at call to call27: autotmp_[0-9]+$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400398 }
Russ Cox1806a572014-08-18 21:13:11 -0400399 call27(func() { x++ }) // ERROR "live at call to call27: autotmp_[0-9]+$"
400 call27(func() { x++ }) // ERROR "live at call to call27: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500401 printnl()
Russ Cox28f18682014-04-03 20:33:25 -0400402}
403
404// but defer does escape to later execution in the function
405
406func f27defer(b bool) {
407 x := 0
408 if b {
Russ Cox1806a572014-08-18 21:13:11 -0400409 defer call27(func() { x++ }) // ERROR "live at call to deferproc: autotmp_[0-9]+$" "live at call to deferreturn: autotmp_[0-9]+$"
Russ Cox28f18682014-04-03 20:33:25 -0400410 }
Dmitry Vyukov76477412015-02-19 22:00:11 +0300411 defer call27(func() { x++ }) // ERROR "f27defer: autotmp_[0-9]+ \(type struct { F uintptr; x \*int }\) is ambiguously live$" "live at call to deferproc: autotmp_[0-9]+ autotmp_[0-9]+$" "live at call to deferreturn: autotmp_[0-9]+ autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500412 printnl() // ERROR "live at call to printnl: autotmp_[0-9]+ autotmp_[0-9]+$"
Russ Cox28f18682014-04-03 20:33:25 -0400413} // ERROR "live at call to deferreturn: autotmp_[0-9]+ autotmp_[0-9]+$"
414
415// and newproc (go) escapes to the heap
416
417func f27go(b bool) {
418 x := 0
419 if b {
Dmitry Vyukov76477412015-02-19 22:00:11 +0300420 go call27(func() { x++ }) // ERROR "live at call to newobject: &x$" "live at call to newproc: &x$"
Russ Cox28f18682014-04-03 20:33:25 -0400421 }
Dmitry Vyukov76477412015-02-19 22:00:11 +0300422 go call27(func() { x++ }) // ERROR "live at call to newobject: &x$"
Russ Cox75d3f622014-11-05 14:42:54 -0500423 printnl()
Russ Coxdaca06f2014-04-01 20:02:54 -0400424}
425
426//go:noescape
427func call27(func())
428
429// concatstring slice should die on return
430
431var s1, s2, s3, s4, s5, s6, s7, s8, s9, s10 string
432
433func f28(b bool) {
434 if b {
Russ Cox75d3f622014-11-05 14:42:54 -0500435 printstring(s1 + s2 + s3 + s4 + s5 + s6 + s7 + s8 + s9 + s10) // ERROR "live at call to concatstrings: autotmp_[0-9]+$" "live at call to printstring: autotmp_[0-9]+$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400436 }
Russ Cox75d3f622014-11-05 14:42:54 -0500437 printstring(s1 + s2 + s3 + s4 + s5 + s6 + s7 + s8 + s9 + s10) // ERROR "live at call to concatstrings: autotmp_[0-9]+$" "live at call to printstring: autotmp_[0-9]+$"
438 printstring(s1 + s2 + s3 + s4 + s5 + s6 + s7 + s8 + s9 + s10) // ERROR "live at call to concatstrings: autotmp_[0-9]+$" "live at call to printstring: autotmp_[0-9]+$"
Russ Cox1806a572014-08-18 21:13:11 -0400439}
Russ Coxdaca06f2014-04-01 20:02:54 -0400440
441// map iterator should die on end of range loop
442
443func f29(b bool) {
444 if b {
445 for k := range m { // ERROR "live at call to mapiterinit: autotmp_[0-9]+$" "live at call to mapiternext: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500446 printstring(k) // ERROR "live at call to printstring: autotmp_[0-9]+$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400447 }
448 }
449 for k := range m { // ERROR "live at call to mapiterinit: autotmp_[0-9]+$" "live at call to mapiternext: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500450 printstring(k) // ERROR "live at call to printstring: autotmp_[0-9]+$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400451 }
452 for k := range m { // ERROR "live at call to mapiterinit: autotmp_[0-9]+$" "live at call to mapiternext: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500453 printstring(k) // ERROR "live at call to printstring: autotmp_[0-9]+$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400454 }
455}
456
457// copy of array of pointers should die at end of range loop
458
459var ptrarr [10]*int
460
461func f30(b bool) {
462 // two live temps during print(p):
463 // the copy of ptrarr and the internal iterator pointer.
464 if b {
465 for _, p := range ptrarr {
Russ Cox75d3f622014-11-05 14:42:54 -0500466 printintpointer(p) // ERROR "live at call to printintpointer: autotmp_[0-9]+ autotmp_[0-9]+$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400467 }
468 }
469 for _, p := range ptrarr {
Russ Cox75d3f622014-11-05 14:42:54 -0500470 printintpointer(p) // ERROR "live at call to printintpointer: autotmp_[0-9]+ autotmp_[0-9]+$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400471 }
472 for _, p := range ptrarr {
Russ Cox75d3f622014-11-05 14:42:54 -0500473 printintpointer(p) // ERROR "live at call to printintpointer: autotmp_[0-9]+ autotmp_[0-9]+$"
Russ Coxdaca06f2014-04-01 20:02:54 -0400474 }
475}
Russ Cox96d90d02014-04-02 14:09:42 -0400476
477// conversion to interface should not leave temporary behind
478
479func f31(b1, b2, b3 bool) {
480 if b1 {
481 g31("a") // ERROR "live at call to convT2E: autotmp_[0-9]+$" "live at call to g31: autotmp_[0-9]+$"
482 }
483 if b2 {
Dmitry Vyukov76477412015-02-19 22:00:11 +0300484 h31("b") // ERROR "live at call to convT2E: autotmp_[0-9]+ autotmp_[0-9]+$" "live at call to h31: autotmp_[0-9]+$" "live at call to newobject: autotmp_[0-9]+$"
Russ Cox96d90d02014-04-02 14:09:42 -0400485 }
486 if b3 {
Keith Randall8217b4a2014-09-05 10:04:16 -0400487 panic("asdf") // ERROR "live at call to convT2E: autotmp_[0-9]+$" "live at call to gopanic: autotmp_[0-9]+$"
Russ Cox96d90d02014-04-02 14:09:42 -0400488 }
489 print(b3)
490}
491
492func g31(interface{})
493func h31(...interface{})
494
495// non-escaping partial functions passed to function call should die on return
496
497type T32 int
498
Dmitry Vyukov76477412015-02-19 22:00:11 +0300499func (t *T32) Inc() { // ERROR "live at entry to \(\*T32\).Inc: t$"
Russ Cox96d90d02014-04-02 14:09:42 -0400500 *t++
501}
502
503var t32 T32
504
505func f32(b bool) {
506 if b {
507 call32(t32.Inc) // ERROR "live at call to call32: autotmp_[0-9]+$"
508 }
509 call32(t32.Inc) // ERROR "live at call to call32: autotmp_[0-9]+$"
510 call32(t32.Inc) // ERROR "live at call to call32: autotmp_[0-9]+$"
511}
512
513//go:noescape
514func call32(func())
515
516// temporaries introduced during if conditions and && || expressions
517// should die once the condition has been acted upon.
518
519var m33 map[interface{}]int
520
521func f33() {
522 if m33[nil] == 0 { // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500523 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400524 return
525 } else {
Russ Cox75d3f622014-11-05 14:42:54 -0500526 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400527 }
Russ Cox75d3f622014-11-05 14:42:54 -0500528 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400529}
530
531func f34() {
532 if m33[nil] == 0 { // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500533 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400534 return
535 }
Russ Cox75d3f622014-11-05 14:42:54 -0500536 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400537}
538
539func f35() {
540 if m33[nil] == 0 && m33[nil] == 0 { // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500541 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400542 return
543 }
Russ Cox75d3f622014-11-05 14:42:54 -0500544 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400545}
546
547func f36() {
548 if m33[nil] == 0 || m33[nil] == 0 { // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500549 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400550 return
551 }
Russ Cox75d3f622014-11-05 14:42:54 -0500552 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400553}
554
555func f37() {
556 if (m33[nil] == 0 || m33[nil] == 0) && m33[nil] == 0 { // ERROR "live at call to mapaccess1: autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500557 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400558 return
559 }
Russ Cox75d3f622014-11-05 14:42:54 -0500560 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400561}
562
563// select temps should disappear in the case bodies
564
565var c38 chan string
566
567func fc38() chan string
568func fi38(int) *string
569func fb38() *bool
570
571func f38(b bool) {
572 // we don't care what temps are printed on the lines with output.
573 // we care that the println lines have no live variables
574 // and therefore no output.
575 if b {
Dmitry Vyukov76477412015-02-19 22:00:11 +0300576 select { // ERROR "live at call to newselect: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$" "live at call to selectgo: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$"
577 case <-fc38(): // ERROR "live at call to selectrecv: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500578 printnl()
Dmitry Vyukov76477412015-02-19 22:00:11 +0300579 case fc38() <- *fi38(1): // ERROR "live at call to fc38: autotmp_[0-9]+$" "live at call to fi38: autotmp_[0-9]+ autotmp_[0-9]+$" "live at call to selectsend: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500580 printnl()
Dmitry Vyukov76477412015-02-19 22:00:11 +0300581 case *fi38(2) = <-fc38(): // ERROR "live at call to fc38: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$" "live at call to fi38: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$" "live at call to selectrecv: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500582 printnl()
Dmitry Vyukov76477412015-02-19 22:00:11 +0300583 case *fi38(3), *fb38() = <-fc38(): // ERROR "live at call to fb38: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$" "live at call to fc38: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$" "live at call to fi38: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$" "live at call to selectrecv2: autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+ autotmp_[0-9]+$"
Russ Cox75d3f622014-11-05 14:42:54 -0500584 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400585 }
Russ Cox75d3f622014-11-05 14:42:54 -0500586 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400587 }
Russ Cox75d3f622014-11-05 14:42:54 -0500588 printnl()
Russ Cox96d90d02014-04-02 14:09:42 -0400589}
Russ Cox89d46fe2014-05-29 13:47:31 -0400590
591// issue 8097: mishandling of x = x during return.
592
593func f39() (x []int) {
594 x = []int{1}
Dmitry Vyukov76477412015-02-19 22:00:11 +0300595 printnl() // ERROR "live at call to printnl: x$"
Russ Cox89d46fe2014-05-29 13:47:31 -0400596 return x
597}
598
599func f39a() (x []int) {
600 x = []int{1}
Dmitry Vyukov76477412015-02-19 22:00:11 +0300601 printnl() // ERROR "live at call to printnl: x$"
Russ Cox89d46fe2014-05-29 13:47:31 -0400602 return
603}
604
605func f39b() (x [10]*int) {
Russ Cox454d1b02014-09-30 12:48:47 -0400606 x = [10]*int{}
Dmitry Vyukov76477412015-02-19 22:00:11 +0300607 x[0] = new(int) // ERROR "live at call to newobject: x$"
608 printnl() // ERROR "live at call to printnl: x$"
Russ Cox89d46fe2014-05-29 13:47:31 -0400609 return x
610}
611
612func f39c() (x [10]*int) {
Russ Cox454d1b02014-09-30 12:48:47 -0400613 x = [10]*int{}
Dmitry Vyukov76477412015-02-19 22:00:11 +0300614 x[0] = new(int) // ERROR "live at call to newobject: x$"
615 printnl() // ERROR "live at call to printnl: x$"
Russ Cox89d46fe2014-05-29 13:47:31 -0400616 return
617}
Russ Coxeb540792014-06-02 21:26:32 -0400618
619// issue 8142: lost 'addrtaken' bit on inlined variables.
620// no inlining in this test, so just checking that non-inlined works.
621
622type T40 struct {
623 m map[int]int
624}
625
626func newT40() *T40 {
Russ Cox454d1b02014-09-30 12:48:47 -0400627 ret := T40{}
Dmitry Vyukov76477412015-02-19 22:00:11 +0300628 ret.m = make(map[int]int) // ERROR "live at call to makemap: &ret$"
Russ Coxeb540792014-06-02 21:26:32 -0400629 return &ret
630}
631
632func bad40() {
633 t := newT40()
Russ Coxeb540792014-06-02 21:26:32 -0400634 _ = t
Russ Cox9ef4e562014-11-14 12:09:42 -0500635 printnl()
Russ Coxeb540792014-06-02 21:26:32 -0400636}
637
638func good40() {
Russ Cox454d1b02014-09-30 12:48:47 -0400639 ret := T40{}
Dmitry Vyukov76477412015-02-19 22:00:11 +0300640 ret.m = make(map[int]int) // ERROR "live at call to makemap: autotmp_[0-9]+ ret$"
Russ Coxeb540792014-06-02 21:26:32 -0400641 t := &ret
Dmitry Vyukov76477412015-02-19 22:00:11 +0300642 printnl() // ERROR "live at call to printnl: autotmp_[0-9]+ ret$"
Russ Coxeb540792014-06-02 21:26:32 -0400643 _ = t
644}