aboutsummaryrefslogtreecommitdiff
path: root/weed/cluster/lock_client.go
diff options
context:
space:
mode:
Diffstat (limited to 'weed/cluster/lock_client.go')
-rw-r--r--weed/cluster/lock_client.go15
1 files changed, 15 insertions, 0 deletions
diff --git a/weed/cluster/lock_client.go b/weed/cluster/lock_client.go
index 9b8ed7556..63d93ed54 100644
--- a/weed/cluster/lock_client.go
+++ b/weed/cluster/lock_client.go
@@ -72,6 +72,14 @@ func (lc *LockClient) StartLongLivedLock(key string, owner string, onLockOwnerCh
isLocked := false
lockOwner := ""
for {
+ // Check for cancellation BEFORE attempting to lock to avoid race condition
+ // where Stop() is called after sleep but before lock attempt
+ select {
+ case <-lock.cancelCh:
+ return
+ default:
+ }
+
if isLocked {
if err := lock.AttemptToLock(lock_manager.LiveLockTTL); err != nil {
glog.V(0).Infof("Lost lock %s: %v", key, err)
@@ -156,7 +164,14 @@ func (lock *LiveLock) Stop() error {
close(lock.cancelCh)
}
+ // Wait a brief moment for the goroutine to see the closed channel
+ // This reduces the race condition window where the goroutine might
+ // attempt one more lock operation after we've released the lock
+ time.Sleep(10 * time.Millisecond)
+
// Also release the lock if held
+ // Note: We intentionally don't clear renewToken here because
+ // StopShortLivedLock needs it to properly unlock
return lock.StopShortLivedLock()
}