From d309c47269952a3afbd6196839939675b91b030d Mon Sep 17 00:00:00 2001 From: DocWilco Date: Thu, 27 Nov 2025 14:27:13 +0100 Subject: [PATCH] Add EspLog to log through ESP-IDF on ESP32 devices This still needs to be manually enabled in Config.hpp, like all the other Log variants. --- include/ableton/platforms/Config.hpp | 1 + include/ableton/platforms/esp32/Log.hpp | 138 ++++++++++++++++++++++++ 2 files changed, 139 insertions(+) create mode 100644 include/ableton/platforms/esp32/Log.hpp diff --git a/include/ableton/platforms/Config.hpp b/include/ableton/platforms/Config.hpp index a95c9b76..3fdd5d5d 100644 --- a/include/ableton/platforms/Config.hpp +++ b/include/ableton/platforms/Config.hpp @@ -47,6 +47,7 @@ #elif defined(ESP_PLATFORM) #include #include +#include #include #include #endif diff --git a/include/ableton/platforms/esp32/Log.hpp b/include/ableton/platforms/esp32/Log.hpp new file mode 100644 index 00000000..ceadc796 --- /dev/null +++ b/include/ableton/platforms/esp32/Log.hpp @@ -0,0 +1,138 @@ +/* Copyright 2025, All rights reserved. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program. If not, see . + */ + +#pragma once + +#include +#include +#include + +namespace ableton +{ +namespace platforms +{ +namespace esp32 +{ + +// ESP-IDF logging implementation for Ableton Link +struct EspLog +{ + enum class Level + { + Debug, + Info, + Warning, + Error + }; + + // Tag used for all Link logging + // + // All Link logging should go through this tag, since ESP-IDF has a lot of + // internal logging and this helps to manage being able to filter. + // + // ESP-IDF has no wildcard filtering support, so for channels we prepend the + // channel name to the message text, since channels can be created based on + // dynamic data, like IP addresses. + static constexpr const char* kTag = "ableton_link"; + + EspLog() = default; + + explicit EspLog(std::string context) + : mContext(std::move(context)) + { + } + + struct EspLogStream + { + EspLogStream(Level level, const std::string& context) + : mLevel(level) + , mContext(context) + { + } + + EspLogStream(EspLogStream&& rhs) + : mLevel(rhs.mLevel) + , mContext(rhs.mContext) + , mStream(std::move(rhs.mStream)) + { + rhs.mMoved = true; + } + + ~EspLogStream() + { + if (!mMoved) + { + std::string msg = mStream.str(); + // Prepend context to message if present + if (!mContext.empty()) + { + msg = "[" + mContext + "] " + msg; + } + switch (mLevel) + { + case Level::Debug: + ESP_LOGD(kTag, "%s", msg.c_str()); + break; + case Level::Info: + ESP_LOGI(kTag, "%s", msg.c_str()); + break; + case Level::Warning: + ESP_LOGW(kTag, "%s", msg.c_str()); + break; + case Level::Error: + ESP_LOGE(kTag, "%s", msg.c_str()); + break; + } + } + } + + template + EspLogStream& operator<<(const T& rhs) + { + mStream << rhs; + return *this; + } + + Level mLevel; + const std::string& mContext; + std::ostringstream mStream; + bool mMoved = false; + }; + + friend EspLogStream debug(const EspLog& log) { return {Level::Debug, log.mContext}; } + + friend EspLogStream info(const EspLog& log) { return {Level::Info, log.mContext}; } + + friend EspLogStream warning(const EspLog& log) + { + return {Level::Warning, log.mContext}; + } + + friend EspLogStream error(const EspLog& log) { return {Level::Error, log.mContext}; } + + friend EspLog channel(const EspLog& log, const std::string& channelName) + { + auto newContext = + log.mContext.empty() ? channelName : log.mContext + "::" + channelName; + return EspLog{std::move(newContext)}; + } + + std::string mContext; +}; + +} // namespace esp32 +} // namespace platforms +} // namespace ableton