Try compiling your code with -gcflags -d=ssa/insert_resched_checks/on . You should see the scheduler thrashing stop, at the expense of some loop overhead. (The simpler the loop, the worse the overhead, that is why this phase is not normally enabled. We're working on the overhead issues, they've not been easy so far.)
On Tuesday, June 20, 2017 at 11:40:12 PM UTC-4, Ronald wrote: > > Hi, I found when running this code below (play > <https://play.golang.org/p/XyxV_1f6Ri>): > > > package main > import "fmt" > import "runtime" > import "time" > type callRet struct { > ret int > } > type callIn struct { > ret_chan chan *callRet > arg1 int > } > func caller(call_in_c chan *callIn, arg1 int) int { > ret_c := make(chan *callRet, 1) > ci := callIn{ret_c, arg1} > t1 := time.Now().UnixNano() > call_in_c <- &ci > ret := <-ret_c > t2 := time.Now().UnixNano() > _, _ = t1, t2 > //fmt.Println(t2, t1, float64(t2-t1)/1e6) > return ret.ret > } > func call_srv(call_in_c chan *callIn) { > //runtime.LockOSThread() > ct := 0 > for { > select { > case in := <-call_in_c: > ret_c := in.ret_chan > ret := callRet{3 + in.arg1} > ret_c <- &ret > ct++ > if ct%1000 == 0 { > fmt.Println(ct) > } > //default: > // time.Sleep(1 * time.Millisecond) > } > } > //runtime.UnlockOSThread() > } > func init() { > //runtime.LockOSThread() > } > func main() { > p := fmt.Println > runtime.GOMAXPROCS(5) > call_in_c := make(chan *callIn, 2000) > fp := func(call_in_c chan *callIn) { > ct := 0 > for ; ct < 2000000; ct = ct + 1 { > caller(call_in_c, 1) > time.Sleep(100 * time.Nanosecond) > } > p("done:)") > } > go fp(call_in_c) > go fp(call_in_c) > go func() { > for { > fmt.Println("heartbeat...") > time.Sleep(10 * 1000 * time.Microsecond) > } > }() > > // after delete this little piece code, it will be ok > > go func() { > for { > } > }() > > // -^ > > call_srv(call_in_c) > return > } > > It will always “stuck” in certain time after start executing (tested in > both go 1.7 , 1.8.1 and 1.8.3, > and you should run it on your own computer, not on the play because it > would cost several seconds). > I have checked the code above dozens of times at least and sure it is all > right. > > I tried to attach the go process with gdb when it is stuck and the `bt` > yielded this: > > >> (gdb) info goroutines >> 1 waiting runtime.gopark >> 2 waiting runtime.gopark >> 3 waiting runtime.gopark >> 4 waiting runtime.gopark >> 5 waiting runtime.gopark >> * 6 running runtime.systemstack_switch >> 7 waiting runtime.gopark >> * 8 running main.main.func3 >> 17 runnable runtime.exitsyscall >> 33 waiting runtime.gopark >> 18 waiting runtime.gopark >> 49 waiting runtime.gopark >> 50 waiting runtime.gopark >> 51 waiting runtime.gopark >> (gdb) goroutine 6 bt >> #0 runtime.systemstack_switch () at >> /usr/local/go/src/runtime/asm_amd64.s:281 >> #1 0x0000000000415088 in runtime.gcStart (mode=0, forceTrigger=false) >> at /usr/local/go/src/runtime/mgc.go:1010 >> #2 0x000000000040d841 in runtime.mallocgc (size=96, typ=0x4a7fa0, >> needzero=true, >> ~r3=0x507998 <runtime.timers+24>) at >> /usr/local/go/src/runtime/malloc.go:785 >> #3 0x000000000040df68 in runtime.newobject (typ=0x4a7fa0, ~r1=0x0) >> at /usr/local/go/src/runtime/malloc.go:820 >> #4 0x00000000004035d2 in runtime.makechan (t=0x492960, size=1, >> ~r2=0xc4200016c0) >> at /usr/local/go/src/runtime/chan.go:92 >> #5 0x00000000004840e4 in main.caller (call_in_c=0xc420056060, arg1=1, >> ~r2=0) >> at /root/go/src/chan/x.go:18 >> #6 0x00000000004846ac in main.main.func1 (call_in_c=0xc420056060) at >> /root/go/src/chan/x.go:62 >> #7 0x000000000044da21 in runtime.goexit () at >> /usr/local/go/src/runtime/asm_amd64.s:2197 >> #8 0x000000c420056060 in ?? () >> #9 0x0000000000000000 in ?? () > > > > -- You received this message because you are subscribed to the Google Groups "golang-nuts" group. To unsubscribe from this group and stop receiving emails from it, send an email to golang-nuts+unsubscr...@googlegroups.com. For more options, visit https://groups.google.com/d/optout.