...

Source file src/golang.conradwood.net/go-easyops/utils/timeout_lock.go

Documentation: golang.conradwood.net/go-easyops/utils

     1  package utils
     2  
     3  import (
     4  	"fmt"
     5  	"time"
     6  )
     7  
     8  type TimeoutLock interface {
     9  	Unlock()
    10  	Lock()
    11  	LockWithTimeout(time.Duration) bool // true if lock was acquired
    12  }
    13  
    14  type timeoutlock struct {
    15  	ch       chan bool
    16  	name     string
    17  	lockedat string
    18  }
    19  
    20  // create a new lock which can be used like sync.Mutex but also adds LockWithTimeout()
    21  func NewTimeoutLock(name string) TimeoutLock {
    22  	tl := &timeoutlock{
    23  		name: name,
    24  		ch:   make(chan bool, 1),
    25  	}
    26  	return tl
    27  }
    28  
    29  // lock - waits indefinitely for a lock to become available
    30  func (tl *timeoutlock) Lock() {
    31  	tl.ch <- true
    32  	tl.lockedat = GetStack("lock %s", tl.name)
    33  }
    34  
    35  // lock, return true if it was able to acquire lock within duration t. false if it was not
    36  func (tl *timeoutlock) LockWithTimeout(t time.Duration) bool {
    37  	select {
    38  	case tl.ch <- true:
    39  		tl.lockedat = GetStack("lock %s", tl.name)
    40  		return true
    41  	case <-time.After(t):
    42  		PrintStack("[go-easyops] lock \"%s\" timeout", tl.name)
    43  		fmt.Printf("lock \"%s\" was locked at: %s\n", tl.name, tl.lockedat)
    44  		return false
    45  	}
    46  
    47  }
    48  
    49  // unlock this lock
    50  func (tl *timeoutlock) Unlock() {
    51  	select {
    52  	case <-tl.ch:
    53  		//
    54  	default:
    55  		// nothing to unlock
    56  		fmt.Printf("[go-easyops] timeoutlock \"%s\" unlocked but was not locked previously\n", tl.name)
    57  		PrintStack("[go-easyops]")
    58  	}
    59  }
    60  

View as plain text