This is a creation in Article, where the information may have evolved or changed. The recent whim, in the Golang how to put the closed pipe opened again. This avoids the need to make a new Chan every time, save memory applications and GC time, view go source code, after simple groping, implemented, the sample code is as follows.
func Testunsafe(T *Testing.T) {C1 = Make(Chan struct{}, Ten)C1 <- struct{}{}<-C1Close(C1)P := (*unsafe.Pointer)(unsafe.Pointer(&C1))C := (*Hchan)(*P)C.closed = 0//Open the closed ChanC1 <- struct{}{}<-C1}
func Testsafe(T *Testing.T) {C1 = Make(Chan struct{}, Ten)C1 <- struct{}{}<-C1Close(C1)P := (*unsafe.Pointer)(unsafe.Pointer(&C1))C := (*Hchan)(*P)Atomic.CompareAndSwapUint32(&C.closed, 1, 0) //Open the closed ChanC1 <- struct{}{}<-C1}
The final code is releasedto Github.com/yireyun/go-openc, and interested friends can look at it.
The biggest drawback of this approach is that if the data structure of the Go runtime is changed, it will no longer be feasible. As a result, the code for changing the go kernel data structure detected in the Init method is added, and the performance test results are as follows.
BenchmarkMakeCloseChan-4 20000000 90.9 ns/op---bench:benchmarkmakeclosechan-4 (each new performance at shutdown) go1.7.4, Times: 1, use:0s 0s/opgo1.7.4, times:100, use:0s 0s/opgo1.7.4, times:10000, Use:998.3µs 99ns/opgo1.7.4, times:1000000, Use:91.0664ms 91ns/opgo1.7.4, times:20000000, u se:1.8185449s 90ns/opbenchmarkcloseopenchan-4 50000000 29.5 ns/op---bench:benchmarkcloseopenchan-4 (non-secure Open performance) go1.7.4, times:1, use:0s 0s/opgo1.7.4, times:100, use:0s 0 s/opgo1.7.4, times:10000, use:0s 0s/opgo1.7.4, times:1000000, Use:28.5199ms 28ns/ opgo1.7.4, times:50000000, use:1.473497s 29ns/opbenchmarkcloseopenchansync-4 30000000 44.9 ns/op---BENCH : BenchmarkCloseOpenChanSync-4 (Safe open performance) go1.7.4, times:1, use:0s 0s/opgo1.7.4, times:1 XX, use:0s 0s/opgo1.7.4, times:10000, Use:498.2µs 49ns/opgo1.7.4, times:1000000, use:47.5278ms 47ns/opgo1.7.4, times:30000000, use:1.3479236s 44ns/oppassok github.com/yireyun/go-openc8.235s