github.com/google/syzkaller@v0.0.0-20251211124644-a066d2bc4b02/pkg/osutil/semaphore.go (about) 1 // Copyright 2025 syzkaller project authors. All rights reserved. 2 // Use of this source code is governed by Apache 2 LICENSE that can be found in the LICENSE file. 3 4 package osutil 5 6 import ( 7 "fmt" 8 ) 9 10 type Semaphore struct { 11 ch chan struct{} 12 } 13 14 func NewSemaphore(count int) *Semaphore { 15 s := &Semaphore{ 16 ch: make(chan struct{}, count), 17 } 18 for i := 0; i < count; i++ { 19 s.Signal() 20 } 21 return s 22 } 23 24 func (s *Semaphore) Wait() { 25 <-s.ch 26 } 27 28 func (s *Semaphore) WaitC() <-chan struct{} { 29 return s.ch 30 } 31 32 func (s *Semaphore) Available() int { 33 return len(s.ch) 34 } 35 36 func (s *Semaphore) Signal() { 37 if av := s.Available(); av == cap(s.ch) { 38 // Not super reliable, but let it be here just in case. 39 panic(fmt.Sprintf("semaphore capacity (%v) is exceeded (%v)", cap(s.ch), av)) 40 } 41 s.ch <- struct{}{} 42 }