diff options
| Commit | 0b083af2d50402a014349dd4ca6eb2d4337aca1e (patch) | |
|---|---|---|
| Author | 2024-05-24 12:53:30 +0300 | |
| Committer | 2024-05-24 13:00:00 +0300 | |
| Files | 3852cd4cd161e26717531db0f00bc6ad9e4f425c | |
| uni-projects-0b083af2d50402a014349dd4ca6eb2d4337aca1e.tar uni-projects-0b083af2d50402a014349dd4ca6eb2d4337aca1e.tar.gz uni-projects-0b083af2d50402a014349dd4ca6eb2d4337aca1e.zip | ||
| Parent | b97a64e8dff8d6b90a9171bb968e0807b3a35c46 (diff) | |
(iot/goam/buttons) Reworked into using tasks and notifications to launch actions
1 files changed, 32 insertions, 9 deletions
| -rw-r--r-- | Year 3/Internet of things/goam/main/buttons.c | 41 |
diff --git a/Year 3/Internet of things/goam/main/buttons.c b/Year 3/Internet of things/goam/main/buttons.c index 9aa3cf4..6dd99ee 100644 --- a/Year 3/Internet of things/goam/main/buttons.c +++ b/Year 3/Internet of things/goam/main/buttons.c @@ -25,20 +25,43 @@ static void IRAM_ATTR gpio_button_interrupt_handler(void* arg) static void (*button_on[40])() = { NULL }; static void (*button_off[40])() = { NULL }; -static void on_button_event(void* arg) +#define BUTTON_ACTION_COMPLETED_BIT 0b1 + +static TaskHandle_t on_button_event_handle = NULL; + +static void button_action(void* arg) { + uint32_t io_num = *(uint32_t*)arg; + if (gpio_get_level(io_num)) { + if (button_on[io_num]) button_on[io_num](); + } + else { + if (button_off[io_num]) button_off[io_num](); + } + + xTaskNotify(on_button_event_handle, BUTTON_ACTION_COMPLETED_BIT, eSetBits); + vTaskDelete(NULL); +} + +static void on_button_event_task(void* arg) { uint32_t io_num; + long unsigned int notification = 0; while (true) { if (!xQueueReceive(gpio_button_queue, &io_num, portMAX_DELAY)) continue; ESP_LOGD(TAG, "GPIO[%ld] intr, val: %d", io_num, gpio_get_level(io_num)); - if (gpio_get_level(io_num)) { - if (button_on[io_num]) button_on[io_num](); - } - else { - if (button_off[io_num]) button_off[io_num](); - } + // button_on/button_off functions require a lot of memory, but most of the time + // we won't be running them, so its more memory efficient to split them off into + // another task, which allocates a lot of memory, but then frees it + xTaskCreate(button_action, "button_action", 2048, &io_num, 10, NULL); + + // We want button_action to be "blocking", in GoAm there is only one button, so + // this logic is good enough. Under normal circumstances there should just be a + // check to not create another task for the same button action + do { + xTaskNotifyWait(ULONG_MAX, 0, ¬ification, 100 / portTICK_PERIOD_MS); + } while (!(notification & BUTTON_ACTION_COMPLETED_BIT)); // If any button was pressed, this effectively blocks all other button presses // that happened in the meantime. @@ -57,9 +80,9 @@ static void on_button_event(void* arg) void buttons_init() { //create a queue to handle gpio event from isr - gpio_button_queue = xQueueCreate(10, sizeof(uint32_t)); + gpio_button_queue = xQueueCreate(5, sizeof(uint32_t)); //start gpio task - xTaskCreate(on_button_event, "on_button_event", 2048, NULL, 10, NULL); + xTaskCreate(on_button_event_task, "on_button_event_task", 768, NULL, 10, &on_button_event_handle); //install gpio isr service gpio_install_isr_service(ESP_INTR_FLAG_DEFAULT); |
