Skip to content

Commit

Permalink
Merge pull request #1812 from statechannels/listeners-lock
Browse files Browse the repository at this point in the history
Add concurrency control to all listeners methods
  • Loading branch information
geoknee committed Oct 9, 2023
2 parents 8b177b1 + 6030044 commit e311e2e
Showing 1 changed file with 16 additions and 6 deletions.
22 changes: 16 additions & 6 deletions node/notifier/listeners.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ type paymentChannelListeners struct {
listeners []chan query.PaymentChannelInfo
// prev is the previous payment channel info that was sent to the listeners.
prev query.PaymentChannelInfo
// listenersLock is used to protect against concurrent access to the listeners slice.
// listenersLock is used to protect against concurrent access to to sibling struct members.
listenersLock *sync.Mutex
}

Expand All @@ -24,6 +24,8 @@ func newPaymentChannelListeners() *paymentChannelListeners {
// Notify notifies all listeners of a payment channel update.
// It only notifies listeners if the new info is different from the previous info.
func (li *paymentChannelListeners) Notify(info query.PaymentChannelInfo) {
li.listenersLock.Lock()
defer li.listenersLock.Unlock()
if li.prev.Equal(info) {
return
}
Expand All @@ -45,10 +47,13 @@ func (li *paymentChannelListeners) createNewListener() <-chan query.PaymentChann

// getOrCreateListener returns the first listener, creating one if none exist.
func (li *paymentChannelListeners) getOrCreateListener() <-chan query.PaymentChannelInfo {
li.listenersLock.Lock()
if len(li.listeners) != 0 {
return li.listeners[0]
l := li.listeners[0]
li.listenersLock.Unlock()
return l
}

li.listenersLock.Unlock()
return li.createNewListener()
}

Expand All @@ -69,7 +74,7 @@ type ledgerChannelListeners struct {
listeners []chan query.LedgerChannelInfo
// prev is the previous ledger channel info that was sent to the listeners.
prev query.LedgerChannelInfo
// listenersLock is used to protect against concurrent access to the listeners slice.
// listenersLock is used to protect against concurrent access to sibling struct members.
listenersLock sync.Mutex
}

Expand All @@ -81,6 +86,8 @@ func newLedgerChannelListeners() *ledgerChannelListeners {
// Notify notifies all listeners of a ledger channel update.
// It only notifies listeners if the new info is different from the previous info.
func (li *ledgerChannelListeners) Notify(info query.LedgerChannelInfo) {
li.listenersLock.Lock()
defer li.listenersLock.Unlock()
if li.prev.Equal(info) {
return
}
Expand All @@ -103,10 +110,13 @@ func (li *ledgerChannelListeners) createNewListener() <-chan query.LedgerChannel

// getOrCreateListener returns the first listener, creating one if none exist.
func (li *ledgerChannelListeners) getOrCreateListener() <-chan query.LedgerChannelInfo {
li.listenersLock.Lock()
if len(li.listeners) != 0 {
return li.listeners[0]
l := li.listeners[0]
li.listenersLock.Unlock()
return l
}

li.listenersLock.Unlock()
return li.createNewListener()
}

Expand Down

0 comments on commit e311e2e

Please sign in to comment.