diff --git a/internal/proxy/proxy_other.go b/internal/proxy/proxy_other.go index bac097ca4..4839efe1b 100644 --- a/internal/proxy/proxy_other.go +++ b/internal/proxy/proxy_other.go @@ -68,6 +68,7 @@ type fuseMount struct { fuseServerMu *sync.Mutex fuseServer *fuse.Server fuseWg *sync.WaitGroup + fuseExitCh chan error // Inode adds support for FUSE operations. fs.Inode @@ -131,10 +132,19 @@ func (c *Client) Lookup(ctx context.Context, instance string, _ *fuse.EntryOut) defer c.fuseWg.Done() sErr := c.serveSocketMount(ctx, s) if sErr != nil { - c.fuseMu.Lock() c.logger.Debugf("could not serve socket for instance %q: %v", instance, sErr) - delete(c.fuseSockets, instance) - c.fuseMu.Unlock() + c.fuseMu.Lock() + defer c.fuseMu.Unlock() + select { + // Best effort attempt to send error. + // If this send fails, it means the reading goroutine has + // already pulled a value out of the channel and is no longer + // reading any more values. In other words, we report only the + // first error. + case c.fuseExitCh <- err: + default: + return + } } }() @@ -165,10 +175,16 @@ func (c *Client) serveFuse(ctx context.Context, notify func()) error { } c.fuseServerMu.Lock() c.fuseServer = srv + c.fuseExitCh = make(chan error) c.fuseServerMu.Unlock() notify() - <-ctx.Done() - return ctx.Err() + select { + case cErr := <-c.fuseExitCh: + return cErr + case <-ctx.Done(): + return ctx.Err() + } + } func (c *Client) fuseMounts() []*socketMount {