]> Sergey Matveev's repositories - btrtrc.git/blob - util/levelmu/levelmu.go
TODO
[btrtrc.git] / util / levelmu / levelmu.go
1 package levelmu
2
3 import (
4         "sync"
5 )
6
7 type LevelMutex struct {
8         mus []sync.Mutex
9         // Protected by the very last mutex.
10         lastLevel int
11 }
12
13 func (lm *LevelMutex) Init(levels int) {
14         if lm.mus != nil {
15                 panic("level mutex already initialized")
16         }
17         lm.mus = make([]sync.Mutex, levels)
18 }
19
20 func (lm *LevelMutex) Lock() {
21         lm.LevelLock(0)
22 }
23
24 func (lm *LevelMutex) Unlock() {
25         stopLevel := lm.lastLevel
26         for i := len(lm.mus) - 1; i >= stopLevel; i-- {
27                 lm.mus[i].Unlock()
28         }
29 }
30
31 func (lm *LevelMutex) LevelLock(level int) {
32         if level >= len(lm.mus) {
33                 panic("lock level exceeds configured level count")
34         }
35         for l := level; l < len(lm.mus); l++ {
36                 lm.mus[l].Lock()
37         }
38         lm.lastLevel = level
39 }