1
0
mirror of https://github.com/golang/go synced 2024-11-18 22:44:48 -07:00
go/pointer/testdata/channels.go
Alan Donovan de47ebac4b go.tools/ssa: fix bad type info in 'for _ = range channel'.
Previously, if the result was not wanted, the received
(value, ok) tuple had no type for 'value'.
Now it is always set to the channel's element type.

Also: set the position on such receive instructions to that of
the = or := token, and document it.

+ (indirect) test via pointer analysis.

R=crawshaw, gri
CC=golang-dev
https://golang.org/cl/12956052
2013-08-27 11:18:31 -04:00

99 lines
2.1 KiB
Go

// +build ignore
package main
func incr(x int) int { return x + 1 }
func decr(x int) int { return x - 1 }
var unknown bool // defeat dead-code elimination
func chan1() {
chA := make(chan func(int) int, 0) // @line c1makeA
chB := make(chan func(int) int, 0) // @line c1makeB
chA <- incr
chB <- decr
chB <- func(int) int { return 1 }
print(chA) // @pointsto makechan@c1makeA:13
print(<-chA) // @pointsto main.incr
print(chB) // @pointsto makechan@c1makeB:13
print(<-chB) // @pointsto main.decr | func@16.9
}
func chan2() {
chA := make(chan func(int) int, 0) // @line c2makeA
chB := make(chan func(int) int, 0) // @line c2makeB
chA <- incr
chB <- decr
chB <- func(int) int { return 1 }
// Channels flow together.
// Labelsets remain distinct but elements are merged.
chAB := chA
if unknown {
chAB = chB
}
print(chA) // @pointsto makechan@c2makeA:13
print(<-chA) // @pointsto main.incr
print(chB) // @pointsto makechan@c2makeB:13
print(<-chB) // @pointsto main.decr | func@30.9
print(chAB) // @pointsto makechan@c2makeA:13 | makechan@c2makeB:13
print(<-chAB) // @pointsto main.incr | main.decr | func@30.9
(<-chA)(3)
}
// @calls main.chan2 -> main.incr
func chan3() {
chA := make(chan func(int) int, 0) // @line c3makeA
chB := make(chan func(int) int, 0) // @line c3makeB
chA <- incr
chB <- decr
chB <- func(int) int { return 1 }
print(chA) // @pointsto makechan@c3makeA:13
print(<-chA) // @pointsto main.incr
print(chB) // @pointsto makechan@c3makeB:13
print(<-chB) // @pointsto main.decr | func@58.9
(<-chA)(3)
}
// @calls main.chan3 -> main.incr
func chan4() {
chA := make(chan func(int) int, 0) // @line c4makeA
chB := make(chan func(int) int, 0) // @line c4makeB
select {
case chA <- incr:
case chB <- decr:
case a := <-chA:
print(a) // @pointsto main.incr
case b := <-chB:
print(b) // @pointsto main.decr
default:
print(chA) // @pointsto makechan@c4makeA:13
print(chB) // @pointsto makechan@c4makeB:13
}
for k := range chA {
print(k) // @pointsto main.incr
}
// Exercise constraint generation (regtest for a crash).
for _ = range chA {
}
}
func main() {
chan1()
chan2()
chan3()
chan4()
}