semaphore cleanup (#6)

This commit is contained in:
Ken Van Hoeylandt 2024-01-05 20:56:44 +01:00 committed by GitHub
parent 73ed5a5ebe
commit b0ffa04d78
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 19 additions and 59 deletions

View File

@ -13,7 +13,6 @@ LIST_DEF(FuriPubSubSubscriptionList, FuriPubSubSubscription, M_POD_OPLIST);
struct FuriPubSub { struct FuriPubSub {
FuriPubSubSubscriptionList_t items; FuriPubSubSubscriptionList_t items;
// TODO: replace recursive mutex with semaphore
FuriMutex* mutex; FuriMutex* mutex;
}; };

View File

@ -24,8 +24,7 @@ FuriSemaphore* furi_semaphore_alloc(uint32_t max_count, uint32_t initial_count)
furi_check(hSemaphore); furi_check(hSemaphore);
/* Return semaphore ID */ return (FuriSemaphore*)hSemaphore;
return ((FuriSemaphore*)hSemaphore);
} }
void furi_semaphore_free(FuriSemaphore* instance) { void furi_semaphore_free(FuriSemaphore* instance) {
@ -41,19 +40,19 @@ FuriStatus furi_semaphore_acquire(FuriSemaphore* instance, uint32_t timeout) {
furi_assert(instance); furi_assert(instance);
SemaphoreHandle_t hSemaphore = (SemaphoreHandle_t)instance; SemaphoreHandle_t hSemaphore = (SemaphoreHandle_t)instance;
FuriStatus stat; FuriStatus status;
BaseType_t yield; BaseType_t yield;
stat = FuriStatusOk; status = FuriStatusOk;
if (FURI_IS_IRQ_MODE()) { if (FURI_IS_IRQ_MODE()) {
if (timeout != 0U) { if (timeout != 0U) {
stat = FuriStatusErrorParameter; status = FuriStatusErrorParameter;
} else { } else {
yield = pdFALSE; yield = pdFALSE;
if (xSemaphoreTakeFromISR(hSemaphore, &yield) != pdPASS) { if (xSemaphoreTakeFromISR(hSemaphore, &yield) != pdPASS) {
stat = FuriStatusErrorResource; status = FuriStatusErrorResource;
} else { } else {
portYIELD_FROM_ISR(yield); portYIELD_FROM_ISR(yield);
} }
@ -61,15 +60,14 @@ FuriStatus furi_semaphore_acquire(FuriSemaphore* instance, uint32_t timeout) {
} else { } else {
if (xSemaphoreTake(hSemaphore, (TickType_t)timeout) != pdPASS) { if (xSemaphoreTake(hSemaphore, (TickType_t)timeout) != pdPASS) {
if (timeout != 0U) { if (timeout != 0U) {
stat = FuriStatusErrorTimeout; status = FuriStatusErrorTimeout;
} else { } else {
stat = FuriStatusErrorResource; status = FuriStatusErrorResource;
} }
} }
} }
/* Return execution status */ return status;
return (stat);
} }
FuriStatus furi_semaphore_release(FuriSemaphore* instance) { FuriStatus furi_semaphore_release(FuriSemaphore* instance) {
@ -105,9 +103,13 @@ uint32_t furi_semaphore_get_count(FuriSemaphore* instance) {
SemaphoreHandle_t hSemaphore = (SemaphoreHandle_t)instance; SemaphoreHandle_t hSemaphore = (SemaphoreHandle_t)instance;
uint32_t count; uint32_t count;
if(FURI_IS_IRQ_MODE()) { if (FURI_IS_IRQ_MODE()) {
furi_crash("not implemented"); // TODO: uxSemaphoreGetCountFromISR is not supported on esp-idf 5.1.2 - perhaps later on?
// count = (uint32_t)uxSemaphoreGetCountFromISR(hSemaphore); #ifdef uxSemaphoreGetCountFromISR
count = (uint32_t)uxSemaphoreGetCountFromISR(hSemaphore);
#else
count = (uint32_t)uxQueueMessagesWaitingFromISR((QueueHandle_t)hSemaphore);
#endif
} else { } else {
count = (uint32_t)uxSemaphoreGetCount(hSemaphore); count = (uint32_t)uxSemaphoreGetCount(hSemaphore);
} }
@ -115,25 +117,3 @@ uint32_t furi_semaphore_get_count(FuriSemaphore* instance) {
/* Return number of tokens */ /* Return number of tokens */
return (count); return (count);
} }
bool furi_semaphore_take(FuriSemaphore* instance, TickType_t timeout) {
furi_assert(instance);
SemaphoreHandle_t hSemaphore = (SemaphoreHandle_t)instance;
if(FURI_IS_IRQ_MODE()) {
furi_crash("not implemented");
} else {
return xSemaphoreTake(hSemaphore, timeout) == pdTRUE;
}
}
bool furi_semaphore_give(FuriSemaphore* instance) {
furi_assert(instance);
SemaphoreHandle_t hSemaphore = (SemaphoreHandle_t)instance;
if(FURI_IS_IRQ_MODE()) {
furi_crash("not implemented");
} else {
return xSemaphoreGive(hSemaphore);
}
}

View File

@ -49,23 +49,6 @@ FuriStatus furi_semaphore_release(FuriSemaphore* instance);
*/ */
uint32_t furi_semaphore_get_count(FuriSemaphore* instance); uint32_t furi_semaphore_get_count(FuriSemaphore* instance);
/** Wait for the semaphore to become available
*
* @param instance The pointer to FuriSemaphore instance
* @param timeout The maximum amount of ticks to wait for the semaphore to become available
*
* @return True if the semaphore became available. False on timeout.
*/
bool furi_semaphore_take(FuriSemaphore* instance, TickType_t timeout);
/** Wait for the semaphore to become available
*
* @param instance The pointer to FuriSemaphore instance
*
* @return True if the semaphore became available. False on timeout.
*/
bool furi_semaphore_give(FuriSemaphore* instance);
#ifdef __cplusplus #ifdef __cplusplus
} }
#endif #endif

View File

@ -25,7 +25,7 @@ Gui* gui_alloc() {
NULL NULL
); );
instance->mutex = xSemaphoreCreateRecursiveMutex(); instance->mutex = furi_mutex_alloc(FuriMutexTypeRecursive);
furi_check(lvgl_port_lock(100)); furi_check(lvgl_port_lock(100));
instance->lvgl_parent = lv_scr_act(); instance->lvgl_parent = lv_scr_act();
@ -56,13 +56,13 @@ void gui_free(Gui* instance) {
void gui_lock() { void gui_lock() {
furi_assert(gui); furi_assert(gui);
furi_assert(gui->mutex); furi_assert(gui->mutex);
furi_check(xSemaphoreTakeRecursive(gui->mutex, portMAX_DELAY) == pdPASS); furi_check(furi_mutex_acquire(gui->mutex, 1000 / portTICK_PERIOD_MS) == FuriStatusOk);
} }
void gui_unlock() { void gui_unlock() {
furi_assert(gui); furi_assert(gui);
furi_assert(gui->mutex); furi_assert(gui->mutex);
furi_check(xSemaphoreGiveRecursive(gui->mutex) == pdPASS); furi_check(furi_mutex_release(gui->mutex) == FuriStatusOk);
} }
void gui_request_draw() { void gui_request_draw() {

View File

@ -1,7 +1,5 @@
#pragma once #pragma once
#include "freertos/FreeRTOS.h"
#include "freertos/semphr.h"
#include "gui.h" #include "gui.h"
#include "message_queue.h" #include "message_queue.h"
#include "mutex.h" #include "mutex.h"
@ -19,7 +17,7 @@
struct Gui { struct Gui {
// Thread and lock // Thread and lock
FuriThread* thread; FuriThread* thread;
SemaphoreHandle_t mutex; FuriMutex* mutex;
// Layers and Canvas // Layers and Canvas
ViewPort* layers[GuiLayerMAX]; ViewPort* layers[GuiLayerMAX];