Skip to content

Commit

Permalink
Merge pull request #238 from nhooyr/dev
Browse files Browse the repository at this point in the history
Fix deadlock introduced in v1.8.5
  • Loading branch information
nhooyr authored May 10, 2020
2 parents 34417b2 + 03cca81 commit 02861b4
Show file tree
Hide file tree
Showing 2 changed files with 18 additions and 7 deletions.
2 changes: 1 addition & 1 deletion ci/all.sh
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ main() {

./ci/fmt.sh
./ci/lint.sh
./ci/test.sh
./ci/test.sh "$@"
}

main "$@"
23 changes: 17 additions & 6 deletions write.go
Original file line number Diff line number Diff line change
Expand Up @@ -246,13 +246,24 @@ func (c *Conn) writeFrame(ctx context.Context, fin bool, flate bool, opcode opco
if err != nil {
return 0, err
}
defer func() {
// We leave it locked when writing the close frame to avoid
// any other goroutine writing any other frame.
if opcode != opClose {
c.writeFrameMu.unlock()
defer c.writeFrameMu.unlock()

// If the state says a close has already been written, we wait until
// the connection is closed and return that error.
//
// However, if the frame being written is a close, that means its the close from
// the state being set so we let it go through.
c.closeMu.Lock()
wroteClose := c.wroteClose
c.closeMu.Unlock()
if wroteClose && opcode != opClose {
select {
case <-ctx.Done():
return 0, ctx.Err()
case <-c.closed:
return 0, c.closeErr
}
}()
}

select {
case <-c.closed:
Expand Down

0 comments on commit 02861b4

Please sign in to comment.