12#include "stk_config.h"
109 if (slock !=
nullptr)
111 slock->~stk_spinlock_t();
147 if (membuf_size >=
sizeof(
stk_cv_t))
197 uint32_t membuf_size,
261 :
handle(static_cast<uint16_t>(initial_count),
262 static_cast<uint16_t>(max_count))
269 uint32_t membuf_size,
270 uint32_t initial_count,
281 result =
new (membuf->
data)
stk_sem_t(initial_count, effective_max);
335 uint32_t membuf_size,
336 uint32_t initial_flags)
342 if (membuf_size >=
sizeof(
stk_ef_t))
383 return ef->
handle.
Wait(flags, options, timeout);
400 stk_pipe_t(uint8_t *buf,
size_t capacity,
size_t element_size)
401 :
handle(buf, capacity, element_size)
406 uint32_t membuf_size,
417 STK_ASSERT(buf_size >= capacity * element_size);
420 if ((membuf_size >=
sizeof(
stk_pipe_t)) && (buf_size >= (capacity * element_size)))
422 result =
new (membuf->
data)
stk_pipe_t(buf, capacity, element_size);
576 :
handle(buf, capacity, msg_size)
583 uint32_t membuf_size,
597 if ((membuf_size >=
sizeof(
stk_msgq_t)) && (buf_size >= (capacity * msg_size)))
599 result =
new (membuf)
stk_msgq_t(buf, capacity, msg_size);
782 rw->~stk_rwmutex_t();
Collection of memory-related primitives (stk::memory namespace).
Top-level STK include. Provides the Kernel class template and all built-in task-switching strategies.
#define STK_ASSERT(e)
Runtime assertion. Halts execution if the expression e evaluates to false.
Collection of synchronization primitives (stk::sync namespace).
C language binding/interface for SuperTinyKernel RTOS.
stk_rwmutex_t * stk_rwmutex_create(stk_rwmutex_mem_t *const membuf, uint32_t membuf_size)
Create an RWMutex (using provided memory).
void stk_sem_signal(stk_sem_t *sem)
Signal/Release a semaphore resource.
size_t stk_pipe_get_capacity(const stk_pipe_t *pipe)
Get the maximum number of elements the pipe can hold.
void stk_msgq_reset(stk_msgq_t *mq)
Discard all messages and reset the queue to the empty state.
bool stk_msgq_is_full(const stk_msgq_t *mq)
Check whether the queue is currently full.
uint32_t stk_ef_set(stk_ef_t *ef, uint32_t flags)
Set one or more flags.
bool stk_event_set(stk_event_t *ev)
Set the event to signaled state.
struct stk_cv_t stk_cv_t
Opaque handle to a Condition Variable instance.
uint32_t stk_ef_clear(stk_ef_t *ef, uint32_t flags)
Clear one or more flags.
void stk_mutex_destroy(stk_mutex_t *mtx)
Destroy a Mutex.
size_t stk_pipe_get_count(const stk_pipe_t *pipe)
Get the current number of elements in the pipe.
bool stk_pipe_write(stk_pipe_t *pipe, const void *data, stk_timeout_t timeout)
Write a single element to the pipe.
size_t stk_pipe_read_bulk(stk_pipe_t *pipe, void *dst, size_t count, stk_timeout_t timeout)
Read multiple elements from the pipe.
size_t stk_pipe_trywrite_bulk(stk_pipe_t *pipe, const void *src, size_t count)
Attempt to write multiple elements to the pipe without blocking.
bool stk_rwmutex_try_read_lock(stk_rwmutex_t *rw)
Try to acquire the read lock without blocking.
size_t stk_pipe_get_space(const stk_pipe_t *pipe)
Get the number of free slots currently available.
stk_sem_t * stk_sem_create(stk_sem_mem_t *const membuf, uint32_t membuf_size, uint32_t initial_count, uint32_t max_count)
Create a Semaphore (using provided memory).
uint32_t stk_ef_wait(stk_ef_t *ef, uint32_t flags, uint32_t options, stk_timeout_t timeout)
Wait for one or more flags to be set.
void stk_ef_destroy(stk_ef_t *ef)
Destroy an EventFlags object.
bool stk_event_wait(stk_event_t *ev, stk_timeout_t timeout)
Wait for the event to become signaled.
bool stk_rwmutex_trylock(stk_rwmutex_t *rw)
Try to acquire the write lock without blocking.
bool stk_cv_wait(stk_cv_t *cv, stk_mutex_t *mtx, stk_timeout_t timeout)
Wait for a signal on the condition variable.
struct stk_ef_t stk_ef_t
Opaque handle to an EventFlags instance.
uint32_t stk_ef_trywait(stk_ef_t *ef, uint32_t flags, uint32_t options)
Non-blocking flag poll.
void stk_spinlock_destroy(stk_spinlock_t *slock)
Destroy the SpinLock.
void stk_cv_notify_one(stk_cv_t *cv)
Wake one task waiting on the condition variable.
bool stk_spinlock_trylock(stk_spinlock_t *slock)
Attempt to acquire the SpinLock immediately.
stk_msgq_t * stk_msgq_create(stk_msgq_mem_t *const membuf, uint32_t membuf_size, uint8_t *buf, uint32_t buf_size, size_t capacity, size_t msg_size)
Create a MessageQueue (using provided memory).
bool stk_msgq_tryget(stk_msgq_t *mq, void *msg)
Attempt to get a message from the queue without blocking.
bool stk_event_trywait(stk_event_t *ev)
Wait for the event to become signaled.
size_t stk_msgq_get_space(const stk_msgq_t *mq)
Get the number of free slots currently available.
void stk_event_destroy(stk_event_t *ev)
Destroy an Event.
bool stk_pipe_is_storage_valid(const stk_pipe_t *pipe)
Verify that the backing storage is valid and the pipe is ready for use.
uint16_t stk_sem_get_count(const stk_sem_t *sem)
Get the current counter value.
stk_event_t * stk_event_create(stk_event_mem_t *const membuf, uint32_t membuf_size, bool manual_reset)
Create an Event (using provided memory).
bool stk_msgq_trypeekfront(stk_msgq_t *mq, void *msg)
Attempt to peek at the front message without blocking.
bool stk_mutex_timed_lock(stk_mutex_t *mtx, stk_timeout_t timeout)
Try to lock the mutex with a timeout.
bool stk_msgq_peekfront(stk_msgq_t *mq, void *msg, stk_timeout_t timeout)
Peek at the most recently front-inserted message without removing it.
struct stk_mutex_t stk_mutex_t
Opaque handle to a Mutex instance.
void stk_mutex_lock(stk_mutex_t *mtx)
Lock the mutex. Blocks until available.
size_t stk_pipe_write_bulk(stk_pipe_t *pipe, const void *src, size_t count, stk_timeout_t timeout)
Write multiple elements to the pipe.
void stk_rwmutex_lock(stk_rwmutex_t *rw)
Acquire the lock for exclusive writing. Blocks until available.
stk_ef_t * stk_ef_create(stk_ef_mem_t *const membuf, uint32_t membuf_size, uint32_t initial_flags)
Create an EventFlags object (using provided memory).
void stk_cv_destroy(stk_cv_t *cv)
Destroy a Condition Variable.
struct stk_event_t stk_event_t
Opaque handle to an Event instance.
bool stk_msgq_is_empty(const stk_msgq_t *mq)
Check whether the queue is currently empty.
bool stk_mutex_trylock(stk_mutex_t *mtx)
Try locking the mutex. Does not block if already locked.
void stk_rwmutex_read_lock(stk_rwmutex_t *rw)
Acquire the lock for shared reading. Blocks until available.
struct stk_sem_t stk_sem_t
Opaque handle to a Semaphore instance.
size_t stk_msgq_get_capacity(const stk_msgq_t *mq)
Get the maximum number of messages the queue can hold.
void stk_mutex_unlock(stk_mutex_t *mtx)
Unlock the mutex.
void stk_pipe_destroy(stk_pipe_t *pipe)
Destroy a Pipe.
size_t stk_pipe_get_element_size(const stk_pipe_t *pipe)
Get the size of each element in bytes.
bool stk_sem_wait(stk_sem_t *sem, stk_timeout_t timeout)
Wait for a semaphore resource.
bool stk_msgq_putfront(stk_msgq_t *mq, const void *msg, stk_timeout_t timeout)
Put a message into the front of the queue (priority insert).
size_t stk_msgq_get_count(const stk_msgq_t *mq)
Get the current number of messages waiting in the queue.
uint8_t * stk_msgq_get_buffer(stk_msgq_t *mq)
Get a pointer to the raw message data buffer.
void stk_spinlock_lock(stk_spinlock_t *slock)
Acquire the SpinLock (recursive).
bool stk_msgq_put(stk_msgq_t *mq, const void *msg, stk_timeout_t timeout)
Put a message into the queue.
bool stk_msgq_tryput(stk_msgq_t *mq, const void *msg)
Attempt to put a message into the queue without blocking.
struct stk_spinlock_t stk_spinlock_t
Opaque handle to a SpinLock instance.
struct stk_msgq_t stk_msgq_t
Opaque handle to a MessageQueue instance.
void stk_pipe_reset(stk_pipe_t *pipe)
Discard all elements and reset the pipe to the empty state.
struct stk_pipe_t stk_pipe_t
Opaque handle to a Pipe instance.
void stk_sem_destroy(stk_sem_t *sem)
Destroy a Semaphore.
void stk_spinlock_unlock(stk_spinlock_t *slock)
Release the SpinLock.
size_t stk_pipe_tryread_bulk_triggered(stk_pipe_t *pipe, void *dst, size_t max_count)
Non-blocking variant of stk_pipe_read_bulk_triggered.
bool stk_sem_trywait(stk_sem_t *sem)
Poll the semaphore without blocking.
stk_pipe_t * stk_pipe_create(stk_pipe_mem_t *const membuf, uint32_t membuf_size, uint8_t *buf, uint32_t buf_size, size_t capacity, size_t element_size)
Create a Pipe (using provided memory).
void stk_rwmutex_read_unlock(stk_rwmutex_t *rw)
Release the shared reader lock.
size_t stk_msgq_get_msg_size(const stk_msgq_t *mq)
Get the size of each message in bytes.
stk_spinlock_t * stk_spinlock_create(stk_spinlock_mem_t *const membuf, uint32_t membuf_size)
Create a recursive SpinLock.
bool stk_pipe_tryread(stk_pipe_t *pipe, void *data)
Attempt to read a single element from the pipe without blocking.
uint32_t stk_ef_get(stk_ef_t *ef)
Read the current flags word without modifying it.
struct stk_rwmutex_t stk_rwmutex_t
Opaque handle to an RWMutex instance.
size_t stk_pipe_read_bulk_triggered(stk_pipe_t *pipe, void *dst, size_t trigger, size_t max_count, stk_timeout_t timeout)
Read at least trigger elements, then drain up to max_count without blocking.
bool stk_msgq_get(stk_msgq_t *mq, void *msg, stk_timeout_t timeout)
Get a message from the queue.
void stk_event_pulse(stk_event_t *ev)
Pulse the event (signal then immediately reset).
bool stk_msgq_tryputfront(stk_msgq_t *mq, const void *msg)
Attempt to put a message into the front of the queue without blocking.
bool stk_pipe_is_full(const stk_pipe_t *pipe)
Check whether the pipe is currently full.
bool stk_pipe_is_empty(const stk_pipe_t *pipe)
Check whether the pipe is currently empty.
bool stk_pipe_read(stk_pipe_t *pipe, void *data, stk_timeout_t timeout)
Read a single element from the pipe.
stk_cv_t * stk_cv_create(stk_cv_mem_t *const membuf, uint32_t membuf_size)
Create a Condition Variable (using provided memory).
stk_mutex_t * stk_mutex_create(stk_mutex_mem_t *const membuf, uint32_t membuf_size)
Create a Mutex (using provided memory).
bool stk_event_reset(stk_event_t *ev)
Reset the event to non-signaled state.
bool stk_msgq_is_storage_valid(const stk_msgq_t *mq)
Verify that the backing storage is valid and the queue is ready for use.
bool stk_rwmutex_timed_lock(stk_rwmutex_t *rw, stk_timeout_t timeout)
Try to acquire the write lock with a timeout.
void stk_rwmutex_destroy(stk_rwmutex_t *rw)
Destroy an RWMutex.
void stk_msgq_destroy(stk_msgq_t *mq)
Destroy a MessageQueue.
bool stk_rwmutex_timed_read_lock(stk_rwmutex_t *rw, stk_timeout_t timeout)
Try to acquire the read lock with a timeout.
int32_t stk_timeout_t
Timeout value.
bool stk_msgq_peek(stk_msgq_t *mq, void *msg, stk_timeout_t timeout)
Peek at the next message to be delivered without removing it.
bool stk_msgq_trypeek(stk_msgq_t *mq, void *msg)
Attempt to peek at the next message without blocking.
void stk_cv_notify_all(stk_cv_t *cv)
Wake all tasks waiting on the condition variable.
bool stk_pipe_trywrite(stk_pipe_t *pipe, const void *data)
Attempt to write a single element to the pipe without blocking.
void stk_rwmutex_unlock(stk_rwmutex_t *rw)
Release the exclusive writer lock.
size_t stk_pipe_tryread_bulk(stk_pipe_t *pipe, void *dst, size_t count)
Attempt to read multiple elements from the pipe without blocking.
Namespace of STK package.
Synchronization primitives for task coordination and resource protection.
Condition Variable primitive for signaling between tasks based on specific predicates.
void NotifyOne()
Wake one waiting task.
bool Wait(IMutex &mutex, Timeout timeout_ticks=WAIT_INFINITE)
Wait for a signal.
void NotifyAll()
Wake all waiting tasks.
Binary synchronization event (signaled / non-signaled) primitive.
bool Set()
Set event to signaled state.
void Pulse()
Pulse event: attempt to release waiters and then reset (Win32 PulseEvent() semantics).
bool TryWait()
Poll event state without blocking.
bool Reset()
Reset event to non-signaled state.
bool Wait(Timeout timeout_ticks=WAIT_INFINITE)
Wait until event becomes signaled or the timeout expires.
32-bit event flags group for multi-flag synchronization between tasks.
uint32_t Wait(uint32_t flags, uint32_t options=OPT_WAIT_ANY, Timeout timeout_ticks=WAIT_INFINITE)
Wait for one or more flags to be set.
uint32_t Get() const
Read the current flags word without modifying it.
uint32_t TryWait(uint32_t flags, uint32_t options=OPT_WAIT_ANY)
Non-blocking flag poll.
uint32_t Clear(uint32_t flags)
Clear one or more flags.
uint32_t Set(uint32_t flags)
Set one or more flags.
Fixed-capacity, fixed-message-size FIFO queue for inter-task communication.
bool TryPeek(void *msg_ptr)
Attempt to peek at the next message without blocking.
bool TryPeekFront(void *msg_ptr)
Attempt to peek at the front message without blocking.
bool IsEmpty() const
Check whether the queue is currently empty.
bool PeekFront(void *msg_ptr, Timeout timeout_ticks=WAIT_INFINITE)
Peek at the most recently front-inserted message (front of the FIFO) without removing it.
size_t GetCapacity() const
Get the maximum number of messages the queue can hold.
bool TryPutFront(const void *msg_ptr)
Attempt to put a message into the front of the queue without blocking.
size_t GetMsgSize() const
Get the size of each message in bytes.
bool TryPut(const void *msg_ptr)
Attempt to put a message into the back of the queue without blocking.
size_t GetSpace() const
Get the number of free slots currently available.
size_t GetCount() const
Get the current number of messages in the queue.
bool TryGet(void *msg_ptr)
Attempt to get a message from the queue without blocking.
uint8_t * GetBuffer()
Get pointer to the message buffer.
bool Peek(void *msg_ptr, Timeout timeout_ticks=WAIT_INFINITE)
Peek at the next message to be delivered (back of the FIFO) without removing it.
bool PutFront(const void *msg_ptr, Timeout timeout_ticks=WAIT_INFINITE)
Put a message into the front of the queue (LIFO / priority-insert order).
bool IsStorageValid() const
Verify that the backing storage is valid and the pool is ready for use.
bool Put(const void *msg_ptr, Timeout timeout_ticks=WAIT_INFINITE)
Put a message into the back of the queue (FIFO order).
bool Get(void *msg_ptr, Timeout timeout_ticks=WAIT_INFINITE)
Get a message from the queue.
bool IsFull() const
Check whether the queue is currently full.
void Reset()
Discard all messages and reset the queue to the empty state.
Recursive mutex primitive that allows the same thread to acquire the lock multiple times.
bool TimedLock(Timeout timeout_ticks)
Acquire lock.
bool TryLock()
Acquire the lock.
void Unlock() override
Release lock.
void Lock() override
Acquire lock.
Thread-safe FIFO communication pipe for inter-task data passing.
size_t WriteBulk(const void *src, size_t count, Timeout timeout_ticks=WAIT_INFINITE)
Write multiple elements to the pipe.
bool TryRead(void *data)
Attempt to read a single element from the pipe without blocking.
size_t TryReadBulkTriggered(void *dst, size_t max_count)
Non-blocking variant of ReadBulkTriggered.
void Reset()
Discard all elements and reset the pipe to the empty state.
bool Read(void *data, Timeout timeout_ticks=WAIT_INFINITE)
Read a single element from the pipe.
size_t ReadBulk(void *dst, size_t count, Timeout timeout_ticks=WAIT_INFINITE)
Read multiple elements from the pipe.
bool Write(const void *data, Timeout timeout_ticks=WAIT_INFINITE)
Write a single element to the pipe.
size_t GetElementSize() const
Get the size of each element in bytes.
size_t TryWriteBulk(const void *src, size_t count)
Attempt to write multiple elements to the pipe without blocking.
bool IsEmpty() const
Check if the pipe is currently empty.
size_t GetCapacity() const
Get the maximum number of elements the pipe can hold.
bool TryWrite(const void *data)
Attempt to write a single element to the pipe without blocking.
size_t GetCount() const
Get the current number of elements in the pipe.
bool IsFull() const
Check if the pipe is currently full.
size_t TryReadBulk(void *dst, size_t count)
Attempt to read multiple elements from the pipe without blocking.
size_t GetSpace() const
Get the number of free slots currently available.
size_t ReadBulkTriggered(void *dst, size_t trigger, size_t max_count, Timeout timeout_ticks=WAIT_INFINITE)
Read at least trigger elements, then drain up to max_count without blocking.
bool IsStorageValid() const
Verify that the backing storage is valid and the pipe is ready for use.
Reader-Writer Lock synchronization primitive for non-recursive shared and exclusive access.
bool TryLock()
Attempt to acquire the lock for exclusive writing without blocking.
bool TimedLock(Timeout timeout_ticks)
Acquire the lock for exclusive writing with a timeout.
void Unlock() override
Release the exclusive writer lock (IMutex interface).
void Lock() override
Acquire the lock for exclusive writing (IMutex interface).
bool TimedReadLock(Timeout timeout_ticks)
Acquire the lock for shared reading with a timeout.
void ReadUnlock()
Release the shared reader lock.
void ReadLock()
Acquire the lock for shared reading.
bool TryReadLock()
Attempt to acquire the lock for shared reading without blocking.
Counting semaphore primitive for resource management and signaling.
void Signal()
Post a signal (increment counter).
uint16_t GetCount() const
Get current counter value.
static const uint16_t COUNT_MAX
Max count value supported.
bool Wait(Timeout timeout_ticks=WAIT_INFINITE)
Wait for a signal (decrement counter).
bool TryWait()
Poll the semaphore without blocking (decrement counter if available).
void Unlock()
Release the lock or decrement the recursion counter.
bool TryLock()
Attempt to acquire the lock without blocking.
void Lock()
Acquire the lock.
Opaque memory container for a Mutex instance.
stk_word_t data[(10U+((0) ? 1U :0U))]
Opaque memory container for SpinLock object.
Opaque memory container for a ConditionVariable instance.
stk_word_t data[(7U+((0) ? 1U :0U))]
Opaque memory container for an Event instance.
stk_word_t data[(8U+((0) ? 1U :0U))]
Opaque memory container for a Semaphore instance.
stk_word_t data[(8U+((0) ? 1U :0U))]
Opaque memory container for an EventFlags instance.
stk_word_t data[((7U+((0) ? 1U :0U))+1U+((0) ? 1U :0U))]
Opaque memory container for a Pipe control-block.
stk_word_t data[(6U+(2U *(7U+((0) ? 1U :0U)))+((0) ? 1U :0U))]
Opaque memory container for a MessageQueue instance.
Opaque memory container for an RWMutex instance.
stk_word_t data[(17U+((0) ? 3U :0U))]
stk_event_t(bool manual_reset)
stk_sem_t(uint32_t initial_count, uint32_t max_count)
stk_ef_t(uint32_t initial_flags)
stk_pipe_t(uint8_t *buf, size_t capacity, size_t element_size)
stk_msgq_t(uint8_t *buf, size_t capacity, size_t msg_size)