-
Notifications
You must be signed in to change notification settings - Fork 65
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conn.Close()
doesn't unblock pending Read
operations
#13
Comments
(The advantage for waiting for Go 1.11 is that deadlines will work out of the box too.) |
I implemented the Go 1.11+ option in a3be7e1, and it works beautifully. |
Very interesting. So if I understand correctly we will get timeouts and everything for free with Go 1.11 too? That's been one of my biggest gripes with nonstandard socket types for years. Once 1.11 lands I have no qualms making changes and requiring 1.11 to build this package. In the mean time, it'd probably be good to do the workaround you suggested for 1.10 and below. |
Thanks again for the report. We hit this issue in production and I made a comparable patch to solve the issue. Closing this issue now as it appears to be fixed. |
This is a pretty big and unexpected departure from the
net.Conn
contract, which explicitly states:The reason it happens is that in current versions of Go,
os.NewFile()
assumes that the provided file descriptor points to a file and doesn't support polling. As a consequence, it uses straight syscalls to handleRead
andWrite
, and it is a well known weirdness of Linux thatclose()
doesn't unblockrecv*()
from other threads. From theclose(2)
manpage:From there, there are two options:
Close()
to callshutdown()
, which will unblock the blockedrecv()
;os.File
objects fromos.NewFile()
. For that, all you have to do is to set the file descriptor to non-blocking mode before passing it toos.NewFile()
The text was updated successfully, but these errors were encountered: