fix memleak in safe.Pool

Co-authored-by: Julien Salleyron <julien.salleyron@gmail.com>
This commit is contained in:
mpl 2020-01-20 17:42:05 +01:00 committed by Traefiker Bot
parent f84d947115
commit 24192a3797
3 changed files with 8 additions and 109 deletions

View file

@ -19,14 +19,13 @@ type routineCtx func(ctx context.Context)
// Pool is a pool of go routines
type Pool struct {
routines []routine
routinesCtx []routineCtx
waitGroup sync.WaitGroup
lock sync.Mutex
baseCtx context.Context
baseCancel context.CancelFunc
ctx context.Context
cancel context.CancelFunc
routines []routine
waitGroup sync.WaitGroup
lock sync.Mutex
baseCtx context.Context
baseCancel context.CancelFunc
ctx context.Context
cancel context.CancelFunc
}
// NewPool creates a Pool
@ -46,17 +45,9 @@ func (p *Pool) Ctx() context.Context {
return p.baseCtx
}
// AddGoCtx adds a recoverable goroutine with a context without starting it
func (p *Pool) AddGoCtx(goroutine routineCtx) {
p.lock.Lock()
p.routinesCtx = append(p.routinesCtx, goroutine)
p.lock.Unlock()
}
// GoCtx starts a recoverable goroutine with a context
func (p *Pool) GoCtx(goroutine routineCtx) {
p.lock.Lock()
p.routinesCtx = append(p.routinesCtx, goroutine)
p.waitGroup.Add(1)
Go(func() {
defer p.waitGroup.Done()
@ -65,17 +56,6 @@ func (p *Pool) GoCtx(goroutine routineCtx) {
p.lock.Unlock()
}
// addGo adds a recoverable goroutine, and can be stopped with stop chan
func (p *Pool) addGo(goroutine func(stop chan bool)) {
p.lock.Lock()
newRoutine := routine{
goroutine: goroutine,
stop: make(chan bool, 1),
}
p.routines = append(p.routines, newRoutine)
p.lock.Unlock()
}
// Go starts a recoverable goroutine, and can be stopped with stop chan
func (p *Pool) Go(goroutine func(stop chan bool)) {
p.lock.Lock()
@ -114,29 +94,6 @@ func (p *Pool) Cleanup() {
p.baseCancel()
}
// Start starts all stopped routines
func (p *Pool) Start() {
p.lock.Lock()
defer p.lock.Unlock()
p.ctx, p.cancel = context.WithCancel(p.baseCtx)
for i := range p.routines {
p.waitGroup.Add(1)
p.routines[i].stop = make(chan bool, 1)
Go(func() {
defer p.waitGroup.Done()
p.routines[i].goroutine(p.routines[i].stop)
})
}
for _, routine := range p.routinesCtx {
p.waitGroup.Add(1)
Go(func() {
defer p.waitGroup.Done()
routine(p.ctx)
})
}
}
// Go starts a recoverable goroutine
func Go(goroutine func()) {
GoWithRecover(goroutine, defaultRecoverGoroutine)