github.com/loov/combiner@v0.1.0/extcombiner/mutex.go (about)

     1  package extcombiner
     2  
     3  import (
     4  	"runtime"
     5  	"sync"
     6  	"sync/atomic"
     7  )
     8  
     9  // Mutex is a combiner queue that uses mutex to serialize operations.
    10  //
    11  // Not recommended, only for comparison.
    12  type Mutex struct {
    13  	mu      sync.Mutex
    14  	batcher Batcher
    15  }
    16  
    17  // NewMutex creates a combiner queue based on a mutex.
    18  func NewMutex(batcher Batcher) *Mutex {
    19  	c := &Mutex{}
    20  	c.batcher = batcher
    21  	return c
    22  }
    23  
    24  // Do passes value to Batcher and waits for completion
    25  func (c *Mutex) Do(v interface{}) {
    26  	c.mu.Lock()
    27  	c.batcher.Start()
    28  	c.batcher.Do(v)
    29  	c.batcher.Finish()
    30  	c.mu.Unlock()
    31  }
    32  
    33  // SpinMutex is a combiner queue that uses a spinning mutex to serialize operations.
    34  //
    35  // Not recommended, only for comparison.
    36  type SpinMutex struct {
    37  	mu      spinmutex
    38  	batcher Batcher
    39  }
    40  
    41  // NewSpinMutex creates a combiner queue based on a spin mutex.
    42  func NewSpinMutex(batcher Batcher) *SpinMutex {
    43  	c := &SpinMutex{}
    44  	c.batcher = batcher
    45  	return c
    46  }
    47  
    48  // Do passes value to Batcher and waits for completion
    49  func (c *SpinMutex) Do(v interface{}) {
    50  	c.mu.Lock()
    51  	c.batcher.Start()
    52  	c.batcher.Do(v)
    53  	c.batcher.Finish()
    54  	c.mu.Unlock()
    55  }
    56  
    57  type spinmutex struct {
    58  	locked int64
    59  	_      [7]int64
    60  }
    61  
    62  func (m *spinmutex) Lock() {
    63  	for atomic.SwapInt64(&m.locked, 1) == 1 {
    64  		for try := 0; atomic.LoadInt64(&m.locked) == 1; try++ {
    65  			if try > 256 {
    66  				runtime.Gosched()
    67  			}
    68  		}
    69  	}
    70  }
    71  
    72  func (m *spinmutex) Unlock() {
    73  	atomic.StoreInt64(&m.locked, 0)
    74  }