Documentation ¶
Index ¶
Constants ¶
This section is empty.
Variables ¶
var ErrRequestExceedsCapacity = errors.New("request exceeds semaphore capacity")
Functions ¶
This section is empty.
Types ¶
type Queue ¶
type Queue[T any] struct { // contains filtered or unexported fields }
Queue implements an allocation efficient FIFO queue. It is not safe for concurrent access.
Note that the queue provides pointer access to the internal storage (via PeekFront and PushBack) so it must be used with care. These pointers must not be used once the respective element is popped out of the queue.
-- Implementation --
The queue is implemented as a linked list of nodes, where each node is a small ring buffer. The nodes are allocated using a sync.Pool (a single pool is created for any given type and is used for all queues of that type).
func MakeQueue ¶
func MakeQueue[T any](pool *QueueBackingPool[T]) Queue[T]
MakeQueue constructs a new Queue.
The pool should be a singleton object initialized with MakeQueueBackingPool. A single pool can and should be used by all queues of that type.
func (*Queue[T]) PeekFront ¶
func (q *Queue[T]) PeekFront() *T
PeekFront returns the current head of the queue, or nil if the queue is empty.
The result is only valid until the next call to PopFront.
type QueueBackingPool ¶
type QueueBackingPool[T any] struct { // contains filtered or unexported fields }
QueueBackingPool is a sync.Pool that used to allocate internal nodes for Queue[T].
func MakeQueueBackingPool ¶
func MakeQueueBackingPool[T any]() QueueBackingPool[T]
MakeQueueBackingPool makes a queue backing pool. It is intented to be used to initialize a singleton (global) variable. A single pool can and should be used by all queues of that type.
type Semaphore ¶
type Semaphore struct {
// contains filtered or unexported fields
}
Semaphore implements a weighted, dynamically reconfigurable semaphore which respects context cancellation.
The semaphore implements a FIFO policy, where Acquire requests are satisfied in order. This policy provides fairness and prevents starvation but is susceptible to head-of-line blocking, where a large request that can't be satisfied blocks many other small requests that could be.
func NewSemaphore ¶
NewSemaphore creates a new semaphore with the given capacity.
func (*Semaphore) Acquire ¶
Acquire n units from the semaphore, waiting if necessary.
If the context is canceled while we are waiting, returns the context error. If n exceeds the current capacity, returns ErrRequestExceedsCapacity. On success, the caller must later Release the units.
func (*Semaphore) Release ¶
Release n units back. These must be units that were acquired by a previous Acquire call. It is legal to split up or coalesce units when releasing.
func (*Semaphore) Stats ¶
func (s *Semaphore) Stats() SemaphoreStats
Stats returns the current state of the semaphore.
func (*Semaphore) TryAcquire ¶
TryAcquire attempts to acquire n units from the semaphore without waiting. On success, returns true and the caller must later Release the units.
func (*Semaphore) UpdateCapacity ¶
UpdateCapacity changes the capacity of the semaphore. If the new capacity is smaller, the already outstanding acquisitions might exceed the new capacity until they are released.
If there are Acquire calls that are waiting which are requesting more than the new capacity, they will error out with ErrRequestExceedsCapacity.
type SemaphoreStats ¶
type SemaphoreStats struct { // Capacity is the current capacity of the semaphore. Capacity int64 // Outstanding is the number of units that have been acquired. Note that this // can exceed Capacity if the capacity was recently decreased. Outstanding int64 // NumHadToWait is the total number of Acquire calls (since the semaphore was // created) that had to wait because the semaphore was exhausted. Useful for // cumulative metrics. NumHadToWait int64 }
SemaphoreStats contains information about the current state of the semaphore.
func (SemaphoreStats) String ¶
func (ss SemaphoreStats) String() string