Skip to content

Commit 68f9eac

Browse files
committed
fix(broadcast): avoid bound method callbacks
Signed-off-by: Christian Stewart <christian@aperture.us>
1 parent e53dc9e commit 68f9eac

1 file changed

Lines changed: 18 additions & 12 deletions

File tree

broadcast/broadcast.go

Lines changed: 18 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ type Broadcast struct {
2121
func (c *Broadcast) HoldLock(cb func(broadcast func(), getWaitCh func() <-chan struct{})) {
2222
c.mtx.Lock()
2323
defer c.mtx.Unlock()
24-
cb(c.broadcastLocked, c.getWaitChLocked)
24+
cb(c.broadcastLockedFunc(), c.getWaitChLockedFunc())
2525
}
2626

2727
// TryHoldLock attempts to lock the mutex and call the callback.
@@ -31,7 +31,7 @@ func (c *Broadcast) TryHoldLock(cb func(broadcast func(), getWaitCh func() <-cha
3131
return false
3232
}
3333
defer c.mtx.Unlock()
34-
cb(c.broadcastLocked, c.getWaitChLocked)
34+
cb(c.broadcastLockedFunc(), c.getWaitChLockedFunc())
3535
return true
3636
}
3737

@@ -44,7 +44,7 @@ func (c *Broadcast) HoldLockMaybeAsync(cb func(broadcast func(), getWaitCh func(
4444
}
4545
// use defer to catch panic cases
4646
defer c.mtx.Unlock()
47-
cb(c.broadcastLocked, c.getWaitChLocked)
47+
cb(c.broadcastLockedFunc(), c.getWaitChLockedFunc())
4848
}
4949

5050
// fast path: lock immediately
@@ -93,18 +93,24 @@ func (c *Broadcast) Wait(ctx context.Context, cb func(broadcast func(), getWaitC
9393
}
9494
}
9595

96-
// broadcastLocked is the implementation of Broadcast while mtx is locked.
97-
func (c *Broadcast) broadcastLocked() {
98-
if c.ch != nil {
99-
close(c.ch)
96+
// broadcastLockedFunc returns the implementation of Broadcast while mtx is locked.
97+
func (c *Broadcast) broadcastLockedFunc() func() {
98+
return func() {
99+
if c.ch == nil {
100+
return
101+
}
102+
ch := c.ch
100103
c.ch = nil
104+
close(ch)
101105
}
102106
}
103107

104-
// getWaitChLocked is the implementation of GetWaitCh while mtx is locked.
105-
func (c *Broadcast) getWaitChLocked() <-chan struct{} {
106-
if c.ch == nil {
107-
c.ch = make(chan struct{})
108+
// getWaitChLockedFunc returns the implementation of GetWaitCh while mtx is locked.
109+
func (c *Broadcast) getWaitChLockedFunc() func() <-chan struct{} {
110+
return func() <-chan struct{} {
111+
if c.ch == nil {
112+
c.ch = make(chan struct{})
113+
}
114+
return c.ch
108115
}
109-
return c.ch
110116
}

0 commit comments

Comments
 (0)