more async improvements and crypto bugfix

This commit is contained in:
ston1th 2022-08-17 23:58:46 +02:00
commit 304135be2e
7 changed files with 161 additions and 79 deletions

View file

@ -36,7 +36,7 @@ func (q *queue) Add(ph *PreloadHandler, name string, prio int) {
func (q *queue) Remove(name string) {
for i, p := range *q {
if p.Name == name {
p.stop()
p.stop(true)
*q = slices.Delete(*q, i, i+1)
q.Sort()
return
@ -56,12 +56,15 @@ type Preload struct {
type Preloads []Preload
type PreloadHandler struct {
mu sync.RWMutex
log logr.Logger
fs *FS
q queue
fin chan string
max int
mu sync.RWMutex
log logr.Logger
fs *FS
q queue
fin chan string
err chan string
stop chan struct{}
done chan struct{}
max int
}
func NewPreloadHandler(ctx context.Context, fs *FS, max int, log logr.Logger) (ph *PreloadHandler) {
@ -69,13 +72,16 @@ func NewPreloadHandler(ctx context.Context, fs *FS, max int, log logr.Logger) (p
max = 1
}
ph = &PreloadHandler{
log: log,
fs: fs,
q: make(queue, 0),
fin: make(chan string, 1),
max: max,
log: log,
fs: fs,
q: make(queue, 0),
fin: make(chan string, 1),
err: make(chan string, 1),
stop: make(chan struct{}, 1),
done: make(chan struct{}),
max: max,
}
go ph.preloadFinish(ctx)
go ph.preloadStatus(ctx)
return
}
@ -109,7 +115,7 @@ func (ph *PreloadHandler) schedule() {
if i < ph.max {
ph.q[i].start()
} else {
ph.q[i].stop()
ph.q[i].stop(true)
}
}
}
@ -131,19 +137,30 @@ func (p *Preload) start() {
ctx, cancel := context.WithCancel(context.Background())
p.Running = true
p.cancel = cancel
go f.Preload(ctx, func() {
p.ph.fin <- name
})
go f.Preload(ctx,
func() {
p.ph.fin <- name
},
func() {
p.ph.err <- name
},
func() {
p.ph.stop <- struct{}{}
},
)
}
func (p *Preload) stop() {
func (p *Preload) stop(collect bool) {
if p.Running {
p.cancel()
p.Running = false
p.cancel()
if collect {
<-p.ph.stop
}
}
}
func (ph *PreloadHandler) preloadFinish(ctx context.Context) {
func (ph *PreloadHandler) preloadStatus(ctx context.Context) {
for {
select {
case <-ctx.Done():
@ -154,19 +171,32 @@ func (ph *PreloadHandler) preloadFinish(ctx context.Context) {
ph.q.Remove(name)
ph.schedule()
ph.mu.Unlock()
case name := <-ph.err:
ph.mu.Lock()
ph.q.Add(ph, name, -1)
ph.schedule()
ph.mu.Unlock()
}
}
}
func (ph *PreloadHandler) close() {
ph.mu.Lock()
defer ph.mu.Unlock()
n := len(ph.q)
for _, p := range ph.q {
p.stop()
p.stop(false)
}
for {
for i := 0; i < n; i++ {
select {
case <-ph.fin:
default:
return
case <-ph.err:
case <-ph.stop:
}
}
close(ph.done)
}
func (ph *PreloadHandler) Done() <-chan struct{} {
return ph.done
}