OpenCores
URL https://opencores.org/ocsvn/openrisc/openrisc/trunk

Subversion Repositories openrisc

[/] [openrisc/] [trunk/] [gnu-dev/] [or1k-gcc/] [gcc/] [testsuite/] [go.test/] [test/] [chan/] [doubleselect.go] - Blame information for rev 700

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 700 jeremybenn
// $G $D/$F.go && $L $F.$A && ./$A.out
2
 
3
// Copyright 2009 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
 
7
// This test is designed to flush out the case where two cases of a select can
8
// both end up running. See http://codereview.appspot.com/180068.
9
package main
10
 
11
import (
12
        "flag"
13
        "runtime"
14
)
15
 
16
var iterations *int = flag.Int("n", 100000, "number of iterations")
17
 
18
// sender sends a counter to one of four different channels. If two
19
// cases both end up running in the same iteration, the same value will be sent
20
// to two different channels.
21
func sender(n int, c1, c2, c3, c4 chan<- int) {
22
        defer close(c1)
23
        defer close(c2)
24
        defer close(c3)
25
        defer close(c4)
26
 
27
        for i := 0; i < n; i++ {
28
                select {
29
                case c1 <- i:
30
                case c2 <- i:
31
                case c3 <- i:
32
                case c4 <- i:
33
                }
34
        }
35
}
36
 
37
// mux receives the values from sender and forwards them onto another channel.
38
// It would be simplier to just have sender's four cases all be the same
39
// channel, but this doesn't actually trigger the bug.
40
func mux(out chan<- int, in <-chan int, done chan<- bool) {
41
        for v := range in {
42
                out <- v
43
        }
44
        done <- true
45
}
46
 
47
// recver gets a steam of values from the four mux's and checks for duplicates.
48
func recver(in <-chan int) {
49
        seen := make(map[int]bool)
50
 
51
        for v := range in {
52
                if _, ok := seen[v]; ok {
53
                        println("got duplicate value: ", v)
54
                        panic("fail")
55
                }
56
                seen[v] = true
57
        }
58
}
59
 
60
func main() {
61
        runtime.GOMAXPROCS(2)
62
 
63
        c1 := make(chan int)
64
        c2 := make(chan int)
65
        c3 := make(chan int)
66
        c4 := make(chan int)
67
        done := make(chan bool)
68
        cmux := make(chan int)
69
        go sender(*iterations, c1, c2, c3, c4)
70
        go mux(cmux, c1, done)
71
        go mux(cmux, c2, done)
72
        go mux(cmux, c3, done)
73
        go mux(cmux, c4, done)
74
        go func() {
75
                <-done
76
                <-done
77
                <-done
78
                <-done
79
                close(cmux)
80
        }()
81
        // We keep the recver because it might catch more bugs in the future.
82
        // However, the result of the bug linked to at the top is that we'll
83
        // end up panicking with: "throw: bad g->status in ready".
84
        recver(cmux)
85
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.