/// © MiroZ 2024

#ifndef __MUTEX_H__
#define __MUTEX_H__

#include <freertos/FreeRTOS.h>
#include <freertos/semphr.h>
#include <freertos/queue.h>
#include <assert.h>
#include <stdint.h>

class Mutex
{
protected:
	SemaphoreHandle_t m_mutex = nullptr;

public:
	Mutex(){ assert(m_mutex = xSemaphoreCreateMutex()); }
	Mutex(SemaphoreHandle_t handle) { m_mutex = handle; }
	
	bool take(uint32_t ticks = portMAX_DELAY) { return xSemaphoreTake(m_mutex, ticks); }
	bool give() { return xSemaphoreGive(m_mutex); }
};

template <typename T>
class Queue
{
protected:
	QueueHandle_t m_queue = nullptr;

public:
	Queue(uint32_t len) { m_queue = xQueueCreate(len, sizeof(T)); }
	Queue(QueueHandle_t handle, uint32_t len) { m_queue = handle; }

	void send(T * data, uint32_t ticks = portMAX_DELAY) { xQueueSend(m_queue, data, ticks); }
	bool receive(T * data, uint32_t ticks = portMAX_DELAY) { return xQueueReceive(m_queue, data, ticks); }
};

class CountingSemaphore
{
protected:
	SemaphoreHandle_t m_semaphore = nullptr;

public:
	CountingSemaphore(uint32_t max, uint32_t initial){ assert(m_semaphore = xSemaphoreCreateCounting(max, initial)); }
	bool take(uint32_t ticks = portMAX_DELAY) { return xSemaphoreTake(m_semaphore, ticks); }
	bool give() { return xSemaphoreGive(m_semaphore); }	
};



#endif