forked from project-chip/connectedhomeip
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
ESP32: Add UAT button for lit-icd-app (project-chip#33043)
* ESP32: Add UAT button for lit-icd-app * Restyled by clang-format * Add some review changes * Restyled by clang-format * fix compile error --------- Co-authored-by: Restyled.io <[email protected]>
- Loading branch information
1 parent
b4650b9
commit a860932
Showing
4 changed files
with
229 additions
and
5 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,148 @@ | ||
/* | ||
* | ||
* Copyright (c) 2024 Project CHIP Authors | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* http://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
*/ | ||
|
||
#include "IcdUatButton.h" | ||
|
||
#include "driver/gpio.h" | ||
#include "esp_attr.h" | ||
#include "esp_log.h" | ||
#include "freertos/FreeRTOS.h" | ||
#include "freertos/queue.h" | ||
#include "freertos/task.h" | ||
#include "hal/gpio_types.h" | ||
#include <cstdint> | ||
|
||
#define ESP_INTR_FLAG_DEFAULT 0 | ||
|
||
static const char TAG[] = "Button"; | ||
QueueHandle_t UatButton::sEventQueue = nullptr; | ||
TaskHandle_t UatButton::sTaskHandle = nullptr; | ||
|
||
static void IRAM_ATTR gpio_isr_handler(void * arg) | ||
{ | ||
if (UatButton::sEventQueue) | ||
{ | ||
UatButton * button = (UatButton *) arg; | ||
button->GpioIntrEnable(false); | ||
xQueueSendFromISR(UatButton::sEventQueue, &button, NULL); | ||
} | ||
} | ||
|
||
void UatButton::RunEventLoop(void * arg) | ||
{ | ||
bool eventDone = true; | ||
UatButton * button = nullptr; | ||
|
||
for (;;) | ||
{ | ||
if (xQueueReceive(sEventQueue, &button, portMAX_DELAY) == pdTRUE && button) | ||
{ | ||
button->GpioIntrEnable(false); | ||
eventDone = false; | ||
} | ||
while (!eventDone) | ||
{ | ||
// GPIO Pull up is enabled so the button is pressed when this value is false. | ||
bool value = gpio_get_level(button->mGpioNum); | ||
switch (button->mState) | ||
{ | ||
case ButtonState::kIdle: | ||
button->mState = value == false ? ButtonState::kPressed : ButtonState::kIdle; | ||
break; | ||
case ButtonState::kPressed: | ||
button->mState = value == false ? ButtonState::kPressed : ButtonState::kReleased; | ||
break; | ||
case ButtonState::kReleased: | ||
button->mState = ButtonState::kIdle; | ||
if (button->mUatButtonPressCallback) | ||
{ | ||
button->mUatButtonPressCallback(button); | ||
} | ||
break; | ||
default: | ||
break; | ||
} | ||
if (button->mState == ButtonState::kIdle) | ||
{ | ||
button->GpioIntrEnable(true); | ||
eventDone = true; | ||
break; | ||
} | ||
vTaskDelay(10 / portTICK_PERIOD_MS); | ||
} | ||
} | ||
} | ||
|
||
void UatButton::GpioIntrEnable(bool enable) | ||
{ | ||
if (enable) | ||
{ | ||
gpio_intr_enable(mGpioNum); | ||
} | ||
else | ||
{ | ||
gpio_intr_disable(mGpioNum); | ||
} | ||
} | ||
|
||
void UatButton::Init(gpio_num_t gpioNum, esp_sleep_ext1_wakeup_mode_t wakeupMode) | ||
{ | ||
mGpioNum = gpioNum; | ||
mState = ButtonState::kIdle; | ||
gpio_config_t io_conf = {}; | ||
io_conf.intr_type = GPIO_INTR_LOW_LEVEL; | ||
io_conf.pin_bit_mask = (1ULL << static_cast<uint8_t>(mGpioNum)); | ||
io_conf.mode = GPIO_MODE_INPUT; | ||
io_conf.pull_down_en = GPIO_PULLDOWN_DISABLE; | ||
io_conf.pull_up_en = GPIO_PULLUP_ENABLE; | ||
// configure GPIO with the given settings | ||
gpio_config(&io_conf); | ||
if (!sEventQueue) | ||
{ | ||
// create a queue to handle gpio event from isr | ||
sEventQueue = xQueueCreate(10, sizeof(UatButton *)); | ||
if (!sEventQueue) | ||
{ | ||
ESP_LOGE(TAG, "Failed to create GPIO EventQueue"); | ||
return; | ||
} | ||
} | ||
if (!sTaskHandle) | ||
{ | ||
// start gpio task | ||
xTaskCreate(RunEventLoop, "UatButton", 4096, nullptr, 10, &sTaskHandle); | ||
if (!sTaskHandle) | ||
{ | ||
ESP_LOGE(TAG, "Failed to create GPIO Task"); | ||
return; | ||
} | ||
} | ||
// install gpio isr service | ||
gpio_install_isr_service(ESP_INTR_FLAG_DEFAULT); | ||
// hook isr handler for specific gpio pin | ||
gpio_isr_handler_add(mGpioNum, gpio_isr_handler, (void *) this); | ||
ESP_LOGI(TAG, "UAT Button initialized.."); | ||
// Configure RTC IO wake up | ||
esp_sleep_enable_ext1_wakeup(1ULL << static_cast<uint8_t>(mGpioNum), wakeupMode); | ||
#if SOC_RTCIO_INPUT_OUTPUT_SUPPORTED | ||
rtc_gpio_pulldown_dis(mGpioNum); | ||
rtc_gpio_pullup_en(mGpioNum); | ||
#else | ||
gpio_pulldown_dis(mGpioNum); | ||
gpio_pullup_en(mGpioNum); | ||
#endif | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,50 @@ | ||
/* | ||
* | ||
* Copyright (c) 2024 Project CHIP Authors | ||
* | ||
* Licensed under the Apache License, Version 2.0 (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* | ||
* http://www.apache.org/licenses/LICENSE-2.0 | ||
* | ||
* Unless required by applicable law or agreed to in writing, software | ||
* distributed under the License is distributed on an "AS IS" BASIS, | ||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
* See the License for the specific language governing permissions and | ||
* limitations under the License. | ||
*/ | ||
|
||
#pragma once | ||
|
||
#include <driver/gpio.h> | ||
#include <esp_sleep.h> | ||
#include <freertos/FreeRTOS.h> | ||
#include <freertos/queue.h> | ||
#include <freertos/task.h> | ||
|
||
class UatButton | ||
{ | ||
public: | ||
using UatButtonPressCallback = void (*)(UatButton *); | ||
|
||
enum class ButtonState : uint8_t | ||
{ | ||
kIdle = 0, | ||
kPressed, | ||
kReleased, | ||
}; | ||
|
||
void Init(gpio_num_t gpioNum, esp_sleep_ext1_wakeup_mode_t wakeMode); | ||
void SetUatButtonPressCallback(UatButtonPressCallback buttonCallback) { mUatButtonPressCallback = buttonCallback; } | ||
void GpioIntrEnable(bool enable); | ||
|
||
static void RunEventLoop(void * arg); | ||
static TaskHandle_t sTaskHandle; | ||
static QueueHandle_t sEventQueue; | ||
|
||
private: | ||
gpio_num_t mGpioNum; | ||
ButtonState mState; | ||
UatButtonPressCallback mUatButtonPressCallback; | ||
}; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters