From 2865c9cb8dc9960fdf6fb5e9f1dfee2fda866000 Mon Sep 17 00:00:00 2001 From: j2rong4cn Date: Sat, 2 Aug 2025 16:42:59 +0800 Subject: [PATCH] fix(fs): deadlock when get link error --- internal/op/fs.go | 1 - pkg/singleflight/singleflight.go | 3 ++- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/internal/op/fs.go b/internal/op/fs.go index 0be7f19e5..1637da6cd 100644 --- a/internal/op/fs.go +++ b/internal/op/fs.go @@ -295,7 +295,6 @@ func Link(ctx context.Context, storage driver.Driver, path string, args model.Li fn := func() (*model.Link, error) { link, err := storage.Link(ctx, file, args) if err != nil { - linkG.Forget(key) return nil, errors.Wrapf(err, "failed get link") } if link.Expiration != nil { diff --git a/pkg/singleflight/singleflight.go b/pkg/singleflight/singleflight.go index c686beb1a..3555d5bd0 100644 --- a/pkg/singleflight/singleflight.go +++ b/pkg/singleflight/singleflight.go @@ -74,6 +74,7 @@ type Group[T any] struct { mu sync.Mutex // protects m m map[string]*call[T] // lazily initialized + // Won't remember error Remember bool } @@ -158,7 +159,7 @@ func (g *Group[T]) doCall(c *call[T], key string, fn func() (T, error)) { g.mu.Lock() defer g.mu.Unlock() c.wg.Done() - if !g.Remember && g.m[key] == c { + if (!g.Remember || c.err != nil) && g.m[key] == c { delete(g.m, key) }