Closed lzhfromustc closed 4 years ago
cc @kardianos
I don't think this is a problem. A connection pool with a million connections, or even a million active goroutines seems unlikely. If someone actually hits this in practice, or is even able to hit this issue in a contrived test case with a real database, let me know.
What version of Go are you using (
go version
)?I believe this issue exists since go1.10 to the latest master branch
Does this issue reproduce with the latest release?
Yes
What operating system and processor architecture are you using (
go env
)?I believe this issue is not relevant to OS or processor.
go env
OutputWhat did you see?
In /src/database/sql/sql.go,
db.openerCh
is used in the following way:When the buffer is full,
db.openerCh <- struct{}{}
can be blocked. In the annotation above, it is believed that this send will be unblocked when "the connectionOpener can satisfy the backlog of requests". However,connectionOpener
(a.k.a. Goroutine 2) can also be blocked trying to acquiredb.mu.Lock()
, which is held by Goroutine 1. So a circular wait presents.I suppose this problem is not noticed because the buffer size is big and hard to be full. However, as the annotation says, send can still be blocking. I am not a security guy, but maybe DOS attack can force this happen? I found an issue mentioning related code, but it seems that they are not talking about circular wait: #10886
To fix this problem, I have written a patch, which can make these goroutines unblockable no matter what happens, but it is quite ugly... Do you think this is a problem? If so, shall I open a PR?