Data Race detected
Thanks for the keyboard package. I am using it in one of my projects, and I recently learnt about go's builtin race detector. I tried using it on my project expecting races in my own code, however it seems I hit a couple of races in keyboard library code. I thought to report this here. I'm not sure if this is serious or not.
Here's the race on keyboard Open
==================
WARNING: DATA RACE
Write at 0x00c42014e000 by goroutine 9:
internal/race.WriteRange()
/usr/local/Cellar/go/1.10.3/libexec/src/internal/race/race.go:49 +0x42
syscall.Read()
/usr/local/Cellar/go/1.10.3/libexec/src/syscall/syscall_unix.go:165 +0x9a
github.com/eiannone/keyboard.initConsole.func1()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard.go:188 +0xc5
Previous read at 0x00c42014e000 by goroutine 10:
runtime.slicecopy()
/usr/local/Cellar/go/1.10.3/libexec/src/runtime/slice.go:192 +0x0
github.com/eiannone/keyboard.inputEventsProducer()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard.go:123 +0x2c4
Goroutine 9 (running) created at:
github.com/eiannone/keyboard.initConsole()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard.go:182 +0x44d
github.com/eiannone/keyboard.Open()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard_common.go:101 +0x4e
main.main()
/Users/someone/go/src/github.com/somehash/someminer/main.go:65 +0x3bc
Goroutine 10 (running) created at:
github.com/eiannone/keyboard.initConsole()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard.go:205 +0x465
github.com/eiannone/keyboard.Open()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard_common.go:101 +0x4e
main.main()
/Users/someone/go/src/github.com/somehash/someminer/main.go:65 +0x3bc
==================
and another one on close()
==================
WARNING: DATA RACE
Read at 0x0000015c74d3 by main goroutine:
github.com/eiannone/keyboard.Close()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard_common.go:113 +0x59
main.main()
/Users/someone/go/src/github.com/somehash/someminer/main.go:187 +0x8fe
Previous write at 0x0000015c74d3 by goroutine 12:
github.com/eiannone/keyboard.GetKey()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard_common.go:124 +0x8e
main.main.func1.1()
/Users/someone/go/src/github.com/somehash/someminer/main.go:83 +0x33
Goroutine 12 (running) created at:
main.main.func1()
/Users/someone/go/src/github.com/somehash/someminer/main.go:80 +0xe7
==================
==================
WARNING: DATA RACE
Write at 0x0000015c74d2 by main goroutine:
github.com/eiannone/keyboard.Close()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard_common.go:117 +0x79
main.main()
/Users/someone/go/src/github.com/somehash/someminer/main.go:187 +0x8fe
Previous read at 0x0000015c74d2 by goroutine 12:
github.com/eiannone/keyboard.GetKey()
/Users/someone/go/src/github.com/eiannone/keyboard/keyboard_common.go:121 +0x6f
main.main.func1.1()
/Users/someone/go/src/github.com/somehash/someminer/main.go:83 +0x33
Goroutine 12 (running) created at:
main.main.func1()
/Users/someone/go/src/github.com/somehash/someminer/main.go:80 +0xe7
==================
Hi @kim0 , than you for your comment. I think to have found the cause of those data races.
For example, regarding the race found in the Open() method, I see that this method runs two threads:
- The first one is started by
initConsole()function and continuously reads from terminal input ('/dev/tty'). When it detects some data from the console, it generates andinput_eventand sends it to theinput_bufchannel. - The second thread runs the
inputEventsProducer()function, which continuously reads frominput_bufchannel and decodes the keyboard events.
The problem lies in the fact that the input_buf elements - of type input_event struct - contain a reference to a shared variable buf, which is concurrently read by both threads and written by one of them.
To solve this issue we should pass a new slice wich is copied from the buffer instead of a reference to it.
It would be very helpful if could provide a sample of your code to reproduce this issue, so that I can be sure that it is solved.
Thank you
With commits 6e7ac5f2b42c16e95f7ef281b0493052d534608c, fdeef67cd149302c448e04bb39ddeef43dc45fca and a10ace96483090f3afe59c54bde218666e924226 I think all the data races should be fixed now.
Encountering what I think is also a race in the Close function (only on Windows). I don't have a Windows machine so it's hard to test (happening in GitHub Actions), but I can see that every once in a while (maybe about 1 in every 20 calls) the tests hang at the keyboard.Close() call. I'll try to do a bit more research but perhaps someone else has encountered this and has some ideas.