diff --git a/CHANGELOG.md b/CHANGELOG.md index 598ea496..3b7a815a 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -78,6 +78,7 @@ Ref: https://keepachangelog.com/en/1.0.0/ * (evm) [tharsis#871](https://github.com/tharsis/ethermint/pull/871) Set correct nonce in `EthCall` and `EstimateGas` grpc query. * (rpc) [tharsis#878](https://github.com/tharsis/ethermint/pull/878) Workaround to make GetBlock RPC api report correct block gas used. * (rpc) [tharsis#900](https://github.com/tharsis/ethermint/pull/900) newPendingTransactions filter return ethereum tx hash. +* (rpc) [tharsis#933](https://github.com/tharsis/ethermint/pull/933) Fix newPendingTransactions subscription deadlock when a Websocket client exits without unsubscribing and the node errors. ## [v0.9.0] - 2021-12-01 diff --git a/rpc/websockets.go b/rpc/websockets.go index 86629e34..76b5c489 100644 --- a/rpc/websockets.go +++ b/rpc/websockets.go @@ -712,8 +712,16 @@ func (api *pubSubAPI) subscribePendingTransactions(wsConn *wsConn) (rpc.ID, erro api.logger.Debug("error writing header, will drop peer", "error", err.Error()) try(func() { + // Release the initial read lock in .RUnlock() before + // invoking .Lock() to avoid the deadlock in + // https://github.com/tharsis/ethermint/issues/821#issuecomment-1033959984 + // and as documented at https://pkg.go.dev/sync#RWMutex + api.filtersMu.RUnlock() api.filtersMu.Lock() - defer api.filtersMu.Unlock() + defer func() { + api.filtersMu.Unlock() + api.filtersMu.RLock() + }() if err != websocket.ErrCloseSent { _ = wsSub.wsConn.Close()