15#if defined(FL_LOG_SPI_ENABLED) && !defined(FASTLED_LOG_SPI_ENABLED)
16 #define FASTLED_LOG_SPI_ENABLED
18#if defined(FL_LOG_RMT_ENABLED) && !defined(FASTLED_LOG_RMT_ENABLED)
19 #define FASTLED_LOG_RMT_ENABLED
21#if defined(FL_LOG_PARLIO_ENABLED) && !defined(FASTLED_LOG_PARLIO_ENABLED)
22 #define FASTLED_LOG_PARLIO_ENABLED
24#if defined(FL_LOG_AUDIO_ENABLED) && !defined(FASTLED_LOG_AUDIO_ENABLED)
25 #define FASTLED_LOG_AUDIO_ENABLED
27#if defined(FL_LOG_INTERRUPT_ENABLED) && !defined(FASTLED_LOG_INTERRUPT_ENABLED)
28 #define FASTLED_LOG_INTERRUPT_ENABLED
30#if defined(FL_LOG_FLEXIO_ENABLED) && !defined(FASTLED_LOG_FLEXIO_ENABLED)
31 #define FASTLED_LOG_FLEXIO_ENABLED
33#if defined(FL_LOG_OBJECTFLED_ENABLED) && !defined(FASTLED_LOG_OBJECTFLED_ENABLED)
34 #define FASTLED_LOG_OBJECTFLED_ENABLED
38#if defined(FASTLED_LOG_SPI_ENABLED) || defined(FASTLED_LOG_RMT_ENABLED) || defined(FASTLED_LOG_PARLIO_ENABLED) || defined(FASTLED_LOG_AUDIO_ENABLED) || defined(FASTLED_LOG_INTERRUPT_ENABLED)
82 #define FL_LOG_LEVEL 2
83#elif !defined(FL_LOG_LEVEL)
84 #if defined(FASTLED_LOG_VERBOSITY)
85 #if FASTLED_LOG_VERBOSITY >= 1
86 #define FL_LOG_LEVEL 2
88 #define FL_LOG_LEVEL 0
91 #define FL_LOG_LEVEL 0
93 #define FL_LOG_LEVEL 1
100#if SKETCH_HAS_LARGE_MEMORY && (FL_LOG_LEVEL >= 1)
101 #define FASTLED_LOG_RUNTIME_ENABLED 1
103 #define FASTLED_LOG_RUNTIME_ENABLED 0
108#if SKETCH_HAS_LARGE_MEMORY && (FL_LOG_LEVEL >= 2)
109 #define FL_HAS_WARN 1
111 #define FL_HAS_WARN 0
121 #define FASTLED_LOG_LITE_ENABLED 1
123 #define FASTLED_LOG_LITE_ENABLED 0
132#ifndef FL_PRINTLN_DECLARED
133#define FL_PRINTLN_DECLARED
218 template <
typename T>
231 template <fl::size N>
236 template <
typename T>
276template <
typename Logger, fl::size N>
279 logger.push(body.c_str());
282template <
typename Logger>
285 logger.push(body.str());
288template <
typename Logger>
291 logger.push(body.str());
317#define _FL_VA_PICK17( \
318 _1, _2, _3, _4, _5, _6, _7, _8, \
319 _9, _10, _11, _12, _13, _14, _15, _16, \
322#define _FL_VA_DISPATCH(_S, _M, ...) \
323 _FL_VA_PICK17(__VA_ARGS__, \
324 _M, _M, _M, _M, _M, _M, _M, _M, \
325 _M, _M, _M, _M, _M, _M, _M, _S)
334#define _FL_LOG_PRINTF_BANNED(...) do { \
335 FL_STATIC_ASSERT(sizeof(#__VA_ARGS__) == 0, \
336 "FastLED: printf-style log formatting is not allowed; use stream " \
337 "form, e.g. FL_WARN(\"x=\" << x). See FastLED#4709."); \
339#define _FL_LOG_NOOP_S(X) do { } while(0)
342#define _FL_LOG_CHECK(...) _FL_VA_DISPATCH(_FL_LOG_NOOP_S, _FL_LOG_PRINTF_BANNED, __VA_ARGS__)(__VA_ARGS__)
349#define _FL_ERROR_S(X) ::fl::detail::log_emit_auto( \
350 ::fl::detail::log_kind::ERROR, \
351 ::fl::fastled_file_offset(__FILE__), int(__LINE__), \
352 ::fl::detail::log_seed() << X)
353#define _FL_ERROR_M(...) _FL_LOG_PRINTF_BANNED(__VA_ARGS__)
358#define FASTLED_ERROR(...) _FL_VA_DISPATCH(_FL_ERROR_S, _FL_ERROR_M, __VA_ARGS__)(__VA_ARGS__)
359#define FASTLED_ERROR_IF(COND, ...) do { if (COND) FASTLED_ERROR(__VA_ARGS__); } while(0)
363#if FASTLED_LOG_RUNTIME_ENABLED
366#define FL_ERROR(...) _FL_VA_DISPATCH(_FL_ERROR_S, _FL_ERROR_M, __VA_ARGS__)(__VA_ARGS__)
367#define FL_ERROR_IF(COND, ...) do { if (COND) FL_ERROR(__VA_ARGS__); } while(0)
373#define FL_ERROR(...) _FL_LOG_CHECK(__VA_ARGS__)
374#define FL_ERROR_IF(COND, ...) _FL_LOG_CHECK(__VA_ARGS__)
383#define _FL_WARN_S(X) ::fl::detail::log_emit_auto( \
384 ::fl::detail::log_kind::WARN, \
385 ::fl::fastled_file_offset(__FILE__), int(__LINE__), \
386 ::fl::detail::log_seed() << X)
387#define _FL_WARN_M(...) _FL_LOG_PRINTF_BANNED(__VA_ARGS__)
392#define FASTLED_WARN(...) _FL_VA_DISPATCH(_FL_WARN_S, _FL_WARN_M, __VA_ARGS__)(__VA_ARGS__)
393#define FASTLED_WARN_IF(COND, ...) do { if (COND) FASTLED_WARN(__VA_ARGS__); } while(0)
400#define FL_WARN(...) _FL_VA_DISPATCH(_FL_WARN_S, _FL_WARN_M, __VA_ARGS__)(__VA_ARGS__)
401#define FL_WARN_IF(COND, ...) do { if (COND) FL_WARN(__VA_ARGS__); } while(0)
405#define FL_WARN_ONCE(...) do { \
406 static bool _warned = false; \
409 FL_WARN(__VA_ARGS__); \
414#define FL_WARN_FMT(...) FL_WARN(__VA_ARGS__)
415#define FL_WARN_FMT_IF(COND, ...) FL_WARN_IF(COND, __VA_ARGS__)
423#define FL_WARN_EVERY(MILLIS, ...) do { \
424 static fl::u32 _last_warn_time = 0; \
425 fl::u32 _now = fl::millis(); \
426 if (_now - _last_warn_time >= (MILLIS)) { \
427 _last_warn_time = _now; \
428 FL_WARN(__VA_ARGS__); \
437#define FL_WARN(...) _FL_LOG_CHECK(__VA_ARGS__)
438#define FL_WARN_IF(COND, ...) _FL_LOG_CHECK(__VA_ARGS__)
439#define FL_WARN_ONCE(...) _FL_LOG_CHECK(__VA_ARGS__)
440#define FL_WARN_FMT(...) _FL_LOG_CHECK(__VA_ARGS__)
441#define FL_WARN_FMT_IF(COND, ...) _FL_LOG_CHECK(__VA_ARGS__)
442#define FL_WARN_EVERY(MILLIS, ...) _FL_LOG_CHECK(__VA_ARGS__)
451#if FASTLED_LOG_LITE_ENABLED
452#define FL_WARN_LIT(LITERAL) fl::println(LITERAL)
453#define FL_LOG_LIT(LITERAL) fl::println(LITERAL)
455#define FL_WARN_LIT(LITERAL) do { } while(0)
456#define FL_LOG_LIT(LITERAL) do { } while(0)
465#define _FL_INFO_S(X) ::fl::detail::log_emit_auto( \
466 ::fl::detail::log_kind::INFO, \
467 ::fl::fastled_file_offset(__FILE__), int(__LINE__), \
468 ::fl::detail::log_seed() << X)
469#define _FL_INFO_M(...) _FL_LOG_PRINTF_BANNED(__VA_ARGS__)
474#define FASTLED_INFO(...) _FL_VA_DISPATCH(_FL_INFO_S, _FL_INFO_M, __VA_ARGS__)(__VA_ARGS__)
475#define FASTLED_INFO_IF(COND, ...) do { if (COND) FASTLED_INFO(__VA_ARGS__); } while(0)
482#define FL_INFO(...) _FL_VA_DISPATCH(_FL_INFO_S, _FL_INFO_M, __VA_ARGS__)(__VA_ARGS__)
483#define FL_INFO_IF(COND, ...) do { if (COND) FL_INFO(__VA_ARGS__); } while(0)
487#define FL_INFO_ONCE(...) do { \
488 static bool _infoed = false; \
491 FL_INFO(__VA_ARGS__); \
496#define FL_INFO(...) _FL_LOG_CHECK(__VA_ARGS__)
497#define FL_INFO_IF(COND, ...) _FL_LOG_CHECK(__VA_ARGS__)
498#define FL_INFO_ONCE(...) _FL_LOG_CHECK(__VA_ARGS__)
506#if defined(FL_IS_WASM) || !defined(RELEASE) || defined(FASTLED_TESTING)
507#define FASTLED_FORCE_DBG 1
511#define FL_DBG_NO_OP(X) do { if (false) { fl::sstream_noop() << X; } } while(0)
520#if defined(FASTLED_DISABLE_DBG) && FASTLED_DISABLE_DBG
522#define FASTLED_HAS_DBG 0
523#define _FASTLED_DGB(X) FL_DBG_NO_OP(X)
524#elif FL_LOG_LEVEL < 2
526#define FASTLED_HAS_DBG 0
527#define _FASTLED_DGB(X) FL_DBG_NO_OP(X)
528#elif !defined(FASTLED_FORCE_DBG) && !SKETCH_HAS_LARGE_MEMORY
530#define FASTLED_HAS_DBG 0
531#define _FASTLED_DGB(X) FL_DBG_NO_OP(X)
534#define FASTLED_HAS_DBG 1
535#define _FASTLED_DGB(X) ::fl::detail::log_emit_auto( \
536 ::fl::detail::log_kind::INFO, \
537 ::fl::fastled_file_offset(__FILE__), int(__LINE__), \
538 ::fl::detail::log_seed() << X)
539#define _FL_DBG_M(...) _FL_LOG_PRINTF_BANNED(__VA_ARGS__)
543#define _FL_DBG_M(...) _FL_LOG_PRINTF_BANNED(__VA_ARGS__)
545#define FASTLED_DBG(...) _FL_VA_DISPATCH(_FASTLED_DGB, _FL_DBG_M, __VA_ARGS__)(__VA_ARGS__)
547#ifndef FASTLED_DBG_IF
548#define FASTLED_DBG_IF(COND, ...) do { if (COND) FASTLED_DBG(__VA_ARGS__); } while(0)
553#define FL_DBG FASTLED_DBG
554#define FL_DBG_IF FASTLED_DBG_IF
559#define FL_DBG_EVERY(MILLIS, ...) do { \
560 static fl::u32 _last_dbg_time = 0; \
561 fl::u32 _now = fl::millis(); \
562 if (_now - _last_dbg_time >= (MILLIS)) { \
563 _last_dbg_time = _now; \
564 FL_DBG(__VA_ARGS__); \
568#define FL_DBG_EVERY(MILLIS, ...) _FL_LOG_CHECK(__VA_ARGS__)
608#define _FL_PRINT_S(X) ::fl::detail::print_emit_auto(::fl::detail::log_seed() << X)
609#define _FL_PRINT_M(...) _FL_LOG_PRINTF_BANNED(__VA_ARGS__)
612#if FASTLED_LOG_RUNTIME_ENABLED
615#define FL_PRINT(...) _FL_VA_DISPATCH(_FL_PRINT_S, _FL_PRINT_M, __VA_ARGS__)(__VA_ARGS__)
619#define FL_PRINT_EVERY(MILLIS, ...) do { \
620 static fl::u32 _last_print_time = 0; \
621 fl::u32 _now = fl::millis(); \
622 if (_now - _last_print_time >= (MILLIS)) { \
623 _last_print_time = _now; \
624 FL_PRINT(__VA_ARGS__); \
629#define FL_PRINT(...) _FL_LOG_CHECK(__VA_ARGS__)
630#define FL_PRINT_EVERY(MILLIS, ...) _FL_LOG_CHECK(__VA_ARGS__)
643#ifdef FASTLED_LOG_SPI_ENABLED
644 #define FL_LOG_SPI(...) FL_WARN(__VA_ARGS__)
646 #define FL_LOG_SPI(...) _FL_LOG_CHECK(__VA_ARGS__)
651#if defined(FASTLED_LOG_RMT_ENABLED) && FL_HAS_WARN
652 #define FL_HAS_RMT_LOG 1
653 #define FL_LOG_RMT(...) FL_WARN(__VA_ARGS__)
655 #define FL_HAS_RMT_LOG 0
656 #define FL_LOG_RMT(...) _FL_LOG_CHECK(__VA_ARGS__)
661#ifdef FASTLED_LOG_PARLIO_ENABLED
662 #define FL_LOG_PARLIO(...) FL_WARN(__VA_ARGS__)
664 #define FL_LOG_PARLIO(...) _FL_LOG_CHECK(__VA_ARGS__)
669#ifdef FASTLED_LOG_AUDIO_ENABLED
670 #define FL_LOG_AUDIO(...) FL_WARN(__VA_ARGS__)
672 #define FL_LOG_AUDIO(...) _FL_LOG_CHECK(__VA_ARGS__)
677#ifdef FASTLED_LOG_INTERRUPT_ENABLED
678 #define FL_LOG_INTERRUPT(...) FL_WARN(__VA_ARGS__)
680 #define FL_LOG_INTERRUPT(...) _FL_LOG_CHECK(__VA_ARGS__)
685#ifdef FASTLED_LOG_FLEXIO_ENABLED
686 #define FL_LOG_FLEXIO(...) FL_WARN(__VA_ARGS__)
688 #define FL_LOG_FLEXIO(...) _FL_LOG_CHECK(__VA_ARGS__)
693#ifdef FASTLED_LOG_OBJECTFLED_ENABLED
694 #define FL_LOG_OBJECTFLED(...) FL_WARN(__VA_ARGS__)
696 #define FL_LOG_OBJECTFLED(...) _FL_LOG_CHECK(__VA_ARGS__)
765#define _FL_LOG_ASYNC_S(logger, X) do { \
766 ::fl::detail::async_log_emit_auto((logger), ::fl::detail::log_seed() << X); \
768#define _FL_LOG_ASYNC_M(logger, ...) _FL_LOG_PRINTF_BANNED(__VA_ARGS__)
772#define FL_LOG_ASYNC(logger, ...) _FL_VA_DISPATCH(_FL_LOG_ASYNC_S, _FL_LOG_ASYNC_M, __VA_ARGS__)(logger, __VA_ARGS__)
780#define FL_LOG_ASYNC_ISR(logger, msg) \
782 (logger).push(msg); \
789#ifdef FASTLED_LOG_SPI_ENABLED
790 #define FL_LOG_SPI_ASYNC_ISR(X) FL_LOG_ASYNC_ISR(fl::get_spi_async_logger_isr(), X)
791 #define FL_LOG_SPI_ASYNC_MAIN(...) FL_LOG_ASYNC(fl::get_spi_async_logger_main(), __VA_ARGS__)
792 #define FL_LOG_SPI_ASYNC_FLUSH() do { \
793 fl::get_spi_async_logger_isr().flush(); \
794 fl::get_spi_async_logger_main().flush(); \
797 #define FL_LOG_SPI_ASYNC_ISR(X) FL_DBG_NO_OP(X)
798 #define FL_LOG_SPI_ASYNC_MAIN(...) do { } while(0)
799 #define FL_LOG_SPI_ASYNC_FLUSH() do {} while(0)
806#ifdef FASTLED_LOG_RMT_ENABLED
807 #define FL_LOG_RMT_ASYNC_ISR(X) FL_LOG_ASYNC_ISR(fl::get_rmt_async_logger_isr(), X)
808 #define FL_LOG_RMT_ASYNC_MAIN(...) FL_LOG_ASYNC(fl::get_rmt_async_logger_main(), __VA_ARGS__)
809 #define FL_LOG_RMT_ASYNC_FLUSH() do { \
810 fl::get_rmt_async_logger_isr().flush(); \
811 fl::get_rmt_async_logger_main().flush(); \
814 #define FL_LOG_RMT_ASYNC_ISR(X) FL_DBG_NO_OP(X)
815 #define FL_LOG_RMT_ASYNC_MAIN(...) do { } while(0)
816 #define FL_LOG_RMT_ASYNC_FLUSH() do {} while(0)
823#ifdef FASTLED_LOG_PARLIO_ENABLED
824 #define FL_LOG_PARLIO_ASYNC_ISR(X) FL_LOG_ASYNC_ISR(fl::get_parlio_async_logger_isr(), X)
825 #define FL_LOG_PARLIO_ASYNC_MAIN(...) FL_LOG_ASYNC(fl::get_parlio_async_logger_main(), __VA_ARGS__)
826 #define FL_LOG_PARLIO_ASYNC_FLUSH() do { \
827 fl::get_parlio_async_logger_isr().flush(); \
828 fl::get_parlio_async_logger_main().flush(); \
831 #define FL_LOG_PARLIO_ASYNC_ISR(X) FL_DBG_NO_OP(X)
832 #define FL_LOG_PARLIO_ASYNC_MAIN(...) do { } while(0)
833 #define FL_LOG_PARLIO_ASYNC_FLUSH() do {} while(0)
840#ifdef FASTLED_LOG_AUDIO_ENABLED
841 #define FL_LOG_AUDIO_ASYNC_ISR(X) FL_LOG_ASYNC_ISR(fl::get_audio_async_logger_isr(), X)
842 #define FL_LOG_AUDIO_ASYNC_MAIN(...) FL_LOG_ASYNC(fl::get_audio_async_logger_main(), __VA_ARGS__)
843 #define FL_LOG_AUDIO_ASYNC_FLUSH() do { \
844 fl::get_audio_async_logger_isr().flush(); \
845 fl::get_audio_async_logger_main().flush(); \
848 #define FL_LOG_AUDIO_ASYNC_ISR(X) FL_DBG_NO_OP(X)
849 #define FL_LOG_AUDIO_ASYNC_MAIN(...) do { } while(0)
850 #define FL_LOG_AUDIO_ASYNC_FLUSH() do {} while(0)
857#ifdef FASTLED_LOG_INTERRUPT_ENABLED
858 #define FL_LOG_INTERRUPT_ASYNC_ISR(X) FL_LOG_ASYNC_ISR(fl::get_interrupt_async_logger_isr(), X)
859 #define FL_LOG_INTERRUPT_ASYNC_MAIN(...) FL_LOG_ASYNC(fl::get_interrupt_async_logger_main(), __VA_ARGS__)
860 #define FL_LOG_INTERRUPT_ASYNC_FLUSH() do { \
861 fl::get_interrupt_async_logger_isr().flush(); \
862 fl::get_interrupt_async_logger_main().flush(); \
865 #define FL_LOG_INTERRUPT_ASYNC_ISR(X) FL_DBG_NO_OP(X)
866 #define FL_LOG_INTERRUPT_ASYNC_MAIN(...) do { } while(0)
867 #define FL_LOG_INTERRUPT_ASYNC_FLUSH() do {} while(0)
874#ifdef FASTLED_LOG_FLEXIO_ENABLED
875 #define FL_LOG_FLEXIO_ASYNC_ISR(X) FL_LOG_ASYNC_ISR(fl::get_flexio_async_logger_isr(), X)
876 #define FL_LOG_FLEXIO_ASYNC_MAIN(...) FL_LOG_ASYNC(fl::get_flexio_async_logger_main(), __VA_ARGS__)
877 #define FL_LOG_FLEXIO_ASYNC_FLUSH() do { \
878 fl::get_flexio_async_logger_isr().flush(); \
879 fl::get_flexio_async_logger_main().flush(); \
882 #define FL_LOG_FLEXIO_ASYNC_ISR(X) FL_DBG_NO_OP(X)
883 #define FL_LOG_FLEXIO_ASYNC_MAIN(...) do { } while(0)
884 #define FL_LOG_FLEXIO_ASYNC_FLUSH() do {} while(0)
891#ifdef FASTLED_LOG_OBJECTFLED_ENABLED
892 #define FL_LOG_OBJECTFLED_ASYNC_ISR(X) FL_LOG_ASYNC_ISR(fl::get_objectfled_async_logger_isr(), X)
893 #define FL_LOG_OBJECTFLED_ASYNC_MAIN(...) FL_LOG_ASYNC(fl::get_objectfled_async_logger_main(), __VA_ARGS__)
894 #define FL_LOG_OBJECTFLED_ASYNC_FLUSH() do { \
895 fl::get_objectfled_async_logger_isr().flush(); \
896 fl::get_objectfled_async_logger_main().flush(); \
899 #define FL_LOG_OBJECTFLED_ASYNC_ISR(X) FL_DBG_NO_OP(X)
900 #define FL_LOG_OBJECTFLED_ASYNC_MAIN(...) do { } while(0)
901 #define FL_LOG_OBJECTFLED_ASYNC_FLUSH() do {} while(0)
ISR-safe async logger using SPSC queue backend (zero heap allocation)
FastLED chrono implementation - duration types for time measurements.
const char * c_str() const FL_NO_EXCEPT
log_literal(const char(&text)[N]) FL_NO_EXCEPT
fl::sstream operator<<(const T &value) const FL_NO_EXCEPT
log_literal< N > operator<<(const char(&text)[N]) const FL_NO_EXCEPT
fl::sstream operator<<(const T &value) const FL_NO_EXCEPT
void print_emit_auto(const log_literal< N > &body) FL_NO_EXCEPT
FL_NO_INLINE const char * log_kind_name(log_kind kind) FL_NO_EXCEPT
FL_NO_INLINE void log_emit_prefix(log_kind kind, const char *file, int line) FL_NO_EXCEPT
void async_log_emit_auto(Logger &logger, const log_literal< N > &body) FL_NO_EXCEPT
FL_NO_INLINE void log_emit_newline() FL_NO_EXCEPT
FL_NO_INLINE void log_emit(log_kind kind, const char *file, int line, fl::sstream &body) FL_NO_EXCEPT
void log_emit_auto(log_kind kind, const char *file, int line, const log_literal< N > &body) FL_NO_EXCEPT
FL_NO_INLINE void log_emit_literal(log_kind kind, const char *file, int line, const char *body) FL_NO_EXCEPT
Compile-time linker keep-alive hook for a single fl::Bus.
u8 u8 fract8 blur_amount FL_NO_EXCEPT
constexpr int type_rank< T >::value
void configureAsyncLogService(u32 interval_ms, fl::size messages_per_tick) FL_NO_EXCEPT
Configure async logger automatic servicing task.
void async_log_service() FL_NO_EXCEPT
void println(const char *str) FL_NO_EXCEPT
const char * fastled_file_offset(const char *file) FL_NO_EXCEPT
Base definition for an LED controller.
Portable compile-time assertion wrapper.