mirror of
https://github.com/ByteWelder/Tactility.git
synced 2026-02-20 15:35:05 +00:00
TactilityFreertos and more
This commit is contained in:
parent
3fc2ff8bc6
commit
bfe0158a4a
2
.github/workflows/tests.yml
vendored
2
.github/workflows/tests.yml
vendored
@ -21,5 +21,7 @@ jobs:
|
|||||||
run: cmake --build build --target build-tests
|
run: cmake --build build --target build-tests
|
||||||
- name: "Run TactilityCore Tests"
|
- name: "Run TactilityCore Tests"
|
||||||
run: build/Tests/TactilityCore/TactilityCoreTests --exit
|
run: build/Tests/TactilityCore/TactilityCoreTests --exit
|
||||||
|
- name: "Run TactilityFreertos Tests"
|
||||||
|
run: build/Tests/TactilityFreertos/TactilityFreertosTests --exit
|
||||||
- name: "Run TactilityHeadless Tests"
|
- name: "Run TactilityHeadless Tests"
|
||||||
run: build/Tests/Tactility/TactilityTests --exit
|
run: build/Tests/Tactility/TactilityTests --exit
|
||||||
|
|||||||
@ -37,6 +37,7 @@ if (DEFINED ENV{ESP_IDF_VERSION})
|
|||||||
"Tactility"
|
"Tactility"
|
||||||
"TactilityC"
|
"TactilityC"
|
||||||
"TactilityCore"
|
"TactilityCore"
|
||||||
|
"TactilityFreeRtos"
|
||||||
"Libraries/esp_lvgl_port"
|
"Libraries/esp_lvgl_port"
|
||||||
"Libraries/elf_loader"
|
"Libraries/elf_loader"
|
||||||
"Libraries/lvgl"
|
"Libraries/lvgl"
|
||||||
@ -74,6 +75,7 @@ project(Tactility)
|
|||||||
if (NOT DEFINED ENV{ESP_IDF_VERSION})
|
if (NOT DEFINED ENV{ESP_IDF_VERSION})
|
||||||
add_subdirectory(Tactility)
|
add_subdirectory(Tactility)
|
||||||
add_subdirectory(TactilityCore)
|
add_subdirectory(TactilityCore)
|
||||||
|
add_subdirectory(TactilityFreeRtos)
|
||||||
add_subdirectory(Devices/simulator)
|
add_subdirectory(Devices/simulator)
|
||||||
endif ()
|
endif ()
|
||||||
|
|
||||||
|
|||||||
@ -1,13 +1,14 @@
|
|||||||
#include "LvglTask.h"
|
#include "LvglTask.h"
|
||||||
|
|
||||||
#include <Tactility/Log.h>
|
|
||||||
#include <Tactility/lvgl/LvglSync.h>
|
|
||||||
#include <Tactility/RecursiveMutex.h>
|
|
||||||
#include <Tactility/Thread.h>
|
#include <Tactility/Thread.h>
|
||||||
|
#include <Tactility/Log.h>
|
||||||
|
#include <Tactility/RecursiveMutex.h>
|
||||||
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
|
|
||||||
|
#include <Tactility/Check.h>
|
||||||
#include <lvgl.h>
|
#include <lvgl.h>
|
||||||
|
|
||||||
#define TAG "lvgl_task"
|
constexpr auto TAG = "lvgl_task";
|
||||||
|
|
||||||
// Mutex for LVGL drawing
|
// Mutex for LVGL drawing
|
||||||
static tt::RecursiveMutex lvgl_mutex;
|
static tt::RecursiveMutex lvgl_mutex;
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#include "Main.h"
|
#include "Main.h"
|
||||||
#include <Tactility/TactilityCore.h>
|
|
||||||
#include <Tactility/Thread.h>
|
#include <Tactility/Thread.h>
|
||||||
|
#include <Tactility/TactilityCore.h>
|
||||||
|
|
||||||
#include "FreeRTOS.h"
|
#include "FreeRTOS.h"
|
||||||
#include "task.h"
|
#include "task.h"
|
||||||
|
|||||||
@ -19,6 +19,7 @@ else ()
|
|||||||
target_link_libraries(FirmwareSim
|
target_link_libraries(FirmwareSim
|
||||||
PRIVATE Tactility
|
PRIVATE Tactility
|
||||||
PRIVATE TactilityCore
|
PRIVATE TactilityCore
|
||||||
|
PRIVATE TactilityFreeRtos
|
||||||
PRIVATE Simulator
|
PRIVATE Simulator
|
||||||
PRIVATE SDL2::SDL2-static SDL2-static
|
PRIVATE SDL2::SDL2-static SDL2-static
|
||||||
)
|
)
|
||||||
|
|||||||
13
LICENSE.md
13
LICENSE.md
@ -1,15 +1,20 @@
|
|||||||
# Tactility
|
# Tactility: Main License
|
||||||
|
|
||||||
The Tactility project is available under the [GNU General Public License v3](Documentation/license-tactility.md).
|
The Tactility project code is available under the [GNU General Public License v3](Documentation/license-tactility.md).
|
||||||
Distributions and forks must adhere to the license terms.
|
Distributions and forks must adhere to the license terms.
|
||||||
|
|
||||||
The Tactility logo copyrights are owned by Ken Van Hoeylandt.
|
The Tactility logo copyrights are owned by Ken Van Hoeylandt.
|
||||||
Firmwares built from [the original repository](https://github.com/ByteWelder/Tactility) can be redistributed with the Tactility logo.
|
Firmwares built from [the original repository](https://github.com/ByteWelder/Tactility) can be redistributed with the Tactility logo.
|
||||||
For other usages, [contact me](https://kenvanhoeylandt.net).
|
For other usages, [contact me](https://kenvanhoeylandt.net).
|
||||||
|
|
||||||
# TactilityC & TactilitySDK
|
Third party projects that were included in Tactility retain their licenses.
|
||||||
|
|
||||||
TactilityC (source & binaries) and the TactilitySDK distribution files are available via the [Apache License Version 2.0](Documentation/license-tactilitysdk.md).
|
# Tactility: Secondary License
|
||||||
|
|
||||||
|
The following projects are also available under [Apache License Version 2.0](Documentation/license-tactilitysdk.md):
|
||||||
|
- TactilityC
|
||||||
|
- TactilityFreertos
|
||||||
|
- TactilitySDK (source and binaries)
|
||||||
|
|
||||||
# Other licenses & copyrights
|
# Other licenses & copyrights
|
||||||
|
|
||||||
|
|||||||
@ -8,6 +8,7 @@ if (DEFINED ENV{ESP_IDF_VERSION})
|
|||||||
|
|
||||||
list(APPEND REQUIRES_LIST
|
list(APPEND REQUIRES_LIST
|
||||||
TactilityCore
|
TactilityCore
|
||||||
|
TactilityFreeRtos
|
||||||
lvgl
|
lvgl
|
||||||
driver
|
driver
|
||||||
elf_loader
|
elf_loader
|
||||||
@ -71,6 +72,7 @@ else()
|
|||||||
|
|
||||||
target_link_libraries(Tactility
|
target_link_libraries(Tactility
|
||||||
PUBLIC cJSON
|
PUBLIC cJSON
|
||||||
|
PUBLIC TactilityFreeRtos
|
||||||
PUBLIC TactilityCore
|
PUBLIC TactilityCore
|
||||||
PUBLIC freertos_kernel
|
PUBLIC freertos_kernel
|
||||||
PUBLIC lvgl
|
PUBLIC lvgl
|
||||||
|
|||||||
@ -1,7 +1,7 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <Tactility/app/AppManifest.h>
|
|
||||||
#include <Tactility/Dispatcher.h>
|
#include <Tactility/Dispatcher.h>
|
||||||
|
#include <Tactility/app/AppManifest.h>
|
||||||
#include <Tactility/hal/Configuration.h>
|
#include <Tactility/hal/Configuration.h>
|
||||||
#include <Tactility/service/ServiceManifest.h>
|
#include <Tactility/service/ServiceManifest.h>
|
||||||
|
|
||||||
|
|||||||
@ -4,8 +4,8 @@
|
|||||||
#include "GpsConfiguration.h"
|
#include "GpsConfiguration.h"
|
||||||
#include "Satellites.h"
|
#include "Satellites.h"
|
||||||
|
|
||||||
#include <Tactility/RecursiveMutex.h>
|
|
||||||
#include <Tactility/Thread.h>
|
#include <Tactility/Thread.h>
|
||||||
|
#include <Tactility/RecursiveMutex.h>
|
||||||
|
|
||||||
#include <minmea.h>
|
#include <minmea.h>
|
||||||
#include <utility>
|
#include <utility>
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <Tactility/RtosCompat.h>
|
#include <Tactility/freertoscompat/RTOS.h>
|
||||||
#include <Tactility/RecursiveMutex.h>
|
#include <Tactility/RecursiveMutex.h>
|
||||||
|
|
||||||
#include <minmea.h>
|
#include <minmea.h>
|
||||||
|
|||||||
@ -3,7 +3,7 @@
|
|||||||
#include "./I2cCompat.h"
|
#include "./I2cCompat.h"
|
||||||
#include "Tactility/Lock.h"
|
#include "Tactility/Lock.h"
|
||||||
|
|
||||||
#include <Tactility/RtosCompat.h>
|
#include <Tactility/freertoscompat/RTOS.h>
|
||||||
|
|
||||||
#include <climits>
|
#include <climits>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|||||||
@ -3,6 +3,7 @@
|
|||||||
#include "../Device.h"
|
#include "../Device.h"
|
||||||
|
|
||||||
#include <Tactility/TactilityCore.h>
|
#include <Tactility/TactilityCore.h>
|
||||||
|
#include <Tactility/Lock.h>
|
||||||
|
|
||||||
namespace tt::hal::sdcard {
|
namespace tt::hal::sdcard {
|
||||||
|
|
||||||
@ -51,7 +52,7 @@ public:
|
|||||||
*/
|
*/
|
||||||
virtual bool unmount() = 0;
|
virtual bool unmount() = 0;
|
||||||
|
|
||||||
virtual State getState(TickType_t timeout = portMAX_DELAY) const = 0;
|
virtual State getState(TickType_t timeout = kernel::MAX_TICKS) const = 0;
|
||||||
|
|
||||||
/** @return empty string when not mounted or the mount path if mounted */
|
/** @return empty string when not mounted or the mount path if mounted */
|
||||||
virtual std::string getMountPath() const = 0;
|
virtual std::string getMountPath() const = 0;
|
||||||
@ -63,7 +64,7 @@ public:
|
|||||||
virtual MountBehaviour getMountBehaviour() const { return mountBehaviour; }
|
virtual MountBehaviour getMountBehaviour() const { return mountBehaviour; }
|
||||||
|
|
||||||
/** @return true if the SD card was mounted, returns false when it was not or when a timeout happened. */
|
/** @return true if the SD card was mounted, returns false when it was not or when a timeout happened. */
|
||||||
bool isMounted(TickType_t timeout = portMAX_DELAY) const { return getState(timeout) == State::Mounted; }
|
bool isMounted(TickType_t timeout = kernel::MAX_TICKS) const { return getState(timeout) == State::Mounted; }
|
||||||
};
|
};
|
||||||
|
|
||||||
/** Return the SdCard device if the path is within the SdCard mounted path (path std::string::starts_with() check)*/
|
/** Return the SdCard device if the path is within the SdCard mounted path (path std::string::starts_with() check)*/
|
||||||
|
|||||||
@ -3,7 +3,7 @@
|
|||||||
#include "SpiCompat.h"
|
#include "SpiCompat.h"
|
||||||
|
|
||||||
#include <Tactility/Lock.h>
|
#include <Tactility/Lock.h>
|
||||||
#include <Tactility/RtosCompat.h>
|
#include <Tactility/freertoscompat/RTOS.h>
|
||||||
|
|
||||||
namespace tt::hal::spi {
|
namespace tt::hal::spi {
|
||||||
|
|
||||||
|
|||||||
@ -1,6 +1,6 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <Tactility/RtosCompat.h>
|
#include <Tactility/freertoscompat/RTOS.h>
|
||||||
|
|
||||||
#include "../gpio/Gpio.h"
|
#include "../gpio/Gpio.h"
|
||||||
#include "Tactility/Lock.h"
|
#include "Tactility/Lock.h"
|
||||||
|
|||||||
@ -1,12 +1,12 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "Tactility/Mutex.h"
|
#include <Tactility/PubSub.h>
|
||||||
#include "Tactility/RecursiveMutex.h"
|
#include <Tactility/Mutex.h>
|
||||||
#include "Tactility/PubSub.h"
|
#include <Tactility/RecursiveMutex.h>
|
||||||
#include "Tactility/hal/gps/GpsDevice.h"
|
#include <Tactility/hal/gps/GpsDevice.h>
|
||||||
#include "Tactility/service/Service.h"
|
#include <Tactility/service/Service.h>
|
||||||
#include "Tactility/service/ServiceContext.h"
|
#include <Tactility/service/ServiceContext.h>
|
||||||
#include "Tactility/service/gps/GpsState.h"
|
#include <Tactility/service/gps/GpsState.h>
|
||||||
|
|
||||||
namespace tt::service::gps {
|
namespace tt::service::gps {
|
||||||
|
|
||||||
|
|||||||
@ -1,11 +1,11 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <Tactility/app/AppInstance.h>
|
|
||||||
#include <Tactility/app/AppManifest.h>
|
|
||||||
#include <Tactility/Bundle.h>
|
|
||||||
#include <Tactility/DispatcherThread.h>
|
#include <Tactility/DispatcherThread.h>
|
||||||
|
#include <Tactility/Bundle.h>
|
||||||
#include <Tactility/PubSub.h>
|
#include <Tactility/PubSub.h>
|
||||||
#include <Tactility/RecursiveMutex.h>
|
#include <Tactility/RecursiveMutex.h>
|
||||||
|
#include <Tactility/app/AppInstance.h>
|
||||||
|
#include <Tactility/app/AppManifest.h>
|
||||||
#include <Tactility/service/Service.h>
|
#include <Tactility/service/Service.h>
|
||||||
|
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
|||||||
@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
#include <Tactility/PubSub.h>
|
#include <Tactility/PubSub.h>
|
||||||
|
|
||||||
|
#include <memory>
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
|
|||||||
@ -5,6 +5,8 @@
|
|||||||
#include <Tactility/app/ElfApp.h>
|
#include <Tactility/app/ElfApp.h>
|
||||||
|
|
||||||
#include <Tactility/Bundle.h>
|
#include <Tactility/Bundle.h>
|
||||||
|
#include <Tactility/Check.h>
|
||||||
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/Mutex.h>
|
#include <Tactility/Mutex.h>
|
||||||
|
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
|||||||
@ -4,7 +4,7 @@
|
|||||||
|
|
||||||
namespace tt::app::i2cscanner {
|
namespace tt::app::i2cscanner {
|
||||||
|
|
||||||
#define TAG "i2cscanner"
|
static constexpr auto TAG = "i2cscanner";
|
||||||
|
|
||||||
enum ScanState {
|
enum ScanState {
|
||||||
ScanStateInitial,
|
ScanStateInitial,
|
||||||
|
|||||||
@ -1,9 +1,9 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <Tactility/app/AppContext.h>
|
|
||||||
#include <Tactility/MessageQueue.h>
|
#include <Tactility/MessageQueue.h>
|
||||||
#include <Tactility/RecursiveMutex.h>
|
|
||||||
#include <Tactility/PubSub.h>
|
#include <Tactility/PubSub.h>
|
||||||
|
#include <Tactility/RecursiveMutex.h>
|
||||||
|
#include <Tactility/app/AppContext.h>
|
||||||
#include <Tactility/service/Service.h>
|
#include <Tactility/service/Service.h>
|
||||||
#include <Tactility/service/loader/Loader.h>
|
#include <Tactility/service/loader/Loader.h>
|
||||||
|
|
||||||
@ -21,6 +21,7 @@ class GuiService final : public Service {
|
|||||||
|
|
||||||
// Thread and lock
|
// Thread and lock
|
||||||
Thread* thread = nullptr;
|
Thread* thread = nullptr;
|
||||||
|
EventGroup threadFlags;
|
||||||
RecursiveMutex mutex;
|
RecursiveMutex mutex;
|
||||||
PubSub<loader::LoaderService::Event>::SubscriptionHandle loader_pubsub_subscription = nullptr;
|
PubSub<loader::LoaderService::Event>::SubscriptionHandle loader_pubsub_subscription = nullptr;
|
||||||
|
|
||||||
@ -49,7 +50,7 @@ class GuiService final : public Service {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void unlock() const {
|
void unlock() const {
|
||||||
tt_check(mutex.unlock());
|
mutex.unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
void showApp(std::shared_ptr<app::AppInstance> app);
|
void showApp(std::shared_ptr<app::AppInstance> app);
|
||||||
|
|||||||
@ -2,8 +2,8 @@
|
|||||||
|
|
||||||
#include "Tactility/service/Service.h"
|
#include "Tactility/service/Service.h"
|
||||||
|
|
||||||
#include <Tactility/Mutex.h>
|
|
||||||
#include <Tactility/Timer.h>
|
#include <Tactility/Timer.h>
|
||||||
|
#include <Tactility/Mutex.h>
|
||||||
|
|
||||||
namespace tt::service::memorychecker {
|
namespace tt::service::memorychecker {
|
||||||
|
|
||||||
@ -14,7 +14,7 @@ namespace tt::service::memorychecker {
|
|||||||
class MemoryCheckerService final : public Service {
|
class MemoryCheckerService final : public Service {
|
||||||
|
|
||||||
Mutex mutex;
|
Mutex mutex;
|
||||||
Timer timer = Timer(Timer::Type::Periodic, [this] { onTimerUpdate(); });
|
Timer timer = Timer(Timer::Type::Periodic, pdMS_TO_TICKS(1000), [this] { onTimerUpdate(); });
|
||||||
|
|
||||||
// LVGL Statusbar icon
|
// LVGL Statusbar icon
|
||||||
int8_t statusbarIconId = -1;
|
int8_t statusbarIconId = -1;
|
||||||
|
|||||||
@ -1,4 +1,4 @@
|
|||||||
#include "Tactility/TactilityConfig.h"
|
#include <Tactility/TactilityConfig.h>
|
||||||
|
|
||||||
#if TT_FEATURE_SCREENSHOT_ENABLED
|
#if TT_FEATURE_SCREENSHOT_ENABLED
|
||||||
|
|
||||||
|
|||||||
@ -5,15 +5,15 @@
|
|||||||
#include <Tactility/Tactility.h>
|
#include <Tactility/Tactility.h>
|
||||||
#include <Tactility/TactilityConfig.h>
|
#include <Tactility/TactilityConfig.h>
|
||||||
|
|
||||||
|
#include <Tactility/DispatcherThread.h>
|
||||||
|
#include <Tactility/MountPoints.h>
|
||||||
#include <Tactility/app/AppManifestParsing.h>
|
#include <Tactility/app/AppManifestParsing.h>
|
||||||
#include <Tactility/app/AppRegistration.h>
|
#include <Tactility/app/AppRegistration.h>
|
||||||
#include <Tactility/DispatcherThread.h>
|
|
||||||
#include <Tactility/file/File.h>
|
#include <Tactility/file/File.h>
|
||||||
#include <Tactility/file/FileLock.h>
|
#include <Tactility/file/FileLock.h>
|
||||||
#include <Tactility/file/PropertiesFile.h>
|
#include <Tactility/file/PropertiesFile.h>
|
||||||
#include <Tactility/hal/HalPrivate.h>
|
#include <Tactility/hal/HalPrivate.h>
|
||||||
#include <Tactility/lvgl/LvglPrivate.h>
|
#include <Tactility/lvgl/LvglPrivate.h>
|
||||||
#include <Tactility/MountPoints.h>
|
|
||||||
#include <Tactility/network/NtpPrivate.h>
|
#include <Tactility/network/NtpPrivate.h>
|
||||||
#include <Tactility/service/ServiceManifest.h>
|
#include <Tactility/service/ServiceManifest.h>
|
||||||
#include <Tactility/service/ServiceRegistration.h>
|
#include <Tactility/service/ServiceRegistration.h>
|
||||||
|
|||||||
@ -1,5 +1,6 @@
|
|||||||
#include <Tactility/app/AppManifestParsing.h>
|
#include <Tactility/app/AppManifestParsing.h>
|
||||||
|
|
||||||
|
#include <Tactility/Log.h>
|
||||||
#include <regex>
|
#include <regex>
|
||||||
|
|
||||||
namespace tt::app {
|
namespace tt::app {
|
||||||
|
|||||||
@ -1,5 +1,7 @@
|
|||||||
#ifdef ESP_PLATFORM
|
#ifdef ESP_PLATFORM
|
||||||
|
|
||||||
|
#include <Tactility/Timer.h>
|
||||||
|
#include <Tactility/Tactility.h>
|
||||||
#include <Tactility/app/AppManifest.h>
|
#include <Tactility/app/AppManifest.h>
|
||||||
#include <Tactility/lvgl/Lvgl.h>
|
#include <Tactility/lvgl/Lvgl.h>
|
||||||
#include <Tactility/lvgl/LvglSync.h>
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
@ -9,8 +11,6 @@
|
|||||||
#include <Tactility/service/development/DevelopmentSettings.h>
|
#include <Tactility/service/development/DevelopmentSettings.h>
|
||||||
#include <Tactility/service/loader/Loader.h>
|
#include <Tactility/service/loader/Loader.h>
|
||||||
#include <Tactility/service/wifi/Wifi.h>
|
#include <Tactility/service/wifi/Wifi.h>
|
||||||
#include <Tactility/Tactility.h>
|
|
||||||
#include <Tactility/Timer.h>
|
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <lvgl.h>
|
#include <lvgl.h>
|
||||||
@ -27,7 +27,7 @@ class DevelopmentApp final : public App {
|
|||||||
lv_obj_t* statusLabel = nullptr;
|
lv_obj_t* statusLabel = nullptr;
|
||||||
std::shared_ptr<service::development::DevelopmentService> service;
|
std::shared_ptr<service::development::DevelopmentService> service;
|
||||||
|
|
||||||
Timer timer = Timer(Timer::Type::Periodic, [this] {
|
Timer timer = Timer(Timer::Type::Periodic, pdMS_TO_TICKS(1000), [this] {
|
||||||
auto lock = lvgl::getSyncLock()->asScopedLock();
|
auto lock = lvgl::getSyncLock()->asScopedLock();
|
||||||
// TODO: There's a crash when this is called when the app is being destroyed
|
// TODO: There's a crash when this is called when the app is being destroyed
|
||||||
if (lock.lock(lvgl::defaultLockTime) && lvgl::isStarted()) {
|
if (lock.lock(lvgl::defaultLockTime) && lvgl::isStarted()) {
|
||||||
@ -148,7 +148,7 @@ public:
|
|||||||
|
|
||||||
updateViewState();
|
updateViewState();
|
||||||
|
|
||||||
timer.start(1000);
|
timer.start();
|
||||||
}
|
}
|
||||||
|
|
||||||
void onHide(AppContext& appContext) override {
|
void onHide(AppContext& appContext) override {
|
||||||
|
|||||||
@ -5,7 +5,7 @@
|
|||||||
#include <Tactility/hal/sdcard/SdCardDevice.h>
|
#include <Tactility/hal/sdcard/SdCardDevice.h>
|
||||||
#include <Tactility/Log.h>
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/MountPoints.h>
|
#include <Tactility/MountPoints.h>
|
||||||
#include <Tactility/kernel/Kernel.h>
|
#include <Tactility/kernel/Platform.h>
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
|
|||||||
@ -1,22 +1,22 @@
|
|||||||
#include <Tactility/app/files/View.h>
|
#include <Tactility/app/files/View.h>
|
||||||
#include <Tactility/app/files/SupportedFiles.h>
|
#include <Tactility/app/files/SupportedFiles.h>
|
||||||
|
|
||||||
|
#include <Tactility/file/File.h>
|
||||||
|
#include <Tactility/file/FileLock.h>
|
||||||
#include <Tactility/app/alertdialog/AlertDialog.h>
|
#include <Tactility/app/alertdialog/AlertDialog.h>
|
||||||
#include <Tactility/app/imageviewer/ImageViewer.h>
|
#include <Tactility/app/imageviewer/ImageViewer.h>
|
||||||
#include <Tactility/app/inputdialog/InputDialog.h>
|
#include <Tactility/app/inputdialog/InputDialog.h>
|
||||||
#include <Tactility/app/notes/Notes.h>
|
#include <Tactility/app/notes/Notes.h>
|
||||||
#include <Tactility/app/ElfApp.h>
|
#include <Tactility/app/ElfApp.h>
|
||||||
|
#include <Tactility/kernel/Platform.h>
|
||||||
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/lvgl/Toolbar.h>
|
#include <Tactility/lvgl/Toolbar.h>
|
||||||
#include <Tactility/lvgl/LvglSync.h>
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
|
|
||||||
#include <Tactility/Tactility.h>
|
|
||||||
#include <Tactility/file/File.h>
|
|
||||||
#include <Tactility/Log.h>
|
|
||||||
#include <Tactility/StringUtils.h>
|
#include <Tactility/StringUtils.h>
|
||||||
|
#include <Tactility/Tactility.h>
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#include <Tactility/file/FileLock.h>
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
#ifdef ESP_PLATFORM
|
||||||
#include <Tactility/service/loader/Loader.h>
|
#include <Tactility/service/loader/Loader.h>
|
||||||
|
|||||||
@ -4,7 +4,7 @@
|
|||||||
#include "Tactility/hal/sdcard/SdCardDevice.h"
|
#include "Tactility/hal/sdcard/SdCardDevice.h"
|
||||||
#include <Tactility/Log.h>
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/MountPoints.h>
|
#include <Tactility/MountPoints.h>
|
||||||
#include <Tactility/kernel/Kernel.h>
|
#include <Tactility/kernel/Platform.h>
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
|
|||||||
@ -1,18 +1,19 @@
|
|||||||
#include "Tactility/app/fileselection/View.h"
|
#include <Tactility/app/fileselection/View.h>
|
||||||
|
|
||||||
#include "Tactility/app/alertdialog/AlertDialog.h"
|
#include <Tactility/app/alertdialog/AlertDialog.h>
|
||||||
#include "Tactility/lvgl/Toolbar.h"
|
#include <Tactility/lvgl/Toolbar.h>
|
||||||
#include "Tactility/lvgl/LvglSync.h"
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
|
|
||||||
#include <Tactility/Tactility.h>
|
#include <Tactility/Tactility.h>
|
||||||
#include "Tactility/file/File.h"
|
#include <Tactility/file/File.h>
|
||||||
#include <Tactility/StringUtils.h>
|
#include <Tactility/StringUtils.h>
|
||||||
|
|
||||||
|
#include <Tactility/kernel/Platform.h>
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
#ifdef ESP_PLATFORM
|
||||||
#include "Tactility/service/loader/Loader.h"
|
#include <Tactility/service/loader/Loader.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
namespace tt::app::fileselection {
|
namespace tt::app::fileselection {
|
||||||
|
|||||||
@ -1,5 +1,6 @@
|
|||||||
#include <Tactility/Tactility.h>
|
#include <Tactility/Tactility.h>
|
||||||
|
|
||||||
|
#include <Tactility/Timer.h>
|
||||||
#include <Tactility/app/AppManifest.h>
|
#include <Tactility/app/AppManifest.h>
|
||||||
#include <Tactility/app/alertdialog/AlertDialog.h>
|
#include <Tactility/app/alertdialog/AlertDialog.h>
|
||||||
#include <Tactility/lvgl/LvglSync.h>
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
@ -7,7 +8,6 @@
|
|||||||
#include <Tactility/service/gps/GpsService.h>
|
#include <Tactility/service/gps/GpsService.h>
|
||||||
#include <Tactility/service/gps/GpsState.h>
|
#include <Tactility/service/gps/GpsState.h>
|
||||||
#include <Tactility/service/loader/Loader.h>
|
#include <Tactility/service/loader/Loader.h>
|
||||||
#include <Tactility/Timer.h>
|
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <format>
|
#include <format>
|
||||||
@ -62,7 +62,7 @@ class GpsSettingsApp final : public App {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void startReceivingUpdates() {
|
void startReceivingUpdates() {
|
||||||
timer->start(kernel::secondsToTicks(1));
|
timer->start();
|
||||||
updateViews();
|
updateViews();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -268,7 +268,7 @@ class GpsSettingsApp final : public App {
|
|||||||
public:
|
public:
|
||||||
|
|
||||||
GpsSettingsApp() {
|
GpsSettingsApp() {
|
||||||
timer = std::make_unique<Timer>(Timer::Type::Periodic, [this] {
|
timer = std::make_unique<Timer>(Timer::Type::Periodic, kernel::secondsToTicks(1), [this] {
|
||||||
updateViews();
|
updateViews();
|
||||||
});
|
});
|
||||||
service = service::gps::findGpsService();
|
service = service::gps::findGpsService();
|
||||||
|
|||||||
@ -8,10 +8,10 @@
|
|||||||
#include <Tactility/lvgl/Toolbar.h>
|
#include <Tactility/lvgl/Toolbar.h>
|
||||||
#include <Tactility/service/loader/Loader.h>
|
#include <Tactility/service/loader/Loader.h>
|
||||||
|
|
||||||
|
#include <Tactility/Timer.h>
|
||||||
#include <Tactility/Assets.h>
|
#include <Tactility/Assets.h>
|
||||||
#include <Tactility/RecursiveMutex.h>
|
#include <Tactility/RecursiveMutex.h>
|
||||||
#include <Tactility/Tactility.h>
|
#include <Tactility/Tactility.h>
|
||||||
#include <Tactility/Timer.h>
|
|
||||||
|
|
||||||
#include <format>
|
#include <format>
|
||||||
|
|
||||||
@ -278,10 +278,10 @@ void I2cScannerApp::startScanning() {
|
|||||||
lv_obj_clean(scanListWidget);
|
lv_obj_clean(scanListWidget);
|
||||||
|
|
||||||
scanState = ScanStateScanning;
|
scanState = ScanStateScanning;
|
||||||
scanTimer = std::make_unique<Timer>(Timer::Type::Once, [this]{
|
scanTimer = std::make_unique<Timer>(Timer::Type::Once, 10, [this]{
|
||||||
onScanTimer();
|
onScanTimer();
|
||||||
});
|
});
|
||||||
scanTimer->start(10);
|
scanTimer->start();
|
||||||
mutex.unlock();
|
mutex.unlock();
|
||||||
} else {
|
} else {
|
||||||
TT_LOG_W(TAG, LOG_MESSAGE_MUTEX_LOCK_FAILED_FMT, "startScanning");
|
TT_LOG_W(TAG, LOG_MESSAGE_MUTEX_LOCK_FAILED_FMT, "startScanning");
|
||||||
|
|||||||
@ -1,12 +1,12 @@
|
|||||||
#include "Tactility/app/AppContext.h"
|
#include <Tactility/app/AppContext.h>
|
||||||
#include "Tactility/lvgl/LvglSync.h"
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
#include "Tactility/lvgl/Style.h"
|
#include <Tactility/lvgl/Style.h>
|
||||||
#include "Tactility/lvgl/Toolbar.h"
|
#include <Tactility/lvgl/Toolbar.h>
|
||||||
#include "Tactility/service/loader/Loader.h"
|
#include <Tactility/service/loader/Loader.h>
|
||||||
|
|
||||||
#include "Tactility/hal/power/PowerDevice.h"
|
#include <Tactility/hal/power/PowerDevice.h>
|
||||||
#include <Tactility/Assets.h>
|
|
||||||
#include <Tactility/Timer.h>
|
#include <Tactility/Timer.h>
|
||||||
|
#include <Tactility/Assets.h>
|
||||||
#include <Tactility/hal/Device.h>
|
#include <Tactility/hal/Device.h>
|
||||||
|
|
||||||
#include <lvgl.h>
|
#include <lvgl.h>
|
||||||
@ -31,7 +31,7 @@ std::shared_ptr<PowerApp> _Nullable optApp() {
|
|||||||
|
|
||||||
class PowerApp : public App {
|
class PowerApp : public App {
|
||||||
|
|
||||||
Timer update_timer = Timer(Timer::Type::Periodic, []() { onTimer(); });
|
Timer update_timer = Timer(Timer::Type::Periodic, kernel::millisToTicks(1000),[]() { onTimer(); });
|
||||||
|
|
||||||
std::shared_ptr<hal::power::PowerDevice> power;
|
std::shared_ptr<hal::power::PowerDevice> power;
|
||||||
|
|
||||||
@ -180,7 +180,7 @@ public:
|
|||||||
|
|
||||||
updateUi();
|
updateUi();
|
||||||
|
|
||||||
update_timer.start(kernel::millisToTicks(1000));
|
update_timer.start();
|
||||||
}
|
}
|
||||||
|
|
||||||
void onHide(TT_UNUSED AppContext& app) override {
|
void onHide(TT_UNUSED AppContext& app) override {
|
||||||
|
|||||||
@ -8,6 +8,7 @@
|
|||||||
|
|
||||||
#include <Tactility/app/App.h>
|
#include <Tactility/app/App.h>
|
||||||
#include <Tactility/app/AppManifest.h>
|
#include <Tactility/app/AppManifest.h>
|
||||||
|
#include <Tactility/kernel/Platform.h>
|
||||||
#include <Tactility/lvgl/Lvgl.h>
|
#include <Tactility/lvgl/Lvgl.h>
|
||||||
#include <Tactility/lvgl/LvglSync.h>
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
#include <Tactility/lvgl/Toolbar.h>
|
#include <Tactility/lvgl/Toolbar.h>
|
||||||
@ -71,7 +72,7 @@ static void onModeSetCallback(TT_UNUSED lv_event_t* event) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
ScreenshotApp::ScreenshotApp() {
|
ScreenshotApp::ScreenshotApp() {
|
||||||
updateTimer = std::make_unique<Timer>(Timer::Type::Periodic, [this]() {
|
updateTimer = std::make_unique<Timer>(Timer::Type::Periodic, 500 / portTICK_PERIOD_MS, [this] {
|
||||||
onTimerTick();
|
onTimerTick();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
@ -274,7 +275,7 @@ void ScreenshotApp::onShow(AppContext& appContext, lv_obj_t* parent) {
|
|||||||
updateScreenshotMode();
|
updateScreenshotMode();
|
||||||
|
|
||||||
if (!updateTimer->isRunning()) {
|
if (!updateTimer->isRunning()) {
|
||||||
updateTimer->start(500 / portTICK_PERIOD_MS);
|
updateTimer->start();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -7,9 +7,9 @@
|
|||||||
#include <Tactility/lvgl/LvglSync.h>
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
#include <Tactility/service/loader/Loader.h>
|
#include <Tactility/service/loader/Loader.h>
|
||||||
|
|
||||||
|
#include <Tactility/Timer.h>
|
||||||
#include <Tactility/MountPoints.h>
|
#include <Tactility/MountPoints.h>
|
||||||
#include <Tactility/StringUtils.h>
|
#include <Tactility/StringUtils.h>
|
||||||
#include <Tactility/Timer.h>
|
|
||||||
|
|
||||||
#include <lvgl.h>
|
#include <lvgl.h>
|
||||||
#include <memory>
|
#include <memory>
|
||||||
@ -82,7 +82,7 @@ class TimeZoneApp final : public App {
|
|||||||
updateTimer->stop();
|
updateTimer->stop();
|
||||||
}
|
}
|
||||||
|
|
||||||
updateTimer->start(500 / portTICK_PERIOD_MS);
|
updateTimer->start();
|
||||||
|
|
||||||
mutex.unlock();
|
mutex.unlock();
|
||||||
}
|
}
|
||||||
@ -220,7 +220,7 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
void onCreate(AppContext& app) override {
|
void onCreate(AppContext& app) override {
|
||||||
updateTimer = std::make_unique<Timer>(Timer::Type::Once, [this] {
|
updateTimer = std::make_unique<Timer>(Timer::Type::Once, 500 / portTICK_PERIOD_MS, [this] {
|
||||||
updateList();
|
updateList();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,5 +1,6 @@
|
|||||||
#include "Tactility/hal/Device.h"
|
#include <Tactility/hal/Device.h>
|
||||||
|
|
||||||
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/RecursiveMutex.h>
|
#include <Tactility/RecursiveMutex.h>
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
|
|
||||||
@ -9,7 +10,7 @@ std::vector<std::shared_ptr<Device>> devices;
|
|||||||
RecursiveMutex mutex;
|
RecursiveMutex mutex;
|
||||||
static Device::Id nextId = 0;
|
static Device::Id nextId = 0;
|
||||||
|
|
||||||
#define TAG "devices"
|
constexpr auto TAG = "devices";
|
||||||
|
|
||||||
Device::Device() : id(nextId++) {}
|
Device::Device() : id(nextId++) {}
|
||||||
|
|
||||||
|
|||||||
@ -1,7 +1,9 @@
|
|||||||
#include "Tactility/hal/gps/GpsDevice.h"
|
#include <Tactility/hal/gps/GpsDevice.h>
|
||||||
#include "Tactility/hal/gps/GpsInit.h"
|
#include <Tactility/hal/gps/GpsInit.h>
|
||||||
#include "Tactility/hal/gps/Probe.h"
|
#include <Tactility/hal/gps/Probe.h>
|
||||||
#include "Tactility/hal/uart/Uart.h"
|
#include <Tactility/hal/uart/Uart.h>
|
||||||
|
#include <Tactility/Log.h>
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
#include <minmea.h>
|
#include <minmea.h>
|
||||||
|
|
||||||
|
|||||||
@ -1,12 +1,16 @@
|
|||||||
#include "Tactility/hal/gps/Cas.h"
|
#include <Tactility/Check.h>
|
||||||
#include "Tactility/hal/gps/GpsDevice.h"
|
#include <Tactility/hal/gps/Cas.h>
|
||||||
#include "Tactility/hal/gps/Ublox.h"
|
#include <Tactility/hal/gps/GpsDevice.h>
|
||||||
|
#include <Tactility/hal/gps/Ublox.h>
|
||||||
|
#include <Tactility/kernel/Kernel.h>
|
||||||
|
#include <Tactility/Log.h>
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
|
|
||||||
#define TAG "gps"
|
|
||||||
|
|
||||||
namespace tt::hal::gps {
|
namespace tt::hal::gps {
|
||||||
|
|
||||||
|
constexpr auto TAG = "gps";
|
||||||
|
|
||||||
bool initMtk(uart::Uart& uart);
|
bool initMtk(uart::Uart& uart);
|
||||||
bool initMtkL76b(uart::Uart& uart);
|
bool initMtkL76b(uart::Uart& uart);
|
||||||
bool initMtkPa1616s(uart::Uart& uart);
|
bool initMtkPa1616s(uart::Uart& uart);
|
||||||
|
|||||||
@ -1,12 +1,14 @@
|
|||||||
#include "Tactility/hal/gps/Satellites.h"
|
#include <Tactility/hal/gps/Satellites.h>
|
||||||
|
#include <Tactility/kernel/Kernel.h>
|
||||||
|
#include <Tactility/Log.h>
|
||||||
|
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
|
|
||||||
#define TAG "satellites"
|
|
||||||
|
|
||||||
namespace tt::hal::gps {
|
namespace tt::hal::gps {
|
||||||
|
|
||||||
constexpr inline bool hasTimeElapsed(TickType_t now, TickType_t timeInThePast, TickType_t expireTimeInTicks) {
|
constexpr auto TAG = "Satellites";
|
||||||
|
|
||||||
|
constexpr bool hasTimeElapsed(TickType_t now, TickType_t timeInThePast, TickType_t expireTimeInTicks) {
|
||||||
return (TickType_t)(now - timeInThePast) >= expireTimeInTicks;
|
return (TickType_t)(now - timeInThePast) >= expireTimeInTicks;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -45,7 +47,7 @@ SatelliteStorage::SatelliteRecord* SatelliteStorage::findRecordToRecycle() {
|
|||||||
lock.lock();
|
lock.lock();
|
||||||
|
|
||||||
int candidate_index = -1;
|
int candidate_index = -1;
|
||||||
auto candidate_age = portMAX_DELAY;
|
auto candidate_age = kernel::MAX_TICKS;
|
||||||
TickType_t expire_duration = kernel::secondsToTicks(recycleTimeSeconds);
|
TickType_t expire_duration = kernel::secondsToTicks(recycleTimeSeconds);
|
||||||
TickType_t now = kernel::getTicks();
|
TickType_t now = kernel::getTicks();
|
||||||
for (int i = 0; i < records.size(); ++i) {
|
for (int i = 0; i < records.size(); ++i) {
|
||||||
|
|||||||
@ -1,12 +1,15 @@
|
|||||||
#include "Tactility/hal/gps/Ublox.h"
|
#include <Tactility/hal/gps/Ublox.h>
|
||||||
#include "Tactility/hal/gps/UbloxMessages.h"
|
#include <Tactility/hal/gps/UbloxMessages.h>
|
||||||
#include "Tactility/hal/uart/Uart.h"
|
#include <Tactility/hal/uart/Uart.h>
|
||||||
|
#include <Tactility/kernel/Kernel.h>
|
||||||
|
#include <Tactility/Log.h>
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
|
|
||||||
#define TAG "ublox"
|
|
||||||
|
|
||||||
namespace tt::hal::gps::ublox {
|
namespace tt::hal::gps::ublox {
|
||||||
|
|
||||||
|
constexpr auto TAG = "ublox";
|
||||||
|
|
||||||
bool initUblox6(uart::Uart& uart);
|
bool initUblox6(uart::Uart& uart);
|
||||||
bool initUblox789(uart::Uart& uart, GpsModel model);
|
bool initUblox789(uart::Uart& uart, GpsModel model);
|
||||||
bool initUblox10(uart::Uart& uart);
|
bool initUblox10(uart::Uart& uart);
|
||||||
|
|||||||
@ -2,15 +2,12 @@
|
|||||||
|
|
||||||
#include <Tactility/Log.h>
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/Mutex.h>
|
#include <Tactility/Mutex.h>
|
||||||
|
#include <Tactility/Check.h>
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include <esp_check.h>
|
|
||||||
#endif // ESP_PLATFORM
|
|
||||||
|
|
||||||
#define TAG "i2c"
|
|
||||||
|
|
||||||
namespace tt::hal::i2c {
|
namespace tt::hal::i2c {
|
||||||
|
|
||||||
|
constexpr auto TAG = "i2c";
|
||||||
|
|
||||||
struct Data {
|
struct Data {
|
||||||
Mutex mutex;
|
Mutex mutex;
|
||||||
bool isConfigured = false;
|
bool isConfigured = false;
|
||||||
|
|||||||
@ -1,5 +1,6 @@
|
|||||||
#include "Tactility/hal/spi/Spi.h"
|
#include <Tactility/hal/spi/Spi.h>
|
||||||
|
|
||||||
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/RecursiveMutex.h>
|
#include <Tactility/RecursiveMutex.h>
|
||||||
|
|
||||||
namespace tt::hal::spi {
|
namespace tt::hal::spi {
|
||||||
|
|||||||
@ -1,17 +1,18 @@
|
|||||||
#ifdef ESP_PLATFORM
|
#ifdef ESP_PLATFORM
|
||||||
|
|
||||||
#include "Tactility/hal/uart/UartEsp.h"
|
#include <Tactility/hal/uart/UartEsp.h>
|
||||||
|
|
||||||
#include <Tactility/Log.h>
|
#include <Tactility/Log.h>
|
||||||
|
#include <Tactility/kernel/Kernel.h>
|
||||||
#include <Tactility/Mutex.h>
|
#include <Tactility/Mutex.h>
|
||||||
|
|
||||||
#include <sstream>
|
|
||||||
#include <esp_check.h>
|
#include <esp_check.h>
|
||||||
|
#include <sstream>
|
||||||
#define TAG "uart"
|
|
||||||
|
|
||||||
namespace tt::hal::uart {
|
namespace tt::hal::uart {
|
||||||
|
|
||||||
|
constexpr auto TAG = "uart";
|
||||||
|
|
||||||
bool UartEsp::start() {
|
bool UartEsp::start() {
|
||||||
TT_LOG_I(TAG, "[%s] Starting", configuration.name.c_str());
|
TT_LOG_I(TAG, "[%s] Starting", configuration.name.c_str());
|
||||||
|
|
||||||
|
|||||||
@ -1,8 +1,8 @@
|
|||||||
#ifndef ESP_PLATFORM
|
#ifndef ESP_PLATFORM
|
||||||
|
|
||||||
#include "Tactility/hal/uart/UartPosix.h"
|
#include <Tactility/hal/uart/UartPosix.h>
|
||||||
#include "Tactility/hal/uart/Uart.h"
|
#include <Tactility/hal/uart/Uart.h>
|
||||||
|
#include <Tactility/kernel/Kernel.h>
|
||||||
#include <Tactility/Log.h>
|
#include <Tactility/Log.h>
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
@ -10,10 +10,10 @@
|
|||||||
#include <sys/ioctl.h>
|
#include <sys/ioctl.h>
|
||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
|
|
||||||
#define TAG "uart"
|
|
||||||
|
|
||||||
namespace tt::hal::uart {
|
namespace tt::hal::uart {
|
||||||
|
|
||||||
|
constexpr auto TAG = "uart";
|
||||||
|
|
||||||
bool UartPosix::start() {
|
bool UartPosix::start() {
|
||||||
auto lock = mutex.asScopedLock();
|
auto lock = mutex.asScopedLock();
|
||||||
lock.lock();
|
lock.lock();
|
||||||
|
|||||||
@ -1,6 +1,9 @@
|
|||||||
#include "Tactility/kernel/SystemEvents.h"
|
#include <Tactility/kernel/SystemEvents.h>
|
||||||
|
|
||||||
|
#include <Tactility/Check.h>
|
||||||
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/Mutex.h>
|
#include <Tactility/Mutex.h>
|
||||||
|
|
||||||
#include <list>
|
#include <list>
|
||||||
|
|
||||||
namespace tt::kernel {
|
namespace tt::kernel {
|
||||||
@ -56,7 +59,7 @@ static const char* getEventName(SystemEvent event) {
|
|||||||
void publishSystemEvent(SystemEvent event) {
|
void publishSystemEvent(SystemEvent event) {
|
||||||
TT_LOG_I(TAG, "%s", getEventName(event));
|
TT_LOG_I(TAG, "%s", getEventName(event));
|
||||||
|
|
||||||
if (mutex.lock(portMAX_DELAY)) {
|
if (mutex.lock(kernel::MAX_TICKS)) {
|
||||||
for (auto& subscription : subscriptions) {
|
for (auto& subscription : subscriptions) {
|
||||||
if (subscription.event == event) {
|
if (subscription.event == event) {
|
||||||
subscription.handler(event);
|
subscription.handler(event);
|
||||||
@ -68,7 +71,7 @@ void publishSystemEvent(SystemEvent event) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
SystemEventSubscription subscribeSystemEvent(SystemEvent event, OnSystemEvent handler) {
|
SystemEventSubscription subscribeSystemEvent(SystemEvent event, OnSystemEvent handler) {
|
||||||
if (mutex.lock(portMAX_DELAY)) {
|
if (mutex.lock(kernel::MAX_TICKS)) {
|
||||||
auto id = ++subscriptionCounter;
|
auto id = ++subscriptionCounter;
|
||||||
|
|
||||||
subscriptions.push_back({
|
subscriptions.push_back({
|
||||||
@ -85,7 +88,7 @@ SystemEventSubscription subscribeSystemEvent(SystemEvent event, OnSystemEvent ha
|
|||||||
}
|
}
|
||||||
|
|
||||||
void unsubscribeSystemEvent(SystemEventSubscription subscription) {
|
void unsubscribeSystemEvent(SystemEventSubscription subscription) {
|
||||||
if (mutex.lock(portMAX_DELAY)) {
|
if (mutex.lock(kernel::MAX_TICKS)) {
|
||||||
std::erase_if(subscriptions, [subscription](auto& item) {
|
std::erase_if(subscriptions, [subscription](auto& item) {
|
||||||
return (item.id == subscription);
|
return (item.id == subscription);
|
||||||
});
|
});
|
||||||
|
|||||||
@ -1,9 +1,12 @@
|
|||||||
#ifdef ESP_PLATFORM
|
#ifdef ESP_PLATFORM
|
||||||
|
|
||||||
#include <Tactility/lvgl/LvglSync.h>
|
#include <Tactility/Thread.h>
|
||||||
#include <esp_lvgl_port.h>
|
|
||||||
#include <Tactility/CpuAffinity.h>
|
#include <Tactility/CpuAffinity.h>
|
||||||
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/Mutex.h>
|
#include <Tactility/Mutex.h>
|
||||||
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
|
|
||||||
|
#include <esp_lvgl_port.h>
|
||||||
|
|
||||||
// LVGL
|
// LVGL
|
||||||
// The minimum task stack seems to be about 3500, but that crashes the wifi app in some scenarios
|
// The minimum task stack seems to be about 3500, but that crashes the wifi app in some scenarios
|
||||||
|
|||||||
@ -22,14 +22,14 @@ void syncSet(LvglLock lock, LvglUnlock unlock) {
|
|||||||
auto old_unlock = unlock_singleton;
|
auto old_unlock = unlock_singleton;
|
||||||
|
|
||||||
// Ensure the old lock is not engaged when changing locks
|
// Ensure the old lock is not engaged when changing locks
|
||||||
old_lock((uint32_t)portMAX_DELAY);
|
old_lock((uint32_t)kernel::MAX_TICKS);
|
||||||
lock_singleton = lock;
|
lock_singleton = lock;
|
||||||
unlock_singleton = unlock;
|
unlock_singleton = unlock;
|
||||||
old_unlock();
|
old_unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool lock(TickType_t timeout) {
|
bool lock(TickType_t timeout) {
|
||||||
return lock_singleton(pdMS_TO_TICKS(timeout == 0 ? portMAX_DELAY : timeout));
|
return lock_singleton(pdMS_TO_TICKS(timeout == 0 ? kernel::MAX_TICKS : timeout));
|
||||||
}
|
}
|
||||||
|
|
||||||
void unlock() {
|
void unlock() {
|
||||||
@ -44,9 +44,8 @@ public:
|
|||||||
return lvgl::lock(timeoutTicks);
|
return lvgl::lock(timeoutTicks);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool unlock() const override {
|
void unlock() const override {
|
||||||
lvgl::unlock();
|
lvgl::unlock();
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@ -3,14 +3,14 @@
|
|||||||
#include <Tactility/Tactility.h>
|
#include <Tactility/Tactility.h>
|
||||||
#include <Tactility/TactilityCore.h>
|
#include <Tactility/TactilityCore.h>
|
||||||
|
|
||||||
|
#include <Tactility/PubSub.h>
|
||||||
|
#include <Tactility/Timer.h>
|
||||||
|
#include <Tactility/RecursiveMutex.h>
|
||||||
#include <Tactility/kernel/SystemEvents.h>
|
#include <Tactility/kernel/SystemEvents.h>
|
||||||
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
#include <Tactility/lvgl/Statusbar.h>
|
#include <Tactility/lvgl/Statusbar.h>
|
||||||
#include <Tactility/lvgl/Style.h>
|
#include <Tactility/lvgl/Style.h>
|
||||||
#include <Tactility/lvgl/LvglSync.h>
|
|
||||||
#include <Tactility/PubSub.h>
|
|
||||||
#include <Tactility/RecursiveMutex.h>
|
|
||||||
#include <Tactility/settings/Time.h>
|
#include <Tactility/settings/Time.h>
|
||||||
#include <Tactility/Timer.h>
|
|
||||||
|
|
||||||
#include <lvgl.h>
|
#include <lvgl.h>
|
||||||
|
|
||||||
@ -30,7 +30,7 @@ struct StatusbarData {
|
|||||||
RecursiveMutex mutex;
|
RecursiveMutex mutex;
|
||||||
std::shared_ptr<PubSub<void*>> pubsub = std::make_shared<PubSub<void*>>();
|
std::shared_ptr<PubSub<void*>> pubsub = std::make_shared<PubSub<void*>>();
|
||||||
StatusbarIcon icons[STATUSBAR_ICON_LIMIT] = {};
|
StatusbarIcon icons[STATUSBAR_ICON_LIMIT] = {};
|
||||||
Timer* time_update_timer = new Timer(Timer::Type::Once, [] { onUpdateTime(); });
|
Timer* time_update_timer = new Timer(Timer::Type::Once, 200 / portTICK_PERIOD_MS, [] { onUpdateTime(); });
|
||||||
uint8_t time_hours = 0;
|
uint8_t time_hours = 0;
|
||||||
uint8_t time_minutes = 0;
|
uint8_t time_minutes = 0;
|
||||||
bool time_set = false;
|
bool time_set = false;
|
||||||
@ -73,12 +73,12 @@ static void onUpdateTime() {
|
|||||||
statusbar_data.time_set = true;
|
statusbar_data.time_set = true;
|
||||||
|
|
||||||
// Reschedule
|
// Reschedule
|
||||||
statusbar_data.time_update_timer->start(getNextUpdateTime());
|
statusbar_data.time_update_timer->reset(getNextUpdateTime());
|
||||||
|
|
||||||
// Notify widget
|
// Notify widget
|
||||||
statusbar_data.pubsub->publish(nullptr);
|
statusbar_data.pubsub->publish(nullptr);
|
||||||
} else {
|
} else {
|
||||||
statusbar_data.time_update_timer->start(pdMS_TO_TICKS(60000U));
|
statusbar_data.time_update_timer->reset(pdMS_TO_TICKS(60000U));
|
||||||
}
|
}
|
||||||
|
|
||||||
statusbar_data.mutex.unlock();
|
statusbar_data.mutex.unlock();
|
||||||
@ -113,9 +113,7 @@ static void statusbar_pubsub_event(Statusbar* statusbar) {
|
|||||||
|
|
||||||
static void onTimeChanged(TT_UNUSED kernel::SystemEvent event) {
|
static void onTimeChanged(TT_UNUSED kernel::SystemEvent event) {
|
||||||
if (statusbar_data.mutex.lock()) {
|
if (statusbar_data.mutex.lock()) {
|
||||||
statusbar_data.time_update_timer->stop();
|
statusbar_data.time_update_timer->reset(5);
|
||||||
statusbar_data.time_update_timer->start(5);
|
|
||||||
|
|
||||||
statusbar_data.mutex.unlock();
|
statusbar_data.mutex.unlock();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -131,7 +129,7 @@ static void statusbar_constructor(const lv_obj_class_t* class_p, lv_obj_t* obj)
|
|||||||
});
|
});
|
||||||
|
|
||||||
if (!statusbar_data.time_update_timer->isRunning()) {
|
if (!statusbar_data.time_update_timer->isRunning()) {
|
||||||
statusbar_data.time_update_timer->start(200 / portTICK_PERIOD_MS);
|
statusbar_data.time_update_timer->start();
|
||||||
statusbar_data.systemEventSubscription = kernel::subscribeSystemEvent(
|
statusbar_data.systemEventSubscription = kernel::subscribeSystemEvent(
|
||||||
kernel::SystemEvent::Time,
|
kernel::SystemEvent::Time,
|
||||||
onTimeChanged
|
onTimeChanged
|
||||||
@ -177,7 +175,7 @@ lv_obj_t* statusbar_create(lv_obj_t* parent) {
|
|||||||
obj_set_style_bg_invisible(left_spacer);
|
obj_set_style_bg_invisible(left_spacer);
|
||||||
lv_obj_set_flex_grow(left_spacer, 1);
|
lv_obj_set_flex_grow(left_spacer, 1);
|
||||||
|
|
||||||
statusbar_data.mutex.lock(portMAX_DELAY);
|
statusbar_data.mutex.lock(kernel::MAX_TICKS);
|
||||||
for (int i = 0; i < STATUSBAR_ICON_LIMIT; ++i) {
|
for (int i = 0; i < STATUSBAR_ICON_LIMIT; ++i) {
|
||||||
auto* image = lv_image_create(obj);
|
auto* image = lv_image_create(obj);
|
||||||
lv_obj_set_size(image, STATUSBAR_ICON_SIZE, STATUSBAR_ICON_SIZE);
|
lv_obj_set_size(image, STATUSBAR_ICON_SIZE, STATUSBAR_ICON_SIZE);
|
||||||
|
|||||||
@ -31,6 +31,7 @@ void download(
|
|||||||
|
|
||||||
auto certificate_length = strlen(reinterpret_cast<const char*>(certificate.get())) + 1;
|
auto certificate_length = strlen(reinterpret_cast<const char*>(certificate.get())) + 1;
|
||||||
|
|
||||||
|
// TODO: Fix for missing initializer warnings
|
||||||
auto config = std::make_unique<esp_http_client_config_t>(esp_http_client_config_t {
|
auto config = std::make_unique<esp_http_client_config_t>(esp_http_client_config_t {
|
||||||
.url = url.c_str(),
|
.url = url.c_str(),
|
||||||
.auth_type = HTTP_AUTH_TYPE_NONE,
|
.auth_type = HTTP_AUTH_TYPE_NONE,
|
||||||
|
|||||||
@ -1,6 +1,8 @@
|
|||||||
#ifdef ESP_PLATFORM
|
#ifdef ESP_PLATFORM
|
||||||
|
|
||||||
#include <Tactility/network/HttpServer.h>
|
#include <Tactility/network/HttpServer.h>
|
||||||
|
|
||||||
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/service/wifi/Wifi.h>
|
#include <Tactility/service/wifi/Wifi.h>
|
||||||
|
|
||||||
namespace tt::network {
|
namespace tt::network {
|
||||||
|
|||||||
@ -1,10 +1,10 @@
|
|||||||
#include <Tactility/service/ServiceRegistration.h>
|
#include <Tactility/service/ServiceRegistration.h>
|
||||||
|
|
||||||
|
#include <Tactility/Log.h>
|
||||||
|
#include <Tactility/Mutex.h>
|
||||||
#include <Tactility/service/ServiceInstance.h>
|
#include <Tactility/service/ServiceInstance.h>
|
||||||
#include <Tactility/service/ServiceManifest.h>
|
#include <Tactility/service/ServiceManifest.h>
|
||||||
|
|
||||||
#include <Tactility/Mutex.h>
|
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
namespace tt::service {
|
namespace tt::service {
|
||||||
|
|||||||
@ -4,9 +4,10 @@
|
|||||||
|
|
||||||
#ifdef CONFIG_ESP_WIFI_ENABLED
|
#ifdef CONFIG_ESP_WIFI_ENABLED
|
||||||
|
|
||||||
#include "Tactility/service/espnow/EspNow.h"
|
#include <Tactility/kernel/Kernel.h>
|
||||||
#include "Tactility/service/wifi/Wifi.h"
|
|
||||||
#include <Tactility/Log.h>
|
#include <Tactility/Log.h>
|
||||||
|
#include <Tactility/service/espnow/EspNow.h>
|
||||||
|
#include <Tactility/service/wifi/Wifi.h>
|
||||||
|
|
||||||
#include <esp_now.h>
|
#include <esp_now.h>
|
||||||
#include <esp_wifi.h>
|
#include <esp_wifi.h>
|
||||||
|
|||||||
@ -25,27 +25,30 @@ void GuiService::onLoaderEvent(LoaderService::Event event) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
int32_t GuiService::guiMain() {
|
int32_t GuiService::guiMain() {
|
||||||
|
auto service = findServiceById<GuiService>(manifest.id);
|
||||||
|
|
||||||
while (true) {
|
while (true) {
|
||||||
uint32_t flags = Thread::awaitFlags(GUI_THREAD_FLAG_ALL, EventFlag::WaitAny, portMAX_DELAY);
|
uint32_t flags = 0;
|
||||||
|
if (service->threadFlags.wait(GUI_THREAD_FLAG_ALL, false, true, portMAX_DELAY, &flags)) {
|
||||||
// When service not started or starting -> exit
|
// When service not started or starting -> exit
|
||||||
State service_state = getState(manifest.id);
|
State service_state = getState(manifest.id);
|
||||||
if (service_state != State::Started && service_state != State::Starting) {
|
if (service_state != State::Started && service_state != State::Starting) {
|
||||||
break;
|
break;
|
||||||
}
|
|
||||||
|
|
||||||
// Process and dispatch draw call
|
|
||||||
if (flags & GUI_THREAD_FLAG_DRAW) {
|
|
||||||
Thread::clearFlags(GUI_THREAD_FLAG_DRAW);
|
|
||||||
auto service = findService();
|
|
||||||
if (service != nullptr) {
|
|
||||||
service->redraw();
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
if (flags & GUI_THREAD_FLAG_EXIT) {
|
// Process and dispatch draw call
|
||||||
Thread::clearFlags(GUI_THREAD_FLAG_EXIT);
|
if (flags & GUI_THREAD_FLAG_DRAW) {
|
||||||
break;
|
service->threadFlags.clear(GUI_THREAD_FLAG_DRAW);
|
||||||
|
auto service = findService();
|
||||||
|
if (service != nullptr) {
|
||||||
|
service->redraw();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (flags & GUI_THREAD_FLAG_EXIT) {
|
||||||
|
service->threadFlags.clear(GUI_THREAD_FLAG_EXIT);
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -177,8 +180,8 @@ void GuiService::onStop(TT_UNUSED ServiceContext& service) {
|
|||||||
appToRender = nullptr;
|
appToRender = nullptr;
|
||||||
isStarted = false;
|
isStarted = false;
|
||||||
|
|
||||||
ThreadId thread_id = thread->getId();
|
auto task_handle = thread->getTaskHandle();
|
||||||
Thread::setFlags(thread_id, GUI_THREAD_FLAG_EXIT);
|
threadFlags.set(GUI_THREAD_FLAG_EXIT);
|
||||||
thread->join();
|
thread->join();
|
||||||
delete thread;
|
delete thread;
|
||||||
|
|
||||||
@ -190,8 +193,8 @@ void GuiService::onStop(TT_UNUSED ServiceContext& service) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
void GuiService::requestDraw() {
|
void GuiService::requestDraw() {
|
||||||
ThreadId thread_id = thread->getId();
|
auto task_handle = thread->getTaskHandle();
|
||||||
Thread::setFlags(thread_id, GUI_THREAD_FLAG_DRAW);
|
threadFlags.set(GUI_THREAD_FLAG_DRAW);
|
||||||
}
|
}
|
||||||
|
|
||||||
void GuiService::showApp(std::shared_ptr<app::AppInstance> app) {
|
void GuiService::showApp(std::shared_ptr<app::AppInstance> app) {
|
||||||
|
|||||||
@ -8,7 +8,6 @@
|
|||||||
namespace tt::service::memorychecker {
|
namespace tt::service::memorychecker {
|
||||||
|
|
||||||
constexpr const char* TAG = "MemoryChecker";
|
constexpr const char* TAG = "MemoryChecker";
|
||||||
constexpr TickType_t TIMER_UPDATE_INTERVAL = 1000U / portTICK_PERIOD_MS;
|
|
||||||
|
|
||||||
// Total memory (in bytes) that should be free before warnings occur
|
// Total memory (in bytes) that should be free before warnings occur
|
||||||
constexpr auto TOTAL_FREE_THRESHOLD = 10'000;
|
constexpr auto TOTAL_FREE_THRESHOLD = 10'000;
|
||||||
@ -58,8 +57,8 @@ bool MemoryCheckerService::onStart(ServiceContext& service) {
|
|||||||
statusbarIconId = lvgl::statusbar_icon_add(icon_path, false);
|
statusbarIconId = lvgl::statusbar_icon_add(icon_path, false);
|
||||||
lvgl::statusbar_icon_set_visibility(statusbarIconId, false);
|
lvgl::statusbar_icon_set_visibility(statusbarIconId, false);
|
||||||
|
|
||||||
timer.setThreadPriority(Thread::Priority::Lower);
|
timer.setCallbackPriority(Thread::Priority::Lower);
|
||||||
timer.start(TIMER_UPDATE_INTERVAL);
|
timer.start();
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -2,11 +2,13 @@
|
|||||||
|
|
||||||
#if TT_FEATURE_SCREENSHOT_ENABLED
|
#if TT_FEATURE_SCREENSHOT_ENABLED
|
||||||
|
|
||||||
|
#include <Tactility/Log.h>
|
||||||
|
#include <Tactility/LogMessages.h>
|
||||||
#include <Tactility/service/screenshot/Screenshot.h>
|
#include <Tactility/service/screenshot/Screenshot.h>
|
||||||
#include <Tactility/service/ServiceRegistration.h>
|
#include <Tactility/service/ServiceRegistration.h>
|
||||||
|
|
||||||
#include <memory>
|
|
||||||
#include <lvgl.h>
|
#include <lvgl.h>
|
||||||
|
#include <memory>
|
||||||
|
|
||||||
namespace tt::service::screenshot {
|
namespace tt::service::screenshot {
|
||||||
|
|
||||||
|
|||||||
@ -159,7 +159,7 @@ void ScreenshotTask::stop() {
|
|||||||
if (thread != nullptr) {
|
if (thread != nullptr) {
|
||||||
if (mutex.lock(50 / portTICK_PERIOD_MS)) {
|
if (mutex.lock(50 / portTICK_PERIOD_MS)) {
|
||||||
interrupted = true;
|
interrupted = true;
|
||||||
tt_check(mutex.unlock());
|
mutex.unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
thread->join();
|
thread->join();
|
||||||
@ -167,7 +167,7 @@ void ScreenshotTask::stop() {
|
|||||||
if (mutex.lock(50 / portTICK_PERIOD_MS)) {
|
if (mutex.lock(50 / portTICK_PERIOD_MS)) {
|
||||||
delete thread;
|
delete thread;
|
||||||
thread = nullptr;
|
thread = nullptr;
|
||||||
tt_check(mutex.unlock());
|
mutex.unlock();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,9 +1,9 @@
|
|||||||
#include <Tactility/service/ServiceContext.h>
|
#include <Tactility/service/ServiceContext.h>
|
||||||
#include <Tactility/service/ServiceRegistration.h>
|
#include <Tactility/service/ServiceRegistration.h>
|
||||||
|
|
||||||
|
#include <Tactility/Timer.h>
|
||||||
#include <Tactility/Mutex.h>
|
#include <Tactility/Mutex.h>
|
||||||
#include <Tactility/Tactility.h>
|
#include <Tactility/Tactility.h>
|
||||||
#include <Tactility/Timer.h>
|
|
||||||
#include <Tactility/hal/sdcard/SdCardDevice.h>
|
#include <Tactility/hal/sdcard/SdCardDevice.h>
|
||||||
|
|
||||||
namespace tt::service::sdcard {
|
namespace tt::service::sdcard {
|
||||||
@ -60,12 +60,12 @@ public:
|
|||||||
}
|
}
|
||||||
|
|
||||||
auto service = findServiceById<SdCardService>(manifest.id);
|
auto service = findServiceById<SdCardService>(manifest.id);
|
||||||
updateTimer = std::make_unique<Timer>(Timer::Type::Periodic, [service]() {
|
updateTimer = std::make_unique<Timer>(Timer::Type::Periodic, 1000, [service] {
|
||||||
service->update();
|
service->update();
|
||||||
});
|
});
|
||||||
|
|
||||||
// We want to try and scan more often in case of startup or scan lock failure
|
// We want to try and scan more often in case of startup or scan lock failure
|
||||||
updateTimer->start(1000);
|
updateTimer->start();
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,16 +1,16 @@
|
|||||||
#include <Tactility/lvgl/Statusbar.h>
|
#include <Tactility/lvgl/Statusbar.h>
|
||||||
|
|
||||||
|
#include <Tactility/Timer.h>
|
||||||
|
#include <Tactility/Mutex.h>
|
||||||
#include <Tactility/hal/power/PowerDevice.h>
|
#include <Tactility/hal/power/PowerDevice.h>
|
||||||
#include <Tactility/hal/sdcard/SdCardDevice.h>
|
#include <Tactility/hal/sdcard/SdCardDevice.h>
|
||||||
#include <Tactility/lvgl/Lvgl.h>
|
#include <Tactility/lvgl/Lvgl.h>
|
||||||
#include <Tactility/lvgl/LvglSync.h>
|
#include <Tactility/lvgl/LvglSync.h>
|
||||||
#include <Tactility/Mutex.h>
|
|
||||||
#include <Tactility/service/gps/GpsService.h>
|
|
||||||
#include <Tactility/service/ServiceContext.h>
|
#include <Tactility/service/ServiceContext.h>
|
||||||
#include <Tactility/service/ServicePaths.h>
|
#include <Tactility/service/ServicePaths.h>
|
||||||
#include <Tactility/service/ServiceRegistration.h>
|
#include <Tactility/service/ServiceRegistration.h>
|
||||||
|
#include <Tactility/service/gps/GpsService.h>
|
||||||
#include <Tactility/service/wifi/Wifi.h>
|
#include <Tactility/service/wifi/Wifi.h>
|
||||||
#include <Tactility/Timer.h>
|
|
||||||
|
|
||||||
namespace tt::service::statusbar {
|
namespace tt::service::statusbar {
|
||||||
|
|
||||||
@ -265,14 +265,14 @@ public:
|
|||||||
assert(service);
|
assert(service);
|
||||||
service->update();
|
service->update();
|
||||||
|
|
||||||
updateTimer = std::make_unique<Timer>(Timer::Type::Periodic, [service] {
|
updateTimer = std::make_unique<Timer>(Timer::Type::Periodic, pdMS_TO_TICKS(1000), [service] {
|
||||||
service->update();
|
service->update();
|
||||||
});
|
});
|
||||||
|
|
||||||
updateTimer->setThreadPriority(Thread::Priority::Lower);
|
updateTimer->setCallbackPriority(Thread::Priority::Lower);
|
||||||
|
|
||||||
// We want to try and scan more often in case of startup or scan lock failure
|
// We want to try and scan more often in case of startup or scan lock failure
|
||||||
updateTimer->start(1000);
|
updateTimer->start();
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,5 +1,6 @@
|
|||||||
#include "Tactility/service/wifi/Wifi.h"
|
#include <Tactility/service/wifi/Wifi.h>
|
||||||
|
|
||||||
|
#include <Tactility/Check.h>
|
||||||
#include <Tactility/service/ServiceManifest.h>
|
#include <Tactility/service/ServiceManifest.h>
|
||||||
#include <Tactility/service/ServiceRegistration.h>
|
#include <Tactility/service/ServiceRegistration.h>
|
||||||
|
|
||||||
|
|||||||
@ -6,15 +6,15 @@
|
|||||||
|
|
||||||
#include <Tactility/service/wifi/Wifi.h>
|
#include <Tactility/service/wifi/Wifi.h>
|
||||||
|
|
||||||
#include <Tactility/EventFlag.h>
|
#include <Tactility/Timer.h>
|
||||||
|
#include <Tactility/EventGroup.h>
|
||||||
|
#include <Tactility/RecursiveMutex.h>
|
||||||
#include <Tactility/Tactility.h>
|
#include <Tactility/Tactility.h>
|
||||||
#include <Tactility/kernel/SystemEvents.h>
|
#include <Tactility/kernel/SystemEvents.h>
|
||||||
#include <Tactility/RecursiveMutex.h>
|
|
||||||
#include <Tactility/service/ServiceContext.h>
|
#include <Tactility/service/ServiceContext.h>
|
||||||
|
#include <Tactility/service/wifi/WifiBootSplashInit.h>
|
||||||
#include <Tactility/service/wifi/WifiGlobals.h>
|
#include <Tactility/service/wifi/WifiGlobals.h>
|
||||||
#include <Tactility/service/wifi/WifiSettings.h>
|
#include <Tactility/service/wifi/WifiSettings.h>
|
||||||
#include <Tactility/service/wifi/WifiBootSplashInit.h>
|
|
||||||
#include <Tactility/Timer.h>
|
|
||||||
|
|
||||||
#include <lwip/esp_netif_net_stack.h>
|
#include <lwip/esp_netif_net_stack.h>
|
||||||
#include <freertos/FreeRTOS.h>
|
#include <freertos/FreeRTOS.h>
|
||||||
@ -66,10 +66,10 @@ public:
|
|||||||
/** @brief Maximum amount of records to scan (value > 0) */
|
/** @brief Maximum amount of records to scan (value > 0) */
|
||||||
uint16_t scan_list_limit = TT_WIFI_SCAN_RECORD_LIMIT;
|
uint16_t scan_list_limit = TT_WIFI_SCAN_RECORD_LIMIT;
|
||||||
/** @brief when we last requested a scan. Loops around every 50 days. */
|
/** @brief when we last requested a scan. Loops around every 50 days. */
|
||||||
TickType_t last_scan_time = portMAX_DELAY;
|
TickType_t last_scan_time = kernel::MAX_TICKS;
|
||||||
esp_event_handler_instance_t event_handler_any_id = nullptr;
|
esp_event_handler_instance_t event_handler_any_id = nullptr;
|
||||||
esp_event_handler_instance_t event_handler_got_ip = nullptr;
|
esp_event_handler_instance_t event_handler_got_ip = nullptr;
|
||||||
EventFlag connection_wait_flags;
|
EventGroup connection_wait_flags;
|
||||||
settings::WifiApSettings connection_target;
|
settings::WifiApSettings connection_target;
|
||||||
bool pause_auto_connect = false; // Pause when manually disconnecting until manually connecting again
|
bool pause_auto_connect = false; // Pause when manually disconnecting until manually connecting again
|
||||||
bool connection_target_remember = false; // Whether to store the connection_target on successful connection or not
|
bool connection_target_remember = false; // Whether to store the connection_target on successful connection or not
|
||||||
@ -792,32 +792,34 @@ static void dispatchConnect(std::shared_ptr<Wifi> wifi) {
|
|||||||
/* Waiting until either the connection is established (WIFI_CONNECTED_BIT)
|
/* Waiting until either the connection is established (WIFI_CONNECTED_BIT)
|
||||||
* or connection failed for the maximum number of re-tries (WIFI_FAIL_BIT).
|
* or connection failed for the maximum number of re-tries (WIFI_FAIL_BIT).
|
||||||
* The bits are set by wifi_event_handler() */
|
* The bits are set by wifi_event_handler() */
|
||||||
uint32_t bits = wifi_singleton->connection_wait_flags.wait(WIFI_FAIL_BIT | WIFI_CONNECTED_BIT);
|
uint32_t bits;
|
||||||
TT_LOG_I(TAG, "Waiting for EventFlag by event_handler()");
|
if (wifi_singleton->connection_wait_flags.wait(WIFI_FAIL_BIT | WIFI_CONNECTED_BIT, false, true, kernel::MAX_TICKS, &bits)) {
|
||||||
|
TT_LOG_I(TAG, "Waiting for EventGroup by event_handler()");
|
||||||
|
|
||||||
if (bits & WIFI_CONNECTED_BIT) {
|
if (bits & WIFI_CONNECTED_BIT) {
|
||||||
wifi->setSecureConnection(config.sta.password[0] != 0x00U);
|
wifi->setSecureConnection(config.sta.password[0] != 0x00U);
|
||||||
wifi->setRadioState(RadioState::ConnectionActive);
|
wifi->setRadioState(RadioState::ConnectionActive);
|
||||||
publish_event(wifi, WifiEvent::ConnectionSuccess);
|
publish_event(wifi, WifiEvent::ConnectionSuccess);
|
||||||
TT_LOG_I(TAG, "Connected to %s", wifi->connection_target.ssid.c_str());
|
TT_LOG_I(TAG, "Connected to %s", wifi->connection_target.ssid.c_str());
|
||||||
if (wifi->connection_target_remember) {
|
if (wifi->connection_target_remember) {
|
||||||
if (!settings::save(wifi->connection_target)) {
|
if (!settings::save(wifi->connection_target)) {
|
||||||
TT_LOG_E(TAG, "Failed to store credentials");
|
TT_LOG_E(TAG, "Failed to store credentials");
|
||||||
} else {
|
} else {
|
||||||
TT_LOG_I(TAG, "Stored credentials");
|
TT_LOG_I(TAG, "Stored credentials");
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
} else if (bits & WIFI_FAIL_BIT) {
|
||||||
|
wifi->setRadioState(RadioState::On);
|
||||||
|
publish_event(wifi, WifiEvent::ConnectionFailed);
|
||||||
|
TT_LOG_I(TAG, "Failed to connect to %s", wifi->connection_target.ssid.c_str());
|
||||||
|
} else {
|
||||||
|
wifi->setRadioState(RadioState::On);
|
||||||
|
publish_event(wifi, WifiEvent::ConnectionFailed);
|
||||||
|
TT_LOG_E(TAG, "UNEXPECTED EVENT");
|
||||||
}
|
}
|
||||||
} else if (bits & WIFI_FAIL_BIT) {
|
|
||||||
wifi->setRadioState(RadioState::On);
|
|
||||||
publish_event(wifi, WifiEvent::ConnectionFailed);
|
|
||||||
TT_LOG_I(TAG, "Failed to connect to %s", wifi->connection_target.ssid.c_str());
|
|
||||||
} else {
|
|
||||||
wifi->setRadioState(RadioState::On);
|
|
||||||
publish_event(wifi, WifiEvent::ConnectionFailed);
|
|
||||||
TT_LOG_E(TAG, "UNEXPECTED EVENT");
|
|
||||||
}
|
|
||||||
|
|
||||||
wifi_singleton->connection_wait_flags.clear(WIFI_FAIL_BIT | WIFI_CONNECTED_BIT);
|
wifi_singleton->connection_wait_flags.clear(WIFI_FAIL_BIT | WIFI_CONNECTED_BIT);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void dispatchDisconnectButKeepActive(std::shared_ptr<Wifi> wifi) {
|
static void dispatchDisconnectButKeepActive(std::shared_ptr<Wifi> wifi) {
|
||||||
@ -920,9 +922,10 @@ public:
|
|||||||
bootSplashInit();
|
bootSplashInit();
|
||||||
});
|
});
|
||||||
|
|
||||||
wifi_singleton->autoConnectTimer = std::make_unique<Timer>(Timer::Type::Periodic, []() { onAutoConnectTimer(); });
|
auto timer_interval = std::min(2000, AUTO_SCAN_INTERVAL);
|
||||||
|
wifi_singleton->autoConnectTimer = std::make_unique<Timer>(Timer::Type::Periodic, timer_interval, [] { onAutoConnectTimer(); });
|
||||||
// We want to try and scan more often in case of startup or scan lock failure
|
// We want to try and scan more often in case of startup or scan lock failure
|
||||||
wifi_singleton->autoConnectTimer->start(std::min(2000, AUTO_SCAN_INTERVAL));
|
wifi_singleton->autoConnectTimer->start();
|
||||||
|
|
||||||
if (settings::shouldEnableOnBoot()) {
|
if (settings::shouldEnableOnBoot()) {
|
||||||
TT_LOG_I(TAG, "Auto-enabling due to setting");
|
TT_LOG_I(TAG, "Auto-enabling due to setting");
|
||||||
|
|||||||
@ -2,9 +2,9 @@
|
|||||||
|
|
||||||
#include <Tactility/service/wifi/Wifi.h>
|
#include <Tactility/service/wifi/Wifi.h>
|
||||||
|
|
||||||
|
#include <Tactility/PubSub.h>
|
||||||
#include <Tactility/Check.h>
|
#include <Tactility/Check.h>
|
||||||
#include <Tactility/Log.h>
|
#include <Tactility/Log.h>
|
||||||
#include <Tactility/PubSub.h>
|
|
||||||
#include <Tactility/RecursiveMutex.h>
|
#include <Tactility/RecursiveMutex.h>
|
||||||
#include <Tactility/service/Service.h>
|
#include <Tactility/service/Service.h>
|
||||||
#include <Tactility/service/ServiceManifest.h>
|
#include <Tactility/service/ServiceManifest.h>
|
||||||
@ -81,26 +81,31 @@ std::vector<ApRecord> getScanResults() {
|
|||||||
records.push_back((ApRecord) {
|
records.push_back((ApRecord) {
|
||||||
.ssid = "Home Wifi",
|
.ssid = "Home Wifi",
|
||||||
.rssi = -30,
|
.rssi = -30,
|
||||||
|
.channel = 0,
|
||||||
.auth_mode = WIFI_AUTH_WPA2_PSK
|
.auth_mode = WIFI_AUTH_WPA2_PSK
|
||||||
});
|
});
|
||||||
records.push_back((ApRecord) {
|
records.push_back((ApRecord) {
|
||||||
.ssid = "No place like 127.0.0.1",
|
.ssid = "No place like 127.0.0.1",
|
||||||
.rssi = -67,
|
.rssi = -67,
|
||||||
|
.channel = 0,
|
||||||
.auth_mode = WIFI_AUTH_WPA2_PSK
|
.auth_mode = WIFI_AUTH_WPA2_PSK
|
||||||
});
|
});
|
||||||
records.push_back((ApRecord) {
|
records.push_back((ApRecord) {
|
||||||
.ssid = "Pretty fly for a Wi-Fi",
|
.ssid = "Pretty fly for a Wi-Fi",
|
||||||
.rssi = -70,
|
.rssi = -70,
|
||||||
|
.channel = 0,
|
||||||
.auth_mode = WIFI_AUTH_WPA2_PSK
|
.auth_mode = WIFI_AUTH_WPA2_PSK
|
||||||
});
|
});
|
||||||
records.push_back((ApRecord) {
|
records.push_back((ApRecord) {
|
||||||
.ssid = "An AP with a really, really long name",
|
.ssid = "An AP with a really, really long name",
|
||||||
.rssi = -80,
|
.rssi = -80,
|
||||||
|
.channel = 0,
|
||||||
.auth_mode = WIFI_AUTH_WPA2_PSK
|
.auth_mode = WIFI_AUTH_WPA2_PSK
|
||||||
});
|
});
|
||||||
records.push_back((ApRecord) {
|
records.push_back((ApRecord) {
|
||||||
.ssid = "Bad Reception",
|
.ssid = "Bad Reception",
|
||||||
.rssi = -90,
|
.rssi = -90,
|
||||||
|
.channel = 0,
|
||||||
.auth_mode = WIFI_AUTH_OPEN
|
.auth_mode = WIFI_AUTH_OPEN
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@ -103,9 +103,8 @@ bool tt_hal_i2c_lock(i2c_port_t port, TickType_t timeout);
|
|||||||
/**
|
/**
|
||||||
* Used to unlock an I2C port.
|
* Used to unlock an I2C port.
|
||||||
* This is useful for creating thread-safe I2C calls while calling ESP-IDF directly of third party I2C APIs.
|
* This is useful for creating thread-safe I2C calls while calling ESP-IDF directly of third party I2C APIs.
|
||||||
* @param[in] port the I2C port to unlock
|
|
||||||
*/
|
*/
|
||||||
bool tt_hal_i2c_unlock(i2c_port_t port);
|
void tt_hal_i2c_unlock(i2c_port_t port);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
|
|||||||
@ -1,8 +1,6 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdbool.h>
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
extern "C" {
|
extern "C" {
|
||||||
#endif
|
#endif
|
||||||
@ -11,43 +9,6 @@ typedef unsigned long TickType;
|
|||||||
|
|
||||||
#define TT_MAX_TICKS ((TickType)(~(TickType)0))
|
#define TT_MAX_TICKS ((TickType)(~(TickType)0))
|
||||||
|
|
||||||
/**
|
|
||||||
* Stall the current task for the specified amount of time.
|
|
||||||
* @param milliseconds the time in milliseconds to stall.
|
|
||||||
*/
|
|
||||||
void tt_kernel_delay_millis(uint32_t milliseconds);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Stall the current task for the specified amount of time.
|
|
||||||
* @param milliseconds the time in microsends to stall.
|
|
||||||
*/
|
|
||||||
void tt_kernel_delay_micros(uint32_t microSeconds);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Stall the current task for the specified amount of time.
|
|
||||||
* @param milliseconds the time in ticks to stall.
|
|
||||||
*/
|
|
||||||
void tt_kernel_delay_ticks(TickType ticks);
|
|
||||||
|
|
||||||
/** @return the number of ticks since the device was started */
|
|
||||||
TickType tt_kernel_get_ticks();
|
|
||||||
|
|
||||||
/** Convert milliseconds to ticks */
|
|
||||||
TickType tt_kernel_millis_to_ticks(uint32_t milliSeconds);
|
|
||||||
|
|
||||||
/** Stall the current task until the specified timestamp
|
|
||||||
* @return false if for some reason the delay was broken off
|
|
||||||
*/
|
|
||||||
bool tt_kernel_delay_until_tick(TickType tick);
|
|
||||||
|
|
||||||
/** @return the tick frequency of the kernel (commonly 1000 Hz when running FreeRTOS) */
|
|
||||||
uint32_t tt_kernel_get_tick_frequency();
|
|
||||||
|
|
||||||
/** @return the number of milliseconds that have passed since the device was started */
|
|
||||||
uint32_t tt_kernel_get_millis();
|
|
||||||
|
|
||||||
unsigned long tt_kernel_get_micros();
|
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
@ -41,9 +41,8 @@ bool tt_lock_acquire(LockHandle handle, TickType timeout);
|
|||||||
/**
|
/**
|
||||||
* Attempt to unlock the lock.
|
* Attempt to unlock the lock.
|
||||||
* @param[in] handle the handle that represents the mutex instance
|
* @param[in] handle the handle that represents the mutex instance
|
||||||
* @return true when the lock was unlocked
|
|
||||||
*/
|
*/
|
||||||
bool tt_lock_release(LockHandle handle);
|
void tt_lock_release(LockHandle handle);
|
||||||
|
|
||||||
/** Free the memory for this lock
|
/** Free the memory for this lock
|
||||||
* This does not auto-release the lock.
|
* This does not auto-release the lock.
|
||||||
|
|||||||
@ -41,23 +41,13 @@ bool tt_message_queue_put(MessageQueueHandle handle, const void* message, TickTy
|
|||||||
*/
|
*/
|
||||||
bool tt_message_queue_get(MessageQueueHandle handle, void* message, TickType_t timeout);
|
bool tt_message_queue_get(MessageQueueHandle handle, void* message, TickType_t timeout);
|
||||||
|
|
||||||
/** @return the total amount of messages that this queue can hold */
|
|
||||||
uint32_t tt_message_queue_get_capacity(MessageQueueHandle handle);
|
|
||||||
|
|
||||||
/** @return the size of a single message in the queue */
|
|
||||||
uint32_t tt_message_queue_get_message_size(MessageQueueHandle handle);
|
|
||||||
|
|
||||||
/** @return the current amount of items in the queue */
|
/** @return the current amount of items in the queue */
|
||||||
uint32_t tt_message_queue_get_count(MessageQueueHandle handle);
|
uint32_t tt_message_queue_get_count(MessageQueueHandle handle);
|
||||||
|
|
||||||
/** @return the remaining capacity in the queue */
|
|
||||||
uint32_t tt_message_queue_get_space(MessageQueueHandle handle);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Remove all items from the queue (if any)
|
* Remove all items from the queue (if any)
|
||||||
* @return true on failure
|
|
||||||
*/
|
*/
|
||||||
bool tt_message_queue_reset(MessageQueueHandle handle);
|
void tt_message_queue_reset(MessageQueueHandle handle);
|
||||||
|
|
||||||
#ifdef __cplusplus
|
#ifdef __cplusplus
|
||||||
}
|
}
|
||||||
|
|||||||
@ -27,7 +27,7 @@ typedef enum {
|
|||||||
} ThreadState;
|
} ThreadState;
|
||||||
|
|
||||||
/** The identifier that represents the thread */
|
/** The identifier that represents the thread */
|
||||||
typedef TaskHandle_t ThreadId;
|
typedef TaskHandle_t TaskHandle;
|
||||||
|
|
||||||
/** ThreadCallback Your callback to run in new thread
|
/** ThreadCallback Your callback to run in new thread
|
||||||
* @warning never use osThreadExit in Thread
|
* @warning never use osThreadExit in Thread
|
||||||
@ -132,16 +132,16 @@ void tt_thread_start(ThreadHandle handle);
|
|||||||
/**
|
/**
|
||||||
* Wait (block) for the thread to finish.
|
* Wait (block) for the thread to finish.
|
||||||
* @param[in] handle the thread instance handle
|
* @param[in] handle the thread instance handle
|
||||||
* @warning make sure you manually interrupt any logic in your thread (e.g. by an EventFlag or boolean+Mutex)
|
* @warning make sure you manually interrupt any logic in your thread (e.g. by an EventGroup or boolean+Mutex)
|
||||||
*/
|
*/
|
||||||
bool tt_thread_join(ThreadHandle handle, TickType_t timeout);
|
bool tt_thread_join(ThreadHandle handle, TickType_t timeout);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get thread id
|
* Get thread task handle
|
||||||
* @param[in] handle the thread instance handle
|
* @param[in] handle the thread instance handle
|
||||||
* @return the ThreadId of a thread
|
* @return the task handle of a thread
|
||||||
* */
|
* */
|
||||||
ThreadId tt_thread_get_id(ThreadHandle handle);
|
TaskHandle tt_thread_get_task_handle(ThreadHandle handle);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the return code of a thread
|
* Get the return code of a thread
|
||||||
|
|||||||
@ -1,7 +1,7 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
|
#include "tt_kernel.h"
|
||||||
#include "tt_thread.h"
|
#include "tt_thread.h"
|
||||||
#include <freertos/FreeRTOS.h>
|
|
||||||
|
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
#include <stdbool.h>
|
#include <stdbool.h>
|
||||||
@ -15,8 +15,8 @@ typedef void* TimerHandle;
|
|||||||
|
|
||||||
/** The behaviour of the timer */
|
/** The behaviour of the timer */
|
||||||
typedef enum {
|
typedef enum {
|
||||||
TimerTypeOnce = 0, ///< One-shot timer.
|
TimerTypeOnce = 0, // Timer triggers once after time has passed
|
||||||
TimerTypePeriodic = 1 ///< Repeating timer.
|
TimerTypePeriodic = 1 // Timer triggers repeatedly after time has passed
|
||||||
} TimerType;
|
} TimerType;
|
||||||
|
|
||||||
typedef void (*TimerCallback)(void* context);
|
typedef void (*TimerCallback)(void* context);
|
||||||
@ -27,7 +27,7 @@ typedef void (*TimerPendingCallback)(void* context, uint32_t arg);
|
|||||||
* @param[in] callback the callback to call when the timer expires
|
* @param[in] callback the callback to call when the timer expires
|
||||||
* @param[in] callbackContext the data to pass to the callback
|
* @param[in] callbackContext the data to pass to the callback
|
||||||
*/
|
*/
|
||||||
TimerHandle tt_timer_alloc(TimerType type, TimerCallback callback, void* callbackContext);
|
TimerHandle tt_timer_alloc(TimerType type, TickType ticks, TimerCallback callback, void* callbackContext);
|
||||||
|
|
||||||
/** Free up the memory of a timer instance */
|
/** Free up the memory of a timer instance */
|
||||||
void tt_timer_free(TimerHandle handle);
|
void tt_timer_free(TimerHandle handle);
|
||||||
@ -35,18 +35,24 @@ void tt_timer_free(TimerHandle handle);
|
|||||||
/**
|
/**
|
||||||
* Start the timer
|
* Start the timer
|
||||||
* @param[in] handle the timer instance handle
|
* @param[in] handle the timer instance handle
|
||||||
* @parma[in] interval the interval of the timer
|
|
||||||
* @return true when the timer was successfully started
|
* @return true when the timer was successfully started
|
||||||
*/
|
*/
|
||||||
bool tt_timer_start(TimerHandle handle, TickType_t interval);
|
bool tt_timer_start(TimerHandle handle);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Restart an already started timer
|
* Restart an already started timer
|
||||||
* @param[in] handle the timer instance handle
|
* @param[in] handle the timer instance handle
|
||||||
* @parma[in] interval the interval of the timer
|
* @param[in] interval the timer new interval
|
||||||
* @return true when the timer was successfully restarted
|
* @return true when the timer was successfully restarted
|
||||||
*/
|
*/
|
||||||
bool tt_timer_restart(TimerHandle handle, TickType_t interval);
|
bool tt_timer_reset_with_interval(TimerHandle handle, TickType interval);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Restart an already started timer
|
||||||
|
* @param[in] handle the timer instance handle
|
||||||
|
* @return true when the timer was successfully restarted
|
||||||
|
*/
|
||||||
|
bool tt_timer_reset(TimerHandle handle);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Stop a started timer
|
* Stop a started timer
|
||||||
@ -63,11 +69,11 @@ bool tt_timer_stop(TimerHandle handle);
|
|||||||
bool tt_timer_is_running(TimerHandle handle);
|
bool tt_timer_is_running(TimerHandle handle);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the expire time of a timer
|
* Get the expiry time of a timer
|
||||||
* @param[in] handle the timer instance handle
|
* @param[in] handle the timer instance handle
|
||||||
* @return the absolute timestamp at which the timer will expire
|
* @return the absolute timestamp at which the timer will expire
|
||||||
*/
|
*/
|
||||||
uint32_t tt_timer_get_expire_time(TimerHandle handle);
|
uint32_t tt_timer_get_expiry_time(TimerHandle handle);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the pending callback for a timer
|
* Set the pending callback for a timer
|
||||||
|
|||||||
@ -3,7 +3,7 @@
|
|||||||
|
|
||||||
#include <symbols/freertos.h>
|
#include <symbols/freertos.h>
|
||||||
|
|
||||||
#include <Tactility/RtosCompat.h>
|
#include <Tactility/freertoscompat/RTOS.h>
|
||||||
#include <freertos/task.h>
|
#include <freertos/task.h>
|
||||||
#include <freertos/event_groups.h>
|
#include <freertos/event_groups.h>
|
||||||
|
|
||||||
|
|||||||
@ -3,7 +3,7 @@
|
|||||||
#include <Tactility/app/AppPaths.h>
|
#include <Tactility/app/AppPaths.h>
|
||||||
#include <Tactility/app/AppContext.h>
|
#include <Tactility/app/AppContext.h>
|
||||||
#include <Tactility/app/ElfApp.h>
|
#include <Tactility/app/ElfApp.h>
|
||||||
#include <Tactility/file/FileLock.h>
|
#include <Tactility/Log.h>
|
||||||
|
|
||||||
#include <cstring>
|
#include <cstring>
|
||||||
|
|
||||||
|
|||||||
@ -43,8 +43,8 @@ bool tt_hal_i2c_lock(i2c_port_t port, TickType_t timeout) {
|
|||||||
return tt::hal::i2c::getLock(port).lock(timeout);
|
return tt::hal::i2c::getLock(port).lock(timeout);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool tt_hal_i2c_unlock(i2c_port_t port) {
|
void tt_hal_i2c_unlock(i2c_port_t port) {
|
||||||
return tt::hal::i2c::getLock(port).unlock();
|
tt::hal::i2c::getLock(port).unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
@ -12,7 +12,6 @@
|
|||||||
#include "tt_hal_i2c.h"
|
#include "tt_hal_i2c.h"
|
||||||
#include "tt_hal_touch.h"
|
#include "tt_hal_touch.h"
|
||||||
#include "tt_hal_uart.h"
|
#include "tt_hal_uart.h"
|
||||||
#include "tt_kernel.h"
|
|
||||||
#include <tt_lock.h>
|
#include <tt_lock.h>
|
||||||
#include "tt_lvgl.h"
|
#include "tt_lvgl.h"
|
||||||
#include "tt_lvgl_keyboard.h"
|
#include "tt_lvgl_keyboard.h"
|
||||||
@ -261,15 +260,6 @@ const esp_elfsym main_symbols[] {
|
|||||||
ESP_ELFSYM_EXPORT(tt_hal_uart_set_baud_rate),
|
ESP_ELFSYM_EXPORT(tt_hal_uart_set_baud_rate),
|
||||||
ESP_ELFSYM_EXPORT(tt_hal_uart_get_baud_rate),
|
ESP_ELFSYM_EXPORT(tt_hal_uart_get_baud_rate),
|
||||||
ESP_ELFSYM_EXPORT(tt_hal_uart_flush_input),
|
ESP_ELFSYM_EXPORT(tt_hal_uart_flush_input),
|
||||||
ESP_ELFSYM_EXPORT(tt_kernel_delay_millis),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_kernel_delay_micros),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_kernel_delay_ticks),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_kernel_get_ticks),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_kernel_millis_to_ticks),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_kernel_delay_until_tick),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_kernel_get_tick_frequency),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_kernel_get_millis),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_kernel_get_micros),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_lvgl_is_started),
|
ESP_ELFSYM_EXPORT(tt_lvgl_is_started),
|
||||||
ESP_ELFSYM_EXPORT(tt_lvgl_lock),
|
ESP_ELFSYM_EXPORT(tt_lvgl_lock),
|
||||||
ESP_ELFSYM_EXPORT(tt_lvgl_unlock),
|
ESP_ELFSYM_EXPORT(tt_lvgl_unlock),
|
||||||
@ -295,8 +285,6 @@ const esp_elfsym main_symbols[] {
|
|||||||
ESP_ELFSYM_EXPORT(tt_message_queue_free),
|
ESP_ELFSYM_EXPORT(tt_message_queue_free),
|
||||||
ESP_ELFSYM_EXPORT(tt_message_queue_put),
|
ESP_ELFSYM_EXPORT(tt_message_queue_put),
|
||||||
ESP_ELFSYM_EXPORT(tt_message_queue_get),
|
ESP_ELFSYM_EXPORT(tt_message_queue_get),
|
||||||
ESP_ELFSYM_EXPORT(tt_message_queue_get_capacity),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_message_queue_get_message_size),
|
|
||||||
ESP_ELFSYM_EXPORT(tt_message_queue_get_count),
|
ESP_ELFSYM_EXPORT(tt_message_queue_get_count),
|
||||||
ESP_ELFSYM_EXPORT(tt_message_queue_reset),
|
ESP_ELFSYM_EXPORT(tt_message_queue_reset),
|
||||||
ESP_ELFSYM_EXPORT(tt_preferences_alloc),
|
ESP_ELFSYM_EXPORT(tt_preferences_alloc),
|
||||||
@ -324,15 +312,16 @@ const esp_elfsym main_symbols[] {
|
|||||||
ESP_ELFSYM_EXPORT(tt_thread_get_state),
|
ESP_ELFSYM_EXPORT(tt_thread_get_state),
|
||||||
ESP_ELFSYM_EXPORT(tt_thread_start),
|
ESP_ELFSYM_EXPORT(tt_thread_start),
|
||||||
ESP_ELFSYM_EXPORT(tt_thread_join),
|
ESP_ELFSYM_EXPORT(tt_thread_join),
|
||||||
ESP_ELFSYM_EXPORT(tt_thread_get_id),
|
ESP_ELFSYM_EXPORT(tt_thread_get_task_handle),
|
||||||
ESP_ELFSYM_EXPORT(tt_thread_get_return_code),
|
ESP_ELFSYM_EXPORT(tt_thread_get_return_code),
|
||||||
ESP_ELFSYM_EXPORT(tt_timer_alloc),
|
ESP_ELFSYM_EXPORT(tt_timer_alloc),
|
||||||
ESP_ELFSYM_EXPORT(tt_timer_free),
|
ESP_ELFSYM_EXPORT(tt_timer_free),
|
||||||
ESP_ELFSYM_EXPORT(tt_timer_start),
|
ESP_ELFSYM_EXPORT(tt_timer_start),
|
||||||
ESP_ELFSYM_EXPORT(tt_timer_restart),
|
ESP_ELFSYM_EXPORT(tt_timer_reset),
|
||||||
|
ESP_ELFSYM_EXPORT(tt_timer_reset_with_interval),
|
||||||
ESP_ELFSYM_EXPORT(tt_timer_stop),
|
ESP_ELFSYM_EXPORT(tt_timer_stop),
|
||||||
ESP_ELFSYM_EXPORT(tt_timer_is_running),
|
ESP_ELFSYM_EXPORT(tt_timer_is_running),
|
||||||
ESP_ELFSYM_EXPORT(tt_timer_get_expire_time),
|
ESP_ELFSYM_EXPORT(tt_timer_get_expiry_time),
|
||||||
ESP_ELFSYM_EXPORT(tt_timer_set_pending_callback),
|
ESP_ELFSYM_EXPORT(tt_timer_set_pending_callback),
|
||||||
ESP_ELFSYM_EXPORT(tt_timer_set_thread_priority),
|
ESP_ELFSYM_EXPORT(tt_timer_set_thread_priority),
|
||||||
ESP_ELFSYM_EXPORT(tt_timezone_set),
|
ESP_ELFSYM_EXPORT(tt_timezone_set),
|
||||||
|
|||||||
@ -1,42 +0,0 @@
|
|||||||
#include "tt_kernel.h"
|
|
||||||
#include <Tactility/kernel/Kernel.h>
|
|
||||||
|
|
||||||
extern "C" {
|
|
||||||
|
|
||||||
void tt_kernel_delay_millis(uint32_t milliseconds) {
|
|
||||||
tt::kernel::delayMillis(milliseconds);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tt_kernel_delay_micros(uint32_t microSeconds) {
|
|
||||||
tt::kernel::delayMicros(microSeconds);
|
|
||||||
}
|
|
||||||
|
|
||||||
void tt_kernel_delay_ticks(TickType ticks) {
|
|
||||||
tt::kernel::delayTicks((TickType_t)ticks);
|
|
||||||
}
|
|
||||||
|
|
||||||
TickType tt_kernel_get_ticks() {
|
|
||||||
return tt::kernel::getTicks();
|
|
||||||
}
|
|
||||||
|
|
||||||
TickType tt_kernel_millis_to_ticks(uint32_t milliSeconds) {
|
|
||||||
return tt::kernel::millisToTicks(milliSeconds);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool tt_kernel_delay_until_tick(TickType tick) {
|
|
||||||
return tt::kernel::delayUntilTick(tick);
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t tt_kernel_get_tick_frequency() {
|
|
||||||
return tt::kernel::getTickFrequency();
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t tt_kernel_get_millis() {
|
|
||||||
return tt::kernel::getMillis();
|
|
||||||
}
|
|
||||||
|
|
||||||
unsigned long tt_kernel_get_micros() {
|
|
||||||
return tt::kernel::getMicros();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
@ -32,7 +32,7 @@ bool tt_lock_acquire(LockHandle handle, TickType timeout) {
|
|||||||
return HANDLE_AS_LOCK(handle)->lock(timeout);
|
return HANDLE_AS_LOCK(handle)->lock(timeout);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool tt_lock_release(LockHandle handle) {
|
void tt_lock_release(LockHandle handle) {
|
||||||
return HANDLE_AS_LOCK(handle)->unlock();
|
return HANDLE_AS_LOCK(handle)->unlock();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -21,23 +21,11 @@ bool tt_message_queue_get(MessageQueueHandle handle, void* message, TickType_t t
|
|||||||
return HANDLE_TO_MESSAGE_QUEUE(handle)->get(message, timeout);
|
return HANDLE_TO_MESSAGE_QUEUE(handle)->get(message, timeout);
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t tt_message_queue_get_capacity(MessageQueueHandle handle) {
|
|
||||||
return HANDLE_TO_MESSAGE_QUEUE(handle)->getCapacity();
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t tt_message_queue_get_message_size(MessageQueueHandle handle) {
|
|
||||||
return HANDLE_TO_MESSAGE_QUEUE(handle)->getMessageSize();
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t tt_message_queue_get_count(MessageQueueHandle handle) {
|
uint32_t tt_message_queue_get_count(MessageQueueHandle handle) {
|
||||||
return HANDLE_TO_MESSAGE_QUEUE(handle)->getCount();
|
return HANDLE_TO_MESSAGE_QUEUE(handle)->getCount();
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t tt_message_queue_get_space(MessageQueueHandle handle) {
|
void tt_message_queue_reset(MessageQueueHandle handle) {
|
||||||
return HANDLE_TO_MESSAGE_QUEUE(handle)->getSpace();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool tt_message_queue_reset(MessageQueueHandle handle) {
|
|
||||||
return HANDLE_TO_MESSAGE_QUEUE(handle)->reset();
|
return HANDLE_TO_MESSAGE_QUEUE(handle)->reset();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -66,8 +66,8 @@ bool tt_thread_join(ThreadHandle handle, TickType_t timeout) {
|
|||||||
return HANDLE_AS_THREAD(handle)->join(timeout);
|
return HANDLE_AS_THREAD(handle)->join(timeout);
|
||||||
}
|
}
|
||||||
|
|
||||||
ThreadId tt_thread_get_id(ThreadHandle handle) {
|
TaskHandle tt_thread_get_task_handle(ThreadHandle handle) {
|
||||||
return HANDLE_AS_THREAD(handle)->getId();
|
return HANDLE_AS_THREAD(handle)->getTaskHandle();
|
||||||
}
|
}
|
||||||
|
|
||||||
int32_t tt_thread_get_return_code(ThreadHandle handle) {
|
int32_t tt_thread_get_return_code(ThreadHandle handle) {
|
||||||
|
|||||||
@ -9,9 +9,9 @@ struct TimerWrapper {
|
|||||||
|
|
||||||
extern "C" {
|
extern "C" {
|
||||||
|
|
||||||
TimerHandle tt_timer_alloc(TimerType type, TimerCallback callback, void* callbackContext) {
|
TimerHandle tt_timer_alloc(TimerType type, TickType ticks, TimerCallback callback, void* callbackContext) {
|
||||||
auto wrapper = new TimerWrapper;
|
auto wrapper = new TimerWrapper;
|
||||||
wrapper->timer = std::make_unique<tt::Timer>(static_cast<tt::Timer::Type>(type), [callback, callbackContext](){ callback(callbackContext); });
|
wrapper->timer = std::make_unique<tt::Timer>(static_cast<tt::Timer::Type>(type), ticks, [callback, callbackContext](){ callback(callbackContext); });
|
||||||
return wrapper;
|
return wrapper;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -21,12 +21,16 @@ void tt_timer_free(TimerHandle handle) {
|
|||||||
delete wrapper;
|
delete wrapper;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool tt_timer_start(TimerHandle handle, TickType_t intervalTicks) {
|
bool tt_timer_start(TimerHandle handle) {
|
||||||
return HANDLE_TO_WRAPPER(handle)->timer->start(intervalTicks);
|
return HANDLE_TO_WRAPPER(handle)->timer->start();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool tt_timer_restart(TimerHandle handle, TickType_t intervalTicks) {
|
bool tt_timer_reset(TimerHandle handle) {
|
||||||
return HANDLE_TO_WRAPPER(handle)->timer->restart(intervalTicks);
|
return HANDLE_TO_WRAPPER(handle)->timer->reset();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool tt_timer_reset_with_interval(TimerHandle handle, TickType interval) {
|
||||||
|
return HANDLE_TO_WRAPPER(handle)->timer->reset(interval);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool tt_timer_stop(TimerHandle handle) {
|
bool tt_timer_stop(TimerHandle handle) {
|
||||||
@ -37,8 +41,8 @@ bool tt_timer_is_running(TimerHandle handle) {
|
|||||||
return HANDLE_TO_WRAPPER(handle)->timer->isRunning();
|
return HANDLE_TO_WRAPPER(handle)->timer->isRunning();
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t tt_timer_get_expire_time(TimerHandle handle) {
|
uint32_t tt_timer_get_expiry_time(TimerHandle handle) {
|
||||||
return HANDLE_TO_WRAPPER(handle)->timer->getExpireTime();
|
return HANDLE_TO_WRAPPER(handle)->timer->getExpiryTime();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool tt_timer_set_pending_callback(TimerHandle handle, TimerPendingCallback callback, void* callbackContext, uint32_t callbackArg, TickType_t timeoutTicks) {
|
bool tt_timer_set_pending_callback(TimerHandle handle, TimerPendingCallback callback, void* callbackContext, uint32_t callbackArg, TickType_t timeoutTicks) {
|
||||||
@ -46,12 +50,12 @@ bool tt_timer_set_pending_callback(TimerHandle handle, TimerPendingCallback call
|
|||||||
callback,
|
callback,
|
||||||
callbackContext,
|
callbackContext,
|
||||||
callbackArg,
|
callbackArg,
|
||||||
(TickType_t)timeoutTicks
|
timeoutTicks
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
void tt_timer_set_thread_priority(TimerHandle handle, ThreadPriority priority) {
|
void tt_timer_set_thread_priority(TimerHandle handle, ThreadPriority priority) {
|
||||||
HANDLE_TO_WRAPPER(handle)->timer->setThreadPriority(static_cast<tt::Thread::Priority>(priority));
|
HANDLE_TO_WRAPPER(handle)->timer->setCallbackPriority(static_cast<tt::Thread::Priority>(priority));
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@ -9,7 +9,7 @@ if (DEFINED ENV{ESP_IDF_VERSION})
|
|||||||
idf_component_register(
|
idf_component_register(
|
||||||
SRCS ${SOURCE_FILES}
|
SRCS ${SOURCE_FILES}
|
||||||
INCLUDE_DIRS "Include/"
|
INCLUDE_DIRS "Include/"
|
||||||
REQUIRES mbedtls nvs_flash esp_rom esp_timer
|
REQUIRES TactilityFreeRtos mbedtls nvs_flash esp_rom
|
||||||
)
|
)
|
||||||
|
|
||||||
if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
|
if(CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
|
||||||
@ -32,7 +32,7 @@ else()
|
|||||||
add_definitions(-D_Nonnull=)
|
add_definitions(-D_Nonnull=)
|
||||||
|
|
||||||
target_link_libraries(TactilityCore
|
target_link_libraries(TactilityCore
|
||||||
|
PUBLIC TactilityFreeRtos
|
||||||
PUBLIC mbedtls
|
PUBLIC mbedtls
|
||||||
PUBLIC freertos_kernel
|
|
||||||
)
|
)
|
||||||
endif()
|
endif()
|
||||||
@ -1,6 +1,6 @@
|
|||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "RtosCompat.h"
|
#include <Tactility/freertoscompat/RTOS.h>
|
||||||
|
|
||||||
namespace tt {
|
namespace tt {
|
||||||
|
|
||||||
|
|||||||
@ -1,56 +0,0 @@
|
|||||||
/**
|
|
||||||
* @file Dispatcher.h
|
|
||||||
*
|
|
||||||
* Dispatcher is a thread-safe code execution queue.
|
|
||||||
*/
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include "MessageQueue.h"
|
|
||||||
#include "Mutex.h"
|
|
||||||
#include "EventFlag.h"
|
|
||||||
|
|
||||||
#include <memory>
|
|
||||||
#include <queue>
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* A thread-safe way to defer code execution.
|
|
||||||
* Generally, one task would dispatch the execution,
|
|
||||||
* while the other thread consumes and executes the work.
|
|
||||||
*/
|
|
||||||
class Dispatcher final {
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
typedef std::function<void()> Function;
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
Mutex mutex;
|
|
||||||
std::queue<Function> queue = {};
|
|
||||||
EventFlag eventFlag;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
explicit Dispatcher() = default;
|
|
||||||
~Dispatcher();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Queue a function to be consumed elsewhere.
|
|
||||||
* @param[in] function the function to execute elsewhere
|
|
||||||
* @param[in] timeout lock acquisition timeout
|
|
||||||
* @return true if dispatching was successful (timeout not reached)
|
|
||||||
*/
|
|
||||||
bool dispatch(Function function, TickType_t timeout = portMAX_DELAY);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Consume 1 or more dispatched function (if any) until the queue is empty.
|
|
||||||
* @warning The timeout is only the wait time before consuming the message! It is not a limit to the total execution time when calling this method.
|
|
||||||
* @param[in] timeout the ticks to wait for a message
|
|
||||||
* @return the amount of messages that were consumed
|
|
||||||
*/
|
|
||||||
uint32_t consume(TickType_t timeout = portMAX_DELAY);
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
@ -1,36 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#include "Dispatcher.h"
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
/** Starts a Thread to process dispatched messages */
|
|
||||||
class DispatcherThread final {
|
|
||||||
|
|
||||||
Dispatcher dispatcher;
|
|
||||||
std::unique_ptr<Thread> thread;
|
|
||||||
bool interruptThread = true;
|
|
||||||
|
|
||||||
int32_t threadMain();
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
explicit DispatcherThread(const std::string& threadName, size_t threadStackSize = 4096);
|
|
||||||
~DispatcherThread();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Dispatch a message.
|
|
||||||
*/
|
|
||||||
bool dispatch(Dispatcher::Function function, TickType_t timeout = portMAX_DELAY);
|
|
||||||
|
|
||||||
/** Start the thread (blocking). */
|
|
||||||
void start();
|
|
||||||
|
|
||||||
/** Stop the thread (blocking). */
|
|
||||||
void stop();
|
|
||||||
|
|
||||||
/** @return true of the thread is started */
|
|
||||||
bool isStarted() const { return thread != nullptr && !interruptThread; }
|
|
||||||
};
|
|
||||||
|
|
||||||
}
|
|
||||||
@ -1,60 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#include "RtosCompatEventGroups.h"
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Wrapper for FreeRTOS xEventGroup.
|
|
||||||
*/
|
|
||||||
class EventFlag final {
|
|
||||||
|
|
||||||
struct EventGroupHandleDeleter {
|
|
||||||
void operator()(EventGroupHandle_t handleToDelete) {
|
|
||||||
vEventGroupDelete(handleToDelete);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
std::unique_ptr<std::remove_pointer_t<EventGroupHandle_t>, EventGroupHandleDeleter> handle;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
EventFlag();
|
|
||||||
~EventFlag();
|
|
||||||
|
|
||||||
enum Flag {
|
|
||||||
WaitAny = 0x00000000U, ///< Wait for any flag (default).
|
|
||||||
WaitAll = 0x00000001U, ///< Wait for all flags.
|
|
||||||
NoClear = 0x00000002U, ///< Do not clear flags which have been specified to wait for.
|
|
||||||
|
|
||||||
Error = 0x80000000U, ///< Error indicator.
|
|
||||||
ErrorUnknown = 0xFFFFFFFFU, ///< TtStatusError (-1).
|
|
||||||
ErrorTimeout = 0xFFFFFFFEU, ///< TtStatusErrorTimeout (-2).
|
|
||||||
ErrorResource = 0xFFFFFFFDU, ///< TtStatusErrorResource (-3).
|
|
||||||
ErrorParameter = 0xFFFFFFFCU, ///< TtStatusErrorParameter (-4).
|
|
||||||
ErrorISR = 0xFFFFFFFAU, ///< TtStatusErrorISR (-6).
|
|
||||||
};
|
|
||||||
|
|
||||||
/** Set the bitmask for 1 or more flags that we might be waiting for */
|
|
||||||
uint32_t set(uint32_t flags) const;
|
|
||||||
|
|
||||||
/** Clear the specified flags */
|
|
||||||
uint32_t clear(uint32_t flags) const;
|
|
||||||
|
|
||||||
/** Get the currently set flags */
|
|
||||||
uint32_t get() const;
|
|
||||||
|
|
||||||
/** Await for flags to be set
|
|
||||||
* @param[in] flags the bitmask of the flags that we want to wait for
|
|
||||||
* @param[in] options the trigger behaviour: WaitAny, WaitAll, NoClear (NoClear can be combined with either WaitAny or WaitAll)
|
|
||||||
* @param[in] timeoutTicks the maximum amount of ticks to wait
|
|
||||||
*/
|
|
||||||
uint32_t wait(
|
|
||||||
uint32_t flags,
|
|
||||||
uint32_t options = WaitAny,
|
|
||||||
uint32_t timeoutTicks = (uint32_t)portMAX_DELAY
|
|
||||||
) const;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
@ -1,86 +0,0 @@
|
|||||||
/**
|
|
||||||
* @file MessageQueue.h
|
|
||||||
*
|
|
||||||
* MessageQueue is a wrapper for FreeRTOS xQueue functionality.
|
|
||||||
* There is no additional thread-safety on top of the xQueue functionality,
|
|
||||||
* so make sure you create a lock if needed.
|
|
||||||
*/
|
|
||||||
#pragma once
|
|
||||||
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include "freertos/FreeRTOS.h"
|
|
||||||
#include "freertos/queue.h"
|
|
||||||
#else
|
|
||||||
#include "FreeRTOS.h"
|
|
||||||
#include "queue.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Message Queue implementation.
|
|
||||||
* Calls can be done from ISR/IRQ mode unless otherwise specified.
|
|
||||||
*/
|
|
||||||
class MessageQueue {
|
|
||||||
|
|
||||||
struct QueueHandleDeleter {
|
|
||||||
void operator()(QueueHandle_t handleToDelete) {
|
|
||||||
vQueueDelete(handleToDelete);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
std::unique_ptr<std::remove_pointer_t<QueueHandle_t>, QueueHandleDeleter> handle;
|
|
||||||
|
|
||||||
public:
|
|
||||||
/** Allocate message queue
|
|
||||||
* @param[in] capacity Maximum messages in queue
|
|
||||||
* @param[in] messageSize The size in bytes of a single message
|
|
||||||
*/
|
|
||||||
MessageQueue(uint32_t capacity, uint32_t messageSize);
|
|
||||||
|
|
||||||
~MessageQueue();
|
|
||||||
|
|
||||||
/** Post a message to the queue.
|
|
||||||
* The message is queued by copy, not by reference.
|
|
||||||
* @param[in] message A pointer to a message. The message will be copied into a buffer.
|
|
||||||
* @param[in] timeout
|
|
||||||
* @return success result
|
|
||||||
*/
|
|
||||||
bool put(const void* message, TickType_t timeout);
|
|
||||||
|
|
||||||
/** Get message from queue
|
|
||||||
* @param[out] message A pointer to an already allocated message object
|
|
||||||
* @param[in] timeout
|
|
||||||
* @return success result
|
|
||||||
*/
|
|
||||||
bool get(void* message, TickType_t timeout);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @return The maximum amount of messages that can be in the queue at any given time.
|
|
||||||
*/
|
|
||||||
uint32_t getCapacity() const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @return The size of a single message in bytes
|
|
||||||
*/
|
|
||||||
uint32_t getMessageSize() const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @return How many messages are currently in the queue.
|
|
||||||
*/
|
|
||||||
uint32_t getCount() const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @return How many messages can be added to the queue before the put() method starts blocking.
|
|
||||||
*/
|
|
||||||
uint32_t getSpace() const;
|
|
||||||
|
|
||||||
/** Reset queue (cannot be called in ISR/IRQ mode)
|
|
||||||
* @return success result
|
|
||||||
*/
|
|
||||||
bool reset();
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
@ -1,13 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Compatibility includes for FreeRTOS.
|
|
||||||
* Custom FreeRTOS from ESP-IDF prefixes paths with "freertos/",
|
|
||||||
* but this isn't the normal behaviour for the regular FreeRTOS project.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include "freertos/FreeRTOS.h"
|
|
||||||
#else
|
|
||||||
#include "FreeRTOS.h"
|
|
||||||
#endif
|
|
||||||
@ -1,14 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
/**
|
|
||||||
* See explanation in RtosCompat.h
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include "freertos/FreeRTOS.h"
|
|
||||||
#include "freertos/event_groups.h"
|
|
||||||
#else
|
|
||||||
#include "FreeRTOS.h"
|
|
||||||
#include "event_groups.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
@ -1,14 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
/**
|
|
||||||
* See explanation in RtosCompat.h
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include "freertos/FreeRTOS.h"
|
|
||||||
#include "freertos/semphr.h"
|
|
||||||
#else
|
|
||||||
#include "FreeRTOS.h"
|
|
||||||
#include "semphr.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
@ -1,14 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
/**
|
|
||||||
* See explanation in RtosCompat.h
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include "freertos/FreeRTOS.h"
|
|
||||||
#include "freertos/task.h"
|
|
||||||
#else
|
|
||||||
#include "FreeRTOS.h"
|
|
||||||
#include "task.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
@ -1,13 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
/**
|
|
||||||
* See explanation in RtosCompat.h
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include "freertos/FreeRTOS.h"
|
|
||||||
#include "freertos/timers.h"
|
|
||||||
#else
|
|
||||||
#include "FreeRTOS.h"
|
|
||||||
#include "timers.h"
|
|
||||||
#endif
|
|
||||||
@ -1,69 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#include "Lock.h"
|
|
||||||
#include "kernel/Kernel.h"
|
|
||||||
#include <cassert>
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include "freertos/FreeRTOS.h"
|
|
||||||
#include "freertos/semphr.h"
|
|
||||||
#else
|
|
||||||
#include "FreeRTOS.h"
|
|
||||||
#include "semphr.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Wrapper for xSemaphoreCreateBinary (max count == 1) and xSemaphoreCreateCounting (max count > 1)
|
|
||||||
* Can be used from IRQ/ISR mode, but cannot be created/destroyed from such a context.
|
|
||||||
*/
|
|
||||||
class Semaphore final : public Lock {
|
|
||||||
|
|
||||||
struct SemaphoreHandleDeleter {
|
|
||||||
void operator()(QueueHandle_t handleToDelete) {
|
|
||||||
assert(!kernel::isIsr());
|
|
||||||
vSemaphoreDelete(handleToDelete);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
std::unique_ptr<std::remove_pointer_t<QueueHandle_t>, SemaphoreHandleDeleter> handle;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
using Lock::lock;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Cannot be called from IRQ/ISR mode.
|
|
||||||
* @param[in] maxAvailable The maximum count
|
|
||||||
* @param[in] initialAvailable The initial count
|
|
||||||
*/
|
|
||||||
Semaphore(uint32_t maxAvailable, uint32_t initialAvailable);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Cannot be called from IRQ/ISR mode.
|
|
||||||
* @param[in] maxAvailable The maximum count
|
|
||||||
*/
|
|
||||||
explicit Semaphore(uint32_t maxAvailable) : Semaphore(maxAvailable, maxAvailable) {};
|
|
||||||
|
|
||||||
/** Cannot be called from IRQ/ISR mode. */
|
|
||||||
~Semaphore() override;
|
|
||||||
|
|
||||||
Semaphore(Semaphore& other) : handle(std::move(other.handle)) {}
|
|
||||||
|
|
||||||
/** Acquire semaphore */
|
|
||||||
bool acquire(TickType_t timeout) const;
|
|
||||||
|
|
||||||
/** Release semaphore */
|
|
||||||
bool release() const;
|
|
||||||
|
|
||||||
bool lock(TickType_t timeout) const override { return acquire(timeout); }
|
|
||||||
|
|
||||||
bool unlock() const override { return release(); }
|
|
||||||
|
|
||||||
/** @return return the amount of times this semaphore can be acquired/locked */
|
|
||||||
uint32_t getAvailable() const;
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
@ -1,152 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include "freertos/FreeRTOS.h"
|
|
||||||
#include "freertos/stream_buffer.h"
|
|
||||||
#else
|
|
||||||
#include "FreeRTOS.h"
|
|
||||||
#include "stream_buffer.h"
|
|
||||||
#endif
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Stream buffers are used to send a continuous stream of data from one task or
|
|
||||||
* interrupt to another. Their implementation is light weight, making them
|
|
||||||
* particularly suited for interrupt to task and core to core communication
|
|
||||||
* scenarios.
|
|
||||||
*
|
|
||||||
* **NOTE**: Stream buffer implementation assumes there is only one task or
|
|
||||||
* interrupt that will write to the buffer (the writer), and only one task or
|
|
||||||
* interrupt that will read from the buffer (the reader).
|
|
||||||
*/
|
|
||||||
class StreamBuffer final {
|
|
||||||
|
|
||||||
struct StreamBufferHandleDeleter {
|
|
||||||
void operator()(StreamBufferHandle_t handleToDelete) {
|
|
||||||
vStreamBufferDelete(handleToDelete);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
std::unique_ptr<std::remove_pointer_t<StreamBufferHandle_t>, StreamBufferHandleDeleter> handle;
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Stream buffer implementation assumes there is only one task or
|
|
||||||
* interrupt that will write to the buffer (the writer), and only one task or
|
|
||||||
* interrupt that will read from the buffer (the reader).
|
|
||||||
*
|
|
||||||
* @param[in] size The total number of bytes the stream buffer will be able to hold at any one time.
|
|
||||||
* @param[in] triggerLevel The number of bytes that must be in the stream buffer
|
|
||||||
* before a task that is blocked on the stream buffer to wait for data is moved out of the blocked state.
|
|
||||||
* @return The stream buffer instance.
|
|
||||||
*/
|
|
||||||
StreamBuffer(size_t size, size_t triggerLevel);
|
|
||||||
|
|
||||||
~StreamBuffer() = default;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Set trigger level for stream buffer.
|
|
||||||
* A stream buffer's trigger level is the number of bytes that must be in the
|
|
||||||
* stream buffer before a task that is blocked on the stream buffer to
|
|
||||||
* wait for data is moved out of the blocked state.
|
|
||||||
*
|
|
||||||
* @param[in] triggerLevel The new trigger level for the stream buffer.
|
|
||||||
* @return true if trigger level can be be updated (new trigger level was less than or equal to the stream buffer's length).
|
|
||||||
* @return false if trigger level can't be be updated (new trigger level was greater than the stream buffer's length).
|
|
||||||
*/
|
|
||||||
bool setTriggerLevel(size_t triggerLevel) const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Sends bytes to a stream buffer. The bytes are copied into the stream buffer.
|
|
||||||
* Wakes up task waiting for data to become available if called from ISR.
|
|
||||||
*
|
|
||||||
* @param[in] data A pointer to the data that is to be copied into the stream buffer.
|
|
||||||
* @param[in] length The maximum number of bytes to copy from data into the stream buffer.
|
|
||||||
* @param[in] timeout The maximum amount of time the task should remain in the
|
|
||||||
* Blocked state to wait for space to become available if the stream buffer is full.
|
|
||||||
* Will return immediately if timeout is zero.
|
|
||||||
* Setting timeout to portMAX_DELAY will cause the task to wait indefinitely.
|
|
||||||
* Ignored if called from ISR.
|
|
||||||
* @return The number of bytes actually written to the stream buffer.
|
|
||||||
*/
|
|
||||||
size_t send(
|
|
||||||
const void* data,
|
|
||||||
size_t length,
|
|
||||||
uint32_t timeout
|
|
||||||
) const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Receives bytes from a stream buffer.
|
|
||||||
* Wakes up task waiting for space to become available if called from ISR.
|
|
||||||
*
|
|
||||||
* @param[in] data A pointer to the buffer into which the received bytes will be
|
|
||||||
* copied.
|
|
||||||
* @param[in] length The length of the buffer pointed to by the data parameter.
|
|
||||||
* @param[in] timeout The maximum amount of time the task should remain in the
|
|
||||||
* Blocked state to wait for data to become available if the stream buffer is empty.
|
|
||||||
* Will return immediately if timeout is zero.
|
|
||||||
* Setting timeout to portMAX_DELAY will cause the task to wait indefinitely.
|
|
||||||
* Ignored if called from ISR.
|
|
||||||
* @return The number of bytes read from the stream buffer, if any.
|
|
||||||
*/
|
|
||||||
size_t receive(
|
|
||||||
void* data,
|
|
||||||
size_t length,
|
|
||||||
uint32_t timeout
|
|
||||||
) const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Queries a stream buffer to see how much data it contains, which is equal to
|
|
||||||
* the number of bytes that can be read from the stream buffer before the stream
|
|
||||||
* buffer would be empty.
|
|
||||||
*
|
|
||||||
* @return The number of bytes that can be read from the stream buffer before
|
|
||||||
* the stream buffer would be empty.
|
|
||||||
*/
|
|
||||||
size_t getAvailableReadBytes() const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Queries a stream buffer to see how much free space it contains, which is
|
|
||||||
* equal to the amount of data that can be sent to the stream buffer before it
|
|
||||||
* is full.
|
|
||||||
*
|
|
||||||
* @return The number of bytes that can be written to the stream buffer before
|
|
||||||
* the stream buffer would be full.
|
|
||||||
*/
|
|
||||||
size_t getAvailableWriteBytes() const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Queries a stream buffer to see if it is full.
|
|
||||||
*
|
|
||||||
* @return true if the stream buffer is full.
|
|
||||||
* @return false if the stream buffer is not full.
|
|
||||||
*/
|
|
||||||
bool isFull() const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Queries a stream buffer to see if it is empty.
|
|
||||||
*
|
|
||||||
* @param stream_buffer The stream buffer instance.
|
|
||||||
* @return true if the stream buffer is empty.
|
|
||||||
* @return false if the stream buffer is not empty.
|
|
||||||
*/
|
|
||||||
bool isEmpty() const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Resets a stream buffer to its initial, empty, state. Any data that was
|
|
||||||
* in the stream buffer is discarded. A stream buffer can only be reset if there
|
|
||||||
* are no tasks blocked waiting to either send to or receive from the stream buffer.
|
|
||||||
*
|
|
||||||
* @return TtStatusOk if the stream buffer is reset.
|
|
||||||
* @return TtStatusError if there was a task blocked waiting to send to or read
|
|
||||||
* from the stream buffer then the stream buffer is not reset.
|
|
||||||
*/
|
|
||||||
bool reset() const;
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
@ -2,11 +2,9 @@
|
|||||||
|
|
||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
|
|
||||||
|
#include "Tactility/Thread.h"
|
||||||
#include "Check.h"
|
#include "Check.h"
|
||||||
#include "CoreDefines.h"
|
#include "CoreDefines.h"
|
||||||
#include "EventFlag.h"
|
|
||||||
#include "kernel/Kernel.h"
|
|
||||||
#include "kernel/critical/Critical.h"
|
|
||||||
#include "Log.h"
|
#include "Log.h"
|
||||||
#include "Mutex.h"
|
|
||||||
#include "Thread.h"
|
#include <Tactility/kernel/Kernel.h>
|
||||||
|
|||||||
@ -1,3 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#define TT_CONFIG_THREAD_MAX_PRIORITIES 10
|
|
||||||
@ -1,195 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#include "RtosCompatTask.h"
|
|
||||||
|
|
||||||
#include <functional>
|
|
||||||
#include <memory>
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
typedef TaskHandle_t ThreadId;
|
|
||||||
|
|
||||||
class Thread final {
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
enum class State{
|
|
||||||
Stopped,
|
|
||||||
Starting,
|
|
||||||
Running,
|
|
||||||
};
|
|
||||||
|
|
||||||
/** ThreadPriority */
|
|
||||||
enum class Priority : UBaseType_t {
|
|
||||||
None = 0U, /**< Uninitialized, choose system default */
|
|
||||||
Idle = 1U,
|
|
||||||
Lower = 2U,
|
|
||||||
Low = 3U,
|
|
||||||
Normal = 4U,
|
|
||||||
High = 5U,
|
|
||||||
Higher = 6U,
|
|
||||||
Critical = 7U
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
/** ThreadCallback Your callback to run in new thread
|
|
||||||
* @warning never use osThreadExit in Thread
|
|
||||||
*/
|
|
||||||
typedef int32_t (*Callback)(void* context);
|
|
||||||
typedef std::function<int32_t()> MainFunction;
|
|
||||||
|
|
||||||
/** Write to stdout callback
|
|
||||||
* @param[in] data pointer to data
|
|
||||||
* @param[in] size data size @warning your handler must consume everything
|
|
||||||
*/
|
|
||||||
typedef void (*StdoutWriteCallback)(const char* data, size_t size);
|
|
||||||
|
|
||||||
/** Thread state change callback called upon thread state change
|
|
||||||
* @param[in] state new thread state
|
|
||||||
* @param[in] context callback context
|
|
||||||
*/
|
|
||||||
typedef void (*StateCallback)(State state, void* context);
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
static void mainBody(void* context);
|
|
||||||
|
|
||||||
TaskHandle_t taskHandle = nullptr;
|
|
||||||
State state = State::Stopped;
|
|
||||||
MainFunction mainFunction;
|
|
||||||
int32_t callbackResult = 0;
|
|
||||||
StateCallback stateCallback = nullptr;
|
|
||||||
void* stateCallbackContext = nullptr;
|
|
||||||
std::string name = {};
|
|
||||||
Priority priority = Priority::Normal;
|
|
||||||
configSTACK_DEPTH_TYPE stackSize = 0;
|
|
||||||
portBASE_TYPE affinity = -1;
|
|
||||||
|
|
||||||
void setState(Thread::State state);
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
Thread() = default;
|
|
||||||
|
|
||||||
/** Allocate Thread, shortcut version
|
|
||||||
* @param[in] name the name of the thread
|
|
||||||
* @param[in] stackSize in bytes
|
|
||||||
* @param[in] function
|
|
||||||
* @param[in] affinity Which CPU core to pin this task to, -1 means unpinned (only works on ESP32)
|
|
||||||
*/
|
|
||||||
Thread(
|
|
||||||
std::string name,
|
|
||||||
configSTACK_DEPTH_TYPE stackSize,
|
|
||||||
MainFunction function,
|
|
||||||
portBASE_TYPE affinity = -1
|
|
||||||
);
|
|
||||||
|
|
||||||
~Thread();
|
|
||||||
|
|
||||||
/** Set Thread name
|
|
||||||
* @param[in] name string
|
|
||||||
*/
|
|
||||||
void setName(std::string name);
|
|
||||||
|
|
||||||
/** Set Thread stack size
|
|
||||||
* @param[in] stackSize stack size in bytes
|
|
||||||
*/
|
|
||||||
void setStackSize(size_t stackSize);
|
|
||||||
|
|
||||||
/** Set CPU core pinning for this thread.
|
|
||||||
* @param[in] affinity -1 means not pinned, otherwise it's the core id (e.g. 0 or 1 on ESP32)
|
|
||||||
*/
|
|
||||||
void setAffinity(portBASE_TYPE affinity);
|
|
||||||
|
|
||||||
/** Set Thread callback
|
|
||||||
* @param[in] callback ThreadCallback, called upon thread run
|
|
||||||
* @param[in] callbackContext what to pass to the callback
|
|
||||||
*/
|
|
||||||
[[deprecated("use setMainFunction()")]]
|
|
||||||
void setCallback(Callback callback, _Nullable void* callbackContext = nullptr);
|
|
||||||
|
|
||||||
/** Set Thread callback
|
|
||||||
* @param[in] function called upon thread run
|
|
||||||
*/
|
|
||||||
void setMainFunction(MainFunction function);
|
|
||||||
|
|
||||||
/** Set Thread priority
|
|
||||||
* @param[in] priority ThreadPriority value
|
|
||||||
*/
|
|
||||||
void setPriority(Priority priority);
|
|
||||||
|
|
||||||
|
|
||||||
/** Set Thread state change callback
|
|
||||||
* @param[in] callback state change callback
|
|
||||||
* @param[in] callbackContext pointer to context
|
|
||||||
*/
|
|
||||||
void setStateCallback(StateCallback callback, _Nullable void* callbackContext = nullptr);
|
|
||||||
|
|
||||||
/** Get Thread state
|
|
||||||
* @return thread state from ThreadState
|
|
||||||
*/
|
|
||||||
State getState() const;
|
|
||||||
|
|
||||||
/** Start Thread */
|
|
||||||
void start();
|
|
||||||
|
|
||||||
/** Join Thread
|
|
||||||
* @warning make sure you manually interrupt any logic in your thread (e.g. by an EventFlag or boolean+Mutex)
|
|
||||||
* @param[in] timeout the maximum amount of time to wait
|
|
||||||
* @param[in] pollInterval the amount of ticks to wait before we check again if the thread is finished
|
|
||||||
* @return success result
|
|
||||||
*/
|
|
||||||
bool join(TickType_t timeout = portMAX_DELAY, TickType_t pollInterval = 10);
|
|
||||||
|
|
||||||
/** Get FreeRTOS ThreadId for Thread instance
|
|
||||||
* @return ThreadId or nullptr
|
|
||||||
*/
|
|
||||||
ThreadId getId() const;
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @warning crashes when state is not "stopped"
|
|
||||||
* @return thread return code
|
|
||||||
*/
|
|
||||||
int32_t getReturnCode() const;
|
|
||||||
|
|
||||||
/** Suspend thread
|
|
||||||
* @param[in] threadId thread id
|
|
||||||
*/
|
|
||||||
static void suspend(ThreadId threadId);
|
|
||||||
|
|
||||||
/** Resume thread
|
|
||||||
* @param[in] threadId thread id
|
|
||||||
*/
|
|
||||||
static void resume(ThreadId threadId);
|
|
||||||
|
|
||||||
/** Get thread suspended state
|
|
||||||
* @param[in] threadId thread id
|
|
||||||
* @return true if thread is suspended
|
|
||||||
*/
|
|
||||||
static bool isSuspended(ThreadId threadId);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Get thread stack watermark
|
|
||||||
* @param[in] threadId
|
|
||||||
* @return uint32_t
|
|
||||||
*/
|
|
||||||
static uint32_t getStackSpace(ThreadId threadId);
|
|
||||||
|
|
||||||
/** @return pointer to Thread instance or nullptr if this thread doesn't belong to Tactility */
|
|
||||||
static Thread* getCurrent();
|
|
||||||
|
|
||||||
static uint32_t setFlags(ThreadId threadId, uint32_t flags);
|
|
||||||
|
|
||||||
static uint32_t clearFlags(uint32_t flags);
|
|
||||||
|
|
||||||
static uint32_t getFlags();
|
|
||||||
|
|
||||||
static uint32_t awaitFlags(uint32_t flags, uint32_t options, uint32_t timeout);
|
|
||||||
};
|
|
||||||
|
|
||||||
constexpr auto THREAD_PRIORITY_SERVICE = Thread::Priority::High;
|
|
||||||
constexpr auto THREAD_PRIORITY_RENDER = Thread::Priority::Higher;
|
|
||||||
constexpr auto THREAD_PRIORITY_ISR = Thread::Priority::Critical;
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
@ -1,98 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#include "RtosCompatTimers.h"
|
|
||||||
#include "Thread.h"
|
|
||||||
|
|
||||||
#include <memory>
|
|
||||||
#include <functional>
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
class Timer {
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
typedef std::function<void()> Callback;
|
|
||||||
typedef void (*PendingCallback)(void* context, uint32_t arg);
|
|
||||||
|
|
||||||
private:
|
|
||||||
|
|
||||||
struct TimerHandleDeleter {
|
|
||||||
void operator()(TimerHandle_t handleToDelete) const {
|
|
||||||
xTimerDelete(handleToDelete, portMAX_DELAY);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
Callback callback;
|
|
||||||
std::unique_ptr<std::remove_pointer_t<TimerHandle_t>, TimerHandleDeleter> handle;
|
|
||||||
|
|
||||||
static void onCallback(TimerHandle_t hTimer);
|
|
||||||
|
|
||||||
public:
|
|
||||||
|
|
||||||
enum class Type {
|
|
||||||
Once = 0, ///< One-shot timer.
|
|
||||||
Periodic = 1 ///< Repeating timer.
|
|
||||||
};
|
|
||||||
|
|
||||||
enum class Priority{
|
|
||||||
Normal, /**< Lower then other threads */
|
|
||||||
Elevated, /**< Same as other threads */
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param[in] type The timer type
|
|
||||||
* @param[in] callback The callback function
|
|
||||||
*/
|
|
||||||
Timer(Type type, Callback callback);
|
|
||||||
|
|
||||||
~Timer();
|
|
||||||
|
|
||||||
/** Start timer
|
|
||||||
* @warning This is asynchronous call, real operation will happen as soon as timer service process this request.
|
|
||||||
* @param[in] interval The interval in ticks
|
|
||||||
* @return success result
|
|
||||||
*/
|
|
||||||
bool start(TickType_t interval);
|
|
||||||
|
|
||||||
/** Restart timer with previous timeout value
|
|
||||||
* @warning This is asynchronous call, real operation will happen as soon as timer service process this request.
|
|
||||||
* @param[in] interval The interval in ticks
|
|
||||||
* @return success result
|
|
||||||
*/
|
|
||||||
bool restart(TickType_t interval);
|
|
||||||
|
|
||||||
/** Stop timer
|
|
||||||
* @warning This is asynchronous call, real operation will happen as soon as timer service process this request.
|
|
||||||
* @return success result
|
|
||||||
*/
|
|
||||||
bool stop();
|
|
||||||
|
|
||||||
/** Is timer running
|
|
||||||
* @warning This cal may and will return obsolete timer state if timer commands are still in the queue. Please read FreeRTOS timer documentation first.
|
|
||||||
* @return true when running
|
|
||||||
*/
|
|
||||||
bool isRunning();
|
|
||||||
|
|
||||||
/** Get timer expire time
|
|
||||||
* @return expire tick
|
|
||||||
*/
|
|
||||||
TickType_t getExpireTime();
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Calls xTimerPendFunctionCall internally.
|
|
||||||
* @param[in] callback the function to call
|
|
||||||
* @param[in] callbackContext the first function argument
|
|
||||||
* @param[in] callbackArg the second function argument
|
|
||||||
* @param[in] timeout the function timeout (must set to 0 in ISR mode)
|
|
||||||
* @return true on success
|
|
||||||
*/
|
|
||||||
bool setPendingCallback(PendingCallback callback, void* callbackContext, uint32_t callbackArg, TickType_t timeout);
|
|
||||||
|
|
||||||
/** Set Timer thread priority
|
|
||||||
* @param[in] priority The priority
|
|
||||||
*/
|
|
||||||
void setThreadPriority(Thread::Priority priority);
|
|
||||||
};
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
@ -4,7 +4,8 @@
|
|||||||
*/
|
*/
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "Tactility/TactilityCore.h"
|
#include <Tactility/TactilityCore.h>
|
||||||
|
#include <Tactility/Lock.h>
|
||||||
|
|
||||||
#include <cstdio>
|
#include <cstdio>
|
||||||
#include <dirent.h>
|
#include <dirent.h>
|
||||||
|
|||||||
@ -1,117 +0,0 @@
|
|||||||
#pragma once
|
|
||||||
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
#include "freertos/FreeRTOS.h"
|
|
||||||
#include <esp_timer.h>
|
|
||||||
#else
|
|
||||||
#include "FreeRTOS.h"
|
|
||||||
#include <sys/time.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
namespace tt::kernel {
|
|
||||||
|
|
||||||
/** Recognized platform types */
|
|
||||||
typedef enum {
|
|
||||||
PlatformEsp,
|
|
||||||
PlatformSimulator
|
|
||||||
} Platform;
|
|
||||||
|
|
||||||
/** Return true when called from an Interrupt Service Routine (~IRQ mode) */
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
constexpr bool isIsr() { return (xPortInIsrContext() == pdTRUE); }
|
|
||||||
#else
|
|
||||||
constexpr bool isIsr() { return false; }
|
|
||||||
#endif
|
|
||||||
|
|
||||||
/** Check if kernel is running
|
|
||||||
* @return true if the FreeRTOS kernel is running, false otherwise
|
|
||||||
*/
|
|
||||||
bool isRunning();
|
|
||||||
|
|
||||||
/** Lock kernel, pause process scheduling
|
|
||||||
* @warning don't call from ISR context
|
|
||||||
* @return true on success
|
|
||||||
*/
|
|
||||||
bool lock();
|
|
||||||
|
|
||||||
/** Unlock kernel, resume process scheduling
|
|
||||||
* @warning don't call from ISR context
|
|
||||||
* @return true on success
|
|
||||||
*/
|
|
||||||
bool unlock();
|
|
||||||
|
|
||||||
/** Restore kernel lock state
|
|
||||||
* @warning don't call from ISR context
|
|
||||||
* @param[in] lock The lock state
|
|
||||||
* @return true on success
|
|
||||||
*/
|
|
||||||
bool restoreLock(bool lock);
|
|
||||||
|
|
||||||
/** Get kernel systick frequency
|
|
||||||
* @return systick counts per second
|
|
||||||
*/
|
|
||||||
uint32_t getTickFrequency();
|
|
||||||
|
|
||||||
TickType_t getTicks();
|
|
||||||
|
|
||||||
constexpr size_t getMillis() { return getTicks() / portTICK_PERIOD_MS; }
|
|
||||||
|
|
||||||
constexpr long int getMicros() {
|
|
||||||
#ifdef ESP_PLATFORM
|
|
||||||
return static_cast<unsigned long>(esp_timer_get_time());
|
|
||||||
#else
|
|
||||||
timeval tv;
|
|
||||||
gettimeofday(&tv, nullptr);
|
|
||||||
return 1000000 * tv.tv_sec + tv.tv_usec;
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
/** Delay execution
|
|
||||||
* @warning don't call from ISR context
|
|
||||||
* Also keep in mind delay is aliased to scheduler timer intervals.
|
|
||||||
* @param[in] ticks The ticks count to pause
|
|
||||||
*/
|
|
||||||
void delayTicks(TickType_t ticks);
|
|
||||||
|
|
||||||
/** Delay until tick
|
|
||||||
* @warning don't call from ISR context
|
|
||||||
* @param[in] ticks The tick until which kerel should delay task execution
|
|
||||||
* @return true on success
|
|
||||||
*/
|
|
||||||
bool delayUntilTick(TickType_t tick);
|
|
||||||
|
|
||||||
constexpr TickType_t secondsToTicks(uint32_t seconds) {
|
|
||||||
return static_cast<TickType_t>(seconds) * 1000U / portTICK_PERIOD_MS;
|
|
||||||
}
|
|
||||||
|
|
||||||
constexpr TickType_t minutesToTicks(uint32_t minutes) {
|
|
||||||
return secondsToTicks(minutes * 60U);
|
|
||||||
}
|
|
||||||
|
|
||||||
/** Convert milliseconds to ticks
|
|
||||||
*
|
|
||||||
* @param[in] milliSeconds time in milliseconds
|
|
||||||
* @return time in ticks
|
|
||||||
*/
|
|
||||||
TickType_t millisToTicks(uint32_t milliSeconds);
|
|
||||||
|
|
||||||
/** Delay in milliseconds
|
|
||||||
* This method uses kernel ticks on the inside, which causes delay to be aliased to scheduler timer intervals.
|
|
||||||
* Real wait time will be between X+ milliseconds.
|
|
||||||
* Special value: 0, will cause task yield.
|
|
||||||
* Also if used when kernel is not running will fall back to delayMicros()
|
|
||||||
* @warning don't call from ISR context
|
|
||||||
* @param[in] milliSeconds milliseconds to wait
|
|
||||||
*/
|
|
||||||
void delayMillis(uint32_t milliSeconds);
|
|
||||||
|
|
||||||
/** Delay in microseconds
|
|
||||||
* Implemented using Cortex DWT counter. Blocking and non aliased.
|
|
||||||
* @param[in] microSeconds microseconds to wait
|
|
||||||
*/
|
|
||||||
void delayMicros(uint32_t microSeconds);
|
|
||||||
|
|
||||||
/** @return the platform that Tactility currently is running on. */
|
|
||||||
Platform getPlatform();
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
14
TactilityCore/Include/Tactility/kernel/Platform.h
Normal file
14
TactilityCore/Include/Tactility/kernel/Platform.h
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
namespace tt::kernel {
|
||||||
|
|
||||||
|
/** Recognized platform types */
|
||||||
|
typedef enum {
|
||||||
|
PlatformEsp,
|
||||||
|
PlatformSimulator
|
||||||
|
} Platform;
|
||||||
|
|
||||||
|
/** @return the platform that Tactility currently is running on. */
|
||||||
|
Platform getPlatform();
|
||||||
|
|
||||||
|
} // namespace
|
||||||
@ -1,9 +1,9 @@
|
|||||||
#include "Tactility/Check.h"
|
#include <Tactility/Check.h>
|
||||||
|
|
||||||
#include "Tactility/Log.h"
|
#include <Tactility/Log.h>
|
||||||
#include "Tactility/RtosCompatTask.h"
|
#include <Tactility/freertoscompat/Task.h>
|
||||||
|
|
||||||
#define TAG "kernel"
|
constexpr auto TAG = "kernel";
|
||||||
|
|
||||||
static void logMemoryInfo() {
|
static void logMemoryInfo() {
|
||||||
#ifdef ESP_PLATFORM
|
#ifdef ESP_PLATFORM
|
||||||
|
|||||||
@ -1,70 +0,0 @@
|
|||||||
#include "Tactility/Dispatcher.h"
|
|
||||||
|
|
||||||
#include "Tactility/Check.h"
|
|
||||||
#include "Tactility/kernel/Kernel.h"
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
#define TAG "dispatcher"
|
|
||||||
#define BACKPRESSURE_WARNING_COUNT ((EventBits_t)100)
|
|
||||||
#define WAIT_FLAG ((EventBits_t)1U)
|
|
||||||
|
|
||||||
Dispatcher::~Dispatcher() {
|
|
||||||
// Wait for Mutex usage
|
|
||||||
mutex.lock();
|
|
||||||
mutex.unlock();
|
|
||||||
}
|
|
||||||
|
|
||||||
bool Dispatcher::dispatch(Function function, TickType_t timeout) {
|
|
||||||
// Mutate
|
|
||||||
if (mutex.lock(timeout)) {
|
|
||||||
queue.push(std::move(function));
|
|
||||||
if (queue.size() == BACKPRESSURE_WARNING_COUNT) {
|
|
||||||
TT_LOG_W(TAG, "Backpressure: You're not consuming fast enough (100 queued)");
|
|
||||||
}
|
|
||||||
tt_check(mutex.unlock());
|
|
||||||
// Signal
|
|
||||||
eventFlag.set(WAIT_FLAG);
|
|
||||||
return true;
|
|
||||||
} else {
|
|
||||||
TT_LOG_E(TAG, LOG_MESSAGE_MUTEX_LOCK_FAILED);
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t Dispatcher::consume(TickType_t timeout) {
|
|
||||||
// Wait for signal
|
|
||||||
uint32_t result = eventFlag.wait(WAIT_FLAG, EventFlag::WaitAny, timeout);
|
|
||||||
if (result & EventFlag::Error) {
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
eventFlag.clear(WAIT_FLAG);
|
|
||||||
|
|
||||||
// Mutate
|
|
||||||
bool processing = true;
|
|
||||||
uint32_t consumed = 0;
|
|
||||||
do {
|
|
||||||
if (mutex.lock(10)) {
|
|
||||||
if (!queue.empty()) {
|
|
||||||
auto function = queue.front();
|
|
||||||
queue.pop();
|
|
||||||
consumed++;
|
|
||||||
processing = !queue.empty();
|
|
||||||
// Don't keep lock as callback might be slow
|
|
||||||
mutex.unlock();
|
|
||||||
function();
|
|
||||||
} else {
|
|
||||||
processing = false;
|
|
||||||
mutex.unlock();
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
TT_LOG_W(TAG, LOG_MESSAGE_MUTEX_LOCK_FAILED);
|
|
||||||
}
|
|
||||||
|
|
||||||
} while (processing);
|
|
||||||
|
|
||||||
return consumed;
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
@ -1,47 +0,0 @@
|
|||||||
#include "Tactility/DispatcherThread.h"
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
DispatcherThread::DispatcherThread(const std::string& threadName, size_t threadStackSize) {
|
|
||||||
thread = std::make_unique<Thread>(
|
|
||||||
threadName,
|
|
||||||
threadStackSize,
|
|
||||||
[this] {
|
|
||||||
return threadMain();
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
DispatcherThread::~DispatcherThread() {
|
|
||||||
if (thread->getState() != Thread::State::Stopped) {
|
|
||||||
stop();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int32_t DispatcherThread::threadMain() {
|
|
||||||
do {
|
|
||||||
/**
|
|
||||||
* If this value is too high (e.g. 1 second) then the dispatcher destroys too slowly when the simulator exits.
|
|
||||||
* This causes the problems with other services doing an update (e.g. Statusbar) and calling into destroyed mutex in the global scope.
|
|
||||||
*/
|
|
||||||
dispatcher.consume(100 / portTICK_PERIOD_MS);
|
|
||||||
} while (!interruptThread);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool DispatcherThread::dispatch(Dispatcher::Function function, TickType_t timeout) {
|
|
||||||
return dispatcher.dispatch(function, timeout);
|
|
||||||
}
|
|
||||||
|
|
||||||
void DispatcherThread::start() {
|
|
||||||
interruptThread = false;
|
|
||||||
thread->start();
|
|
||||||
}
|
|
||||||
|
|
||||||
void DispatcherThread::stop() {
|
|
||||||
interruptThread = true;
|
|
||||||
thread->join();
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
@ -1,135 +0,0 @@
|
|||||||
#include "Tactility/EventFlag.h"
|
|
||||||
|
|
||||||
#include "Tactility/Check.h"
|
|
||||||
#include "Tactility/kernel/Kernel.h"
|
|
||||||
|
|
||||||
#define TT_EVENT_FLAG_MAX_BITS_EVENT_GROUPS 24U
|
|
||||||
#define TT_EVENT_FLAG_INVALID_BITS (~((1UL << TT_EVENT_FLAG_MAX_BITS_EVENT_GROUPS) - 1U))
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
EventFlag::EventFlag() :
|
|
||||||
handle(xEventGroupCreate())
|
|
||||||
{
|
|
||||||
assert(!kernel::isIsr());
|
|
||||||
tt_check(handle);
|
|
||||||
}
|
|
||||||
|
|
||||||
EventFlag::~EventFlag() {
|
|
||||||
assert(!kernel::isIsr());
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t EventFlag::set(uint32_t flags) const {
|
|
||||||
assert(handle);
|
|
||||||
assert((flags & TT_EVENT_FLAG_INVALID_BITS) == 0U);
|
|
||||||
|
|
||||||
uint32_t rflags;
|
|
||||||
BaseType_t yield;
|
|
||||||
|
|
||||||
if (kernel::isIsr()) {
|
|
||||||
yield = pdFALSE;
|
|
||||||
if (xEventGroupSetBitsFromISR(handle.get(), (EventBits_t)flags, &yield) == pdFAIL) {
|
|
||||||
rflags = (uint32_t)ErrorResource;
|
|
||||||
} else {
|
|
||||||
rflags = flags;
|
|
||||||
portYIELD_FROM_ISR(yield);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
rflags = xEventGroupSetBits(handle.get(), (EventBits_t)flags);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Return event flags after setting */
|
|
||||||
return rflags;
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t EventFlag::clear(uint32_t flags) const {
|
|
||||||
assert((flags & TT_EVENT_FLAG_INVALID_BITS) == 0U);
|
|
||||||
|
|
||||||
uint32_t rflags;
|
|
||||||
|
|
||||||
if (kernel::isIsr()) {
|
|
||||||
rflags = xEventGroupGetBitsFromISR(handle.get());
|
|
||||||
|
|
||||||
if (xEventGroupClearBitsFromISR(handle.get(), (EventBits_t)flags) == pdFAIL) {
|
|
||||||
rflags = (uint32_t)ErrorResource;
|
|
||||||
} else {
|
|
||||||
/* xEventGroupClearBitsFromISR only registers clear operation in the timer command queue. */
|
|
||||||
/* Yield is required here otherwise clear operation might not execute in the right order. */
|
|
||||||
/* See https://github.com/FreeRTOS/FreeRTOS-Kernel/issues/93 for more info. */
|
|
||||||
portYIELD_FROM_ISR(pdTRUE);
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
rflags = xEventGroupClearBits(handle.get(), (EventBits_t)flags);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Return event flags before clearing */
|
|
||||||
return rflags;
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t EventFlag::get() const {
|
|
||||||
uint32_t rflags;
|
|
||||||
|
|
||||||
if (kernel::isIsr()) {
|
|
||||||
rflags = xEventGroupGetBitsFromISR(handle.get());
|
|
||||||
} else {
|
|
||||||
rflags = xEventGroupGetBits(handle.get());
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Return current event flags */
|
|
||||||
return (rflags);
|
|
||||||
}
|
|
||||||
|
|
||||||
uint32_t EventFlag::wait(
|
|
||||||
uint32_t flags,
|
|
||||||
uint32_t options,
|
|
||||||
uint32_t timeoutTicksw
|
|
||||||
) const {
|
|
||||||
assert(!kernel::isIsr());
|
|
||||||
assert((flags & TT_EVENT_FLAG_INVALID_BITS) == 0U);
|
|
||||||
|
|
||||||
BaseType_t wait_all;
|
|
||||||
BaseType_t exit_clear;
|
|
||||||
uint32_t rflags;
|
|
||||||
|
|
||||||
if (options & WaitAll) {
|
|
||||||
wait_all = pdTRUE;
|
|
||||||
} else {
|
|
||||||
wait_all = pdFALSE;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (options & NoClear) {
|
|
||||||
exit_clear = pdFALSE;
|
|
||||||
} else {
|
|
||||||
exit_clear = pdTRUE;
|
|
||||||
}
|
|
||||||
|
|
||||||
rflags = xEventGroupWaitBits(
|
|
||||||
handle.get(),
|
|
||||||
(EventBits_t)flags,
|
|
||||||
exit_clear,
|
|
||||||
wait_all,
|
|
||||||
(TickType_t)timeoutTicksw
|
|
||||||
);
|
|
||||||
|
|
||||||
if (options & WaitAll) {
|
|
||||||
if ((flags & rflags) != flags) {
|
|
||||||
if (timeoutTicksw > 0U) {
|
|
||||||
rflags = (uint32_t)ErrorTimeout;
|
|
||||||
} else {
|
|
||||||
rflags = (uint32_t)ErrorResource;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
if ((flags & rflags) == 0U) {
|
|
||||||
if (timeoutTicksw > 0U) {
|
|
||||||
rflags = (uint32_t)ErrorTimeout;
|
|
||||||
} else {
|
|
||||||
rflags = (uint32_t)ErrorResource;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return rflags;
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace
|
|
||||||
@ -1,9 +0,0 @@
|
|||||||
#include "Tactility/Lock.h"
|
|
||||||
|
|
||||||
namespace tt {
|
|
||||||
|
|
||||||
ScopedLock Lock::asScopedLock() const {
|
|
||||||
return ScopedLock(*this);
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user